[bind10-dev] shutdown problem

Shane Kerr shane at isc.org
Mon Oct 18 11:12:11 UTC 2010


Jeremy,

On Fri, 2010-10-15 at 11:44 -0500, Jeremy C. Reed wrote: 
> On Fri, 15 Oct 2010, Shane Kerr wrote:
> 
> > So, I'd like to propose a general BIND 10 policy that most processes
> > should only catch SIGINT, and that with SIG_IGN, unless there is a
> > specific reason for handling other signals.
> 
> I often run the components individually for quickly testing them 
> (without running bind10 parent process). I normally just press Ctrl-C to 
> stop. I don't need to do this as I can fall back to "kill" instead. (Or 
> use bindctl with shutdown in some cases.)

Okay, this is a good reason to let processes continue to receive SIGINT.

My new proposal is:

        Processes should not catch any signals unless there is a
        specific reason.

:)

Some more details about SIGINT below...

> I may not understand, but I thought if running with bind10 parent, the 
> SIGINT would never be seen my the child anyways. (I don't understand why 
> to ignore for each component.)

It's a bit more complicated than that. Here's an excerpt from the NOTES
section of the "setpgrp" man page in Linux:

       A  session can have a controlling terminal.  At any time, one
       (and only one) of the process groups in the  session  can  be
       the  foreground process group for the terminal; the remaining
       process groups are in the background.  If a signal is  gener‐
       ated  from  the  terminal  (e.g., typing the interrupt key to
       generate SIGINT), that  signal  is  sent  to  the  foreground
       process  group.   (See  termios(3)  for  a description of the
       characters  that  generate  signals.)   Only  the  foreground
       process  group may read(2) from the terminal; if a background
       process group tries to read(2) from the  terminal,  then  the
       group  is  sent  a  SIGTSTP  signal,  which suspends it.  The
       tcgetpgrp(3) and tcsetpgrp(3) functions are used  to  get/set
       the foreground process group of the controlling terminal.

I wrote a little test program:

---------------------------------------------------------------
import signal
import os
import sys
import time

def handler(signum, frame):
    if signum == signal.SIGINT:
        print("\nprocess %d got SIGINT" % (os.getpid(),))
    else:
        print("\nprocess %d got %d" % (os.getpid(), signum))
    sys.exit(0)

signal.signal(signal.SIGINT, handler)
if os.fork() == 0:
    print("child is %d" % os.getpid())
    if len(sys.argv) > 1:
        print("running child in separate process group")
        os.setpgrp()
else:
    print("parent is %d" % os.getpid())

time.sleep(5)
print("process %d exiting" % os.getpid())
---------------------------------------------------------------

If you invoke this without arguments, it does not call "os.setpgrp()"
and you get:

---------------------------------------------------------------
shane at shane-asus-laptop:/tmp$ python test.py
parent is 6835
child is 6836
^C

process 6836 got SIGINT
process 6835 got SIGINT
---------------------------------------------------------------

If you invoke with arguments, it invokes "os.setpgrp()" and you get
(note that the child process exits after timeout in the background):

---------------------------------------------------------------
shane at shane-asus-laptop:/tmp$ python test.py foo
parent is 6843
child is 6844
running child in separate process group
^C
process 6843 got SIGINT
shane at shane-asus-laptop:/tmp$ process 6844 exiting
---------------------------------------------------------------

We don't currently use os.setpgrp(), but we should, then we don't have
it ignore SIG_INT and we won't have the problem with processes getting
restarted inappropriately by the boss.

I've made a ticket for this, #378, and coded up the change.

--
Shane 




More information about the bind10-dev mailing list