刚接一个线上问题,服务端接口偶发超时,日志打了,代码翻了几遍也没看出毛病。同事随口一句"抓包看看呗",我熟练地在终端敲下一行命令就开始抓包,心里却突然想起几年前刚接触 tcpdump 时,对着 man 手册一脸懵的样子。那时候连 -i any 都不知道,抓了半天全是错误提示。
tcpdump 是 Linux 下最经典的命令行抓包工具,没有图形界面,但胜在轻量、灵活、覆盖面广。它既能抓普通网卡流量,也能抓 loopback 环回口,还能配合各种过滤表达式精准定位某一类报文。无论是排查网络不通、定位接口超时,还是分析 TCP 握手异常、验证协议实现是否符合预期,tcpdump 都是第一选择。这篇文章就把它从安装到实战、从参数到排障完整过一遍,适合刚上手的新人,也适合已经用过但想系统补漏的同学。
1. 为什么是 tcpdump:一次抓包救场的经历
1.1 从一次线上事故说起
那次接口超时的排查,最后靠 tcpdump 收尾。客户端调用服务端接口,偶发性延迟 3 到 5 秒,但又不是每次都发生。代码里查不到可疑日志,数据库慢查询也没有,监控面板上 CPU、内存、带宽都正常。当时我们的第一反应是代码问题,结果越查越偏。
后来在服务端网卡上抓包,命令很简单:
bash复制tcpdump -i eth0 -nn 'tcp port 8080' -w /tmp/issue.pcap -c 5000
抓了五分钟,拿 pcap 文件用 Wireshark 打开,看 TCP 流的时序图。问题一下就清楚了:客户端发送请求后,服务端一直没有回复 ACK,隔了 3 秒才出现一个 TCP Dup ACK,随后重传。继续往上追,发现服务端进程确实收到了数据,但业务线程池在等一个分布式锁,锁等待超时才返回。这就把问题从"网络层"拉回了"应用层",但如果没有抓包定位到这个现象,我们可能还在代码里瞎猜。
这就是 tcpdump 最核心的价值:在网络层和应用层之间架起一座看得见的桥。代码把数据交给内核协议栈之后,到底发生了什么,日志往往看不到,tcpdump 能看到。
1.2 它和 Wireshark、Charles 这类工具怎么分工
很多新人会问:有 Wireshark 图形界面,为什么还要用 tcpdump?
实际场景里,生产服务器大多没有图形界面,只有命令行。Wireshark 再强大,你也得先把流量抓下来再分析,而抓流量这个动作本身就是 tcpdump 的活。所以常见的组合是:服务器上用 tcpdump 抓包保存成 pcap 文件,传到本地用 Wireshark 做可视化分析。tcpdump 负责采集,Wireshark 负责分析,两者是上下游关系。
至于 Charles、Fiddler 这类工具,它们主要针对 HTTP/HTTPS 层面的抓包,能看请求头、响应体、Cookie,还能做断点修改。但它们的实现原理是代理,只处理应用层协议,对 TCP 重传、IP 分片、ARP 请求这些网络层问题完全无能为力。tcpdump 是直接挂在数据链路层上的,能看到 MAC 帧、IP 报文、TCP/UDP 报文段,属于更底层的抓包方式。
用一句话总结:Charles/Fiddler 是"应用层调试器",Wireshark 是"协议分析器",tcpdump 是"网络报文采集器"。三者的定位不同,适用的场景也不同。如果你连不上数据库、ping 不通网关、TCP 握手异常,第一反应应该是 tcpdump,而不是 Charles。
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. 环境准备:从安装到第一条抓包命令
2.1 在线安装与版本确认
大部分 Linux 发行版都自带 tcpdump,或者可以通过官方源直接安装。Debian/Ubuntu 系用 apt,CentOS/RHEL 系用 yum 或 dnf。
bash复制# Debian / Ubuntu
sudo apt-get update
sudo apt-get install -y tcpdump
# CentOS / RHEL 7/8
sudo yum install -y tcpdump
# CentOS / RHEL 9
sudo dnf install -y tcpdump
安装完确认版本,编译选项决定了功能差异,建议确认一下:
bash复制tcpdump --version
输出大致长这样:
text复制tcpdump version 4.9.3
libpcap version 1.9.1
OpenSSL 1.1.1k FIPS 26 Mar 2021
这里有两个信息要关注。第一是 libpcap 的版本,tcpdump 自身的版本号只是前端,真正的抓包能力由 libpcap 库提供。第二是 OpenSSL 字段,如果有这个字段说明支持加密流量解码的部分功能,但实际很有限,主要影响 -w 写文件时是否支持加密的 pcap 文件(极少用)。
注意:tcpdump 和 libpcap 是配套关系。如果后续发现抓包行为异常,先确认这两个版本是否兼容,尤其是离线安装时容易踩版本不匹配的坑。
2.2 离线安装的两种做法:rpm 包与源码编译
内网服务器没法访问外网源是常态,离线安装 tcpdump 有两个常用思路:
方式一:找同版本系统的 rpm/deb 包,离线安装
bash复制# 在有网的机器上下载,再拷贝到目标机器
yumdownloader --resolve tcpdump
# 或者
apt-get download tcpdump libpcap0.8
# 目标机器上安装
sudo rpm -ivh tcpdump-*.rpm libpcap-*.rpm
sudo dpkg -i tcpdump*.deb libpcap*.deb
这里的关键是 libpcap 必须一起装上,很多人只装 tcpdump 导致报 libpcap.so.1: cannot open shared object file,这就是典型的依赖缺失。
方式二:源码编译静态链接
如果目标机器的系统版本比较老,软件源里找不到合适的二进制包,源码编译更稳妥:
bash复制# 下载 libpcap 和 tcpdump 源码,版本要匹配
wget https://www.tcpdump.org/release/libpcap-1.10.4.tar.gz
wget https://www.tcpdump.org/release/tcpdump-4.99.4.tar.gz
# 先编译安装 libpcap
tar xzf libpcap-1.10.4.tar.gz
cd libpcap-1.10.4
./configure --prefix=/usr/local
make -j$(nproc)
sudo make install
# 再编译 tcpdump
export LDFLAGS="-L/usr/local/lib"
export CPPFLAGS="-
