summaryrefslogtreecommitdiff
path: root/src/tools
diff options
context:
space:
mode:
Diffstat (limited to 'src/tools')
-rw-r--r--src/tools/fuzzing/fuzzing.cpp9
-rw-r--r--src/tools/fuzzing/heap-types.cpp27
-rw-r--r--src/tools/wasm-fuzz-types.cpp106
3 files changed, 96 insertions, 46 deletions
diff --git a/src/tools/fuzzing/fuzzing.cpp b/src/tools/fuzzing/fuzzing.cpp
index cdefe29f1..cc64b3b6a 100644
--- a/src/tools/fuzzing/fuzzing.cpp
+++ b/src/tools/fuzzing/fuzzing.cpp
@@ -1968,6 +1968,10 @@ Expression* TranslateToFuzzReader::makeConstBasicRef(Type type) {
assert(heapType.isBasic());
assert(wasm.features.hasReferenceTypes());
switch (heapType.getBasic()) {
+ case HeapType::ext: {
+ assert(type.isNullable() && "Cannot handle non-nullable externref");
+ return builder.makeRefNull(type);
+ }
case HeapType::func: {
return makeRefFuncConst(type);
}
@@ -3089,13 +3093,14 @@ HeapType TranslateToFuzzReader::getSubType(HeapType type) {
case HeapType::func:
// TODO: Typed function references.
return HeapType::func;
+ case HeapType::ext:
+ return HeapType::ext;
case HeapType::any:
// TODO: nontrivial types as well.
return pick(
FeatureOptions<HeapType>()
- .add(FeatureSet::ReferenceTypes, HeapType::func, HeapType::any)
+ .add(FeatureSet::ReferenceTypes, HeapType::func /*, HeapType::ext*/)
.add(FeatureSet::ReferenceTypes | FeatureSet::GC,
- HeapType::func,
HeapType::any,
HeapType::eq,
HeapType::i31,
diff --git a/src/tools/fuzzing/heap-types.cpp b/src/tools/fuzzing/heap-types.cpp
index 364065b8b..5a8f0fc0e 100644
--- a/src/tools/fuzzing/heap-types.cpp
+++ b/src/tools/fuzzing/heap-types.cpp
@@ -153,6 +153,7 @@ struct HeapTypeGeneratorImpl {
HeapType::BasicHeapType generateBasicHeapType() {
return rand.pick(HeapType::func,
+ HeapType::ext,
HeapType::any,
HeapType::eq,
HeapType::i31,
@@ -278,6 +279,7 @@ struct HeapTypeGeneratorImpl {
return type;
} else {
switch (type) {
+ case HeapType::ext:
case HeapType::i31:
// No other subtypes.
return type;
@@ -371,6 +373,8 @@ struct HeapTypeGeneratorImpl {
// This is not a constructed type, so it must be a basic type.
assert(type.isBasic());
switch (type.getBasic()) {
+ case HeapType::ext:
+ return HeapType::ext;
case HeapType::func:
return pickSubFunc();
case HeapType::any:
@@ -477,16 +481,31 @@ struct HeapTypeGeneratorImpl {
switch (*basic) {
case HeapType::func:
return SignatureKind{};
+ case HeapType::ext:
case HeapType::i31:
return super;
case HeapType::any:
- return generateHeapTypeKind();
+ if (rand.oneIn(4)) {
+ switch (rand.upTo(3)) {
+ case 0:
+ return HeapType::eq;
+ case 1:
+ return HeapType::i31;
+ case 2:
+ return HeapType::data;
+ }
+ }
+ return DataKind{};
case HeapType::eq:
if (rand.oneIn(4)) {
- return HeapType::i31;
- } else {
- return DataKind{};
+ switch (rand.upTo(2)) {
+ case 0:
+ return HeapType::i31;
+ case 1:
+ return HeapType::data;
+ }
}
+ return DataKind{};
case HeapType::data:
return DataKind{};
case HeapType::string:
diff --git a/src/tools/wasm-fuzz-types.cpp b/src/tools/wasm-fuzz-types.cpp
index d80c89ea8..bbf4967e3 100644
--- a/src/tools/wasm-fuzz-types.cpp
+++ b/src/tools/wasm-fuzz-types.cpp
@@ -152,46 +152,72 @@ void Fuzzer::checkLUBs() const {
HeapType a = types[i], b = types[j];
// Check that their LUB is stable when calculated multiple times and in
// reverse order.
- HeapType lub = HeapType::getLeastUpperBound(a, b);
- if (lub != HeapType::getLeastUpperBound(b, a) ||
- lub != HeapType::getLeastUpperBound(a, b)) {
- Fatal() << "Could not calculate a stable LUB of HeapTypes " << i
- << " and " << j << "!\n"
- << i << ": " << a << "\n"
- << j << ": " << b << "\n";
- }
- // Check that each type is a subtype of the LUB.
- if (!HeapType::isSubType(a, lub)) {
- Fatal() << "HeapType " << i
- << " is not a subtype of its LUB with HeapType " << j << "!\n"
- << i << ": " << a << "\n"
- << j << ": " << b << "\n"
- << "lub: " << lub << "\n";
- }
- if (!HeapType::isSubType(b, lub)) {
- Fatal() << "HeapType " << j
- << " is not a subtype of its LUB with HeapType " << i << "!\n"
- << i << ": " << a << "\n"
- << j << ": " << b << "\n"
- << "lub: " << lub << "\n";
- }
- // Check that the LUB of each type and the original LUB is still the
- // original LUB.
- if (lub != HeapType::getLeastUpperBound(a, lub)) {
- Fatal() << "The LUB of HeapType " << i << " and HeapType " << j
- << " should be the LUB of itself and HeapType " << i
- << ", but it is not!\n"
- << i << ": " << a << "\n"
- << j << ": " << b << "\n"
- << "lub: " << lub << "\n";
- }
- if (lub != HeapType::getLeastUpperBound(lub, b)) {
- Fatal() << "The LUB of HeapType " << i << " and HeapType " << j
- << " should be the LUB of itself and HeapType " << j
- << ", but it is not!\n"
- << i << ": " << a << "\n"
- << j << ": " << b << "\n"
- << "lub: " << lub << "\n";
+ auto lub = HeapType::getLeastUpperBound(a, b);
+ if (lub) {
+ if (lub != HeapType::getLeastUpperBound(b, a) ||
+ lub != HeapType::getLeastUpperBound(a, b)) {
+ Fatal() << "Could not calculate a stable LUB of HeapTypes " << i
+ << " and " << j << "!\n"
+ << i << ": " << a << "\n"
+ << j << ": " << b << "\n";
+ }
+ // Check that each type is a subtype of the LUB.
+ if (!HeapType::isSubType(a, *lub)) {
+ Fatal() << "HeapType " << i
+ << " is not a subtype of its LUB with HeapType " << j << "!\n"
+ << i << ": " << a << "\n"
+ << j << ": " << b << "\n"
+ << "lub: " << *lub << "\n";
+ }
+ if (!HeapType::isSubType(b, *lub)) {
+ Fatal() << "HeapType " << j
+ << " is not a subtype of its LUB with HeapType " << i << "!\n"
+ << i << ": " << a << "\n"
+ << j << ": " << b << "\n"
+ << "lub: " << *lub << "\n";
+ }
+ // Check that the LUB of each type and the original LUB is still the
+ // original LUB.
+ if (lub != HeapType::getLeastUpperBound(a, *lub)) {
+ Fatal() << "The LUB of HeapType " << i << " and HeapType " << j
+ << " should be the LUB of itself and HeapType " << i
+ << ", but it is not!\n"
+ << i << ": " << a << "\n"
+ << j << ": " << b << "\n"
+ << "lub: " << *lub << "\n";
+ }
+ if (lub != HeapType::getLeastUpperBound(*lub, b)) {
+ Fatal() << "The LUB of HeapType " << i << " and HeapType " << j
+ << " should be the LUB of itself and HeapType " << j
+ << ", but it is not!\n"
+ << i << ": " << a << "\n"
+ << j << ": " << b << "\n"
+ << "lub: " << *lub << "\n";
+ }
+ } else {
+ // No LUB. Check that this is symmetrical.
+ if (auto lub2 = HeapType::getLeastUpperBound(b, a)) {
+ Fatal() << "There is no LUB of HeapType " << i << " and HeapType "
+ << j << ", but there is a LUB in the reverse direction!\n"
+ << i << ": " << a << "\n"
+ << j << ": " << b << "\n"
+ << "lub: " << *lub2 << "\n";
+ }
+ // There also shouldn't be a subtype relation in this case.
+ if (HeapType::isSubType(a, b)) {
+ Fatal() << "There is no LUB of HeapType " << i << " and HeapType "
+ << j << ", but HeapType " << i << " is a subtype of HeapType "
+ << j << "!\n"
+ << i << ": " << a << "\n"
+ << j << ": " << b << "\n";
+ }
+ if (HeapType::isSubType(b, a)) {
+ Fatal() << "There is no LUB of HeapType " << i << " and HeapType "
+ << j << ", but HeapType " << j << " is a subtype of HeapType "
+ << i << "!\n"
+ << i << ": " << a << "\n"
+ << j << ": " << b << "\n";
+ }
}
}
}