diff options
author | Alon Zakai <azakai@google.com> | 2022-06-01 16:12:18 -0700 |
---|---|---|
committer | GitHub <noreply@github.com> | 2022-06-01 16:12:18 -0700 |
commit | fc00dcc64c337a8128fbf2b5fbdb40bb0aaa861b (patch) | |
tree | 0daaeba892f71afa945a1df27e328a2a3efc8071 /src/tools/fuzzing/fuzzing.cpp | |
parent | 8470e7d780e6cf6171f47638e54bd5a019d8e055 (diff) | |
download | binaryen-fc00dcc64c337a8128fbf2b5fbdb40bb0aaa861b.tar.gz binaryen-fc00dcc64c337a8128fbf2b5fbdb40bb0aaa861b.tar.bz2 binaryen-fc00dcc64c337a8128fbf2b5fbdb40bb0aaa861b.zip |
Fuzzer: Add support for creating structs and arrays in makeConst (#4707)
#4659 adds a testcase with an import of (ref $struct). This could cause an error in
the fuzzer, since it wants to remove imports (because the various fuzzers cannot pass
in custom imports - they want to just run the wasm). When it tries to remove that
import it tries to create a constant for a struct reference, and fails. To fix that, add
enough support to create structs and arrays at least in the simple case where all their
fields are defaultable.
Diffstat (limited to 'src/tools/fuzzing/fuzzing.cpp')
-rw-r--r-- | src/tools/fuzzing/fuzzing.cpp | 28 |
1 files changed, 20 insertions, 8 deletions
diff --git a/src/tools/fuzzing/fuzzing.cpp b/src/tools/fuzzing/fuzzing.cpp index fe091c91f..e5afbf559 100644 --- a/src/tools/fuzzing/fuzzing.cpp +++ b/src/tools/fuzzing/fuzzing.cpp @@ -2017,23 +2017,35 @@ Expression* TranslateToFuzzReader::makeConstCompoundRef(Type type) { assert(wasm.features.hasReferenceTypes()); if (heapType.isSignature()) { return makeRefFuncConst(type); - } else { - // TODO: Handle nontrivial array and struct types. } + // We weren't able to directly materialize a non-null constant. Try again to // create a null. if (type.isNullable()) { return builder.makeRefNull(type); } + // We have to produce a non-null value. Possibly create a null and cast it // to non-null even though that will trap at runtime. We must have a - // function context because the cast is not allowed in globals. - if (!funcContext) { - std::cerr << type << "\n"; + // function context for this because the cast is not allowed in globals. + if (funcContext) { + return builder.makeRefAs(RefAsNonNull, + builder.makeRefNull(Type(heapType, Nullable))); + } + + // Otherwise, we are not in a function context. This can happen if we need + // to make a constant for the initializer of a global, for example. We've + // already handled simple cases of this above, for basic heap types, so what + // we have left here are user-defined heap types like structs. + // TODO: support non-defaultable fields. for now, just use default values. + if (type.isStruct()) { + return builder.makeStructNew(type.getHeapType(), + std::vector<Expression*>{}); + } else if (type.isArray()) { + return builder.makeArrayNew(type.getHeapType(), makeConst(Type::i32)); + } else { + WASM_UNREACHABLE("bad user-defined ref type"); } - assert(funcContext); - return builder.makeRefAs(RefAsNonNull, - builder.makeRefNull(Type(heapType, Nullable))); } Expression* TranslateToFuzzReader::buildUnary(const UnaryArgs& args) { |