From d8e60d5a1f5cbee150c1db2ecb8bc6b2e8d725cd Mon Sep 17 00:00:00 2001 From: Marius Gerbershagen Date: Thu, 1 Aug 2024 19:29:29 +0200 Subject: [PATCH] Describe strategies to scan data roots on stack (Emscripten) PR #651 (bdwgc). Update README.emscripten adding a note about the strategies that could be employed in order for the collector to work correctly. * docs/platforms/README.emscripten: Add info about strategies to deal with Emscripten limitation of scanning data roots on stack; update how-to-build instruction. --- docs/platforms/README.emscripten | 28 ++++++++++++++++++++++++---- 1 file changed, 24 insertions(+), 4 deletions(-) diff --git a/docs/platforms/README.emscripten b/docs/platforms/README.emscripten index c869f19ac..15a9df297 100644 --- a/docs/platforms/README.emscripten +++ b/docs/platforms/README.emscripten @@ -1,15 +1,35 @@ -The build system (at least autotools-based) should detect and configure +The build system (at least autotools-based one) should detect and configure emscripten correctly. +Due to the limitations of webassembly, finding all roots on the stack needs +more coordination with the code using the collector than on other platforms. +There are two strategies for dealing with this: + +1. Compile any code relying on the collector with + -sBINARYEN_EXTRA_PASSES='--spill-pointers' option. This instructs the + C compiler to always keep roots in a place where the collector can find + them. This is the simplest option but there is some negative impact on + the code size and performance. + +2. Only trigger the GC at points where it can be guaranteed that there are + no pointers on the stack. When running in the browser, this can be done, + e.g., in the main event loop using emscripten_set_timeout(). Triggering + the collection manually involves calling GC_enable(), GC_gcollect() and + GC_disable() in succession, having also a GC_disable() call at start. + This method does not have a drawback on the code size and performance but + might lead to the garbage collection running too often or, vice versa, + rarely if the timeouts are chosen incorrectly, as a consequence, leading + to the heap growth. + As of now, gctest almost passes, except for the tests that involve a_get(). No thread support for now. No idea how to stop other threads (perhaps we need support from JS side). -How to build: +How to build (LDFLAGS could be omitted depending on the strategy): # source EMSDK first - emconfigure ./configure + LDFLAGS="-sBINARYEN_EXTRA_PASSES='--spill-pointers'" emconfigure ./configure emmake make gctest.html - # point your browser at .libs/gctest.html + # point your browser at .libs/gctest.html or call `node .libs/gctest.js`