SIG_IGN 关于 SIGFPE、SIGILL、SIGSEGV 的未定义行为的规范是否多余?

Is the specification of SIG_IGN's undefined behavior regarding SIGFPE, SIGILL, SIGSEGV redundant?

POSIX.1-2017 在 XSH 2.4.3 SIG_IGN 下指定

The behavior of a process is undefined after it ignores a SIGFPE, SIGILL, SIGSEGV, or SIGBUS signal that was not generated by kill(), sigqueue(), or raise().

我想知道强调部分的意义是什么?

你能忽略那些仅由上述函数产生的信号,同时避免调用未定义的行为吗?

换句话说,如果信号是由于硬件故障或陷阱而由内核生成的,则忽略此类信号具有未定义的行为。

如果您希望内核生成这些信号,您不应该 SIG_IGN-ore 这些信号。

您可以在 .sa_flags 中使用 sigactionSA_SIGINFO 捕获它们并使用 SA_SIGINFO 这样您就可以在处理程序中使用 info->si_code 来区分它们kernel-sent 和 user-sent 变体。 如果信号不是 kernel-sent 和 exit/abort 如果信号不是 exit/abort 那么你在处理程序中什么都不做,那么使用 SA_RESTART 处理程序你基本上得到了 [= 的用户空间模拟10=] 也适用于 kernel-sent SISGEVSIGILL

如果你使用真实 SIG_IGN,你必须注意不要激怒内核生成这些信号(没有无效的内存引用,没有无效的指令等)。

我认为 POSIX 允许您安全地忽略 SIGFPESIGILLSIGSEGVSIGBUS,因为没有充分的理由断然拒绝在所有情况下都忽略这些信号,但我认为该功能在其他情况下没有太大意义。

进程行为的未定义性质可能源于首先发送这些信号的原因。

如果您正在处理出于某种原因手动发送的假信号,则内核没有参与。

导致内核发送这些信号的情况也是进程有效“使保证无效”的情况。