Skip to content

Commit ea62172

Browse files
authored
[Stack Switching] Support Continuations in TypeMerging (#7831)
1 parent 3a38c07 commit ea62172

File tree

3 files changed

+63
-2
lines changed

3 files changed

+63
-2
lines changed

scripts/test/fuzzing.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -118,6 +118,7 @@
118118
'cont_many_unhandled.wast',
119119
'cont_export.wast',
120120
'cont_export_throw.wast',
121+
'type-merging-cont.wast',
121122
# TODO: fix split_wast() on tricky escaping situations like a string ending
122123
# in \\" (the " is not escaped - there is an escaped \ before it)
123124
'string-lifting-section.wast',

src/passes/TypeMerging.cpp

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -224,6 +224,7 @@ bool shapeEq(HeapType a, HeapType b);
224224
bool shapeEq(const Struct& a, const Struct& b);
225225
bool shapeEq(Array a, Array b);
226226
bool shapeEq(Signature a, Signature b);
227+
bool shapeEq(Continuation a, Continuation b);
227228
bool shapeEq(Field a, Field b);
228229
bool shapeEq(Type a, Type b);
229230
bool shapeEq(const Tuple& a, const Tuple& b);
@@ -232,6 +233,7 @@ size_t shapeHash(HeapType a);
232233
size_t shapeHash(const Struct& a);
233234
size_t shapeHash(Array a);
234235
size_t shapeHash(Signature a);
236+
size_t shapeHash(Continuation a);
235237
size_t shapeHash(Field a);
236238
size_t shapeHash(Type a);
237239
size_t shapeHash(const Tuple& a);
@@ -690,7 +692,10 @@ bool shapeEq(HeapType a, HeapType b) {
690692
}
691693
break;
692694
case HeapTypeKind::Cont:
693-
WASM_UNREACHABLE("TODO: cont");
695+
if (!shapeEq(a.getContinuation(), b.getContinuation())) {
696+
return false;
697+
}
698+
break;
694699
case HeapTypeKind::Basic:
695700
WASM_UNREACHABLE("unexpected kind");
696701
}
@@ -719,7 +724,8 @@ size_t shapeHash(HeapType a) {
719724
hash_combine(digest, shapeHash(type.getArray()));
720725
continue;
721726
case HeapTypeKind::Cont:
722-
WASM_UNREACHABLE("TODO: cont");
727+
hash_combine(digest, shapeHash(type.getContinuation()));
728+
continue;
723729
case HeapTypeKind::Basic:
724730
continue;
725731
}
@@ -762,6 +768,10 @@ size_t shapeHash(Signature a) {
762768
return digest;
763769
}
764770

771+
bool shapeEq(Continuation a, Continuation b) { return shapeEq(a.type, b.type); }
772+
773+
size_t shapeHash(Continuation a) { return shapeHash(a.type); }
774+
765775
bool shapeEq(Field a, Field b) {
766776
return a.packedType == b.packedType && a.mutable_ == b.mutable_ &&
767777
shapeEq(a.type, b.type);
Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
;; NOTE: Assertions have been generated by update_lit_checks.py --all-items and should not be edited.
2+
3+
;; RUN: foreach %s %t wasm-opt -all --closed-world --preserve-type-order \
4+
;; RUN: --type-merging --remove-unused-types -S -o - | filecheck %s
5+
6+
;; $A1 and $A2 can be merged, and $B1/$B2, as they have identical continuation
7+
;; fields. But $A*/B* cannot be merged, as the continuations differ.
8+
9+
(module
10+
;; CHECK: (rec
11+
;; CHECK-NEXT: (type $f (func))
12+
(type $f (func))
13+
;; CHECK: (type $f_0 (func))
14+
15+
;; CHECK: (type $k (cont $f_0))
16+
(type $k (cont $f))
17+
18+
(type $f-i32 (func (result i32)))
19+
;; CHECK: (type $f-i32_0 (func (result i32)))
20+
21+
;; CHECK: (type $k-i32 (cont $f-i32_0))
22+
(type $k-i32 (cont $f-i32))
23+
24+
(rec
25+
;; CHECK: (type $A1 (struct (field (ref $k))))
26+
(type $A1 (struct (ref $k)))
27+
(type $A2 (struct (ref $k)))
28+
;; CHECK: (type $B1 (struct (field (ref $k-i32))))
29+
(type $B1 (struct (ref $k-i32)))
30+
(type $B2 (struct (ref $k-i32)))
31+
)
32+
33+
;; CHECK: (func $test (type $f)
34+
;; CHECK-NEXT: (local $k (ref $k))
35+
;; CHECK-NEXT: (local $k-i32 (ref $k-i32))
36+
;; CHECK-NEXT: (local $a1 (ref $A1))
37+
;; CHECK-NEXT: (local $a2 (ref $A1))
38+
;; CHECK-NEXT: (local $b1 (ref $B1))
39+
;; CHECK-NEXT: (local $b2 (ref $B1))
40+
;; CHECK-NEXT: )
41+
(func $test
42+
(local $k (ref $k))
43+
(local $k-i32 (ref $k-i32))
44+
(local $a1 (ref $A1))
45+
(local $a2 (ref $A2))
46+
(local $b1 (ref $B1))
47+
(local $b2 (ref $B2))
48+
)
49+
)
50+

0 commit comments

Comments
 (0)