Cannot terminate a shell command with Ctrl+c

好久不见. 提交于 2020-01-15 10:55:13

问题


Would someone please tell me why below bash statement cannot be terminated by Ctrl+c properly?

$( { ( tail -fn0 /tmp/a.txt & )| while read line; do echo $line; done } 3>&1 )

I run this statement, then two bash processes and one tail process are launched(got from ps auxf), then input Ctrl+c, and it won't quit to the bash prompt, at this moment, I see the two bash processes stopped, while the tail is still running, then I input something into /tmp/a.txt, then we could get into bash prompt.

What I want is, input Ctrl+c, then just quit into bash prompt without any relevant process left.

It will be more appreciative that someone explains the exact process of this statement, like a pipe causes the bash fork, something redirect to somewhere, etc.

Updated at Oct 9 2014:

Here provide some update in case it's useful to you. My adopt solution is alike with 2 factors:

  1. use a tmp pid file

    ( tail -Fn0 ${monitor_file} & echo "$!" >${tail_pid} ) | \
    while IFS= read -r line; do 
        xxxx
    done 
    
  2. use trap like: trap "rm ${tail_pid} 2>/dev/null; kill 0 2>/dev/null; exit;" INT TERM to kill relevant processes and remove remain files.

Please note, this kill 0 2 is bash specific, and 0 means all processes in the current process group. This solution used a tmp pid file, while I still expect other solution without tmp pid file.


回答1:


It works to trap the INT signal (sent by Ctrl-C) to kill the tail process.

$( r=$RANDOM; trap '{ kill $(cat /tmp/pid$r.pid);rm /tmp/pid$r.pid;exit; }' SIGINT EXIT; { ( tail -fn0 /tmp/a.txt & echo $! > /tmp/pid$r.pid  )| while read line; do echo $line; done } 3>&1 )

(I use a random value on the PID file name to at least mostly allow multiple instances to run)



来源:https://stackoverflow.com/questions/20533745/cannot-terminate-a-shell-command-with-ctrlc

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!