diff --git a/src/library_pthread.js b/src/library_pthread.js index 15cf1468127ae..1daa32022aad1 100644 --- a/src/library_pthread.js +++ b/src/library_pthread.js @@ -1043,7 +1043,7 @@ var LibraryPThread = { '$runtimeKeepaliveCounter', #endif ], - $invokeEntryPoint: (ptr, arg) => { + $invokeEntryPoint: {{{ asyncIf(ASYNCIFY == 2) }}} (ptr, arg) => { #if PTHREADS_DEBUG dbg(`invokeEntryPoint: ${ptrToString(ptr)}`); #endif @@ -1079,7 +1079,9 @@ var LibraryPThread = { // *ThreadMain(void *arg) form, or try linking with the Emscripten linker // flag -sEMULATE_FUNCTION_POINTER_CASTS to add in emulation for this x86 // ABI extension. - var result = {{{ makeDynCall('pp', 'ptr') }}}(arg); + + var result = {{{ makeDynCall('pp', 'ptr', ASYNCIFY == 2) }}}(arg); + #if STACK_OVERFLOW_CHECK checkStackCookie(); #endif @@ -1098,10 +1100,9 @@ var LibraryPThread = { #endif } #if ASYNCIFY == 2 - Promise.resolve(result).then(finish); -#else - finish(result); + result = await result; #endif + finish(result); }, #if MAIN_MODULE diff --git a/src/parseTools.mjs b/src/parseTools.mjs index 01c3dc242d9e6..ca474affa3978 100644 --- a/src/parseTools.mjs +++ b/src/parseTools.mjs @@ -597,11 +597,12 @@ function charCode(char) { return char.charCodeAt(0); } -function makeDynCall(sig, funcPtr) { +function makeDynCall(sig, funcPtr, promising = false) { assert( !sig.includes('j'), 'Cannot specify 64-bit signatures ("j" in signature string) with makeDynCall!', ); + assert(!(DYNCALLS && promising), 'DYNCALLS cannot be used with JSPI.'); let args = []; for (let i = 1; i < sig.length; ++i) { @@ -672,10 +673,15 @@ Please update to new syntax.`); return `(() => ${dyncall}(${funcPtr}))`; } + let getWasmTableEntry = `getWasmTableEntry(${funcPtr})`; + if (promising) { + getWasmTableEntry = `WebAssembly.promising(${getWasmTableEntry})`; + } + if (needArgConversion) { - return `((${args}) => getWasmTableEntry(${funcPtr}).call(null, ${callArgs}))`; + return `((${args}) => ${getWasmTableEntry}.call(null, ${callArgs}))`; } - return `getWasmTableEntry(${funcPtr})`; + return getWasmTableEntry; } function makeEval(code) { diff --git a/src/runtime_pthread.js b/src/runtime_pthread.js index b57903e086ca2..b9a74ba19e871 100644 --- a/src/runtime_pthread.js +++ b/src/runtime_pthread.js @@ -87,7 +87,7 @@ if (ENVIRONMENT_IS_PTHREAD) { // notified about them. self.onunhandledrejection = (e) => { throw e.reason || e; }; - function handleMessage(e) { + {{{ asyncIf(ASYNCIFY == 2) }}} function handleMessage(e) { try { var msgData = e['data']; //dbg('msgData: ' + Object.keys(msgData)); @@ -198,7 +198,7 @@ if (ENVIRONMENT_IS_PTHREAD) { } try { - invokeEntryPoint(msgData.start_routine, msgData.arg); + {{{ awaitIf(ASYNCIFY == 2) }}} invokeEntryPoint(msgData.start_routine, msgData.arg); } catch(ex) { if (ex != 'unwind') { // The pthread "crashed". Do not call `_emscripten_thread_exit` (which diff --git a/test/core/test_pthread_join_and_asyncify.c b/test/core/test_pthread_join_and_asyncify.c index de358f5aee7b7..d3f24cdf69481 100644 --- a/test/core/test_pthread_join_and_asyncify.c +++ b/test/core/test_pthread_join_and_asyncify.c @@ -13,8 +13,7 @@ EM_ASYNC_JS(int, async_call, (), { return 42; }); -// TODO Remove EMSCRIPTEN_KEEPALIVE when support for async attributes is enabled. -EMSCRIPTEN_KEEPALIVE void *run_thread(void *args) { +void *run_thread(void *args) { int ret = async_call(); assert(ret == 42); return NULL; @@ -22,6 +21,9 @@ EMSCRIPTEN_KEEPALIVE void *run_thread(void *args) { int main() { pthread_t id; + // Test that JSPI works on the main thread. + emscripten_sleep(1); + // Also test that JSPI works on other threads. pthread_create(&id, NULL, run_thread, NULL); printf("joining thread!\n"); pthread_join(id, NULL); diff --git a/test/test_core.py b/test/test_core.py index aa5de85c36a63..b9a8470b5fa7b 100644 --- a/test/test_core.py +++ b/test/test_core.py @@ -8312,7 +8312,7 @@ def test_pthread_join_and_asyncify(self): # TODO Test with ASYNCIFY=1 https://github.com/emscripten-core/emscripten/issues/17552 self.require_jspi() self.do_runf('core/test_pthread_join_and_asyncify.c', 'joining thread!\njoined thread!', - emcc_args=['-sJSPI_EXPORTS=run_thread', + emcc_args=['-sJSPI', '-sEXIT_RUNTIME=1', '-pthread', '-sPROXY_TO_PTHREAD'])