For those like you who cannot use ngrep
, here's how to use awk
to make the tcpdump
output of packet contents grepable.
First some sample output as provided by tcpdump -x
, in order to present the task ahead:
$ tcpdump -xr dump.pcap 2>/dev/null
12:04:59.590664 IP 10.17.14.93.51009 > 239.194.1.9.51009: UDP, length 370
0x0000: 4500 018e 0000 4000 fa11 7625 0a11 0e5d
0x0010: efc2 0109 c741 c741 017a 6f28 1120 2020
0x0020: 3337 3030 3039 3031 3835 3635 3430 3130
...
And this is the copy-and-pastable awk
script you can pipe the output to
awk '{ if (match($0, /^[0-9]/, _)) { printf (NR == 1 ? "%s " : "\n%s "), $0; fflush() } else { sub(/^\s+0x[0-9a-z]+:\s+/, " "); gsub(" ", ""); printf "%s", $0 } } END { print ""; fflush() }'
in order to get the following, grepable output
12:04:59.590664 IP 10.17.14.93.51009 > 239.194.1.9.51009: UDP, length 370 4500018e00004000fa1176250a...
12:04:59.590798 IP 10.17.14.113.51011 > 239.194.1.11.51011: UDP, length 370 4500018e00004000fa11760f...
...
Below is a commented version of above script:
awk '{
# if this is a header line
if (match($0, /^[0-9]/, _)) {
# print the header, but:
# except for the first line,
# we need to insert a newline,
# as the preceding data lines
# have been stripped of theirs
# we also append a space to
# separate header info from the
# data that will get appended
printf (NR == 1 ? "%s " : "\n%s "), $0
# enforce line-buffering
fflush()
}
# otherwise it is a data line
else {
# remove the data address
sub(/^\s+0x[0-9a-z]+:\s+/, " ");
# remove all spaces
gsub(" ", "");
# print w/o newline
printf "%s", $0
}
}
END {
# print final newline, as
# the preceding data lines
# have been stripped of theirs
print ""
# enforce line-buffering
fflush()
}'
As per the tcpdump
man page:
-i Listen on interface. If unspecified, tcpdump searches the system interface list for the lowest numbered, configured up interface (excluding loop‐
back), which may turn out to be, for example, ``eth0''.
On Linux systems with 2.2 or later kernels, an interface argument of ``any'' can be used to capture packets from all interfaces. Note that captures
on the ``any'' device will not be done in promiscuous mode.
So, looking at your output, seems that the first available interface is bluetooth0
which does not allow packet printing, and thus the error.
However, if specifying the -i
flag to any
, you're picking up any available interface that allows packet printing and that's why it works in this case.
Best Answer
I think you want to put the output redirection before the pipe, so that it applies to tcpdump's output, not grep's.