0

我正在尝试创建一个脚本,其中包含:

tcpdump (options) | fgrep (options) > file

在我使用 CTRL+CI 终止 tcpdump 后,希望执行这些命令:

sed (options) file | awk (options)
wait
rm file

第一部分已经完成,但在我按下 CTRL+CI 后会被抛出提示。我尝试了等待,使用陷阱 SIGINT,同样的问题。

现在把显而易见的事情排除在外:为什么不简单地管道所有内容而不将中间未过滤的输出转储到临时文件?好吧,我试过了,但似乎信息在我的屏幕输出中丢失了(繁忙的服务器,不知道),我发现打破这样的命令将使我获得完整的输出。

更新:根据我在下面得到的答案,我尝试这样做,这似乎是使其工作的最安全方法:

function1 ()
{
tcpdump (options) | fgrep (options) > file
trap "function2" SIGINT SIGTERM
}

function2 ()
{
sed (options) file | awk (options)
wait
rm -i file
}

它不起作用。生成了“文件”,但 sed | 似乎没有读取和过滤其内容 在我执行 CTRL+C 之后的 awk 语法,它甚至没有被 rm 命令删除,所以这进一步证明了辅助的被困函数没有被执行。我不明白这种行为,我做错了吗?

更新2:我可以让它正常工作的唯一方法是这样的:

set -m

tcpdump (options) | fgrep (options) > filename &

trap "kill -9 $!" SIGINT

sed (options) filename | mawk (options)

\rm filename

但是我无法通过杀死后台进程来抑制输出,尝试了我能找到的所有解决方案: 在后台运行 bash 命令而不打印作业和进程 ID - 这使我的陷阱不起作用;使用 Bash 脚本,如何抑制命令的所有输出?- 这里的所有变体都不起作用,无论我做什么,我仍然得到输出。尝试定义 $! 使用另一个变量,尝试了 /dev/null 的所有变体,尝试将其放在陷阱命令中,没有用。

4

1 回答 1

0

在后台启动tcpdump命令并在固定时间后终止它对您有用吗?例如运行

(tcpdump (options) | fgrep (options) > file) & 

然后获取进程的pid并等待一段时间,

pid=$! 
sleep 60

最后杀死命令并解析输出

kill -9 $pid
sed (options) file | awk (options)
rm file

更新

如果你真的想Ctrl-P停下来tcpdumptrap就是要走的路。但是,在执行了被困命令之后,您将始终以 shell 结束!所以你描述的行为实际上trap是应该做的。

因此,您可以将trap命令编写为

trap "{ sed (options) file | awk (options); rm file; }" SIGINT SIGTERM

它应该在中断时执行所有后处理。如果您拥有的不仅仅是这些简单的命令,那么将所有后处理命令放在一个新的脚本或函数中可能更有意义,例如

exec_on_interrupt() {
  sed (options) file | awk (options)
  rm file
  # other stuff...
}

trap "exec_on_interrupt" SIGINT SIGTERM
于 2013-12-27T00:32:31.913 回答