tshark命令行版WireShark
安装命令:yum install -y wireshark
在Linux下,当我们需要抓取网络数据包分析时,通常是使用tcpdump抓取网络raw数据包存到一个文件,然后下载到本地使用wireshark界面网络分析工具进行网络包分析。
最近才发现,原来wireshark也提供有Linux命令行工具-tshark。tshark不仅有抓包的功能,还带了解析各种协议的能力。下面我们以两个实例来介绍tshark工具。
主要参数:
1. 抓包接口类
- -i 设置抓包的网络接口,不设置则默认为第一个非自环接口。
- -D 列出当前存在的网络接口。在不了解OS所控制的网络设备时,一般先用“tshark -D”查看网络接口的编号以供-i参数使用。
- -f 设定抓包过滤表达式(capture filter expression)。抓包过滤表达式的写法雷同于tcpdump,可参考tcpdump man page的有关部分。
- -s 设置每个抓包的大小,默认为65535,多于这个大小的数据将不会被程序记入内存、写入文件。(这个参数相当于tcpdump的-s,tcpdump默认抓包的大小仅为68)
- -p 设置网络接口以非混合模式工作,即只关心和本机有关的流量。
- -B 设置内核缓冲区大小,仅对windows有效。
- -y 设置抓包的数据链路层协议,不设置则默认为-L找到的第一个协议,局域网一般是EN10MB等。
- -L 列出本机支持的数据链路层协议,供-y参数使用。
2. 抓包停止条件
- -c 抓取的packet数,在处理一定数量的packet后,停止抓取,程序退出。
- -a 设置tshark抓包停止向文件书写的条件,事实上是tshark在正常启动之后停止工作并返回的条件。条件写为test:value的形式,如“-a duration:5”表示tshark启动后在5秒内抓包然后停止;“-a filesize:10”表示tshark在输出文件达到10kB后停止;“-a files:n”表示tshark在写满n个文件后停止。(windows版的tshark0.99.3用参数“-a files:n”不起作用——会有无数多个文件生成。由于-b参数有自己的files参数,所谓“和-b的其它参数结合使用”无从说起。这也许是一个bug,或tshark的man page的书写有误。)
3. 文件输出控制
- -b 设置ring buffer文件参数。ring buffer的文件名由-w参数决定。-b参数采用test:value的形式书写。“-b duration:5”表示每5秒写下一个ring buffer文件;“-b filesize:5”表示每达到5kB写下一个ring buffer文件;“-b files:7”表示ring buffer文件最多7个,周而复始地使用,如果这个参数不设定,tshark会将磁盘写满为止。
4. 文件输入
- -r 设置tshark分析的输入文件。tshark既可以抓取分析即时的网络流量,又可以分析dump在文件中的数据。-r不能是命名管道和标准输入。
5. 处理类
- -R 设置读取(显示)过滤表达式(read filter expression)。不符合此表达式的流量同样不会被写入文件。注意,读取(显示)过滤表达式的语法和底层相关的抓包过滤表达式语法不相同,它的语法表达要丰富得多,请参考http://www.ethereal.com/docs/dfref/和http://www.ethereal.com/docs/man-pages/ethereal-filter.4.html。类似于抓包过滤表达式,在命令行使用时最好将它们quote起来。
- -n 禁止所有地址名字解析(默认为允许所有)。
- -N 启用某一层的地址名字解析。“m”代表MAC层,“n”代表网络层,“t”代表传输层,“C”代表当前异步DNS查找。如果-n和-N参数同时存在,-n将被忽略。如果-n和-N参数都不写,则默认打开所有地址名字解析。
- -d 将指定的数据按有关协议解包输出。如要将tcp 8888端口的流量按http解包,应该写为“-d tcp.port==8888,http”。注意选择子和解包协议之间不能留空格。
6. 输出类
- -w 设置raw数据的输出文件。这个参数不设置,tshark将会把解码结果输出到stdout。“-w-”表示把raw输出到stdout。如果要把解码结果输出到文件,使用重定向“>”而不要-w参数。
- -F 设置输出raw数据的格式,默认为libpcap。“tshark -F”会列出所有支持的raw格式。
- -V 设置将解码结果的细节输出,否则解码结果仅显示一个packet一行的summary。
- -x 设置在解码输出结果中,每个packet后面以HEX dump的方式显示具体数据。
- -T 设置解码结果输出的格式,包括text,ps,psml和pdml,默认为text。
- -t 设置解码结果的时间格式。“ad”表示带日期的绝对时间,“a”表示不带日期的绝对时间,“r”表示从第一个包到现在的相对时间,“d”表示两个相邻包之间的增量时间(delta)。
- -S 在向raw文件输出的同时,将解码结果打印到控制台。
- -l 在处理每个包时即时刷新输出。
- -X 扩展项。
- -q 设置安静的stdout输出(例如做统计时)
- -z 设置统计参数。
7. 其它
- -h 显示命令行帮助。
- -v 显示tshark的版本信息。
- -o 重载选项。
1,实时打印当前http请求的url
# tshark -s 512 -i eth0 -n -f 'tcp dst port 80' -R 'http.host and http.request.uri' -T fields -e http.host -e http.request.uri -l | tr -d '\t'
参数含义:
-s 512 :只抓取前512个字节数据
-i eth0 :捕获eth0网卡
-n :禁止网络对象名称解析
-f 'tcp dst port 80' :只捕捉协议为tcp,目的端口为80的数据包
-R 'http.host and http.request.uri' :过滤出http.host和http.request.uri
-T fields -e http.host -e http.request.uri :打印http.host和http.request.uri
-l :输出到标准输出
查看捕获包的摘要信息:
tshark -i <interface> -q -z <statistics>
tshark -i eth0 -q -z "http,stats"
tshark -i ens33 -q -z io,stat,1,"MIN(tcp.analysis.ack_rtt)tcp.analysis.ack_rtt","MAX(tcp.analysis.ack_rtt)tcp.analysis.ack_rtt","AVG(tcp.analysis.ack_rtt)tcp.analysis.ack_rtt"
-q
: 以安静模式运行,减少输出的冗余信息
io
: 指定进行IO统计。stat
: 指定进行统计操作。1
: 指定统计周期为1秒。"MIN(tcp.analysis.ack_rtt)tcp.analysis.ack_rtt"
: 统计TCP确认应答时间的最小值。"MAX(tcp.analysis.ack_rtt)tcp.analysis.ack_rtt"
: 统计TCP确认应答时间的最大值。"AVG(tcp.analysis.ack_rtt)tcp.analysis.ack_rtt"
: 统计TCP确认应答时间的平均值。
HTTP响应时间分析
//按秒汇总每个http response 耗时
tshark -r dump.pcap -Y 'http.time>0 ' -T fields -e frame.number -e frame.time_epoch -e frame.time_delta_displayed -e ip.src -e ip.dst -e tcp.stream -e http.request.full_uri -e http.response.code -e http.time | awk '{ print int($2), $8 }' | awk '{ sum[$1]+=$2; count[$1]+=1 ;} END { for (key in count) { printf "time= %s \t count=%s \t avg=%.6f \n", key, count[key], sum[key]/count[key] } }' | sort -k2n | awk '{ print strftime("%c",$2), $0 }'
//on macOS
tshark -r dump.pcap -Y 'http.response_for.uri contains "health" ' -T fields -e frame.number -e frame.time_epoch -e frame.time_delta_displayed -e ip.src -e ip.dst -e tcp.stream -e http.request.full_uri -e http.response_for.uri -e http.time | awk '{ print int($2/10), $8 }' | awk '{ sum[$1]+=$2; count[$1]+=1 ;} END { for (key in count) { printf "time= %s \t count=%s \t avg=%.6f \n", key, count[key], sum[key]/count[key] } }' | sort -k2n | gawk '{ print strftime("%c",$2), $0 }'
tshark -r ./dhttp.pcap -o tcp.calculate_timestamps:true -Y "http.request or http.response" -T fields -e frame.number -e frame.time_epoch -e tcp.time_delta -e ip.src -e ip.dst -e tcp.stream -e http.request.full_uri -e http.response.code -e http.response.phrase | sort -nk6 -nk1
第三列是RT,倒数第二列是stream,同一个stream是一个连接。对应http response 200的是请求响应结果的RT
分析每个包的response time
$ tshark -r rsb2.cap -o tcp.calculate_timestamps:true -T fields -e frame.number -e frame.time_epoch -e ip.src -e ip.dst -e tcp.stream -e tcp.len -e tcp.analysis.initial_rtt -e tcp.time_delta
分析每个会话的流量
$ tshark -r retrans.cap -q -z 'conv,tcp'
tshark -i ens33 -q -z 'conv,tcp'
分析每两个IP之间的流量
tshark -i ens33 -q -z 'conv,ip'
分析有问题的包、概览
tshark -i ens33 -q -z 'expert,note'
分析rtt、丢包、deplicate等等
tshark -r retrans.cap -q -z io,stat,1,”AVG(tcp.analysis.ack_rtt)tcp.analysis.ack_rtt”,
”COUNT(tcp.analysis.retransmission) tcp.analysis.retransmission”,
”COUNT(tcp.analysis.fast_retransmission) tcp.analysis.fast_retransmission”,
”COUNT(tcp.analysis.duplicate_ack) tcp.analysis.duplicate_ack”,
”COUNT(tcp.analysis.lost_segment) tcp.analysis.lost_segment”,
”MIN(tcp.window_size)tcp.window_size”
分析丢包、duplicate ack
$ tshark -r retrans.cap -q -z io,stat,5,”COUNT(tcp.analysis.retransmission) tcp.analysis.retransmission”,”COUNT(tcp.analysis.fast_retransmission) tcp.analysis.fast_retransmission”,”COUNT(tcp.analysis.duplicate_ack) tcp.analysis.duplicate_ack”,”COUNT(tcp.analysis.lost_segment) tcp.analysis.lost_segment”
分析rtt 时间
$ tshark -r ~/ali/metrics/tcpdump/rsb2.cap -q -z io,stat,1,”MIN(tcp.analysis.ack_rtt)tcp.analysis.ack_rtt”,”MAX(tcp.analysis.ack_rtt)tcp.analysis.ack_rtt”,”AVG(tcp.analysis.ack_rtt)tcp.analysis.ack_rtt”
计算window size
$ tshark -r rsb-single2.cap -q -z io,stat,5,”COUNT(tcp.analysis.retransmission) tcp.analysis.retransmission”,”AVG(tcp.window_size) tcp.window_size”,”MAX(tcp.window_size) tcp.window_size”,”MIN(tcp.window_size) tcp.window_size”
常用排错过滤条件:
对于排查网络延时/应用问题有一些过滤条件是非常有用的:
- tcp.analysis.lost_segment:表明已经在抓包中看到不连续的序列号。报文丢失会造成重复的ACK,这会导致重传。
- tcp.analysis.duplicate_ack:显示被确认过不止一次的报文。大量的重复ACK是TCP端点之间高延时的迹象。
- tcp.analysis.retransmission:显示抓包中的所有重传。如果重传次数不多的话还是正常的,过多重传可能有问题。这通常意味着应用性能缓慢和/或用户报文丢失。
- tcp.analysis.window_update:将传输过程中的TCP window大小图形化。如果看到窗口大小下降为零,这意味着发送方已经退出了,并等待接收方确认所有已传送数据。这可能表明接收端已经不堪重负了。
- tcp.analysis.bytes_in_flight:某一时间点网络上未确认字节数。未确认字节数不能超过你的TCP窗口大小(定义于最初3此TCP握手),为了最大化吞吐量你想要获得尽可能接近TCP窗口大小。如果看到连续低于TCP窗口大小,可能意味着报文丢失或路径上其他影响吞吐量的问题。
- tcp.analysis.ack_rtt:衡量抓取的TCP报文与相应的ACK。如果这一时间间隔比较长那可能表示某种类型的网络延时(报文丢失,拥塞,等等)。
计算丢包情况
tshark -r wechat.pcap -q \
-z io,stat,1,"COUNT(tcp.analysis.retransmission) tcp.analysis.retransmission",
"COUNT(tcp.analysis.fast_retransmission) tcp.analysis.fast_retransmission","COUNT(tcp.analysis.duplicate_ack) tcp.analysis.duplicate_ack",
"COUNT(tcp.analysis.lost_segment) tcp.analysis.lost_segment"
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· SQL Server 2025 AI相关能力初探
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 开源Multi-agent AI智能体框架aevatar.ai,欢迎大家贡献代码
· Manus重磅发布:全球首款通用AI代理技术深度解析与实战指南