summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/wasm2js.h20
-rw-r--r--test/wasm2js/br_table_to_loop.2asm.js67
-rw-r--r--test/wasm2js/br_table_to_loop.wast16
3 files changed, 94 insertions, 9 deletions
diff --git a/src/wasm2js.h b/src/wasm2js.h
index 3c868e8dd..927dbac24 100644
--- a/src/wasm2js.h
+++ b/src/wasm2js.h
@@ -973,6 +973,14 @@ Ref Wasm2JSBuilder::processFunctionBody(Module* m, Function* func, IString resul
return ValueBuilder::makeLabel(fromName(asmLabel, NameScope::Label), ret);
}
+ Ref makeBreakOrContinue(Name name) {
+ if (continueLabels.count(name)) {
+ return ValueBuilder::makeContinue(fromName(name, NameScope::Label));
+ } else {
+ return ValueBuilder::makeBreak(fromName(name, NameScope::Label));
+ }
+ }
+
Ref visitBreak(Break* curr) {
if (curr->condition) {
// we need an equivalent to an if here, so use that code
@@ -983,13 +991,7 @@ Ref Wasm2JSBuilder::processFunctionBody(Module* m, Function* func, IString resul
fakeIf.ifTrue = &fakeBreak;
return visit(&fakeIf, result);
}
- Ref theBreak;
- auto iter = continueLabels.find(curr->name);
- if (iter == continueLabels.end()) {
- theBreak = ValueBuilder::makeBreak(fromName(curr->name, NameScope::Label));
- } else {
- theBreak = ValueBuilder::makeContinue(fromName(curr->name, NameScope::Label));
- }
+ Ref theBreak = makeBreakOrContinue(curr->name);
if (!curr->value) return theBreak;
// generate the value, including assigning to the result, and then do the break
Ref ret = visitAndAssign(curr->value, breakResults[curr->name]);
@@ -1016,10 +1018,10 @@ Ref Wasm2JSBuilder::processFunctionBody(Module* m, Function* func, IString resul
ret[1]->push_back(theSwitch);
for (size_t i = 0; i < curr->targets.size(); i++) {
ValueBuilder::appendCaseToSwitch(theSwitch, ValueBuilder::makeNum(i));
- ValueBuilder::appendCodeToSwitch(theSwitch, blockify(ValueBuilder::makeBreak(fromName(curr->targets[i], NameScope::Label))), false);
+ ValueBuilder::appendCodeToSwitch(theSwitch, blockify(makeBreakOrContinue(curr->targets[i])), false);
}
ValueBuilder::appendDefaultToSwitch(theSwitch);
- ValueBuilder::appendCodeToSwitch(theSwitch, blockify(ValueBuilder::makeBreak(fromName(curr->default_, NameScope::Label))), false);
+ ValueBuilder::appendCodeToSwitch(theSwitch, blockify(makeBreakOrContinue(curr->default_)), false);
return ret;
}
diff --git a/test/wasm2js/br_table_to_loop.2asm.js b/test/wasm2js/br_table_to_loop.2asm.js
new file mode 100644
index 000000000..31e9ac0ae
--- /dev/null
+++ b/test/wasm2js/br_table_to_loop.2asm.js
@@ -0,0 +1,67 @@
+
+function asmFunc(global, env, buffer) {
+ "use asm";
+ var HEAP8 = new global.Int8Array(buffer);
+ var HEAP16 = new global.Int16Array(buffer);
+ var HEAP32 = new global.Int32Array(buffer);
+ var HEAPU8 = new global.Uint8Array(buffer);
+ var HEAPU16 = new global.Uint16Array(buffer);
+ var HEAPU32 = new global.Uint32Array(buffer);
+ var HEAPF32 = new global.Float32Array(buffer);
+ var HEAPF64 = new global.Float64Array(buffer);
+ var Math_imul = global.Math.imul;
+ var Math_fround = global.Math.fround;
+ var Math_abs = global.Math.abs;
+ var Math_clz32 = global.Math.clz32;
+ var Math_min = global.Math.min;
+ var Math_max = global.Math.max;
+ var Math_floor = global.Math.floor;
+ var Math_ceil = global.Math.ceil;
+ var Math_sqrt = global.Math.sqrt;
+ var abort = env.abort;
+ var nan = global.NaN;
+ var infinity = global.Infinity;
+ var i64toi32_i32$HIGH_BITS = 0;
+ function $0() {
+ block : {
+ loop : do {
+ switch (1 | 0) {
+ case 0:
+ break block;
+ case 1:
+ continue loop;
+ default:
+ break block;
+ };
+ break loop;
+ } while (1);
+ }
+ }
+
+ function $1() {
+ block : {
+ loop : do {
+ switch (1 | 0) {
+ case 0:
+ continue loop;
+ case 1:
+ break block;
+ default:
+ continue loop;
+ };
+ break loop;
+ } while (1);
+ }
+ }
+
+ var FUNCTION_TABLE = [];
+ return {
+ exp1: $0,
+ exp2: $1
+ };
+}
+
+const memasmFunc = new ArrayBuffer(65536);
+const retasmFunc = asmFunc({Math,Int8Array,Uint8Array,Int16Array,Uint16Array,Int32Array,Uint32Array,Float32Array,Float64Array,NaN,Infinity}, {abort:function() { throw new Error('abort'); }},memasmFunc);
+export const exp1 = retasmFunc.exp1;
+export const exp2 = retasmFunc.exp2;
diff --git a/test/wasm2js/br_table_to_loop.wast b/test/wasm2js/br_table_to_loop.wast
new file mode 100644
index 000000000..83d3702c2
--- /dev/null
+++ b/test/wasm2js/br_table_to_loop.wast
@@ -0,0 +1,16 @@
+(module
+ (func "exp1"
+ (block $block
+ (loop $loop
+ (br_table $block $loop $block (i32.const 1))
+ )
+ )
+ )
+ (func "exp2"
+ (block $block
+ (loop $loop
+ (br_table $loop $block $loop (i32.const 1))
+ )
+ )
+ )
+)