summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAlon Zakai <azakai@google.com>2023-03-06 17:15:22 -0800
committerGitHub <noreply@github.com>2023-03-06 17:15:22 -0800
commit61921b4af3f471508dff0d764b4ffbf0a4cba5fb (patch)
tree604f9f6e8adf1bb4908fc8897b27d2c9333ac4c7
parent661fe5e72987e97d5f6db0d4cbefc73c1e166e36 (diff)
downloadbinaryen-61921b4af3f471508dff0d764b4ffbf0a4cba5fb.tar.gz
binaryen-61921b4af3f471508dff0d764b4ffbf0a4cba5fb.tar.bz2
binaryen-61921b4af3f471508dff0d764b4ffbf0a4cba5fb.zip
SignatureRefining: Skip types with supertypes for now (#5548)
We'd need to handle contravariance to optimize them.
-rw-r--r--src/passes/SignatureRefining.cpp6
-rw-r--r--test/lit/passes/signature-refining.wast30
2 files changed, 36 insertions, 0 deletions
diff --git a/src/passes/SignatureRefining.cpp b/src/passes/SignatureRefining.cpp
index 376c74442..de669dbb2 100644
--- a/src/passes/SignatureRefining.cpp
+++ b/src/passes/SignatureRefining.cpp
@@ -147,6 +147,12 @@ struct SignatureRefining : public Pass {
for (auto& [type, info] : allInfo) {
if (!subTypes.getStrictSubTypes(type).empty()) {
info.canModify = false;
+ } else if (type.getSuperType()) {
+ // Also avoid modifying types with supertypes, as we do not handle
+ // contravariance here. That is, when we refine parameters we look for
+ // a more refined type, but the type must be *less* refined than the
+ // param type for the parent (or equal) TODO
+ info.canModify = false;
}
}
diff --git a/test/lit/passes/signature-refining.wast b/test/lit/passes/signature-refining.wast
index 353d3d211..d8da19a64 100644
--- a/test/lit/passes/signature-refining.wast
+++ b/test/lit/passes/signature-refining.wast
@@ -780,3 +780,33 @@
(ref.func $func)
)
)
+
+;; Until we handle contravariance, do not try to optimize a type that has a
+;; supertype. In this example, refining the child's anyref to nullref would
+;; cause an error.
+(module
+ ;; CHECK: (type $parent (func (param anyref)))
+ (type $parent (func (param anyref)))
+ ;; CHECK: (type $child (func_subtype (param anyref) $parent))
+ (type $child (func_subtype (param anyref) $parent))
+
+ ;; CHECK: (type $none_=>_none (func))
+
+ ;; CHECK: (func $func (type $child) (param $0 anyref)
+ ;; CHECK-NEXT: (unreachable)
+ ;; CHECK-NEXT: )
+ (func $func (type $child) (param anyref)
+ (unreachable)
+ )
+
+ ;; CHECK: (func $caller (type $none_=>_none)
+ ;; CHECK-NEXT: (call $func
+ ;; CHECK-NEXT: (ref.null none)
+ ;; CHECK-NEXT: )
+ ;; CHECK-NEXT: )
+ (func $caller
+ (call $func
+ (ref.null eq)
+ )
+ )
+)