X-Git-Url: http://erislabs.net/gitweb/?a=blobdiff_plain;f=lib%2Fexecute.c;h=6de6c62f83daef10842555b1a428a5d77bf6f1b9;hb=a6b16b69fe1cad695b270dd5bf3deb2850fc4dd1;hp=c9f25b52d2a10fa2b8c28cb9f4f85b1d01430840;hpb=d629f6d28665184cf8970b691e48ea2dfccfa25f;p=gnulib.git diff --git a/lib/execute.c b/lib/execute.c index c9f25b52d..6de6c62f8 100644 --- a/lib/execute.c +++ b/lib/execute.c @@ -1,5 +1,5 @@ /* Creation of autonomous subprocesses. - Copyright (C) 2001-2004, 2006-2009 Free Software Foundation, Inc. + Copyright (C) 2001-2004, 2006-2011 Free Software Foundation, Inc. Written by Bruno Haible , 2001. This program is free software: you can redistribute it and/or modify @@ -35,7 +35,7 @@ #define _(str) gettext (str) -#if defined _MSC_VER || defined __MINGW32__ +#if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__ /* Native Woe32 API. */ # include @@ -98,13 +98,13 @@ nonintr_open (const char *pathname, int oflag, mode_t mode) creator receives a catchable fatal signal. */ int execute (const char *progname, - const char *prog_path, char **prog_argv, - bool ignore_sigpipe, - bool null_stdin, bool null_stdout, bool null_stderr, - bool slave_process, bool exit_on_error, - int *termsigp) + const char *prog_path, char **prog_argv, + bool ignore_sigpipe, + bool null_stdin, bool null_stdout, bool null_stderr, + bool slave_process, bool exit_on_error, + int *termsigp) { -#if defined _MSC_VER || defined __MINGW32__ +#if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__ /* Native Woe32 API. */ int orig_stdin; @@ -119,11 +119,11 @@ execute (const char *progname, /* Save standard file handles of parent process. */ if (null_stdin) - orig_stdin = dup_noinherit (STDIN_FILENO); + orig_stdin = dup_safer_noinherit (STDIN_FILENO); if (null_stdout) - orig_stdout = dup_noinherit (STDOUT_FILENO); + orig_stdout = dup_safer_noinherit (STDOUT_FILENO); if (null_stderr) - orig_stderr = dup_noinherit (STDERR_FILENO); + orig_stderr = dup_safer_noinherit (STDERR_FILENO); exitcode = -1; /* Create standard file handles of child process. */ @@ -131,20 +131,20 @@ execute (const char *progname, nulloutfd = -1; if ((!null_stdin || ((nullinfd = open ("NUL", O_RDONLY, 0)) >= 0 - && (nullinfd == STDIN_FILENO - || (dup2 (nullinfd, STDIN_FILENO) >= 0 - && close (nullinfd) >= 0)))) + && (nullinfd == STDIN_FILENO + || (dup2 (nullinfd, STDIN_FILENO) >= 0 + && close (nullinfd) >= 0)))) && (!(null_stdout || null_stderr) - || ((nulloutfd = open ("NUL", O_RDWR, 0)) >= 0 - && (!null_stdout - || nulloutfd == STDOUT_FILENO - || dup2 (nulloutfd, STDOUT_FILENO) >= 0) - && (!null_stderr - || nulloutfd == STDERR_FILENO - || dup2 (nulloutfd, STDERR_FILENO) >= 0) - && ((null_stdout && nulloutfd == STDOUT_FILENO) - || (null_stderr && nulloutfd == STDERR_FILENO) - || close (nulloutfd) >= 0)))) + || ((nulloutfd = open ("NUL", O_RDWR, 0)) >= 0 + && (!null_stdout + || nulloutfd == STDOUT_FILENO + || dup2 (nulloutfd, STDOUT_FILENO) >= 0) + && (!null_stderr + || nulloutfd == STDERR_FILENO + || dup2 (nulloutfd, STDERR_FILENO) >= 0) + && ((null_stdout && nulloutfd == STDOUT_FILENO) + || (null_stderr && nulloutfd == STDERR_FILENO) + || close (nulloutfd) >= 0)))) /* Use spawnvpe and pass the environment explicitly. This is needed if the program has modified the environment using putenv() or [un]setenv(). On Windows, programs have two environments, one in the "environment @@ -154,15 +154,17 @@ execute (const char *progname, copy of the environment block - ignoring the effects of putenv() and [un]setenv(). */ { - exitcode = spawnvpe (P_WAIT, prog_path, prog_argv, environ); + exitcode = spawnvpe (P_WAIT, prog_path, (const char **) prog_argv, + (const char **) environ); if (exitcode < 0 && errno == ENOEXEC) - { - /* prog is not an native executable. Try to execute it as a - shell script. Note that prepare_spawn() has already prepended - a hidden element "sh.exe" to prog_argv. */ - --prog_argv; - exitcode = spawnvpe (P_WAIT, prog_argv[0], prog_argv, environ); - } + { + /* prog is not a native executable. Try to execute it as a + shell script. Note that prepare_spawn() has already prepended + a hidden element "sh.exe" to prog_argv. */ + --prog_argv; + exitcode = spawnvpe (P_WAIT, prog_argv[0], (const char **) prog_argv, + (const char **) environ); + } } if (nulloutfd >= 0) close (nulloutfd); @@ -171,11 +173,11 @@ execute (const char *progname, /* Restore standard file handles of parent process. */ if (null_stderr) - dup2 (orig_stderr, STDERR_FILENO), close (orig_stderr); + undup_safer_noinherit (orig_stderr, STDERR_FILENO); if (null_stdout) - dup2 (orig_stdout, STDOUT_FILENO), close (orig_stdout); + undup_safer_noinherit (orig_stdout, STDOUT_FILENO); if (null_stdin) - dup2 (orig_stdin, STDIN_FILENO), close (orig_stdin); + undup_safer_noinherit (orig_stdin, STDIN_FILENO); if (termsigp != NULL) *termsigp = 0; @@ -183,8 +185,8 @@ execute (const char *progname, if (exitcode == -1) { if (exit_on_error || !null_stderr) - error (exit_on_error ? EXIT_FAILURE : 0, errno, - _("%s subprocess failed"), progname); + error (exit_on_error ? EXIT_FAILURE : 0, errno, + _("%s subprocess failed"), progname); return 127; } @@ -215,49 +217,49 @@ execute (const char *progname, attrs_allocated = false; if ((err = posix_spawn_file_actions_init (&actions)) != 0 || (actions_allocated = true, - (null_stdin - && (err = posix_spawn_file_actions_addopen (&actions, - STDIN_FILENO, - "/dev/null", O_RDONLY, - 0)) - != 0) - || (null_stdout - && (err = posix_spawn_file_actions_addopen (&actions, - STDOUT_FILENO, - "/dev/null", O_RDWR, - 0)) - != 0) - || (null_stderr - && (err = posix_spawn_file_actions_addopen (&actions, - STDERR_FILENO, - "/dev/null", O_RDWR, - 0)) - != 0) - || (slave_process - && ((err = posix_spawnattr_init (&attrs)) != 0 - || (attrs_allocated = true, - (err = posix_spawnattr_setsigmask (&attrs, - &blocked_signals)) - != 0 - || (err = posix_spawnattr_setflags (&attrs, - POSIX_SPAWN_SETSIGMASK)) - != 0))) - || (err = posix_spawnp (&child, prog_path, &actions, - attrs_allocated ? &attrs : NULL, prog_argv, - environ)) - != 0)) + (null_stdin + && (err = posix_spawn_file_actions_addopen (&actions, + STDIN_FILENO, + "/dev/null", O_RDONLY, + 0)) + != 0) + || (null_stdout + && (err = posix_spawn_file_actions_addopen (&actions, + STDOUT_FILENO, + "/dev/null", O_RDWR, + 0)) + != 0) + || (null_stderr + && (err = posix_spawn_file_actions_addopen (&actions, + STDERR_FILENO, + "/dev/null", O_RDWR, + 0)) + != 0) + || (slave_process + && ((err = posix_spawnattr_init (&attrs)) != 0 + || (attrs_allocated = true, + (err = posix_spawnattr_setsigmask (&attrs, + &blocked_signals)) + != 0 + || (err = posix_spawnattr_setflags (&attrs, + POSIX_SPAWN_SETSIGMASK)) + != 0))) + || (err = posix_spawnp (&child, prog_path, &actions, + attrs_allocated ? &attrs : NULL, prog_argv, + environ)) + != 0)) { if (actions_allocated) - posix_spawn_file_actions_destroy (&actions); + posix_spawn_file_actions_destroy (&actions); if (attrs_allocated) - posix_spawnattr_destroy (&attrs); + posix_spawnattr_destroy (&attrs); if (slave_process) - unblock_fatal_signals (); + unblock_fatal_signals (); if (termsigp != NULL) - *termsigp = 0; + *termsigp = 0; if (exit_on_error || !null_stderr) - error (exit_on_error ? EXIT_FAILURE : 0, err, - _("%s subprocess failed"), progname); + error (exit_on_error ? EXIT_FAILURE : 0, err, + _("%s subprocess failed"), progname); return 127; } posix_spawn_file_actions_destroy (&actions); @@ -270,7 +272,7 @@ execute (const char *progname, } return wait_subprocess (child, progname, ignore_sigpipe, null_stderr, - slave_process, exit_on_error, termsigp); + slave_process, exit_on_error, termsigp); #endif }