The Perl Cookbook advises being paranoid and always
reinstalling your SIG handler as the first step of
your signal handler except in the case of SIGCHLD for
the following reason:
If you re-install the SIGCHLD handler before wait or waitpid
gets its information from the OS's process table you risk the child
becoming a zombie. Recomended is the following:
Loop in the SIGCHLD handler and only re-install the SIGCHLD handler after the loop is complete (code below taken from Perl Cookbook).
$SIG{CHLD}=\&REAPER;
sub REAPER{
my $stiff;
while(($stiff = waitpid(-1,&WNOHANG))>0){
# do something with $stiff if you want
}
$SIG{CHLD}=\&REAPER;
}
This is necessary because most OSes will not queue up signals
so if 2 are sent to your process at aprox the same time your process may
behave as if it has received only 1.
This may point to a possible solution to the original problem:
$SIG{CHLD}=\&REAPER;
sub REAPER{
$SIG{CHLD}='IGNORE';
my $stiff;
while(($stiff = waitpid(-1,&WNOHANG))>0){
# do something with $stiff if you want
}
$SIG{CHLD}=\&REAPER;
}
For a detailed discussion see sections 6.17 thru 6.19
(espscially 6.19) of
the Perl Cookbook. |