2017-03-27 4 views
0

Zuerst einige Hintergrund, diese Frage folgt auf System.DllNotFoundException: Unable to load DLL with dotnet core.Seg Fehler mit Dotnetcore und Callbacks

Wir haben es geschafft, eine Interop-Fassade, die in Windows funktioniert, vollständig zu implementieren. Allerdings hatten wir Probleme mit Linux. Wir bekommen Segmentfehler immer wieder zufällig. Es funktioniert manchmal für Minuten oder Stunden, aber schließlich stirbt es. Hier sind einige Code-Schnipsel.
N.B OnNotificationFromUnmanaged tut mehr als nur log, aber wir haben festgestellt, dass, egal was es enthält, sogar void ist dies immer noch der Punkt, an dem die App stirbt.

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"); 

} 

Bei einem Fehler erhalten wir:

2017-03-27 15: 53: 22,005 Info, Rückruf zu C#, 0x7fe2184175fc $

[7.383,514872] Dotnet [21218]: segfault bei 7fe218418000 ip 00007fe218418000 sp 00007fe0ebffec88 Fehler 14

Wir haben festgestellt, dass der Fehler passiert immer im 1k Bereich nach dem Ende des unmanaged Wir sind uns nicht sicher, ob das überhaupt wichtig ist. Zum Beispiel:

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

Alle Ideen sind sehr willkommen! An diesem Punkt haben wir irgendwie den Willen zu leben verloren.

uname -a
Linux dh-vm-ubuntu01 4.8.0-41-generiC# 44 ~ 16.04.1-Ubuntu SMP Fr 3. März 17.11.16 UTC 2017 x86_64 x86_64 x86_64 GNU/Linux

dotnet --version
2.0.0-preview1-005416

+1

Da Ihr OnNotificationFromUnmanaged nicht statisch ist - wird vielleicht die Instanz Müll gesammelt? – Evk

+0

Es ist eine Klasse private Funktion. Die Klasse ist ein Singleton. Kannst du ein Beispiel als Antwort posten, vielleicht fehlt mir etwas? – Mark

+1

Nur ein Gedanke. Wenn es ein Singleton ist, wird seine Instanz im statischen Feld gespeichert und kann daher nicht gesammelt werden. – Evk

Antwort

0

per @ Evk Kommentar geändert ich den Code leicht

.....

Handler += OnNotificationFromUnmanaged; 

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

und das scheint es behoben zu haben.