fuzzing: Add tests for dummy import generation (#2604)

This commit is contained in:
Nick Fitzgerald
2021-01-26 07:11:24 -08:00
committed by GitHub
parent f4faa04dca
commit c7c6e76f9b
2 changed files with 231 additions and 2 deletions

View File

@@ -349,3 +349,232 @@ fn wat_ty(ty: &ValType) -> &'static str {
ValType::FuncRef => "funcref",
}
}
#[cfg(test)]
mod tests {
use super::*;
use std::collections::HashSet;
fn store() -> Store {
let mut config = Config::default();
config.wasm_module_linking(true);
config.wasm_multi_memory(true);
let engine = wasmtime::Engine::new(&config);
Store::new(&engine)
}
#[test]
fn dummy_table_import() {
let store = store();
let table = dummy_table(
&store,
TableType::new(ValType::ExternRef, Limits::at_least(10)),
);
assert_eq!(table.size(), 10);
for i in 0..10 {
assert!(table.get(i).unwrap().unwrap_externref().is_none());
}
}
#[test]
fn dummy_global_import() {
let store = store();
let global = dummy_global(&store, GlobalType::new(ValType::I32, Mutability::Const));
assert_eq!(global.val_type(), ValType::I32);
assert_eq!(global.mutability(), Mutability::Const);
}
#[test]
fn dummy_memory_import() {
let store = store();
let memory = dummy_memory(&store, MemoryType::new(Limits::at_least(1)));
assert_eq!(memory.size(), 1);
}
#[test]
fn dummy_function_import() {
let store = store();
let func_ty = FuncType::new(vec![ValType::I32], vec![ValType::I64]);
let func = dummy_func(&store, func_ty.clone());
assert_eq!(func.ty(), func_ty);
}
#[test]
fn dummy_instance_import() {
let store = store();
let mut instance_ty = InstanceType::new();
// Functions.
instance_ty.add_named_export("func0", FuncType::new(vec![ValType::I32], vec![]).into());
instance_ty.add_named_export("func1", FuncType::new(vec![], vec![ValType::I64]).into());
// Globals.
instance_ty.add_named_export(
"global0",
GlobalType::new(ValType::I32, Mutability::Const).into(),
);
instance_ty.add_named_export(
"global1",
GlobalType::new(ValType::I64, Mutability::Var).into(),
);
// Tables.
instance_ty.add_named_export(
"table0",
TableType::new(ValType::ExternRef, Limits::at_least(1)).into(),
);
instance_ty.add_named_export(
"table1",
TableType::new(ValType::ExternRef, Limits::at_least(1)).into(),
);
// Memories.
instance_ty.add_named_export("memory0", MemoryType::new(Limits::at_least(1)).into());
instance_ty.add_named_export("memory1", MemoryType::new(Limits::at_least(1)).into());
// Modules.
instance_ty.add_named_export("module0", ModuleType::new().into());
instance_ty.add_named_export("module1", ModuleType::new().into());
// Instances.
instance_ty.add_named_export("instance0", InstanceType::new().into());
instance_ty.add_named_export("instance1", InstanceType::new().into());
let instance = dummy_instance(&store, instance_ty.clone());
let mut expected_exports = vec![
"func0",
"func1",
"global0",
"global1",
"table0",
"table1",
"memory0",
"memory1",
"module0",
"module1",
"instance0",
"instance1",
]
.into_iter()
.collect::<HashSet<_>>();
for exp in instance.ty().exports() {
let was_expected = expected_exports.remove(exp.name());
assert!(was_expected);
}
assert!(expected_exports.is_empty());
}
#[test]
fn dummy_module_import() {
let store = store();
let mut module_ty = ModuleType::new();
// Multiple exported and imported functions.
module_ty.add_named_export("func0", FuncType::new(vec![ValType::I32], vec![]).into());
module_ty.add_named_export("func1", FuncType::new(vec![], vec![ValType::I64]).into());
module_ty.add_named_import(
"func2",
None,
FuncType::new(vec![ValType::I64], vec![]).into(),
);
module_ty.add_named_import(
"func3",
None,
FuncType::new(vec![], vec![ValType::I32]).into(),
);
// Multiple exported and imported globals.
module_ty.add_named_export(
"global0",
GlobalType::new(ValType::I32, Mutability::Const).into(),
);
module_ty.add_named_export(
"global1",
GlobalType::new(ValType::I64, Mutability::Var).into(),
);
module_ty.add_named_import(
"global2",
None,
GlobalType::new(ValType::I32, Mutability::Var).into(),
);
module_ty.add_named_import(
"global3",
None,
GlobalType::new(ValType::I64, Mutability::Const).into(),
);
// Multiple exported and imported tables.
module_ty.add_named_export(
"table0",
TableType::new(ValType::ExternRef, Limits::at_least(1)).into(),
);
module_ty.add_named_export(
"table1",
TableType::new(ValType::ExternRef, Limits::at_least(1)).into(),
);
module_ty.add_named_import(
"table2",
None,
TableType::new(ValType::ExternRef, Limits::at_least(1)).into(),
);
module_ty.add_named_import(
"table3",
None,
TableType::new(ValType::ExternRef, Limits::at_least(1)).into(),
);
// Multiple exported and imported memories.
module_ty.add_named_export("memory0", MemoryType::new(Limits::at_least(1)).into());
module_ty.add_named_export("memory1", MemoryType::new(Limits::at_least(1)).into());
module_ty.add_named_import("memory2", None, MemoryType::new(Limits::at_least(1)).into());
module_ty.add_named_import("memory3", None, MemoryType::new(Limits::at_least(1)).into());
// An exported and an imported module.
module_ty.add_named_export("module0", ModuleType::new().into());
module_ty.add_named_import("module1", None, ModuleType::new().into());
// An exported and an imported instance.
module_ty.add_named_export("instance0", InstanceType::new().into());
module_ty.add_named_import("instance1", None, InstanceType::new().into());
// Create the module.
let module = dummy_module(&store, module_ty);
// Check that we have the expected exports.
assert!(module.get_export("func0").is_some());
assert!(module.get_export("func1").is_some());
assert!(module.get_export("global0").is_some());
assert!(module.get_export("global1").is_some());
assert!(module.get_export("table0").is_some());
assert!(module.get_export("table1").is_some());
assert!(module.get_export("memory0").is_some());
assert!(module.get_export("memory1").is_some());
assert!(module.get_export("instance0").is_some());
assert!(module.get_export("module0").is_some());
// Check that we have the exported imports.
let mut expected_imports = vec![
"func2",
"func3",
"global2",
"global3",
"table2",
"table3",
"memory2",
"memory3",
"instance1",
"module1",
]
.into_iter()
.collect::<HashSet<_>>();
for imp in module.imports() {
assert!(imp.name().is_none());
let was_expected = expected_imports.remove(imp.module());
assert!(was_expected);
}
assert!(expected_imports.is_empty());
}
}

View File

@@ -466,12 +466,12 @@ impl ModuleType {
}
/// Adds a new export to this `ModuleType`.
pub(crate) fn add_named_export(&mut self, name: &str, ty: ExternType) {
pub fn add_named_export(&mut self, name: &str, ty: ExternType) {
self.exports.push((name.to_string(), ty));
}
/// Adds a new import to this `ModuleType`.
pub(crate) fn add_named_import(&mut self, module: &str, field: Option<&str>, ty: ExternType) {
pub fn add_named_import(&mut self, module: &str, field: Option<&str>, ty: ExternType) {
self.imports
.push((module.to_string(), field.map(|f| f.to_string()), ty));
}