diff --git a/src/lib/libwasm_worker.js b/src/lib/libwasm_worker.js index c77a1ba5c0395..5c957cd362d11 100644 --- a/src/lib/libwasm_worker.js +++ b/src/lib/libwasm_worker.js @@ -135,6 +135,11 @@ addToLibrary({ writeStackCookie(); #endif +#if EMBIND + // Embind must initialize itself on all threads, as it generates support JS. + __embind_initialize_bindings(); +#endif + #if AUDIO_WORKLET // Audio Worklets do not have postMessage()ing capabilities. if (typeof AudioWorkletGlobalScope === 'undefined') { diff --git a/test/embind/test_embind_wasm_workers.cpp b/test/embind/test_embind_wasm_workers.cpp new file mode 100644 index 0000000000000..c6ea42859078a --- /dev/null +++ b/test/embind/test_embind_wasm_workers.cpp @@ -0,0 +1,34 @@ +#include +#include +#include +#include +#include +#include + +using namespace emscripten; + +int foo() { + return 42; +} + +void do_exit() { + emscripten_out("do_exit"); + emscripten_terminate_all_wasm_workers(); +} + +void run_in_worker() { + emscripten_out("Hello from Wasm Worker!"); + int result = val::module_property("foo")().as(); + assert(result == 42); + emscripten_wasm_worker_post_function_v(EMSCRIPTEN_WASM_WORKER_ID_PARENT, do_exit); +} + +int main() { + emscripten_wasm_worker_t worker = emscripten_malloc_wasm_worker(/*stackSize: */1024); + emscripten_wasm_worker_post_function_v(worker, run_in_worker); + emscripten_exit_with_live_runtime(); +} + +EMSCRIPTEN_BINDINGS(xxx) { + function("foo", &foo); +} diff --git a/test/embind/test_embind_wasm_workers.out b/test/embind/test_embind_wasm_workers.out new file mode 100644 index 0000000000000..9bc4e0f4d447e --- /dev/null +++ b/test/embind/test_embind_wasm_workers.out @@ -0,0 +1,2 @@ +Hello from Wasm Worker! +do_exit diff --git a/test/test_core.py b/test/test_core.py index 6f983653f2731..f8d360a4b2a0b 100644 --- a/test/test_core.py +++ b/test/test_core.py @@ -7588,6 +7588,10 @@ def test_embind_no_rtti_followed_by_rtti(self): self.emcc_args += ['-lembind', '-fno-rtti', '-frtti'] self.do_run(src, '418\ndotest returned: 42\n') + @no_asan('ASan does not support WASM_WORKERS') + def test_embind_wasm_workers(self): + self.do_run_in_out_file_test('embind/test_embind_wasm_workers.cpp', emcc_args=['-lembind', '-sWASM_WORKERS']) + @parameterized({ '': ('DEFAULT', False), 'all': ('ALL', False), diff --git a/tools/link.py b/tools/link.py index 03e167b47f7db..f4185731f437b 100644 --- a/tools/link.py +++ b/tools/link.py @@ -516,9 +516,6 @@ def setup_pthreads(): '_emscripten_thread_crashed', ] - if settings.EMBIND: - settings.REQUIRED_EXPORTS.append('_embind_initialize_bindings') - if settings.MAIN_MODULE: settings.REQUIRED_EXPORTS += [ '_emscripten_dlsync_self', @@ -1381,6 +1378,8 @@ def limit_incoming_module_api(): # Workaround for embind+LTO issue: # https://github.com/emscripten-core/emscripten/issues/21653 settings.REQUIRED_EXPORTS.append('__getTypeName') + if settings.PTHREADS or settings.WASM_WORKERS: + settings.REQUIRED_EXPORTS.append('_embind_initialize_bindings') if options.emit_tsd: settings.EMIT_TSD = True