当其中一个子进程退出时退出 bash 脚本
Exit a bash script when one of the subprocesses exits
我运行我的脚本中有几个后台进程
run_gui()
{
exec ... # the real commands here
}
函数run_ai1(), run_ai2
类似。
然后我 运行 函数并完成所需的管道
run_gui &
run_ai1 &
run_ai2 &
while true; do
while true; do
read -u $ai1_outfd line || echo "Nothing read"
if [[ $line ]]; then
: # processing
fi
done
sleep $turndelay
while true; do
read -u $ai2_outfd line || echo "nothing read"
if [[ $line ]]; then
: # processing
fi
done
sleep $turndelay
done
如果这三个进程中的任何一个退出,我想检查它们的退出代码并终止其余进程。例如,如果 run_ai2
以退出代码 3 退出,那么我想停止进程 run_ai1
和 run_gui
并以退出代码 1 退出主脚本。不同背景的正确退出代码流程可能不同。
问题是:我怎样才能检测到它?有命令 wait
但我事先不知道哪个脚本会先完成。我可以 运行 wait
作为后台进程 - 但它变得更加笨拙。
你能帮帮我吗?
以下脚本监控测试 child 进程(在示例中为 sleep+false 和 sleep+true)并报告它们的 PID 和退出代码:
#!/bin/bash
set -m
trap myhandler CHLD
myhandler() {
echo sigchld received
cat /tmp/foo
}
( sleep 5; false; echo "exit p1=$?" ) > /tmp/foo &
p1=$!
echo "p1=$p1"
( sleep 3; true; echo "exit p2=$?" ) > /tmp/foo &
p2=$!
echo "p2=$p2"
pstree -p $$
wait
结果是:
p1=3197
p2=3198
prueba(3196)─┬─prueba(3197)───sleep(3199)
├─prueba(3198)───sleep(3201)
└─pstree(3200)
sigchld received
sigchld received
exit p2=0
sigchld received
exit p1=1
使用 SIGUSR1
代替 SIGCHLD
可能会很有趣;示例见此处:.
此外,在陷阱处理程序内部,可以验证哪个 child 仍然存在。类似于:
myhandler() {
if kill -0 $p1; then
echo "child1 is alive"
fi
if kill -0 $p2; then
echo "child2 is alive"
fi
}
或者当 child 中的一个死亡时杀死他们:
myhandler() {
if kill -0 $p1 && kill -0 $p2; then
echo "all childs alive"
else
kill -9 $p1 $p2
fi
}
我运行我的脚本中有几个后台进程
run_gui()
{
exec ... # the real commands here
}
函数run_ai1(), run_ai2
类似。
然后我 运行 函数并完成所需的管道
run_gui &
run_ai1 &
run_ai2 &
while true; do
while true; do
read -u $ai1_outfd line || echo "Nothing read"
if [[ $line ]]; then
: # processing
fi
done
sleep $turndelay
while true; do
read -u $ai2_outfd line || echo "nothing read"
if [[ $line ]]; then
: # processing
fi
done
sleep $turndelay
done
如果这三个进程中的任何一个退出,我想检查它们的退出代码并终止其余进程。例如,如果 run_ai2
以退出代码 3 退出,那么我想停止进程 run_ai1
和 run_gui
并以退出代码 1 退出主脚本。不同背景的正确退出代码流程可能不同。
问题是:我怎样才能检测到它?有命令 wait
但我事先不知道哪个脚本会先完成。我可以 运行 wait
作为后台进程 - 但它变得更加笨拙。
你能帮帮我吗?
以下脚本监控测试 child 进程(在示例中为 sleep+false 和 sleep+true)并报告它们的 PID 和退出代码:
#!/bin/bash
set -m
trap myhandler CHLD
myhandler() {
echo sigchld received
cat /tmp/foo
}
( sleep 5; false; echo "exit p1=$?" ) > /tmp/foo &
p1=$!
echo "p1=$p1"
( sleep 3; true; echo "exit p2=$?" ) > /tmp/foo &
p2=$!
echo "p2=$p2"
pstree -p $$
wait
结果是:
p1=3197
p2=3198
prueba(3196)─┬─prueba(3197)───sleep(3199)
├─prueba(3198)───sleep(3201)
└─pstree(3200)
sigchld received
sigchld received
exit p2=0
sigchld received
exit p1=1
使用 SIGUSR1
代替 SIGCHLD
可能会很有趣;示例见此处:.
此外,在陷阱处理程序内部,可以验证哪个 child 仍然存在。类似于:
myhandler() {
if kill -0 $p1; then
echo "child1 is alive"
fi
if kill -0 $p2; then
echo "child2 is alive"
fi
}
或者当 child 中的一个死亡时杀死他们:
myhandler() {
if kill -0 $p1 && kill -0 $p2; then
echo "all childs alive"
else
kill -9 $p1 $p2
fi
}