在Python中处理SIGTERM时阻塞SIGUSR1(sigaction(2)的sa_掩码)
sigaction(2)调用有一个mask参数,允许在处理信号时阻止其他不同类型的信号在Python中处理SIGTERM时阻塞SIGUSR1(sigaction(2)的sa_掩码),python,signals,Python,Signals,sigaction(2)调用有一个mask参数,允许在处理信号时阻止其他不同类型的信号 在处理SIGTERM时,我希望SIGUSR1被阻止。Python信号模块似乎没有sigaction调用,只有一个函数来阻止信号(这将导致竞争条件)。如何为处理程序设置此块掩码?Python信号处理程序不会在低级(C)信号处理程序中执行。相反,低级信号处理程序设置一个标志,告诉虚拟机在稍后的时间点(例如在下一个字节码指令)执行相应的Python信号处理程序 因此,尝试阻止是没有意义的。虽然它有点让它被封锁了:
在处理SIGTERM时,我希望SIGUSR1被阻止。Python信号模块似乎没有sigaction调用,只有一个函数来阻止信号(这将导致竞争条件)。如何为处理程序设置此块掩码?Python信号处理程序不会在低级(C)信号处理程序中执行。相反,低级信号处理程序设置一个标志,告诉虚拟机在稍后的时间点(例如在下一个字节码指令)执行相应的Python信号处理程序 因此,尝试阻止是没有意义的。虽然它有点让它被封锁了:
from ctypes import Structure, POINTER, CFUNCTYPE, CDLL, byref, get_errno, \
sizeof, c_int, c_long, c_ulong, c_void_p
from ctypes.util import find_library
from typing import Callable
class SIGSET_T(Structure):
_fields_ = [
("__val", c_ulong * (1024 // (8 * sizeof(c_long)))),
]
SA_HANDLER_FUNCTYPE = CFUNCTYPE(None, c_int, use_errno=True)
class SIGACTION(Structure):
_fields_ = [
("sa_handler", SA_HANDLER_FUNCTYPE),
("sa_mask", SIGSET_T),
("sa_flags", c_int),
("sa_restorer", c_void_p),
]
libc = CDLL(find_library('c'), use_errno=True)
def sigaction(signal, sighandler: Callable[[int], None], masked_signals=None):
"""Change the action taken by a process on receipt
of a specific signal.
A partial Python wrapper for the sigaction(2) function.
:param signal: a signal value (from the signal module)
:param sighandler: handler to install
:param masked_signals: list of other signals to block while handling
:raises: OSError if a library call fails
"""
action = SIGACTION(sa_handler=SA_HANDLER_FUNCTYPE(sighandler))
for maksed_signal in (masked_signals or []):
if libc.sigaddset(byref(action.sa_mask), maksed_signal.value) != 0:
if get_errno() != 0:
raise OSError(get_errno())
if libc.sigaction(signal.value, byref(action), None) != 0:
if get_errno() != 0:
raise OSError(get_errno())