From: Ivan Maidanski Date: Mon, 31 Mar 2014 21:25:18 +0000 (+0400) Subject: GC_scratch_alloc code refactoring (and WARN message improvement) X-Git-Tag: gc7_6_0~272 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=ba620ba49ef211a849b21857084674d0305cbf8c;p=gc GC_scratch_alloc code refactoring (and WARN message improvement) * headers.c (GC_scratch_alloc): Remove "register" keyword for "result" local variable; replace tail recursion with a loop; adjust and add comments. * headers.c (GC_scratch_alloc): Adjust message and output requested allocation size in WARN(). * include/private/gc_priv.h (_GC_arrays._scratch_last_end_ptr): Improve comment. --- diff --git a/headers.c b/headers.c index 108adf18..361f19c1 100644 --- a/headers.c +++ b/headers.c @@ -108,7 +108,7 @@ GC_INNER hdr * } /* Routines to dynamically allocate collector data structures that will */ -/* never be freed. */ +/* never be freed. */ static ptr_t scratch_free_ptr = 0; @@ -117,43 +117,48 @@ static ptr_t scratch_free_ptr = 0; GC_INNER ptr_t GC_scratch_alloc(size_t bytes) { - register ptr_t result = scratch_free_ptr; + ptr_t result = scratch_free_ptr; + word bytes_to_get; bytes = ROUNDUP_GRANULE_SIZE(bytes); - scratch_free_ptr += bytes; - if ((word)scratch_free_ptr <= (word)GC_scratch_end_ptr) { - return(result); - } - { - word bytes_to_get = MINHINCR * HBLKSIZE; + for (;;) { + scratch_free_ptr += bytes; + if ((word)scratch_free_ptr <= (word)GC_scratch_end_ptr) { + /* Unallocated space of scratch buffer has enough size. */ + return result; + } + bytes_to_get = MINHINCR * HBLKSIZE; if (bytes_to_get <= bytes) { - /* Undo the damage, and get memory directly */ bytes_to_get = ROUNDUP_PAGESIZE_IF_MMAP(bytes); result = (ptr_t)GET_MEM(bytes_to_get); GC_add_to_our_memory(result, bytes_to_get); + /* Undo scratch free area pointer update; get memory directly. */ scratch_free_ptr -= bytes; if (result != NULL) { + /* Update end point of last obtained area (needed only */ + /* by GC_register_dynamic_libraries for some targets). */ GC_scratch_last_end_ptr = result + bytes; } - return(result); + return result; } bytes_to_get = ROUNDUP_PAGESIZE_IF_MMAP(bytes_to_get); /* for safety */ result = (ptr_t)GET_MEM(bytes_to_get); GC_add_to_our_memory(result, bytes_to_get); - if (result == 0) { - WARN("Out of memory - trying to allocate less\n", 0); - scratch_free_ptr -= bytes; + if (NULL == result) { + WARN("Out of memory - trying to allocate requested amount" + " (%" WARN_PRIdPTR " bytes)...\n", (word)bytes); + scratch_free_ptr -= bytes; /* Undo free area pointer update */ bytes_to_get = ROUNDUP_PAGESIZE_IF_MMAP(bytes); result = (ptr_t)GET_MEM(bytes_to_get); GC_add_to_our_memory(result, bytes_to_get); return result; } + /* Update scratch area pointers and retry. */ scratch_free_ptr = result; GC_scratch_end_ptr = scratch_free_ptr + bytes_to_get; GC_scratch_last_end_ptr = GC_scratch_end_ptr; - return(GC_scratch_alloc(bytes)); } } diff --git a/include/private/gc_priv.h b/include/private/gc_priv.h index c3235421..69c32e9c 100644 --- a/include/private/gc_priv.h +++ b/include/private/gc_priv.h @@ -1140,7 +1140,7 @@ struct _GC_arrays { ptr_t _scratch_end_ptr; ptr_t _scratch_last_end_ptr; /* Used by headers.c, and can easily appear to point to */ - /* heap. */ + /* heap. Also used by GC_register_dynamic_libraries(). */ mse *_mark_stack; /* Limits of stack for GC_mark routine. All ranges */ /* between GC_mark_stack (incl.) and GC_mark_stack_top */