diff options
| author | Andrew Kelley <superjoe30@gmail.com> | 2018-11-05 10:56:42 -0500 |
|---|---|---|
| committer | Andrew Kelley <superjoe30@gmail.com> | 2018-11-05 10:56:42 -0500 |
| commit | f8d6f5daff5ac9b9f69319b9bd827ccc34ea9d72 (patch) | |
| tree | fc0da10e6a69eb167e7d994f348148917c8ef98b /src/os.cpp | |
| parent | ce912e29640e0a3b39a5c304c86bdbb5fff67169 (diff) | |
| parent | 973e0abe79abf33cb5e9f4550fe323cb93eb6ee1 (diff) | |
| download | zig-f8d6f5daff5ac9b9f69319b9bd827ccc34ea9d72.tar.gz zig-f8d6f5daff5ac9b9f69319b9bd827ccc34ea9d72.zip | |
Merge remote-tracking branch 'origin/master' into llvm8
Diffstat (limited to 'src/os.cpp')
| -rw-r--r-- | src/os.cpp | 44 |
1 files changed, 23 insertions, 21 deletions
diff --git a/src/os.cpp b/src/os.cpp index b682429884..f01a99fc23 100644 --- a/src/os.cpp +++ b/src/os.cpp @@ -46,6 +46,7 @@ typedef SSIZE_T ssize_t; #include <sys/wait.h> #include <fcntl.h> #include <limits.h> +#include <spawn.h> #endif @@ -70,6 +71,12 @@ static clock_serv_t cclock; #include <errno.h> #include <time.h> +// Apple doesn't provide the environ global variable +#if defined(__APPLE__) && !defined(environ) +#include <crt_externs.h> +#define environ (*_NSGetEnviron()) +#endif + #if defined(ZIG_OS_POSIX) static void populate_termination(Termination *term, int status) { if (WIFEXITED(status)) { @@ -88,25 +95,22 @@ static void populate_termination(Termination *term, int status) { } static void os_spawn_process_posix(const char *exe, ZigList<const char *> &args, Termination *term) { - pid_t pid = fork(); - if (pid == -1) - zig_panic("fork failed"); - if (pid == 0) { - // child - const char **argv = allocate<const char *>(args.length + 2); - argv[0] = exe; - argv[args.length + 1] = nullptr; - for (size_t i = 0; i < args.length; i += 1) { - argv[i + 1] = args.at(i); - } - execvp(exe, const_cast<char * const *>(argv)); - zig_panic("execvp failed: %s", strerror(errno)); - } else { - // parent - int status; - waitpid(pid, &status, 0); - populate_termination(term, status); + const char **argv = allocate<const char *>(args.length + 2); + argv[0] = exe; + argv[args.length + 1] = nullptr; + for (size_t i = 0; i < args.length; i += 1) { + argv[i + 1] = args.at(i); } + + pid_t pid; + int rc = posix_spawnp(&pid, exe, nullptr, nullptr, const_cast<char *const*>(argv), environ); + if (rc != 0) { + zig_panic("posix_spawn failed: %s", strerror(rc)); + } + + int status; + waitpid(pid, &status, 0); + populate_termination(term, status); } #endif @@ -806,7 +810,7 @@ static int os_exec_process_posix(const char *exe, ZigList<const char *> &args, pid_t pid = fork(); if (pid == -1) - zig_panic("fork failed"); + zig_panic("fork failed: %s", strerror(errno)); if (pid == 0) { // child if (dup2(stdin_pipe[0], STDIN_FILENO) == -1) @@ -1378,8 +1382,6 @@ int os_init(void) { #if defined(ZIG_OS_WINDOWS) _setmode(fileno(stdout), _O_BINARY); _setmode(fileno(stderr), _O_BINARY); -#endif -#if defined(ZIG_OS_WINDOWS) unsigned __int64 frequency; if (QueryPerformanceFrequency((LARGE_INTEGER*) &frequency)) { win32_time_resolution = 1.0 / (double) frequency; |
