损坏的pipe道不再结束程序?

当你pipe道两个进程并杀死pipe道的“输出”时,第一个进程用来接收“Broken Pipe”信号,这通常会终止它。 如跑步

$> do_something_intensive | less 

然后退出使用较less ,立即返回到一个响应式shell,在SuSE8或以前的版本。 当我今天尝试, do_something_intensive显然仍然运行,直到我手动杀死它。 看起来有些变化(glib?shell?),使得程序忽略了“破碎的pipe道”…

你们中的任何人都有这个暗示吗? 如何恢复以前的行为? 为什么它被改变(或为什么它总是存在多个语义)?

编辑 :进一步testing(使用strace)显示“SIGPIPE” 生成,但程序没有中断。 一个简单的

 #include <stdio.h> int main() { while(1) printf("dumb test\n"); exit(0); } 

将继续下去

 --- SIGPIPE (Broken pipe) @ 0 (0) --- write(1, "dumb test\ndumb test\ndumb test\ndu"..., 1024) = -1 EPIPE (Broken pipe) 

less的时候死亡。 我可以肯定地编程我的程序中的信号处理程序,并确保它终止,但我更寻找一些环境variables或shell选项,将强制程序终止在SIGPIPE

再次编辑 :它似乎是一个tcsh特定的问题(bash处理它正确)和terminal依赖(Eterm 0.9.4)

那么,如果在阅读器消失后尝试写入管道,就会生成一个SIGPIPE信号。 应用程序有能力捕捉到这个信号,但是如果没有,这个过程就会被终止。

在调用进程尝试写入之前,SIGPIPE不会被生成,所以如果没有更多的输出,它将不会被生成。

有做“密集的事情”吗?

正如丹尼尔所说,SIGPIPE不是一个神奇的“你的管道消失”的信号,而是一个“不错的尝试,你不能再读/写管道”的信号。

如果你有控制“做一些密集的事情”,你可以改变它写出一些“进度指示器”输出,因为它旋转。 这将及时提升SIGPIPE。

感谢您的建议,解决方案正在接近…

根据tcsh的说明书,“非登录shell从父节点继承终止行为,其他信号具有shell从父节点继承的值”。

这意味着我的终端实际上是问题的根源…如果忽略了SIGPIPE,那么shell本身也将忽略SIGPIPE …

编辑:我有确定的确认,问题只出现在Eterm + tcsh,并发现Eterm源代码中的可疑丢失信号(SIGPIPE,SIG_DFL)。 我认为结案。