目前,我的用户抱怨我的应用程序终止时遇到问题。在某些(看似随意的)条件和桌面环境下,应用程序不会终止,并且设置不会在重启时保存。我在相关的 irc 频道中询问,大部分时间我都被告知要正确处理信号。我知道终端中 Ctrl-C 的 SIGINT 和“正常”终止的 SIGTERM。但有人告诉我 SIGHUP 也很重要。所以我的问题是:
我必须处理哪些信号才能构建性能良好的应用程序?
https://en.wikipedia.org/wiki/Unix_signal
有一个标准信号及其默认操作的列表。任何有足够特权的进程总是可以向您发送任何信号,但进程(或您,通过进程)不应该这样做。
您应该只kill
使用并期望您的进程使用kill
TERM和可由您的环境(shell、终端驱动程序)生成的一堆信号,除非您知道目标处理您想要发送的特殊信号。
您可以按操作对基本信号进行排序。
核心转储信号
ABRT TRAP SYS BUS FPE ILL SEGV XFSZ XCPU QUIT
Run Code Online (Sandbox Code Playgroud)
要么是由您(TRAP、ABRT、SYS)使用某些专用函数生成的,要么是由您进入硬错误状态(BUS、FPE、ILL、SEGV)生成的。
QUIT
由用户在想要核心转储的终端上生成 ( C+\
)。
您可能希望将它们保留为默认配置。
在终止信号之外:
HUP INT PIPE TERM ALRM POLL PROF USR1 USR2
Run Code Online (Sandbox Code Playgroud)
你应该期待
HUP INT PIPE TERM
Run Code Online (Sandbox Code Playgroud)
根据您的环境在不同情况下的情况:
HUP -- when the terminal hungs up or you become a stopped orphaned process
INT -- when the user at the terminal interrupts you with C-c
PIPE -- when a PIPE or socket you write into closes, e.g. by
exiting before you finished writing to it
(`yourprogram | (exit)` will give you a `PIPE`
if yourprogram attempts to write to its STDOUT)
TERM -- when a process ends you a normal termination request
Run Code Online (Sandbox Code Playgroud)
仅当您自己设置时,您才应该收到其余的终止信号。
杀戮和阻止你无能为力。
您可能希望拦截终端生成的停止信号:
TTIN -- you read from the terminal and you're a backgrounded process
TTOU -- you write the terminal when you're a backgrounded process
and the terminal is set to put you to sleep when you do
TSTP -- you're being put to sleep with `C-Z`
Run Code Online (Sandbox Code Playgroud)
但最坏的情况是,这些只会停止您的进程,而不会破坏您的状态。
除非您知道需要处理CHLD
、CONT
、 或URG
,否则您不需要。
长话短说:
基本上,我认为如果您通常想要进行一些退出前清理,则应该处理(或忽略)HUP、INT、PIPE 和 TERM。其余的可以不用管,除非你的程序使用这些信号,或者除非你在所有情况下都绝对需要一些清理。
在后一种情况下,您可以空白地阻止所有未处理的信号,但要注意信号阻止掩码会在 fork 和 execve 调用之间继承,并忽略或阻止像 ILL 这样的信号(如果它们是在进程运行时产生的并且没有发送给您)通过kill 或sigqueue 会给你未定义的行为。
如果您想了解更多信息,请浏览联机帮助页和标准。信号在 Unix 上是一个相当大的话题,处理它们可能会变得非常棘手。
归档时间: |
|
查看次数: |
1307 次 |
最近记录: |