[PATCH 3/5] Linux waitpid/__WALL emulation wrapper: If WNOHANG is set, don't touch sigprocmask.

Pedro Alves
2014-01-23T14:10:21Z

So the caller can use waitpid WNOHANG+sigsuspend. Otherwise,
my_waitpid lets the SIGCHLD handler run by mistake.
---
gdb/nat/linux-waitpid.c | 21 +++++++++++++--------
1 file changed, 13 insertions(+), 8 deletions(-)

diff --git a/gdb/nat/linux-waitpid.c b/gdb/nat/linux-waitpid.c
index e9e69db..4693120 100644
--- a/gdb/nat/linux-waitpid.c
+++ b/gdb/nat/linux-waitpid.c
@@ -92,15 +92,19 @@ my_waitpid (int pid, int *status, int flags)

wnohang = (flags & WNOHANG) != 0;
flags &= ~(__WALL | __WCLONE);
- flags |= WNOHANG;

- /* Block all signals while here. This avoids knowing about
- LinuxThread's signals. */
- sigfillset (&block_mask);
- sigprocmask (SIG_BLOCK, &block_mask, &org_mask);
+ if (!wnohang)
+ {
+ flags |= WNOHANG;
+
+ /* Block all signals while here. This avoids knowing about
+ LinuxThread's signals. */
+ sigfillset (&block_mask);
+ sigprocmask (SIG_BLOCK, &block_mask, &org_mask);

- /* ... except during the sigsuspend below. */
- sigemptyset (&wake_mask);
+ /* ... except during the sigsuspend below. */
+ sigemptyset (&wake_mask);
+ }

while (1)
{
@@ -129,7 +133,8 @@ my_waitpid (int pid, int *status, int flags)
flags ^= __WCLONE;
}

- sigprocmask (SIG_SETMASK, &org_mask, NULL);
+ if (!wnohang)
+ sigprocmask (SIG_SETMASK, &org_mask, NULL);
}
else
{
--
1.7.11.7