| |
 | Posted by Max Samukha | Permalink Reply |
|
Max Samukha 
| http://d.puremagic.com/issues/show_bug.cgi?id=4104
Summary: No way to get notified about D runtime termination.
Product: D
Version: unspecified
Platform: Other
OS/Version: Linux
Status: NEW
Severity: critical
Priority: P2
Component: druntime
AssignedTo: sean@invisibleduck.org
ReportedBy: samukha@voliacable.com
--- Comment #0 from Max Samukha <samukha@voliacable.com> 2010-04-19 06:07:29 PDT ---
Qt classes have corresponding D wrappers in QtD. For many Qt classes we can avoid creating duplicate wrappers (or searching a wrapper cache) and store the D wrapper pointers directly in the C++ objects.
When Qt takes ownership of such an object, QtD disables garbage collection for the D wrapper by adding its reference to the GC roots. When later Qt deletes the object, a callback to D is emitted, during which the wrapper is destroyed.
Everything works well unless the C++ object is statically allocated or is owned by a statically allocated object. If it is, the C++ destructor is called *after* the D runtime has been terminated, meaning GC pools has been freed and there is no wrapper to delete.
One solution is to have a flag that would be set after the D runtime has been terminated. Then we could avoid deleting already freed wrappers by checking the flag in the callback.
Patch for druntime/src/rt/dmain2.d:
@@ -165,12 +165,18 @@
}
shared bool _d_isHalting = false;
+shared bool _d_isTerminated = false;
extern (C) bool rt_isHalting()
{
return _d_isHalting;
}
+extern (C) bool rt_isTerminated()
+{
+ return _d_isTerminated;
+}
+
// This variable is only ever set by a debugger on initialization so it should
// be fine to leave it as __gshared.
extern (C) __gshared bool rt_trapExceptions = true;
@@ -244,6 +250,7 @@
finally
{
_d_criticalTerm();
+ _d_isTerminated = true;
}
return false;
}
@@ -404,5 +411,7 @@
_STD_critical_term();
_STD_monitor_staticdtor();
}
+
+ _d_isTerminated = true;
return result;
}
Another solution would be a notification. Tests show that 'atexit' doesn't work for us because the handlers registered with 'atexit' are invoked after the destructors has been run. So we need a separate notification.
Even better solution: don't free the GC memory on exit and give the rooted objects a chance to be finalized properly.
This is critical.
--
Configure issuemail: http://d.puremagic.com/issues/userprefs.cgi?tab=email
------- You are receiving this mail because: -------
|