1
Fork 0
mirror of https://git.savannah.gnu.org/git/guile.git synced 2025-04-30 03:40:34 +02:00

Add gc_heap_set_allocation_failure_handler

Also wire it up to bdw.
This commit is contained in:
Andy Wingo 2025-04-23 11:42:21 +02:00
parent 1e41f0e093
commit e2b75d302d
5 changed files with 54 additions and 9 deletions

View file

@ -42,6 +42,10 @@ struct gc_heap_roots;
GC_API_ void gc_heap_set_roots(struct gc_heap *heap,
struct gc_heap_roots *roots);
GC_API_ void gc_heap_set_allocation_failure_handler(struct gc_heap *heap,
void* (*)(struct gc_heap*,
size_t));
struct gc_extern_space;
GC_API_ void gc_heap_set_extern_space(struct gc_heap *heap,
struct gc_extern_space *space);

View file

@ -60,6 +60,7 @@ struct gc_heap {
struct gc_finalizer_state *finalizer_state;
gc_finalizer_callback have_finalizers;
void *event_listener_data;
void* (*allocation_failure)(struct gc_heap *, size_t);
};
struct gc_mutator {
@ -116,11 +117,8 @@ allocate_small(void **freelist, size_t idx, enum gc_inline_kind kind) {
size_t bytes = gc_inline_freelist_object_size(idx);
GC_generic_malloc_many(bytes, kind, freelist);
head = *freelist;
if (GC_UNLIKELY (!head)) {
fprintf(stderr, "ran out of space, heap size %zu\n",
GC_get_heap_size());
GC_CRASH();
}
if (GC_UNLIKELY (!head))
return __the_bdw_gc_heap->allocation_failure(__the_bdw_gc_heap, bytes);
}
*freelist = *(void **)(head);
@ -152,14 +150,21 @@ void* gc_allocate_slow(struct gc_mutator *mut, size_t size,
} else {
switch (kind) {
case GC_ALLOCATION_TAGGED:
case GC_ALLOCATION_UNTAGGED_CONSERVATIVE:
return GC_malloc(size);
case GC_ALLOCATION_UNTAGGED_CONSERVATIVE: {
void *ret = GC_malloc(size);
if (GC_LIKELY (ret != NULL))
return ret;
return __the_bdw_gc_heap->allocation_failure(__the_bdw_gc_heap, size);
}
case GC_ALLOCATION_TAGGED_POINTERLESS:
case GC_ALLOCATION_UNTAGGED_POINTERLESS: {
void *ret = GC_malloc_atomic(size);
if (GC_LIKELY (ret != NULL)) {
memset(ret, 0, size);
return ret;
}
return __the_bdw_gc_heap->allocation_failure(__the_bdw_gc_heap, size);
}
default:
GC_CRASH();
}
@ -521,6 +526,22 @@ uint64_t gc_allocation_counter(struct gc_heap *heap) {
return GC_get_total_bytes();
}
static void* allocation_failure(struct gc_heap *heap, size_t size) {
fprintf(stderr, "ran out of space, heap size %zu\n", GC_get_heap_size());
GC_CRASH();
return NULL;
}
static void* oom_fn(size_t nbytes) {
return NULL;
}
void gc_heap_set_allocation_failure_handler(struct gc_heap *heap,
void* (*handler)(struct gc_heap*,
size_t)) {
heap->allocation_failure = handler;
}
int gc_init(const struct gc_options *options, struct gc_stack_addr stack_base,
struct gc_heap **heap, struct gc_mutator **mutator,
struct gc_event_listener event_listener,
@ -607,6 +628,8 @@ int gc_init(const struct gc_options *options, struct gc_stack_addr stack_base,
HEAP_EVENT(init, GC_get_heap_size());
GC_set_on_collection_event(on_collection_event);
GC_set_on_heap_resize(on_heap_resize);
GC_set_oom_fn (oom_fn);
(*heap)->allocation_failure = allocation_failure;
*mutator = add_mutator(*heap);

View file

@ -1121,6 +1121,12 @@ static void* allocation_failure(struct gc_heap *heap, size_t size) {
return NULL;
}
void gc_heap_set_allocation_failure_handler(struct gc_heap *heap,
void* (*handler)(struct gc_heap*,
size_t)) {
heap->allocation_failure = handler;
}
static int
heap_init(struct gc_heap *heap, const struct gc_options *options) {
// *heap is already initialized to 0.

View file

@ -1199,6 +1199,12 @@ static void* allocation_failure(struct gc_heap *heap, size_t size) {
return NULL;
}
void gc_heap_set_allocation_failure_handler(struct gc_heap *heap,
void* (*handler)(struct gc_heap*,
size_t)) {
heap->allocation_failure = handler;
}
static int heap_init(struct gc_heap *heap, const struct gc_options *options) {
// *heap is already initialized to 0.

View file

@ -636,6 +636,12 @@ static void* allocation_failure(struct gc_heap *heap, size_t size) {
return NULL;
}
void gc_heap_set_allocation_failure_handler(struct gc_heap *heap,
void* (*handler)(struct gc_heap*,
size_t)) {
heap->allocation_failure = handler;
}
static int heap_init(struct gc_heap *heap, const struct gc_options *options) {
heap->extern_space = NULL;
heap->pending_ephemerons_size_factor = 0.01;