linux - 如果父进程收集终止状态失败一次,内核将再次尝试发送 SIGCHLD

标签 linux process linux-kernel parent-child zombie-process

当父进程未能收集到系统(Kernel)通过SIGCHLD发送的子进程的终止状态时,子进程成为僵尸进程。

系统是否再次尝试发送此进程终止状态,以便父进程尝试收集其子进程的退出状态?

会不会发生这种情况,僵尸进程会从进程表中移除?

parent 是否再次尝试读取其 child 的终止状态?

最佳答案

When a parent process fails to collect the termination status of its child process send by system(Kernel) through SIGCHLD, the child process becomes a Zombie process.

这在技术上并不准确。僵尸进程不是其父进程未能获取其终止状态的进程 - 相反,它是一个已经终止但尚未获得其终止状态的进程。

因此,当 SIGCHLD 在父进程中传递时,该进程已经是一个僵尸进程,因为它终止了,但终止状态尚未获得。

重点是,SIGCHLD 在这里有点无关紧要:父进程获取子进程的终止状态,或者没有,在这种情况下,子进程仍然是僵尸。

Does System try again to send this process termination status for the parent process to try collecting the exit status of its child?

没有。 SIGCHLD 只传递一次。如果父进程没有在信号处理程序中获得僵尸的终止状态(这不是必需的),那么它要么稍后这样做(在程序代码中的某个时刻),要么不这样做而终止(在这种情况下, zombie 的父进程成为 init 进程;init 周期性地获取孤儿的状态来清理 zombies)。

Will such thing happen and zombie process will be removed from the process table?

一旦父进程获得退出状态,僵尸进程使用的资源就会被释放。

OTOH,如果 SIGCHLD 被显式忽略(即通过将其配置更改为 SIG_IGN),将不会有僵尸进程,因为忽略 SIGCHLD恰恰阻止了这一点。但是,将无法获得终止状态。

来自 man 2 sigaction:

POSIX.1-1990 disallowed setting the action for SIGCHLD to SIG_IGN.

POSIX.1-2001 allows this possibility, so that ignoring SIGCHLD can be used to prevent the creation of zombies (see wait(2)).

最后:

Does the parent try again to read this termination status of its child?

一般来说,一旦父级收集了僵尸的退出状态,再次尝试这样做会导致错误。正如我之前所说,获取僵尸的终止状态将释放僵尸正在使用的所有资源,因此您不能多次获取终止状态。

此规则的异常(exception)情况是 WNOWAIT 标志被传递给 waitid(2)。该标志收集子进程的终止状态并使其处于可等待状态;可以在同一进程上再次使用稍后的调用来获取终止状态。

关于linux - 如果父进程收集终止状态失败一次,内核将再次尝试发送 SIGCHLD,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31832224/

相关文章:

linux - 使用 Ansible 查找具有特定复制日期的文件

c - mmap、msync 和 linux 进程终止

linux - linux shell 中的管道管理

Linux 文本编辑器临时文件搜索

c - 用于测试、报告或调试的 GLib/GObject 拦截错误/结构代码

Java单进程多线程

windows - 获取有关 Windows 上其他进程的信息

linux - 产生中断(调用irqfd)如何在KVM虚拟机上调用中断?

linux - 设备驱动程序不工作

linux - 如何在 makefile 中指定将结果发送到哪里