Is there any way to pass C# object references (class types, not structs) into and out of C++ via native interop?
Here's my use case:
I'm trying to write a game engine in C# but want to use a native (C++) physics library. The physics library maintains its own internal state of all the physical bodies and lets the user associate a small amount of data (a pointer) with each body. After a physics simulation tick, the library supplies a list of all physical bodies that moved. I want to iterate over this list and relay all the changes to the corresponding C# objects.
The question is: what's the best way to associate objects in C# with the corresponding physical bodies in C++?
I can think of a couple ways:
Is there any mechanism like option 3 I don't know of? C++/CLI isn't an option since I want to support platforms without it.
I would suggest using the tool that was specifically designed for situations like that, ie System.Runtime.InteropServices.GCHandle
.
Usage
In:
GCHandle
for your CLR object with GCHandleType.Normal
or GCHandleType.Weak
. GCHandle
to an IntPtr
via GCHandle.ToIntPtr
. IntPtr
to the C++ side as the userdata pointer that you mentioned. Out:
IntPtr
back from the C++ side. IntPtr
back to a GCHandle
via GCHandle.FromIntPtr
Target
Property of the GCHandle
to get to the original CLR object. When the CLR object is no longer being referenced from the C++ side (either because the C++ object was destroyed or because you reset the userdata pointer to eg IntPtr.Zero
), release the GCHandle
by calling GCHandle.Free
.
What type of GCHandle
you should allocate depends on whether you want the GCHandle
to keep the object alive ( GCHandleType.Normal
) or not ( GCHandleType.Weak
).
Marshal.GetFunctionPointerForDelegate
to get an address to pass to the unmanaged side. The only thing to note is that you have to make sure that the callback is using __stdcall
. Also, remember that AccessViolationException
s are generally not catchable in .NET.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.