我想生成一个字节向量(Rust中的Vec< u8>)并使用JS作为Array或Uint8Array访问它,并将其发送到WebSocket或IndexedDB.
我找到了How can I pass an array from JavaScript to Rust that has been compiled with Emscripten?,这与我想做的完全相反,但非常相关.除此之外,我知道Emscripten中的数组类型,但我不知道如何正确使用它.
我对如何使其工作的最佳猜测是尝试返回向量as_mut_ptr,并使用Module.HEAPU8上的指针.
main.rs
#[no_mangle]
pub fn bytes() -> *mut u8 {
vec![1, 2, 3].as_mut_ptr()
}
fn main() {}
index.html的一部分
var Module = {
wasmBinaryFile: "site.wasm",
onRuntimeInitialized: main,
};
function main() {
let ptr = Module._bytes();
console.log(ptr);
console.log(Module.HEAPU8.slice(ptr, ptr + 10));
console.log(Module.HEAPU8.subarray(ptr, ptr + 100));
let arr = Module.cwrap('bytes', 'array', []);
console.log(arr());
}
控制台的结果最终看起来像这样:
5260296 site:11:13
Uint8Array [ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ] site:12:13
Uint8Array [ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 90 more… ] site:13:13
5260296 site:15:13
第一个问题是两个值都表示空数组,其次两个单独的调用指向相同的内存位置.我完全不知道如何访问堆上指向的数据,以及向量的长度.
指向相同存储器位置的两个指针可能是因为Rust掉落了Vec< u8>.在它的生命周期结束时写入(字节结束)函数.
对不起,如果我错过了一些Wasm和Emscripten的基础知识,我今天只建立了我的第一个Wasm hello world.
最佳答案 与编写Rust相同的规则适用于此处.这意味着该函数必须返回一个拥有的值;当前它返回一个指向函数返回时丢弃的数据的指针.
一个人将返回Vec< u8>它包括(ptr,长度,容量)并且太大而无法返回C.
有两种类似的解决方案:
> return Box< Vec< u8>>并定义另一个提取的函数
它的指针.
>定义您可以从C访问的自己的Vec.
我使用后者here.