tcpdump & Wireshark
Quick Reference
# Capture on interface
tcpdump -i eth0
# Capture to file
tcpdump -i eth0 -w capture.pcap
# Read from file
tcpdump -r capture.pcap
# Capture with filter
tcpdump -i eth0 'port 80'
tcpdump -i eth0 'host 192.168.1.1'
tcpdump -i eth0 'tcp and port 443'
# Verbose output
tcpdump -i eth0 -v # Verbose
tcpdump -i eth0 -vv # More verbose
tcpdump -i eth0 -vvv # Maximum verbosity
# Show packet contents
tcpdump -i eth0 -X # Hex and ASCII
tcpdump -i eth0 -A # ASCII only
# Common options
tcpdump -i eth0 -n # Don't resolve hostnames
tcpdump -i eth0 -nn # Don't resolve hostnames or ports
tcpdump -i eth0 -c 100 # Capture 100 packets then stop
Understanding Packet Capture
Capture Architecture
┌──────────────────────────────────────────────────────────────────┐
│ User Space │
├──────────────────────────────────────────────────────────────────┤
│ ┌────────────┐ ┌────────────┐ ┌────────────────────┐ │
│ │ tcpdump │ │ Wireshark │ │ tshark (CLI) │ │
│ └─────┬──────┘ └─────┬──────┘ └─────────┬──────────┘ │
│ │ │ │ │
│ ┌─────▼─────────────────▼─────────────────────▼────────┐ │
│ │ libpcap / WinPcap │ │
│ └───────────────────────┬──────────────────────────────┘ │
├───────────────────────────┼──────────────────────────────────────┤
│ │ Kernel Space │
│ ┌───────────────────────▼──────────────────────────────┐ │
│ │ BPF (Berkeley Packet Filter) │ │
│ └───────────────────────┬──────────────────────────────┘ │
│ ┌───────────────────────▼──────────────────────────────┐ │
│ │ Network Interface │ │
│ └──────────────────────────────────────────────────────┘ │
└──────────────────────────────────────────────────────────────────┘
Tools Comparison
| Feature | tcpdump | tshark | Wireshark |
|---|---|---|---|
Interface |
Command-line |
Command-line |
Graphical |
Live capture |
Yes |
Yes |
Yes |
File analysis |
Basic |
Advanced |
Advanced |
Protocol decode |
Basic |
Comprehensive |
Comprehensive |
Filtering |
BPF only |
BPF + display |
BPF + display |
Statistics |
Basic |
Advanced |
Advanced |
Best for |
Quick captures |
Scripted analysis |
Deep analysis |
tcpdump
Basic Syntax
tcpdump [options] [expression]
# Common options:
# -i <interface> : Interface to capture on
# -c <count> : Number of packets to capture
# -w <file> : Write to pcap file
# -r <file> : Read from pcap file
# -n : Don't resolve hostnames
# -nn : Don't resolve hostnames or ports
# -v/-vv/-vvv : Verbosity levels
# -X : Print hex and ASCII
# -A : Print ASCII only
# -s <snaplen> : Capture length (0 = full packet)
# -e : Show link-layer header
# -q : Quiet/brief output
Interface Selection
# List available interfaces
tcpdump -D
tcpdump --list-interfaces
# Capture on specific interface
tcpdump -i eth0
tcpdump -i enp3s0
# Capture on all interfaces
tcpdump -i any
# Capture on loopback
tcpdump -i lo
Output Options
# Basic output (default)
tcpdump -i eth0
# No hostname resolution (faster)
tcpdump -i eth0 -n
# No hostname or port resolution
tcpdump -i eth0 -nn
# Verbose (show TTL, ID, etc.)
tcpdump -i eth0 -v
# More verbose (show more details)
tcpdump -i eth0 -vv
# Maximum verbosity
tcpdump -i eth0 -vvv
# Show hex dump
tcpdump -i eth0 -x # Hex only
tcpdump -i eth0 -X # Hex and ASCII
tcpdump -i eth0 -XX # Include link-layer header
# Show ASCII payload
tcpdump -i eth0 -A
# Quiet output (less protocol info)
tcpdump -i eth0 -q
# Show link-layer (Ethernet) header
tcpdump -i eth0 -e
# Timestamp options
tcpdump -i eth0 -t # No timestamp
tcpdump -i eth0 -tt # Unix epoch timestamp
tcpdump -i eth0 -ttt # Delta from previous packet
tcpdump -i eth0 -tttt # Date and time
tcpdump -i eth0 -ttttt # Delta from first packet
Capture Options
# Limit packet count
tcpdump -i eth0 -c 100
# Capture full packets (default snaplen is 262144)
tcpdump -i eth0 -s 0
# Capture only headers (68 bytes)
tcpdump -i eth0 -s 68
# Buffer size (for high-speed capture)
tcpdump -i eth0 -B 4096
# Don't put interface in promiscuous mode
tcpdump -i eth0 -p
# Write to file
tcpdump -i eth0 -w capture.pcap
# Rotate files (ring buffer)
tcpdump -i eth0 -w capture.pcap -C 100 -W 10
# -C 100 = 100 MB per file
# -W 10 = keep 10 files max
# Time-based rotation
tcpdump -i eth0 -w capture.pcap -G 3600 -W 24
# -G 3600 = rotate every hour
# -W 24 = keep 24 files
# File with timestamp in name
tcpdump -i eth0 -w 'capture_%Y%m%d_%H%M%S.pcap' -G 3600
Reading Capture Files
# Read pcap file
tcpdump -r capture.pcap
# Read with filter
tcpdump -r capture.pcap 'port 80'
# Read with options
tcpdump -r capture.pcap -nn -X
# Count packets
tcpdump -r capture.pcap | wc -l
# First/last N packets
tcpdump -r capture.pcap -c 10
tcpdump -r capture.pcap | tail -10
BPF Filter Expressions
Basic Primitives
| Filter | Description |
|---|---|
|
Traffic to/from host |
|
Traffic from host |
|
Traffic to host |
|
Traffic to/from network |
|
Traffic on port (TCP or UDP) |
|
Traffic from port |
|
Traffic to port |
|
Traffic on port range |
Protocol Filters
# Layer 3 protocols
tcpdump -i eth0 ip # IPv4 only
tcpdump -i eth0 ip6 # IPv6 only
tcpdump -i eth0 arp # ARP packets
tcpdump -i eth0 icmp # ICMP packets
tcpdump -i eth0 icmp6 # ICMPv6 packets
# Layer 4 protocols
tcpdump -i eth0 tcp # TCP packets
tcpdump -i eth0 udp # UDP packets
# Application protocols (by port)
tcpdump -i eth0 'port 53' # DNS
tcpdump -i eth0 'port 80 or port 443' # HTTP/HTTPS
tcpdump -i eth0 'port 22' # SSH
tcpdump -i eth0 'port 25' # SMTP
Combining Filters
# Logical AND
tcpdump -i eth0 'host 192.168.1.1 and port 80'
tcpdump -i eth0 'tcp and port 443'
# Logical OR
tcpdump -i eth0 'port 80 or port 443'
tcpdump -i eth0 'host 192.168.1.1 or host 192.168.1.2'
# Logical NOT
tcpdump -i eth0 'not port 22'
tcpdump -i eth0 '! arp'
tcpdump -i eth0 'host 192.168.1.1 and not port 22'
# Grouping with parentheses (must be quoted or escaped)
tcpdump -i eth0 'host 192.168.1.1 and (port 80 or port 443)'
tcpdump -i eth0 '(src host 10.0.0.1 or src host 10.0.0.2) and dst port 80'
Direction Filters
# Source/destination
tcpdump -i eth0 'src 192.168.1.1'
tcpdump -i eth0 'dst 192.168.1.1'
tcpdump -i eth0 'src port 80'
tcpdump -i eth0 'dst port 80'
# Inbound/outbound (relative to interface)
tcpdump -i eth0 'inbound' # Packets arriving
tcpdump -i eth0 'outbound' # Packets leaving
TCP Flag Filters
# TCP flags
tcpdump -i eth0 'tcp[tcpflags] & tcp-syn != 0' # SYN set
tcpdump -i eth0 'tcp[tcpflags] & tcp-ack != 0' # ACK set
tcpdump -i eth0 'tcp[tcpflags] & tcp-fin != 0' # FIN set
tcpdump -i eth0 'tcp[tcpflags] & tcp-rst != 0' # RST set
tcpdump -i eth0 'tcp[tcpflags] & tcp-push != 0' # PSH set
# Common combinations
tcpdump -i eth0 'tcp[tcpflags] == tcp-syn' # SYN only
tcpdump -i eth0 'tcp[tcpflags] == tcp-syn|tcp-ack' # SYN-ACK
tcpdump -i eth0 'tcp[tcpflags] & (tcp-syn|tcp-fin) != 0' # Connection start/end
# Numeric flag values (alternative syntax)
# SYN=0x02, ACK=0x10, FIN=0x01, RST=0x04, PSH=0x08
tcpdump -i eth0 'tcp[13] & 2 != 0' # SYN
tcpdump -i eth0 'tcp[13] == 18' # SYN-ACK (0x12)
Packet Size Filters
# By packet length
tcpdump -i eth0 'greater 1000' # Packets > 1000 bytes
tcpdump -i eth0 'less 64' # Packets < 64 bytes
# Alternative syntax
tcpdump -i eth0 'len > 1000'
tcpdump -i eth0 'len < 64'
tcpdump -i eth0 'len >= 64 and len <= 128'
Byte Offset Filters
# Access specific bytes in packet
# Format: protocol[offset:size]
# IP header
tcpdump -i eth0 'ip[0] & 0x0f > 5' # IP options present (IHL > 5)
tcpdump -i eth0 'ip[8] < 64' # TTL < 64
tcpdump -i eth0 'ip[9] = 6' # Protocol = TCP (6)
# TCP header
tcpdump -i eth0 'tcp[12] > 20' # TCP header > 20 bytes (options)
tcpdump -i eth0 'tcp[13] = 2' # SYN flag only
# ICMP
tcpdump -i eth0 'icmp[0] = 8' # ICMP echo request
tcpdump -i eth0 'icmp[0] = 0' # ICMP echo reply
Common Capture Scenarios
Troubleshooting Connectivity
# See all traffic to/from a host
tcpdump -i eth0 -nn host 192.168.1.100
# DNS queries
tcpdump -i eth0 -nn 'port 53'
tcpdump -i eth0 -nn -vvv 'port 53' # See query details
# DHCP traffic
tcpdump -i eth0 -nn 'port 67 or port 68'
# ARP traffic
tcpdump -i eth0 -nn arp
# ICMP (ping)
tcpdump -i eth0 -nn icmp
# Specific conversation
tcpdump -i eth0 -nn 'host 192.168.1.1 and host 192.168.1.2'
Web Traffic Analysis
# HTTP traffic
tcpdump -i eth0 -nn 'port 80'
# HTTPS traffic
tcpdump -i eth0 -nn 'port 443'
# HTTP and HTTPS
tcpdump -i eth0 -nn 'port 80 or port 443'
# HTTP GET requests (content inspection)
tcpdump -i eth0 -nn -A 'port 80' | grep -E '^GET|^Host:'
# HTTP POST requests
tcpdump -i eth0 -nn -A 'port 80' | grep -E '^POST|^Host:|^Content-'
# Show HTTP request/response
tcpdump -i eth0 -nn -A -s0 'tcp port 80 and (((ip[2:2] - ((ip[0]&0xf)<<2)) - ((tcp[12]&0xf0)>>2)) != 0)'
Connection Analysis
# New TCP connections (SYN)
tcpdump -i eth0 -nn 'tcp[tcpflags] == tcp-syn'
# Completed handshakes (SYN-ACK)
tcpdump -i eth0 -nn 'tcp[tcpflags] == tcp-syn|tcp-ack'
# Connection resets
tcpdump -i eth0 -nn 'tcp[tcpflags] & tcp-rst != 0'
# Connection teardowns (FIN)
tcpdump -i eth0 -nn 'tcp[tcpflags] & tcp-fin != 0'
# Failed connections (RST after SYN)
tcpdump -i eth0 -nn '(tcp[tcpflags] == tcp-syn or tcp[tcpflags] & tcp-rst != 0)'
Security Analysis
# Port scan detection (many SYN, no SYN-ACK)
tcpdump -i eth0 -nn 'tcp[tcpflags] == tcp-syn'
# Null scan (no flags)
tcpdump -i eth0 -nn 'tcp[13] == 0'
# XMAS scan (FIN+PSH+URG)
tcpdump -i eth0 -nn 'tcp[13] == 41'
# SSH brute force (many connections to port 22)
tcpdump -i eth0 -nn 'dst port 22 and tcp[tcpflags] == tcp-syn' | \
awk '{print $3}' | cut -d. -f1-4 | sort | uniq -c | sort -rn
# Non-standard ports
tcpdump -i eth0 -nn 'tcp and not port 80 and not port 443 and not port 22'
Performance Analysis
# Large packets
tcpdump -i eth0 -nn 'greater 1400'
# Small packets (possible fragmentation issues)
tcpdump -i eth0 -nn 'less 64'
# Retransmissions (duplicate packets)
tcpdump -i eth0 -nn -v 'tcp' | grep -i 'retransmit'
# Zero window
tcpdump -i eth0 -nn 'tcp[14:2] = 0'
# ECN-capable traffic
tcpdump -i eth0 -nn 'ip[1] & 3 != 0'
tshark (Wireshark CLI)
Basic Usage
# Capture on interface
tshark -i eth0
# Capture to file
tshark -i eth0 -w capture.pcap
# Read from file
tshark -r capture.pcap
# List interfaces
tshark -D
# Capture filter (BPF)
tshark -i eth0 -f 'port 80'
# Display filter (Wireshark syntax)
tshark -i eth0 -Y 'http'
tshark -r capture.pcap -Y 'tcp.port == 80'
Display Filters
# Protocol filters
tshark -r capture.pcap -Y 'http'
tshark -r capture.pcap -Y 'dns'
tshark -r capture.pcap -Y 'tcp'
tshark -r capture.pcap -Y 'tls'
# Field-based filters
tshark -r capture.pcap -Y 'ip.addr == 192.168.1.1'
tshark -r capture.pcap -Y 'tcp.port == 80'
tshark -r capture.pcap -Y 'tcp.flags.syn == 1'
tshark -r capture.pcap -Y 'http.request.method == "GET"'
tshark -r capture.pcap -Y 'dns.qry.name contains "google"'
# Comparisons
tshark -r capture.pcap -Y 'frame.len > 1000'
tshark -r capture.pcap -Y 'ip.ttl < 64'
tshark -r capture.pcap -Y 'tcp.analysis.retransmission'
# Logical operators
tshark -r capture.pcap -Y 'http and ip.addr == 192.168.1.1'
tshark -r capture.pcap -Y 'tcp.port == 80 or tcp.port == 443'
tshark -r capture.pcap -Y 'not arp'
tshark -r capture.pcap -Y '!(tcp.port == 22)'
Output Formatting
# Default output
tshark -r capture.pcap
# Specific fields
tshark -r capture.pcap -T fields -e ip.src -e ip.dst -e tcp.port
# Field separator
tshark -r capture.pcap -T fields -E separator=, -e ip.src -e ip.dst
# JSON output
tshark -r capture.pcap -T json
# XML output
tshark -r capture.pcap -T pdml
# One-line summary
tshark -r capture.pcap -q -z io,stat,1
# Protocol hierarchy
tshark -r capture.pcap -q -z io,phs
Statistics
# Protocol hierarchy
tshark -r capture.pcap -q -z io,phs
# Endpoint statistics
tshark -r capture.pcap -q -z endpoints,ip
tshark -r capture.pcap -q -z endpoints,tcp
# Conversation statistics
tshark -r capture.pcap -q -z conv,ip
tshark -r capture.pcap -q -z conv,tcp
# HTTP statistics
tshark -r capture.pcap -q -z http,tree
tshark -r capture.pcap -q -z http_req,tree
# DNS statistics
tshark -r capture.pcap -q -z dns,tree
# Expert info (errors, warnings)
tshark -r capture.pcap -q -z expert
# Follow TCP stream
tshark -r capture.pcap -q -z follow,tcp,ascii,0
# IO graph data
tshark -r capture.pcap -q -z io,stat,1,"COUNT(frame)"
Extracting Data
# Extract HTTP objects
tshark -r capture.pcap --export-objects http,/tmp/http_objects/
# Extract specific fields
tshark -r capture.pcap -T fields -e dns.qry.name | sort -u
# Extract credentials (basic auth)
tshark -r capture.pcap -T fields -e http.authbasic
# Extract URIs
tshark -r capture.pcap -Y 'http.request' -T fields -e http.host -e http.request.uri
# Extract TLS SNI
tshark -r capture.pcap -Y 'tls.handshake.type == 1' -T fields -e tls.handshake.extensions_server_name
# Extract file hashes
tshark -r capture.pcap -Y 'http.content_type contains "application"' -T fields -e http.file_data
Wireshark GUI
Common Display Filters
# TCP/IP
ip.addr == 192.168.1.1
ip.src == 192.168.1.1
ip.dst == 192.168.1.1
tcp.port == 80
tcp.srcport == 80
tcp.dstport == 443
tcp.flags.syn == 1
tcp.flags.fin == 1
tcp.flags.rst == 1
tcp.analysis.retransmission
tcp.analysis.duplicate_ack
tcp.analysis.zero_window
# HTTP
http
http.request
http.response
http.request.method == "POST"
http.response.code == 200
http.response.code >= 400
http.host contains "google"
http.request.uri contains "/api/"
http.content_type contains "json"
# DNS
dns
dns.qry.name
dns.qry.name contains "example"
dns.flags.response == 0 # Queries only
dns.flags.response == 1 # Responses only
dns.flags.rcode != 0 # DNS errors
# TLS/SSL
tls
tls.handshake
tls.handshake.type == 1 # Client Hello
tls.handshake.type == 2 # Server Hello
tls.handshake.extensions_server_name
tls.record.content_type == 23 # Application data
# Other protocols
arp
icmp
dhcp
ssh
ftp
smtp
Following Streams
In Wireshark GUI:
-
Right-click on packet
-
Follow → TCP Stream (or UDP/TLS/HTTP)
-
View decoded conversation
Or via menu: Analyze → Follow → TCP Stream
Practical Examples
Capturing for Later Analysis
# Capture with rotation, full packets
tcpdump -i eth0 -s0 -w /var/log/capture/traffic.pcap \
-C 100 -W 50 -Z root
# Capture specific traffic for analysis
tcpdump -i eth0 -s0 -w suspicious.pcap \
'host 192.168.1.100 and (port 80 or port 443)'
# Background capture with ring buffer
nohup tcpdump -i eth0 -w /tmp/ring.pcap -W 10 -C 100 &
Analyzing HTTP Traffic
# Count HTTP methods
tshark -r capture.pcap -Y 'http.request' -T fields -e http.request.method | \
sort | uniq -c | sort -rn
# Top requested URLs
tshark -r capture.pcap -Y 'http.request' -T fields -e http.host -e http.request.uri | \
sort | uniq -c | sort -rn | head -20
# Response codes distribution
tshark -r capture.pcap -Y 'http.response' -T fields -e http.response.code | \
sort | uniq -c | sort -rn
# Slow responses (> 1 second)
tshark -r capture.pcap -Y 'http.time > 1' -T fields -e http.host -e http.time
DNS Analysis
# All DNS queries
tshark -r capture.pcap -Y 'dns.flags.response == 0' -T fields -e dns.qry.name | \
sort | uniq -c | sort -rn
# Failed DNS lookups
tshark -r capture.pcap -Y 'dns.flags.rcode != 0' -T fields \
-e dns.qry.name -e dns.flags.rcode
# DNS response times
tshark -r capture.pcap -Y 'dns.flags.response == 1' -T fields \
-e dns.qry.name -e dns.time
# External DNS servers used
tshark -r capture.pcap -Y 'dns and ip.dst != 192.168.1.1' -T fields -e ip.dst | \
sort -u
TCP Connection Analysis
# Connection summary
tshark -r capture.pcap -q -z conv,tcp
# Retransmissions
tshark -r capture.pcap -Y 'tcp.analysis.retransmission' | wc -l
# Zero windows
tshark -r capture.pcap -Y 'tcp.analysis.zero_window' | wc -l
# RST packets
tshark -r capture.pcap -Y 'tcp.flags.rst == 1' -T fields \
-e ip.src -e ip.dst -e tcp.srcport -e tcp.dstport
# Connection attempts per source
tshark -r capture.pcap -Y 'tcp.flags.syn == 1 and tcp.flags.ack == 0' \
-T fields -e ip.src | sort | uniq -c | sort -rn
TLS/SSL Analysis
# TLS handshakes
tshark -r capture.pcap -Y 'tls.handshake' | wc -l
# SNI (Server Name Indication)
tshark -r capture.pcap -Y 'tls.handshake.type == 1' -T fields \
-e tls.handshake.extensions_server_name | sort -u
# TLS versions
tshark -r capture.pcap -Y 'tls.handshake.type == 1' -T fields \
-e tls.record.version | sort | uniq -c
# Certificate information
tshark -r capture.pcap -Y 'tls.handshake.type == 11' -T fields \
-e x509sat.uTF8String
# Failed TLS handshakes
tshark -r capture.pcap -Y 'tls.alert' -T fields \
-e ip.src -e ip.dst -e tls.alert.description
Remote Capture
Troubleshooting
Permission Issues
# Check capabilities
getcap /usr/sbin/tcpdump
# Add capture capability
setcap cap_net_raw,cap_net_admin=eip /usr/sbin/tcpdump
# Or run as root
sudo tcpdump -i eth0
# Add user to wireshark group
usermod -aG wireshark $USER
# Logout and login required
High Packet Loss
# Check dropped packets
tcpdump -i eth0 -w /dev/null 2>&1 | grep dropped
# Increase buffer size
tcpdump -i eth0 -B 8192 -w capture.pcap
# Increase kernel buffer
sysctl -w net.core.rmem_max=8388608
sysctl -w net.core.rmem_default=8388608
# Use ring buffer to files
tcpdump -i eth0 -w capture.pcap -C 100 -W 10
Quick Command Reference
# === tcpdump ===
# Basic capture
tcpdump -i eth0 -nn # Capture, no resolution
tcpdump -i eth0 -w file.pcap # Save to file
tcpdump -r file.pcap # Read file
tcpdump -i eth0 -c 100 # Capture 100 packets
# Filters
tcpdump -i eth0 'host 192.168.1.1' # Specific host
tcpdump -i eth0 'port 80' # Specific port
tcpdump -i eth0 'tcp and port 443' # Protocol and port
tcpdump -i eth0 'src 192.168.1.1' # Source filter
tcpdump -i eth0 'dst port 80' # Destination port
# Output
tcpdump -i eth0 -X # Hex + ASCII
tcpdump -i eth0 -A # ASCII only
tcpdump -i eth0 -vvv # Maximum verbosity
# === tshark ===
tshark -i eth0 # Live capture
tshark -r file.pcap # Read file
tshark -Y 'http' # Display filter
tshark -T fields -e ip.src -e ip.dst # Specific fields
tshark -q -z io,phs # Protocol hierarchy
tshark -q -z conv,tcp # Conversations
tshark -q -z expert # Expert analysis
tshark --export-objects http,./objects/ # Extract files
# === editcap ===
editcap -c 10000 in.pcap out.pcap # Split by count
editcap -i 3600 in.pcap out.pcap # Split by time
editcap -A "2024-01-01 00:00:00" in.pcap out.pcap # Time filter
# === mergecap ===
mergecap -w out.pcap in1.pcap in2.pcap # Merge files
# === capinfos ===
capinfos capture.pcap # File statistics