如何在终端上按 Ctrl + C 以使子终端不被关闭?

如何在终端上按 Ctrl + C 以使子终端不被关闭?

该脚本打开了三个终端,但是如果我在运行该脚本的地方点击Ctrl+ C,所有三个子终端也将关闭!

文件testChildDetach.sh

#!/bin/bash
echo $$
while true; do
    nohup xterm -e "echo nohup;bash"&
    
    xterm -e "echo disown;bash"&
    disown
    
    xterm -e "echo normal;bash"&
    
    while true; do
        ps -A -o pid,ppid,command |grep xterm |grep -v grep
        echo sleep 5
        sleep 5
    done
done

我需要找到一种方法来保持子终端打开!

我无法像那样分叉脚本,testChildDetach.sh&因为它会返回命令行。真正的脚本要复杂得多,不能这样做。

这是 Ubuntu 12.10 64 位(我记得我无法让它在 Ubuntu 12.04 上运行)。

在输出中可以看到这些终端的父级保持不变。我想知道,如果父终端/进程被终止,子进程/终端的父级会发生什么?我希望它们变成“1”。

根据@amrith92给出的提示,我设法将脚本改进如下:

测试ChildDetach.sh

#!/bin/bash
echo $$

function FUNCdetach() {
    nohup xterm -e "echo nohup_detach;bash"&
    
    xterm -e "echo disown_detach;bash"&
    disown
    
    xterm -e "echo normal_detach;bash"&
}
export -f FUNCdetach

while true; do
    nohup xterm -e "echo nohup;bash"&
    
    xterm -e "echo disown;bash"&
    disown
    
    xterm -e "echo normal;bash"&
    
    xterm -e "echo FUNCdetach; FUNCdetach; bash;"&
    
    while true; do
        ps -A -o pid,ppid,command |grep xterm |grep -v grep
        echo sleep 5
        sleep 5
    done
done

现在,当您按下Ctrl+时C,3+1 个子终端将会死亡,但 3 个将会存活!

而且,在这种情况下,使用似乎没有什么区别nohupdisown或者什么都没有......

简而言之,xterm -e "xterm -e \"bash\""允许我点击Ctrl+ C,子终端保持打开状态!但是...我觉得我发现了一个缺陷,将来可能会修复...所以我不太愿意以这种方式编写脚本。

答案1

使用 fork 运行脚本本身&,例如,如果您的脚本名称是test.sh,则按如下方式运行它:

:$ ./test.sh &

即使父进程被终止,你生成的终端仍然应该运行:)

当然,如果你这样做,将Ctrl+C不会有任何效果 [即,该进程仍将在后台运行。我用 kill -9 杀死了它。你也可以关闭 shell。]

回答你的第二个问题,如果父终端/进程被终止,那么父 id 确实会变成1。请参阅我附上的屏幕截图 :) 杀死spawner进程后的父进程ID

答案2

在我看来这是一个临时的解决方案,因为我觉得是利用了一个缺陷来使它工作...无论如何,如果有更好的解决方案,我仍然想知道:

testChildDetach002.sh

#!/bin/bash 

function FUNCdoSomething() {
    while true; do 
        echo "CHILD: doing something"
        sleep 1; 
    done
}
export -f FUNCdoSomething

xterm -e "echo \"TEMP xterm...\"; xterm -e \"FUNCdoSomething\""&
# wait for the child to open
while ! ps --ppid $! 2>&1 >/dev/null; do
    sleep 1
done
kill -SIGINT $!

while true; do 
    echo "MAIN: doing something, you can hit ctrl+c here and child will keep running!";
    sleep 1; 
done;

再次感谢@amrith92 的提示!

相关内容