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

Allo monks, I have a strange, strange puzzle for you. I have a class library built that uses a symbolic reference for SIGTERM. Basically, its
$SIG{TERM} = "sigterm_handler";
I do this basically so each app that uses this class can have its own set sigterm handler.

Now, this is where the wierdness starts. First, I start up multiple instances of the same perl script which is using this class. They have different PIDS and PGIDs but the same PPIDs and SIDs.

Now I send a SIGTERM (basically "kill <pid>") to ANY of these processes.. and the rest also receives the SIGTERM! I'm fairly sure its a clean SIGTERM exit because I log in the handler. But now if I remove the sym ref in the class, this DOESN'T happen.

This is just so odd to me. How would sending a SIGTERM to one process propagate to another? I need help.. and an Advil.

TIA
Mike

Replies are listed 'Best First'.
Re: wierd wierd behavior with SIGTERM and classes
by steves (Curate) on Feb 28, 2002 at 21:53 UTC

    On UNIX systems, signals are subject to rules defined by process groups, process group leaders, and controlling terminals. There are a number of write-ups on this you should read up on.

    SIGTERM is a signal that gets propogated to a process group. The common example is if your shell goes away, then any processes it started also die. A process can disassociate itself from its parent process group and become a true daemon by making certain system calls. These are often UNIX-specific. At my first job (C programming) we wrote a daemonize function that hid these details. That code was lifted almost directly out of the book UNIX Network Progamming by Richard Stevens.

      I have been reading a few articles on it and have to elaborate some.

      First, it's a Solaris 5.6 box with perl 5.6.0. Also, I've run other scripts that uses this class almost identically and this behavior doesn't happen. That is what's baffling and I'm not sure where to look. I'm not too sure about your theory of kill sending SIGTERM to an entire group. I found this little writeup that basically says, you make the number negative to send to a group. I'm definately not sending it negative.

      kill

      Specifies a decimal integer representing a process or process group to be signaled. If PID is a positive value, the kill command sends the process whose process ID is equal to the PID. If the PID value is 0, the kill command sends the signal to all processes having a process group ID equal to the process group ID of the sender. The signal is not sent to processes with a PID of 0 or 1. If the PID is -1, the kill command sends the signal to all processes owned by the effective user of the sender. The signal is not sent to processes with a PID of 0 or 1. If it is a negative number but not -1, the kill command sends the signal to all processes that have a process group ID equal to the absolute value of the PID. -l Lists all signal names supported by the implementation

Re: wierd wierd behavior with SIGTERM and classes
by bluto (Curate) on Mar 01, 2002 at 00:06 UTC
    It sure does sound like the signal is getting sent to the entire process group (for whatever strange reason). If you just need a work around and the children don't need to be in the same process group, just have the child move itself into a new process group with setpgrp or see POSIX for setpgid or setsid (a man page on your system is probably a better description though). They are not very portable, but I think all of them are implemented on Solaris.

    bluto

      The thing is.. there aren't really any children involved. I'm starting each script up on the command line so each one is already in its own process group. And apparently, setsid() only works if your not a process leader.

      Another thing I just found was, killing the first instance of the script doesn't do anything but stop the first script. Killing the 2nd or 3rd kills all 3 but killing the first only kills that instance.

      This is just getting odder and odder.

        This is strange. Do you have more specifics? Such as the OS, the OS version, which shell, which version of Perl, and a sample of what the command line looks like starting these? If you also had a case where it fails like this along with the PID, PPID, SID, etc. of each one it would help.