如何在BASH 2.05脚本中获取管道命令的PID?

时间:2012-08-30 16:41:05

标签: bash scripting

我正在尝试在BASH脚本中获取管道数据收集命令的PID,这样我就可以在另一个(前台)进程完成后终止该进程。我的数据收集命令有一个超时,但我事先不知道应该多长时间;从几分钟到几个小时的任何地方。

这个问题How to get the PID of a process in a pipeline提供了丰富的信息,但并没有成功。可能是因为我使用的是BASH 2.05(在嵌入式系统上)。

jobs -p命令在命令行上的初始测试看起来很有希望。在实践中,我使用管道命令(ksmon)替换下面的ksmon | {various filters} | gzip -c > file命令,因此“$!”BASH变量提供管道中的最后一个进程,而不是ksmon程序我想杀人:

Test:/ $  ksmon > /dev/null & jobs -p
[1] 2016
2016
Test:/ $  ps | grep ksmon
 2016 root        660 S   ksmon
 2018 root        580 S   grep ksmon
Test:/ $  kill $(jobs -p)
[1]+  Terminated              ksmon >/dev/null
Test:/ $  ps | grep ksmon
 2021 root        580 S   grep ksmon
Test:/ $

Whoohoo!所以我试着把它放在一个脚本中:

Test:/ $  cat > test.sh << EOF
> #!/bin/bash
> # That's bash 2.05
> ksmon > /dev/null & jobs -p
> EOF
Test:/ $  chmod 755 test.sh
Test:/ $  ./test.sh
Test:/ $
Test:/ $  # Nothing ...
Test:/ $  ps | grep ksmon
 2025 root        660 S   ksmon
 2027 root        580 S   grep ksmon
Test:/ $  jobs -p
Test:/ $

这是我试图让它与之合作的版本:

Test:/ $  bash --version
GNU bash, version 2.05.0(2)-release (arm-Artila-linux-gnu)
Copyright 2000 Free Software Foundation, Inc.

奇怪的是,上面的脚本适用于Ubuntu主机。

我需要做些什么才能使jobs -p在BASH 2.05脚本中运行,还是有替代方案?

一种想法是从$!变量中减去一个固定数字,但我不确定这是不是一个好主意......

修改 我想要删除管道中的第一个程序的原因是管道中的所有程序,特别是gzip将很好地关闭它们的输出流。

1 个答案:

答案 0 :(得分:2)

我建议你用$!获取管道中最后一个进程的PID;然后use lsof to sequentially determine previous processes in chain by open file descriptors from /proc