|
3 | 3 | // META: script=/wasm/jsapi/wasm-module-builder.js
|
4 | 4 |
|
5 | 5 | test(() => {
|
6 |
| - const tag = new WebAssembly.Tag({ parameters: ["i32"] }); |
7 |
| - const exn = new WebAssembly.Exception(tag, [42]); |
8 |
| - const exn_same_payload = new WebAssembly.Exception(tag, [42]); |
9 |
| - const exn_diff_payload = new WebAssembly.Exception(tag, [53]); |
10 |
| - |
11 | 6 | const builder = new WasmModuleBuilder();
|
12 |
| - const jsfuncIndex = builder.addImport("module", "jsfunc", kSig_v_v); |
13 |
| - const tagIndex = builder.addImportedTag("module", "tag", kSig_v_i); |
| 7 | + |
| 8 | + // Tag defined in JavaScript and imported into Wasm |
| 9 | + const jsTag = new WebAssembly.Tag({ parameters: ["i32"] }); |
| 10 | + const jsTagIndex = builder.addImportedTag("module", "jsTag", kSig_v_i) |
| 11 | + const jsTagExn = new WebAssembly.Exception(jsTag, [42]); |
| 12 | + const jsTagExnSamePayload = new WebAssembly.Exception(jsTag, [42]); |
| 13 | + const jsTagExnDiffPayload = new WebAssembly.Exception(jsTag, [53]); |
| 14 | + const throwJSTagExnIndex = builder.addImport("module", "throwJSTagExn", kSig_v_v); |
| 15 | + |
14 | 16 | const imports = {
|
15 | 17 | module: {
|
16 |
| - jsfunc: function() { throw exn; }, |
17 |
| - tag: tag |
| 18 | + throwJSTagExn: function() { throw jsTagExn; }, |
| 19 | + jsTag: jsTag |
18 | 20 | }
|
19 | 21 | };
|
20 | 22 |
|
| 23 | + // Call a JS function that throws an exception using a JS-defined tag, catches |
| 24 | + // it with a 'catch' instruction, and rethrows it. |
21 | 25 | builder
|
22 |
| - .addFunction("catch_rethrow", kSig_v_v) |
| 26 | + .addFunction("catch_js_tag_rethrow", kSig_v_v) |
23 | 27 | .addBody([
|
24 | 28 | kExprTry, kWasmStmt,
|
25 |
| - kExprCallFunction, jsfuncIndex, |
26 |
| - kExprCatch, tagIndex, |
| 29 | + kExprCallFunction, throwJSTagExnIndex, |
| 30 | + kExprCatch, jsTagIndex, |
27 | 31 | kExprDrop,
|
28 | 32 | kExprRethrow, 0x00,
|
29 | 33 | kExprEnd
|
30 | 34 | ])
|
31 | 35 | .exportFunc();
|
32 | 36 |
|
| 37 | + // Call a JS function that throws an exception using a JS-defined tag, catches |
| 38 | + // it with a 'catch_all' instruction, and rethrows it. |
33 | 39 | builder
|
34 |
| - .addFunction("catch_all_rethrow", kSig_v_v) |
| 40 | + .addFunction("catch_all_js_tag_rethrow", kSig_v_v) |
35 | 41 | .addBody([
|
36 | 42 | kExprTry, kWasmStmt,
|
37 |
| - kExprCallFunction, jsfuncIndex, |
| 43 | + kExprCallFunction, throwJSTagExnIndex, |
38 | 44 | kExprCatchAll,
|
39 | 45 | kExprRethrow, 0x00,
|
40 | 46 | kExprEnd
|
41 | 47 | ])
|
42 | 48 | .exportFunc();
|
43 | 49 |
|
44 | 50 | const buffer = builder.toBuffer();
|
| 51 | + |
| 52 | + // The exception object's identity should be preserved across 'rethrow's in |
| 53 | + // Wasm code. Do tests with a tag defined in JS. |
45 | 54 | WebAssembly.instantiate(buffer, imports).then(result => {
|
46 | 55 | try {
|
47 |
| - result.instance.exports.catch_rethrow(); |
| 56 | + result.instance.exports.catch_js_tag_rethrow(); |
48 | 57 | } catch (e) {
|
49 |
| - assert_equals(e, exn); |
50 |
| - assert_not_equals(e, exn_same_payload); |
51 |
| - assert_not_equals(e, exn_diff_payload); |
| 58 | + assert_equals(e, jsTagExn); |
| 59 | + // Even if they have the same payload, they are different objects, so they |
| 60 | + // shouldn't compare equal. |
| 61 | + assert_not_equals(e, jsTagExnSamePayload); |
| 62 | + assert_not_equals(e, jsTagExnDiffPayload); |
52 | 63 | }
|
53 | 64 | try {
|
54 |
| - result.instance.exports.catch_all_rethrow(); |
| 65 | + result.instance.exports.catch_all_js_tag_rethrow(); |
55 | 66 | } catch (e) {
|
56 |
| - assert_equals(e, exn); |
57 |
| - assert_not_equals(e, exn_same_payload); |
58 |
| - assert_not_equals(e, exn_diff_payload); |
| 67 | + assert_equals(e, jsTagExn); |
| 68 | + assert_not_equals(e, jsTagExnSamePayload); |
| 69 | + assert_not_equals(e, jsTagExnDiffPayload); |
59 | 70 | }
|
60 | 71 | });
|
61 | 72 | }, "Identity check");
|
0 commit comments