xref: /wasmtime-44.0.1/crates/c-api/src/module.rs (revision cca558cd)
1 use crate::{
2     handle_result, wasm_byte_vec_t, wasm_exporttype_t, wasm_exporttype_vec_t, wasm_importtype_t,
3     wasm_importtype_vec_t, wasm_store_t, wasmtime_error_t,
4 };
5 use std::ptr;
6 use wasmtime::{Engine, Module};
7 
8 #[repr(C)]
9 #[derive(Clone)]
10 pub struct wasm_module_t {
11     pub(crate) module: Module,
12     pub(crate) imports: Vec<wasm_importtype_t>,
13     pub(crate) exports: Vec<wasm_exporttype_t>,
14 }
15 
16 wasmtime_c_api_macros::declare_ref!(wasm_module_t);
17 
18 #[repr(C)]
19 #[derive(Clone)]
20 pub struct wasm_shared_module_t {
21     module: Module,
22 }
23 
24 wasmtime_c_api_macros::declare_own!(wasm_shared_module_t);
25 
26 #[no_mangle]
27 pub extern "C" fn wasm_module_new(
28     store: &wasm_store_t,
29     binary: &wasm_byte_vec_t,
30 ) -> Option<Box<wasm_module_t>> {
31     let mut ret = ptr::null_mut();
32     match wasmtime_module_new(store, binary, &mut ret) {
33         Some(_err) => None,
34         None => {
35             assert!(!ret.is_null());
36             Some(unsafe { Box::from_raw(ret) })
37         }
38     }
39 }
40 
41 #[no_mangle]
42 pub extern "C" fn wasmtime_module_new(
43     store: &wasm_store_t,
44     binary: &wasm_byte_vec_t,
45     ret: &mut *mut wasm_module_t,
46 ) -> Option<Box<wasmtime_error_t>> {
47     let binary = binary.as_slice();
48     let store = &store.store;
49     handle_result(Module::from_binary(store.engine(), binary), |module| {
50         let imports = module
51             .imports()
52             .map(|i| wasm_importtype_t::new(i.module().to_owned(), i.name().to_owned(), i.ty()))
53             .collect::<Vec<_>>();
54         let exports = module
55             .exports()
56             .map(|e| wasm_exporttype_t::new(e.name().to_owned(), e.ty()))
57             .collect::<Vec<_>>();
58         let module = Box::new(wasm_module_t {
59             module: module,
60             imports,
61             exports,
62         });
63         *ret = Box::into_raw(module);
64     })
65 }
66 
67 #[no_mangle]
68 pub extern "C" fn wasm_module_validate(store: &wasm_store_t, binary: &wasm_byte_vec_t) -> bool {
69     wasmtime_module_validate(store, binary).is_none()
70 }
71 
72 #[no_mangle]
73 pub extern "C" fn wasmtime_module_validate(
74     store: &wasm_store_t,
75     binary: &wasm_byte_vec_t,
76 ) -> Option<Box<wasmtime_error_t>> {
77     let binary = binary.as_slice();
78     handle_result(Module::validate(store.store.engine(), binary), |()| {})
79 }
80 
81 #[no_mangle]
82 pub extern "C" fn wasm_module_exports(module: &wasm_module_t, out: &mut wasm_exporttype_vec_t) {
83     let buffer = module
84         .exports
85         .iter()
86         .map(|et| Some(Box::new(et.clone())))
87         .collect::<Vec<_>>();
88     out.set_buffer(buffer);
89 }
90 
91 #[no_mangle]
92 pub extern "C" fn wasm_module_imports(module: &wasm_module_t, out: &mut wasm_importtype_vec_t) {
93     let buffer = module
94         .imports
95         .iter()
96         .map(|it| Some(Box::new(it.clone())))
97         .collect::<Vec<_>>();
98     out.set_buffer(buffer);
99 }
100 
101 #[no_mangle]
102 pub extern "C" fn wasm_module_share(module: &wasm_module_t) -> Box<wasm_shared_module_t> {
103     Box::new(wasm_shared_module_t {
104         module: module.module.clone(),
105     })
106 }
107 
108 #[no_mangle]
109 pub extern "C" fn wasm_module_obtain(
110     store: &wasm_store_t,
111     shared_module: &wasm_shared_module_t,
112 ) -> Option<Box<wasm_module_t>> {
113     let module = shared_module.module.clone();
114     if !Engine::same(store.store.engine(), module.engine()) {
115         return None;
116     }
117     let imports = module
118         .imports()
119         .map(|i| wasm_importtype_t::new(i.module().to_owned(), i.name().to_owned(), i.ty()))
120         .collect::<Vec<_>>();
121     let exports = module
122         .exports()
123         .map(|e| wasm_exporttype_t::new(e.name().to_owned(), e.ty()))
124         .collect::<Vec<_>>();
125     Some(Box::new(wasm_module_t {
126         module: module,
127         imports,
128         exports,
129     }))
130 }
131