slaniel has asked for the wisdom of the Perl Monks concerning the following question:

I have a script that calls out to a number of other scripts via system(). When I Ctrl+C any of the child processes, I want the parent process to handle that SIGINT. The problem is that when I Ctrl+C one of the child processes, the child process gets killed and we return to the flow of control in the parent process -- which then moves on to the next system() call. Instead, I want the parent process to die. The hack way to do this is to set the appropriate signal handler in each of the child scripts:
$SIG{'INT'} = sub { kill -9, getppid() };
which sends SIGKILL to the process's parent. But of course that doesn't scale: every time I create a new script, I'll have to add that handler in it. And if the parent process happens to not be the parent script -- e.g., if the parent process is a login shell -- that 'kill -9, getppid' has just killed my login shell. So what's the approach here, if I want the parent process to handle all the signals for its children?

Replies are listed 'Best First'.
Re: Get parent process to handle signals for its children?
by ikegami (Patriarch) on Jul 12, 2006 at 18:53 UTC
    Why don't you simply check how the child died before running the next system call? Refer to system's return value.

      For example, doing something along this lines:

      while (1) { print "sleeping\n"; system 'sleep', 2; warn "system: $!" if -1 == $?; my $signal_caught = $? & 127; die "Child got a SIGINT" if 2 == $signal_caught; }

      --
      David Serrano

        Oh, I see! I had forgotten about $?. That seems to get me most of the rest of what I want. Beautiful! Thanks so much for the clarification.
      That's certainly a good approach that gets me 90% of what I want. I'd still like to know whether the parent can handle signals for its children. It would also be nice to get more specific information than just system(foo) != 0; it would be nice to know that system() died when it handled a SIGINT. Is that doable?
        The value returned by system is composed of three fields. The exit value of the subprocess is $rv >> 8, $rv & 127 gives the signal (if any) from which the process died, and $rv & 128 reports whether or not there was a core dump.