ore*_*oli 5 scripting types communication rust webassembly
我正在开发一个 Rust 程序,我想在运行时使用 WebAssembly 作为脚本语言来驱动其行为。我们假设脚本也是用 Rust 编写的。我读过 Wasmer、Wasmtime 和 Lucet 的教程,虽然导出/导入的函数可以作为参数并返回 WASM 原始类型,但似乎没有简单/无痛的解决方案可以在 Rust 二进制文件和 WASM 脚本之间传递任意数据在其中运行。特别是,必须通过手动传递原语作为指向运行时线性内存和长度的指针来处理字符串。
wasm-bindgen看起来它能够解决我的问题,但它只针对浏览器中的 WASM-JS 通信。有*-interface-typesWasmer 和 Wasmtime 的板条箱,但它们没有教程,并且是实验性的,可能会发生变化。我不需要通过structs,但我想实现这样的目标:
// in the host program
let argument: &[u8] = &[0, 1... n]; // dumb byte slice
let guest_result: Vec<u8> = wasm_runtime.call("guest_function", &[argument]);
// in the guest WASM library/script
let data_from_host: Vec<u8> = imported_function(some_other_bytes);
Run Code Online (Sandbox Code Playgroud)
只需双向传递和返回Vec<u8>s 或&[u8]s 就足够了,我可以用bincode或 其他方式反序列化它们。有人实现了吗?我可以像字符串一样共享线性内存,但这似乎不安全,特别是对于多个线程上的多个脚本。
&[u8]tl;dr 我想使用 WASM 作为脚本语言并使用或与之交谈Vec<u8>,但还没有找到任何简单的方法来做到这一点。
这个可用性问题是已知的,并且似乎正在积极解决:https://hacks.mozilla.org/2019/08/web assembly -interface-types/
以下是该文章中一些结束语的后续内容:https://github.com/bytecodealliance/wasmtime/issues/677
我编写 C 语言或处理系统调用接口的经验很少,因此传递值对我来说也很麻烦。在大多数情况下,我只是投入时间来构建更高级别的抽象(就像 wasm-bindgen 所做的那样),以便我可以更轻松地传递数据。
例如,看起来 wasi 提供了一个可以实现的接口,并且它们抽象了所有繁琐的部分:https ://docs.rs/crate/wasi/0.9.0+wasi-snapshot-preview1/source/src/ lib_ generated.rs你可以在这里看到 lucet 实现它:https://github.com/bytecodealliance/lucet/blob/master/lucet-wasi/src/runtime.rs
我认为除非您尝试实现 wasi,否则这不会对您有太大帮助,但它是实现您想要的抽象类型的一个很好的例子。