[wasm2c] Fix exception testing on macOS#2716
Conversation
This commit addresses the assertion failures during exception testing in `wasm2c` on macOS: `Assertion failed: (!(ss.ss_flags & SS_ONSTACK) && "attempt to deallocate altstack while in use")` Exception handling in wasm2c uses `wasm_rt_try(target)` which mapped to `sigsetjmp(buf, 1)`. However, on macOS (XNU), performing nested `sigsetjmp(..., 1)` and `siglongjmp` across threads with an allocated alternate signal stack can erroneously cause the kernel to preserve the `SS_ONSTACK` flag in the thread state, even when the exception did not originate from the signal handler. Since WebAssembly exception handling relies strictly on `setjmp`/`longjmp` for control flow and does not need to restore signal masks (unlike stack exhaustion traps, which do need the mask to unblock `SIGSEGV`), the fix is to simply avoid saving the signal mask for exception boundaries. We split `WASM_RT_SETJMP_SETBUF` into two variants: - `WASM_RT_SETJMP_TRAP_SETBUF`: Uses `sigsetjmp(buf, 1)` for traps (safely handles `SIGSEGV`). - `WASM_RT_SETJMP_EXN_SETBUF`: Uses `sigsetjmp(buf, 0)` for Wasm exceptions (bypasses `SS_ONSTACK` bug). This also reverts commit 74cc83c (which temporarily disabled `macos-latest` in CI), as the tests now pass successfully. Fixes WebAssembly#2654
|
CC @sbc100 This is 99% vibe coded. I know ~0 C++. I asked gemini to investigate the failure and see if we could resolve it carefully. Gemini wrote the commit message. Zero offence will be taken if this is closed w/ prejudice. |
|
Thanks for working on this! Is there an actual upstream macOS kernel bug for this maybe? |
|
I saw zero info on anything upstream. Just the same issue being hit in Go. |
|
I tried to leave enough breadcrumbs... |
|
Here's the gemini-CLI dump of the explanation of this issue. Again, this is 99% vibes. Core macOS Bug: XNU Kernel
|
There was a problem hiding this comment.
@sbc100 I don't know what the policy in this project is AI generated submissions, so I'll let you approve this PR if needed. I haven't checked the source of the bug, but if is as described, the spirit of this fix looks reasonable modulo comments
|
Thanks @kevmoo and AI for the fix :) Thanks @shravanrn for taking a second a look. Good to see the rather nasty OS bug fixed (worked around). |
This commit addresses the assertion failures during exception testing
in
wasm2con macOS:Assertion failed: (!(ss.ss_flags & SS_ONSTACK) && "attempt to deallocate altstack while in use")Exception handling in wasm2c uses
wasm_rt_try(target)which mappedto
sigsetjmp(buf, 1). However, on macOS (XNU), performing nestedsigsetjmp(..., 1)andsiglongjmpacross threads with an allocatedalternate signal stack can erroneously cause the kernel to preserve the
SS_ONSTACKflag in the thread state, even when the exception did notoriginate from the signal handler.
Since WebAssembly exception handling relies strictly on
setjmp/longjmpfor control flow and does not need to restore signal masks (unlike stack
exhaustion traps, which do need the mask to unblock
SIGSEGV), the fixis to simply avoid saving the signal mask for exception boundaries.
We split
WASM_RT_SETJMP_SETBUFinto two variants:WASM_RT_SETJMP_TRAP_SETBUF: Usessigsetjmp(buf, 1)for traps (safely handlesSIGSEGV).WASM_RT_SETJMP_EXN_SETBUF: Usessigsetjmp(buf, 0)for Wasm exceptions (bypassesSS_ONSTACKbug).This also reverts commit 74cc83c
(which temporarily disabled
macos-latestin CI), as the tests nowpass successfully.
Fixes #2654