2014-11-21 177 views
-1

问题是我有一个C++ DLL,我想在我的C#项目中使用。在C中调用C++ DLL

有问题的函数原型:

int MRK3LINK_Open(void (*pfLog)(const char* s),void (*pfErrorOut)(const char* s));  

的文档指出:

  • 的pflog是一个记录类型为const char的处理函数*指针。
  • pfErrorOut是指向const char *类型的错误输出处理函数的指针。

以及如何从C++调用的DLL函数的例子:

static void _LogHandler(const char* sLog) { 
    printf(sLog); 
} 

static void _ErrorOutHandler(const char* sError) { 
    MessageBox(NULL, sError, "2-Link", MB_OK); 
} 

MRK3LINK_Open(_LogHandler, _ErrorOutHandler); 

我现在被困在这2天。你能提供一些提示吗?

谢谢。

+0

两个可能的错误,你没有发布足够的。您可能忘记了委托声明中的[UnmanagedFunctionPointer]属性,以确保CLR知道这是一个CallingConvention.Cdecl函数指针。而且你并没有将委托对象存储在任何地方,所以他们会收集垃圾,当C代码进行回调时会崩溃程序。 – 2014-11-21 12:15:30

+0

感谢您的建议,您是对的。 – 2014-12-16 13:28:59

回答

1

这两个参数是函数指针。他们将用C++映射到代表。就像这样:

[UnmanagedFunctionPointer(CallingConvention.Cdecl)] 
public delegate void LogHandlerDelegate(string str); 

[UnmanagedFunctionPointer(CallingConvention.Cdecl)] 
public delegate void ErrorOutHandlerDelegate(string error); 

然后你导入功能:

[DllImport(dllname, CallingConvention = CallingConvention.Cdecl)] 
public static extern int MRK3LINK_Open(
    LogHandlerDelegate LogHandler, 
    ErrorOutHandlerDelegate ErrorOutHandler 
); 

那么你通常的方式创建的代表,并通过他们向MRK3LINK_Open。如果非托管代码引用它们并在MRK3LINK_Open返回后调用它们,请确保您存储对委托的引用。否则垃圾收集器有责任收集它们。

+0

感谢您的回答,我现在拥有了:) – 2014-12-16 13:29:37