I'm trying to export a function so that it can be used from the native unmanaged world. In my case this would be a Delphi application.
I'm using [UnmanagedCallersOnly]
keyword to export the functions. And I use DNNE
(https://github.com/AaronRobinsonMSFT/DNNE) to generate the appropriate wrapper file.
Returning a string from a function is as simple as
[UnmanagedCallersOnly]
public static IntPtr Foo()
{
return Marshal.StringToBSTR("hello from c#");
}
But I also need to return "complex" structures. So I created a struct
public struct ReturnTest
{
public int code;
public IntPtr txt;
}
and use this in my function
[UnmanagedCallersOnly]
public static ReturnTest TestFunction()
{
ReturnTest returnTest = new ReturnTest();
returnTest.code = 1337;
returnTest.txt = Marshal.StringToBSTR("a b c d q ¥ K xyz");
return returnTest;
}
But during the compiling it errors out:
The command ""C:\Program Files\Microsoft Visual Studio\2022\Professional\VC\Tools\MSVC\14.42.34433\bin\Hostx64\x64\cl.exe" /Od /LDd /TC /MT /GS /Zi /D DNNE_ASSEMBLY_NAME=UnmanagedCallersOnlyStructReturn /D DNNE_COMPILE_AS_SOURCE /I "C:\Program Files\Microsoft Visual Studio\2022\Professional\VC\Tools\MSVC\14.42.34433\include" /I "C:\Users\XXXX\.nuget\packages\dnne\2.0.7\tools\platform" /I "C:\Program Files\dotnet\packs\Microsoft.NETCore.App.Host.win-x64\9.0.1\runtimes\win-x64\native" /I "C:\Program Files (x86)\Windows Kits\10\Include\10.0.22621.0\shared" /I "C:\Program Files (x86)\Windows Kits\10\Include\10.0.22621.0\um" /I "C:\Program Files (x86)\Windows Kits\10\Include\10.0.22621.0\ucrt" "C:\git\stackoverflow\UnmanagedCallersOnlyStructReturn\obj\Debug\net8.0-windows7.0\dnne\UnmanagedCallersOnlyStructReturn.g.c" "C:\Users\XXXX\.nuget\packages\dnne\2.0.7\tools\platform\platform.c" /link /DLL /LIBPATH:"C:\Program Files\Microsoft Visual Studio\2022\Professional\VC\Tools\MSVC\14.42.34433\lib\x64" /LIBPATH:"C:\Program Files (x86)\Windows Kits\10\Lib\10.0.22621.0\um\x64" /LIBPATH:"C:\Program Files (x86)\Windows Kits\10\Lib\10.0.22621.0\ucrt\x64" "C:\Program Files\dotnet\packs\Microsoft.NETCore.App.Host.win-x64\9.0.1\runtimes\win-x64\native\libnethost.lib" Advapi32.lib /IGNORE:4099 /IMPLIB:"C:\git\stackoverflow\UnmanagedCallersOnlyStructReturn\obj\Debug\net8.0-windows7.0\dnne\bin\UnmanagedCallersOnlyStructReturnNE.lib" /OUT:"C:\git\stackoverflow\UnmanagedCallersOnlyStructReturn\obj\Debug\net8.0-windows7.0\dnne\bin\UnmanagedCallersOnlyStructReturnNE.dll" " exited with code 2.
syntax error: '__cdecl'
What are I'm doing wrong?
Full source code available here: https://github.com/JYPDWhite/UnmanagedCallersOnlyStructReturn
According to this issue, it seems that this library does not know how to translate the C# struct. You need to manually declare the C struct as follow:
[UnmanagedCallersOnly]
[DNNE.C99DeclCode("struct ReturnTest{int code; intptr_t txt;};")]
[return: DNNE.C99Type("struct ReturnTest")]
public static ReturnTest TestFunction()
{
ReturnTest returnTest = new ReturnTest();
returnTest.code = 1337;
returnTest.txt = Marshal.StringToBSTR("a b c d q ¥ K xyz");
return returnTest;
}