D issues are now tracked on GitHub. This Bugzilla instance remains as a read-only archive.
Issue 10364 - Mac OS 10.8 program crash
Summary: Mac OS 10.8 program crash
Status: ASSIGNED
Alias: None
Product: D
Classification: Unclassified
Component: druntime (show other issues)
Version: D2
Hardware: x86_64 Mac OS X
: P2 major
Assignee: Lars T. Kyllingstad
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2013-06-15 12:11 UTC by Gary Willoughby
Modified: 2024-12-07 13:32 UTC (History)
5 users (show)

See Also:


Attachments
Sample crash log (8.69 KB, text/x-log)
2013-06-15 12:11 UTC, Gary Willoughby
Details

Note You need to log in before you can comment on or make changes to this issue.
Description Gary Willoughby 2013-06-15 12:11:36 UTC
Created attachment 1226 [details]
Sample crash log

The following code produces a program crash on Mac OS 10.8. Nothing is output
to the opened file and a crash is reported to /etc/log/system.log.

import core.sys.posix.unistd;
import std.c.stdlib;
import std.process;
import std.stdio;
import std.string;

int main(string[] args)
{
    pid_t pid = fork();
    if (pid < 0)
    {
        exit(EXIT_FAILURE);
    }

    if (pid > 0)
    {
        exit(EXIT_SUCCESS);
    }

    auto logFile = File("/Users/gary/Desktop/test.log", "a");
    logFile.writeln("Opened file");

    string command = format("logger -t %s %s", "hello", "This is a test");
    executeShell(command);

    logFile.writeln("Done");

    return 0;
}

See attached for sample crash log.
Comment 1 Gary Willoughby 2013-06-15 12:20:52 UTC
Another example of maybe the same bug? This also crashes but does so silently with no system.log entry or crash dump.

import core.sys.posix.sys.stat;
import core.sys.posix.unistd;
import std.c.stdio;
import std.c.stdlib;
import std.process;
import std.stdio;
import std.string;
import std.file;
import std.datetime;

class Logger
{
     private File _logFile;

     public this(string logFile)
     {
         this._logFile = File(logFile, "a");
     }

     public void info(string, A...)(string text, A args)
     {
         this._logFile.writefln(format(text, args));
     }
}

int main(string[] args)
{
     pid_t pid, sid;

     pid = fork();
     if (pid < 0)
     {
         exit(EXIT_FAILURE);
     }

     if (pid > 0)
     {
         exit(EXIT_SUCCESS);
     }

     umask(0);

     sid = setsid();
     if (sid < 0)
     {
         exit(EXIT_FAILURE);
     }

     if ((core.sys.posix.unistd.chdir("/")) < 0)
     {
         exit(EXIT_FAILURE);
     }

     close(STDIN_FILENO);
     close(STDOUT_FILENO);
     close(STDERR_FILENO);

     auto logger = new Logger("/Users/gary/Desktop/test.log");

     // Crash!
     logger.info("Reading file");

     string configFileContents = readText("/etc/hosts");

     // Never executes!
     logger.info(configFileContents);

     return 0;
}
Comment 2 Lars T. Kyllingstad 2013-07-28 08:11:16 UTC
I can not reproduce this on Linux.  It would be great to get confirmation from someone else on OSX, to verify that it isn't a local issue.

One thing I've noticed is that you call exit() in the parent process after a successful fork().  You should call _exit() instead, to avoid double-flushing buffers etc.  This probably won't fix your problem, but it's worth a try.
Comment 3 Gary Willoughby 2013-07-28 08:37:03 UTC
(In reply to comment #2)
> I can not reproduce this on Linux.  It would be great to get confirmation from
> someone else on OSX, to verify that it isn't a local issue.
> 
> One thing I've noticed is that you call exit() in the parent process after a
> successful fork().  You should call _exit() instead, to avoid double-flushing
> buffers etc.  This probably won't fix your problem, but it's worth a try.

I've reduced it to this:

import std.stdio;
import std.string;
import std.process;

extern (C)
{
	int daemon(int nochdir, int noclose);
}

void main(string[] args)
{
	daemon(0, 0);

	auto logFile = File("/Users/gary/Desktop/test.log", "a");
	logFile.writeln("Opened file");

	string command = format("logger -t %s %s", "Hello", "This is a test.");
	executeShell(command); // Crash dump logged at /var/log/system.log

	logFile.writeln("Done!"); // Never executes.
}
Comment 4 Andrei Alexandrescu 2013-12-27 14:45:30 UTC
Gary, is this still failing?
Comment 5 Jacob Carlborg 2013-12-28 05:33:06 UTC
(In reply to comment #4)
> Gary, is this still failing?

It's failing for me as well. I don't get a crash but the last line is never printed. It's printed if "executeShell" is not invoked.
Comment 6 Jacob Carlborg 2013-12-28 05:41:09 UTC
Doesn't seem to matter what command is passed to "executeShell".
Comment 7 Vladimir Panteleev 2017-07-21 02:04:10 UTC
I reproduced it with macOS 10.12 and DMD 2.074.

Changing daemon(0,0) to daemon(0,1) (so that stderr isn't redirected to /dev/null) reveals a clue:

core.thread.ThreadError@src/core/thread.d(3002): Unable to load thread state

It looks like the daemon() call is interfering with Druntime's threading code.
Comment 8 Jacob Carlborg 2017-07-21 07:10:37 UTC
(In reply to Vladimir Panteleev from comment #7)
> I reproduced it with macOS 10.12 and DMD 2.074.
> 
> Changing daemon(0,0) to daemon(0,1) (so that stderr isn't redirected to
> /dev/null) reveals a clue:
> 
> core.thread.ThreadError@src/core/thread.d(3002): Unable to load thread state
> 
> It looks like the daemon() call is interfering with Druntime's threading
> code.

I did some more debugging. The error returned by "thread_get_state" is 268435459 (0x10000003) which seems to correspond to MACH_SEND_INVALID_DEST. This bug had the same error code [1]

[1] https://issues.dlang.org/show_bug.cgi?id=6135
Comment 9 Vladimir Panteleev 2017-07-21 14:52:54 UTC
(In reply to Jacob Carlborg from comment #8)
> I did some more debugging. The error returned by "thread_get_state" is
> 268435459 (0x10000003) which seems to correspond to MACH_SEND_INVALID_DEST.

Interesting. daemon() calls fork(), and forked processes go on without the other threads from their parent process. It could be that something in Druntime has created a thread, which is now gone after the fork; or, possibly, that the thread ID of the main thread has changed, and Druntime is unable to correctly address it. I'm not familiar with Mach threading, though, so I can only guess.
Comment 10 Mathias LANG 2020-01-16 13:30:06 UTC
I cannot reproduce the issue anymore (Mac OSX 10.15.2, DMD 2.090.0). Is it still present ?
Comment 11 dlangBugzillaToGithub 2024-12-07 13:32:45 UTC
THIS ISSUE HAS BEEN MOVED TO GITHUB

https://github.com/dlang/dmd/issues/17256

DO NOT COMMENT HERE ANYMORE, NOBODY WILL SEE IT, THIS ISSUE HAS BEEN MOVED TO GITHUB