【问题标题】:Delegate to trigger C# function from referenced C++ DLL委托从引用的 C++ DLL 触发 C# 函数
【发布时间】:2012-08-15 18:13:54
【问题描述】:

我有一个工作的非托管 C++ DLL,它使用 p/invoke 附加到我的 C# 代码

    [DllImport("p2p.dll", EntryPoint = "Start")]
    public static extern void Start();

    [STAThread]
    static void Main()
    {
        Thread th= new Thread(Start);
         th.Start();
....

这样我可以从我的 C++ 代码中检索信息,但是如果我的 C++ 代码需要触发一个 C# 函数,那么我该如何以一种聪明的方式来完成它,而不是将所有请求放在一个队列中并从 C# 中检查它线。

【问题讨论】:

    标签: c# c++ visual-c++ dll pinvoke


    【解决方案1】:

    您可以使用托管 C++,也可以通过将一组函数指针(托管端的委托)传递给所有相关入口点,从 C# 初始化您的 C++ 库。

    在程序开始时调用初始化程序:

    [DllImport("p2p.dll")]
    public static extern void Initialize(Action triggerManagedAction);
    
    Initialize(() => {Console.WriteLine("called from C++");});
    

    在该函数的 C++ 实现中,记住函数指针。

    在使用此技术之前,还请阅读 Hans Passant 和 Google 的评论。我在这里很容易引入错误。

    【讨论】:

    • 谢谢,我不能使用托管 C++,但您能否详细说明您所说的第二个关于函数指针的内容
    • 当然。我添加了一些示例代码。你必须自己研究 C++ 方面,因为我对这方面了解不够。
    • 代码sn-p非常危险,当垃圾收集器销毁委托对象时很容易导致崩溃。它必须存储在一个字段中才能保持活力。最好单独声明委托类型,以便可以显式指定调用约定。发布的 sn-p 需要函数指针上的 __stdcall 才能正常工作。
    • @HansPassant,我现在从我的回答中引用您非常重要的评论。顺便说一句,请随时编辑我的帖子。
    • @usr 有责任在你而不是汉斯来修复帖子
    【解决方案2】:

    您可以通过创建托管 C++ 类来做到这一点,该类充当您的 C++ 和 .Net 事件处理程序之间的代理。这是它的外观:

    • 假设您通过发布一个 ICEventHandler 接口为 C++ 类注册通知,该接口的 notify() 方法将被调用。
    • 在托管 C++ 中创建一个派生自 ICEventHandler 的类,该类具有一个委托,例如 Notify()。在继承的 ICEvenhHandler.notifty() 中调用 Notify 委托。
    • 拥有 .net Nofity 方法,构造代理类的实例,并将其传递给 C++ 事件源类

    这样,C++ 事件将触发您的 .Net Notify 方法。

    【讨论】:

    • 好吧..,我想这里的问题将是当我实现非托管和托管之间的桥梁时,不是吗?因为我无法将我的代码编译为托管的,是的,我可以将未托管的代码引用为托管的 C++,但这不是一个漫长的过程,而且 DLL 是一个网络层,所以它不会变慢。
    • 托管 c++ 桥可以引用 C++ dll 库,并将生成一个 .net 程序集,可以从任何 .net 项目引用。我们这样做了,并没有特别慢,但是其他进程间通信方式可能更快(命名管道、套接字等)
    • 谢谢,我会调查并告诉你:)
    • 我希望您指的是 C++/CLI,而不是“C++ 托管扩展”。
    【解决方案3】:

    其中一种方法是使用 /clr 标志编译 C++ 代码。在this SO thread 中可以找到几个不同的示例。

    【讨论】:

    • 我正在使用 boost/asio 和 boost/thread,所以我不能用 /clr 编译它。可以在 /clr 中编译 boost,但在我的情况下它有点复杂。
    猜你喜欢
    • 2013-01-07
    • 1970-01-01
    • 1970-01-01
    • 2018-11-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多