1 use std::sync::atomic::{AtomicU32, Ordering};
2 use wasmtime::*;
3
4 #[test]
5 #[cfg_attr(miri, ignore)]
func_wrap_no_extern() -> Result<()>6 fn func_wrap_no_extern() -> Result<()> {
7 let mut config = Config::default();
8 config.wasm_function_references(true);
9 config.wasm_gc(true);
10
11 let engine = Engine::new(&config)?;
12
13 let module = Module::new(
14 &engine,
15 r#"
16 (module
17 (import "" "" (func (param nullexternref) (result nullexternref)))
18 (func $main
19 ref.null noextern
20 call 0
21 drop
22 )
23 (start $main)
24 )
25 "#,
26 )?;
27
28 let mut store = Store::new(&engine, ());
29
30 static HITS: AtomicU32 = AtomicU32::new(0);
31
32 let f = Func::wrap(&mut store, |x: Option<NoExtern>| -> Option<NoExtern> {
33 assert!(x.is_none());
34 HITS.fetch_add(1, Ordering::SeqCst);
35 x
36 });
37
38 let _ = Instance::new(&mut store, &module, &[f.into()])?;
39 assert_eq!(HITS.load(Ordering::SeqCst), 1);
40
41 Ok(())
42 }
43
44 #[test]
45 #[cfg_attr(miri, ignore)]
func_typed_no_extern() -> Result<()>46 fn func_typed_no_extern() -> Result<()> {
47 let mut config = Config::default();
48 config.wasm_function_references(true);
49 config.wasm_gc(true);
50
51 let engine = Engine::new(&config)?;
52
53 let module = Module::new(
54 &engine,
55 r#"
56 (module
57 (func (export "f") (param nullexternref) (result nullexternref)
58 local.get 0
59 )
60 )
61 "#,
62 )?;
63
64 let mut store = Store::new(&engine, ());
65 let instance = Instance::new(&mut store, &module, &[])?;
66 let f = instance.get_typed_func::<Option<NoExtern>, Option<NoExtern>>(&mut store, "f")?;
67 let result = f.call(&mut store, None)?;
68 assert!(result.is_none());
69
70 Ok(())
71 }
72