C++ platform: Fix ambiguous call to "call" (#303)

* chg: add void/non-void test functions

* fix: fix ambiguous call method, add more examples

* chg: add newline

* fix: indentation

* docs: added call() examples / fixed desc.
opam-2.0.0
Stuff is on GitLab 2 years ago committed by GitHub
parent c101549795
commit dc9fa49340
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

@ -52,9 +52,30 @@ If the module doesn't reference an imported function named `func`, an exception
`function` object can be obtained from a `runtime`, looking up the function by name. Function objects are used to call WebAssembly functions.
`template <typename Ret> Ret function::call()` — call a WebAssembly function which doesn't take any arguments. The return value of the function is automatically converted to the type `Ret`. Note that you need to specify the return type when using this template function, and the type has to match the type returned by the WebAssembly function.
`template <typename Ret = void, typename ...Args> Ret function::call(Args...)` — calls a WebAssembly function with or without arguments and a return value.<br>
The return value of the function, if not `void`, is automatically converted to the type `Ret`.<br>
Note that you always need to specify the matching return type when using this template with a non-void function.<br>
Examples:
```cpp
// WASM signature: [] → []
func.call();
`template <typename Ret, typename ...Args> Ret function::call(Args...)` — same as above, but also allows passing arguments to the WebAssembly function.
// WASM signature: [i32, i32] → []
func.call(42, 43); // implicit argument types
// WASM signature: [i32, i64] → []
func.call<void, int32_t, int64_t>(42, 43); // explicit argument types require the return type
// WASM signature: [] → [i32]
auto result = func.call<int32_t>();
// WASM signature: [i32, i32] → [i64]
auto result = func.call<int64_t>(42, 43); // implicit argument types
// WASM signature: [i32, i64] → [i64]
auto result = func.call<int64_t, int32_t, int64_t>(42, 43); // explicit argument types
```
`template <typename Ret, typename ...Args> Ret function::call_argv(Args...)` — same as above, except that this function takes arguments as C strings (`const char*`).

@ -56,6 +56,29 @@ int main(void)
auto res = memcpy_test_fn.call<int64_t>();
std::cout << "result: 0x" << std::hex << res << std::dec << std::endl;
}
/**
* Calling functions that modify an internal state, with mixed argument / return types
*/
{
wasm3::function counter_get_fn = runtime.find_function("test_counter_get");
wasm3::function counter_inc_fn = runtime.find_function("test_counter_inc");
wasm3::function counter_add_fn = runtime.find_function("test_counter_add");
// call with no arguments and a return value
auto value = counter_get_fn.call<int32_t>();
std::cout << "counter: " << value << std::endl;
// call with no arguments and no return value
counter_inc_fn.call();
value = counter_get_fn.call<int32_t>();
std::cout << "counter after increment: " << value << std::endl;
// call with one argument and no return value
counter_add_fn.call(42);
value = counter_get_fn.call<int32_t>();
std::cout << "counter after adding value: " << value << std::endl;
}
}
catch(wasm3::error &e) {
std::cerr << "WASM3 error: " << e.what() << std::endl;

@ -4,6 +4,8 @@
extern int sum(int, int);
extern int ext_memcpy(void*, const void*, size_t);
int32_t counter = 0;
#define WASM_EXPORT __attribute__((used)) __attribute__((visibility ("default")))
int WASM_EXPORT test(int32_t arg1, int32_t arg2)
@ -22,3 +24,18 @@ int64_t WASM_EXPORT test_memcpy(void)
ext_memcpy(((uint8_t*)&x) + 4, &high, 4);
return x;
}
int32_t WASM_EXPORT test_counter_get()
{
return counter;
}
void WASM_EXPORT test_counter_inc()
{
++counter;
}
void WASM_EXPORT test_counter_add(int32_t inc_value)
{
counter += inc_value;
}

Binary file not shown.

