Closed johannesvollmer closed 10 months ago
Actually, to pass an instance method or a closure, nothing needs to be changed. The C# marshaller knows how to create a working function pointer from a C# closure. But of course you need to keep alive a delegate of the correct type, which is M3RawCall
. For example, like this:
m3Module.LinkRawFunction(
"externals", "print_add", "i(ii)",
this.keepAliveM3FunctionPointer = new M3RawCall(MyClosureDelegate)
);
where MyClosureDelegate
can by a closure with state or a non-static method reference.
I apologize for not responding for more than one year.
Today I fixed the problem using approach you suggested (keep a delegate above by storing it) in commit 55c8ab0.
Excellent! I have had a workaround monkey-patched, but I'm glad that you are back :) because I have a few more fixes in my fork that I would be glad to discuss with you, and maybe feed back to your repo :)
I'll close this issue for now, as C# will manage the closures in my use case, which means I don't need LinkRawFunctionEx anymore.
If I am not mistaken, this function will be necessary for linking non-static C# functions, such as closures, correct? I have experimented a little bit, but could not make it work. This would be necessary to later add a function that automatically marshals all the arguments and return types between c# and wasm3.
My plan is as follows:
m3_LinkRawFunctionEx(..., void* userdata)
can be used to call functions with extra datapublic static extern string m3_LinkRawFunctionEx(...)
function mappingIM3ImportContext
type mappingIM3ImportContext
type mapping everywhere instead ofIntPtr
m3_LinkRawFunctionEx
with a pointer to a data structure that contains a closure objectM3RawCall
callback, when called, retrieve closure object from thectx->userdata
pointer inIM3ImportContext
Will this work? Is this a clean approach? I would like to contribute.