1 use anyhow::{bail, Result};
2 use wasmtime::*;
3 
4 fn serialize(engine: &Engine, wat: &'static str) -> Result<Vec<u8>> {
5     let module = Module::new(&engine, wat)?;
6     Ok(module.serialize()?)
7 }
8 
9 unsafe fn deserialize_and_instantiate(store: &mut Store<()>, buffer: &[u8]) -> Result<Instance> {
10     let module = Module::deserialize(store.engine(), buffer)?;
11     Ok(Instance::new(store, &module, &[])?)
12 }
13 
14 #[test]
15 fn test_version_mismatch() -> Result<()> {
16     let engine = Engine::default();
17     let mut buffer = serialize(&engine, "(module)")?;
18     buffer[13 /* header length */ + 1 /* version length */] = 'x' as u8;
19 
20     match unsafe { Module::deserialize(&engine, &buffer) } {
21         Ok(_) => bail!("expected deserialization to fail"),
22         Err(e) => assert!(e
23             .to_string()
24             .starts_with("Module was compiled with incompatible Wasmtime version")),
25     }
26 
27     // Test deserialize_check_wasmtime_version, which disables the logic which rejects the above.
28     let mut config = Config::new();
29     config.deserialize_check_wasmtime_version(false);
30     let engine = Engine::new(&config).unwrap();
31     unsafe { Module::deserialize(&engine, &buffer) }
32         .expect("module with corrupt version should deserialize when check is disabled");
33 
34     Ok(())
35 }
36 
37 #[test]
38 fn test_module_serialize_simple() -> Result<()> {
39     let buffer = serialize(
40         &Engine::default(),
41         "(module (func (export \"run\") (result i32) i32.const 42))",
42     )?;
43 
44     let mut store = Store::default();
45     let instance = unsafe { deserialize_and_instantiate(&mut store, &buffer)? };
46     let run = instance.get_typed_func::<(), i32, _>(&mut store, "run")?;
47     let result = run.call(&mut store, ())?;
48 
49     assert_eq!(42, result);
50     Ok(())
51 }
52 
53 #[test]
54 fn test_module_serialize_fail() -> Result<()> {
55     let buffer = serialize(
56         &Engine::default(),
57         "(module (func (export \"run\") (result i32) i32.const 42))",
58     )?;
59 
60     let mut config = Config::new();
61     config.cranelift_opt_level(OptLevel::None);
62     let mut store = Store::new(&Engine::new(&config)?, ());
63     match unsafe { deserialize_and_instantiate(&mut store, &buffer) } {
64         Ok(_) => bail!("expected failure at deserialization"),
65         Err(_) => (),
66     }
67     Ok(())
68 }
69