我注意到,当使用tcpdump
命令读取 pcap 文件时,tcpdump
即使我重定向 STDOUT 和 STDERR,该命令仍会以某种方式将信息打印到我的控制台。如何防止每次运行时都tcpdump
打印“ ”?reading from file capture, link type EN10MB (Ethernet)
例如,当我预期没有打印行时,以下命令会打印一行:
$ tcpdump -A -r capture.pcap | grep interesting-string > /dev/null 2>&1
reading from file capture.pcap, link-type EN10MB (Ethernet)
我想阻止该行出现,因为它会给脚本的输出添加不必要的噪音。我查看了手册页,没有看到阻止该消息出现的选项。我在网上搜索了抑制 STDOUT 和 STDERR 未捕获的输出的方法,找到了一些结果,但没有一个是我能够理解或在这种情况下使用的。
答案1
我认为您想将输出重定向放在管道之前,以便它适用于 tcpdump 的输出,而不是 grep 的输出。
tcpdump -A -r capture.pcap 2>&1 | grep interesting-string > /dev/null
答案2
Spiff 的答案的更详细版本:
如果你有管道
command1 | command2
然后是命令 1 的标准输出,但是不是它的标准错误被重定向到通向命令 2 的标准输入的管道。
所以如果你
command1 | command2 >/dev/null 2>&1
将命令 2 的标准输出发送到/dev/null
,并将标准错误发送到发送标准输出的同一位置(因此/dev/null
在这种情况下它也会转到),但它不对命令 1 的标准错误执行任何操作,并将命令 1 的标准输出通过管道传输到命令 2 的标准输入。
但是,命令
command1 2>/dev/null | command2 >/dev/null 2>&1
会将命令 1 的标准输出发送到命令 2 的标准输入,将命令 1 的标准错误发送到/dev/null
,将命令 2 的标准输出和错误发送到/dev/null
,命令
command1 2>&1 | command2 >/dev/null 2>&1
将会把命令 1 的标准输出发送到命令 2 的标准输入,将命令 1 的标准错误发送到与命令 1 的标准输出相同的位置 - 即,发送到命令 2 的标准输入 - 并且将会把命令 2 的标准输出和错误发送到/dev/null
。
例如
tcpdump -A -r capture.pcap 2>&1 | grep interesting-string > /dev/null 2>&1
将导致grep
看到 的标准输出和错误tcpdump
(因此它会看到reading from file...
消息,如果有趣的字符串是其中的一部分,则匹配它),并将 的标准输出和错误发送到grep
,/dev/null
因此它不应该产生任何输出,它应该只给出退出状态grep
(我认为这是你的意图,即你想知道的是有趣的字符串是否是任何数据包的一部分)。
顺便说一句,如果你正在使用grep
来查明给定的字符串是否是其输入的一部分,并且不想要任何输出,请尝试使用(grep -q
如果你的版本grep
支持它);这样运行速度会更快,因为
grep
不必花费 CPU 时间写入/dev/null
;grep
一旦看到该字符串,它可能会立即退出,因此它不会再花费任何 CPU 时间来读取,然后 tcpdump 将在grep
退出后因“管道已关闭”错误而终止,并且它不会再花费 CPU 时间或磁盘/SSD 带宽来读取文件。
(旧版本的grep
用于-s
相同目的,但 UNIX 标准规定它是-q
,并且现在大多数 UNIX 和类 UNIX 系统都这样做;grep
例如,GNU 使用-q
。)