diff options
author | Doug Evans <dje@google.com> | 2011-12-14 20:53:57 +0000 |
---|---|---|
committer | Doug Evans <dje@google.com> | 2011-12-14 20:53:57 +0000 |
commit | 0b6cb71e500807ed48bc5317bb7ec03b073fc0a0 (patch) | |
tree | 876bb7834ffd9b4d1c81f8b97feb39731a6a6664 /gdb/utils.c | |
parent | afaabefa90aba4f0e37e7ed865ccd64b66dfa354 (diff) | |
download | gdb-0b6cb71e500807ed48bc5317bb7ec03b073fc0a0.zip gdb-0b6cb71e500807ed48bc5317bb7ec03b073fc0a0.tar.gz gdb-0b6cb71e500807ed48bc5317bb7ec03b073fc0a0.tar.bz2 |
* defs.h (wait_to_die_with_timeout): Declare.
* utils.c: #include "gdb_wait.h".
(sigalrm_handler, wait_to_die_with_timeout): New functions.
* ser-pipe.c: Don't #include "gdb_wait.h".
(pipe_close): Give child a chance to die on its own after closing
its stdin before SIGTERM'ing it.
Diffstat (limited to 'gdb/utils.c')
-rw-r--r-- | gdb/utils.c | 73 |
1 files changed, 73 insertions, 0 deletions
diff --git a/gdb/utils.c b/gdb/utils.c index cc93915..16405d1 100644 --- a/gdb/utils.c +++ b/gdb/utils.c @@ -24,6 +24,7 @@ #include "gdb_assert.h" #include <ctype.h> #include "gdb_string.h" +#include "gdb_wait.h" #include "event-top.h" #include "exceptions.h" #include "gdbthread.h" @@ -3784,6 +3785,78 @@ producer_is_gcc_ge_4 (const char *producer) return minor; } +#ifdef HAVE_WAITPID + +#ifdef SIGALRM + +/* SIGALRM handler for waitpid_with_timeout. */ + +static void +sigalrm_handler (int signo) +{ + /* Nothing to do. */ +} + +#endif + +/* Wrapper to wait for child PID to die with TIMEOUT. + TIMEOUT is the time to stop waiting in seconds. + If TIMEOUT is zero, pass WNOHANG to waitpid. + Returns PID if it was successfully waited for, otherwise -1. + + Timeouts are currently implemented with alarm and SIGALRM. + If the host does not support them, this waits "forever". + It would be odd though for a host to have waitpid and not SIGALRM. */ + +pid_t +wait_to_die_with_timeout (pid_t pid, int *status, int timeout) +{ + pid_t waitpid_result; + + gdb_assert (pid > 0); + gdb_assert (timeout >= 0); + + if (timeout > 0) + { +#ifdef SIGALRM +#if defined (HAVE_SIGACTION) && defined (SA_RESTART) + struct sigaction sa, old_sa; + + sa.sa_handler = sigalrm_handler; + sigemptyset (&sa.sa_mask); + sa.sa_flags = 0; + sigaction (SIGALRM, &sa, &old_sa); +#else + void (*ofunc) (); + + ofunc = (void (*)()) signal (SIGALRM, sigalrm_handler); +#endif + + alarm (timeout); +#endif + + waitpid_result = waitpid (pid, status, 0); + +#ifdef SIGALRM + alarm (0); +#if defined (HAVE_SIGACTION) && defined (SA_RESTART) + sigaction (SIGALRM, &old_sa, NULL); +#else + signal (SIGALRM, ofunc); +#endif +#endif + } + else + waitpid_result = waitpid (pid, status, WNOHANG); + + if (waitpid_result == pid) + return pid; + else + return -1; +} + +#endif /* HAVE_WAITPID */ + /* Provide a prototype to silence -Wmissing-prototypes. */ extern initialize_file_ftype _initialize_utils; |