Hello,
I am running into a problem when calling a (not typed) function: "expected 1 results, got 0". If I set the function as typed (arg i32 and result i32, i.e. <i32, i32>
) the function call works fine, the problem only happens if it's not typed.
This is how I am calling it:
let mut results = Vec::new();
func.call(&mut *self.store(), args, &mut results)
.map_err(|e| eyre!(r#"failed to call func "{fn_name}": {e}"#))?;
Is this a common error? I couldn't find any references to it.
Huh. So I looked into the implementation and it compares the expected vs actual length of results
.
Why is that? So this returns a i32 pointer, so I need to initialise the results as 0:
let mut results = [Val::I32(0)];
Not very intuitive API IMO. I assumed it would just fill an empty buffer with the results.
Looks like you ended up finding the answer, but to confirm yes the results
vector here needed to have an element in it to have the same length as the results.
As to the unintuitive nature of the API, the signature of the function actually takes &mut [Val]
which is not a resizable array so it's not possible to fill an empty Vec
with results. What you're running into is that Rust is coercing &mut Vec<T>
into &mut [T]
which in this case is an empty vector. That's combining together to create this situation.
One thing we could consider in Wasmtime is to have a function that doesn't take a results buffer at all and insteads returns a Vec<T>
, but that has efficiency concerns since it requires reallocating a vector every time it's called. API design is quite difficult!
Thanks for the reply, that makes sense. Overall I'm happy with wasmtime. I had to move over from wasmer because I needed async support on host functions :grinning_face_with_smiling_eyes:
Last updated: Dec 23 2024 at 13:07 UTC