diff options
-rw-r--r-- | src/asm2wasm.cpp | 27 | ||||
-rw-r--r-- | src/wasm.h | 2 | ||||
-rw-r--r-- | test/emcc_hello_world.wast | 13 |
3 files changed, 30 insertions, 12 deletions
diff --git a/src/asm2wasm.cpp b/src/asm2wasm.cpp index ac2c1d5e8..50f504c6a 100644 --- a/src/asm2wasm.cpp +++ b/src/asm2wasm.cpp @@ -24,7 +24,8 @@ IString GLOBAL("global"), NAN_("NaN"), INFINITY_("Infinity"), FLOAT64ARRAY("Float64Array"), IMPOSSIBLE_CONTINUE("impossible-continue"), MATH("Math"), - IMUL("imul"); + IMUL("imul"), + CLZ32("clz32"); static void abort_on(std::string why) { @@ -246,6 +247,7 @@ class Asm2WasmModule : public wasm::Module { std::map<IString, View> views; // name (e.g. HEAP8) => view info IString Math_imul; // imported name of Math.imul + IString Math_clz32; // imported name of Math.imul // function types. we fill in this information as we see // uses, in the first pass @@ -466,10 +468,16 @@ void Asm2WasmModule::processAsm(Ref ast) { if (module[0] == DOT) { // we can have (global.Math).floor; skip the 'Math' assert(module[1][0] == NAME); - if (module[2] == MATH && imported[2] == IMUL) { - assert(Math_imul.isNull()); - Math_imul = name; - return; + if (module[2] == MATH) { + if (imported[2] == IMUL) { + assert(Math_imul.isNull()); + Math_imul = name; + return; + } else if (imported[2] == CLZ32) { + assert(Math_clz32.isNull()); + Math_clz32 = name; + return; + } } module = module[1]; } @@ -885,6 +893,7 @@ Function* Asm2WasmModule::processFunction(Ref ast) { if (ast[1][0] == NAME) { IString name = ast[1][1]->getIString(); if (name == Math_imul) { + assert(ast[2]->size() == 2); auto ret = allocator.alloc<Binary>(); ret->op = Mul; ret->left = process(ast[2][0]); @@ -892,6 +901,14 @@ Function* Asm2WasmModule::processFunction(Ref ast) { ret->type = BasicType::i32; return ret; } + if (name == Math_clz32) { + assert(ast[2]->size() == 1); + auto ret = allocator.alloc<Unary>(); + ret->op = Clz; + ret->value = process(ast[2][0]); + ret->type = BasicType::i32; + return ret; + } Call* ret; if (imports.find(name) != imports.end()) { ret = allocator.alloc<CallImport>(); diff --git a/src/wasm.h b/src/wasm.h index d8cada7f5..a978e71ca 100644 --- a/src/wasm.h +++ b/src/wasm.h @@ -569,7 +569,9 @@ public: std::ostream& print(std::ostream &o, unsigned indent) override { printOpening(o, "unary "); switch (op) { + case Clz: o << "clz"; break; case Neg: o << "neg"; break; + case Floor: o << "floor"; break; default: abort(); } incIndent(o, indent); diff --git a/test/emcc_hello_world.wast b/test/emcc_hello_world.wast index 129b8e5de..5b13cc418 100644 --- a/test/emcc_hello_world.wast +++ b/test/emcc_hello_world.wast @@ -3,7 +3,6 @@ (type $FUNCSIG$ii (func (param i32) (result i32))) (type $FUNCSIG$iiii (func (param i32 i32 i32) (result i32))) (type $FUNCSIG$vi (func (param i32))) - (import $Math_clz32 "global" "clz32" (param i32) (result i32)) (import $___lock "env" "___lock" (param i32)) (import $___syscall140 "env" "___syscall140" (param i32 i32) (result i32)) (import $___syscall146 "env" "___syscall146" (param i32 i32) (result i32)) @@ -26495,14 +26494,14 @@ ) ) (set_local $$49 - (call_import $Math_clz32 + (unary clz (get_local $$d_sroa_1_4_extract_trunc) ) ) (set_local $$51 (i32.sub (get_local $$49) - (call_import $Math_clz32 + (unary clz (get_local $$n_sroa_1_4_extract_trunc) ) ) @@ -26638,14 +26637,14 @@ ) (block (set_local $$117 - (call_import $Math_clz32 + (unary clz (get_local $$d_sroa_1_4_extract_trunc) ) ) (set_local $$119 (i32.sub (get_local $$117) - (call_import $Math_clz32 + (unary clz (get_local $$n_sroa_1_4_extract_trunc) ) ) @@ -26806,7 +26805,7 @@ (block (set_local $$86 (i32.add - (call_import $Math_clz32 + (unary clz (get_local $$d_sroa_0_0_extract_trunc) ) (i32.const 33) @@ -26815,7 +26814,7 @@ (set_local $$88 (i32.sub (get_local $$86) - (call_import $Math_clz32 + (unary clz (get_local $$n_sroa_1_4_extract_trunc) ) ) |