From a3f6f600c60ecd9d1ae54e5b76cae1055dfe59bd Mon Sep 17 00:00:00 2001 From: Kleis Auke Wolthuizen Date: Mon, 4 May 2026 12:43:07 +0200 Subject: [PATCH 1/3] Micro-optimize timed wait loops. NFC --- system/lib/pthread/library_pthread.c | 11 +++++------ system/lib/pthread/proxying_legacy.c | 27 +++++++++++---------------- 2 files changed, 16 insertions(+), 22 deletions(-) diff --git a/system/lib/pthread/library_pthread.c b/system/lib/pthread/library_pthread.c index a89425874b113..0a47e1a4dd863 100644 --- a/system/lib/pthread/library_pthread.c +++ b/system/lib/pthread/library_pthread.c @@ -85,18 +85,17 @@ void emscripten_thread_sleep(double msecs) { __pthread_testcancel(); if (msecs > 0) { uint32_t dummyZeroAddress = 0; - double start = emscripten_get_now(); - double elapsed = 0; - while (elapsed < msecs) { + double target = emscripten_get_now() + msecs; + do { emscripten_conditional_set_current_thread_status(EM_THREAD_STATUS_RUNNING, EM_THREAD_STATUS_SLEEPING); - emscripten_futex_wait(&dummyZeroAddress, 0, msecs - elapsed); + emscripten_futex_wait(&dummyZeroAddress, 0, msecs); emscripten_conditional_set_current_thread_status(EM_THREAD_STATUS_SLEEPING, EM_THREAD_STATUS_RUNNING); emscripten_current_thread_process_queued_calls(); __pthread_testcancel(); - elapsed = emscripten_get_now() - start; - } + msecs = target - emscripten_get_now(); + } while (msecs > 0); } } diff --git a/system/lib/pthread/proxying_legacy.c b/system/lib/pthread/proxying_legacy.c index b9c0e148ba8a9..0d3d68f11e503 100644 --- a/system/lib/pthread/proxying_legacy.c +++ b/system/lib/pthread/proxying_legacy.c @@ -530,24 +530,19 @@ em_queued_call* emscripten_async_waitable_run_in_main_runtime_thread_( } EMSCRIPTEN_RESULT emscripten_wait_for_call_v(em_queued_call* call, double timeoutMSecs) { + emscripten_set_current_thread_status(EM_THREAD_STATUS_WAITPROXY); + int r; + double target = emscripten_get_now() + timeoutMSecs; + do { + r = -emscripten_futex_wait(&call->operationDone, 0, timeoutMSecs); - int done = atomic_load(&call->operationDone); - if (!done) { - double now = emscripten_get_now(); - double waitEndTime = now + timeoutMSecs; - emscripten_set_current_thread_status(EM_THREAD_STATUS_WAITPROXY); - while (!done && now < waitEndTime) { - r = emscripten_futex_wait(&call->operationDone, 0, waitEndTime - now); - done = atomic_load(&call->operationDone); - now = emscripten_get_now(); - } - emscripten_set_current_thread_status(EM_THREAD_STATUS_RUNNING); - } - if (done) - return EMSCRIPTEN_RESULT_SUCCESS; - else - return EMSCRIPTEN_RESULT_TIMED_OUT; + timeoutMSecs = target - emscripten_get_now(); + } while (r == ETIMEDOUT && timeoutMSecs > 0); + + emscripten_set_current_thread_status(EM_THREAD_STATUS_RUNNING); + + return r == ETIMEDOUT ? EMSCRIPTEN_RESULT_TIMED_OUT : EMSCRIPTEN_RESULT_SUCCESS; } EMSCRIPTEN_RESULT emscripten_wait_for_call_i( From ab6b2bf61b7eb53b281fb30c76b359a11a291b7c Mon Sep 17 00:00:00 2001 From: Kleis Auke Wolthuizen Date: Mon, 4 May 2026 19:10:07 +0200 Subject: [PATCH 2/3] Incorporate feedback --- system/lib/pthread/proxying_legacy.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/system/lib/pthread/proxying_legacy.c b/system/lib/pthread/proxying_legacy.c index 0d3d68f11e503..664e2a299ec8d 100644 --- a/system/lib/pthread/proxying_legacy.c +++ b/system/lib/pthread/proxying_legacy.c @@ -530,6 +530,10 @@ em_queued_call* emscripten_async_waitable_run_in_main_runtime_thread_( } EMSCRIPTEN_RESULT emscripten_wait_for_call_v(em_queued_call* call, double timeoutMSecs) { + int done = atomic_load(&call->operationDone); + if (done) + return EMSCRIPTEN_RESULT_SUCCESS; + emscripten_set_current_thread_status(EM_THREAD_STATUS_WAITPROXY); int r; @@ -538,7 +542,7 @@ EMSCRIPTEN_RESULT emscripten_wait_for_call_v(em_queued_call* call, double timeou r = -emscripten_futex_wait(&call->operationDone, 0, timeoutMSecs); timeoutMSecs = target - emscripten_get_now(); - } while (r == ETIMEDOUT && timeoutMSecs > 0); + } while (r == EINTR && timeoutMSecs > 0); emscripten_set_current_thread_status(EM_THREAD_STATUS_RUNNING); From 79f46a59188381a31f5cd57ca4047eec24d61ac2 Mon Sep 17 00:00:00 2001 From: Kleis Auke Wolthuizen Date: Mon, 4 May 2026 19:34:33 +0200 Subject: [PATCH 3/3] Remove unnecessary `atomic_load()` --- system/lib/pthread/proxying_legacy.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/system/lib/pthread/proxying_legacy.c b/system/lib/pthread/proxying_legacy.c index 664e2a299ec8d..f6dae33fef15f 100644 --- a/system/lib/pthread/proxying_legacy.c +++ b/system/lib/pthread/proxying_legacy.c @@ -530,9 +530,9 @@ em_queued_call* emscripten_async_waitable_run_in_main_runtime_thread_( } EMSCRIPTEN_RESULT emscripten_wait_for_call_v(em_queued_call* call, double timeoutMSecs) { - int done = atomic_load(&call->operationDone); - if (done) + if (call->operationDone) { return EMSCRIPTEN_RESULT_SUCCESS; + } emscripten_set_current_thread_status(EM_THREAD_STATUS_WAITPROXY);