使用Dotnetcore和回调进行Seg故障

时间:2017-03-27 15:25:17

标签: c# c++ ubuntu .net-core

首先是一些背景知识,这个问题来自System.DllNotFoundException: Unable to load DLL with dotnet core

我们设法完全实现了在windows中工作的互操作外观。但是我们在linux中运行时遇到了问题。我们随机地得到段错误。它有时会工作几分钟或几小时,但最终会死亡。 以下是一些代码段。
N.B OnNotificationFromUnmanaged不仅仅记录,但我们发现无论它包含什么,甚至无效,这仍然是应用程序死亡的重点。

C#

private void OnNotificationFromUnmanaged(ZWNotification notification)
{
    Console.WriteLine ( "OnNotificationFromUnmanaged");
}

var callback = Marshal.GetFunctionPointerForDelegate((ManagedNotificationsHandler)OnNotificationFromUnmanaged);
Console.WriteLine($"Callback Ptr = {callback}");

Interop.RegisterCallback(callback);
GC.Collect();//all calls should now segfault should the callback get GC'd

CPP

#ifdef __GNUC__
#define EXPORT extern "C"
#define CC
#else
#define EXPORT extern "C" __declspec (dllexport)
#define CC __stdcall
#endif



typedef void(CC *CallBackDelegate)(ZWNotification);

CallBackDelegate cb; //set by another function


void OnNotification ( Notification const* _notification, void* _context)
{

        ZWNotification zw;
        ...init stuff here

        Log::Write( LogLevel_Info, "Callback to C#, %p", cb);

        if ( cb)
                cb ( zw);
        Log::Write( LogLevel_Info, "Callback to C# - done");

}

失败后我们得到:

  

2017-03-27 15:53:22.005 Info,Call to C#,0x7fe2184175fc   $

dmesg reveals 
  

[7383.514872] dotnet [21218]:段错误在7fe218418000 ip   00007fe218418000 sp 00007fe0ebffec88错误14

我们注意到,在非托管ptr结束后,故障总是发生在1k范围内,我们不确定这是否很重要。 例如:

>     segfault at 7f72c17f4000 ip 00007f72c17f4000 sp 00007f718d0fac88 error 14
>     segfault at 7f1656b75000 ip 00007f1656b75000 sp 00007f152d50bc88 error 14

非常欢迎任何想法!在这一点上,我们已经失去了生存的意志。

  

uname -a
  Linux dh-vm-ubuntu01 4.8.0-41-generic#44~16.04.1-Ubuntu SMP   3月3日星期五17:11:16 UTC x86_64 x86_64 x86_64 GNU / Linux

     

dotnet --version
  2.0.0-preview1-005416

1 个答案:

答案 0 :(得分:0)

根据@Evk的评论,我稍微修改了代码

        private ManagedNotificationsHandler Handler;

.....

Handler += OnNotificationFromUnmanaged;

var callback = Marshal.GetFunctionPointerForDelegate(Handler);
Interop.RegisterCallback(callback);

似乎已修复它。