Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 10 additions & 0 deletions system/lib/libcxxabi/src/cxa_guard_impl.h
Original file line number Diff line number Diff line change
Expand Up @@ -436,6 +436,16 @@ void PlatformFutexWake(int* addr) {
__tsan_release(addr);
syscall(SYS_futex, addr, WAKE, INT_MAX);
}
#elif defined(__EMSCRIPTEN__) && defined(__EMSCRIPTEN_SHARED_MEMORY__)
// WASM Workers: pthread stubs are noops, making GlobalMutex broken
// (non-atomic read-then-write allows double initialization).
// InitByteFutex uses atomic CAS for correct single initialization.
// Wait/wake are no-ops — losers spin in the CAS retry loop.
// Cannot use memory.atomic.wait32 (traps on the main browser thread).
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This seems like something we should be using emscripten_futex_wait and emscripten_futex_wake for.. although I don't think those are currently available in wasm workers.

They probably should be.

It looks like wasm workers does define the emscripten_atomic_wait_u32 and emscripten_atomic_wait_u64 but they are just wrappers arount the __builtin_wasm_memory_atomic_xx functions so cannot be used on the main thread.

@juj @cwoffenden WDYT, should we make the higher level (and safe-to-call) emscripten_futex_wait API available in wasm workers and use it here?

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I agree that a locking solution would be useful, especially one that works with the main thread and various workers. I watched the current state of locks bite the devs here new to Emscripten.

It's not something I have time to look at right now (and for the next months).

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have a PR up to enable this API in wasm workers: #26325

// In practice, contention on a single guard is rare and the spin is
// bounded by the static constructor duration (typically sub-microsecond).
void PlatformFutexWait(int*, int) {}
void PlatformFutexWake(int*) {}
#else
constexpr void (*PlatformFutexWait)(int*, int) = nullptr;
constexpr void (*PlatformFutexWake)(int*) = nullptr;
Expand Down
2 changes: 2 additions & 0 deletions tools/system_libs.py
Original file line number Diff line number Diff line change
Expand Up @@ -1648,6 +1648,8 @@ def get_cflags(self):
cflags = super().get_cflags()
if not self.is_mt and not self.is_ww:
cflags.append('-D_LIBCXXABI_HAS_NO_THREADS')
elif self.is_ww:
cflags.append('-D_LIBCXXABI_USE_FUTEX')
match self.eh_mode:
case Exceptions.NONE:
cflags.append('-D_LIBCXXABI_NO_EXCEPTIONS')
Expand Down
Loading