views:

58

answers:

3

So in visual studio i have my solution with two projects, first one is managed c++ code and second one is unmanaged c++ library (waffles). I want to use classes from library in my managed code.

If i simply add 'include "GMacros.h"', then i get 'cannot compile with /clr' error. Tried to wrap include in #pragma unmanaged/managed, but it doesnt seem to work.

Is there anything i can do without editing external library code or writing any wrappers?

A: 

The generic solution is to wrap the library calls in thin wrapper functions/classes whose header files you can include in managed code. Not very pretty but will get you there.

jdv
A: 

Unmanaged code can't be called directly in managed .NET. You need to add __declspec(dllexport) to your functions' declarations that should be visible outside the unmanaged library:

public:
    void __declspec(dllexport) MyUnmanagedMethod();

And then in your managed code write a simple wrapper like this:

public ref class Wrapper
{
public:
    [DllImport("MyUnmanagedLibrary.dll")]
    static extern void MyUnmanagedMethod();
}

Now you can call Wrapper.MyUnmanagedMethod like any other static method from you managed code.

A.
What if i dont have the .dll file? Only bunch of .h and .cpp
spacevillain
.dll file is created by the compiler when you build your unmanaged project. Look for it in your Debug or Release directory
A.
A: 

P/Invoke with the DLLImport attribute also requires you to get down and dirty with marshalling the function parameters, if it has any, to CLR types. So for example a DWORD becomes an int, IN HANDLE can become an IntPtr, LPDWORD becomes an out int, LPVOID can usually be marshalled as a byte[]... and so on. See a decent summary about it here.

An example pulled out of my recent project where I had to interface with a DLL for an old digital output box:

//This function's header in the DLL was:
//BOOL _stdcall fnPerformaxComSendRecv(IN HANDLE pHandle, IN LPVOID wBuffer, IN DWORD dwNumBytesToWrite, IN DWORD dwNumBytesToRead, OUT LPVOID rBuffer);
[DllImport("PerformaxCom.dll", SetLastError = true, CharSet = CharSet.Auto)]
private static extern bool fnPerformaxComSendRecv(IntPtr pHandle, byte[] wBuffer, int dwNumBytesToWrite, int dwNumBytesToRead, byte[] rBuffer);
Aphex