![[ 永远的UNIX::UNIX技术资料的宝库 ]](/images/title.gif)
|
| 首页 > 系统管理 > 其它 > 正文 |
 |
| 要怎样才能避免在内存中留下zombie processes? |
| Steve Hayman (2001-04-19 11:33:05) |
很不幸地,对于死掉的子 process 应有的行为特性并没有办法做一般化,因
为这些特定/特定的机制会随著 Unix 的种类不同而有所差异。
首先,在各种 Unix 上面您都必需使用 wait() 来处理子 process。也就是
说,我还没看过有一种 Unix 会自动把结束的子 process 干掉,即使您不告
诉它该怎么做。
其次,在某些从 SysV 衍生的系统当中,如果您执行了 signal(SIGCHLD,
SIG_IGN)",(嗯,事实上应该是SIGCLD 而非SIGCHLD,但大多数新出
炉的 SysV 系统都会在表头档当中加上 #define SIGCHLD SIGCLD),那
么子 processes 都会自动被清除得乾乾净净,您什么事都不用做。看看这个
方式是否可行的最佳做法就是自己在机器上试试看。如果您想试著写出具可
携性的程式码,那么依赖这种特殊处理方式可能不是好主意。不幸的是,在
POSIX 并不允许您这样做;把 SIGCHLD 的行匦陨璩?nbsp;SIG_IGN 在
POSIX 当中并没有定义,所以如果您要让您的程式合乎 POSIX 的要求
时,您就不可以这样做。
那么怎样才算是 POSIX 的做法呢?如同前面所述,您必需设定一个 signal
的处理函数,然后让它去 wait。在 POSIX 当中 signal 处理函数是经由
sigaction 设定,由于您只对终止的子 process 感兴趣,而不是那些 stopped
的子 process,所以可以在 sa_flags 当中加上 SA_NOCLDSTOP。如果要
wait 子 process 而本身不因此被挡 (block),可以使用 waitpid()。第一
个参数必需是 -1 (代表 wait 任何 pid),第三个参数必需是 WNOHANG,这是
最具可携性的做法,也是可能会成为未来最具可携性的写法。
如果您的系统不支援 POSIX,那就有很多做法了。最简单的方式就是先试
试signal(SIGCHLD, SIG_IGN) 是否可行,可以的话那就好了。如果
SIG_IGN 无法用来强制自动收拾残骸,那么您就要自己写一个 signal 处理
函数来收拾残骸了。要写出一个适用于每一种 Unix 的 singal 处理函数来
做这件事是不容易的事,因为有下列不一致的地方:
在一些 Unix 中,一个或一个以上的子 process 死时,会呼叫 SIGCHLD 的
signal 处理函数。也就是说,如果你的 signal 处理函数只有一个 wait()
时,并不会把所有的子 process 都收拾乾净。不过还好,我相信这类的
Unix 都会有 wait3() 或 waitpid(),这两者都有可在 option 参数中使用
WNOHNAG 可用来检查是否有子 process 尚待收拾。所以在一个有
wait3()/waitpid() 的系统中,你可以一再重复使用 wait3()/waitpid()
以确定所有的子 process 都已收拾乾净W詈檬怯?nbsp;waitpid() 因为
它在 POSIX 标准中。
在一些 SysV-derived 的系统中,再 SIGCHLD 的 signal 处理函数结束后,
若还有子 process 等待清除,还是会产生 SIGCHLD signal。 因此,在大部
份的 SysV 系统中,在 signal 处理函数里可以假设要处理的 signal 只有一
个,
(http://www.fanqiang.com)
进入【UNIX论坛】
|
|
| 相关文章 |
|
===更多相关=== |
|
|
 |
★ 樊强制作 欢迎分享 ★ |