diff options
-rw-r--r-- | src/wasm/wasm.cpp | 8 | ||||
-rw-r--r-- | test/passes/dce_all-features.txt | 6 | ||||
-rw-r--r-- | test/passes/dce_all-features.wast | 15 |
3 files changed, 29 insertions, 0 deletions
diff --git a/src/wasm/wasm.cpp b/src/wasm/wasm.cpp index 5b1163ae0..0dfcf5c2e 100644 --- a/src/wasm/wasm.cpp +++ b/src/wasm/wasm.cpp @@ -959,9 +959,17 @@ Type BrOn::getSentType() { // BrOnNull does not send a value on the branch. return Type::none; case BrOnNonNull: + // If the input is unreachable, the branch is not taken, and there is no + // valid type we can report as being sent. Report it as unreachable. + if (ref->type == Type::unreachable) { + return Type::unreachable; + } // BrOnNonNull sends the non-nullable type on the branch. return Type(ref->type.getHeapType(), NonNullable); case BrOnCast: + if (ref->type == Type::unreachable) { + return Type::unreachable; + } return Type(rtt->type.getHeapType(), NonNullable); case BrOnFunc: return Type::funcref; diff --git a/test/passes/dce_all-features.txt b/test/passes/dce_all-features.txt index bc1e24951..779405c13 100644 --- a/test/passes/dce_all-features.txt +++ b/test/passes/dce_all-features.txt @@ -591,3 +591,9 @@ ) ) ) +(module + (type $none_=>_ref|any| (func (result (ref any)))) + (func $foo (result (ref any)) + (unreachable) + ) +) diff --git a/test/passes/dce_all-features.wast b/test/passes/dce_all-features.wast index 0f0416f66..95344be93 100644 --- a/test/passes/dce_all-features.wast +++ b/test/passes/dce_all-features.wast @@ -792,3 +792,18 @@ ) ) ) +(module + (func $foo (result (ref any)) + (block $label$1 (result (ref any)) + ;; this break has an unreachable input, and so it does not have a heap type + ;; there, and no heap type to send on the branch. this tests we do not hit + ;; the assertion in getHeapType() if we call that. + (br_on_non_null $label$1 + (block (result anyref) + (unreachable) + ) + ) + (unreachable) + ) + ) +) |