1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
|
// |jit-test| skip-if: !wasmGcEnabled()
// Attempt to test intercalls from ion to baseline and back.
//
// We get into this situation when the modules are compiled with different
// tiering policies, or one tiers up before the other, or (for now) one opts
// into gc and is baseline-compiled and the other does not and is ion-compiled.
// There are lots of variables here. Generally, a small module will be
// ion-compiled unless there's reason to baseline-compile it, so we're likely
// actually testing something here.
//
// Some logging with printf confirms that refmod is baseline-compiled and
// nonrefmod is ion-compiled at present, with --setpref=wasm_gc=true enabled.
var refmod = new WebAssembly.Module(wasmTextToBinary(
`(module
(import "" "tbl" (table $tbl 4 funcref))
(import "" "print" (func $print (param i32)))
;; Just a dummy
(type $s (struct (field i32)))
(type $htype (func (param externref)))
(type $itype (func (result externref)))
(elem (i32.const 0) $f $g)
(func $f (param externref)
(call $print (i32.const 1)))
(func $g (result externref)
(call $print (i32.const 2))
(ref.null extern))
(func (export "test_h")
(call_indirect (type $htype) (ref.null extern) (i32.const 2)))
(func (export "test_i")
(drop (call_indirect (type $itype) (i32.const 3))))
)`));
var nonrefmod = new WebAssembly.Module(wasmTextToBinary(
`(module
(import "" "tbl" (table $tbl 4 funcref))
(import "" "print" (func $print (param i32)))
(type $ftype (func (param i32)))
(type $gtype (func (result i32)))
(elem (i32.const 2) $h $i)
;; Should fail because of the signature mismatch: parameter
(func (export "test_f")
(call_indirect (type $ftype) (i32.const 37) (i32.const 0)))
;; Should fail because of the signature mismatch: return value
(func (export "test_g")
(drop (call_indirect (type $gtype) (i32.const 1))))
(func $h (param i32)
(call $print (i32.const 2)))
(func $i (result i32)
(call $print (i32.const 3))
(i32.const 37))
)`));
var tbl = new WebAssembly.Table({initial:4, element:"anyfunc"});
var refins = new WebAssembly.Instance(refmod, {"":{print, tbl}}).exports;
var nonrefins = new WebAssembly.Instance(nonrefmod, {"":{print, tbl}}).exports;
assertErrorMessage(() => nonrefins.test_f(),
WebAssembly.RuntimeError,
/indirect call signature mismatch/);
assertErrorMessage(() => nonrefins.test_g(),
WebAssembly.RuntimeError,
/indirect call signature mismatch/);
assertErrorMessage(() => refins.test_h(),
WebAssembly.RuntimeError,
/indirect call signature mismatch/);
assertErrorMessage(() => refins.test_i(),
WebAssembly.RuntimeError,
/indirect call signature mismatch/);
|