@ -1,25 +1,68 @@
unsigned char test_prog_wasm[] = {
0x00, 0x61, 0x73, 0x6d, 0x01, 0x00, 0x00, 0x00, 0x01, 0x15, 0x04, 0x60,
0x02, 0x7f, 0x7f, 0x01, 0x7f, 0x60, 0x00, 0x00, 0x60, 0x03, 0x7f, 0x7f,
0x7f, 0x01, 0x7f, 0x60, 0x00, 0x01, 0x7e, 0x02, 0x1c, 0x02, 0x03, 0x65,
0x00, 0x61, 0x73, 0x6d, 0x01, 0x00, 0x00, 0x00, 0x01, 0x22, 0x07, 0x60,
0x02, 0x7f, 0x7f, 0x01, 0x7f, 0x60, 0x01, 0x7f, 0x00, 0x60, 0x00, 0x00,
0x60, 0x00, 0x01, 0x7f, 0x60, 0x03, 0x7f, 0x7f, 0x7f, 0x01, 0x7f, 0x60,
0x00, 0x01, 0x7e, 0x60, 0x01, 0x7f, 0x01, 0x7f, 0x02, 0x94, 0x01, 0x06,
0x03, 0x65, 0x6e, 0x76, 0x03, 0x73, 0x75, 0x6d, 0x00, 0x00, 0x03, 0x65,
0x6e, 0x76, 0x0a, 0x65, 0x78, 0x74, 0x5f, 0x6d, 0x65, 0x6d, 0x63, 0x70,
0x79, 0x00, 0x02, 0x03, 0x65, 0x6e, 0x76, 0x03, 0x73, 0x75, 0x6d, 0x00,
0x00, 0x03, 0x04, 0x03, 0x01, 0x03, 0x00, 0x05, 0x06, 0x01, 0x01, 0x80,
0x02, 0x80, 0x02, 0x06, 0x09, 0x01, 0x7f, 0x01, 0x41, 0x80, 0x8c, 0xc0,
0x02, 0x0b, 0x07, 0x28, 0x04, 0x06, 0x6d, 0x65, 0x6d, 0x6f, 0x72, 0x79,
0x02, 0x00, 0x04, 0x74, 0x65, 0x73, 0x74, 0x00, 0x04, 0x0b, 0x74, 0x65,
0x73, 0x74, 0x5f, 0x6d, 0x65, 0x6d, 0x63, 0x70, 0x79, 0x00, 0x03, 0x06,
0x5f, 0x73, 0x74, 0x61, 0x72, 0x74, 0x00, 0x02, 0x0a, 0x71, 0x03, 0x03,
0x00, 0x01, 0x0b, 0x59, 0x02, 0x01, 0x7f, 0x01, 0x7e, 0x23, 0x00, 0x41,
0x10, 0x6b, 0x22, 0x00, 0x24, 0x00, 0x20, 0x00, 0x42, 0x00, 0x37, 0x03,
0x08, 0x20, 0x00, 0x41, 0xe7, 0x8a, 0x8d, 0x09, 0x36, 0x02, 0x04, 0x20,
0x00, 0x41, 0xef, 0x9b, 0xaf, 0xcd, 0x78, 0x36, 0x02, 0x00, 0x20, 0x00,
0x41, 0x08, 0x6a, 0x20, 0x00, 0x41, 0x04, 0x6a, 0x41, 0x04, 0x10, 0x00,
0x1a, 0x20, 0x00, 0x41, 0x08, 0x6a, 0x41, 0x04, 0x72, 0x20, 0x00, 0x41,
0x04, 0x10, 0x00, 0x1a, 0x20, 0x00, 0x29, 0x03, 0x08, 0x21, 0x01, 0x20,
0x00, 0x41, 0x10, 0x6a, 0x24, 0x00, 0x20, 0x01, 0x0b, 0x11, 0x00, 0x20,
0x00, 0x20, 0x01, 0x6a, 0x20, 0x00, 0x20, 0x01, 0x6b, 0x10, 0x01, 0x41,
0x02, 0x6d, 0x0b, 0x0b, 0x0a, 0x01, 0x00, 0x41, 0x80, 0x0c, 0x0b, 0x03,
0xa0, 0x06, 0x50
0x79, 0x00, 0x04, 0x16, 0x77, 0x61, 0x73, 0x69, 0x5f, 0x73, 0x6e, 0x61,
0x70, 0x73, 0x68, 0x6f, 0x74, 0x5f, 0x70, 0x72, 0x65, 0x76, 0x69, 0x65,
0x77, 0x31, 0x0e, 0x61, 0x72, 0x67, 0x73, 0x5f, 0x73, 0x69, 0x7a, 0x65,
0x73, 0x5f, 0x67, 0x65, 0x74, 0x00, 0x00, 0x16, 0x77, 0x61, 0x73, 0x69,
0x5f, 0x73, 0x6e, 0x61, 0x70, 0x73, 0x68, 0x6f, 0x74, 0x5f, 0x70, 0x72,
0x65, 0x76, 0x69, 0x65, 0x77, 0x31, 0x08, 0x61, 0x72, 0x67, 0x73, 0x5f,
0x67, 0x65, 0x74, 0x00, 0x00, 0x03, 0x65, 0x6e, 0x76, 0x04, 0x6d, 0x61,
0x69, 0x6e, 0x00, 0x00, 0x16, 0x77, 0x61, 0x73, 0x69, 0x5f, 0x73, 0x6e,
0x61, 0x70, 0x73, 0x68, 0x6f, 0x74, 0x5f, 0x70, 0x72, 0x65, 0x76, 0x69,
0x65, 0x77, 0x31, 0x09, 0x70, 0x72, 0x6f, 0x63, 0x5f, 0x65, 0x78, 0x69,
0x74, 0x00, 0x01, 0x03, 0x0c, 0x0b, 0x02, 0x00, 0x05, 0x03, 0x02, 0x01,
0x02, 0x03, 0x01, 0x06, 0x03, 0x04, 0x05, 0x01, 0x70, 0x01, 0x02, 0x02,
0x05, 0x06, 0x01, 0x01, 0x80, 0x02, 0x80, 0x02, 0x06, 0x09, 0x01, 0x7f,
0x01, 0x41, 0x90, 0x88, 0xc0, 0x02, 0x0b, 0x07, 0xb8, 0x01, 0x0c, 0x06,
0x6d, 0x65, 0x6d, 0x6f, 0x72, 0x79, 0x02, 0x00, 0x04, 0x74, 0x65, 0x73,
0x74, 0x00, 0x07, 0x0b, 0x74, 0x65, 0x73, 0x74, 0x5f, 0x6d, 0x65, 0x6d,
0x63, 0x70, 0x79, 0x00, 0x08, 0x10, 0x74, 0x65, 0x73, 0x74, 0x5f, 0x63,
0x6f, 0x75, 0x6e, 0x74, 0x65, 0x72, 0x5f, 0x67, 0x65, 0x74, 0x00, 0x09,
0x10, 0x74, 0x65, 0x73, 0x74, 0x5f, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x65,
0x72, 0x5f, 0x69, 0x6e, 0x63, 0x00, 0x0a, 0x10, 0x74, 0x65, 0x73, 0x74,
0x5f, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x65, 0x72, 0x5f, 0x61, 0x64, 0x64,
0x00, 0x0b, 0x19, 0x5f, 0x5f, 0x69, 0x6e, 0x64, 0x69, 0x72, 0x65, 0x63,
0x74, 0x5f, 0x66, 0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x5f, 0x74,
0x61, 0x62, 0x6c, 0x65, 0x01, 0x00, 0x06, 0x5f, 0x73, 0x74, 0x61, 0x72,
0x74, 0x00, 0x0c, 0x10, 0x5f, 0x5f, 0x65, 0x72, 0x72, 0x6e, 0x6f, 0x5f,
0x6c, 0x6f, 0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x00, 0x10, 0x09, 0x73,
0x74, 0x61, 0x63, 0x6b, 0x53, 0x61, 0x76, 0x65, 0x00, 0x0d, 0x0c, 0x73,
0x74, 0x61, 0x63, 0x6b, 0x52, 0x65, 0x73, 0x74, 0x6f, 0x72, 0x65, 0x00,
0x0e, 0x0a, 0x73, 0x74, 0x61, 0x63, 0x6b, 0x41, 0x6c, 0x6c, 0x6f, 0x63,
0x00, 0x0f, 0x09, 0x07, 0x01, 0x00, 0x41, 0x01, 0x0b, 0x01, 0x06, 0x0a,
0xd1, 0x02, 0x0b, 0x03, 0x00, 0x01, 0x0b, 0x11, 0x00, 0x20, 0x00, 0x20,
0x01, 0x6a, 0x20, 0x00, 0x20, 0x01, 0x6b, 0x10, 0x00, 0x41, 0x02, 0x6d,
0x0b, 0x58, 0x02, 0x02, 0x7f, 0x01, 0x7e, 0x23, 0x00, 0x41, 0x10, 0x6b,
0x22, 0x00, 0x24, 0x00, 0x20, 0x00, 0x42, 0x00, 0x37, 0x03, 0x08, 0x20,
0x00, 0x41, 0xe7, 0x8a, 0x8d, 0x09, 0x36, 0x02, 0x04, 0x20, 0x00, 0x41,
0xef, 0x9b, 0xaf, 0xcd, 0x78, 0x36, 0x02, 0x00, 0x20, 0x00, 0x41, 0x08,
0x6a, 0x22, 0x01, 0x20, 0x00, 0x41, 0x04, 0x6a, 0x41, 0x04, 0x10, 0x01,
0x1a, 0x20, 0x01, 0x41, 0x04, 0x72, 0x20, 0x00, 0x41, 0x04, 0x10, 0x01,
0x1a, 0x20, 0x00, 0x29, 0x03, 0x08, 0x21, 0x02, 0x20, 0x00, 0x41, 0x10,
0x6a, 0x24, 0x00, 0x20, 0x02, 0x0b, 0x08, 0x00, 0x41, 0x80, 0x08, 0x28,
0x02, 0x00, 0x0b, 0x11, 0x00, 0x41, 0x80, 0x08, 0x41, 0x80, 0x08, 0x28,
0x02, 0x00, 0x41, 0x01, 0x6a, 0x36, 0x02, 0x00, 0x0b, 0x11, 0x00, 0x41,
0x80, 0x08, 0x41, 0x80, 0x08, 0x28, 0x02, 0x00, 0x20, 0x00, 0x6a, 0x36,
0x02, 0x00, 0x0b, 0x8f, 0x01, 0x01, 0x04, 0x7f, 0x02, 0x7f, 0x23, 0x00,
0x41, 0x10, 0x6b, 0x22, 0x00, 0x24, 0x00, 0x02, 0x40, 0x20, 0x00, 0x22,
0x01, 0x41, 0x0c, 0x6a, 0x20, 0x00, 0x41, 0x08, 0x6a, 0x10, 0x02, 0x45,
0x04, 0x40, 0x20, 0x01, 0x28, 0x02, 0x0c, 0x22, 0x02, 0x04, 0x7f, 0x20,
0x00, 0x20, 0x02, 0x41, 0x02, 0x74, 0x22, 0x03, 0x41, 0x13, 0x6a, 0x41,
0x70, 0x71, 0x6b, 0x22, 0x00, 0x24, 0x00, 0x20, 0x00, 0x20, 0x01, 0x28,
0x02, 0x08, 0x41, 0x0f, 0x6a, 0x41, 0x70, 0x71, 0x6b, 0x22, 0x02, 0x24,
0x00, 0x20, 0x00, 0x20, 0x03, 0x6a, 0x41, 0x00, 0x36, 0x02, 0x00, 0x20,
0x00, 0x20, 0x02, 0x10, 0x03, 0x0d, 0x02, 0x20, 0x01, 0x28, 0x02, 0x0c,
0x05, 0x41, 0x00, 0x0b, 0x20, 0x00, 0x10, 0x04, 0x21, 0x00, 0x20, 0x01,
0x41, 0x10, 0x6a, 0x24, 0x00, 0x20, 0x00, 0x0c, 0x02, 0x0b, 0x41, 0xc7,
0x00, 0x10, 0x05, 0x00, 0x0b, 0x41, 0xc7, 0x00, 0x10, 0x05, 0x00, 0x0b,
0x10, 0x05, 0x00, 0x0b, 0x04, 0x00, 0x23, 0x00, 0x0b, 0x06, 0x00, 0x20,
0x00, 0x24, 0x00, 0x0b, 0x10, 0x00, 0x23, 0x00, 0x20, 0x00, 0x6b, 0x41,
0x70, 0x71, 0x22, 0x00, 0x24, 0x00, 0x20, 0x00, 0x0b, 0x05, 0x00, 0x41,
0x84, 0x08, 0x0b
};
unsigned int test_prog_wasm_len = 255;
unsigned int test_prog_wasm_len = 771;

@ -344,25 +344,21 @@ namespace wasm3 {
*
* Note that the type of the return value must be explicitly specified as a template argument.
*
* @return the return value of the function.
* @return the return value of the function or void.
*/
template<typename Ret, typename ... Args>
template<typename Ret = void, typename ... Args>
Ret call(Args... args) {
const void *arg_ptrs[] = { reinterpret_cast<const void*>(&args)... };
M3Result res = m3_Call(m_func, sizeof...(args), arg_ptrs);
detail::check_error(res);
Ret ret;
const void* ret_ptrs[] = { &ret };
res = m3_GetResults(m_func, 1, ret_ptrs);
detail::check_error(res);
return ret;
}
template<typename ... Args>
void call(Args... args) {
const void *arg_ptrs[] = { reinterpret_cast<const void*>(&args)... };
M3Result res = m3_Call(m_func, sizeof...(args), arg_ptrs);
detail::check_error(res);
if constexpr (!std::is_void<Ret>::value) {
Ret ret;
const void* ret_ptrs[] = { &ret };
res = m3_GetResults(m_func, 1, ret_ptrs);
detail::check_error(res);
return ret;
}
}
protected:

Loading…
Cancel
Save