在struct中从C#发送回调函数到C dll

时间:2014-08-13 21:38:28

标签: c# c++ dll native

我试图发送一个结构,其中包含从C#到C ++本机DLL的回调函数的引用,我正在做什么>做错了什么?,结构传递了!,所有回调引用都不为null但是当调用它时,我没有从DLL到达C#函数:(

class Native_Wrraper
{
    [UnmanagedFunctionPointer(CallingConvention.StdCall)]
    public delegate int LogMessageCallback(string mMyStruct);
    [UnmanagedFunctionPointer(CallingConvention.StdCall)]
    public delegate int ActionCompleteCallback(int actionId, int actionResult);
    [UnmanagedFunctionPointer(CallingConvention.StdCall)]
    public delegate string GetFilePathCallback(string filter);

结构:

    [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Auto)]
    public struct InitCallBacksStruct
    {
        [MarshalAs(UnmanagedType.FunctionPtr)]
        public LogMessageCallback logMessageCallback;

        [MarshalAs(UnmanagedType.FunctionPtr)]
        public ActionCompleteCallback actionCompleteCallback;

        [MarshalAs(UnmanagedType.FunctionPtr)]
        public GetFilePathCallback getPath;
        //UpdaterCallback updaterCallback;
    };

    [DllImport("_Wrraper.dll", CharSet = CharSet.Unicode)]
    public static extern int InitDll(InitCallBacksStruct mMyStruct);

    [DllImport("_Wrraper.dll", CharSet = CharSet.Unicode)]
    public static extern int StartTestAPIDll(string TestHeader, int someNumber);

这里是DLL应该调用的回调函数(输入)

    public static int FuncLogMessageCallback(string mMyStruct)
    {
        return 1;
    }
    public static int FuncActionCompleteCallback(int actionId, int actionResult)
    {
        return 1;
    }
    public static string FuncGetFilePathCallback(string filter)
    {
        return "The Call back worked!";
    }
}

测试按钮:

    private void btnTest_Click(object sender, EventArgs e)
    {
        Native_Wrraper.InitCallBacksStruct str =  new Native_Wrraper.InitCallBacksStruct();
        str.actionCompleteCallback = new Native_Wrraper.ActionCompleteCallback(Native_Wrraper.FuncActionCompleteCallback);
        str.getPath = new Native_Wrraper.GetFilePathCallback(Native_Wrraper.FuncGetFilePathCallback);
        str.logMessageCallback = new Native_Wrraper.LogMessageCallback(Native_Wrraper.FuncLogMessageCallback);
        Native_Wrraper.InitDll(str);
        Native_Wrraper.StartTestAPIDll(DateTime.Now.ToShortTimeString(), 0xEE);
    }
C DLL中的

结构:

#define DLL __declspec(dllexport)
typedef void (__stdcall * ActionCompleteCallback)(int actionId, int actionResult);
typedef char* (__stdcall * GetFilePathCallback)(char* filter);
typedef void (__stdcall * LogMessageCallback)(char* message);


//This structure include all the references to a call backs functions 
struct InitCallBacksStruct
{
    LogMessageCallback logMessageCallback;
    ActionCompleteCallback actionCompleteCallback;
    GetFilePathCallback getPath;
};

#endif

API:

#ifdef __cplusplus
extern "C"
{
#endif

#define DLL __declspec(dllexport)
DLL int InitDll(InitCallBacksStruct mMyStruct);
DLL int StartTestAPIDll( __in LPWSTR TestHeader, int someNumber);

#ifdef __cplusplus
}
#endif

从DLL调用的示例:

if(this->mInitCallBacksStruct.actionCompleteCallback)
{
    this->mInitCallBacksStruct.actionCompleteCallback(someNumber,0xCC);
}

1 个答案:

答案 0 :(得分:0)

抱歉伙计们,CODE完美工作!!!

问题是C#中的断点! :)

添加MessageBox.Show并验证所有工作。

因此,对于正在寻找解决方案的人来说,这将是一个模板和/或答案:

如何使用结构内的一个函数调用将来自C#的本机DLL发送回调函数引用列表。

  

只有,请注意,您应该将回调保存在C#的某个地方,并且更好的静态而不是btnTest_Click函数内部!确保引用不会消失,意味着对回调函数的引用应该是全局变量或静态变量,例如:

static Native_Wrraper.ActionCompleteCallback refFunction = new Native_Wrraper.ActionCompleteCallback(Native_Wrraper.FuncGetFilePathCallback);
  

然后将其发送到DLL

str.actionCompleteCallback = refFunction
祝你好运! 约瑟夫

相关问题