diff --git a/py/gc.c b/py/gc.c index b4822ee29..a9dd2aa4b 100644 --- a/py/gc.c +++ b/py/gc.c @@ -326,6 +326,7 @@ machine_uint_t gc_nbytes(void *ptr_in) { return 0; } +#if 0 // use this realloc for now, one below is broken void *gc_realloc(void *ptr, machine_uint_t n_bytes) { machine_uint_t n_existing = gc_nbytes(ptr); @@ -342,8 +343,7 @@ void *gc_realloc(void *ptr, machine_uint_t n_bytes) { return ptr2; } } - -#if 0 +#else void *gc_realloc(void *ptr_in, machine_uint_t n_bytes) { void *ptr_out = NULL; machine_uint_t block = 0; @@ -360,21 +360,22 @@ void *gc_realloc(void *ptr_in, machine_uint_t n_bytes) { byte block_type; machine_uint_t n_free = 0; machine_uint_t n_blocks = 1; /* counting HEAD block */ + machine_uint_t max_block = gc_alloc_table_byte_len * BLOCKS_PER_ATB; /* get the number of consecutive tail blocks and the number of free blocks after last tail block */ - // XXX make sure we stop if we get to end of heap - do { - block_type = ATB_GET_KIND(block + n_blocks + n_free); + /* stop if we reach (or are at) end of heap */ + while ((block + n_blocks + n_free) < max_block + /* stop as soon as we find enough blocks for n_bytes */ + && (n_bytes > ((n_blocks+n_free) * BYTES_PER_BLOCK)) + /* stop if block is HEAD */ + && (block_type = ATB_GET_KIND(block + n_blocks + n_free)) != AT_HEAD) { switch (block_type) { case AT_FREE: n_free++; break; case AT_TAIL: n_blocks++; break; default: break; } - /* stop as soon as we find enough blocks for n_bytes */ - // XXX check for n_bytes is wrong since we don't include n_free - } while (block_type != AT_HEAD && (n_bytes > (n_blocks * BYTES_PER_BLOCK))); - + } /* number of allocated bytes */ machine_uint_t n_existing = n_blocks * BYTES_PER_BLOCK; @@ -387,8 +388,7 @@ void *gc_realloc(void *ptr_in, machine_uint_t n_bytes) { } /* check if we can expand in place */ - // XXX disabled for now - } else if (0 && n_bytes <= (n_existing + (n_free * BYTES_PER_BLOCK))) { + } else if (n_bytes <= (n_existing + (n_free * BYTES_PER_BLOCK))) { /* number of blocks needed to expand +1 if there's a remainder */ // XXX this has a bug, but don't know why; try: l=[i for i in range(1000)]; for i in l: print(i/3) machine_uint_t n_diff = ( n_bytes - n_existing)/BYTES_PER_BLOCK+ @@ -397,7 +397,7 @@ void *gc_realloc(void *ptr_in, machine_uint_t n_bytes) { DEBUG_printf("gc_realloc: expanding " UINT_FMT " blocks (" UINT_FMT " bytes) to " UINT_FMT " blocks (" UINT_FMT " bytes)\n", n_existing/BYTES_PER_BLOCK, n_existing, n_existing/BYTES_PER_BLOCK+n_diff, n_existing + n_diff*BYTES_PER_BLOCK); - /* mark rest of blocks as used tail */ + /* mark rest of blocks as used tail */ for (machine_uint_t bl = block + n_blocks; bl < (block + n_blocks + n_diff); bl++) { ATB_FREE_TO_TAIL(bl); } @@ -405,7 +405,7 @@ void *gc_realloc(void *ptr_in, machine_uint_t n_bytes) { /* try to find a new contiguous chain */ } else if ((ptr_out = gc_alloc(n_bytes)) != NULL) { - DEBUG_printf("gc_realloc: allocated new block \n"); + DEBUG_printf("gc_realloc: allocating new block \n"); memcpy(ptr_out, ptr_in, n_existing); gc_free(ptr_in); } @@ -413,6 +413,7 @@ void *gc_realloc(void *ptr_in, machine_uint_t n_bytes) { return ptr_out; } + #endif void gc_dump_info() {