Index: lib/sanitizer_common/sanitizer_posix_libcdep.cc =================================================================== --- lib/sanitizer_common/sanitizer_posix_libcdep.cc +++ lib/sanitizer_common/sanitizer_posix_libcdep.cc @@ -29,6 +29,7 @@ #include #include #include +#include #include #include #include @@ -45,6 +46,8 @@ #define MAP_NORESERVE 0 #endif +extern char **environ; + typedef void (*sa_sigaction_t)(int, siginfo_t *, void *); namespace __sanitizer { @@ -448,40 +451,40 @@ } }); - int pid = internal_fork(); - - if (pid < 0) { - int rverrno; - if (internal_iserror(pid, &rverrno)) { - Report("WARNING: failed to fork (errno %d)\n", rverrno); - } - return pid; + posix_spawn_file_actions_t fa; + int result = posix_spawn_file_actions_init(&fa); + if (result != 0) { + Report("WARNING: posix_spawn_file_actions_init failed (result %d)\n", result); + return -1; } - - if (pid == 0) { - // Child subprocess - if (stdin_fd != kInvalidFd) { - internal_close(STDIN_FILENO); - internal_dup2(stdin_fd, STDIN_FILENO); - internal_close(stdin_fd); + if (stdin_fd != kInvalidFd) { + result = posix_spawn_file_actions_adddup2(&fa, stdin_fd, STDIN_FILENO); + if (result != 0) { + Report("WARNING: posix_spawn_file_actions_adddup2 failed (result %d)\n", result); + return -1; } - if (stdout_fd != kInvalidFd) { - internal_close(STDOUT_FILENO); - internal_dup2(stdout_fd, STDOUT_FILENO); - internal_close(stdout_fd); + } + if (stdout_fd != kInvalidFd) { + result = posix_spawn_file_actions_adddup2(&fa, stdout_fd, STDOUT_FILENO); + if (result != 0) { + Report("WARNING: posix_spawn_file_actions_adddup2 failed (result %d)\n", result); + return -1; } - if (stderr_fd != kInvalidFd) { - internal_close(STDERR_FILENO); - internal_dup2(stderr_fd, STDERR_FILENO); - internal_close(stderr_fd); + } + if (stderr_fd != kInvalidFd) { + result = posix_spawn_file_actions_adddup2(&fa, stderr_fd, STDERR_FILENO); + if (result != 0) { + Report("WARNING: posix_spawn_file_actions_adddup2 failed (result %d)\n", result); + return -1; } - - for (int fd = sysconf(_SC_OPEN_MAX); fd > 2; fd--) internal_close(fd); - - execv(program, const_cast(&argv[0])); - internal__exit(1); } + pid_t pid; + result = posix_spawn(&pid, program, &fa, nullptr, const_cast(argv), environ); + if (result != 0) { + Report("WARNING: failed to spawn process (result %d)\n", result); + return -1; + } return pid; }