发送信号

singal.pause

  • 暂停 进程 等待接受信号

    • 即,休眠进程

signal.alarm

  • 计时功能

    • 在给定时间之后,发出 singal.SIGAlRM 信号(默认结束进程)
    • 多个 singal.alarm 覆盖前面的
  • 取值

    • 正值,设置计时时间
    • 0,取消计时

获取信号处理函数

signal.getsignal

1
2
3
4
signal.getsignal(<Signal Number>)

# 例子
singal.getsignal(singal.SIGINT)

设置信号处理函数

signal.singal

1
Signal.singal(<signal number>, <handler function>)

处理函数的取值

  • 函数签名如: handler(signum, frame) 的函数

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    
    import signal, os
    
    def handler(signum, frame):
        print('Signal handler called with signal', signum)
        raise OSError("Couldn't open device!")
    
    # Set the signal handler and a 5-second alarm
    signal.signal(signal.SIGALRM, handler)
    signal.alarm(5)
    
    # This open() may hang indefinitely
    fd = os.open('/dev/ttyS0', os.O_RDWR)
    
    signal.alarm(0)          # Disable the alarm
  • 两种特殊取值

    singal.SIG_IGN
    ignore 忽略信号
    signal.SIG_DFL
    默认处理方式

注意

  • SIGSTOPSIGKILL 不能处理

终止整个进程组

  • 使用 os.killpg()

    1
    2
    3
    4
    5
    
    def term(sig_num, addtion):
        print current pid is %s, group id is %s % (os.getpid(), os.getpgrp())
        os.killpg(os.getpgid(os.getpid()), signal.SIGKILL)
    
    signal.signal(signal.SIGTERM, term)
  • 获取进程组 id pgid

    • os.getpgid(os.getpid())
  • 杀死进程组

    • os.killpg(<进程组id>, <singal 信号>)

对子进程控制 使用 psutil.Process

  • 第三方模块 psutil

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    
    import signal
    import logging
    
    import psutil
    from tornado import ioloop
    
    log = logging.getLogger(__name__)
    pid = psutil.Process(os.getpid())
    
    def stop_handler(*args, **kwargs):
        io_loop = ioloop.IOLoop.current()
    
        try:
            for children_pid in pid.get_children():
            children_pid.send_signal(signal.SIGINT)
    
            io_loop.add_callback_from_signal(io_loop.stop)
        except Exception as exc:
            log.exception(exc)
    
    signal.signal(signal.SIGINT, stop_handler)
    signal.signal(signal.SIGQUIT, stop_handler)
    signal.signal(signal.SIGTERM, stop_handler)
  • 方法

    • 使用 process.children() 获取所有子进程
    • 使用 process.send_signal 发送信号