diff options
author | Ivan Maidanski <ivmai@mail.ru> | 2022-01-19 22:07:41 +0300 |
---|---|---|
committer | Ivan Maidanski <ivmai@mail.ru> | 2022-01-19 22:15:37 +0300 |
commit | 9027a0b429ad3f2f3f0eb77210f22c4a1d21ee4a (patch) | |
tree | 57fcc8f153f1e0388b522eaf085e8a868fa7ddb6 /mach_dep.c | |
parent | 26b2fb160670314200c6a5792b40ee21b585cf8f (diff) | |
download | bdwgc-9027a0b429ad3f2f3f0eb77210f22c4a1d21ee4a.tar.gz |
Support malloc redirection on E2K (single-threaded mode only)
Issue #413 (bdwgc).
* include/private/gc_priv.h [E2K_USE_SCRATCH] (GC_e2k_ps_buffer,
GC_e2k_ps_capacity): Define macro.
* include/private/gcconfig.h [E2K && LINUX && REDIRECT_MALLOC
&& !GC_LINUX_THREADS] (E2K_USE_SCRATCH): Likewise.
* include/private/gc_priv.h [E2K_USE_SCRATCH] (_GC_arrays): Add
_e2k_ps_buffer and _e2k_ps_capacity fields; add comment.
* include/private/gcconfig.h [E2K && LINUX && REDIRECT_MALLOC
&& GC_LINUX_THREADS && !CPPCHECK]: Issue an error directive.
* mach_dep.c [E2K && E2K_USE_SCRATCH] (GC_free_procedure_stack): Do not
call free(); assert that buf is non-null but GC_e2k_ps_buffer is null;
set GC_e2k_ps_buffer to buf.
* mach_dep.c [E2K && E2K_USE_SCRATCH] (GC_get_procedure_stack):
Initialize buf local variable to GC_e2k_ps_buffer; initialize buf_sz
local variable to GC_e2k_ps_capacity; clear GC_e2k_ps_buffer value;
change FIXME item to TODO one; pass buf to GC_scratch_recycle_no_gww()
instead of free(); call GC_scratch_alloc() instead of malloc().
* mach_dep.c [E2K && LOG_E2K_ALLOCS] (GC_get_procedure_stack): Call
GC_log_printf() to print buf_sz, new_sz and GC_gc_no values if errno
is ENOMEM.
* mach_dep.c [E2K] (GC_get_procedure_stack): Ensure buf_sz<new_sz
(instead of buf_sz!=new_sz) after the loop; return new_sz instead of
buf_sz.
Diffstat (limited to 'mach_dep.c')
-rw-r--r-- | mach_dep.c | 43 |
1 files changed, 35 insertions, 8 deletions
@@ -67,15 +67,29 @@ } while (0) GC_INNER void GC_free_procedure_stack(ptr_t buf) { - free(buf); +# ifdef E2K_USE_SCRATCH + GC_ASSERT(buf != NULL); + GC_ASSERT(NULL == GC_e2k_ps_buffer); + GC_e2k_ps_buffer = buf; /* the buffer could be reused */ +# else + free(buf); +# endif } GC_INNER size_t GC_get_procedure_stack(ptr_t *buf_ptr) { word ps; - ptr_t buf = NULL; - word buf_sz = 0; + ptr_t buf; + word buf_sz; word new_sz = 0; +# ifdef E2K_USE_SCRATCH + buf = GC_e2k_ps_buffer; + buf_sz = (word)GC_e2k_ps_capacity; + GC_e2k_ps_buffer = NULL; /* indicate the buffer is in use */ +# else + buf = NULL; + buf_sz = 0; +# endif get_stack_index(&ps); for (;;) { int res = syscall(__NR_access_hw_stacks, E2K_READ_PROCEDURE_STACK, @@ -83,9 +97,22 @@ if (res != -1) break; if (ENOMEM == errno && buf_sz != new_sz) { - /* FIXME: use GC_scratch_alloc to support malloc redirection? */ - free(buf); - buf = malloc((size_t)new_sz); +# ifdef LOG_E2K_ALLOCS + GC_log_printf("GC_get_procedure_stack(): free/alloc %lu/%lu bytes," + " GC #%lu\n", + (unsigned long)buf_sz, (unsigned long)new_sz, + (unsigned long)GC_gc_no); +# endif +# ifdef E2K_USE_SCRATCH + GC_ASSERT(new_sz > (word)GC_e2k_ps_capacity); + GC_scratch_recycle_no_gww(buf, GC_e2k_ps_capacity); + buf = GC_scratch_alloc((size_t)new_sz); + GC_e2k_ps_capacity = (size_t)new_sz; + /* TODO: support malloc redirection if multi-threaded */ +# else + free(buf); + buf = malloc((size_t)new_sz); +# endif if (NULL == buf) ABORT_ARG1("Could not allocate memory for procedure stack", ", %lu bytes requested", (unsigned long)new_sz); @@ -100,13 +127,13 @@ get_stack_index(&ps); } - if (buf_sz != new_sz) + if (buf_sz < new_sz) ABORT_ARG2("Buffer size mismatch while reading procedure stack", ": buf_sz= %lu, new_sz= %lu", (unsigned long)buf_sz, (unsigned long)new_sz); GC_ASSERT(buf != NULL); *buf_ptr = buf; - return (size_t)buf_sz; + return (size_t)new_sz; } ptr_t GC_save_regs_in_stack(void) { |