diff options
author | Andrew J. Schorr <aschorr@telemetry-investments.com> | 2013-07-04 16:26:51 -0400 |
---|---|---|
committer | Andrew J. Schorr <aschorr@telemetry-investments.com> | 2013-07-04 16:26:51 -0400 |
commit | ad5c8d1f818c96579fa9e7f3c691739e9761e1e7 (patch) | |
tree | e46d7c0d5492318cf7eacd60ae36036fd030f927 | |
parent | d8bd9f5261761dd4ffca331d9c6055c48a0a332b (diff) | |
download | egawk-ad5c8d1f818c96579fa9e7f3c691739e9761e1e7.tar.gz egawk-ad5c8d1f818c96579fa9e7f3c691739e9761e1e7.tar.bz2 egawk-ad5c8d1f818c96579fa9e7f3c691739e9761e1e7.zip |
Revert incorrect patch to wait_any and instead use waitpid to avoid blocking.
-rw-r--r-- | ChangeLog | 10 | ||||
-rw-r--r-- | configh.in | 3 | ||||
-rwxr-xr-x | configure | 2 | ||||
-rw-r--r-- | configure.ac | 2 | ||||
-rw-r--r-- | io.c | 20 |
5 files changed, 31 insertions, 6 deletions
@@ -1,3 +1,13 @@ +2013-07-04 Andrew J. Schorr <aschorr@telemetry-investments.com> + + * configure.ac (AC_CHECK_FUNCS): Add a check for waitpid. + * io.c (wait_any): Enhance comment to explain why we loop reaping all + exited children when the argument is zero. When available, use waitpid + with WNOHANG to avoid blocking. Remove my previous incorrect patch to + exit after reaping the first child. The function is intended to + wait for all children, since we are not careful about reaping children + as soon as they die. + 2013-07-02 Andrew J. Schorr <aschorr@telemetry-investments.com> * gawkapi.h (gawk_api): Remove unused api_lookup_file hook. @@ -296,6 +296,9 @@ /* Define to 1 if you have the `vprintf' function. */ #undef HAVE_VPRINTF +/* Define to 1 if you have the `waitpid' function. */ +#undef HAVE_WAITPID + /* Define to 1 if you have the <wchar.h> header file. */ #undef HAVE_WCHAR_H @@ -10020,7 +10020,7 @@ for ac_func in atexit btowc fmod getgrent getgroups grantpt \ memcmp memcpy memcpy_ulong memmove memset \ memset_ulong mkstemp posix_openpt setenv setlocale setsid snprintf strchr \ strerror strftime strncasecmp strcoll strtod strtoul \ - system tmpfile towlower towupper tzset usleep wcrtomb \ + system tmpfile towlower towupper tzset usleep waitpid wcrtomb \ wcscoll wctype do : as_ac_var=`$as_echo "ac_cv_func_$ac_func" | $as_tr_sh` diff --git a/configure.ac b/configure.ac index b401cb40..ba242c51 100644 --- a/configure.ac +++ b/configure.ac @@ -276,7 +276,7 @@ AC_CHECK_FUNCS(atexit btowc fmod getgrent getgroups grantpt \ memcmp memcpy memcpy_ulong memmove memset \ memset_ulong mkstemp posix_openpt setenv setlocale setsid snprintf strchr \ strerror strftime strncasecmp strcoll strtod strtoul \ - system tmpfile towlower towupper tzset usleep wcrtomb \ + system tmpfile towlower towupper tzset usleep waitpid wcrtomb \ wcscoll wctype) dnl this check is for both mbrtowc and the mbstate_t type, which is good AC_FUNC_MBRTOWC @@ -2168,7 +2168,16 @@ use_pipes: #ifndef PIPES_SIMULATED /* real pipes */ -/* wait_any --- wait for a child process, close associated pipe */ +/* + * wait_any --- if the argument pid is 0, wait for all child processes that + * have exited. We loop to make sure to reap all children that have exited to + * minimize the risk of running out of process slots. Since we don't process + * SIGCHLD, we do not immediately reap exited children. So when we get here, + * we want to reap any that have piled up. + * + * Note: on platforms that do not support waitpid with WNOHANG, when called with + * a zero argument, this function will hang until all children have exited. + */ static int wait_any(int interesting) /* pid of interest, if any */ @@ -2198,7 +2207,11 @@ wait_any(int interesting) /* pid of interest, if any */ hstat = signal(SIGHUP, SIG_IGN); qstat = signal(SIGQUIT, SIG_IGN); for (;;) { -# ifdef HAVE_SYS_WAIT_H /* POSIX compatible sys/wait.h */ +# if defined(HAVE_WAITPID) && defined(WNOHANG) + if ((pid = waitpid(-1, & status, WNOHANG)) == 0) + /* No children have exited */ + break; +# elif defined(HAVE_SYS_WAIT_H) /* POSIX compatible sys/wait.h */ pid = wait(& status); # else pid = wait((union wait *) & status); @@ -2210,13 +2223,12 @@ wait_any(int interesting) /* pid of interest, if any */ if (pid == redp->pid) { redp->pid = -1; redp->status = status; - goto finished; + break; } } if (pid == -1 && errno == ECHILD) break; } -finished: signal(SIGHUP, hstat); signal(SIGQUIT, qstat); #endif |