【发布时间】:2012-01-13 10:25:48
【问题描述】:
这些设置有什么区别?
$SIG{CHLD} = 'IGNORE'
$SIG{CHLD} = 'DEFAULT'
$SIG{CHLD} = ''
$SIG{CHLD} = undef
根据“Advanced Programming in the UNIX Environment, 2nd edition”,图 10.1 SIGCHLD 的默认值为“ignore”。
如果“忽略”意味着“SIG_IGN”,那么任何孩子都不会成为僵尸,而事实并非如此。
从那里并没有变得更清楚:
如果进程专门将其处置设置为 SIG_IGN,则子进程 调用进程不会产生僵尸进程。注意 这与它的默认操作 (SIG_DFL) 不同,后者来自图 10.1 将被忽略。相反,在终止时,这些子进程的状态 被丢弃。
我很难理解各种值(或未定义的非值)的影响是什么。到目前为止,解决方案一直是轮流选择这些选项,直到获得所需的行为,我宁愿准确了解每个值如何定义信号的行为。
行为:子进程正在调用“系统”或使用创建另一个子进程的反引号,并且信号通常会被错误的(父)处理程序捕获。设置本地处理程序可以工作,但如果我希望来自孙子的信号什么都不做,我不明白哪个值最合适。
有人可以给我发光吗?
更新: 根据ikegami的反馈,我做了一些具体的测试。该行为至少部分是特定于平台的。
考虑以下片段:
$SIG{CHLD} = sub {
while( ( my $child = waitpid( -1, &WNOHANG ) ) > 0 ) {
print "SIGNAL CHLD $child\n";
}
};
my $pid = fork();
if( ! $pid ) {
system( 'echo Grandchild PID = $$' );
sleep 2;
exit;
}
print "Child PID = $pid\n";
sleep 5;
Solaris 10 上的 Perl 5.8.6 将为 system() 调用的 PID 显示“SIGNAL CHLD”消息。做任何事,哪怕是微不足道的事情
本地 $SIG{CHLD};
在孩子中会抑制这些消息。
在我尝试过的所有其他口味中,收割者都看不到孩子。
【问题讨论】:
-
local $SIG{CHLD};与local $SIG{CHLD} = undef;相同
标签: perl unix signals signal-handling sigchld