[Date Prev][Date Next] [Thread Prev][Thread Next] [Date Index] [Thread Index]

Bug#132321: marked as done (manpages-dev: waitpid(2) does not return on signal)



Your message dated Thu, 8 Feb 2007 11:18:49 +0100
with message-id <20070208101849.GA4564@mad.intersec.eu>
and subject line manpages-dev: waitpid(2) does not return on signal
has caused the attached Bug report to be marked as done.

This means that you claim that the problem has been dealt with.
If this is not the case it is now your responsibility to reopen the
Bug report if necessary, and/or fix the problem forthwith.

(NB: If you are a system administrator and have no idea what I am
talking about this indicates a serious mail system misconfiguration
somewhere.  Please contact me immediately.)

Debian bug tracking system administrator
(administrator, Debian Bugs database)

--- Begin Message ---
Package: manpages-dev
Version: 1.39-1.1
Severity: normal
File: /usr/share/man/man2/waitpid.2.gz

The waitpid(2) man page says that:

The waitpid function suspends execution of the current process until
[...] a signal is delivered whose action is to [...] call a signal
handling function.

This is wrong.  The below program demonstrates that waitpid does in
fact *not* return when a signal is received, even though .  If that
was the case, the program should stop when the user presses ^C or
tries to kill it with kill(1).  The only thing that happens when I try
it is that it prints what signal it has received; the waitpid() call
never returns.

#include <sys/types.h>
#include <sys/wait.h>
#include <sys/types.h>
#include <unistd.h>
#include <stdlib.h>
#include <signal.h>
#include <stdio.h>

void sighandler(int signalNo)
{
   printf("Got signal %d\n", signalNo);
}

int main(int argc, char *argv[])
{
   signal(SIGUSR1, sighandler);
   signal(SIGTERM, sighandler);
   signal(SIGINT, sighandler);
   
   if (fork() == 0) {
      // This is the child process
      while (1) {
         usleep(1000000);
      }
   }

   waitpid(-1, NULL, WUNTRACED);
   
   return 0;
}


-- System Information
Debian Release: 3.0
Architecture: i386
Kernel: Linux barbara 2.4.16-686 #1 Wed Nov 28 09:27:17 EST 2001 i686
Locale: LANG=sv_SE.ISO-8859-1, LC_CTYPE=sv_SE.ISO-8859-1

Versions of packages manpages-dev depends on:
ii  manpages                      1.39-1.1   Man pages about using a Linux syst



--- End Message ---
--- Begin Message ---
On Mon, Feb 04, 2002 at 02:46:16PM +0100, Johan Walles wrote:
> Package: manpages-dev
> Version: 1.39-1.1
> Severity: normal
> File: /usr/share/man/man2/waitpid.2.gz
> 
> The waitpid(2) man page says that:
> 
> The waitpid function suspends execution of the current process until
> [...] a signal is delivered whose action is to [...] call a signal
> handling function.
> 
> This is wrong.  The below program demonstrates that waitpid does in
> fact *not* return when a signal is received, even though .  If that
> was the case, the program should stop when the user presses ^C or
> tries to kill it with kill(1).  The only thing that happens when I try
> it is that it prints what signal it has received; the waitpid() call
> never returns.
> 
> #include <sys/types.h>
> #include <sys/wait.h>
> #include <sys/types.h>
> #include <unistd.h>
> #include <stdlib.h>
> #include <signal.h>
> #include <stdio.h>
> 
> void sighandler(int signalNo)
> {
>    printf("Got signal %d\n", signalNo);
> }
> 
> int main(int argc, char *argv[])
> {
>    signal(SIGUSR1, sighandler);
>    signal(SIGTERM, sighandler);
>    signal(SIGINT, sighandler);
>    
>    if (fork() == 0) {
>       // This is the child process
>       while (1) {
>          usleep(1000000);
>       }
>    }
> 
>    waitpid(-1, NULL, WUNTRACED);
>    
>    return 0;
> }

  Since then the waitpid(2) manpage explains that you must ensure that
the signal SA_RESTART is not on, which seems to be the case by default,
with the following testcase, code works:

===================================
#include <signal.h>
#include <stdio.h>
#include <stdbool.h>
#include <sys/types.h>
#include <unistd.h>

void handler(int foo)
{
    printf("got signal %d\n", foo);
}

int main(void) {
    pid_t father = getpid();
    pid_t pid;
    struct sigaction sa;
    int st, res;

    signal(SIGUSR1, &handler);
    sigaction(SIGUSR1, NULL, &sa);
    sa.sa_flags &= ~SA_RESTART;
    sigaction(SIGUSR1, &sa, NULL);

    pid = fork();
    if (pid == 0) {
        while (true) {
            sleep(1);
            kill(father, SIGUSR1);
        }
    }

    res = waitpid(pid, &st, 0);
    puts("works OK !");
    kill(pid, SIGKILL);
    return 0;
}
===================================

$ ./test
got signal 10
works OK !

and strace shows:

    wait4(4668, 0x7fffe39b047c, 0, NULL)    = ? ERESTARTSYS (To be restarted)
    --- SIGUSR1 (User defined signal 1) @ 0 (0) ---
    fstat(1, {st_mode=S_IFCHR|0620, st_rdev=makedev(136, 15), ...}) = 0
    mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x2b2ec7111000
    write(1, "got signal 10\n", 14got signal 10
    )         = 14
    rt_sigreturn(0x1)                       = -1 EINTR (Interrupted system call)


so deactivating SA_RESTART for SIGUSR1 give the intended behaviour as
specified per documentation.

  Hence closing the bug.


-- 
·O·  Pierre Habouzit
··O                                                madcoder@debian.org
OOO                                                http://www.madism.org

Attachment: pgpZTOVosr6dH.pgp
Description: PGP signature


--- End Message ---

Reply to: