summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorYuta Saito <kateinoigakukun@gmail.com>2022-01-15 23:59:37 +0900
committerYuta Saito <kateinoigakukun@gmail.com>2022-01-19 11:19:06 +0900
commitbf1c4d254beb0e01fac1d9e6cb805de8ec6260eb (patch)
tree5669f945f0f3780c2dde64b13182cb40e3ee146e
parente7fb1fa0414a0c6e43796052c877f317e8e09846 (diff)
downloadruby-bf1c4d254beb0e01fac1d9e6cb805de8ec6260eb.tar.gz
[wasm] gc.c: scan wasm locals and c stack to mark living objects
WebAssembly has function local infinite registers and stack values, but there is no way to scan the values in a call stack for now. This implementation uses Asyncify to spilling out wasm locals into linear memory.
-rw-r--r--gc.c61
1 files changed, 40 insertions, 21 deletions
diff --git a/gc.c b/gc.c
index 2fa4eabc41..b87c72a477 100644
--- a/gc.c
+++ b/gc.c
@@ -30,6 +30,7 @@
#if defined(__wasm__) && !defined(__EMSCRIPTEN__)
# include "wasm/setjmp.h"
+# include "wasm/machine.h"
#else
# include <setjmp.h>
#endif
@@ -6504,7 +6505,45 @@ mark_const_tbl(rb_objspace_t *objspace, struct rb_id_table *tbl)
static void each_stack_location(rb_objspace_t *objspace, const rb_execution_context_t *ec,
const VALUE *stack_start, const VALUE *stack_end, void (*cb)(rb_objspace_t *, VALUE));
-#ifndef __EMSCRIPTEN__
+#if defined(__wasm__)
+
+
+static VALUE *rb_stack_range_tmp[2];
+
+static void
+rb_mark_locations(void *begin, void *end)
+{
+ rb_stack_range_tmp[0] = begin;
+ rb_stack_range_tmp[1] = end;
+}
+
+# if defined(__EMSCRIPTEN__)
+
+static void
+mark_current_machine_context(rb_objspace_t *objspace, rb_execution_context_t *ec)
+{
+ emscripten_scan_stack(rb_mark_locations);
+ each_stack_location(objspace, ec, rb_stack_range_tmp[0], rb_stack_range_tmp[1], gc_mark_maybe);
+
+ emscripten_scan_registers(rb_mark_locations);
+ each_stack_location(objspace, ec, rb_stack_range_tmp[0], rb_stack_range_tmp[1], gc_mark_maybe);
+}
+# else // use Asyncify version
+
+static void
+mark_current_machine_context(rb_objspace_t *objspace, rb_execution_context_t *ec)
+{
+ rb_wasm_scan_stack(rb_mark_locations);
+ each_stack_location(objspace, ec, rb_stack_range_tmp[0], rb_stack_range_tmp[1], gc_mark_maybe);
+
+ rb_wasm_scan_locals(rb_mark_locations);
+ each_stack_location(objspace, ec, rb_stack_range_tmp[0], rb_stack_range_tmp[1], gc_mark_maybe);
+}
+
+# endif
+
+#else // !defined(__wasm__)
+
static void
mark_current_machine_context(rb_objspace_t *objspace, rb_execution_context_t *ec)
{
@@ -6529,26 +6568,6 @@ mark_current_machine_context(rb_objspace_t *objspace, rb_execution_context_t *ec
each_stack_location(objspace, ec, stack_start, stack_end, gc_mark_maybe);
}
-#else
-
-static VALUE *rb_emscripten_stack_range_tmp[2];
-
-static void
-rb_emscripten_mark_locations(void *begin, void *end)
-{
- rb_emscripten_stack_range_tmp[0] = begin;
- rb_emscripten_stack_range_tmp[1] = end;
-}
-
-static void
-mark_current_machine_context(rb_objspace_t *objspace, rb_execution_context_t *ec)
-{
- emscripten_scan_stack(rb_emscripten_mark_locations);
- each_stack_location(objspace, ec, rb_emscripten_stack_range_tmp[0], rb_emscripten_stack_range_tmp[1], gc_mark_maybe);
-
- emscripten_scan_registers(rb_emscripten_mark_locations);
- each_stack_location(objspace, ec, rb_emscripten_stack_range_tmp[0], rb_emscripten_stack_range_tmp[1], gc_mark_maybe);
-}
#endif
static void