免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
12
最近访问板块 发新帖
楼主: nightfall
打印 上一主题 下一主题

子进程退出父进程没有收到SIGCHLD? [复制链接]

论坛徽章:
0
11 [报告]
发表于 2006-02-17 17:43 |只看该作者
to assiss :

我在信号处理函数中把一个全局变量child累加,没有printf
父进程在创建完子进程后开始for循环:
for(; 1;
{
      if ( child > 9 )
     {
         printf("all child process exited\n";
          break;
      }
}

结果是程序进入死循环,没有任何输出,为什么?

论坛徽章:
0
12 [报告]
发表于 2006-02-17 19:37 |只看该作者
原帖由 nightfall 于 2006-2-17 17:43 发表
to assiss :

我在信号处理函数中把一个全局变量child累加,没有printf
父进程在创建完子进程后开始for循环:
for(; 1;
{
      if ( child > 9 )
     {
         printf("all child process ...

我前面的表达有些混乱,

当你在信号处理函数里改变全局、静态局部变量的时候,实际上就已经使得该函数不可重入了。标准IO库函数之所以大部分不可重入,正是因为它们以不可重入的方式(比如修改变量)利用大量的全局变量。

论坛徽章:
0
13 [报告]
发表于 2006-02-18 09:51 |只看该作者
【APUE】8.6. wait and waitpid Functions:
传统上,这两个函数(指wait和waitpid)返回的整数状态是由具体实现方案自己定义的,其中某些bit表示退出状态(对于正常返回),某些bit则用于表示信号的数值(对于非正常返回),一个bit用于表示是否产生了core文件,等等。POSIX.1规定终止状态应该使用<sys/wait.h>中定义的多个宏来查看。其中有4个互斥的宏可以告诉我们进程是如何终止的,它们的名字都以WIF开始。基于这4个宏中的哪个为真,然后再使用其它的宏来取得退出状态,信号数值等信息。

sys/wait.h:
  1. /*
  2. * Macros to test the exit status returned by wait and extract the relevant
  3. * values.
  4. */
  5. #if __BSD_VISIBLE
  6. #define        WCOREFLAG        0200
  7. #endif
  8. #define        _W_INT(i)        (i)

  9. #define        _WSTATUS(x)        (_W_INT(x) & 0177)
  10. #define        _WSTOPPED        0177                /* _WSTATUS if process is stopped */
  11. #define        WIFSTOPPED(x)        (_WSTATUS(x) == _WSTOPPED)
  12. #define        WSTOPSIG(x)        (_W_INT(x) >> 8)
  13. #define        WIFSIGNALED(x)        (_WSTATUS(x) != _WSTOPPED && _WSTATUS(x) != 0)
  14. #define        WTERMSIG(x)        (_WSTATUS(x))
  15. #define        WIFEXITED(x)        (_WSTATUS(x) == 0)
  16. #define        WEXITSTATUS(x)        (_W_INT(x) >> 8)
  17. #define        WIFCONTINUED(x)        (x == 0x13)        /* 0x13 == SIGCONT */
  18. #if __BSD_VISIBLE
  19. #define        WCOREDUMP(x)        (_W_INT(x) & WCOREFLAG)

  20. #define        W_EXITCODE(ret, sig)        ((ret) << 8 | (sig))
  21. #define        W_STOPCODE(sig)                ((sig) << 8 | _WSTOPPED)
  22. #endif
复制代码

关于wait返回的整数状态中的低8位里面存放的是什么,可以参考以下的内核代码:

sys/libkern/kern/kern_exit.c
  1. void
  2. sys_exit(struct thread *td, struct sys_exit_args *uap)
  3. {

  4.         exit1(td, W_EXITCODE(uap->rval, 0));
  5.         /* NOTREACHED */
  6. }
复制代码

这应该是进程正常exit的情况,参见W_EXITCODE宏的定义,这里实际上就是把“返回值”
左移8位再或上一个0,所以exit(1)的时候打印出来的int型变量就是256。

sys/libkern/kern/kern_sig.c
  1. void
  2. sigexit(td, sig)
  3.         struct thread *td;
  4.         int sig;
  5. {
  6.     ......
  7.         exit1(td, W_EXITCODE(0, sig));
  8. }
复制代码

这应该是进程因收到某个信号而终止的情况,调用完W_EXITCODE宏之后,我们所说的int
型状态的低8位里面存储的就是信号,而其它字节则为0。想办法让子进程非正常终止就
可以验证这个情况。
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP