Более подробная версия ответа Спиффа:
Если у вас есть трубопровод
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
не должен тратить процессорное время на запись в /dev/null
;
grep
может завершить работу, как только увидит строку, поэтому он не будет тратить больше времени на чтение процессорного времени, а tcpdump умрет с ошибкой "Closed pipe" после выхода из grep
и не будет тратить больше процессорного времени или диска / Чтение пропускной способности SSD из файла.
(Старые версии grep
использовали -s
для той же цели, но стандарт UNIX гласит, что это -q
, и большинство UNIX- и UNIX-подобных систем делают это сейчас; например, GNU grep
использует -q
.)