I have a native library which passes hardware data to managed code via callbacks.
The basic native-to-managed plumbing is done by
[DllImport("Library.dll")]
public static extern bool Init(IntPtr dataCallBack)
[UnmanagedFunctionPointer(CallingConvention.StdCall)]
public delegate void Data(string data);
...
var handler = Marshal.GetFunctionPointerForDelegate(HandleData);
Init(handler);
...
private static void HandleData(string data)
{
//use data
}
The above works just fine.
However, because HandleData can be called hundreds or even thousands of times a second (depending on the exact hardware module) and the data string can also be quite long, it creates a noticeable pressure on the GC.
I would like to avoid the creation of all those strings and instead receive the data as char[] or even byte[] as I just need to extract a few fields.
I tried to substitute 'string' with StringBuilder or char[] but that didn't work.
Additional information:
- The native library passes the data as char * (null terminated string)
- The memory is allocated and released by the native code
- .NET version: 4.5
I would appreciate your help.
Thank you!
Have you tried changing callback signature like this?
[UnmanagedFunctionPointer(CallingConvention.StdCall)]
public delegate void Data(IntPtr data);
private unsafe static void HandleData(IntPtr data)
{
byte* charPtr = (byte*)data;
// work with bytes here (which are single-byte chars).
}
Here you need to be cautios and check for null character manually.