When it comes to network troubleshooting and monitoring, what types of tools you are using make a world of difference. While required tools may vary depending on the types of network problems you are dealing with, there are a set of essential tools that every network administrator must be familiar with, and tcpdump
is definitely one of them.
tcpdump
is a command-line tool packet sniffing that allows you to capture network packets based on packet filtering rules, interpret captured packet content, and display the result in a human-readable format. The main power of tcpdump
comes from its (1) flexible packet filtering rules and (2) versatile protocol dissection capability. Although GUI-based Wireshark provides equally powerful filtering/dissecting capabilities via a more user-friendly interface, its relatively high memory footprint (for buffering packets) and GUI-based operations make Wireshark unsuitable when you are troubleshooting directly from remote headless servers.
Using tcpdump
, you can troubleshoot a wide range of network issues including but not limited to:
- Packet loss diagnosis: Detect packet loss and diagnose the cause for dropped packets.
- Application performance: Estimate application-level latency from packet timestamps.
- Rogue DHCP server detection: Discover DHCP responses from unauthorized DHCP servers.
- Multi-homed routing: Verify traffic routing in multi-homed environment.
- Firewall debugging: Troubleshoot packet filtering rules in the firewall.
- VLAN misconfiguration: Monitor VLAN tags carried by traffic from a specific network interface.
- Penetration analysis: Sniff and analyze malicious traffic on local network.
The rest of the post provides a comprehensive tcpdump
cheat sheet, which illustrates different types of packet capture scenarios using actual tcpdump
examples.
1. Capture Packets from a Specific Network Interface
When running tcpdump
, typically you specify, with -i
option, which network interface you want to monitor traffic on. If you do not specify a network interface, tcpdump
will listen on a default network interface, which is the lowest-number interface in the network interface list. tcpdump -D
will show the network interface list.
To capture packets received on network interface docker0
:
$ sudo tcpdump -i docker0
2. Capture Packets from All Available Network Interfaces
Suppose there are multiple network interfaces on your system, and you want to capture traffic from all those interfaces simultaneously. Exactly for this purpose tcpdump
provides a special interface name called “any
“. Thus, simply run tcpdump
with -i any
option to capture traffic from all available network interfaces.
$ sudo tcpdump -i any
3. Change the Output Format
To print the layer-2 header information such as MAC addresses:
$ sudo tcpdump -e
13:27:18.002070 9c:b6:d0:fe:4d:95 (oui Unknown) > 48:d6:e5:7b:81:70 (oui Unknown), ethertype IPv4 (0x0800), length 66: xxxx.xxxx.xxxx.33800 > xxxx.xxxx.xxxx.8009: Flags [.], ack 111, win 501, options [nop,nop,TS val 1624743259 ecr 4014866], length 0
To print IP addresses and port numbers without DNS lookup or port name conversion:
$ sudo tcpdump -n
13:30:50.832688 IP 75.135.195.199.443 > 192.168.1.236.35267: UDP, length 45
To adjust the verbosity of output:
$ sudo tcpdump -v $ sudo tcpdump -vv $ sudo tcpdump -vvv
4. Capture Packets with a Specific IP Address or a Subnet
To capture packets from a source IP address 8.8.8.8
:
$ sudo tcpdump src 8.8.8.8
To capture packets originating from a source subnet 192.168.100.0/24
:
$ sudo tcpdump src net 192.168.100.0/24
To capture packets with a destination IP address 10.0.0.1
:
$ sudo tcpdump dst 10.0.0.1
To capture packets with a destination address prefix 192.168.100.0/24
:
$ sudo tcpdump dst net 192.168.100.0/24
5. Capture Packets between Two Hosts or Two Subnets
To capture packets from 10.10.0.1
to 192.168.100.54
:
$ sudo tcpdump src 10.10.0.1 and dst 192.168.100.54
To capture packets from source network 10.10.0.0/24
to destination network 192.168.100.0/24
:
$ sudo tcpdump src net 10.10.0.0/24 and dst net 192.168.100.0/24
To capture packets between 10.10.0.1
and 192.168.100.54
in both directions:
$ sudo tcpdump host 10.10.0.1 and host 192.168.100.54
To capture packets between two subnets 10.10.0.0/24
and 192.168.100.0./24
in both directions:
sudo tcpdump net 10.10.0.0/24 and net 192.168.100.0/24
6. Capture Packets with a Specific Network Protocol
tcpdump
allows you to capture network traffic with a specific network protocol. For well-known layer-3 or layer-4 protocols, you just need to specify their names. For other types of transport protocols (e.g., DHCP, DNS, SSH), you can filter them based on their port numbers (shown next).
To capture IP packets only:
$ sudo tcpdump ip
To capture ICMP packets only:
$ sudo tcpdump icmp
To capture ARP (request/response) packets only:
$ sudo tcpdump arp
To capture IPv6 packets only:
$ sudo tcpdump ip6
To capture TCP packets only:
$ sudo tcpdump tcp
To capture UDP packets only:
$ sudo tcpdump udp
To capture TCP packets between 10.10.0.1 and 192.168.100.54 in both directions:
$ sudo tcpdump tcp and host 10.10.0.1 and host 192.168.100.54
7. Capture Packets with Specific TCP/UDP Port(s)
To capture packets with destination port 80:
$ sudo tcpdump dst port 80
To capture UDP packets with source port 4001:
$ sudo tcpdump udp src port 4001
To capture SSH packets (either source or destination port 22):
$ sudo tcpdump port 22
To capture DNS packets (either source or destination port 53):
$ sudo tcpdump port 53
To capture packets with port 80 or 8000:
$ sudo tcpdump port 80 or port 8000
To capture packets with TCP port 80 or UDP port 4001:
$ sudo tcpdump 'tcp port 80 or udp port 4001'
To capture packets with port numbers between 800 and 900:
$ sudo tcpdump portrange 800-900
To capture TCP packets with destination port range of [8000, 8010]:
$ sudo tcpdump tcp dst portrange 8000-8010
8. Capture All Packets Excluding My Own SSH Session
If my SSH session is originating from 192.168.100.250
:
$ sudo tcpdump port not 22 and not host 192.168.100.250
9. Capture the First N Number of Packets
To capture the first 100 TCP packets:
$ sudo tcpdump -c 100 tcp
10. Capture Packets with Specific Packet Length
To capture packets whose length are greater than 200 bytes:
$ sudo tcpdump greater 200
To capture TCP packets with destination port 80, and whose size are smaller than 200 bytes:
$ sudo tcpdump tcp dst port 80 and less 200
Note that the greater
and less
operators check the length of an entire packet, including all headers (e.g., Ethernet, IP, TCP headers).
To capture packets with packet size between 200 and 500 bytes:
$ sudo tcpdump not less 200 and not greater 500
11. Capture Packets with Specific MAC addresses
You can filter packets by MAC address with the ether
qualifier.
To capture layer-2 broadcast traffic (i.e., packets with destination MAC address ff:ff:ff:ff:ff:ff
):
$ sudo tcpdump ether dst ff:ff:ff:ff:ff:ff
To capture packets between e8:2b:88:ef:55:11
and 9c:b6:d0:ee:fd:90
in both directions:
$ sudo tcpdump ether host e8:2b:88:ef:55:11 and ether host 9c:b6:d0:ee:fd:90
To capture packets sent to or received by e8:2b:88:ef:55:11
:
$ sudo tcpdump ether host e8:2b:88:ef:55:11
12. Print the Payload of Captured Packets
To print the payload of captured TCP packets in ASCII format:
$ sudo tcpdump -A tcp
Printing packet payload in ASCII format can be useful to inspect (unencrypted) HTTP protocol headers. For example:
To print the payload of captured packets in hexadecimal format:
$ sudo tcpdump -X
13. Save Captured Packets to a File, and Read Packets from a File
To save the first 1000 packets to a file trace.pcap
:
$ sudo tcpdump -c 1000 -w trace.pcap
To read only TCP packets from a file trace.pcap
:
$ tcpdump -r trace.pcap tcp
14. Rotate Packet Capture Files by Time and Size
When you dump captured packets to a file, the capture file can grow quickly depending on the rate of incoming packets. So you want to rotate capture files regularly.
To rotate capture files every hour or every 500 MB, whichever comes first:
$ sudo tcpdump -w /tmp/trace -W 24 -G 3600 -C 500
This will create 24 capture files (/tmp/trace00, /tmp/trace01, …, /tmp/trace23) in 24 hours. After that, it will overwrite the files from the beginning.
To rotate capture files every 30 minutes and name the capture files with collected timestamps:
$ sudo tcpdump -w /tmp/trace-%Y-%m-%d_%H-%M.pcap -G 1800
This will create a new trace file every 30 minutes with the following names.
/tmp/trace-2021-23-29_12-00.pcap /tmp/trace-2021-23-29_12-30.pcap /tmp/trace-2021-23-29_13-00.pcap /tmp/trace-2021-23-29_13-30.pcap . . .
15. Capture Packets with High-Resolution Timestamp
By default tcpdump
use micro-second resolution for timestamping packets. However, tcpdump
version 4.6 or later supports nano-second resolution timestamp.
To capture packets with nano-second resolution:
$ sudo tcpdump --time-stamp-precision nano
16. Capture Packets with Different Timestamp Formats
To print packet timestamp with Unix epoch time (seconds since January 1, 1970):
$ sudo tcpdump -tt
1617031894.463313 IP 192.168.1.236.35627 > 193.194.206.100.443: UDP, length 1350
To print packet timestamp as the date followed by hours, minutes, seconds, and microseconds:
$ sudo tcpdump -tttt
2021-03-29 11:33:57.181125 IP 192.168.1.236.52472 > 200.189.40.8.123: NTPv4, Client, length 48
To print relative timestamp (since the first packet captured):
$ sudo tcpdump -ttttt
00:00:00.000000 IP 192.168.1.228.49669 > 255.255.255.255.1947: UDP, length 40 00:00:00.205198 IP 185.199.206.189.443 > 192.168.1.236.35627: UDP, length 44 00:00:00.211631 IP 192.168.1.236.35627 > 173.194.206.189.443: UDP, length 33 00:00:02.356055 ARP, Request who-has 192.168.1.1 tell 192.168.1.204, length 46
To print packet timestamp in a specific time zone:
tcpdump
prints packet timestamp in the default timezone of your Linux system. If you want to show timestamp in a different timezone, you can specify the timezone in TZ
environment variable before calling tcpdump
.
$ sudo TZ=America/New_York tcpdump $ sudo TZ=Europe/London tcpdump $ sudo TZ=Asia/Seoul tcpdump
17. Capture TCP Control Packets
tcpdump
‘s expressive filter allows you to check for any arbitrary byte ranges in a packet. Using this capability, for example, you can capture TCP packets with particular flags in their TCP headers.
To capture TCP SYN packets:
$ sudo tcpdump "tcp[tcpflags] & (tcp-syn) != 0"