diff options
author | Alon Zakai <azakai@google.com> | 2021-09-20 10:47:14 -0700 |
---|---|---|
committer | GitHub <noreply@github.com> | 2021-09-20 17:47:14 +0000 |
commit | 737c22d30798c491eea3b401b948b9327ac979de (patch) | |
tree | f75a72adbd81a85eca19b732378837670c828b23 /src/wasm/wasm.cpp | |
parent | b5e8c371001de20128453d5064ac0422d481020e (diff) | |
download | binaryen-737c22d30798c491eea3b401b948b9327ac979de.tar.gz binaryen-737c22d30798c491eea3b401b948b9327ac979de.tar.bz2 binaryen-737c22d30798c491eea3b401b948b9327ac979de.zip |
[Wasm GC] Add static variants of ref.test, ref.cast, and br_on_cast* (#4163)
These variants take a HeapType that is the type we intend to cast to,
and do not take an RTT.
These are intended to be more statically optimizable. For now though
this PR just implements the minimum to get them parsing and to get
through the optimizer without crashing.
Spec: https://docs.google.com/document/d/1afthjsL_B9UaMqCA5ekgVmOm75BVFu6duHNsN9-gnXw/edit#
See #4149
Diffstat (limited to 'src/wasm/wasm.cpp')
-rw-r--r-- | src/wasm/wasm.cpp | 25 |
1 files changed, 20 insertions, 5 deletions
diff --git a/src/wasm/wasm.cpp b/src/wasm/wasm.cpp index 2861c4cee..45137fffe 100644 --- a/src/wasm/wasm.cpp +++ b/src/wasm/wasm.cpp @@ -895,23 +895,33 @@ void CallRef::finalize(Type type_) { } void RefTest::finalize() { - if (ref->type == Type::unreachable || rtt->type == Type::unreachable) { + if (ref->type == Type::unreachable || + (rtt && rtt->type == Type::unreachable)) { type = Type::unreachable; } else { type = Type::i32; } } +HeapType RefTest::getIntendedType() { + return rtt ? rtt->type.getHeapType() : intendedType; +} + void RefCast::finalize() { - if (ref->type == Type::unreachable || rtt->type == Type::unreachable) { + if (ref->type == Type::unreachable || + (rtt && rtt->type == Type::unreachable)) { type = Type::unreachable; } else { // The output of ref.cast may be null if the input is null (in that case the // null is passed through). - type = Type(rtt->type.getHeapType(), ref->type.getNullability()); + type = Type(getIntendedType(), ref->type.getNullability()); } } +HeapType RefCast::getIntendedType() { + return rtt ? rtt->type.getHeapType() : intendedType; +} + void BrOn::finalize() { if (ref->type == Type::unreachable || (rtt && rtt->type == Type::unreachable)) { @@ -938,7 +948,7 @@ void BrOn::finalize() { case BrOnCastFail: // If we do not branch, the cast worked, and we have something of the cast // type. - type = Type(rtt->type.getHeapType(), NonNullable); + type = Type(getIntendedType(), NonNullable); break; case BrOnNonFunc: type = Type(HeapType::func, NonNullable); @@ -954,6 +964,11 @@ void BrOn::finalize() { } } +HeapType BrOn::getIntendedType() { + assert(op == BrOnCast || op == BrOnCastFail); + return rtt ? rtt->type.getHeapType() : intendedType; +} + Type BrOn::getSentType() { switch (op) { case BrOnNull: @@ -971,7 +986,7 @@ Type BrOn::getSentType() { if (ref->type == Type::unreachable) { return Type::unreachable; } - return Type(rtt->type.getHeapType(), NonNullable); + return Type(getIntendedType(), NonNullable); case BrOnFunc: return Type::funcref; case BrOnData: |