将wasm运行时嵌入到独立的Rust应用程序中,并允许wasm和host函数相互调用



是否可以像下面这样编写一个独立的Rust应用程序,将其编译为两个部分,一个是wasm,另一个是本机,并将wasm运行时(如wasmtime(嵌入到最终的二进制文件中,整个部分就像一个应用程序一样工作?

WasmEdge有一个标记wasm函数的宏#[wasmedge_bindgen],但没有任何内容可以使宿主函数在wasm运行时访问。

#[make_a_wasm_func]
fn f1(i: i32)->i32{
i+1
}

#[make_a_host_func_that_can_be_called_from_wasm]
fn f2(i: i32)->i32{
f1(i)+2
} 
#[make_a_wasm_func]
fn f3(i:i32)-> i32{
f2(i)+3
}
fn main(){
let r=f3(1);
println!("{}",r);   
}
The expected output is 7.

WasmEdge的维护人员。希望以下示例代码可以帮助您:

use wasmedge_sdk::{
error::HostFuncError, host_function, params, Caller, ImportObjectBuilder, ValType, Vm, WasmVal,
WasmValue,
};
#[host_function]
fn my_add(_caller: Caller, input: Vec<WasmValue>) -> Result<Vec<WasmValue>, HostFuncError> {
// check the number of inputs
if input.len() != 2 {
return Err(HostFuncError::User(1));
}
// parse the first input of WebAssembly value type into Rust built-in value type
let a = if input[0].ty() == ValType::I32 {
input[0].to_i32()
} else {
return Err(HostFuncError::User(2));
};
// parse the second input of WebAssembly value type into Rust built-in value type
let b = if input[1].ty() == ValType::I32 {
input[1].to_i32()
} else {
return Err(HostFuncError::User(3));
};
let c = a + b;
Ok(vec![WasmValue::from_i32(c)])
}
fn main() -> Result<(), Box<dyn std::error::Error>> {
// create an import module
let import = ImportObjectBuilder::new()
.with_func::<(i32, i32), i32>("add", my_add)?
.build("extern")?;
// create a new vm with default config and register the import module into the vm.
let res = Vm::new(None)?.register_import_module(import)?.run_func(
Some("extern"),
"add",
params!(15, 51),
)?;
println!("add({}, {}) = {}", 15, 51, res[0].to_i32());
Ok(())
}

此外,在Cargo.toml中添加以下依赖项:

[dependencies]
wasmedge-sdk = "0.7.1"

最新更新