Bug 1612534 - Manually fix wasm/ jit-tests. r=lth

This commit includes all the manual changes needed to get 'wasm/' jit-tests
passing.

Differential Revision: https://phabricator.services.mozilla.com/D67255

--HG--
extra : moz-landing-system : lando
This commit is contained in:
Ryan Hunt 2020-03-23 16:31:21 +00:00
parent 0133f62c5a
commit e50c835e32
44 changed files with 385 additions and 441 deletions

View File

@ -157,7 +157,7 @@ function create_wasmModule() {
);
const fooModuleCode = wasmTextToBinary(`(module
(func $foo (result i32) (i32.const 42))
(export "foo" $foo)
(export "foo" (func $foo))
)`);
WebAssembly.compile(fooModuleCode).then(

View File

@ -37,7 +37,7 @@ function create_wasmModule() {
const wasmTextToBinary = SpecialPowers.unwrap(SpecialPowers.Cu.getJSTestingFunctions().wasmTextToBinary);
const fooModuleCode = wasmTextToBinary(`(module
(func $foo (result i32) (i32.const 42))
(export "foo" $foo)
(export "foo" (func $foo))
)`);
WebAssembly.compile(fooModuleCode).then(m => {

View File

@ -36,7 +36,7 @@ function create_wasmModule() {
const wasmTextToBinary = SpecialPowers.unwrap(SpecialPowers.Cu.getJSTestingFunctions().wasmTextToBinary);
const fooModuleCode = wasmTextToBinary(`(module
(func $foo (result i32) (i32.const 42))
(export "foo" $foo)
(export "foo" (func $foo))
)`);
WebAssembly.compile(fooModuleCode).then(m => {

View File

@ -37,7 +37,7 @@ function runTestInIframe() {
const wasmTextToBinary = SpecialPowers.unwrap(SpecialPowers.Cu.getJSTestingFunctions().wasmTextToBinary);
const fooModuleCode = wasmTextToBinary(`(module
(func $foo (result i32) (i32.const 42))
(export "foo" $foo)
(export "foo" (func $foo))
)`);
node.port.postMessage(fooModuleCode);

View File

@ -24,6 +24,7 @@ const startId = 8;
const elemId = 9;
const codeId = 10;
const dataId = 11;
const dataCountId = 12;
const gcFeatureOptInId = 42;
// User-defined section names
@ -341,6 +342,12 @@ function dataSection(segmentArrays) {
return { name: dataId, body };
}
function dataCountSection(count) {
var body = [];
body.push(...varU32(count));
return { name: dataCountId, body };
}
function elemSection(elemArrays) {
var body = [];
body.push(...varU32(elemArrays.length));

View File

@ -10,10 +10,10 @@ let SHARED = 'shared';
let UNSHARED = '';
let sharedError = 'memory with atomic operations without shared memory';
for (let [type,view] of [['i32','8_u'],['i32','16_u'],['i32',''],['i64','8_u'],['i64','16_u'],['i64','32_u'],['i64','']]) {
for (let [type,width,view] of [['i32','8', '_u'],['i32','16','_u'],['i32','',''],['i64','8','_u'],['i64','16','_u'],['i64','32','_u'],['i64','','']]) {
{
let text = (shared) => `(module (memory 1 1 ${shared})
(func (result ${type}) (${type}.atomic.load${view} (i32.const 0)))
(func (result ${type}) (${type}.atomic.load${width}${view} (i32.const 0)))
(export "" (func 0)))`;
assertEq(valText(text(SHARED)), true);
assertEq(valText(text(UNSHARED)), false);
@ -21,7 +21,7 @@ for (let [type,view] of [['i32','8_u'],['i32','16_u'],['i32',''],['i64','8_u'],[
{
let text = (shared) => `(module (memory 1 1 ${shared})
(func (${type}.atomic.store${view} (i32.const 0) (${type}.const 1)))
(func (${type}.atomic.store${width} (i32.const 0) (${type}.const 1)))
(export "" (func 0)))`;
assertEq(valText(text(SHARED)), true);
assertEq(valText(text(UNSHARED)), false);
@ -30,7 +30,7 @@ for (let [type,view] of [['i32','8_u'],['i32','16_u'],['i32',''],['i64','8_u'],[
{
let text = (shared) => `(module (memory 1 1 ${shared})
(func (result ${type})
(${type}.atomic.rmw${view}.cmpxchg (i32.const 0) (${type}.const 1) (${type}.const 2)))
(${type}.atomic.rmw${width}.cmpxchg${view} (i32.const 0) (${type}.const 1) (${type}.const 2)))
(export "" (func 0)))`;
assertEq(valText(text(SHARED)), true);
assertEq(valText(text(UNSHARED)), false);
@ -39,7 +39,7 @@ for (let [type,view] of [['i32','8_u'],['i32','16_u'],['i32',''],['i64','8_u'],[
for (let op of ['add','and','or','sub','xor','xchg']) {
// Operate with appropriately-typed value 1 on address 0
let text = (shared) => `(module (memory 1 1 ${shared})
(func (result ${type}) (${type}.atomic.rmw${view}.${op} (i32.const 0) (${type}.const 1)))
(func (result ${type}) (${type}.atomic.rmw${width}.${op}${view} (i32.const 0) (${type}.const 1)))
(export "" (func 0)))`;
assertEq(valText(text(SHARED)), true);
@ -55,14 +55,11 @@ for (let type of ['i32', 'i64']) {
assertEq(valText(text(UNSHARED)), false);
}
// 'wake' remains a backwards-compatible alias for 'notify'
for ( let notify of ['wake', 'notify']) {
let text = (shared) => `(module (memory 1 1 ${shared})
(func (result i32) (atomic.${notify} (i32.const 0) (i32.const 1)))
(export "" (func 0)))`;
assertEq(valText(text(SHARED)), true);
assertEq(valText(text(UNSHARED)), false);
}
let text = (shared) => `(module (memory 1 1 ${shared})
(func (result i32) (atomic.notify (i32.const 0) (i32.const 1)))
(export "" (func 0)))`;
assertEq(valText(text(SHARED)), true);
assertEq(valText(text(UNSHARED)), false);
// Required explicit alignment for WAIT is the size of the datum
@ -168,14 +165,14 @@ function widen(TA, value, complement = true) {
var RMWOperation =
{
loadStoreModule(type, view, address, operand) {
loadStoreModule(type, width, view, address, operand) {
let bin = wasmTextToBinary(
`(module
(memory (import "" "memory") 1 1 shared)
(func (export "st") (param i32)
(${type}.atomic.store${view} ${address} ${operand}))
(${type}.atomic.store${width} ${address} ${operand}))
(func $ld (param i32) (result ${type})
(${type}.atomic.load${view} ${address}))
(${type}.atomic.load${width}${view} ${address}))
(func (export "ld") (param i32) (result i32)
(${type}.eq (call $ld (local.get 0)) ${operand})))`);
let mod = new WebAssembly.Module(bin);
@ -184,12 +181,12 @@ var RMWOperation =
return [mem, ins.exports.ld, ins.exports.st];
},
opModuleEffect(type, view, address, op, operand, ignored) {
opModuleEffect(type, width, view, address, op, operand, ignored) {
let bin = wasmTextToBinary(
`(module
(memory (import "" "memory") 1 1 shared)
(func (export "f") (param i32) (result i32)
(drop (${type}.atomic.rmw${view}.${op} ${address} ${operand}))
(drop (${type}.atomic.rmw${width}.${op}${view} ${address} ${operand}))
(i32.const 1)))`);
let mod = new WebAssembly.Module(bin);
let mem = new WebAssembly.Memory({initial: 1, maximum: 1, shared: true});
@ -197,12 +194,12 @@ var RMWOperation =
return [mem, ins.exports.f];
},
opModuleReturned(type, view, address, op, operand, expected) {
opModuleReturned(type, width, view, address, op, operand, expected) {
let bin = wasmTextToBinary(
`(module
(memory (import "" "memory") 1 1 shared)
(func $_f (param i32) (result ${type})
(${type}.atomic.rmw${view}.${op} ${address} ${operand}))
(${type}.atomic.rmw${width}.${op}${view} ${address} ${operand}))
(func (export "f") (param i32) (result i32)
(${type}.eq (call $_f (local.get 0)) (${type}.const ${expected}))))`);
let mod = new WebAssembly.Module(bin);
@ -211,24 +208,24 @@ var RMWOperation =
return [mem, ins.exports.f];
},
cmpxchgModuleEffect(type, view, address, operand1, operand2, ignored) {
cmpxchgModuleEffect(type, width, view, address, operand1, operand2, ignored) {
let bin = wasmTextToBinary(
`(module
(memory (import "" "memory") 1 1 shared)
(func (export "f") (param i32)
(drop (${type}.atomic.rmw${view}.cmpxchg ${address} ${operand1} ${operand2}))))`);
(drop (${type}.atomic.rmw${width}.cmpxchg${view} ${address} ${operand1} ${operand2}))))`);
let mod = new WebAssembly.Module(bin);
let mem = new WebAssembly.Memory({initial: 1, maximum: 1, shared: true});
let ins = new WebAssembly.Instance(mod, {"": {memory: mem}});
return [mem, ins.exports.f];
},
cmpxchgModuleReturned(type, view, address, operand1, operand2, expected) {
cmpxchgModuleReturned(type, width, view, address, operand1, operand2, expected) {
let bin = wasmTextToBinary(
`(module
(memory (import "" "memory") 1 1 shared)
(func $_f (param i32) (result ${type})
(${type}.atomic.rmw${view}.cmpxchg ${address} ${operand1} ${operand2}))
(${type}.atomic.rmw${width}.cmpxchg${view} ${address} ${operand1} ${operand2}))
(func (export "f") (param i32) (result i32)
(${type}.eq (call $_f (local.get 0)) (${type}.const ${expected}))))`);
let mod = new WebAssembly.Module(bin);
@ -250,10 +247,10 @@ var RMWOperation =
const OPD2 = 42; // Sometimes we'll put another operand here
for ( let [type, variations] of
[["i32", [[Uint8Array,"8_u"], [Uint16Array,"16_u"], [Uint32Array,""]]],
["i64", [[Uint8Array,"8_u"], [Uint16Array,"16_u"], [Uint32Array,"32_u"], [Uint64Array,""]]]] )
[["i32", [[Uint8Array,"8", "_u"], [Uint16Array,"16", "_u"], [Uint32Array,"",""]]],
["i64", [[Uint8Array,"8","_u"], [Uint16Array,"16","_u"], [Uint32Array,"32","_u"], [Uint64Array,"",""]]]] )
{
for ( let [TA, view] of variations )
for ( let [TA, width, view] of variations )
{
for ( let addr of [`(i32.const ${LOC * TA.BYTES_PER_ELEMENT})`,
`(local.get 0)`] )
@ -262,9 +259,9 @@ var RMWOperation =
{
let [opd_str, opd_num] = widen(TA, operand);
for ( let rhs of [`(${type}.const ${opd_str})`,
`(${type}.load${view} (i32.const ${OPD1 * TA.BYTES_PER_ELEMENT}))`] )
`(${type}.load${width}${view} (i32.const ${OPD1 * TA.BYTES_PER_ELEMENT}))`] )
{
let [mem, ld, st] = this.loadStoreModule(type, view, addr, rhs);
let [mem, ld, st] = this.loadStoreModule(type, width, view, addr, rhs);
let array = new TA(mem.buffer);
array.write(OPD1, opd_num);
array.write(LOC, initial);
@ -289,11 +286,11 @@ var RMWOperation =
let [opd_str, opd_num] = widen(TA, operand, complement);
let [exp_str, exp_num] = widen(TA, expected, complement);
for ( let rhs of [`(${type}.const ${opd_str})`,
`(${type}.load${view} (i32.const ${OPD1 * TA.BYTES_PER_ELEMENT}))`] )
`(${type}.load${width}${view} (i32.const ${OPD1 * TA.BYTES_PER_ELEMENT}))`] )
{
for ( let [generateIt, checkIt] of [["opModuleEffect", false], ["opModuleReturned", true]] )
{
let [mem, f] = this[generateIt](type, view, addr, op, rhs, ini_str);
let [mem, f] = this[generateIt](type, width, view, addr, op, rhs, ini_str);
let array = new TA(mem.buffer);
array.write(OPD1, opd_num);
array.write(LOC, ini_num);
@ -314,14 +311,14 @@ var RMWOperation =
let [opd2_str, opd2_num] = widen(TA, operand2);
let [exp_str, exp_num] = widen(TA, expected);
for ( let op1 of [`(${type}.const ${opd1_str})`,
`(${type}.load${view} (i32.const ${OPD1 * TA.BYTES_PER_ELEMENT}))`] )
`(${type}.load${width}${view} (i32.const ${OPD1 * TA.BYTES_PER_ELEMENT}))`] )
{
for ( let op2 of [`(${type}.const ${opd2_str})`,
`(${type}.load${view} (i32.const ${OPD2 * TA.BYTES_PER_ELEMENT}))`] )
`(${type}.load${width}${view} (i32.const ${OPD2 * TA.BYTES_PER_ELEMENT}))`] )
{
for ( let [generateIt, checkIt] of [["cmpxchgModuleEffect", false], ["cmpxchgModuleReturned", true]] )
{
let [mem, f] = this[generateIt](type, view, addr, op1, op2, ini_str);
let [mem, f] = this[generateIt](type, width, view, addr, op1, op2, ini_str);
let array = new TA(mem.buffer);
array.write(OPD1, opd1_num);
array.write(OPD2, opd2_num);
@ -364,71 +361,71 @@ function assertNum(a, b) {
var BoundsAndAlignment =
{
loadModule(type, ext, offset) {
loadModule(type, view, width, offset) {
return wasmEvalText(
`(module
(memory 1 1 shared)
(func $0 (param i32) (result ${type})
(${type}.atomic.load${ext} offset=${offset} (local.get 0)))
(${type}.atomic.load${width}${view} offset=${offset} (local.get 0)))
(func (export "f") (param i32)
(drop (call $0 (local.get 0)))))
`).exports.f;
},
loadModuleIgnored(type, ext, offset) {
loadModuleIgnored(type, view, width, offset) {
return wasmEvalText(
`(module
(memory 1 1 shared)
(func (export "f") (param i32)
(drop (${type}.atomic.load${ext} offset=${offset} (local.get 0)))))
(drop (${type}.atomic.load${width}${view} offset=${offset} (local.get 0)))))
`).exports.f;
},
storeModule(type, ext, offset) {
storeModule(type, view, width, offset) {
return wasmEvalText(
`(module
(memory 1 1 shared)
(func (export "f") (param i32)
(${type}.atomic.store${ext} offset=${offset} (local.get 0) (${type}.const 37))))
(${type}.atomic.store${width} offset=${offset} (local.get 0) (${type}.const 37))))
`).exports.f;
},
opModule(type, ext, offset, op) {
opModule(type, view, width, offset, op) {
return wasmEvalText(
`(module
(memory 1 1 shared)
(func $0 (param i32) (result ${type})
(${type}.atomic.rmw${ext}.${op} offset=${offset} (local.get 0) (${type}.const 37)))
(${type}.atomic.rmw${width}.${op}${view} offset=${offset} (local.get 0) (${type}.const 37)))
(func (export "f") (param i32)
(drop (call $0 (local.get 0)))))
`).exports.f;
},
opModuleForEffect(type, ext, offset, op) {
opModuleForEffect(type, view, width, offset, op) {
return wasmEvalText(
`(module
(memory 1 1 shared)
(func (export "f") (param i32)
(drop (${type}.atomic.rmw${ext}.${op} offset=${offset} (local.get 0) (${type}.const 37)))))
(drop (${type}.atomic.rmw${width}.${op}${view} offset=${offset} (local.get 0) (${type}.const 37)))))
`).exports.f;
},
cmpxchgModule(type, ext, offset) {
cmpxchgModule(type, view, width, offset) {
return wasmEvalText(
`(module
(memory 1 1 shared)
(func $0 (param i32) (result ${type})
(${type}.atomic.rmw${ext}.cmpxchg offset=${offset} (local.get 0) (${type}.const 37) (${type}.const 42)))
(${type}.atomic.rmw${width}.cmpxchg${view} offset=${offset} (local.get 0) (${type}.const 37) (${type}.const 42)))
(func (export "f") (param i32)
(drop (call $0 (local.get 0)))))
`).exports.f;
},
run() {
for ( let [type, variations] of [["i32", [["8_u", 1], ["16_u", 2], ["", 4]]],
["i64", [["8_u",1], ["16_u",2], ["32_u",4], ["",8]]]] )
for ( let [type, variations] of [["i32", [["8","_u", 1], ["16","_u", 2], ["","", 4]]],
["i64", [["8","_u",1], ["16","_u",2], ["32","_u",4], ["","",8]]]] )
{
for ( let [ext,size] of variations )
for ( let [width,view,size] of variations )
{
// Aligned but out-of-bounds
let addrs = [[65536, 0, oob], [65536*2, 0, oob], [65532, 4, oob],
@ -451,14 +448,14 @@ var BoundsAndAlignment =
for ( let [ base, offset, re ] of addrs )
{
assertErrorMessage(() => this.loadModule(type, ext, offset)(base), RuntimeError, re);
assertErrorMessage(() => this.loadModuleIgnored(type, ext, offset)(base), RuntimeError, re);
assertErrorMessage(() => this.storeModule(type, ext, offset)(base), RuntimeError, re);
assertErrorMessage(() => this.loadModule(type, view, width, offset)(base), RuntimeError, re);
assertErrorMessage(() => this.loadModuleIgnored(type, view, width, offset)(base), RuntimeError, re);
assertErrorMessage(() => this.storeModule(type, view, width, offset)(base), RuntimeError, re);
for ( let op of [ "add", "sub", "and", "or", "xor", "xchg" ]) {
assertErrorMessage(() => this.opModule(type, ext, offset, op)(base), RuntimeError, re);
assertErrorMessage(() => this.opModuleForEffect(type, ext, offset, op)(base), RuntimeError, re);
assertErrorMessage(() => this.opModule(type, view, width, offset, op)(base), RuntimeError, re);
assertErrorMessage(() => this.opModuleForEffect(type, view, width, offset, op)(base), RuntimeError, re);
}
assertErrorMessage(() => this.cmpxchgModule(type, ext, offset)(base), RuntimeError, re);
assertErrorMessage(() => this.cmpxchgModule(type, view, width, offset)(base), RuntimeError, re);
}
}
}
@ -514,7 +511,7 @@ assertErrorMessage(() => wasmEvalText(`(module
(func (export "main")
i32.const 1
i32.const 2816
i32.atomic.rmw16_u.xchg align=2
i32.atomic.rmw16.xchg_u align=2
i32.load16_s offset=83 align=1
drop
)

View File

@ -194,7 +194,8 @@ function makeModule(id) {
return ((val << (pos * VALSHIFT)) + 0x100000000).toString(16).substring(1);
}
let tag = bits < 32 ? bits + '_u' : '';
let width = bits < 32 ? '' + bits : '';
let view = bits < 32 ? '_u' : '';
let prefix = bits == 64 ? 'i64' : 'i32';
return `
(func ${name} (param $barrierValue i32) (result i32)
@ -205,7 +206,7 @@ function makeModule(id) {
(if (local.get $n)
(block
${isMaster ? `;; Init
(${prefix}.atomic.store${tag} ${loc} (${prefix}.const ${distribute(initial)}))` : ``}
(${prefix}.atomic.store${width} ${loc} (${prefix}.const ${distribute(initial)}))` : ``}
${barrier}
${(() => {
@ -216,7 +217,7 @@ ${(() => {
// we would avoid fences in that case.
if (op.match(/cmpxchg/)) {
s += `(loop $doit
(local.set $tmp (${prefix}.atomic.load${tag} ${loc}))
(local.set $tmp (${prefix}.atomic.load${width}${view} ${loc}))
(br_if $doit (i32.eqz
(${prefix}.eq
(local.get $tmp)
@ -230,7 +231,7 @@ ${(() => {
return s
})()}
(loop $wait_done
(br_if $wait_done (${prefix}.ne (${prefix}.atomic.load${tag} ${loc}) (${prefix}.const ${distribute(expected)}))))
(br_if $wait_done (${prefix}.ne (${prefix}.atomic.load${width}${view} ${loc}) (${prefix}.const ${distribute(expected)}))))
${barrier}
(local.set $n (i32.sub (local.get $n) (i32.const 1)))
(br $outer))))
@ -270,21 +271,21 @@ ${(() => {
return `
(module
(import "" "memory" (memory 1 1 shared))
(import $print "" "print" (param i32))
(import "" "print" (func $print (param i32)))
${makeLoop(8, "$test_add8", "i32.atomic.rmw8_u.add", ADDLOC, ADDINIT, ADDVAL[id], ADDRESULT)}
${makeLoop(8, "$test_sub8", "i32.atomic.rmw8_u.sub", SUBLOC, SUBINIT, SUBVAL[id], SUBRESULT)}
${makeLoop(8, "$test_and8", "i32.atomic.rmw8_u.and", ANDLOC, ANDINIT, ANDVAL[id], ANDRESULT)}
${makeLoop(8, "$test_or8", "i32.atomic.rmw8_u.or", ORLOC, ORINIT, ORVAL[id], ORRESULT)}
${makeLoop(8, "$test_xor8", "i32.atomic.rmw8_u.xor", XORLOC, XORINIT, XORVAL[id], XORRESULT)}
${makeLoop(8, "$test_cmpxchg8", "i32.atomic.rmw8_u.cmpxchg", CMPXCHGLOC, CMPXCHGINIT, CMPXCHGVAL[id], CMPXCHGRESULT)}
${makeLoop(8, "$test_add8", "i32.atomic.rmw8.add_u", ADDLOC, ADDINIT, ADDVAL[id], ADDRESULT)}
${makeLoop(8, "$test_sub8", "i32.atomic.rmw8.sub_u", SUBLOC, SUBINIT, SUBVAL[id], SUBRESULT)}
${makeLoop(8, "$test_and8", "i32.atomic.rmw8.and_u", ANDLOC, ANDINIT, ANDVAL[id], ANDRESULT)}
${makeLoop(8, "$test_or8", "i32.atomic.rmw8.or_u", ORLOC, ORINIT, ORVAL[id], ORRESULT)}
${makeLoop(8, "$test_xor8", "i32.atomic.rmw8.xor_u", XORLOC, XORINIT, XORVAL[id], XORRESULT)}
${makeLoop(8, "$test_cmpxchg8", "i32.atomic.rmw8.cmpxchg_u", CMPXCHGLOC, CMPXCHGINIT, CMPXCHGVAL[id], CMPXCHGRESULT)}
${makeLoop(16, "$test_add16", "i32.atomic.rmw16_u.add", ADDLOC, ADDINIT, ADDVAL[id], ADDRESULT)}
${makeLoop(16, "$test_sub16", "i32.atomic.rmw16_u.sub", SUBLOC, SUBINIT, SUBVAL[id], SUBRESULT)}
${makeLoop(16, "$test_and16", "i32.atomic.rmw16_u.and", ANDLOC, ANDINIT, ANDVAL[id], ANDRESULT)}
${makeLoop(16, "$test_or16", "i32.atomic.rmw16_u.or", ORLOC, ORINIT, ORVAL[id], ORRESULT)}
${makeLoop(16, "$test_xor16", "i32.atomic.rmw16_u.xor", XORLOC, XORINIT, XORVAL[id], XORRESULT)}
${makeLoop(16, "$test_cmpxchg16", "i32.atomic.rmw16_u.cmpxchg", CMPXCHGLOC, CMPXCHGINIT, CMPXCHGVAL[id], CMPXCHGRESULT)}
${makeLoop(16, "$test_add16", "i32.atomic.rmw16.add_u", ADDLOC, ADDINIT, ADDVAL[id], ADDRESULT)}
${makeLoop(16, "$test_sub16", "i32.atomic.rmw16.sub_u", SUBLOC, SUBINIT, SUBVAL[id], SUBRESULT)}
${makeLoop(16, "$test_and16", "i32.atomic.rmw16.and_u", ANDLOC, ANDINIT, ANDVAL[id], ANDRESULT)}
${makeLoop(16, "$test_or16", "i32.atomic.rmw16.or_u", ORLOC, ORINIT, ORVAL[id], ORRESULT)}
${makeLoop(16, "$test_xor16", "i32.atomic.rmw16.xor_u", XORLOC, XORINIT, XORVAL[id], XORRESULT)}
${makeLoop(16, "$test_cmpxchg16", "i32.atomic.rmw16.cmpxchg_u", CMPXCHGLOC, CMPXCHGINIT, CMPXCHGVAL[id], CMPXCHGRESULT)}
${makeLoop(32, "$test_add", "i32.atomic.rmw.add", ADDLOC, ADDINIT, ADDVAL[id], ADDRESULT)}
${makeLoop(32, "$test_sub", "i32.atomic.rmw.sub", SUBLOC, SUBINIT, SUBVAL[id], SUBRESULT)}

View File

@ -1,5 +1,5 @@
var code = `(module
(import $i "env" "test")
(import "env" "test" (func $i))
(func $t (call $i))
(export "test" (func $t))
)`;

View File

@ -63,7 +63,7 @@ wasmValidateText('(module (func (nop)))');
wasmValidateText('(module (func (result i32) (i32.const 42)))');
wasmValidateText('(module (func (param i32)))');
wasmValidateText('(module (func (param i32) (result i32) (i32.const 42)))');
wasmValidateText('(module (func (result i32) (param i32) (i32.const 42)))');
wasmValidateText('(module (func (param i32) (result i32) (i32.const 42)))');
wasmValidateText('(module (func (param f32)))');
wasmValidateText('(module (func (param f64)))');
@ -82,13 +82,13 @@ wasmFullPassI64('(module (func $run (param i64) (result i64) (i64.add (local.get
const noImportObj = "second argument must be an object";
assertErrorMessage(() => wasmEvalText('(module (import "a" "b"))', 1), TypeError, noImportObj);
assertErrorMessage(() => wasmEvalText('(module (import "a" "b"))', null), TypeError, noImportObj);
assertErrorMessage(() => wasmEvalText('(module (import "a" "b" (func)))', 1), TypeError, noImportObj);
assertErrorMessage(() => wasmEvalText('(module (import "a" "b" (func)))', null), TypeError, noImportObj);
const notObject = /import object field '\w*' is not an Object/;
const notFunction = /import object field '\w*' is not a Function/;
var code = '(module (import "a" "b"))';
var code = '(module (import "a" "b" (func)))';
assertErrorMessage(() => wasmEvalText(code), TypeError, noImportObj);
assertErrorMessage(() => wasmEvalText(code, {}), TypeError, notObject);
assertErrorMessage(() => wasmEvalText(code, {a:1}), TypeError, notObject);
@ -96,23 +96,23 @@ assertErrorMessage(() => wasmEvalText(code, {a:{}}), LinkError, notFunction);
assertErrorMessage(() => wasmEvalText(code, {a:{b:1}}), LinkError, notFunction);
wasmEvalText(code, {a:{b:()=>{}}});
var code = '(module (import "" "b"))';
var code = '(module (import "" "b" (func)))';
wasmEvalText(code, {"":{b:()=>{}}});
var code = '(module (import "a" ""))';
var code = '(module (import "a" "" (func)))';
assertErrorMessage(() => wasmEvalText(code), TypeError, noImportObj);
assertErrorMessage(() => wasmEvalText(code, {}), TypeError, notObject);
assertErrorMessage(() => wasmEvalText(code, {a:1}), TypeError, notObject);
wasmEvalText(code, {a:{"":()=>{}}});
var code = '(module (import "a" "") (import "b" "c") (import "c" ""))';
var code = '(module (import "a" "" (func)) (import "b" "c" (func)) (import "c" "" (func)))';
assertErrorMessage(() => wasmEvalText(code, {a:()=>{}, b:{c:()=>{}}, c:{}}), LinkError, notFunction);
wasmEvalText(code, {a:{"":()=>{}}, b:{c:()=>{}}, c:{"":()=>{}}});
wasmEvalText('(module (import "a" "" (result i32)))', {a:{"":()=>{}}});
wasmEvalText('(module (import "a" "" (result f32)))', {a:{"":()=>{}}});
wasmEvalText('(module (import "a" "" (result f64)))', {a:{"":()=>{}}});
wasmEvalText('(module (import $foo "a" "" (result f64)))', {a:{"":()=>{}}});
wasmEvalText('(module (import "a" "" (func (result i32))))', {a:{"":()=>{}}});
wasmEvalText('(module (import "a" "" (func (result f32))))', {a:{"":()=>{}}});
wasmEvalText('(module (import "a" "" (func (result f64))))', {a:{"":()=>{}}});
wasmEvalText('(module (import "a" "" (func $foo (result f64))))', {a:{"":()=>{}}});
// ----------------------------------------------------------------------------
// memory
@ -173,15 +173,15 @@ assertEq(wasmEvalText('(module (func (param i32) (param i32) (result i32) (local
wasmFailValidateText('(module (func (local.get 0)))', /local.get index out of range/);
wasmFailValidateText('(module (func (result f32) (local i32) (local.get 0)))', mismatchError("i32", "f32"));
wasmFailValidateText('(module (func (result i32) (local f32) (local.get 0)))', mismatchError("f32", "i32"));
wasmFailValidateText('(module (func (result f32) (param i32) (local f32) (local.get 0)))', mismatchError("i32", "f32"));
wasmFailValidateText('(module (func (result i32) (param i32) (local f32) (local.get 1)))', mismatchError("f32", "i32"));
wasmFailValidateText('(module (func (param i32) (result f32) (local f32) (local.get 0)))', mismatchError("i32", "f32"));
wasmFailValidateText('(module (func (param i32) (result i32) (local f32) (local.get 1)))', mismatchError("f32", "i32"));
wasmValidateText('(module (func (local i32)))');
wasmValidateText('(module (func (local i32) (local f32)))');
wasmFullPass('(module (func (result i32) (local i32) (local.get 0)) (export "run" (func 0)))', 0);
wasmFullPass('(module (func (result i32) (param i32) (local f32) (local.get 0)) (export "run" (func 0)))', 0);
wasmFullPass('(module (func (result f32) (param i32) (local f32) (local.get 1)) (export "run" (func 0)))', 0);
wasmFullPass('(module (func (param i32) (result i32) (local f32) (local.get 0)) (export "run" (func 0)))', 0);
wasmFullPass('(module (func (param i32) (result f32) (local f32) (local.get 1)) (export "run" (func 0)))', 0);
wasmFailValidateText('(module (func (local.set 0 (i32.const 0))))', /local.set index out of range/);
wasmFailValidateText('(module (func (local f32) (local.set 0 (i32.const 0))))', mismatchError("i32", "f32"));
@ -197,7 +197,7 @@ wasmFullPass('(module (func (result i32) (local i32) (tee_local 0 (i32.const 42)
wasmFullPass('(module (func (result i32) (local i32) (tee_local 0 (local.get 0))) (export "run" (func 0)))', 0);
wasmFullPass('(module (func (param $a i32) (result i32) (local.get $a)) (export "run" (func 0)))', 0);
wasmFullPass('(module (func (param $a i32) (local $b i32) (result i32) (block (result i32) (local.set $b (local.get $a)) (local.get $b))) (export "run" (func 0)))', 42, {}, 42);
wasmFullPass('(module (func (param $a i32) (result i32) (local $b i32) (block (result i32) (local.set $b (local.get $a)) (local.get $b))) (export "run" (func 0)))', 42, {}, 42);
wasmValidateText('(module (func (local i32) (local $a f32) (local.set 0 (i32.const 1)) (local.set $a (f32.const nan))))');
@ -216,7 +216,7 @@ wasmFullPass('(module (func (result i32) (block (result i32) (block (result i32)
wasmFailValidateText('(module (func (result f32) (block (result i32) (i32.const 0))))', mismatchError("i32", "f32"));
wasmFullPass('(module (func (result i32) (block (result i32) (drop (i32.const 13)) (block (result i32) (i32.const 42)))) (export "run" (func 0)))', 42);
wasmFailValidateText('(module (func (result f32) (param f32) (block (result i32) (drop (local.get 0)) (i32.const 0))))', mismatchError("i32", "f32"));
wasmFailValidateText('(module (func (param f32) (result f32) (block (result i32) (drop (local.get 0)) (i32.const 0))))', mismatchError("i32", "f32"));
wasmFullPass('(module (func (result i32) (local i32) (local.set 0 (i32.const 42)) (local.get 0)) (export "run" (func 0)))', 42);
@ -239,19 +239,19 @@ assertThrowsInstanceOf(() => wasmEvalText('(module (func (call 1)) (func (call 0
wasmValidateText('(module (func (param i32 f32)) (func (call 0 (i32.const 0) (f32.const nan))))');
wasmFailValidateText('(module (func (param i32 f32)) (func (call 0 (i32.const 0) (i32.const 0))))', mismatchError("i32", "f32"));
wasmFailValidateText('(module (import "a" "") (func (call 0 (i32.const 0))))', unusedValuesError);
wasmFailValidateText('(module (import "a" "" (param i32)) (func (call 0)))', emptyStackError);
wasmFailValidateText('(module (import "a" "" (param f32)) (func (call 0 (i32.const 0))))', mismatchError("i32", "f32"));
wasmFailValidateText('(module (import "a" "" (func)) (func (call 0 (i32.const 0))))', unusedValuesError);
wasmFailValidateText('(module (import "a" "" (func (param i32))) (func (call 0)))', emptyStackError);
wasmFailValidateText('(module (import "a" "" (func (param f32))) (func (call 0 (i32.const 0))))', mismatchError("i32", "f32"));
assertErrorMessage(() => wasmEvalText('(module (import "a" "") (func (call 1)))'), TypeError, noImportObj);
wasmEvalText('(module (import "" "a") (func (call 0)))', {"":{a:()=>{}}});
wasmEvalText('(module (import "" "a" (param i32)) (func (call 0 (i32.const 0))))', {"":{a:()=>{}}});
assertErrorMessage(() => wasmEvalText('(module (import "a" "" (func)) (func (call 1)))'), TypeError, noImportObj);
wasmEvalText('(module (import "" "a" (func)) (func (call 0)))', {"":{a:()=>{}}});
wasmEvalText('(module (import "" "a" (func (param i32))) (func (call 0 (i32.const 0))))', {"":{a:()=>{}}});
function checkF32CallImport(v) {
wasmFullPass('(module (import "" "a" (result f32)) (func (result f32) (call 0)) (export "run" (func 1)))',
wasmFullPass('(module (import "" "a" (func (result f32))) (func (result f32) (call 0)) (export "run" (func 1)))',
Math.fround(v),
{"":{a:()=>{ return v; }}});
wasmFullPass('(module (import "" "a" (param f32)) (func (param f32) (call 0 (local.get 0))) (export "run" (func 1)))',
wasmFullPass('(module (import "" "a" (func (param f32))) (func (param f32) (call 0 (local.get 0))) (export "run" (func 1)))',
undefined,
{"":{a:x=>{ assertEq(Math.fround(v), x); }}},
v);
@ -263,28 +263,28 @@ checkF32CallImport(-0);
checkF32CallImport(Math.pow(2, 32) - 1);
var counter = 0;
var f = wasmEvalText('(module (import "" "inc") (func (call 0)) (export "" (func 1)))', {"":{inc:()=>counter++}}).exports[""];
var g = wasmEvalText('(module (import "" "f") (func (block (call 0) (call 0))) (export "" (func 1)))', {"":{f}}).exports[""];
var f = wasmEvalText('(module (import "" "inc" (func)) (func (call 0)) (export "" (func 1)))', {"":{inc:()=>counter++}}).exports[""];
var g = wasmEvalText('(module (import "" "f" (func)) (func (block (call 0) (call 0))) (export "" (func 1)))', {"":{f}}).exports[""];
f();
assertEq(counter, 1);
g();
assertEq(counter, 3);
var f = wasmEvalText('(module (import "" "callf") (func (call 0)) (export "" (func 1)))', {"":{callf:()=>f()}}).exports[""];
var f = wasmEvalText('(module (import "" "callf" (func)) (func (call 0)) (export "" (func 1)))', {"":{callf:()=>f()}}).exports[""];
assertThrowsInstanceOf(() => f(), InternalError);
var f = wasmEvalText('(module (import "" "callg") (func (call 0)) (export "" (func 1)))', {"":{callg:()=>g()}}).exports[""];
var g = wasmEvalText('(module (import "" "callf") (func (call 0)) (export "" (func 1)))', {"":{callf:()=>f()}}).exports[""];
var f = wasmEvalText('(module (import "" "callg" (func)) (func (call 0)) (export "" (func 1)))', {"":{callg:()=>g()}}).exports[""];
var g = wasmEvalText('(module (import "" "callf" (func)) (func (call 0)) (export "" (func 1)))', {"":{callf:()=>f()}}).exports[""];
assertThrowsInstanceOf(() => f(), InternalError);
var code = '(module (import "" "one" (result i32)) (import "" "two" (result i32)) (func (result i32) (i32.const 3)) (func (result i32) (i32.const 4)) (func (result i32) BODY) (export "run" (func 4)))';
var code = '(module (import "" "one" (func (result i32))) (import "" "two" (func (result i32))) (func (result i32) (i32.const 3)) (func (result i32) (i32.const 4)) (func (result i32) BODY) (export "run" (func 4)))';
var imports = {"":{one:()=>1, two:()=>2}};
wasmFullPass(code.replace('BODY', '(call 0)'), 1, imports);
wasmFullPass(code.replace('BODY', '(call 1)'), 2, imports);
wasmFullPass(code.replace('BODY', '(call 2)'), 3, imports);
wasmFullPass(code.replace('BODY', '(call 3)'), 4, imports);
wasmFullPass(`(module (import "" "evalcx" (param i32) (result i32)) (func (result i32) (call 0 (i32.const 0))) (export "run" (func 1)))`, 0, {"":{evalcx}});
wasmFullPass(`(module (import "" "evalcx" (func (param i32) (result i32))) (func (result i32) (call 0 (i32.const 0))) (export "run" (func 1)))`, 0, {"":{evalcx}});
if (typeof evaluate === 'function')
evaluate(`new WebAssembly.Instance(new WebAssembly.Module(wasmTextToBinary('(module)'))) `, { fileName: null });
@ -340,7 +340,7 @@ assertErrorMessage(() => i2v(5), Error, signatureMismatch);
wasmFullPass(
`(module
(type $v2v (func))
(import $foo "" "f")
(import "" "f" (func $foo))
(func $a (call $foo))
(func $b (result i32) (i32.const 0))
(table funcref (elem $a $b))
@ -368,7 +368,7 @@ for (bad of [6, 7, 100, Math.pow(2,31)-1, Math.pow(2,31), Math.pow(2,31)+1, Math
wasmValidateText('(module (func $foo (nop)) (func (call $foo)))');
wasmValidateText('(module (func (call $foo)) (func $foo (nop)))');
wasmValidateText('(module (import $bar "" "a") (func (call $bar)) (func $foo (nop)))');
wasmValidateText('(module (import "" "a" (func $bar)) (func (call $bar)) (func $foo (nop)))');
// ----------------------------------------------------------------------------
// select
@ -396,9 +396,9 @@ var imports = {"": {
// Test that side-effects are applied on both branches.
var f = wasmEvalText(`
(module
(import "" "ifTrue" (result i32))
(import "" "ifFalse" (result i32))
(func (result i32) (param i32)
(import "" "ifTrue" (func (result i32)))
(import "" "ifFalse" (func (result i32)))
(func (param i32) (result i32)
(select
(call 0)
(call 1)
@ -443,7 +443,7 @@ function testSelect(type, trueVal, falseVal) {
// Always true condition
var alwaysTrue = wasmEvalText(`
(module
(func (result ${type}) (param i32)
(func (param i32) (result ${type})
(select
(${type}.const ${trueVal})
(${type}.const ${falseVal})
@ -461,7 +461,7 @@ function testSelect(type, trueVal, falseVal) {
// Always false condition
var alwaysFalse = wasmEvalText(`
(module
(func (result ${type}) (param i32)
(func (param i32) (result ${type})
(select
(${type}.const ${trueVal})
(${type}.const ${falseVal})
@ -479,7 +479,7 @@ function testSelect(type, trueVal, falseVal) {
// Variable condition
var f = wasmEvalText(`
(module
(func (result ${type}) (param i32)
(func (param i32) (result ${type})
(select
(${type}.const ${trueVal})
(${type}.const ${falseVal})
@ -496,7 +496,7 @@ function testSelect(type, trueVal, falseVal) {
wasmFullPass(`
(module
(func (result ${type}) (param i32)
(func (param i32) (result ${type})
(select
(${type}.const ${trueVal})
(${type}.const ${falseVal})
@ -514,16 +514,16 @@ testSelect('i32', 13, 37);
testSelect('i32', Math.pow(2, 31) - 1, -Math.pow(2, 31));
testSelect('f32', Math.fround(13.37), Math.fround(19.89));
testSelect('f32', 'infinity', '-0');
testSelect('f32', 'inf', '-0');
testSelect('f32', 'nan', Math.pow(2, -31));
testSelect('f64', 13.37, 19.89);
testSelect('f64', 'infinity', '-0');
testSelect('f64', 'inf', '-0');
testSelect('f64', 'nan', Math.pow(2, -31));
wasmAssert(`
(module
(func $f (result i64) (param i32)
(func $f (param i32) (result i64)
(select
(i64.const 0xc0010ff08badf00d)
(i64.const 0x12345678deadc0de)

View File

@ -13,8 +13,8 @@ function unary(name) {
let f64 = Math[name];
let i = wasmEvalText(`(module
(import $f32 "math" "func" (param f32) (result f32))
(import $f64 "math" "func" (param f64) (result f64))
(import "math" "func" (func $f32 (param f32) (result f32)))
(import "math" "func" (func $f64 (param f64) (result f64)))
(table $t 10 funcref)
(type $f_f (func (param f32) (result f32)))
@ -62,8 +62,8 @@ function binary(name) {
let f64 = Math[name];
let i = wasmEvalText(`(module
(import $f32 "math" "func" (param f32) (param f32) (result f32))
(import $f64 "math" "func" (param f64) (param f64) (result f64))
(import "math" "func" (func $f32 (param f32) (param f32) (result f32)))
(import "math" "func" (func $f64 (param f64) (param f64) (result f64)))
(table $t 10 funcref)
(type $ff_f (func (param f32) (param f32) (result f32)))

View File

@ -1,5 +1,5 @@
// sanity check
assertErrorMessage(() => wasmEvalText(''), SyntaxError, /parsing wasm text/);
assertErrorMessage(() => wasmEvalText(''), SyntaxError, /wasm text error/);
// single line comment
var o = wasmEvalText('(module (func)) ;; end');
@ -25,7 +25,7 @@ assertEq(Object.getOwnPropertyNames(o)[0], "a");
var o = wasmEvalText('(module (;nested(;comment;);)(func (;;;;)))');
var o = wasmEvalText(';;;;;;;;;;\n(module ;;(;n \n(func (;\n;;;)))');
assertErrorMessage(() => wasmEvalText(';; only comment'), SyntaxError, /parsing wasm text/);
assertErrorMessage(() => wasmEvalText(';; only comment\n'), SyntaxError, /parsing wasm text/);
assertErrorMessage(() => wasmEvalText('(; only comment ;)'), SyntaxError, /parsing wasm text/);
assertErrorMessage(() => wasmEvalText(';; only comment\n'), SyntaxError, /parsing wasm text/);
assertErrorMessage(() => wasmEvalText(';; only comment'), SyntaxError, /wasm text error/);
assertErrorMessage(() => wasmEvalText(';; only comment\n'), SyntaxError, /wasm text error/);
assertErrorMessage(() => wasmEvalText('(; only comment ;)'), SyntaxError, /wasm text error/);
assertErrorMessage(() => wasmEvalText(';; only comment\n'), SyntaxError, /wasm text error/);

View File

@ -8,8 +8,8 @@ for (var i = 1000; i --> 0; ) {
var code = `(module
(func
(result f32)
(param f32)
(result f32)
${expr}
)
(export "run" (func 0))

View File

@ -6,7 +6,7 @@ function testConst(type, str, expected) {
}
function testConstError(type, str) {
assertErrorMessage(() => wasmEvalText(`(module (func (result ${type}) (${type}.const ${str})) (export "" (func 0)))`).exports[""](), Error, /parsing wasm text/);
assertErrorMessage(() => wasmEvalText(`(module (func (result ${type}) (${type}.const ${str})) (export "" (func 0)))`).exports[""](), Error, /wasm text error/);
}
testConst('i32', '0', 0);
@ -72,9 +72,9 @@ testConst('f32', '-0x0.0', -0.0);
testConst('f32', '-0x0', -0.0);
testConst('f32', '0x0.0p0', 0.0);
testConst('f32', '-0x0.0p0', -0.0);
testConst('f32', 'infinity', Infinity);
testConst('f32', '-infinity', -Infinity);
testConst('f32', '+infinity', Infinity);
testConst('f32', 'inf', Infinity);
testConst('f32', '-inf', -Infinity);
testConst('f32', '+inf', Infinity);
testConst('f32', 'nan', NaN);
//testConst('f32', '-nan', NaN); // TODO: NYI
testConst('f32', '+nan', NaN);
@ -100,8 +100,8 @@ testConst('f32', '0x1p-147', 5.605193857299268e-45);
testConst('f32', '0x1p-126', 1.1754943508222875e-38);
testConst('f32', '0x0.1fffffep+131', 3.4028234663852886e+38);
testConst('f32', '0x1.fffffep+127', 3.4028234663852886e+38);
testConst('f32', '0x2.0p+127', Infinity);
testConst('f32', '0x1.fffffep+128', Infinity);
testConstError('f32', '0x2.0p+127');
testConstError('f32', '0x1.fffffep+128');
testConst('f32', '0x0.1fffffep+128', 4.2535293329816107e+37);
testConst('f32', '0x1p2', 4);
testConst('f32', '0x10p2', 64);
@ -114,7 +114,7 @@ testConst('f32', '-0x1p+3', -8);
testConst('f32', '0x3p-2', .75);
testConst('f32', '-0x76.54p-32', -2.7550413506105542e-8);
testConst('f32', '0xf.ffffffffffffffffp+123', 170141183460469231731687303715884105728);
testConst('f32', '0xf.ffffffffffffffffp+124', Infinity);
testConstError('f32', '0xf.ffffffffffffffffp+124');
testConst('f32', '1.1754943508222875e-38', 1.1754943508222875e-38);
testConst('f32', '3.4028234663852886e+38', 3.4028234663852886e+38);
testConst('f32', '1.1754943508222875e-35', 1.1754943508222875e-35);
@ -139,7 +139,7 @@ testConst('f32', '-5.066758603788912e-7', -5.066758603788912e-7);
testConst('f32', '1.875000e-01', 1.875000e-01);
testConst('f32', '-0x1.b021fb98e9a17p-104', -8.322574059965897e-32);
testConst('f32', '0x1.08de5bf3f784cp-129', 1.5202715065429227e-39);
testConst('f32', '0x1.d50b969fbbfb3p+388', Infinity);
testConstError('f32', '0x1.d50b969fbbfb3p+388');
testConst('f32', '0x3434.2p4', 2.138260e+05);
testConst('f32', '0x1434.2p-120', 3.891074380317903e-33);
testConst('f32', '-0x0434.234p43', -9465807272673280);
@ -158,9 +158,9 @@ testConst('f64', '-0x0.0', -0.0);
testConst('f64', '-0x0', -0.0);
testConst('f64', '0x0.0p0', 0.0);
testConst('f64', '-0x0.0p0', -0.0);
testConst('f64', 'infinity', Infinity);
testConst('f64', '-infinity', -Infinity);
testConst('f64', '+infinity', Infinity);
testConst('f64', 'inf', Infinity);
testConst('f64', '-inf', -Infinity);
testConst('f64', '+inf', Infinity);
testConst('f64', 'nan', NaN);
//testConst('f64', '-nan', NaN); // TODO: NYI
testConst('f64', '+nan', NaN);

View File

@ -53,7 +53,7 @@ wasmFullPass(`(module
counter = 0;
var imports = { "":{inc() { counter++ }} };
wasmFullPass(`(module
(import "" "inc" (result i32))
(import "" "inc" (func (result i32)))
(func
(result i32)
(if (result i32)
@ -67,7 +67,7 @@ wasmFullPass(`(module
assertEq(counter, 0);
wasmFullPass(`(module
(import "" "inc" (result i32))
(import "" "inc" (func (result i32)))
(func
(result i32)
(if (result i32)
@ -81,7 +81,7 @@ wasmFullPass(`(module
assertEq(counter, 0);
wasmFullPass(`(module
(import "" "inc" (result i32))
(import "" "inc" (func (result i32)))
(func
(if
(i32.const 0)
@ -93,7 +93,7 @@ wasmFullPass(`(module
assertEq(counter, 0);
assertEq(wasmEvalText(`(module
(import "" "inc" (result i32))
(import "" "inc" (func (result i32)))
(func
(if
(i32.const 1)
@ -131,7 +131,7 @@ assertEq(counter, 1);
// One can chain if with if/if
counter = 0;
wasmFullPass(`(module
(import "" "inc" (result i32))
(import "" "inc" (func (result i32)))
(func
(result i32)
(if (result i32)
@ -256,8 +256,8 @@ var imports = {"": {
called() {called = true}
}};
wasmFullPass(`(module
(import "" "notcalled")
(import "" "called")
(import "" "notcalled" (func))
(import "" "called" (func))
(func
(block
(return (br 0))
@ -296,7 +296,7 @@ wasmFullPass('(module (func (block (br_if 0 (i32.const 1)))) (export "run" (func
wasmFullPass('(module (func (block (br_if 0 (i32.const 0)))) (export "run" (func 0)))', undefined);
wasmFullPass('(module (func (block $l (br_if $l (i32.const 1)))) (export "run" (func 0)))', undefined);
var isNonZero = wasmEvalText(`(module (func (result i32) (param i32)
var isNonZero = wasmEvalText(`(module (func (param i32) (result i32)
(block
(br_if 0 (local.get 0))
(return (i32.const 0))
@ -315,8 +315,8 @@ wasmFailValidateText('(module (func (result i32) (br 0 (f32.const 42))))', misma
wasmFailValidateText('(module (func (result i32) (block (br 0))))', emptyStackError);
wasmFailValidateText('(module (func (result i32) (block (result f32) (br 0 (f32.const 42)))))', mismatchError("f32", "i32"));
wasmFailValidateText(`(module (func (result i32) (param i32) (block (if (result i32) (local.get 0) (br 0 (i32.const 42))))) (export "" (func 0)))`, /if without else with a result value/);
wasmFailValidateText(`(module (func (result i32) (param i32) (block (result i32) (if (local.get 0) (drop (i32.const 42))) (br 0 (f32.const 42)))) (export "" (func 0)))`, mismatchError("f32", "i32"));
wasmFailValidateText(`(module (func (param i32) (result i32) (block (if (result i32) (local.get 0) (br 0 (i32.const 42))))) (export "" (func 0)))`, /if without else with a result value/);
wasmFailValidateText(`(module (func (param i32) (result i32) (block (result i32) (if (local.get 0) (drop (i32.const 42))) (br 0 (f32.const 42)))) (export "" (func 0)))`, mismatchError("f32", "i32"));
wasmFullPass('(module (func (result i32) (br 0 (i32.const 42)) (i32.const 13)) (export "run" (func 0)))', 42);
wasmFullPass('(module (func (result i32) (block (result i32) (br 0 (i32.const 42)) (i32.const 13))) (export "run" (func 0)))', 42);
@ -324,41 +324,41 @@ wasmFullPass('(module (func (result i32) (block (result i32) (br 0 (i32.const 42
wasmFailValidateText('(module (func) (func (block (result i32) (br 0 (call 0)) (i32.const 13))) (export "" (func 0)))', emptyStackError);
wasmFailValidateText('(module (func) (func (block (result i32) (br_if 0 (call 0) (i32.const 1)) (i32.const 13))) (export "" (func 0)))', emptyStackError);
var f = wasmEvalText(`(module (func (result i32) (param i32) (block (result i32) (if (local.get 0) (drop (i32.const 42))) (i32.const 43))) (export "" (func 0)))`).exports[""];
var f = wasmEvalText(`(module (func (param i32) (result i32) (block (result i32) (if (local.get 0) (drop (i32.const 42))) (i32.const 43))) (export "" (func 0)))`).exports[""];
assertEq(f(0), 43);
assertEq(f(1), 43);
wasmFailValidateText(`(module (func (result i32) (param i32) (block (result i32) (if (result i32) (local.get 0) (br 0 (i32.const 42))) (i32.const 43))) (export "" (func 0)))`, /if without else with a result value/);
wasmFailValidateText(`(module (func (param i32) (result i32) (block (result i32) (if (result i32) (local.get 0) (br 0 (i32.const 42))) (i32.const 43))) (export "" (func 0)))`, /if without else with a result value/);
var f = wasmEvalText(`(module (func (result i32) (param i32) (block (result i32) (if (local.get 0) (br 1 (i32.const 42))) (i32.const 43))) (export "" (func 0)))`).exports[""];
var f = wasmEvalText(`(module (func (param i32) (result i32) (block (result i32) (if (local.get 0) (br 1 (i32.const 42))) (i32.const 43))) (export "" (func 0)))`).exports[""];
assertEq(f(0), 43);
assertEq(f(1), 42);
wasmFailValidateText(`(module (func (result i32) (param i32) (block (br_if 0 (i32.const 42) (local.get 0)) (i32.const 43))) (export "" (func 0)))`, /unused values not explicitly dropped by end of block/);
wasmFailValidateText(`(module (func (param i32) (result i32) (block (br_if 0 (i32.const 42) (local.get 0)) (i32.const 43))) (export "" (func 0)))`, /unused values not explicitly dropped by end of block/);
var f = wasmEvalText(`(module (func (result i32) (param i32) (block (result i32) (drop (br_if 0 (i32.const 42) (local.get 0))) (i32.const 43))) (export "" (func 0)))`).exports[""];
var f = wasmEvalText(`(module (func (param i32) (result i32) (block (result i32) (drop (br_if 0 (i32.const 42) (local.get 0))) (i32.const 43))) (export "" (func 0)))`).exports[""];
assertEq(f(0), 43);
assertEq(f(1), 42);
var f = wasmEvalText(`(module (func (result i32) (param i32) (block (result i32) (if (local.get 0) (drop (i32.const 42))) (br 0 (i32.const 43)))) (export "" (func 0)))`).exports[""];
var f = wasmEvalText(`(module (func (param i32) (result i32) (block (result i32) (if (local.get 0) (drop (i32.const 42))) (br 0 (i32.const 43)))) (export "" (func 0)))`).exports[""];
assertEq(f(0), 43);
assertEq(f(1), 43);
wasmFailValidateText(`(module (func (result i32) (param i32) (block (result i32) (if (result i32) (local.get 0) (br 0 (i32.const 42))) (br 0 (i32.const 43)))) (export "" (func 0)))`, /if without else with a result value/);
wasmFailValidateText(`(module (func (param i32) (result i32) (block (result i32) (if (result i32) (local.get 0) (br 0 (i32.const 42))) (br 0 (i32.const 43)))) (export "" (func 0)))`, /if without else with a result value/);
var f = wasmEvalText(`(module (func (result i32) (param i32) (if (local.get 0) (br 1 (i32.const 42))) (br 0 (i32.const 43))) (export "" (func 0)))`).exports[""];
var f = wasmEvalText(`(module (func (param i32) (result i32) (if (local.get 0) (br 1 (i32.const 42))) (br 0 (i32.const 43))) (export "" (func 0)))`).exports[""];
assertEq(f(0), 43);
assertEq(f(1), 42);
var f = wasmEvalText(`(module (func (result i32) (param i32) (block (result i32) (if (local.get 0) (br 1 (i32.const 42))) (br 0 (i32.const 43)))) (export "" (func 0)))`).exports[""];
var f = wasmEvalText(`(module (func (param i32) (result i32) (block (result i32) (if (local.get 0) (br 1 (i32.const 42))) (br 0 (i32.const 43)))) (export "" (func 0)))`).exports[""];
assertEq(f(0), 43);
assertEq(f(1), 42);
var f = wasmEvalText(`(module (func (result i32) (param i32) (br_if 0 (i32.const 42) (local.get 0)) (br 0 (i32.const 43))) (export "" (func 0)))`).exports[""];
var f = wasmEvalText(`(module (func (param i32) (result i32) (br_if 0 (i32.const 42) (local.get 0)) (br 0 (i32.const 43))) (export "" (func 0)))`).exports[""];
assertEq(f(0), 43);
assertEq(f(1), 42);
var f = wasmEvalText(`(module (func (result i32) (param i32) (block (result i32) (br_if 0 (i32.const 42) (local.get 0)) (br 0 (i32.const 43)))) (export "" (func 0)))`).exports[""];
var f = wasmEvalText(`(module (func (param i32) (result i32) (block (result i32) (br_if 0 (i32.const 42) (local.get 0)) (br 0 (i32.const 43)))) (export "" (func 0)))`).exports[""];
assertEq(f(0), 43);
assertEq(f(1), 42);
@ -392,8 +392,8 @@ var imports = {
}
}
var f = wasmEvalText(`(module
(import "sideEffects" "ifTrue" (param i32))
(import "sideEffects" "ifFalse" (param i32))
(import "sideEffects" "ifTrue" (func (param i32)))
(import "sideEffects" "ifFalse" (func (param i32)))
(func
(param i32) (result i32)
(block $outer
@ -415,17 +415,19 @@ assertEq(f(1), 42);
assertEq(called, 0);
// br/br_if and loop
wasmFullPass(`(module (func (param i32) (result i32) (loop $out $in i32 (br $out (local.get 0)))) (export "run" (func 0)))`, 1, {}, 1);
wasmFullPass(`(module (func (param i32) (result i32) (block $out (result i32) (loop $in (result i32) (br $out (local.get 0))))) (export "run" (func 0)))`, 1, {}, 1);
wasmFullPass(`(module (func (param i32) (result i32) (loop $in (result i32) (br 1 (local.get 0)))) (export "run" (func 0)))`, 1, {}, 1);
wasmFullPass(`(module (func (param i32) (result i32) (block $out (result i32) (loop $in (result i32) (br $out (local.get 0))))) (export "run" (func 0)))`, 1, {}, 1);
wasmFailValidateText(`(module (func (param i32) (result i32)
(loop $out $in
(if (local.get 0) (br $in (i32.const 1)))
(if (local.get 0) (br $in (f32.const 2)))
(if (local.get 0) (br $in (f64.const 3)))
(if (local.get 0) (br $in))
(i32.const 7)
(block $out
(loop $in
(if (local.get 0) (br $in (i32.const 1)))
(if (local.get 0) (br $in (f32.const 2)))
(if (local.get 0) (br $in (f64.const 3)))
(if (local.get 0) (br $in))
(i32.const 7)
)
)
) (export "" (func 0)))`, /unused values not explicitly dropped by end of block/);
@ -472,23 +474,9 @@ wasmFullPass('(module (func (result i32) (loop (drop (i32.const 2))) (i32.const
wasmFullPass('(module (func (loop (br 1))) (export "run" (func 0)))', undefined);
wasmFullPass('(module (func (loop $a (br 1))) (export "run" (func 0)))', undefined);
wasmFullPass('(module (func (loop $a (br_if $a (i32.const 0)))) (export "run" (func 0)))', undefined);
wasmFullPass('(module (func (loop $a $b (br $a))) (export "run" (func 0)))', undefined);
wasmFullPass('(module (func (block $a (loop $b (br $a)))) (export "run" (func 0)))', undefined);
wasmFullPass('(module (func (result i32) (loop (result i32) (i32.const 1))) (export "run" (func 0)))', 1);
wasmFullPass(`(module (func (result i32) (local i32)
(loop
$break $continue
(if
(i32.gt_u (local.get 0) (i32.const 5))
(br $break)
)
(local.set 0 (i32.add (local.get 0) (i32.const 1)))
(br $continue)
)
(return (local.get 0))
) (export "run" (func 0)))`, 6);
wasmFullPass(`(module (func (result i32) (local i32)
(block
$break
@ -505,19 +493,6 @@ wasmFullPass(`(module (func (result i32) (local i32)
(return (local.get 0))
) (export "run" (func 0)))`, 6);
wasmFullPass(`(module (func (result i32) (local i32)
(loop
$break $continue
(br_if
$break
(i32.gt_u (local.get 0) (i32.const 5))
)
(local.set 0 (i32.add (local.get 0) (i32.const 1)))
(br $continue)
)
(return (local.get 0))
) (export "run" (func 0)))`, 6);
wasmFullPass(`(module (func (result i32) (local i32)
(block
$break
@ -534,18 +509,6 @@ wasmFullPass(`(module (func (result i32) (local i32)
(return (local.get 0))
) (export "run" (func 0)))`, 6);
wasmFullPass(`(module (func (result i32) (local i32)
(loop
$break $continue
(local.set 0 (i32.add (local.get 0) (i32.const 1)))
(br_if
$continue
(i32.le_u (local.get 0) (i32.const 5))
)
)
(return (local.get 0))
) (export "run" (func 0)))`, 6);
wasmFullPass(`(module (func (result i32) (local i32)
(block
$break
@ -561,22 +524,6 @@ wasmFullPass(`(module (func (result i32) (local i32)
(return (local.get 0))
) (export "run" (func 0)))`, 6);
wasmFullPass(`(module (func (result i32) (local i32)
(loop
$break $continue
(br_if
$break
(i32.gt_u (local.get 0) (i32.const 5))
)
(local.set 0 (i32.add (local.get 0) (i32.const 1)))
(loop
(br $continue)
)
(return (i32.const 42))
)
(return (local.get 0))
) (export "run" (func 0)))`, 6);
wasmFullPass(`(module (func (result i32) (local i32)
(block
$break
@ -596,21 +543,6 @@ wasmFullPass(`(module (func (result i32) (local i32)
(return (local.get 0))
) (export "run" (func 0)))`, 6);
wasmFullPass(`(module (func (result i32) (local i32)
(loop
$break $continue
(local.set 0 (i32.add (local.get 0) (i32.const 1)))
(loop
(br_if
$continue
(i32.le_u (local.get 0) (i32.const 5))
)
)
(br $break)
)
(return (local.get 0))
) (export "run" (func 0)))`, 6);
wasmFullPass(`(module (func (result i32) (local i32)
(block
$break
@ -642,7 +574,7 @@ wasmFailValidateText('(module (func (loop (br_table 2 0 (i32.const 0)))))', DEPT
wasmFailValidateText('(module (func (loop (br_table 0 2 (i32.const 0)))))', DEPTH_OUT_OF_BOUNDS);
wasmFailValidateText('(module (func (loop (br_table 0 (f32.const 0)))))', mismatchError("f32", "i32"));
wasmFullPass(`(module (func (result i32) (param i32)
wasmFullPass(`(module (func (param i32) (result i32)
(block $default
(br_table $default (local.get 0))
(return (i32.const 0))
@ -650,7 +582,7 @@ wasmFullPass(`(module (func (result i32) (param i32)
(return (i32.const 1))
) (export "run" (func 0)))`, 1);
wasmFullPass(`(module (func (result i32) (param i32)
wasmFullPass(`(module (func (param i32) (result i32)
(block $default
(br_table $default (return (i32.const 1)))
(return (i32.const 0))
@ -658,7 +590,7 @@ wasmFullPass(`(module (func (result i32) (param i32)
(return (i32.const 2))
) (export "run" (func 0)))`, 1);
wasmFullPass(`(module (func (result i32) (param i32)
wasmFullPass(`(module (func (param i32) (result i32)
(block $outer
(block $inner
(br_table $inner (local.get 0))
@ -669,7 +601,7 @@ wasmFullPass(`(module (func (result i32) (param i32)
(return (i32.const 2))
) (export "run" (func 0)))`, 1);
var f = wasmEvalText(`(module (func (result i32) (param i32)
var f = wasmEvalText(`(module (func (param i32) (result i32)
(block $0
(block $1
(block $2

View File

@ -216,26 +216,26 @@ testConversion('i64', 'trunc_u', 'f32', 18446742974197923840.0, "0xffffff0000000
testTrap('i64', 'trunc_s', 'f64', 9223372036854776000.0);
testTrap('i64', 'trunc_s', 'f64', -9223372036854778000.0);
testTrap('i64', 'trunc_s', 'f64', "nan");
testTrap('i64', 'trunc_s', 'f64', "infinity");
testTrap('i64', 'trunc_s', 'f64', "-infinity");
testTrap('i64', 'trunc_s', 'f64', "inf");
testTrap('i64', 'trunc_s', 'f64', "-inf");
testTrap('i64', 'trunc_u', 'f64', -1);
testTrap('i64', 'trunc_u', 'f64', 18446744073709551616.0);
testTrap('i64', 'trunc_u', 'f64', "nan");
testTrap('i64', 'trunc_u', 'f64', "infinity");
testTrap('i64', 'trunc_u', 'f64', "-infinity");
testTrap('i64', 'trunc_u', 'f64', "inf");
testTrap('i64', 'trunc_u', 'f64', "-inf");
testTrap('i64', 'trunc_s', 'f32', 9223372036854776000.0);
testTrap('i64', 'trunc_s', 'f32', -9223372586610630000.0);
testTrap('i64', 'trunc_s', 'f32', "nan");
testTrap('i64', 'trunc_s', 'f32', "infinity");
testTrap('i64', 'trunc_s', 'f32', "-infinity");
testTrap('i64', 'trunc_s', 'f32', "inf");
testTrap('i64', 'trunc_s', 'f32', "-inf");
testTrap('i64', 'trunc_u', 'f32', 18446744073709551616.0);
testTrap('i64', 'trunc_u', 'f32', -1);
testTrap('i64', 'trunc_u', 'f32', "nan");
testTrap('i64', 'trunc_u', 'f32', "infinity");
testTrap('i64', 'trunc_u', 'f32', "-infinity");
testTrap('i64', 'trunc_u', 'f32', "inf");
testTrap('i64', 'trunc_u', 'f32', "-inf");
testConversion('i64', 'reinterpret', 'f64', 40.09999999999968, "0x40440ccccccccca0");
testConversion('f64', 'reinterpret', 'i64', "0x40440ccccccccca0", 40.09999999999968);
@ -273,26 +273,26 @@ testConversion('i32', 'trunc_u:sat', 'f64', p(2, 32), -1);
testConversion('i64', 'trunc_s:sat', 'f64', 9223372036854776000.0, s64max);
testConversion('i64', 'trunc_s:sat', 'f64', -9223372036854778000.0, s64min);
testConversion('i64', 'trunc_s:sat', 'f64', 'nan', '0');
testConversion('i64', 'trunc_s:sat', 'f64', 'infinity', s64max);
testConversion('i64', 'trunc_s:sat', 'f64', '-infinity', s64min);
testConversion('i64', 'trunc_s:sat', 'f64', 'inf', s64max);
testConversion('i64', 'trunc_s:sat', 'f64', '-inf', s64min);
testConversion('i64', 'trunc_u:sat', 'f64', -1, '0');
testConversion('i64', 'trunc_u:sat', 'f64', 18446744073709551616.0, u64max);
testConversion('i64', 'trunc_u:sat', 'f64', 'nan', '0');
testConversion('i64', 'trunc_u:sat', 'f64', 'infinity', u64max);
testConversion('i64', 'trunc_u:sat', 'f64', '-infinity', '0');
testConversion('i64', 'trunc_u:sat', 'f64', 'inf', u64max);
testConversion('i64', 'trunc_u:sat', 'f64', '-inf', '0');
testConversion('i64', 'trunc_s:sat', 'f32', 9223372036854776000.0, s64max);
testConversion('i64', 'trunc_s:sat', 'f32', -9223372586610630000.0, s64min);
testConversion('i64', 'trunc_s:sat', 'f32', 'nan', '0');
testConversion('i64', 'trunc_s:sat', 'f32', 'infinity', s64max);
testConversion('i64', 'trunc_s:sat', 'f32', '-infinity', s64min);
testConversion('i64', 'trunc_s:sat', 'f32', 'inf', s64max);
testConversion('i64', 'trunc_s:sat', 'f32', '-inf', s64min);
testConversion('i64', 'trunc_u:sat', 'f32', 18446744073709551616.0, u64max);
testConversion('i64', 'trunc_u:sat', 'f32', -1, '0');
testConversion('i64', 'trunc_u:sat', 'f32', 'nan', '0');
testConversion('i64', 'trunc_u:sat', 'f32', 'infinity', u64max);
testConversion('i64', 'trunc_u:sat', 'f32', '-infinity', '0');
testConversion('i64', 'trunc_u:sat', 'f32', 'inf', u64max);
testConversion('i64', 'trunc_u:sat', 'f32', '-inf', '0');
testSignExtension('i32', 'extend8_s', 'i32', 0x7F, 0x7F);
testSignExtension('i32', 'extend8_s', 'i32', 0x80, -0x80);
@ -312,8 +312,8 @@ testConversion('i32', 'trunc_s', 'f32', p(2, 31) - 128, p(2, 31) - 128); // last
testConversion('i32', 'trunc_s', 'f32', -p(2, 31), -p(2,31)); // last f32 value exactly representable > -2**31 - 1.
testTrap('i32', 'trunc_s', 'f32', 'nan');
testTrap('i32', 'trunc_s', 'f32', 'infinity');
testTrap('i32', 'trunc_s', 'f32', '-infinity');
testTrap('i32', 'trunc_s', 'f32', 'inf');
testTrap('i32', 'trunc_s', 'f32', '-inf');
testTrap('i32', 'trunc_s', 'f32', p(2, 31));
testTrap('i32', 'trunc_s', 'f32', -p(2,31) - 256);
@ -323,8 +323,8 @@ testConversion('i32', 'trunc_s', 'f64', -p(2,31) - 0.999, -p(2,31)); // example
// f64:
testTrap('i32', 'trunc_s', 'f64', 'nan');
testTrap('i32', 'trunc_s', 'f64', 'infinity');
testTrap('i32', 'trunc_s', 'f64', '-infinity');
testTrap('i32', 'trunc_s', 'f64', 'inf');
testTrap('i32', 'trunc_s', 'f64', '-inf');
testTrap('i32', 'trunc_s', 'f64', p(2,31));
testTrap('i32', 'trunc_s', 'f64', -p(2,31) - 1);
@ -336,8 +336,8 @@ testConversion('i32', 'trunc_u', 'f32', p(2,32) - 256, (p(2,32) - 256)|0); // la
testConversion('i32', 'trunc_u', 'f32', -0.99, 0); // example value near the bottom.
testTrap('i32', 'trunc_u', 'f32', 'nan');
testTrap('i32', 'trunc_u', 'f32', 'infinity');
testTrap('i32', 'trunc_u', 'f32', '-infinity');
testTrap('i32', 'trunc_u', 'f32', 'inf');
testTrap('i32', 'trunc_u', 'f32', '-inf');
testTrap('i32', 'trunc_u', 'f32', -1);
testTrap('i32', 'trunc_u', 'f32', p(2,32));
@ -347,8 +347,8 @@ testConversion('i32', 'trunc_u', 'f64', p(2,32) - 0.001, (p(2,32) - 1)|0); // ex
testConversion('i32', 'trunc_u', 'f64', -0.99999, 0); // example value near the bottom.
testTrap('i32', 'trunc_u', 'f64', 'nan');
testTrap('i32', 'trunc_u', 'f64', 'infinity');
testTrap('i32', 'trunc_u', 'f64', '-infinity');
testTrap('i32', 'trunc_u', 'f64', 'inf');
testTrap('i32', 'trunc_u', 'f64', '-inf');
testTrap('i32', 'trunc_u', 'f64', -1);
testTrap('i32', 'trunc_u', 'f64', p(2,32));

View File

@ -4,7 +4,7 @@
wasmFullPass(`
(module
(func $f1)
(elem declared $f1)
(elem declare $f1)
(func $run)
(export "run" (func $run))
)
@ -12,12 +12,12 @@ wasmFullPass(`
// Declared segments cannot use ref.null
assertThrowsInstanceOf(() => {
wasmTextToBinary(`
new WebAssembly.Module(wasmTextToBinary(`
(module
(elem declared (ref.null))
(elem declare (ref.null))
)
`)
}, SyntaxError);
`))
}, WebAssembly.CompileError);
// Declared segments cannot be used by bulk-memory operations
function test(ins) {
@ -26,7 +26,7 @@ function test(ins) {
(module
(func $f1)
(table 1 1 funcref)
(elem declared $f1)
(elem declare $f1)
(func $start ${ins})
(start $start)
)
@ -41,7 +41,7 @@ wasmAssert(`
(module
(func $f1)
(table 1 1 funcref)
(elem declared $f1)
(elem declare $f1)
(func $at (param i32) (result i32)
local.get 0
table.get 0

View File

@ -1,7 +1,7 @@
for (let type of ['i32', 'f32', 'f64']) {
assertEq(wasmEvalText(`
(module
(func $test (result ${type}) (param $p ${type}) (param $p2 ${type})
(func $test (param $p ${type}) (param $p2 ${type}) (result ${type})
local.get $p
local.get $p2
(block)
@ -14,7 +14,7 @@ for (let type of ['i32', 'f32', 'f64']) {
assertEq(wasmEvalText(`
(module
(func $test (result i32) (param $p i32) (param $p2 f32) (param $p3 f64) (param $p4 i32)
(func $test (param $p i32) (param $p2 f32) (param $p3 f64) (param $p4 i32) (result i32)
local.get $p
local.get $p2
local.get $p3
@ -32,7 +32,7 @@ assertEq(wasmEvalText(`
wasmAssert(`
(module
(func $test (result i64) (param $p i64) (param $p2 i64)
(func $test (param $p i64) (param $p2 i64) (result i64)
local.get $p
local.get $p2
(block)

View File

@ -1,5 +1,5 @@
wasmFullPass(`(module
(func $test (result i32) (param i32) (param i32) (i32.add (local.get 0) (local.get 1)))
(func $test (param i32) (param i32) (result i32) (i32.add (local.get 0) (local.get 1)))
(func $run (result i32) (call $test (i32.const 1) (i32.const ${Math.pow(2, 31) - 1})))
(export "run" (func $run))
)`, -Math.pow(2, 31));
@ -28,7 +28,7 @@ wasmFullPass(`
// Global section.
wasmFullPass(`(module
(import $imported "globals" "x" (global i32))
(import "globals" "x" (global $imported i32))
(global $mut_local (mut i32) (i32.const 0))
(global $imm_local i32 (i32.const 37))
(global $imm_local_2 i32 (global.get 0))
@ -123,7 +123,7 @@ for (let [p, result] of [
[42, 4]
]) {
wasmFullPass(`(module
(func (export "run") (result i32) (param $p i32) (local $n i32)
(func (export "run") (param $p i32) (result i32) (local $n i32)
i32.const 0
local.set $n
block $c block $b block $a

View File

@ -1,9 +1,10 @@
const { Instance, Module, LinkError } = WebAssembly;
// Locally-defined globals
assertErrorMessage(() => wasmEvalText(`(module (global))`), SyntaxError, /parsing/);
assertErrorMessage(() => wasmEvalText(`(module (global i32))`), SyntaxError, /parsing/);
assertErrorMessage(() => wasmEvalText(`(module (global (mut i32)))`), SyntaxError, /parsing/);
assertErrorMessage(() => wasmEvalText(`(module (global))`), SyntaxError, /wasm text error/);
// A global field in the text format is valid with an empty expression, but this produces an invalid module
assertErrorMessage(() => wasmEvalText(`(module (global i32))`), WebAssembly.CompileError, /unexpected initializer expression/);
assertErrorMessage(() => wasmEvalText(`(module (global (mut i32)))`), WebAssembly.CompileError, /unexpected initializer expression/);
// Initializer expressions.
wasmFailValidateText(`(module (global i32 (f32.const 13.37)))`, /type mismatch/);
@ -108,10 +109,10 @@ assertEq(module.f, module.tbl.get(1));
// Import/export semantics.
module = wasmEvalText(`(module
(import $g "globals" "x" (global i32))
(import "globals" "x" (global $g i32))
(func $get (result i32) (global.get $g))
(export "getter" (func $get))
(export "value" global 0)
(export "value" (global 0))
)`, { globals: {x: 42} }).exports;
assertEq(module.getter(), 42);
@ -168,8 +169,8 @@ for (let v of [
module = wasmEvalText(`(module
(import "globals" "x" (global i32))
(global i32 (i32.const 1337))
(export "imported" global 0)
(export "defined" global 1)
(export "imported" (global 0))
(export "defined" (global 1))
)`, { globals: {x: 42} }).exports;
assertEq(Number(module.imported), 42);
@ -352,15 +353,15 @@ wasmAssert(`(module
// When a global is exported twice, the two objects are the same.
let i = wasmEvalText(`(module
(global i32 (i32.const 0))
(export "a" global 0)
(export "b" global 0))`);
(export "a" (global 0))
(export "b" (global 0)))`);
assertEq(i.exports.a, i.exports.b);
// When a global is imported and then exported, the exported object is
// the same as the imported object.
let j = wasmEvalText(`(module
(import "" "a" (global i32))
(export "x" global 0))`,
(export "x" (global 0)))`,
{ "": {a: i.exports.a}});
assertEq(i.exports.a, j.exports.x);
@ -371,8 +372,8 @@ wasmAssert(`(module
let k = wasmEvalText(`(module
(import "" "a" (global i32))
(import "" "b" (global i32))
(export "x" global 0)
(export "y" global 1))`,
(export "x" (global 0))
(export "y" (global 1)))`,
{ "": {a: i.exports.a,
b: i.exports.a}});

View File

@ -2,43 +2,43 @@
// signatures, in the test mode only, for fuzzers.
var module = new WebAssembly.Module(wasmTextToBinary(`(module
(import $vv "env" "v_v")
(import "env" "v_v" (func $vv))
(export "v_v" (func $vv))
(import $vi "env" "v_i" (param i32))
(import "env" "v_i" (func $vi (param i32)))
(export "v_i" (func $vi))
(import $vI "env" "v_I" (param i64))
(import "env" "v_I" (func $vI (param i64)))
(export "v_I" (func $vI))
(import $vf "env" "v_f" (param f32))
(import "env" "v_f" (func $vf (param f32)))
(export "v_f" (func $vf))
(import $mem "env" "memory" (memory 0))
(import "env" "memory" (memory $mem 0))
(export "mem" (memory $mem))
(import $vd "env" "v_d" (param f64))
(import "env" "v_d" (func $vd (param f64)))
(export "v_d" (func $vd))
(import $vfd "env" "v_fd" (param f32) (param f64))
(import "env" "v_fd" (func $vfd (param f32) (param f64)))
(export "v_fd" (func $vfd))
(import $vIfifd "env" "v_Ififd" (param i64) (param f32) (param i32) (param f32) (param f64))
(import "env" "v_Ififd" (func $vIfifd (param i64) (param f32) (param i32) (param f32) (param f64)))
(export "v_Ififd" (func $vIfifd))
(import $iv "env" "i_v" (result i32))
(import "env" "i_v" (func $iv (result i32)))
(export "i_v" (func $iv))
(import $Ii "env" "I_i" (result i64) (param i32))
(import "env" "I_i" (func $Ii (param i32) (result i64)))
(export "I_i" (func $Ii))
(import $table "env" "table" (table 0 funcref))
(import "env" "table" (table $table 0 funcref))
(export "table" (table $table))
(import $fd "env" "f_d" (result f32) (param f64))
(import "env" "f_d" (func $fd (param f64) (result f32)))
(export "f_d" (func $fd))
(import $dffd "env" "d_ffd" (result f64) (param f32) (param f32) (param f64))
(import "env" "d_ffd" (func $dffd (param f32) (param f32) (param f64) (result f64)))
(export "d_ffd" (func $dffd))
)`));

View File

@ -44,7 +44,7 @@ assertErrorMessage(() => new Table({initial:10000001, element:"funcref"}), Range
new Table({ initial: 0, maximum: 10000000, element:"funcref" });
assertErrorMessage(() => new Table({initial:0, maximum: 10000001, element:"funcref"}), RangeError, /bad Table maximum size/);
const m1 = new Module(wasmTextToBinary('(module (import "foo" "bar") (import "baz" "quux"))'));
const m1 = new Module(wasmTextToBinary('(module (import "foo" "bar" (func)) (import "baz" "quux" (func)))'));
assertErrorMessage(() => new Instance(m1), TypeError, /second argument must be an object/);
assertErrorMessage(() => new Instance(m1, {foo:null}), TypeError, /import object field 'foo' is not an Object/);
assertErrorMessage(() => new Instance(m1, {foo:{bar:{}}}), LinkError, /import object field 'bar' is not a Function/);
@ -67,7 +67,7 @@ assertEq(new Instance(m2, {x:{y:mem3PageMax3}}) instanceof Instance, true);
assertEq(new Instance(m2, {x:{y:mem2PageMax3}}) instanceof Instance, true);
assertErrorMessage(() => new Instance(m2, {x:{y:mem2PageMax4}}), LinkError, /imported Memory with incompatible maximum size/);
const m3 = new Module(wasmTextToBinary('(module (import "foo" "bar" (memory 1 1)) (import "baz" "quux"))'));
const m3 = new Module(wasmTextToBinary('(module (import "foo" "bar" (memory 1 1)) (import "baz" "quux" (func)))'));
assertErrorMessage(() => new Instance(m3), TypeError, /second argument must be an object/);
assertErrorMessage(() => new Instance(m3, {foo:null}), TypeError, /import object field 'foo' is not an Object/);
assertErrorMessage(() => new Instance(m3, {foo:{bar:{}}}), LinkError, /import object field 'bar' is not a Memory/);
@ -76,7 +76,7 @@ assertErrorMessage(() => new Instance(m3, {foo:{bar:mem1Page}, baz:{quux:mem1Pag
assertErrorMessage(() => new Instance(m3, {foo:{bar:mem1Page}, baz:{quux:()=>{}}}), LinkError, /imported Memory with incompatible maximum size/);
assertEq(new Instance(m3, {foo:{bar:mem1PageMax1}, baz:{quux:()=>{}}}) instanceof Instance, true);
const m4 = new Module(wasmTextToBinary('(module (import "baz" "quux") (import "foo" "bar" (memory 1 1)))'));
const m4 = new Module(wasmTextToBinary('(module (import "baz" "quux" (func)) (import "foo" "bar" (memory 1 1)))'));
assertErrorMessage(() => new Instance(m4), TypeError, /second argument must be an object/);
assertErrorMessage(() => new Instance(m4, {baz:null}), TypeError, /import object field 'baz' is not an Object/);
assertErrorMessage(() => new Instance(m4, {baz:{quux:{}}}), LinkError, /import object field 'quux' is not a Function/);
@ -111,13 +111,13 @@ wasmFailValidateText('(module (import "a" "b" (table 2 1 funcref)))', /maximum l
// Import wasm-wasm type mismatch
var e = wasmEvalText('(module (func $i2v (param i32)) (export "i2v" (func $i2v)) (func $f2v (param f32)) (export "f2v" (func $f2v)))').exports;
var i2vm = new Module(wasmTextToBinary('(module (import "a" "b" (param i32)))'));
var f2vm = new Module(wasmTextToBinary('(module (import "a" "b" (param f32)))'));
var i2vm = new Module(wasmTextToBinary('(module (import "a" "b" (func (param i32))))'));
var f2vm = new Module(wasmTextToBinary('(module (import "a" "b" (func (param f32))))'));
assertEq(new Instance(i2vm, {a:{b:e.i2v}}) instanceof Instance, true);
assertErrorMessage(() => new Instance(i2vm, {a:{b:e.f2v}}), LinkError, /imported function 'a.b' signature mismatch/);
assertErrorMessage(() => new Instance(f2vm, {a:{b:e.i2v}}), LinkError, /imported function 'a.b' signature mismatch/);
assertEq(new Instance(f2vm, {a:{b:e.f2v}}) instanceof Instance, true);
var l2vm = new Module(wasmTextToBinary('(module (import "x" "y" (memory 1)) (import "c" "d" (param i64)))'));
var l2vm = new Module(wasmTextToBinary('(module (import "x" "y" (memory 1)) (import "c" "d" (func (param i64))))'));
assertErrorMessage(() => new Instance(l2vm, {x:{y:mem1Page}, c:{d:e.i2v}}), LinkError, /imported function 'c.d' signature mismatch/);
// Import order:
@ -301,10 +301,10 @@ assertEq(e.tbl1.get(0), e.tbl1.get(3));
var args;
var m = new Module(wasmTextToBinary(`(module
(export "a" (func $a)) (import $a "" "a" (param f32))
(export "b" (func $b)) (import $b "" "b" (param i32) (result i32))
(export "c" (func $c)) (import $c "" "c" (result i32))
(export "d" (func $d)) (import $d "" "d")
(export "a" (func $a)) (import "" "a" (func $a (param f32)))
(export "b" (func $b)) (import "" "b" (func $b (param i32) (result i32)))
(export "c" (func $c)) (import "" "c" (func $c (result i32)))
(export "d" (func $d)) (import "" "d" (func $d))
)`));
var js = function() { args = arguments; return 42 }
var e = new Instance(m, {"":{a:js, b:js, c:js, d:js}}).exports;
@ -360,9 +360,9 @@ assertEq(tbl.get(0) === e1.foo, false);
assertEq(e1.foo === e2.foo, false);
var m = new Module(wasmTextToBinary(`(module
(import "" "foo" (func $foo (result i32)))
(import "" "bar" (func $bar (result i32)))
(table 3 funcref)
(import $foo "" "foo" (result i32))
(import $bar "" "bar" (result i32))
(func $baz (result i32) (i32.const 13))
(elem (i32.const 0) $foo $bar $baz)
(export "foo" (func $foo))
@ -414,14 +414,14 @@ assertEq(e4.baz, e4.tbl.get(2));
var code1 = wasmTextToBinary('(module (func $exp (param i64) (result i64) (i64.add (local.get 0) (i64.const 10))) (export "exp" (func $exp)))');
var e1 = new Instance(new Module(code1)).exports;
var code2 = wasmTextToBinary('(module (import $i "a" "b" (param i64) (result i64)) (func $f (result i32) (i32.wrap/i64 (call $i (i64.const 42)))) (export "f" (func $f)))');
var code2 = wasmTextToBinary('(module (import "a" "b" (func $i (param i64) (result i64))) (func $f (result i32) (i32.wrap/i64 (call $i (i64.const 42)))) (export "f" (func $f)))');
var e2 = new Instance(new Module(code2), {a:{b:e1.exp}}).exports;
assertEq(e2.f(), 52);
// Non-existent export errors
wasmFailValidateText('(module (export "a" (func 0)))', /exported function index out of bounds/);
wasmFailValidateText('(module (export "a" global 0))', /exported global index out of bounds/);
wasmFailValidateText('(module (export "a" (global 0)))', /exported global index out of bounds/);
wasmFailValidateText('(module (export "a" (memory 0)))', /exported memory index out of bounds/);
wasmFailValidateText('(module (export "a" (table 0)))', /exported table index out of bounds/);
@ -492,8 +492,8 @@ var m = new Module(wasmTextToBinary(`
(module
(import "a" "mem" (memory 1))
(import "a" "tbl" (table 1 funcref))
(import $memOff "a" "memOff" (global i32))
(import $tblOff "a" "tblOff" (global i32))
(import "a" "memOff" (global $memOff i32))
(import "a" "tblOff" (global $tblOff i32))
(func $f)
(func $g)
(data (i32.const 0) "\\01")
@ -647,7 +647,7 @@ assertEq(tbl.get(3)(), undefined);
// Cross-instance calls
var i1 = new Instance(new Module(wasmTextToBinary(`(module (func) (func (param i32) (result i32) (i32.add (local.get 0) (i32.const 1))) (func) (export "f" (func 1)))`)));
var i2 = new Instance(new Module(wasmTextToBinary(`(module (import $imp "a" "b" (param i32) (result i32)) (func $g (result i32) (call $imp (i32.const 13))) (export "g" (func $g)))`)), {a:{b:i1.exports.f}});
var i2 = new Instance(new Module(wasmTextToBinary(`(module (import "a" "b" (func $imp (param i32) (result i32))) (func $g (result i32) (call $imp (i32.const 13))) (export "g" (func $g)))`)), {a:{b:i1.exports.f}});
assertEq(i2.exports.g(), 14);
var i1 = new Instance(new Module(wasmTextToBinary(`(module
@ -657,7 +657,7 @@ var i1 = new Instance(new Module(wasmTextToBinary(`(module
(export "f" (func $f))
)`)));
var i2 = new Instance(new Module(wasmTextToBinary(`(module
(import $imp "a" "b" (result i32))
(import "a" "b" (func $imp (result i32)))
(memory 1 1)
(data (i32.const 0) "\\13")
(table 2 2 funcref)
@ -671,8 +671,8 @@ assertEq(i2.exports.call(0), 0x42);
assertEq(i2.exports.call(1), 0x13);
var m = new Module(wasmTextToBinary(`(module
(import $val "a" "val" (global i32))
(import $next "a" "next" (result i32))
(import "a" "val" (global $val i32))
(import "a" "next" (func $next (result i32)))
(memory 1)
(func $start (i32.store (i32.const 0) (global.get $val)))
(start $start)
@ -721,11 +721,11 @@ assertEq(e.call(), 1090);
};
i = wasmEvalText(`(module
(import $ffi "a" "ffi" (param i32) (result i32))
(import "a" "ffi" (func $ffi (param i32) (result i32)))
(import $missingOneArg "a" "sum" (param i32) (param i32) (result i32))
(import $missingTwoArgs "a" "sum" (param i32) (result i32))
(import $missingThreeArgs "a" "sum" (result i32))
(import "a" "sum" (func $missingOneArg (param i32) (param i32) (result i32)))
(import "a" "sum" (func $missingTwoArgs (param i32) (result i32)))
(import "a" "sum" (func $missingThreeArgs (result i32)))
(func (export "foo") (param i32) (result i32)
local.get 0
@ -788,8 +788,8 @@ assertEq(e.call(), 1090);
// we call it here.
var i1 = new Instance(new Module(wasmTextToBinary(`
(module
(import $imp1 "a" "f1" (result i32))
(import $imp2 "a" "f2" (result i32))
(import "a" "f1" (func $imp1 (result i32)))
(import "a" "f2" (func $imp2 (result i32)))
(import "a" "m" (memory 1))
(func $test (result i32)
(i32.add
@ -809,7 +809,7 @@ assertEq(e.call(), 1090);
// Inter-module/inter-realm wasm => wasm calls.
var src = `
(module
(import $imp "a" "othertest" (result i32))
(import "a" "othertest" (func $imp (result i32)))
(import "a" "m" (memory 1))
(func (result i32) (i32.add (call $imp) (memory.size)))
(export "test" (func 1)))

View File

@ -6,7 +6,7 @@ const Module = WebAssembly.Module;
const Instance = WebAssembly.Instance;
const m1 = new Module(wasmTextToBinary(`(module (func $f) (export "f" (func $f)))`));
const m2 = new Module(wasmTextToBinary(`(module (import "a" "f") (func $f) (export "g" (func $f)))`));
const m2 = new Module(wasmTextToBinary(`(module (import "a" "f" (func)) (func $f) (export "g" (func $f)))`));
// Imported instance objects should stay alive as long as any importer is alive.
resetFinalizeCount();

View File

@ -1,20 +1,21 @@
let { exports } = wasmEvalText(`(module
(func (export "i32") (result i32) (param i32)
(func (export "i32") (param i32) (result i32)
local.get 0
)
(func (export "f32") (result f32) (param f32)
(func (export "f32") (param f32) (result f32)
local.get 0
)
(func (export "f64") (result f64) (param f64)
(func (export "f64") (param f64) (result f64)
local.get 0
)
(func (export "mixed_args") (result f64)
(func (export "mixed_args")
(param i32) (param i32) (param i32) (param i32) (param i32) ;; 5 i32
(param $f64 f64) ;; 1 f64
(param i32)
(result f64)
local.get $f64
)
)`);
@ -79,9 +80,10 @@ function call(func, coercion, arg) {
// Test high number of arguments.
// All integers.
let {func} = wasmEvalText(`(module
(func (export "func") (result i32)
(func (export "func")
${Array(32).join('(param i32)')}
(param $last i32)
(result i32)
local.get $last
)
)`).exports;
@ -96,9 +98,10 @@ let {func} = wasmEvalText(`(module
// All floats.
func = wasmEvalText(`(module
(func (export "func") (result i32)
(func (export "func")
${Array(32).join('(param f64)')}
(param $last i32)
(result i32)
local.get $last
)
)`).exports.func;
@ -121,9 +124,10 @@ for (let i = 0; i < 32; i++) {
}
func = wasmEvalText(`(module
(func (export "func") (result i32)
(func (export "func")
${Array(32).join('(param f64)')}
(param $last i32)
(result i32)
local.get $last
)
)`).exports.func;

View File

@ -9,20 +9,20 @@ const ITER = 2 * TRIGGER;
const EXCEPTION_ITER = ITER - 2;
var instance = wasmEvalText(`(module
(func $add (export "add") (result i32) (param i32) (param i32)
(func (export "add") (param i32) (param i32) (result i32)
local.get 0
local.get 1
i32.add
)
(func $addi64 (export "add64") (result i64) (param i32) (param i32)
(func (export "add64") (param i32) (param i32) (result i64)
local.get 0
local.get 1
call $add
i64.extend_s/i32
)
(func $add_two_i64 (export "add_two_i64") (result i64) (param i64) (param i64)
(func (export "add_two_i64") (param i64) (param i64) (result i64)
local.get 0
local.get 1
i64.add

View File

@ -18,7 +18,7 @@ enableGeckoProfiling();
for (let type of ['i32', 'f32', 'f64']) {
var instance = wasmEvalText(`(module
(func $add (export "add") (result ${type}) (param ${type}) (param ${type})
(func (export "add") (param ${type}) (param ${type}) (result ${type})
local.get 0
local.get 1
${type}.add

View File

@ -6,7 +6,7 @@ const { assertStackTrace, startProfiling, endProfiling, assertEqPreciseStacks }
enableGeckoProfiling();
let { add } = wasmEvalText(`(module
(func $add (export "add") (result i32) (param i32) (param i32)
(func (export "add") (param i32) (param i32) (result i32)
local.get 0
i32.const 42
i32.eq

View File

@ -18,18 +18,18 @@ var imports = {
};
var instance = new WebAssembly.Instance(new WebAssembly.Module(wasmTextToBinary(`(module
(import $main "main" "f" (func))
(func $lol (export "add") (result i32) (param i32) (param i32)
(import "main" "f" (func))
(func (export "add") (param i32) (param i32) (result i32)
local.get 0
local.get 1
call $add
call 2
)
(func $add (result i32) (param i32) (param i32)
(func (param i32) (param i32) (result i32)
local.get 0
i32.const 5000
i32.eq
if
call $main
call 0
end
local.get 0
@ -81,18 +81,18 @@ var imports = {
};
var instance = new WebAssembly.Instance(new WebAssembly.Module(wasmTextToBinary(`(module
(import $main "main" "f" (func))
(func $lol (export "add") (result i32) (param i32) (param i32)
(import "main" "f" (func))
(func (export "add") (param i32) (param i32) (result i32)
local.get 0
local.get 1
call $add
call 2
)
(func $add (result i32) (param i32) (param i32)
(func (param i32) (param i32) (result i32)
local.get 0
i32.const 5000
i32.eq
if
call $main
call 0
unreachable
end

View File

@ -8,7 +8,7 @@ const EXCEPTION_ITER = TRIGGER + 5;
for (let type of ['i32', 'f32', 'f64']) {
var instance = wasmEvalText(`(module
(func $add (export "add") (result ${type}) (param ${type}) (param ${type})
(func $add (export "add") (param ${type}) (param ${type}) (result ${type})
local.get 0
local.get 1
${type}.add

View File

@ -15,13 +15,13 @@ const EXPECTED_STACKS = [SLOW_ENTRY_STACK, FAST_ENTRY_STACK, INLINED_CALL_STACK]
function main() {
var { table } = wasmEvalText(`(module
(func $add (result i32) (param i32) (param i32)
(func (param i32) (param i32) (result i32)
local.get 0
local.get 1
i32.add
)
(table (export "table") 10 funcref)
(elem (i32.const 0) $add)
(elem (i32.const 0) 0)
)`).exports;
for (var i = 0; i < ITER; i++) {
@ -35,13 +35,13 @@ function withTier2() {
setJitCompilerOption('wasm.delay-tier2', 1);
var module = new WebAssembly.Module(wasmTextToBinary(`(module
(func $add (result i32) (param i32) (param i32)
(func (param i32) (param i32) (result i32)
local.get 0
local.get 1
i32.add
)
(table (export "table") 10 funcref)
(elem (i32.const 0) $add)
(elem (i32.const 0) 0)
)`));
var { table } = new WebAssembly.Instance(module).exports;

View File

@ -2,7 +2,7 @@ var ITERATIONS = 10;
var INNER_ITERATIONS = 100;
let instance = wasmEvalText(`(module
(func (export "add") (result i32) (param i32) (param i32)
(func (export "add") (param i32) (param i32) (result i32)
local.get 0
local.get 1
i32.add

View File

@ -11,10 +11,10 @@ function accum(...args) {
}
var e = wasmEvalText(`(module
(import $a "" "a" (param i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32) (result i32))
(import $b "" "b" (param f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32) (result f32))
(import $c "" "c" (param f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64) (result f64))
(import $d "" "d" (param i32 f32 f64 i32 f32 f64 i32 f32 f64 i32 f32 f64 i32 f32 f64 i32 f32 f64 i32 f32) (result f64))
(import "" "a" (func $a (param i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32) (result i32)))
(import "" "b" (func $b (param f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32 f32) (result f32)))
(import "" "c" (func $c (param f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64 f64) (result f64)))
(import "" "d" (func $d (param i32 f32 f64 i32 f32 f64 i32 f32 f64 i32 f32 f64 i32 f32 f64 i32 f32 f64 i32 f32) (result f64)))
(func (export "a") (result i32)
i32.const 1 i32.const 2 i32.const 3 i32.const 4 i32.const 5
i32.const 6 i32.const 7 i32.const 8 i32.const 9 i32.const 10
@ -55,7 +55,7 @@ setJitCompilerOption("baseline.warmup.trigger", 5);
setJitCompilerOption("ion.warmup.trigger", 10);
var e = wasmEvalText(`(module
(import $a "" "a" (param i32 f64) (result f64))
(import "" "a" (func $a (param i32 f64) (result f64)))
(export "a" (func $a))
)`, {"":{a:(a,b)=>a+b}}).exports;
for (var i = 0; i < 100; i++)

View File

@ -309,7 +309,7 @@ for (var foldOffsets = 0; foldOffsets <= 1; foldOffsets++) {
(memory 1)
(data (i32.const 0) "\\00\\01\\02\\03\\04\\05\\06\\07\\08\\09\\0a\\0b\\0c\\0d\\0e\\0f")
(data (i32.const 16) "\\f0\\f1\\f2\\f3\\f4\\f5\\f6\\f7\\f8\\f9\\fa\\fb\\fc\\fd\\fe\\ff")
(func (param i32) (local i32 i32 i32 i32 f32 f64) (result i32)
(func (param i32) (result i32) (local i32 i32 i32 i32 f32 f64)
(local.set 1 (i32.load8_s offset=4 (local.get 0)))
(local.set 2 (i32.load16_s (local.get 1)))
(i32.store8 offset=4 (local.get 0) (local.get 1))
@ -466,7 +466,7 @@ new WebAssembly.Module(wasmTextToBinary(`(module (memory 1) (data 0 (offset (i32
new WebAssembly.Module(wasmTextToBinary(`(module (memory 1) (data ""))`));
assertErrorMessage(() => new WebAssembly.Module(wasmTextToBinary(`(module (memory 1) (data 0 ""))`)),
SyntaxError,
/data segment with memory index must have offset/);
/wasm text error/);
assertErrorMessage(() => new WebAssembly.Module(wasmTextToBinary(`(module (memory 1) (data 1 (i32.const 0) ""))`)),
SyntaxError,
/can't handle non-default memory/);
WebAssembly.CompileError,
/memory index must be zero/);

View File

@ -27,14 +27,14 @@ var checkBitPatterns = {
}
}
wasmEvalText('(module (import "" "float32" (param f32)) (func (call 0 (f32.const nan:0x123456))) (export "" (func 0)))', checkBitPatterns).exports[""]();
wasmEvalText('(module (import "" "float32" (func (param f32))) (func (call 0 (f32.const nan:0x123456))) (export "" (func 0)))', checkBitPatterns).exports[""]();
f64[0] = NaN;
f64[0] = f64[0]; // Force canonicalization.
f64[1] = wasmEvalText('(module (func (result f64) (f64.const nan:0x123456)) (export "" (func 0)))').exports[""]();
assertSameBitPattern(0, 8, 8);
wasmEvalText('(module (import "" "float64" (param f64)) (func (call 0 (f64.const nan:0x123456))) (export "" (func 0)))', checkBitPatterns).exports[""]();
wasmEvalText('(module (import "" "float64" (func (param f64))) (func (call 0 (f64.const nan:0x123456))) (export "" (func 0)))', checkBitPatterns).exports[""]();
// SANITY CHECKS

View File

@ -243,7 +243,7 @@ mem_test("data.drop 1 (i32.const 42)", "",
// init: too many args
mem_test("(memory.init 1 (i32.const 1) (i32.const 1) (i32.const 1) (i32.const 1))",
"",
SyntaxError, /parsing wasm text at/);
WebAssembly.CompileError, /unused values/);
// init: too few args
mem_test("(memory.init 1 (i32.const 1) (i32.const 1))", "",
@ -369,7 +369,7 @@ tab_test("elem.drop 1 (i32.const 42)", "",
// init: too many args
tab_test("(table.init 1 (i32.const 1) (i32.const 1) (i32.const 1) (i32.const 1))",
"",
SyntaxError, /parsing wasm text at/);
WebAssembly.CompileError, /unused values/);
// init: too few args
tab_test("(table.init 1 (i32.const 1) (i32.const 1))", "",

View File

@ -43,11 +43,11 @@ function gen_tab_impmod_t(insn)
(elem (i32.const 12) 7 5 2 3 6)
(elem func 5 9 2 7 6)
;; -------- Imports --------
(import "a" "if0" (result i32)) ;; index 0
(import "a" "if1" (result i32))
(import "a" "if2" (result i32))
(import "a" "if3" (result i32))
(import "a" "if4" (result i32)) ;; index 4
(import "a" "if0" (func (result i32))) ;; index 0
(import "a" "if1" (func (result i32)))
(import "a" "if2" (func (result i32)))
(import "a" "if3" (func (result i32)))
(import "a" "if4" (func (result i32))) ;; index 4
;; -------- Functions --------
(func (result i32) (i32.const 5)) ;; index 5
(func (result i32) (i32.const 6))
@ -260,23 +260,24 @@ mem_test("(memory.init 1 (i32.const 7) (i32.const 0) (i32.const 4)) \n" +
"(memory.copy (i32.const 19) (i32.const 20) (i32.const 5))",
[e,e,3,1,4, 1,e,2,7,1, 8,e,7,e,7, 5,2,7,e,9, e,7,e,8,8, e,e,e,e,e]);
// DataCount section is present but value is too low for the number of data segments
assertErrorMessage(() => wasmEvalText(
`(module
(datacount 1)
(data "")
(data ""))`),
WebAssembly.CompileError,
/number of data segments does not match declared count/);
function checkDataCount(count, err) {
let binary = moduleWithSections(
[v2vSigSection,
dataCountSection(count),
dataSection([
{offset: 0, elems: []},
{offset: 0, elems: []},
])
]);
assertErrorMessage(() => new WebAssembly.Module(binary),
WebAssembly.CompileError,
err);
}
// DataCount section is present but value is too low for the number of data segments
checkDataCount(1, /number of data segments does not match declared count/);
// DataCount section is present but value is too high for the number of data segments
assertErrorMessage(() => wasmEvalText(
`(module
(datacount 3)
(data "")
(data ""))`),
WebAssembly.CompileError,
/number of data segments does not match declared count/);
checkDataCount(3, /number of data segments does not match declared count/);
// DataCount section is not present but memory.init or data.drop uses it
function checkNoDataCount(body, err) {

View File

@ -28,7 +28,7 @@ wasmFullPass(`(module
// Grow during import call:
var exports = wasmEvalText(`(module
(import $imp "" "imp")
(import "" "imp" (func $imp))
(memory 1)
(func $grow (drop (memory.grow (i32.const 99))))
(export "grow" (func $grow))
@ -134,7 +134,7 @@ assertEq(mem.buffer.byteLength, 2 * 64*1024);
// Grow during import call:
var exports = wasmEvalText(`(module
(type $v2i (func (result i32)))
(import $grow "" "grow")
(import "" "grow" (func $grow))
(table (export "tbl") 1 funcref)
(func $test (result i32)
(i32.add
@ -157,14 +157,14 @@ assertEq(exports.tbl.length, 11);
// Grow during call_indirect:
var exports1 = wasmEvalText(`(module
(import $grow "" "grow")
(import "" "grow" (func $grow))
(func $exp (call $grow))
(export "exp" (func $exp))
)`, {"":{grow() { exports2.tbl.grow(1); exports2.tbl.set(2, exports2.eleven) }}}).exports;
var exports2 = wasmEvalText(`(module
(type $v2v (func))
(type $v2i (func (result i32)))
(import $imp "" "imp")
(import "" "imp" (func $imp))
(elem (i32.const 0) $imp)
(table 2 funcref)
(func $test (result i32)

View File

@ -6,8 +6,8 @@ function moduleText(cmp_kind /* "eq", "ne", "le_u" etc */)
{
return `(module
(func (export "cmpI32_selI32")
(result i32)
(param i32) (param i32) (param i32) (param i32)
(result i32)
(select (get_local 2)
(get_local 3)
(i32.${cmp_kind} (get_local 0) (get_local 1))

View File

@ -1,5 +1,5 @@
assertErrorMessage(() => wasmEvalText('(module (func) (start 0) (start 0))'), SyntaxError, /wasm text error/);
assertErrorMessage(() => wasmEvalText('(module (func) (start $unknown))'), SyntaxError, /label.*not found/);
assertErrorMessage(() => wasmEvalText('(module (func) (start $unknown))'), SyntaxError, /failed to find/);
wasmFailValidateText('(module (func) (start 1))', /unknown start function/);
wasmFailValidateText('(module (func (param i32)) (start 0))', /must be nullary/);
@ -10,12 +10,12 @@ wasmFailValidateText('(module (func (result f32)) (start 0))', /must not return
// Basic use case.
var count = 0;
function inc() { count++; }
var exports = wasmEvalText(`(module (import $imp "" "inc") (func $f (call $imp)) (start $f))`, { "":{inc} }).exports;
var exports = wasmEvalText(`(module (import "" "inc" (func $imp)) (func $f (call $imp)) (start $f))`, { "":{inc} }).exports;
assertEq(count, 1);
assertEq(Object.keys(exports).length, 0);
count = 0;
exports = wasmEvalText(`(module (import "" "inc") (func $start (call 0)) (start $start) (export "" (func 0)))`, { "":{inc} }).exports;
exports = wasmEvalText(`(module (import "" "inc" (func)) (func $start (call 0)) (start $start) (export "" (func 0)))`, { "":{inc} }).exports;
assertEq(count, 1);
assertEq(typeof exports[""], 'function');
assertEq(exports[""](), undefined);
@ -26,7 +26,7 @@ const Module = WebAssembly.Module;
const Instance = WebAssembly.Instance;
count = 0;
const m = new Module(wasmTextToBinary('(module (import $imp "" "inc") (func) (func $start (call $imp)) (start $start) (export "" (func $start)))'));
const m = new Module(wasmTextToBinary('(module (import "" "inc" (func $imp)) (func) (func $start (call $imp)) (start $start) (export "" (func $start)))'));
assertEq(count, 0);
assertErrorMessage(() => new Instance(m), TypeError, /second argument must be an object/);
@ -43,7 +43,7 @@ assertEq(count, 3);
function fail() { assertEq(true, false); }
count = 0;
const m2 = new Module(wasmTextToBinary('(module (import "" "fail") (import $imp "" "inc") (func) (start $imp))'));
const m2 = new Module(wasmTextToBinary('(module (import "" "fail" (func)) (import "" "inc" (func $imp)) (func) (start $imp))'));
assertEq(count, 0);
new Instance(m2, {"":{ inc, fail }});
assertEq(count, 1);

View File

@ -62,7 +62,7 @@ testFailInstantiate(code, {js:{foo:42}}, TypeError);
var text = `(module\n`;
text += ` (func (result i32) i32.const 0)\n`;
for (var i = 1; i <= 100; i++)
for (var i = 1; i <= 200; i++)
text += ` (func (result i32) (i32.add (i32.const ${i}) (call ${i-1})))\n`;
text += ` (func (export "run") (result i32) call 100)\n`;
text += `)`;

View File

@ -192,7 +192,7 @@ function runTest() {
}
var i = wasmEvalText(
`(module
(import $imp "a" "b" (result i32))
(import "a" "b" (func $imp (result i32)))
(func $f (param i32) (result i32) (call $imp))
(export "f" (func $f))
)`,

View File

@ -26,13 +26,13 @@ assertSegmentFitError(() => wasmEvalText(`(module (table 10 funcref) (elem (i32.
assertSegmentFitError(() => wasmEvalText(`(module (table 10 funcref) (elem (i32.const 8) $f0 $f0 $f0) ${callee(0)})`));
assertSegmentFitError(() => wasmEvalText(`(module (table 0 funcref) (func) (elem (i32.const 0x10001)))`));
assertSegmentFitError(() => wasmEvalText(`(module (table 10 funcref) (import "globals" "a" (global i32)) (elem (global.get 0) $f0) ${callee(0)})`, {globals:{a:10}}));
assertSegmentFitError(() => wasmEvalText(`(module (table 10 funcref) (import "globals" "a" (global i32)) (elem (global.get 0) $f0 $f0 $f0) ${callee(0)})`, {globals:{a:8}}));
assertSegmentFitError(() => wasmEvalText(`(module (import "globals" "a" (global i32)) (table 10 funcref) (elem (global.get 0) $f0) ${callee(0)})`, {globals:{a:10}}));
assertSegmentFitError(() => wasmEvalText(`(module (import "globals" "a" (global i32)) (table 10 funcref) (elem (global.get 0) $f0 $f0 $f0) ${callee(0)})`, {globals:{a:8}}));
assertEq(new Module(wasmTextToBinary(`(module (table 10 funcref) (elem (i32.const 1) $f0 $f0) (elem (i32.const 0) $f0) ${callee(0)})`)) instanceof Module, true);
assertEq(new Module(wasmTextToBinary(`(module (table 10 funcref) (elem (i32.const 1) $f0 $f0) (elem (i32.const 2) $f0) ${callee(0)})`)) instanceof Module, true);
wasmEvalText(`(module (table 10 funcref) (import "globals" "a" (global i32)) (elem (i32.const 1) $f0 $f0) (elem (global.get 0) $f0) ${callee(0)})`, {globals:{a:0}});
wasmEvalText(`(module (table 10 funcref) (import "globals" "a" (global i32)) (elem (global.get 0) $f0 $f0) (elem (i32.const 2) $f0) ${callee(0)})`, {globals:{a:1}});
wasmEvalText(`(module (import "globals" "a" (global i32)) (table 10 funcref) (elem (i32.const 1) $f0 $f0) (elem (global.get 0) $f0) ${callee(0)})`, {globals:{a:0}});
wasmEvalText(`(module (import "globals" "a" (global i32)) (table 10 funcref) (elem (global.get 0) $f0 $f0) (elem (i32.const 2) $f0) ${callee(0)})`, {globals:{a:1}});
// Explicit table index in a couple of ways, note this requires us to talk about the table type also.
assertEq(new Module(wasmTextToBinary(`(module
@ -99,7 +99,7 @@ assertErrorMessage(() => call(6), RuntimeError, /indirect call to null/);
assertErrorMessage(() => call(10), RuntimeError, /index out of bounds/);
var imports = {a:{b:()=>42}};
var call = wasmEvalText(`(module (table 10 funcref) (elem (i32.const 0) $f0 $f1 $f2) ${callee(0)} (import "a" "b" (func $f1)) (import "a" "b" (func $f2 (result i32))) ${caller})`, imports).exports.call;
var call = wasmEvalText(`(module (import "a" "b" (func $f1)) (import "a" "b" (func $f2 (result i32))) (table 10 funcref) (elem (i32.const 0) $f0 $f1 $f2) ${callee(0)} ${caller})`, imports).exports.call;
assertEq(call(0), 0);
assertErrorMessage(() => call(1), RuntimeError, /indirect call signature mismatch/);
assertEq(call(2), 42);
@ -165,7 +165,7 @@ var m = new Module(wasmTextToBinary(`(module
(type $i2i (func (param i32) (result i32)))
(import "a" "mem" (memory 1))
(import "a" "tbl" (table 10 funcref))
(import $imp "a" "imp" (result i32))
(import "a" "imp" (func $imp (result i32)))
(func $call (param $i i32) (result i32)
(i32.add
(call $imp)

View File

@ -1,4 +1,4 @@
var parsingError = /parsing wasm text at/;
var parsingError = /wasm text error/;
assertErrorMessage(() => wasmEvalText(''), SyntaxError, parsingError);
assertErrorMessage(() => wasmEvalText('('), SyntaxError, parsingError);
@ -8,19 +8,19 @@ assertErrorMessage(() => wasmEvalText('(moduler'), SyntaxError, parsingError);
assertErrorMessage(() => wasmEvalText('(module (func) (export "a'), SyntaxError, parsingError);
assertErrorMessage(() => wasmEvalText('(module (func (local $a i32) (param $b f32)))'), SyntaxError, parsingError);
assertErrorMessage(() => wasmEvalText('(module (func $a) (func) (export "a" (func $a)) (export "b" (func $b)))'), SyntaxError, /Function label '\$b' not found/);
assertErrorMessage(() => wasmEvalText('(module (import $foo "a" "b") (import $foo "a" "b"))'), SyntaxError, /duplicate function import/);
assertErrorMessage(() => wasmEvalText('(module (func $foo) (func $foo))'), SyntaxError, /duplicate function/);
assertErrorMessage(() => wasmEvalText('(module (func (param $a i32) (local $a i32)))'), SyntaxError, /duplicate var/);
assertErrorMessage(() => wasmEvalText('(module (func (local.get $a)))'), SyntaxError, /Local label '\$a' not found/);
assertErrorMessage(() => wasmEvalText('(module (type $a (func)) (type $a (func (param i32))))'), SyntaxError, /duplicate signature/);
assertErrorMessage(() => wasmEvalText('(module (import "a" "") (func (call $abc)))'), SyntaxError, /Function label '\$abc' not found/);
assertErrorMessage(() => wasmEvalText('(module (type $a (func)) (func (type $b) (i32.const 13)))'), SyntaxError, /Signature label '\$b' not found/);
assertErrorMessage(() => wasmEvalText('(module (type $a (func)) (func (call_indirect (type $c) (i32.const 0) (local.get 0))))'), SyntaxError, /Signature label '\$c' not found/);
assertErrorMessage(() => wasmEvalText('(module (func (br $a)))'), SyntaxError, /branch target label '\$a' not found/);
assertErrorMessage(() => wasmEvalText('(module (func (block $a ) (br $a)))'), SyntaxError, /branch target label '\$a' not found/);
assertErrorMessage(() => wasmEvalText('(module (func $a) (func) (export "a" (func $a)) (export "b" (func $b)))'), SyntaxError, /failed to find func/);
assertErrorMessage(() => wasmEvalText('(module (import "a" "b" (func $foo)) (import "a" "b" (func $foo)))'), SyntaxError, /duplicate identifier for func/);
assertErrorMessage(() => wasmEvalText('(module (func $foo) (func $foo))'), SyntaxError, /duplicate identifier for func/);
assertErrorMessage(() => wasmEvalText('(module (func (param $a i32) (local $a i32)))'), SyntaxError, /duplicate identifier for local/);
assertErrorMessage(() => wasmEvalText('(module (func (local.get $a)))'), SyntaxError, /failed to find local/);
assertErrorMessage(() => wasmEvalText('(module (type $a (func)) (type $a (func (param i32))))'), SyntaxError, /duplicate identifier for type/);
assertErrorMessage(() => wasmEvalText('(module (import "a" "" (func)) (func (call $abc)))'), SyntaxError, /failed to find func/);
assertErrorMessage(() => wasmEvalText('(module (type $a (func)) (func (type $b) (i32.const 13)))'), SyntaxError, /failed to find type/);
assertErrorMessage(() => wasmEvalText('(module (type $a (func)) (func (call_indirect (type $c) (i32.const 0) (local.get 0))))'), SyntaxError, /failed to find type/);
assertErrorMessage(() => wasmEvalText('(module (func (br $a)))'), SyntaxError, /failed to find label/);
assertErrorMessage(() => wasmEvalText('(module (func (block $a ) (br $a)))'), SyntaxError, /failed to find label/);
assertErrorMessage(() => wasmEvalText(`(module (func (call ${0xffffffff})))`), SyntaxError, parsingError);
assertErrorMessage(() => wasmEvalText(`(module (func (call ${0xffffffff})))`), WebAssembly.CompileError, /callee index out of range/);
assertErrorMessage(() => wasmEvalText(`(module (export "func" ${0xffffffff}))`), SyntaxError, parsingError);
wasmEvalText('(module (func (param $a i32)))');
@ -69,10 +69,10 @@ assertErrorMessage(() => wasmEvalText('(module (func $t (import "mod" "func" (lo
const func = i => 42 + i;
wasmEvalText('(module (func $t (import "mod" "func")))', { mod: {func} });
wasmEvalText('(module (func $t (import "mod" "func")(param i32)))', { mod: {func} });
wasmEvalText('(module (func $t (import "mod" "func")(result i32)))', { mod: {func} });
wasmEvalText('(module (func $t (import "mod" "func")(param i32) (result i32)))', { mod: {func} });
wasmEvalText('(module (func $t (import "mod" "func")(result i32) (param i32)))', { mod: {func} });
wasmEvalText('(module (func $t (import "mod" "func") (param i32)))', { mod: {func} });
wasmEvalText('(module (func $t (import "mod" "func") (result i32)))', { mod: {func} });
wasmEvalText('(module (func $t (import "mod" "func") (param i32) (result i32)))', { mod: {func} });
wasmEvalText('(module (func $t (import "mod" "func") (param i32)))', { mod: {func} });
assertErrorMessage(() => wasmEvalText('(module (func $t (import "mod" "func") (type)))', { mod: {func} }), SyntaxError, parsingError);
wasmEvalText('(module (type $t (func)) (func $t (import "mod" "func") (type $t)))', { mod: {func} });
@ -80,7 +80,7 @@ wasmEvalText('(module (type $t (func)) (func $t (import "mod" "func") (type $t))
assertErrorMessage(() => wasmEvalText('(module (func $t (export))))'), SyntaxError, parsingError);
wasmEvalText('(module (func (export "f")))');
wasmEvalText('(module (func $f (export "f")))');
wasmEvalText('(module (func $f (export "f") (result i32) (param i32) (i32.add (local.get 0) (i32.const 42))))');
wasmEvalText('(module (func $f (export "f") (param i32) (result i32) (i32.add (local.get 0) (i32.const 42))))');
assertErrorMessage(() => wasmEvalText(`
(module
@ -90,12 +90,12 @@ assertErrorMessage(() => wasmEvalText(`
(func (import "mod" "b") (type $tf))
(func (export "f2"))
)
`), SyntaxError, /import after function definition/);
`), SyntaxError, /import after function/);
// Globals.
assertErrorMessage(() => wasmEvalText('(module (global $t (export)))'), SyntaxError, parsingError);
assertErrorMessage(() => wasmEvalText('(module (global $t (export "g")))'), SyntaxError, parsingError);
assertErrorMessage(() => wasmEvalText('(module (global $t (export "g") i32))'), SyntaxError, parsingError);
assertErrorMessage(() => wasmEvalText('(module (global $t (export "g") i32))'), WebAssembly.CompileError, /unexpected initializer expression/);
wasmEvalText('(module (global $t (export "g") i32 (i32.const 42)))');
assertErrorMessage(() => wasmEvalText('(module (global $t (import) i32))'), SyntaxError, parsingError);
@ -110,7 +110,7 @@ assertErrorMessage(() => wasmEvalText(`
(global (export "f1") i32 (i32.const 42))
(global (import "mod" "b") i32)
)
`), SyntaxError, /import after global definition/);
`), SyntaxError, /import after global/);
// Memory.
assertErrorMessage(() => wasmEvalText('(module (memory (export)))'), SyntaxError, parsingError);

View File

@ -23,14 +23,14 @@ assertEq(WebAssembly.validate(bin), false);
assertThrowsInstanceOf(() => new WebAssembly.Module(bin), WebAssembly.CompileError);
assertThrowsInstanceOf(() => wasmEvalText(`(module (import "\u2603" "")) `, {}), TypeError);
assertThrowsInstanceOf(() => wasmEvalText(`(module (import "\u2603" "" (func))) `, {}), TypeError);
{
let i1 = wasmEvalText(` (module (func (export "\u2603")))`);
assertThrowsInstanceOf(() => wasmEvalText(`(module (import "" "\u2603" (result i32)))`,
assertThrowsInstanceOf(() => wasmEvalText(`(module (import "" "\u2603" (func (result i32))))`,
{ "": { "\u2603": i1.exports['\u2603'] } }),
WebAssembly.LinkError);
assertThrowsInstanceOf(() => wasmEvalText(`(module (import "\u2603" "" (result i32)))`,
assertThrowsInstanceOf(() => wasmEvalText(`(module (import "\u2603" "" (func (result i32))))`,
{ "\u2603": { "": i1.exports['\u2603'] } }),
WebAssembly.LinkError);
}

View File

@ -86,9 +86,10 @@ assertThrowsInstanceOf(() => setSharedObject(new WebAssembly.Memory({initial: 1,
// We can store wasm modules
var mod = new WebAssembly.Module(wasmTextToBinary(`(module
(import "m" "f" (func (param i32) (result i32)))
(func (export "hi") (result i32)
(i32.const 37))
(import "m" "f" (param i32) (result i32)))`));
)`));
setSharedObject(mod);