如何在没有wait-n的bash上等待任何一个子进程终止?

如何在没有wait-n的bash上等待任何一个子进程终止?,bash,wait,child-process,Bash,Wait,Child Process,我基本上需要找到一个wait-n的替代品,我可以在较旧版本的bash(例如,CentOS 7中包含的bash4.2)中使用它来等待任何子进程(不是全部)的终止。我运气不好吗?陷阱SIGCHLD在我的场景中不起作用。如果您知道PID,最明显的解决方案是: while ps $pid > /dev/null ; do sleep 1 done 这与等待信号并不完全相同,但在功能上也是如此。一种方法是使用FIFO在退出时发送通知: mkfifo notify_fd exec 3<

我基本上需要找到一个
wait-n
的替代品,我可以在较旧版本的
bash
(例如,CentOS 7中包含的
bash
4.2)中使用它来等待任何子进程(不是全部)的终止。我运气不好吗?陷阱
SIGCHLD
在我的场景中不起作用。

如果您知道PID,最明显的解决方案是:

while ps $pid > /dev/null ; do
    sleep 1
done

这与等待信号并不完全相同,但在功能上也是如此。

一种方法是使用FIFO在退出时发送通知:

mkfifo notify_fd
exec 3<>notify_fd
count=0

background() { { "$@"; echo "${BASHPID} $?" >&3; } & (( ++count )); }

background sleep 3
background sleep 4
background sleep 5

while read pid status <&3; do
  echo "One exited, with PID $pid and status $status"
  (( --count == 0 )) && break
done
mkfifo通知
执行官3通知
计数=0
背景()
背景睡眠3
背景睡眠4
背景睡眠5

读pid状态时,我觉得你运气不好。添加了
-n
选项,因为以前没有办法这样做。如果控制子进程的启动方式,则可以按
(command&&touch$$)
启动每个子进程,然后使用
inotifywait
或带有中间休眠的循环等待其中一个文件出现。我不控制。听起来很有趣。如果
命令
异常退出将
|
而不是
&
就足够了,那么情况如何?如果您知道启动了多少后台进程,那么您可以将该数字与
pgrep-c-P$$
的结果进行比较,这将告诉您有多少进程仍在运行。@Miguel Use
(command;touch…
如果您不关心
command
是否成功。
$
不合适,因为它始终是父shell的进程ID,而不是子shell。
(command&pid=$;wait;touch$pid)
可能更合适。您的计算机将以足够快的速度生成如此多的进程,以至于
pid
在您的进程组中不一定是唯一的风险非常小。OP有许多pid,而不仅仅是一个;他们希望等待集合中的任何一个。(坦率地说,
ps$pid
作为检查单个pid是否处于活动状态的一种方法,其效率远远低于
kill-0“$pid”
)。