Skip to content

Commit 226787d

Browse files
authored
PrintBoundary: Handle recursive types (#8786)
Before, we infinitely recursed. Add this to fuzzing to find further issues. Drive-by: fix a `python` to `python3` in a script I just noticed.
1 parent 5d704ad commit 226787d

4 files changed

Lines changed: 25 additions & 5 deletions

File tree

scripts/bundle_clusterfuzz.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -184,5 +184,5 @@
184184
print('Done.')
185185
print('To run the tests on this bundle, do:')
186186
print()
187-
print(f'BINARYEN_CLUSTER_FUZZ_BUNDLE={output_file} python -m unittest test/unit/test_cluster_fuzz.py')
187+
print(f'BINARYEN_CLUSTER_FUZZ_BUNDLE={output_file} python3 -m unittest test/unit/test_cluster_fuzz.py')
188188
print()

scripts/fuzz_opt.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2698,6 +2698,7 @@ def write_commands(commands, filename):
26982698
("--precompute",),
26992699
("--precompute-propagate",),
27002700
("--print",),
2701+
("--print-boundary",),
27012702
("--remove-unused-brs",),
27022703
("--remove-unused-nonfunction-module-elements",),
27032704
("--remove-unused-module-elements",),

src/passes/PrintBoundary.cpp

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -104,15 +104,17 @@ struct PrintBoundary : public Pass {
104104
// results.
105105
//
106106
// We emit an array only when needed, unless forceArray is set.
107-
json::Value::Ref getTypes(Type type, bool forceArray = false) {
108-
if (type.isRef()) {
107+
json::Value::Ref
108+
getTypes(Type type, bool forceArray = false, size_t depth = 0) {
109+
// Avoid infinite recursion.
110+
if (type.isRef() && depth == 0) {
109111
auto heapType = type.getHeapType();
110112
if (heapType.isSignature()) {
111113
auto sig = heapType.getSignature();
112114
auto ret = json::Value::makeObject();
113115
// Always emit arrays for params and results.
114-
ret["params"] = getTypes(sig.params, true);
115-
ret["results"] = getTypes(sig.results, true);
116+
ret["params"] = getTypes(sig.params, true, depth + 1);
117+
ret["results"] = getTypes(sig.results, true, depth + 1);
116118
return ret;
117119
}
118120
}

test/lit/passes/print-boundary.wast

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
11
(module
22
(type $struct (struct))
33

4+
(type $recurse (func (param $x (ref $recurse))))
5+
46
(import "module" "base" (func $foo (param i32) (param f64) (result anyref)))
57

68
(import "module2" "other" (func $bar (result i32 f32)))
@@ -26,6 +28,10 @@
2628
(func $one (param $x (ref $struct)) (result i32 i32 i32)
2729
(unreachable)
2830
)
31+
32+
(func $recurse (export "recurse") (param $x (ref $recurse))
33+
;; We should not error on printing a recursive type.
34+
)
2935
)
3036

3137
;; RUN: wasm-opt %s -all --print-boundary -S -o - | filecheck %s
@@ -62,6 +68,17 @@
6268
;; CHECK-NEXT: ],
6369
;; CHECK-NEXT: "exports": [
6470
;; CHECK-NEXT: {
71+
;; CHECK-NEXT: "name": "recurse",
72+
;; CHECK-NEXT: "kind": "func",
73+
;; CHECK-NEXT: "type": {
74+
;; CHECK-NEXT: "params": [
75+
;; CHECK-NEXT: "(ref $func.0)"
76+
;; CHECK-NEXT: ],
77+
;; CHECK-NEXT: "results": [
78+
;; CHECK-NEXT: ]
79+
;; CHECK-NEXT: }
80+
;; CHECK-NEXT: },
81+
;; CHECK-NEXT: {
6582
;; CHECK-NEXT: "name": "one",
6683
;; CHECK-NEXT: "kind": "func",
6784
;; CHECK-NEXT: "type": {

0 commit comments

Comments
 (0)