summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAlon Zakai <azakai@google.com>2023-10-19 09:11:36 -0700
committerGitHub <noreply@github.com>2023-10-19 16:11:36 +0000
commitbe6a3393c36ccc1a0cb0d79b116cbe48e169f93b (patch)
tree8240468a78e62b6d18d747c865557d69f01b4b9f
parentf79b5aa26b1fc722853e56b541cd35128786ef6b (diff)
downloadbinaryen-be6a3393c36ccc1a0cb0d79b116cbe48e169f93b.tar.gz
binaryen-be6a3393c36ccc1a0cb0d79b116cbe48e169f93b.tar.bz2
binaryen-be6a3393c36ccc1a0cb0d79b116cbe48e169f93b.zip
RemoveUnusedModuleElements: Make exports skip trampolines (#6026)
If we export a function that just calls another function, we can export that one instead. Then the one in the middle may be unused, function foo() { return bar(); } export foo; // can be an export of bar This saves a few bytes in rare cases, but probably more important is that it saves the trampoline, so if this is on a hot path, we save a call. Context: emscripten-core/emscripten#20478 (comment) In general this is not needed as inlining helps us out by inlining foo() into the caller (since foo is tiny, that always ends up happening). But exports are a case the inliner cannot handle, so we do it here.
-rw-r--r--src/passes/RemoveUnusedModuleElements.cpp61
-rw-r--r--test/lit/merge/chain.wat6
-rw-r--r--test/lit/passes/O3_inline-functions-with-loops_flexible-inline-max-function-size=30.wast7
-rw-r--r--test/lit/passes/extract-function.wast14
-rw-r--r--test/lit/passes/remove-unused-module-elements-refs.wast14
-rw-r--r--test/lit/passes/remove-unused-module-elements_all-features.wast245
-rw-r--r--test/metadce/threaded.wast.dced15
-rw-r--r--test/metadce/threaded_cycle.wast.dced20
-rw-r--r--test/passes/remove-unused-nonfunction-module-elements_all-features.txt6
-rw-r--r--test/wasm2js/dot_import.2asm.js6
-rw-r--r--test/wasm2js/dot_import.2asm.js.opt6
-rw-r--r--test/wasm2js/emscripten.2asm.js6
-rw-r--r--test/wasm2js/emscripten.2asm.js.opt6
-rw-r--r--test/wasm2js/func_ptrs.2asm.js7
14 files changed, 314 insertions, 105 deletions
diff --git a/src/passes/RemoveUnusedModuleElements.cpp b/src/passes/RemoveUnusedModuleElements.cpp
index e082f8e15..cf1f265bc 100644
--- a/src/passes/RemoveUnusedModuleElements.cpp
+++ b/src/passes/RemoveUnusedModuleElements.cpp
@@ -601,6 +601,8 @@ struct RemoveUnusedModuleElements : public Pass {
: rootAllFunctions(rootAllFunctions) {}
void run(Module* module) override {
+ prepare(module);
+
std::vector<ModuleElement> roots;
// Module start is a root.
if (module->start.is()) {
@@ -712,6 +714,65 @@ struct RemoveUnusedModuleElements : public Pass {
// to a function from an element segment, we may be able to remove
// that function, etc.)
}
+
+ // Do simple work that prepares the module to be efficiently optimized.
+ void prepare(Module* module) {
+ // If a function export is a function that just calls another function, we
+ // can export that one directly. Doing so might make the function in the
+ // middle unused:
+ //
+ // (export "export" (func $middle))
+ // (func $middle
+ // (call $real)
+ // )
+ //
+ // =>
+ //
+ // (export "export" (func $real)) ;; this changed
+ // (func $middle
+ // (call $real)
+ // )
+ //
+ // (Normally this is not needed, as inlining will end up removing such
+ // silly trampoline functions, but the case of an import being exported does
+ // not have any code for inlining to work with, so we need to handle it
+ // directly.)
+ for (auto& exp : module->exports) {
+ if (exp->kind != ExternalKind::Function) {
+ continue;
+ }
+
+ auto* func = module->getFunction(exp->value);
+ if (!func->body) {
+ continue;
+ }
+
+ auto* call = func->body->dynCast<Call>();
+ if (!call) {
+ continue;
+ }
+
+ // Don't do this if the type is different, as then we might be
+ // changing the external interface to the module.
+ auto* calledFunc = module->getFunction(call->target);
+ if (calledFunc->type != func->type) {
+ continue;
+ }
+
+ // Finally, all the params must simply be forwarded.
+ auto ok = true;
+ for (Index i = 0; i < call->operands.size(); i++) {
+ auto* get = call->operands[i]->dynCast<LocalGet>();
+ if (!get || get->index != i) {
+ ok = false;
+ break;
+ }
+ }
+ if (ok) {
+ exp->value = calledFunc->name;
+ }
+ }
+ }
};
Pass* createRemoveUnusedModuleElementsPass() {
diff --git a/test/lit/merge/chain.wat b/test/lit/merge/chain.wat
index 528b20d0e..76004e9bd 100644
--- a/test/lit/merge/chain.wat
+++ b/test/lit/merge/chain.wat
@@ -13,12 +13,8 @@
;; CHECK: (export "g" (func $0))
-;; CHECK: (export "h" (func $0_2))
+;; CHECK: (export "h" (func $0))
;; CHECK: (func $0 (type $0)
;; CHECK-NEXT: (nop)
;; CHECK-NEXT: )
-
-;; CHECK: (func $0_2 (type $0)
-;; CHECK-NEXT: (call $0)
-;; CHECK-NEXT: )
diff --git a/test/lit/passes/O3_inline-functions-with-loops_flexible-inline-max-function-size=30.wast b/test/lit/passes/O3_inline-functions-with-loops_flexible-inline-max-function-size=30.wast
index e0045579d..907891aee 100644
--- a/test/lit/passes/O3_inline-functions-with-loops_flexible-inline-max-function-size=30.wast
+++ b/test/lit/passes/O3_inline-functions-with-loops_flexible-inline-max-function-size=30.wast
@@ -18,7 +18,7 @@
;; CHECK: (export "t1" (func $t1))
- ;; CHECK: (export "t2" (func $t2))
+ ;; CHECK: (export "t2" (func $fib))
;; CHECK: (export "t3" (func $t3))
@@ -155,11 +155,6 @@
)
)
)
- ;; CHECK: (func $t2 (; has Stack IR ;) (param $0 i32) (result i32)
- ;; CHECK-NEXT: (call $fib
- ;; CHECK-NEXT: (local.get $0)
- ;; CHECK-NEXT: )
- ;; CHECK-NEXT: )
(func $t2 (export "t2") (type $t0) (param $p0 i32) (result i32)
(call $fib
(local.get $p0)
diff --git a/test/lit/passes/extract-function.wast b/test/lit/passes/extract-function.wast
index 9258f8c63..e4b804abe 100644
--- a/test/lit/passes/extract-function.wast
+++ b/test/lit/passes/extract-function.wast
@@ -5,15 +5,6 @@
;; RUN: foreach %s %t wasm-opt --extract-function-index --pass-arg=extract-function-index@0 -S -o - | filecheck %s
(module
- ;; CHECK: (type $0 (func))
-
- ;; CHECK: (import "env" "bar" (func $bar))
-
- ;; CHECK: (export "foo" (func $foo))
-
- ;; CHECK: (func $foo
- ;; CHECK-NEXT: (call $bar)
- ;; CHECK-NEXT: )
(func $foo
(call $bar)
)
@@ -27,6 +18,11 @@
)
)
+;; CHECK: (type $0 (func))
+
+;; CHECK: (import "env" "bar" (func $bar))
+
+;; CHECK: (export "foo" (func $bar))
(module
;; Use another function in the table, but the table is not used in the
;; extracted function
diff --git a/test/lit/passes/remove-unused-module-elements-refs.wast b/test/lit/passes/remove-unused-module-elements-refs.wast
index 00ea9767f..377639e51 100644
--- a/test/lit/passes/remove-unused-module-elements-refs.wast
+++ b/test/lit/passes/remove-unused-module-elements-refs.wast
@@ -656,24 +656,18 @@
(ref.func $d)
))
- ;; CHECK: (export "export" (func $export))
-
- ;; CHECK: (func $export (type $void)
- ;; CHECK-NEXT: (call $b)
- ;; CHECK-NEXT: )
- ;; OPEN_WORLD: (export "export" (func $export))
-
- ;; OPEN_WORLD: (func $export (type $void)
- ;; OPEN_WORLD-NEXT: (call $b)
- ;; OPEN_WORLD-NEXT: )
(func $export (export "export")
;; Call $b but not $a or $c
(call $b)
)
+ ;; CHECK: (export "export" (func $b))
+
;; CHECK: (func $a (type $void)
;; CHECK-NEXT: (unreachable)
;; CHECK-NEXT: )
+ ;; OPEN_WORLD: (export "export" (func $b))
+
;; OPEN_WORLD: (func $a (type $void)
;; OPEN_WORLD-NEXT: (call_ref $void
;; OPEN_WORLD-NEXT: (struct.get $vtable 0
diff --git a/test/lit/passes/remove-unused-module-elements_all-features.wast b/test/lit/passes/remove-unused-module-elements_all-features.wast
index 2979d1cd5..b5c5d701e 100644
--- a/test/lit/passes/remove-unused-module-elements_all-features.wast
+++ b/test/lit/passes/remove-unused-module-elements_all-features.wast
@@ -19,7 +19,7 @@
;; CHECK: (export "memory" (memory $0))
- ;; CHECK: (export "exported" (func $exported))
+ ;; CHECK: (export "exported" (func $called2))
;; CHECK: (export "other1" (func $other1))
@@ -64,9 +64,6 @@
(func $called_indirect (type $0)
(nop)
)
- ;; CHECK: (func $exported (type $0)
- ;; CHECK-NEXT: (call $called2)
- ;; CHECK-NEXT: )
(func $exported (type $0-dupe)
(call $called2)
)
@@ -459,15 +456,15 @@
(func $waka) ;; used in table
)
(module ;; one is exported, and one->two->int global, whose init->imported
- ;; CHECK: (type $0 (func (result i32)))
+ ;; CHECK: (type $0 (func (param i32) (result i32)))
- ;; CHECK: (type $1 (func))
+ ;; CHECK: (type $1 (func (result i32)))
- ;; CHECK: (type $2 (func (param i32) (result i32)))
+ ;; CHECK: (type $2 (func))
;; CHECK: (import "env" "imported" (global $imported i32))
(import "env" "imported" (global $imported i32))
- ;; CHECK: (import "env" "_puts" (func $_puts (type $2) (param i32) (result i32)))
+ ;; CHECK: (import "env" "_puts" (func $_puts (type $0) (param i32) (result i32)))
(import "env" "forgetme" (global $forgetme i32))
(import "env" "_puts" (func $_puts (param i32) (result i32)))
(import "env" "forget_puts" (func $forget_puts (param i32) (result i32)))
@@ -478,32 +475,26 @@
(global $forglobal.get (mut i32) (i32.const 500))
;; CHECK: (global $exp_glob i32 (i32.const 600))
(global $exp_glob i32 (i32.const 600))
- ;; CHECK: (export "one" (func $one))
+ ;; CHECK: (export "one" (func $two))
(export "one" (func $one))
- ;; CHECK: (export "three" (func $three))
+ ;; CHECK: (export "three" (func $four))
(export "three" (func $three))
;; CHECK: (export "exp_glob" (global $exp_glob))
(export "exp_glob" (global $exp_glob))
(start $starter)
- ;; CHECK: (func $one (type $0) (result i32)
- ;; CHECK-NEXT: (call $two)
- ;; CHECK-NEXT: )
(func $one (result i32)
(call $two)
)
- ;; CHECK: (func $two (type $0) (result i32)
+ ;; CHECK: (func $two (type $1) (result i32)
;; CHECK-NEXT: (global.get $int)
;; CHECK-NEXT: )
(func $two (result i32)
(global.get $int)
)
- ;; CHECK: (func $three (type $1)
- ;; CHECK-NEXT: (call $four)
- ;; CHECK-NEXT: )
(func $three
(call $four)
)
- ;; CHECK: (func $four (type $1)
+ ;; CHECK: (func $four (type $2)
;; CHECK-NEXT: (global.set $set
;; CHECK-NEXT: (i32.const 200)
;; CHECK-NEXT: )
@@ -746,6 +737,7 @@
)
)
)
+
;; CHECK: (export "func" (func $0))
;; CHECK: (func $0 (type $0)
@@ -761,3 +753,220 @@
;; CHECK-NEXT: )
;; CHECK-NEXT: )
;; CHECK-NEXT: )
+(module
+ ;; When we export a function that calls another, we can export the called
+ ;; function, skipping the one in the middle. The exports of $middle and
+ ;; $other-middle can be changed to their targets here.
+
+ ;; CHECK: (type $0 (func))
+
+ ;; CHECK: (import "a" "b" (func $import (type $0)))
+ (import "a" "b" (func $import))
+
+ ;; CHECK: (export "export-import" (func $import))
+ (export "export-import" (func $import))
+
+ ;; CHECK: (export "export-middle" (func $import))
+ (export "export-middle" (func $middle))
+
+ ;; CHECK: (export "export-other-middle" (func $internal))
+ (export "export-other-middle" (func $other-middle))
+
+ ;; CHECK: (export "export-internal" (func $internal))
+ (export "export-internal" (func $internal))
+
+ (func $middle
+ (call $import)
+ )
+
+ (func $other-middle
+ (call $internal)
+ )
+
+ ;; CHECK: (func $internal (type $0)
+ ;; CHECK-NEXT: (nop)
+ ;; CHECK-NEXT: )
+ (func $internal
+ )
+)
+
+;; As above, but we do not do that optimization when it would change the
+;; exported type.
+(module
+ (rec
+ ;; CHECK: (rec
+ ;; CHECK-NEXT: (type $A (func))
+ (type $A (func))
+ ;; CHECK: (type $B (func))
+ (type $B (func))
+ )
+
+ ;; CHECK: (import "a" "a" (func $import-A (type $A)))
+ (import "a" "a" (func $import-A (type $A)))
+ ;; CHECK: (import "b" "b" (func $import-B (type $B)))
+ (import "b" "b" (func $import-B (type $B)))
+
+ ;; CHECK: (export "export-import-A" (func $import-A))
+ (export "export-import-A" (func $import-A))
+
+ ;; CHECK: (export "export-import-B" (func $import-B))
+ (export "export-import-B" (func $import-B))
+
+ ;; CHECK: (export "export-middle-A-A" (func $import-A))
+ (export "export-middle-A-A" (func $middle-A-A))
+
+ ;; CHECK: (export "export-middle-A-B" (func $middle-A-B))
+ (export "export-middle-A-B" (func $middle-A-B))
+
+ ;; CHECK: (export "export-middle-B-A" (func $middle-B-A))
+ (export "export-middle-B-A" (func $middle-B-A))
+
+ ;; CHECK: (export "export-middle-B-B" (func $import-B))
+ (export "export-middle-B-B" (func $middle-B-B))
+
+ (func $middle-A-A (type $A)
+ (call $import-A)
+ )
+
+ ;; CHECK: (func $middle-A-B (type $A)
+ ;; CHECK-NEXT: (call $import-B)
+ ;; CHECK-NEXT: )
+ (func $middle-A-B (type $A)
+ (call $import-B)
+ )
+
+ ;; CHECK: (func $middle-B-A (type $B)
+ ;; CHECK-NEXT: (call $import-A)
+ ;; CHECK-NEXT: )
+ (func $middle-B-A (type $B)
+ (call $import-A)
+ )
+
+ (func $middle-B-B (type $B)
+ (call $import-B)
+ )
+)
+
+;; As above, but checking for parameters: It's ok to pass values through, but
+;; not to do anything else.
+(module
+ ;; CHECK: (type $0 (func (param i32)))
+
+ ;; CHECK: (import "a" "b" (func $import (type $0) (param i32)))
+ (import "a" "b" (func $import (param i32)))
+
+ ;; CHECK: (export "export-import" (func $import))
+ (export "export-import" (func $import))
+
+ ;; CHECK: (export "export-middle" (func $import))
+ (export "export-middle" (func $middle))
+
+ ;; CHECK: (export "export-middle-local" (func $middle-local))
+ (export "export-middle-local" (func $middle-local))
+
+ ;; CHECK: (export "export-middle-other" (func $middle-other))
+ (export "export-middle-other" (func $middle-other))
+
+ ;; CHECK: (export "export-middle-noncall" (func $middle-noncall))
+ (export "export-middle-noncall" (func $middle-noncall))
+
+ (func $middle (param $x i32)
+ ;; This extra local is not a problem.
+ (local $y i32)
+ (call $import
+ (local.get $x)
+ )
+ )
+
+ ;; CHECK: (func $middle-local (type $0) (param $x i32)
+ ;; CHECK-NEXT: (local $y i32)
+ ;; CHECK-NEXT: (call $import
+ ;; CHECK-NEXT: (local.get $y)
+ ;; CHECK-NEXT: )
+ ;; CHECK-NEXT: )
+ (func $middle-local (param $x i32)
+ (local $y i32)
+ (call $import
+ ;; Now we get the local instead of the param, so we cannot optimize.
+ (local.get $y)
+ )
+ )
+
+ ;; CHECK: (func $middle-other (type $0) (param $x i32)
+ ;; CHECK-NEXT: (call $import
+ ;; CHECK-NEXT: (i32.const 1)
+ ;; CHECK-NEXT: )
+ ;; CHECK-NEXT: )
+ (func $middle-other (param $x i32)
+ (call $import
+ ;; Something other than local.get, so we cannot optimize.
+ (i32.const 1)
+ )
+ )
+
+ ;; CHECK: (func $middle-noncall (type $0) (param $x i32)
+ ;; CHECK-NEXT: (drop
+ ;; CHECK-NEXT: (i32.const 1)
+ ;; CHECK-NEXT: )
+ ;; CHECK-NEXT: )
+ (func $middle-noncall (param $x i32)
+ ;; Not even a call here.
+ (drop
+ (i32.const 1)
+ )
+ )
+)
+
+;; Function with two parameters: we can only optimize when the arguments are in
+;; the right order.
+;;
+;; Also test with a return value.
+(module
+ ;; CHECK: (type $0 (func (param i32 i32) (result f64)))
+
+ ;; CHECK: (import "a" "b" (func $import (type $0) (param i32 i32) (result f64)))
+ (import "a" "b" (func $import (param i32) (param i32) (result f64)))
+
+ ;; CHECK: (export "export-middle-right" (func $import))
+ (export "export-middle-right" (func $middle-right))
+
+ ;; CHECK: (export "export-middle-wrong" (func $middle-wrong))
+ (export "export-middle-wrong" (func $middle-wrong))
+
+ (func $middle-right (param $x i32) (param $y i32) (result f64)
+ (call $import
+ (local.get $x)
+ (local.get $y)
+ )
+ )
+
+ ;; CHECK: (func $middle-wrong (type $0) (param $x i32) (param $y i32) (result f64)
+ ;; CHECK-NEXT: (call $import
+ ;; CHECK-NEXT: (local.get $y)
+ ;; CHECK-NEXT: (local.get $x)
+ ;; CHECK-NEXT: )
+ ;; CHECK-NEXT: )
+ (func $middle-wrong (param $x i32) (param $y i32) (result f64)
+ ;; The local.gets are reversed here, so we cannot optimize.
+ (call $import
+ (local.get $y)
+ (local.get $x)
+ )
+ )
+)
+
+(module
+ ;; As above, but with a return_call. We can optimize it like a call.
+
+ ;; CHECK: (type $0 (func))
+
+ ;; CHECK: (import "a" "b" (func $import (type $0)))
+ (import "a" "b" (func $import))
+
+ ;; CHECK: (export "export-middle" (func $import))
+ (export "export-middle" (func $middle))
+
+ (func $middle
+ (return_call $import)
+ )
+)
diff --git a/test/metadce/threaded.wast.dced b/test/metadce/threaded.wast.dced
index 0d5d2f98d..3157a360a 100644
--- a/test/metadce/threaded.wast.dced
+++ b/test/metadce/threaded.wast.dced
@@ -3,20 +3,11 @@
(import "env" "js_func4" (func $js_func_4 (type $0)))
(import "env" "js_func3" (func $js_func_3 (type $0)))
(import "env" "js_func2" (func $js_func_2 (type $0)))
- (export "wasm_func1" (func $wasm_func_1))
- (export "wasm_func2" (func $wasm_func_2))
- (export "wasm_func3" (func $wasm_func_3))
+ (export "wasm_func1" (func $js_func_2))
+ (export "wasm_func2" (func $js_func_3))
+ (export "wasm_func3" (func $js_func_4))
(export "wasm_func4" (func $wasm_func_4))
(func $wasm_func_4 (type $0)
(nop)
)
- (func $wasm_func_3 (type $0)
- (call $js_func_4)
- )
- (func $wasm_func_2 (type $0)
- (call $js_func_3)
- )
- (func $wasm_func_1 (type $0)
- (call $js_func_2)
- )
)
diff --git a/test/metadce/threaded_cycle.wast.dced b/test/metadce/threaded_cycle.wast.dced
index 302cb3faf..1b30eadc5 100644
--- a/test/metadce/threaded_cycle.wast.dced
+++ b/test/metadce/threaded_cycle.wast.dced
@@ -4,20 +4,8 @@
(import "env" "js_func3" (func $js_func_3 (type $0)))
(import "env" "js_func2" (func $js_func_2 (type $0)))
(import "env" "js_func1" (func $js_func_1 (type $0)))
- (export "wasm_func1" (func $wasm_func_1))
- (export "wasm_func2" (func $wasm_func_2))
- (export "wasm_func3" (func $wasm_func_3))
- (export "wasm_func4" (func $wasm_func_4))
- (func $wasm_func_4 (type $0)
- (call $js_func_1)
- )
- (func $wasm_func_3 (type $0)
- (call $js_func_4)
- )
- (func $wasm_func_2 (type $0)
- (call $js_func_3)
- )
- (func $wasm_func_1 (type $0)
- (call $js_func_2)
- )
+ (export "wasm_func1" (func $js_func_2))
+ (export "wasm_func2" (func $js_func_3))
+ (export "wasm_func3" (func $js_func_4))
+ (export "wasm_func4" (func $js_func_1))
)
diff --git a/test/passes/remove-unused-nonfunction-module-elements_all-features.txt b/test/passes/remove-unused-nonfunction-module-elements_all-features.txt
index d19fcc514..186bdd69b 100644
--- a/test/passes/remove-unused-nonfunction-module-elements_all-features.txt
+++ b/test/passes/remove-unused-nonfunction-module-elements_all-features.txt
@@ -6,7 +6,7 @@
(table $0 1 1 funcref)
(elem $0 (i32.const 0) $called_indirect)
(export "memory" (memory $0))
- (export "exported" (func $exported))
+ (export "exported" (func $called2))
(export "other1" (func $other1))
(export "other2" (func $other2))
(start $start)
@@ -240,8 +240,8 @@
(global $int (mut i32) (global.get $imported))
(global $set (mut i32) (i32.const 100))
(global $exp_glob i32 (i32.const 600))
- (export "one" (func $one))
- (export "three" (func $three))
+ (export "one" (func $two))
+ (export "three" (func $four))
(export "exp_glob" (global $exp_glob))
(func $one (type $1) (result i32)
(call $two)
diff --git a/test/wasm2js/dot_import.2asm.js b/test/wasm2js/dot_import.2asm.js
index a35eabe95..0cd48aaf1 100644
--- a/test/wasm2js/dot_import.2asm.js
+++ b/test/wasm2js/dot_import.2asm.js
@@ -13,12 +13,8 @@ function asmFunc(imports) {
var Math_sqrt = Math.sqrt;
var mod_ule = imports["mod.ule"];
var base = mod_ule["ba.se"];
- function $0() {
- base();
- }
-
return {
- "exported": $0
+ "exported": base
};
}
diff --git a/test/wasm2js/dot_import.2asm.js.opt b/test/wasm2js/dot_import.2asm.js.opt
index a35eabe95..0cd48aaf1 100644
--- a/test/wasm2js/dot_import.2asm.js.opt
+++ b/test/wasm2js/dot_import.2asm.js.opt
@@ -13,12 +13,8 @@ function asmFunc(imports) {
var Math_sqrt = Math.sqrt;
var mod_ule = imports["mod.ule"];
var base = mod_ule["ba.se"];
- function $0() {
- base();
- }
-
return {
- "exported": $0
+ "exported": base
};
}
diff --git a/test/wasm2js/emscripten.2asm.js b/test/wasm2js/emscripten.2asm.js
index 8ba8564ce..52412f676 100644
--- a/test/wasm2js/emscripten.2asm.js
+++ b/test/wasm2js/emscripten.2asm.js
@@ -61,10 +61,6 @@ function asmFunc(imports) {
exported(1 | 0) | 0;
}
- function other() {
- main();
- }
-
function foo() {
wasm2js_trap();
}
@@ -222,7 +218,7 @@ function asmFunc(imports) {
return {
"main": main,
- "other": other,
+ "other": main,
"__growWasmMemory": __growWasmMemory,
"exported": exported,
"sub_zero": sub_zero,
diff --git a/test/wasm2js/emscripten.2asm.js.opt b/test/wasm2js/emscripten.2asm.js.opt
index caef23896..1faf11933 100644
--- a/test/wasm2js/emscripten.2asm.js.opt
+++ b/test/wasm2js/emscripten.2asm.js.opt
@@ -70,10 +70,6 @@ function asmFunc(imports) {
FUNCTION_TABLE[HEAP32[257]]();
}
- function other() {
- main();
- }
-
function foo() {
wasm2js_trap();
}
@@ -217,7 +213,7 @@ function asmFunc(imports) {
return {
"main": main,
- "other": other,
+ "other": main,
"__growWasmMemory": __growWasmMemory,
"exported": internal,
"sub_zero": sub_zero,
diff --git a/test/wasm2js/func_ptrs.2asm.js b/test/wasm2js/func_ptrs.2asm.js
index 4b7c4fd44..ccd220152 100644
--- a/test/wasm2js/func_ptrs.2asm.js
+++ b/test/wasm2js/func_ptrs.2asm.js
@@ -27,16 +27,11 @@ function asmFunc(imports) {
return a - 2 | 0 | 0;
}
- function $6($0) {
- $0 = $0 | 0;
- print($0 | 0);
- }
-
return {
"one": $3,
"two": $4,
"three": $5,
- "four": $6
+ "four": print
};
}