|
Boost-Commit : |
From: kbelco_at_[hidden]
Date: 2008-02-08 11:32:35
Author: noel_belcourt
Date: 2008-02-08 11:32:35 EST (Fri, 08 Feb 2008)
New Revision: 43176
URL: http://svn.boost.org/trac/boost/changeset/43176
Log:
Force PPC Darwin to use fork instead of vfork. This change
requires both the parent and child process to explicitly set
the process group id. Vfork guarantees the child process
runs to the exec before it releases the parent process.
Now that we use fork instead of vfork, it's possible for the
parent to wait on the child process without having the child
setpgid on itself. This eliminates spurious hangs on ppc
darwin caused by either a race condition between vfork and
execvp, or a bug in the vfork implementation.
Added a test to ensure we don't try to read from the
stderr pipe descriptor if the descriptor's not valid.
Text files modified:
trunk/tools/jam/src/execunix.c | 20 ++++++++++++++------
1 files changed, 14 insertions(+), 6 deletions(-)
Modified: trunk/tools/jam/src/execunix.c
==============================================================================
--- trunk/tools/jam/src/execunix.c (original)
+++ trunk/tools/jam/src/execunix.c 2008-02-08 11:32:35 EST (Fri, 08 Feb 2008)
@@ -25,6 +25,10 @@
# ifdef USE_EXECUNIX
# include <sys/times.h>
+# if defined(__APPLE__) && defined(__ppc__)
+# define NO_VFORK
+# endif
+
# ifdef NO_VFORK
# define vfork() fork()
# endif
@@ -211,6 +215,8 @@
if ((cmdtab[slot].pid = vfork()) == 0)
{
+ int pid = getpid();
+
close(out[0]);
close(err[0]);
@@ -239,17 +245,19 @@
r_limit.rlim_max = globs.timeout;
setrlimit(RLIMIT_CPU, &r_limit);
}
- setpgid(cmdtab[slot].pid, cmdtab[slot].pid);
-
- execvp( argv[0], argv );
- _exit(127);
- }
+ setpgid(pid,pid);
+ execvp( argv[0], argv );
+ perror( "execvp" );
+ _exit(127);
+ }
else if( cmdtab[slot].pid == -1 )
{
perror( "vfork" );
exit( EXITBAD );
}
+ setpgid(cmdtab[slot].pid, cmdtab[slot].pid);
+
/* close write end of pipes */
close(out[1]);
close(err[1]);
@@ -458,7 +466,7 @@
if (FD_ISSET(cmdtab[i].fd[OUT], &fds))
out = read_descriptor(i, OUT);
- if (FD_ISSET(cmdtab[i].fd[ERR], &fds))
+ if ((globs.pipe_action != 0) && (FD_ISSET(cmdtab[i].fd[ERR], &fds)))
err = read_descriptor(i, ERR);
/* if feof on either descriptor, then we're done */
Boost-Commit list run by bdawes at acm.org, david.abrahams at rcn.com, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk