Bug 1550 – D DLLs close standard input/output streams when unloading

Status
RESOLVED
Resolution
FIXED
Severity
normal
Priority
P3
Component
tools
Product
D
Version
D2
Platform
x86
OS
Windows
Creation time
2007-10-07T16:32:18Z
Last change time
2019-10-28T08:24:21Z
Keywords
dll
Assigned to
No Owner
Creator
Vladimir Panteleev
See also
https://issues.dlang.org/show_bug.cgi?id=15443

Comments

Comment #0 by dlang-bugzilla — 2007-10-07T16:32:18Z
=== loader.d === import std.stdio; import std.string; import std.c.windows.windows; void main() { writefln("Loading DLL..."); HANDLE h = LoadLibraryA("library.dll"); if(!h) return writefln("Failed to load DLL."); writefln("DLL loaded. Unloading..."); if(!FreeLibrary(h)) return writefln("Failed to unload DLL."); writefln("DLL unloaded."); } === library.d === (standard DLL template copied from the documentation) import std.c.windows.windows; HINSTANCE g_hInst; extern (C) { void gc_init(); void gc_term(); void _minit(); void _moduleCtor(); void _moduleUnitTests(); } extern (Windows) BOOL DllMain(HINSTANCE hInstance, ULONG ulReason, LPVOID pvReserved) { switch (ulReason) { case DLL_PROCESS_ATTACH: gc_init(); // initialize GC _minit(); // initialize module list _moduleCtor(); // run module constructors _moduleUnitTests(); // run module unit tests break; case DLL_PROCESS_DETACH: gc_term(); // shut down GC break; case DLL_THREAD_ATTACH: case DLL_THREAD_DETACH: // Multiple threads not supported yet return false; } g_hInst=hInstance; return true; } === output === Loading DLL... DLL loaded. Unloading... === comments === D's runtime (DMC libc) closes the standard streams when the DLL is unloaded. Call stack: DllEntryPoint __cexit _exit ___fcloseall _fclose _close Needless to say, that shouldn't happen with DLLs. Workaround: import std.stdio and add _fcloseallp = null; somewhere in your DllMain.
Comment #1 by dlang-bugzilla — 2007-10-07T17:04:17Z
I just noticed that this is somewhat documented at http://digitalmars.com/d/dll.html#Dcode . However, this applies not only when a program in D is the one loading the DLL. Thus, it should be moved outside the "D code calling D code in DLLs" section, and also into the "DLLs with a C Interface" source code template.
Comment #2 by r.sagitario — 2010-04-07T11:20:55Z
The workaround (setting _fcloseallp = null) also prevents any other open file from being closed. I think it should be fixed in the C-runtime library, where the handle for stdin/out/err is taken from a call to GetStdHandle(), and probably should not be closed when terminating.
Comment #3 by zan77137 — 2010-10-06T05:50:52Z
*** Issue 4996 has been marked as a duplicate of this issue. ***
Comment #4 by dlang-bugzilla — 2014-02-12T19:34:19Z
Doesn't happen in D2.
Comment #5 by r.sagitario — 2017-04-14T15:16:05Z
Still happens with the example dclient/dserver in dmd/samples.
Comment #6 by razvan.nitu1305 — 2019-10-24T09:31:01Z
Does this issue still manifests?
Comment #7 by r.sagitario — 2019-10-24T18:03:46Z
The pull request for the dmc runtime has been merged https://github.com/DigitalMars/dmc/pull/3 , but there has never been an update to the released snn.lib AFAICT.
Comment #8 by razvan.nitu1305 — 2019-10-25T10:05:09Z
(In reply to Rainer Schuetze from comment #7) > The pull request for the dmc runtime has been merged > https://github.com/DigitalMars/dmc/pull/3 , but there has never been an > update to the released snn.lib AFAICT. Any ideas on what actions should be taken to update the snn.lib? This is the first time I hear about this.
Comment #9 by r.sagitario — 2019-10-25T10:33:03Z
(In reply to RazvanN from comment #8) > Any ideas on what actions should be taken to update the snn.lib? This is the > first time I hear about this. Walter has to build it and upload it to http://ftp.digitalmars.com/snn.lib That's where the release build program downloads it from.
Comment #10 by r.sagitario — 2019-10-28T08:24:21Z
I verified the reported example (after some updates) works with the new snn.lib in 2.089-rc1 (and still failed with 2.088.1).