예제 #1
0
U8_EXPORT
/* u8_grow_input_stream:
     Arguments: a pointer to an input stream and max buffer size
     Returns: the size of the new buffer

     Doubles the size of the input buffer
*/
ssize_t u8_grow_input_stream(struct U8_INPUT *in,ssize_t to_size)
{
  int owns_buf = ((in->u8_streaminfo)&(U8_STREAM_OWNS_BUF));
  size_t max = in->u8_bufsz, 
    bytes_buffered = in->u8_inlim - in->u8_read,
    bytes_read = in->u8_read - in->u8_inbuf;
  size_t new_max = ((max>=U8_BUF_THROTTLE_POINT)?
                    (max+(U8_BUF_THROTTLE_POINT/2)):
                    (max*2));

  if (to_size<0) to_size=new_max;
  else if ((to_size+U8_BUF_MIN_GROW)<max)
    return max;
  else {}
  while (new_max<to_size) 
    new_max = ((new_max>=U8_BUF_THROTTLE_POINT)?
               (new_max+(U8_BUF_THROTTLE_POINT/2)):
               (new_max*2));
  u8_byte *buf = in->u8_inbuf, *new_buf=NULL;
  /* Reset buffer */
  if (bytes_read>0) {
    memcpy(buf, in->u8_read, bytes_buffered);
    in->u8_read = buf;
    in->u8_inlim -= bytes_read;
    *(in->u8_inlim) = '\0';}
  /* Try to allocate a new buffer */
  new_buf=(owns_buf)?(u8_realloc(buf,new_max)):(u8_malloc(new_max));
  if (new_buf==NULL) {
    size_t shrink_by = (new_max-max)/16;
    while (new_buf==NULL) {
      /* The alloc/realloc call failed, so try smaller sizes */
      errno=0; /* Reset errno */
      /* Shrink until it works or the buffer size is smaller than the
         current value */
      new_max=new_max-shrink_by;
      if (new_max<=max) {
        u8_log(LOGCRIT,"MallocFailed/grow_output",
               "Couldn't grow buffer for input stream");
        return max;}
      u8_log(LOGCRIT,"MemoryRestricted",
             "Couldn't grow u8_input_stream buffer (x%llx) to %lld bytes, trying %lld",
             (long long) in,new_max+shrink_by,new_max);
      new_buf=(owns_buf)?(u8_realloc(in->u8_inbuf,new_max)):
        (u8_malloc(new_max));}}
  if (!(owns_buf)) {
    memcpy(new_buf,buf,bytes_buffered);
    in->u8_streaminfo|=U8_STREAM_OWNS_BUF;}
  in->u8_inbuf=new_buf;
  in->u8_read=new_buf;
  in->u8_inlim=new_buf+bytes_buffered;
  in->u8_bufsz=new_max;
  return new_max;
}
예제 #2
0
U8_EXPORT void *u8_contour_realloc(u8_contour c,void *ptr,size_t new_size)
{
  u8_contour scan=c;
  while (scan) {
    if (scan->u8c_n_blocks) {
      void **blocks=scan->u8c_blocks;
      /* Intentionally scanning backwards */
      int i=scan->u8c_n_blocks-1;
      while (i>=0)
        if (blocks[i]==ptr) {
          void *newptr=u8_realloc(ptr,new_size);
          blocks[i]=newptr;
          return newptr;}
        else i++;}
    scan=scan->u8c_outer_contour;}
  /* Should this err or warn? */
  return u8_realloc(ptr,new_size);
}
예제 #3
0
U8_EXPORT void u8_grow_contour(u8_contour c)
{
  if (c->u8c_max_blocks==0) {
    c->u8c_blocks=u8_malloc(U8_CONTOUR_INIT_N_BLOCKS*sizeof(void *));
    c->u8c_max_blocks=U8_CONTOUR_INIT_N_BLOCKS;}
  else if ((c->u8c_flags)&(U8_CONTOUR_BLOCKS_MALLOCD)) {
    int new_max=c->u8c_max_blocks*2;
    void **new_blocks=u8_realloc(c->u8c_blocks,new_max*sizeof(void *));
    c->u8c_blocks=new_blocks;
    c->u8c_max_blocks=new_max;}
  else {
    int new_max=c->u8c_max_blocks*2;
    void **new_blocks=u8_malloc(new_max*sizeof(void *));
    memcpy(new_blocks,c->u8c_blocks,sizeof(void *)*(c->u8c_n_blocks));
    c->u8c_blocks=new_blocks;
    c->u8c_max_blocks=new_max;}
}