Skip to content
This repository has been archived by the owner on Jul 12, 2024. It is now read-only.

Fix #32: Implement exception handling. #38

Merged
merged 9 commits into from
Mar 27, 2024

Conversation

sjrd
Copy link
Collaborator

@sjrd sjrd commented Mar 26, 2024

Unfortunately, we cannot write unit tests for TryCatch and TryFinally yet. The latest Node.js nightly build is still using an old version of v8 that does not support the latest spec for Wasm exception handling. However, it possible to run the sample from a web browser when it contains try..catch and try..finally.

We do not use the tags in any translation yet.
That one is not a case class, and therefore does not depend on
plenty of things from the scalalib that we do not support yet.
Because the latest nightly of Node.js does not support the latest
specification for Wasm exceptions yet.
Including adding all the missing instructions and types for the
latest specification of exception handling.
Currently, it does not correctly handle `Labeled/Return` pairs that
cross its boundary.
@sjrd sjrd requested a review from tanishiking March 26, 2024 17:14
@sjrd sjrd changed the title Implement exception handling. Fix #32: Implement exception handling. Mar 26, 2024
@sjrd sjrd linked an issue Mar 26, 2024 that may be closed by this pull request
Copy link
Owner

@tanishiking tanishiking left a comment

Choose a reason for hiding this comment

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

LGTM!

Thank you for updating the EH-spec related stuffs, I didn't know that there was an update on the spec recently WebAssembly/exception-handling#283 😅

IIUC, this implementation is able to catch the exception thrown from JS like

JS throws something else -> Scala.js catches it wrapped in a js.JavaScriptException
https://www.scala-js.org/doc/interoperability/exceptions.html

am I right?

val resultLocals = resultType.map(fctx.addSyntheticLocal(_))

fctx.block() { doneLabel =>
fctx.block(Types.WasmExnRef) { catchLabel =>
Copy link
Owner

Choose a reason for hiding this comment

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

(note) If the inner try block throws an uncaught exception, jump to the outside of this block (skipping ref.null exn)

Can we say the t.block is always TryCatch ?

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

try_table is always a try..catch, yes. We have to implement the finally behavior manually on top of that.

(That's not uncommon for low-level bytecode formats. The JVM does the same.)

wasm/src/main/scala/wasm4s/Defaults.scala Show resolved Hide resolved
@sjrd
Copy link
Collaborator Author

sjrd commented Mar 27, 2024

IIUC, this implementation is able to catch the exception thrown from JS like

JS throws something else -> Scala.js catches it wrapped in a js.JavaScriptException
https://www.scala-js.org/doc/interoperability/exceptions.html

am I right?

Unfortunately not yet. For that we will need a not-yet-approved addition to the exception handling feature. See WebAssembly/exception-handling#269

Currently all the wrap/unwrap thing does is allow to throw non-Throwable the way JavaScript would do.

@tanishiking
Copy link
Owner

Currently all the wrap/unwrap thing does is allow to throw non-Throwable the way JavaScript would do.

Gotcha, thanks!

@tanishiking tanishiking merged commit eaff125 into tanishiking:main Mar 27, 2024
1 check passed
@sjrd sjrd deleted the exceptions branch March 27, 2024 07:53
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Support try-catch-finally
2 participants