1 use wasmtime::Result; 2 use wasmtime::component::*; 3 use wasmtime::{Module, Store}; 4 5 #[test] 6 #[cfg_attr(miri, ignore)] 7 fn instance_exports() -> Result<()> { 8 let engine = super::engine(); 9 let component = r#" 10 (component 11 (import "a" (instance $i)) 12 (import "b" (instance $i2 (export "m" (core module)))) 13 14 (alias export $i2 "m" (core module $m)) 15 16 (component $c 17 (component $c 18 (export "m" (core module $m)) 19 ) 20 (instance $c (instantiate $c)) 21 (export "i" (instance $c)) 22 ) 23 (instance $c (instantiate $c)) 24 (export "i" (instance $c)) 25 (export "r" (instance $i)) 26 (export "r2" (instance $i2)) 27 ) 28 "#; 29 let component = Component::new(&engine, component)?; 30 let mut store = Store::new(&engine, ()); 31 let mut linker = Linker::new(&engine); 32 linker.instance("a")?; 33 linker 34 .instance("b")? 35 .module("m", &Module::new(&engine, "(module)")?)?; 36 let instance = linker.instantiate(&mut store, &component)?; 37 38 assert!( 39 instance 40 .get_export(&mut store, None, "not an instance") 41 .is_none() 42 ); 43 let i = instance.get_export_index(&mut store, None, "r").unwrap(); 44 assert!(instance.get_export(&mut store, Some(&i), "x").is_none()); 45 instance.get_export(&mut store, None, "i").unwrap(); 46 let i2 = instance.get_export_index(&mut store, None, "r2").unwrap(); 47 let m = instance 48 .get_export_index(&mut store, Some(&i2), "m") 49 .unwrap(); 50 assert!(instance.get_func(&mut store, &m).is_none()); 51 assert!(instance.get_module(&mut store, &m).is_some()); 52 53 let i = instance.get_export_index(&mut store, None, "i").unwrap(); 54 let i = instance 55 .get_export_index(&mut store, Some(&i), "i") 56 .unwrap(); 57 let m = instance 58 .get_export_index(&mut store, Some(&i), "m") 59 .unwrap(); 60 instance.get_module(&mut store, &m).unwrap(); 61 62 Ok(()) 63 } 64 65 #[test] 66 fn export_old_get_new() -> Result<()> { 67 let engine = super::engine(); 68 let component = r#" 69 (component 70 (core module $m) 71 (export "a:b/[email protected]" (core module $m)) 72 73 (instance $i (export "m" (core module $m))) 74 (export "a:b/[email protected]" (instance $i)) 75 ) 76 "#; 77 78 let component = Component::new(&engine, component)?; 79 component.get_export(None, "a:b/[email protected]").unwrap(); 80 let i = component.get_export_index(None, "a:b/[email protected]").unwrap(); 81 component.get_export(Some(&i), "m").unwrap(); 82 83 let mut store = Store::new(&engine, ()); 84 let linker = Linker::new(&engine); 85 let instance = linker.instantiate(&mut store, &component)?; 86 87 instance.get_module(&mut store, "a:b/[email protected]").unwrap(); 88 instance 89 .get_export(&mut store, None, "a:b/[email protected]") 90 .unwrap(); 91 92 let i = instance 93 .get_export_index(&mut store, None, "a:b/[email protected]") 94 .unwrap(); 95 instance.get_export(&mut store, Some(&i), "m").unwrap(); 96 97 Ok(()) 98 } 99 100 #[test] 101 fn export_new_get_old() -> Result<()> { 102 let engine = super::engine(); 103 let component = r#" 104 (component 105 (core module $m) 106 (export "a:b/[email protected]" (core module $m)) 107 108 (instance $i (export "m" (core module $m))) 109 (export "a:b/[email protected]" (instance $i)) 110 ) 111 "#; 112 113 let component = Component::new(&engine, component)?; 114 component.get_export(None, "a:b/[email protected]").unwrap(); 115 let i = component.get_export_index(None, "a:b/[email protected]").unwrap(); 116 component.get_export(Some(&i), "m").unwrap(); 117 118 let mut store = Store::new(&engine, ()); 119 let linker = Linker::new(&engine); 120 let instance = linker.instantiate(&mut store, &component)?; 121 122 instance.get_module(&mut store, "a:b/[email protected]").unwrap(); 123 instance 124 .get_export(&mut store, None, "a:b/[email protected]") 125 .unwrap(); 126 127 let i = instance 128 .get_export_index(&mut store, None, "a:b/[email protected]") 129 .unwrap(); 130 instance.get_export(&mut store, Some(&i), "m").unwrap(); 131 132 Ok(()) 133 } 134 135 #[test] 136 #[cfg_attr(miri, ignore)] 137 fn export_missing_get_max() -> Result<()> { 138 let engine = super::engine(); 139 let component = r#" 140 (component 141 (core module $m1) 142 (core module $m2 (import "" "" (func))) 143 (export "a:b/[email protected]" (core module $m1)) 144 (export "a:b/[email protected]" (core module $m2)) 145 ) 146 "#; 147 148 fn assert_m2(module: &Module) { 149 assert_eq!(module.imports().len(), 1); 150 } 151 fn assert_m1(module: &Module) { 152 assert_eq!(module.imports().len(), 0); 153 } 154 155 let component = Component::new(&engine, component)?; 156 let mut store = Store::new(&engine, ()); 157 let instance = Linker::new(&engine).instantiate(&mut store, &component)?; 158 159 let tests = [ 160 ("a:b/[email protected]", assert_m2 as fn(&_)), // no exact, should pick max available 161 ("a:b/[email protected]", assert_m1), // exact hit 162 ("a:b/[email protected]", assert_m2), // no exact, should pick max available 163 ("a:b/[email protected]", assert_m2), // exact hit 164 ("a:b/[email protected]", assert_m2), // no exact, should pick max available 165 ]; 166 167 for (name, test_fn) in tests { 168 println!("test {name}"); 169 let m = component.get_export_index(None, name).unwrap(); 170 let m = instance.get_module(&mut store, &m).unwrap(); 171 test_fn(&m); 172 173 let m = instance.get_module(&mut store, name).unwrap(); 174 test_fn(&m); 175 176 let m = instance.get_export_index(&mut store, None, name).unwrap(); 177 let m = instance.get_module(&mut store, &m).unwrap(); 178 test_fn(&m); 179 } 180 181 Ok(()) 182 } 183