当前位置:  技术问答>linux和unix

忽略SIGCHLD信号能避免僵尸进程吗?

    来源: 互联网  发布时间:2016-08-25

    本文导语:  主程序要一直运行,会经常调用另一个程序,运行久了之后就看到很多僵尸进程,在网上看到有人说忽略SIGCHLD信号能避免僵尸进程,因为忽略SIGCHLD后僵尸进程会交给init管理,也有人说忽略SIGCHLD只会让僵尸进程越来越...

主程序要一直运行,会经常调用另一个程序,运行久了之后就看到很多僵尸进程,在网上看到有人说忽略SIGCHLD信号能避免僵尸进程,因为忽略SIGCHLD后僵尸进程会交给init管理,也有人说忽略SIGCHLD只会让僵尸进程越来越多。
麻烦各位说说你们的看法

|

这种方法,不是所有的操作系统都实现了。
前面的帖子有点问, 应该加一句:

void sig_chld(int signo)
{
        pid_t   pid;
        int     stat;

        signal(SIGCHLD, &sig_chld);
        while((pid = waitpid(-1, &stat, WNOHANG)) > 0) {
                printf("child %d terminatedn", pid);
        }
        return;


int main(void)
{
        int rc;

        rc = 0;
        signal(SIGCHLD, &sig_chld);
        return (rc);
}


|

部分源自System V的Unix(比如AIX)的signal()函数保留了原始Unix的不可靠信号的语意:
信号被捕获后,信号处理自动被重置为SIG_DEF,就好像调用了signal(SIGCHLD, SIG_DEF)一样,
而且不会屏蔽正在处理的信号。
所以,需要在信号处理函数内的开始重新安装信号处理函数
当然这里也存在一个时间窗,在进入信号处理函数后,调用signal之前又收到信号的话,如果这个信号
的缺省行为是结束进程的话,进程可能会意外终止。
当然在这里,SIGCHLD的缺省行为不会终止进程,但是由于信号处理函数被重置,还会留下zombie,

POSIX 的sigaction就提供和可靠信号:
1. 从不重置信号处理为SIG_DEF, 除非特别设置。
2. 在信号处理函数执行期间,自动屏蔽正在处理的信号,除非特别设置。

|

当然不是,除非这些僵尸的父进程结束。

|

加上后,如果在进入信号处理函数和调用signal(SIGCHLD, &sig_chld);之间
又几个子进程结束,可能会留下几个zombie, 但是,一旦signal(SIGCHLD, &sig_chld);调用
结束,又有子进程结束的话,
while((pid = waitpid(-1, &stat, WNOHANG)) > 0)
将会清除上次这些zombie. 这样就基本消除了zombie产生的可能性。

最好使用sigaction 代替signal, 可以完美的保证在支持(sigaction + waitpid)不会留下zombie.
实际上很多Unix系统上zombie是进程的必经阶段,是给父进程机会查看子进程的退出状态。
sigaction + waitpid 完全可以可靠的清除zombie,不要把自己的工作留给系统去做。
使用fork的服务器服务程序,会不断产生子进程,子进程完成任务后会退出,如果不清除zombie,
会缓慢消耗系统资源的。

|
忽略SIGCHILD后, 僵死进程并不一定会被INIT处理, 如果进程的父进程不是INIT

|
避免产生僵尸进程的方法一般有:
1. fork两次,使得孙子进程的父亲为init,孙子进程去执行job
2. 制定自己的SIGCHLD信号处理函数,在这个信号处理函数中调用wait()
3. 通过sigaction系统调用指定信号SIGCHLD处理动作中的sa_flags为SA_NOCLDWAIT

|
避免僵尸进程要父进程wait子进程 或者直接把子进程由INIT进程管理
总归要有个进程收尸
你的父进程一直在(无法让子进程被INIT进程收养),而又不给子进程收尸就会产生了。

LS很全面了

|
当父进程结束 这子进程就成了孤儿进程  INIT进程会领养  子进程结束就没了
这个只是在系统上有条记录,不占资源,等回收后连记录都没了。但是在有些调试状态会一直有
kill -9 PID可以杀掉 弄不好要有个记录 占用了一个进程ID而已,不碍事

    
 
 
 
本站(WWW.)旨在分享和传播互联网科技相关的资讯和技术,将尽最大努力为读者提供更好的信息聚合和浏览方式。
本站(WWW.)站内文章除注明原创外,均为转载、整理或搜集自网络。欢迎任何形式的转载,转载请注明出处。












  • 相关文章推荐
  • 如何在gdb调试中忽略自定义信号阿?
  • Linux下的信号忽略和信号阻塞是什么意思
  • C++ I/O 成员 ignore():读取字符并忽略指定字符
  • 好多输出调试代码,我想用一个宏忽略他可以吗?
  • grep -i忽略大小写的问题
  • POSIX.1要求system忽略SIGINT和SITQUIT,阻塞SIGCHLD,求解释。UNIX环境高级编程 system函数
  • 谁知道怎么能让 JTextArea忽略重复击键?多谢!
  • unix/linux知识 iis7站长之家
  • RegexOptions.IgnoreCase正则表达式替换,忽略大小写
  • find命令在查找时怎样忽略大小写??
  • expect脚本中用exec执行命令时如何忽略命令产生的错误?
  • javascript正则表达式容易被忽略的小问题整理
  • C#.NET字符串比较中忽略符号的方法
  • 分享MYSQL插入数据时忽略重复数据的方法
  • 我用getKeyTyped()得到当前按下的按键,想让不符合要求的按键忽略掉,像没按一样,不知怎么做
  • 请问用什么办法可以让String忽略空格和其它符号?
  • 浅析C++字节对齐容易被忽略的两个问题
  • 请问如何忽略interrupted system call
  • 一些很不错的css技巧,但也常为人们所忽略


  • 站内导航:


    特别声明:169IT网站部分信息来自互联网,如果侵犯您的权利,请及时告知,本站将立即删除!

    ©2012-2021,,E-mail:www_#163.com(请将#改为@)

    浙ICP备11055608号-3