Branch: refs/heads/webkitglib/2.50 Home: https://github.com/WebKit/WebKit Commit: 9c732f1b504b2cbfd673e41cfad35a6fcf7b6424 https://github.com/WebKit/WebKit/commit/9c732f1b504b2cbfd673e41cfad35a6fcf7b6424 Author: Vassili Bykov <v_by...@apple.com> Date: 2025-08-29 (Fri, 29 Aug 2025)
Changed paths: A JSTests/wasm/stress/wasm-try-table-catching-backwards.js M Source/JavaScriptCore/llint/InPlaceInterpreter64.asm M Source/JavaScriptCore/wasm/WasmIPIntGenerator.cpp M Source/JavaScriptCore/wasm/WasmIPIntGenerator.h Log Message: ----------- Cherry-pick 298437@main (666190cff29d). https://bugs.webkit.org/show_bug.cgi?id=292599 Segmentation fault in JSC coming from throwWasmToJSException https://bugs.webkit.org/show_bug.cgi?id=292599 rdar://150752978 Reviewed by Daniel Liu and Yusuke Suzuki. The failure is triggered by the fact that in the Wasm code `$label0` comes before the `try_table` that uses it as a catch label. A test case with a less random and verbose example reproducing the issue is included in the patch. The "normal" expected behavior for the example in the bug report is to loop infinitely. The `call` instruction inside the `try_table` block throws an exception on return because `f0` (a JS function) returned by the call can't be marshaled into a `funcref` required by the import signature. The control transfer on a caught exception is implemented as a "ghost" `block` instruction, which is to say that there is no actual `block` instruction in the code, but the exception logic jumps to the `block` instruction handler while `PC` is pointing at the `try_table` and `MC` at a `BlockMetadata` structure embedded in the `try_table` metadata block. The deltas in the metadata are negative because control is transferred to `$label0` located earlier in the code. The problem is that the deltas are 32-bit values loaded into `w0` and `w1`. The values are then not sign-extended to the full 64-bit width before being added to `PC` and `MC` as `x0` and `x1`. As a result, they work as very large positive values and make `PC` and `MC` point at random data. That explains the randomness of failure modes. If `PC` happens to point at a zero byte, the byte works as an `unreachable` instruction, causing an exception exit. Other values are treated as random instructions with random metadata, typically triggering a segfault. The patch changes the implementation of `block` to sign-extend the deltas. As far as I understand them, other instructions using `BlockMetadata` deltas only ever skip forward and never require sign extension, but I added comments to make that assumption explicit. I also changed the type of `BlockMetadata` fields to `int32_t` to raise awareness of their nature. Originally-landed-as: 289651.509@safari-7621-branch (e5dbc8e03d41). rdar://157792804 Canonical link: https://commits.webkit.org/298437@main Canonical link: https://commits.webkit.org/298234.74@webkitglib/2.50 To unsubscribe from these emails, change your notification settings at https://github.com/WebKit/WebKit/settings/notifications _______________________________________________ webkit-changes mailing list webkit-changes@lists.webkit.org https://lists.webkit.org/mailman/listinfo/webkit-changes