* Make sure the object free list for size gran (in granules) is not empty. * Return a pointer to the first object on the free list. * The object MUST BE REMOVED FROM THE FREE LIST BY THE CALLER. * Assumes we hold the allocator lock and signals are disabled. * */
| 985 | * |
| 986 | */ |
| 987 | ptr_t GC_allocobj(size_t gran, int kind) |
| 988 | { |
| 989 | void ** flh = &(GC_obj_kinds[kind].ok_freelist[gran]); |
| 990 | GC_bool tried_minor = FALSE; |
| 991 | |
| 992 | if (gran == 0) return(0); |
| 993 | |
| 994 | while (*flh == 0) { |
| 995 | ENTER_GC(); |
| 996 | /* Do our share of marking work */ |
| 997 | if(TRUE_INCREMENTAL) GC_collect_a_little_inner(1); |
| 998 | /* Sweep blocks for objects of this size */ |
| 999 | GC_continue_reclaim(gran, kind); |
| 1000 | EXIT_GC(); |
| 1001 | if (*flh == 0) { |
| 1002 | GC_new_hblk(gran, kind); |
| 1003 | } |
| 1004 | if (*flh == 0) { |
| 1005 | ENTER_GC(); |
| 1006 | if (GC_incremental && GC_time_limit == GC_TIME_UNLIMITED |
| 1007 | && ! tried_minor ) { |
| 1008 | GC_collect_a_little_inner(1); |
| 1009 | tried_minor = TRUE; |
| 1010 | } else { |
| 1011 | if (!GC_collect_or_expand((word)1,FALSE)) { |
| 1012 | EXIT_GC(); |
| 1013 | return(0); |
| 1014 | } |
| 1015 | } |
| 1016 | EXIT_GC(); |
| 1017 | } |
| 1018 | } |
| 1019 | /* Successful allocation; reset failure count. */ |
| 1020 | GC_fail_count = 0; |
| 1021 | |
| 1022 | return(*flh); |
| 1023 | } |
no test coverage detected