tcpdump抓包命令

tcpdump抓包命令

tcpdump是一个用于截取网络分组,并输出分组内容的工具。tcpdump凭借强大的功能和灵活的截取策略,使其成为类UNIX系统下用于网络分析和问题排查的首选工具。

tcpdump提供了源代码,公开了接口,因此具备很强的可扩展性,对于网络维护和入侵者都是非常有用的工具。tcpdump存在于基本的Linux系统中,由于它需要将网络界面设置为混杂模式,普通用户不能正常执行,但具备root权限的用户可以直接执行它来获取网络上的信息。因此系统中存在网络分析工具主要不是对本机安全的威胁,而是对网络上的其他计算机的安全存在威胁。

一、概述

顾名思义,tcpdump可以将网络中传送的数据包的“头”完全截获下来提供分析。它支持针对网络层、协议、主机、网络或端口的过滤,并提供and、or、not等逻辑语句来帮助你去掉无用的信息。

# tcpdump -vv # -vv表示显示详细的信息
tcpdump: listening on eth0, link-type EN10MB (Ethernet), capture size 96 bytes
11:53:21.444591 IP (tos 0x10, ttl 64, id 19324, offset 0, flags [DF], proto 6, length: 92)

asptest.localdomain.ssh > 192.168.228.244.1858: P 3962132600:3962132652(52) ack 2726525936 win 1266

asptest.localdomain.1077 > 192.168.228.153.domain: [bad udp cksum 166e!] 325+ PTR? 244.228.168.192.in-addr.arpa. (46)

11:53:21.446929 IP (tos 0x0, ttl 64, id 42911, offset 0, flags [DF], proto 17, length: 151) 192.168.228.153.domain > asptest.localdomain.1077: 325 NXDomain q: PTR? 244.228.168.192.in-addr.arpa. 0/1/0 ns: 168.192.in-addr.arpa. (123)

11:53:21.447408 IP (tos 0x10, ttl 64, id 19328, offset 0, flags [DF], proto 6, length: 172) asptest.localdomain.ssh > 192.168.228.244.1858: P 168:300(132) ack 1 win 1266

<==按下[ctrl]-c之后结束
347 packets captured
1474 packets received by filter
745 packets dropped by kernel

不带参数的tcpdump会收集网络中所有的信息包头,数据量巨大,必须过滤。

二、选项介绍

tcpdump采用命令行方式,它的命令大致如下:

tcpdump [ -AbdDefhHIJKlLnNOpqStuUvxX# ] [ -B buffer_size ]
               [ -c count ]
               [ -C file_size ] [ -G rotate_seconds ] [ -F file ]
               [ -i interface ] [ -j tstamp_type ] [ -m module ] [ -M secret ]
               [ --number ] [ -Q in|out|inout ]
               [ -r file ] [ -V file ] [ -s snaplen ] [ -T type ] [ -w file ]
               [ -W filecount ]
               [ -y datalinktype ] [ -z postrotate-command ] [ -Z user ]
               [ --immediate-mode ]
               [ expression ]

参数的含义如下:

参数 含义
-A 以ASCII格式打印出所有分组,通常用来抓取www的网页数据包数据。
-c 在收到指定的数量的分组后,tcpdump就会停止。
-C 在将一个原始分组写入文件之前,检查文件当前的大小是否超过了参数file_size 中指定的大小。如果超过了指定大小,则关闭当前文件,然后在打开一个新的文件。参数 file_size 的单位是兆字节(是1,000,000字节,而不是1,048,576字节)。
-d 将匹配信息包的代码以人们能够理解的汇编格式给出。
-dd 将匹配信息包的代码以c语言程序段的格式给出。
-ddd 将匹配信息包的代码以十进制的形式给出。
-D 打印出系统中所有可以用tcpdump截包的网络接口。
-e 在输出行打印出数据链路层的头部信息,也就是使用数据链路层的MAC数据包数据来显示.
-f 将外部的Internet地址以数字的形式打印出来。
-F 从指定的文件中读取表达式,忽略命令行中给出的表达式。
-i 指定监听的网络接口。
-l 使标准输出变为缓冲行形式,可以把数据导出到文件。
-L 列出网络接口的已知数据链路。
-b 在数据-链路层上选择协议,包括ip、arp、rarp、ipx都是这一层的。
-n 不把网络地址转换成名字。
-nn 不进行端口名称的转换。
-N 不输出主机名中的域名部分。例如,‘nic.ddn.mil‘只输出’nic‘。
-t 在输出的每一行不打印时间戳。
-O 不运行分组分组匹配(packet-matching)代码优化程序。
-P 不将网络接口设置成混杂模式。
-q 快速输出。只输出较少的协议信息。
-r 从指定的文件中读取包(这些包一般通过-w选项产生)。
-S 将tcp的序列号以绝对值形式输出,而不是相对值。
-s 从每个分组中读取最开始的snaplen个字节,而不是默认的68个字节。
-T 将监听到的包直接解释为指定的类型的报文,常见的类型有rpc远程过程调用)和snmp(简单网络管理协议)。
-t 不在每一行中输出时间戳。
-tt 在每一行中输出非格式化的时间戳
-ttt 输出本行和前面一行之间的时间差。
-tttt 在每一行中输出由date处理的默认格式的时间戳。
-v 输出一个稍微详细的信息,例如在ip包中可以包括ttl和服务类型的信息。
-vv 输出详细的报文信息。
-w 直接将分组写入文件中,而不是不分析并打印出来。
-X 可以列出16进制以及ASCII的数据包内容,对于监听数据包内容很有用.

推荐的一些写法:

tcpdump -ntv -i xxx # -n表示不将网络地址转化为名称,-t不输出时间戳,-v输出一些比较详细的信息(这个很好用)

三、tcpdump的表达式介绍

表达式对应命令参数中最后的可省略的expression.tcpdump利用它作为过滤报文的条件,如果一个报文满足表 达式的条件,则这个报文将会被捕获。如果没有给出任何条件,则网络上所有的信息包 将会被截获。

表达式(expression)实际遵循的是bpf的语法,有关于bpf的相关介绍,可以查看这个页面:
https://biot.com/capstats/bpf.html,下面的部分,基本是此页面的翻译.

在表达式中一般如下几种类型的关键字:

表达式由一个或多个表达元组成(nt: primitive, 表达元, 可理解为组成表达式的基本元素). 一个表达元通常由一个或多个修饰符(qualifiers)后跟一个名字或数字表示的id组成(nt: 即, qualifiers id).

有三种不同类型的修饰符(或者说限定符):type, dir以及 proto.

type 修饰符指定id 所代表的对象类型, id可以是名字也可以是数字. 可选的对象类型有: host, net, port 以及portrange(nt: host 表明id表示主机, net表明id是网络, port 表明id是端口, 而portrange表明id是一个端口范围). 如, host foo, net 128.3, port 20, portrange 6000-6008(nt: 分别表示主机foo, 网络128.3, 端口20, 端口范围 6000-6008). 如果不指定type修饰符, id默认的修饰符为host.

dir 修饰符描述id 所对应的传输方向, 即发往id 还是从id 接收(nt: 而id到底指什么需要看其前面的type修饰符).可取的方向为: src, dst, src or dst, src and dst.(nt:分别表示, id是传输源, id是传输目的, id是传输源或者传输目的, id是传输源并且是传输目的). 例如, src foo,dst net 128.3, src or dst port ftp-data.(nt: 分别表示符合条件的数据包中, 源主机是foo, 目的网络是128.3, 源或目的端口为 ftp-data).如果不指定dir修饰符, id 默认的修饰符为src or dst.

proto修饰符描述id所属的协议. 常用的协议有: ether, wlan, ip, ip6, arp, rarp, tcp以及 upd.(nt | rt: ether可理解为物理以太网传输协议; wlan, 无线局域网协议; ip,ip6 即通常的TCP/IP协议栈中所使用的ipv4以及ipv6网络层协议;arp, rarp 即地址解析协议, 反向地址解析协议; tcp and udp, 即通常TCP/IP协议栈中的两个传输层协议).

例如, ether src foo, arp net 128.3, tcp port 21, udp portrange 7000-7009分别表示从以太网地址foo 来的数据包,发往或来自128.3网络的arp协议数据包, 发送或接收端口为21的 tcp协议数据包, 发送或接收端口范围为7000-7009的udp协议数据包.

如果不指定proto 修饰符, 则默认为与相应type匹配的修饰符.

例子:

  1. src foo 含义是 (ip or arp or rarp) src foo (nt: 即, 来自主机fooip/arp/rarp协议数据包, 默认typehost).
  2. net bar 含义是(ip or arp or rarp) net bar (nt: 即, 来自或发往bar网络的ip/arp/rarp协议数据包).
  3. port 53 含义是 (tcp or udp) port 53(nt: 即, 发送或接收端口为53tcp/udp协议数据包).

对于修饰符后跟id的格式,可理解为, type id是对包最基本的过滤条件: 即对包相关的主机, 网络, 端口的限制; dir 表示对包的传送方向的限制; proto表示对包相关的协议限制)

除以上所描述的表达元('primitive'), 还有其他形式的表达元, 并且与上述表达元格式不同. 比如: gateway, broadcast, less, greater以及算术表达式(nt: 其中每一个都算一种新的表达元). 下面将会对这些表达元进行说明.

表达元之间还可以通过关键字and, or以及 not 进行连接, 从而可组成比较复杂的条件表达式. 比如,
host foo and not port ftp and not port ftp-data(nt: 其过滤条件可理解为, 数据包的主机为foo,并且端口不是ftp(端口21) 和ftp-data(端口20, 常用端口和名字的对应可在linux 系统中的/etc/service文件中找到)).

为了表示方便, 同样的修饰符可以被省略, 如tcp dst port ftp or ftp-data or domain与以下的表达式含义相同tcp dst port ftp or tcp dst port ftp-data or tcp dst port domain.(nt: 其过滤条件可理解为,包的协议为tcp, 目的端口为ftpftp-datadomain(端口53) ).

可用的表达元

==========================================
dst host host
如果IPv4/v6 数据包的目的ip地址是host, 那么捕获该数据包.host 可以是一个ip地址, 也可以是一个主机名.

src host host
如果IPv4/v6 数据包的源ip地址是host, 则捕获该数据包.host 可以是一个ip地址, 也可以是一个主机名.

host host
如果IPv4/v6数据包的源或目的ip地址是host, 则捕获该数据包.以上的几个host 表达式之前可以添加以下关键字:ip, arp, rarp, 以及 ip6.比如:

ip host host

也可以表达为:

ether proto \ip and host host # 这种表达方式在下面有说明, 其中ip之前需要有\来转义,因为ip 对tcpdump 来说已经是一个关键字了.

如果host是一个拥有多个IP的主机, 那么任何一个地址都会用于包的匹配(nt: 即发向host 的数据包的目的地址可以是这几个IP中的任何一个, 从host 接收的数据包的源地址也可以是这几个IP中的任何一个).

==========================================
ether dst ehost
如果数据包(nt: 指tcpdump 可抓取的数据包, 包括ip 数据包, tcp数据包)的以太网目标地址是ehost,则捕获该数据包.

ehost 可以是/etc/ethers 文件中的名字或一个数字地址(nt: 可通过 man ethers 看到对/etc/ethers 文件的描述, 样例中用的是数字地址)

ether src ehost
如果数据包的以太网源地址是ehost(mac地址), 则捕获该数据包.

ether host ehost
如果数据包的以太网源地址或目标地址是ehost, 则捕获该数据包..

==========================================

dst net net
如果数据包的目标地址(IPv4或IPv6格式)的网络号字段为net, 则捕获该数据包.

net可以是从网络数据库文件/etc/networks 中的名字, 也可以用数字形式的来表示.

一个数字IPv4 网络号可以用点分四元组(比如, 192.168.1.0), 或点分三元组(比如, 192.168.1), 或点分二元组(比如, 172.16), 或单一单元组(比如,10)来表示.

这四种情况对应的网络掩码分别为:四元组:255.255.255.255(这实际上已经是是一个具体的网络地址了),三元组:255.255.255.0, 二元组:255.255.0.0, 一元组:255.0.0.0.

src net net
如果数据包的源地址(IPv4或IPv6格式)的网络号字段为 net, 则捕获该数据包.

net net
如果数据包的源或目的地址(IPv4或IPv6格式)的网络号字段为 net, 则捕获该数据包.

net net mask netmask
如果数据包的源或目的ip地址的网络掩码与netmask匹配, 则捕获该数据包.

此选项之前还可以配合srcdst来进一步限定数据包的来源,比如.

src net 192.168.1.0 mask 255.255.255.0 

net net/len
如果数据包的源或目的地址(IPv4或IPv6格式)的属于该网段(net/len表示的网段), 则捕获该数据包.

此选项之前还可以配合srcdst来进一步限定数据包的来源.

src net 192.168.1.0/24 # 表示需要匹配源地址的网络编号有24位的数据包

dst port port
如果数据包(包括ip/tcp, ip/udp, ip6/tcp or ip6/udp协议)的目的端口为port, 则捕获该数据包.

port 可以是一个数字也可以是一个名字(相应名字可以在/etc/services 中找到该名字, 也可以通过man tcpman udp来得到相关描述信息 ). 推荐使用数字.

dst port 80 # 监听目的端口为80的数据包

src port port
如果数据包的源端口为port, 则捕获该数据包.

port port
如果数据包的源或目的端口为port, 则捕获该数据包.

==========================================
dst portrange port1-port2
监听目的端口在[port1, port2]的数据包,当然,既然存在端口,那么这个数据包必然属于ip/tcp, ip/udp, ip6/tcp 或者ip6/udp这几种中的一种.

src portrange port1-port2
监听源端口在[port1, port2]范围内的数据包.

portrange port1-port2
如果数据包的源端口或目的端口在[port1,port2]这个端口范围, 则捕获该数据包.以上关于port 的选项都可以在其前面添加关键字:tcp 或者udp对数据包加以更严格的限定.

tcp src port 80 # 抓取源端口是80的tcp数据包

==========================================

less length
如果数据包的长度比length 小或等于length, 则捕获该数据包. 这与len <= length的含义一致.

greater length
如果数据包的长度比length 大或等于length, 则捕获该数据包. 这与len >= length的含义一致.

==========================================

ip proto protocol
如果数据包为ipv4数据包并且其协议类型为protocol, 则与此对应的条件表达式为真.protocol可以是一个数字也可以是名字, 比如:icmp, pim, udp, tcp等. 由于tcp , udp 以及icmp是tcpdump 的关键字,所以在这些协议名字之前必须要用\来进行转义(如果在C-shell 中需要用\来进行转义). 有时候为了书写方便,我们可以直接用tcp, upd, icmp来替换,这个其实是

ip proto p or ip6 proto p

的缩写,p指代tcp,upd以及icmp.

 tcpdump -i eth0 'ip proto \tcp and host 192.168.3.144

则只打印主机192.168.3.144发出或接收的数据包中tcp 协议头所包含的信息)

==========================================
ether broadcast
如果数据包是以太网广播数据包, 则捕获该数据包. ether 关键字是可选的.

ip broadcast
如果数据包是IPv4广播数据包, 则捕获该数据包.

==========================================

ether multicast
如果数据包是一个以太网多点广播数据包,则捕获该数据包.关键字ether可以省略.

ip multicast
如果数据包是ipv4多点广播数据包, 则捕获该数据包.

==========================================

ether proto protocol
如果数据包属于以下以太协议类型, 则与此对应的条件表达式为真.协议(protocol)字段, 可以是数字或以下所列出的名字: ip, ip6, arp, rarp, stp(Spanning tree protocol, 生成树协议, 可用于防止网络中产生链接循环)等.必须要注意的是如果标识符也是关键字, 从而必须通过\来进行转义.
有时候为了书写方便,我们往往直接使用ip, ip6, arp, rarp, aarp, decnet, stp来代替,它们其实是

ether proto p

的一个省略形式,p表示ip, ip6...

expr relop expr
如果关系为真,就抓取此类数据包. relop可以是>, <, >=, <=, =, !=之一, expr是一个算数表达式,它由整数常量,常规的二进制操作符,如[+, -, *, /, &, |, <<, >>],长度操作符,包数据访问器组成.值得注意的是,所有的组成部分都是无符号的,举个例子, 0x80000000 and 0xffffffff 大于0.可以使用下面的语法,来获取包中的数据:

proto [ expr : size ]

proto字段可以是 ether, fddi, wlan, ip, arp, rarp, tcp, udp, icmp, ip6等协议的名称,expr用于描述比特偏移,size是可选的,表示我们只对从偏移处开始的size字节的数据感兴趣,如果没有的话,默认值为1.

举个例子, ether[0] & 1 != 0可以抓取所有的多播流量,表达式ip[0] & 0xf != 5可以抓取到所有的带选项的ipv4包,表达式ip[6:2] & 0x1fff = 0可以抓取到所有未分片的ipv4包以及第一个ipv4分片包.

一些偏移量以及字段的值可以用名称来直接描述,比如说icmptype (ICMP type字段), icmpcode (ICMP code字段), 以及tcpflags (TCP flags字段).

以下的ICMP字段的值是合法的: icmp-echoreply, icmp-unreach, icmp-sourcequench, icmp-redirect, icmp-echo, icmp-routeradvert, icmp-routersolicit, icmp-timxceed, icmp-paramprob, icmp-tstamp, icmp-tstampreply, icmp-ireq, icmp-ireqreply, icmp-maskreq, icmp-maskreply.

以下的TCP flags字段的值是合法的: tcp-fin, tcp-syn, tcp-rst, tcp-push, tcp-ack, tcp-urg.

四、输出结果介绍

下面我们介绍几种典型的tcpdump命令的输出信息

(1) 数据链路层头信息

使用命令:

#tcpdump --e host ICE

ICE是一台装有linux的主机。它的MAC地址是0:90:27:58:AF:1A, H219是一台装有Solaris的SUN工作站。它的MAC地址是8:0:20:79:5B:46.

上一条命令的输出结果如下所示:

21:50:12.847509 eth0 < 8:0:20:79:5b:46 0:90:27:58:af:1a ip 60: h219.33357 > ICE. telne t 0:0(0) ack 22535 win 8760 (DF)

21:50:12是显示的时间, 847509是ID号,eth0 > 表示从网络接口eth0接收该分组, 同理eth0 >表示从网络接口设备eth0发送分组,8:0:20:79:5b:46是主机H219的MAC地址, 它表明是从源地址H219发来的分组.0:90:27:58:af:1a 是主机ICE的MAC地址, 表示该分组的目的地址是ICE。 ip 是表明该分组是IP分组,60是分组的长度, h219.33357 > ICE. telnet 表明该分组是从主机H219的33357端口发往主机ICE的 TELNET(23)端口。 ack 22535表明对序列号是222535的包进行响应。 win 8760表明发 送窗口的大小是8760。

(2) ARP包的tcpdump输出信息

使用命令:

#tcpdump arp

得到的输出结果是:

22:32:42.802509 eth0 > arp who-has route tell ICE (0:90:27:58:af:1a)
22:32:42.802902 eth0 < arp reply route is-at 0:90:27:12:10:66 (0:90:27:58:af:1a)

22:32:42是时间戳, 802509是ID号, eth0 >表明从主机发出该分组,arp表明是ARP请求包, who-has route tell ICE表明是主机ICE请求主机route的MAC地址。 0:90:27:58:af:1a 是主机 ICE的MAC地址。

(3) TCP包的输出信息

用tcpdump捕获的TCP包的一般输出信息是:

src > dst: flags data-seqno ack window urgent options

src > dst:表明从源地址到目的地址, flags是TCP报文中的标志信息,具体描述如下:

标识 字符缩写 描述
S SYN 同步标识
F FIN 终止标识
R RST 复位标识
P PSH 推送标识
. 以上四个标识bit全部为0

data-seqno是报文中的数据的顺序号, ack是下次期望的顺序号, window是接收缓存的窗口大小, urgent表明 报文中是否有紧急指针。 Options是选项。

(4) UDP包的输出信息

用tcpdump捕获的UDP包的一般输出信息是:

route.port1 > ICE.port2: udp lenth

UDP十分简单,上面的输出行表明从主机routeport1端口发出的一个UDP报文 到主机ICEport2端口,类型是UDP, 包的长度是lenth

五、举例

(1) 想要截获所有210.27.48.1 的主机收到的和发出的所有的分组:

#tcpdump host 210.27.48.1 

(2) 想要截获主机210.27.48.1 和主机210.27.48.2或210.27.48.3的通信,使用命令(注意:括号前的反斜杠是必须的):

#tcpdump host 210.27.48.1 and \(210.27.48.2 or 210.27.48.3 \)

(3) 如果想要获取主机210.27.48.1除了和主机210.27.48.2之外所有主机通信的ip包,使用命令:

#tcpdump ip host 210.27.48.1 and ! 210.27.48.2

(4) 如果想要获取主机192.168.228.246接收或发出的ssh包,并且不转换主机名使用如下命令:

#tcpdump -nn -n src host 192.168.228.246 and port 22 and tcp

(5) 获取主机192.168.228.246接收或发出的ssh包,并把mac地址也一同显示:

# tcpdump -e src host 192.168.228.246 and port 22 and tcp -n -nn

(6) 过滤的是源主机为192.168.0.1与目的网络为192.168.0.0的报头:

tcpdump src host 192.168.0.1 and dst net 192.168.0.0/24

(7) 过滤源主机物理地址为XXX的报头:

tcpdump ether src 00:50:04:BA:9B and dst……

(为什么ether src后面没有host或者net?物理地址当然不可能有网络喽)。
(8) 过滤源主机192.168.0.1和目的端口不是telnet的报头,并导入到tes.t.txt文件中:

Tcpdump src host 192.168.0.1 and dst port not telnet -l > test.txt

ip icmp arp rarptcpudpicmp这些选项等都要放到第一个参数的位置,用来过滤数据报的类型。

六.man手册中的一些例子

打印所有进入或离开主机sundown的数据包.

tcpdump host sundown

打印主机helios 与主机** hot** 或者与 主机ace 之间通信的数据包

tcpdump host helios and \( hot or ace \)

打印主机ace 与 任何其他主机之间通信的IP 数据包, 但不包括与helios之间的数据包.

tcpdump ip host ace and not helios

打印本地主机与Berkeley网络上的主机之间的所有通信数据包.

tcpdump net ucb-ether

打印所有源地址或目标地址是本地主机的IP数据包(如果本地网络通过网关连到了另一网络, 则另一网络并不能算作本地网络.localnet在 实际使用时要真正替换成本地网络的名字.

tcpdump ip and not net localnet

打印长度超过576字节, 并且网关地址是snupIP数据包

tcpdump 'gateway snup and ip[2:2] > 576'

以下列出了tcp, ip头的结构, 以方便查看(需要以等宽字体查看).

TCP 头格式(rfc793)

    0                   1                   2                   3
    0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
    |          Source Port          |       Destination Port        |
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
    |                        Sequence Number                        |
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
    |                    Acknowledgment Number                      |
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
    |  Data |           |U|A|P|R|S|F|                               |
    | Offset| Reserved  |R|C|S|S|Y|I|            Window             |
    |       |           |G|K|H|T|N|N|                               |
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
    |           Checksum            |         Urgent Pointer        |
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
    |                    Options                    |    Padding    |
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
    |                             data                              |
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+

IPV4 头格式(rfc791)

    0                   1                   2                   3
    0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
    |Version|  IHL  |Type of Service|          Total Length         |
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
    |         Identification        |Flags|      Fragment Offset    |
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
    |  Time to Live |    Protocol   |         Header Checksum       |
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
    |                       Source Address                          |
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
    |                    Destination Address                        |
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
    |                    Options                    |    Padding    |
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+

七.输出格式

tcpdump 的输出格式与协议有关. 以下简要描述了大部分常用的格式及相关例子.

链路层头

ARP/RARP 数据包

tcpdump对arp/rarp包的输出信息中会包含请求类型及该请求对应的参数. 显示格式简洁明了. 以下是从主机rtsg到主机csam的rlogin(远程登录)过程开始阶段的数据包样例:

arp who-has csam tell rtsg
arp reply csam is-at CSAM

第一行表示:rtsg发送了一个arp数据包(nt:向全网段发送,arp数据包)以询问csam的以太网地址,csam以她自己的以太网地址做了回应(在这个例子中, 以太网地址以大写的名字标识, 而internet地址(即ip地址)以全部的小写名字标识).

如果使用tcpdump -n, 可以清晰看到以太网以及ip地址而不是名字标识:

arp who-has 128.3.254.6 tell 128.3.254.68
arp reply 128.3.254.6 is-at 02:07:01:00:01:c4

如果我们使用tcpdump -e, 则可以清晰的看到第一个数据包是全网广播的, 而第二个数据包是点对点的:

RTSG Broadcast 0806  64: arp who-has csam tell rtsg
CSAM RTSG 0806  64: arp reply csam is-at CSAM

第一个数据包表明:以arp包的源以太地址是RTSG, 目标地址是全以太网段, type域的值为16进制0806(表示ETHER_ARP即arp包的类型标识).包的总长度为64字节.

TCP 数据包

通常tcpdump对tcp数据包的显示格式如下:

src > dst: flags data-seqno ack window urgent options

srcdst 是源和目的IP地址以及相应的端口. flags 标志由S(SYN), F(FIN), P(PUSH, R(RST)等组成,

单独一个.表示没有flags标识. 数据段顺序号(Data-seqno)描述了此包中数据所对应序列号空间中的一个位置.

ack描述的是同一个连接,同一个方向,下一个本端应该接收的(对方应该发送的)数据片段的顺序号.

window是本端可用的数据接收缓冲区的大小(也是对方发送数据时需根据这个大小来组织数据).

urg(urgent) 表示数据包中有紧急的数据. options 描述了tcp的一些选项, 这些选项都用尖括号来表示(如 <mss 1024>).

src, dstflags 这三个域总是会被显示. 其他域的显示与否依赖于tcp协议头里的信息.

下面是一个从主机trsg到csam的一个rlogin应用登录的开始阶段.

rtsg.1023 > csam.login: S 768512:768512(0) win 4096 <mss 1024>
csam.login > rtsg.1023: S 947648:947648(0) ack 768513 win 4096 <mss 1024>
rtsg.1023 > csam.login: . ack 1 win 4096
rtsg.1023 > csam.login: P 1:2(1) ack 1 win 4096
csam.login > rtsg.1023: . ack 2 win 4096
rtsg.1023 > csam.login: P 2:21(19) ack 1 win 4096
csam.login > rtsg.1023: P 1:2(1) ack 21 win 4077
csam.login > rtsg.1023: P 2:3(1) ack 21 win 4077 urg 1
csam.login > rtsg.1023: P 3:4(1) ack 21 win 4077 urg 1

第一行表示有一个数据包从rtsg主机的tcp端口1023发送到了csam主机的tcp端口login上. S表示设置了SYN标志. 包的顺序号是768512, 并且没有包含数据.

如果包含有数据,那么数据的表示格式为:first:last(nbytes), 其含义是此包中数据的顺序号从first开始直到last结束,不包括last. 并且总共包含nbytes的用户数据.

没有捎带应答即ack, 可用的接受窗口的大小为4096bytes, 并且请求端(rtsg)的最大可接受的数据段大小是1024字节.

主机csam 向主机rtsg 回复了基本相同的SYN数据包, 其区别只是多了一个piggy-backed ack(nt:捎带回的ack应答, 针对rtsg的SYN数据包).

rtsg 同样针对csam的SYN数据包回复了一ACK数据包作为应答. .的含义就是此包中没有标志被设置. 由于此应答包中不含有数据, 所以包中也没有数据段序列号.

提醒! 此ACK数据包的顺序号只是一个小整数1. 有如下解释:tcpdump对于一个tcp连接上的会话, 只打印会话两端的初始数据包的序列号,其后相应数据包只打印出与初始包序列号的差异.即初始序列号之后的序列号, 可被看作此会话上当前所传数据片段在整个要传输的数据中的'相对字节'位置(nt:双方的第一个位置都是1, 即'相对字节'的开始编号). -S将覆盖这个功能,使数据包的原始顺序号被打印出来.

第六行的含义为:主机rtsg 向 主机csam发送了19字节的数据(字节的编号为2到20,传送方向为rtsg到csam). 包中设置了PUSH标志.

在第7行,主机csam回应道, 她已经从主机rtsg中收到了21以下的字节, 但不包括21编号的字节. 这些字节存放在主机csam的socket的接收缓冲中, 相应地,csam的接收缓冲窗口大小会减少19字节(nt:可以从第5行和第7行win属性值的变化看出来). csam在第7行这个包中也向rtsg发送了一个字节. 在第8行和第9行, csam 继续向rtsg 分别发送了两个只包含一个字节的数据包, 并且这个数据包带PUSH标志.

如果头部含有虚假的属性信息(比如其长度属性其实比头部实际长度长或短), tcpdump会为该头部显示[bad opt].

如果头部的长度告诉我们某些选项(nt | rt:从下文来看, 指tcp包的头部中针对ip包的一些选项, 回头再翻)会在此包中,而真正的IP(数据包的长度又不够容纳这些选项, tcpdump会显示[bad hdr length].

UDP 数据包

UDP 数据包的显示格式,可通过rwho这个具体应用所产生的数据包来说明:

        actinide.who > broadcast.who: udp 84

其含义为:actinide主机上的端口whobroadcast主机上的端口who发送了一个udp数据包.这个数据包包含有84个字节的用户数据.

一些UDP服务可通过数据包的源或目的端口来辨别,也可从所显示的更高层协议信息来识别. 比如, Domain Name service requests(DNS 请求).

UDP 名称服务请求

名称服务请求有如下的格式:

src > dst: id op? flags qtype qclass name (len)

比如有一个实际显示为:

h2opolo.1538 > helios.domain: 3+ A? ucbvax.berkeley.edu. (37)

主机h2opolo 向主机helios 上运行的名称服务器查询ucbvax.berkeley.edu的地址记录(nt: qtype等于A). 此查询本身的id号为3.

符号+意味着递归查询标志被设置(nt: dns服务器可向更高层dns服务器查询本服务器不包含的地址记录). 这个最终通过IP包发送的查询请求数据长度为37字节, 其中不包括UDPIP协议的头数据.

因为此查询操作为默认值(nt | rt: normal one的理解), op字段被省略.如果op字段没被省略, 会被显示在3+之间. 同样, qclass也是默认值, C_IN, 从而也没被显示, 如果没被忽略, 她会被显示在A之后.

UDP 名称服务应答

对名称服务应答的数据包,tcpdump会有如下的显示格式

    src > dst:  id op rcode flags a/n/au type class data (len)

比如具体显示如下:

helios.domain > h2opolo.1538: 3 3/3/7 A 128.32.137.3 (273)
helios.domain > h2opolo.1537: 2 NXDomain* 0/1/0 (97)

第一行表示: 主机helios 对主机h2opolo所发送的3号查询请求回应了3条回答记录(nt | rt: answer records), 3条名称服务器记录,以及7条附加的记录. 第一个回答记录(nt: 3个回答记录中的第一个)类型为A(nt: 表示地址), 其数据为internet地址128.32.137.3.此回应UDP数据包, 包含273字节的数据(不包含UPD和IP的头部数据). op字段和rcode字段被忽略(nt: op的实际值为Query, rcode, 即response code的实际值为NoError), 同样被忽略的字段还有class 字段(nt | rt: 其值为C_IN, 这也是A类型记录默认取值)

第二行表示: heliosh2opolo所发送的2号查询请求做了回应. 回应中, rcode编码为NXDomain(nt: 表示不存在的域)), 没有回答记录,但包含一个名称服务器记录, 不包含权威服务器记录(nt | ck: 从上文来看, 此处的authority records 就是上文中对应的additional records).

*表示权威服务器回答标志被设置(nt: 从而additional records就表示的是authority records).

由于没有回答记录, type, class, data字段都被忽略.

flag字段还有可能出现其他一些字符, 比如-(nt: 表示可递归地查询, 即RA 标志没有被设置), |(nt: 表示被截断的消息, 即TC 标志被置位). 如果应答(nt | ct: 可理解为, 包含名称服务应答的UDP数据包, tcpdump知道这类数据包该怎样解析其数据)的'question'段一个条目(entry)都不包含(nt: 每个条目的含义, 需补充),'[nq]' 会被打印出来.

要注意的是:名称服务器的请求和应答数据量比较大, 而默认的68字节的抓取长度(nt: snaplen, 可理解为tcpdump的一个设置选项)可能不足以抓取数据包的全部内容. 如果你真的需要仔细查看名称服务器的负载, 可以通过tcpdump 的-s 选项来扩大snaplen值.

IP 数据包分片

IP分片数据包(nt: 即一个大的IP数据包切分后生成的小IP数据包)有如下两种显示格式.

(frag id:size@offset+)
(frag id:size@offset)

(第一种格式表示, 此分片之后还有后续分片. 第二种格式表示, 此分片为最后一个碎片.)

id 表示分片的编号( 每个小IP包被分配一个分片编号, 以便区分各个小分片).

size表示此分片的大小 , 不包含分片头部数据.

offset表示此分片所含数据在原始整个IP包中的偏移.

每个分片都会使tcpdump产生相应的输出打印. 第一个分片包含了高层协议的头数据(nt:从下文来看, 被破碎IP数据包中相应tcp头以及IP头都放在了第一个碎片中 ), 从而tcpdump会针对第一个分片显示这些信息, 并接着显示此分片本身的信息. 其后的一些分片并不包含高层协议头信息, 从而只会在显示源和目的之后显示分片本身的信息. 以下有一个例子:

这是一个从arizona.edulbl-rtsg.arpa途经CSNET网络的ftp应用通信片段:

arizona.ftp-data > rtsg.1170: . 1024:1332(308) ack 1 win 4096 (frag 595a:328@0+)
arizona > rtsg: (frag 595a:204@328)
rtsg.1170 > arizona.ftp-data: . ack 1536 win 2560

有几点值得注意:
第一, 第二行的打印中, 地址后面没有端口号.
这是因为TCP协议信息都放到了第一个分片中, 当显示第二个分片时, 我们无法知道此分片所对应TCP包的顺序号.

第二, 从第一行的信息中, 可以发现主机arizonartsg发送308字节的用户数据, 而事实是, 相应IP包经分片后会总共产生512字节数据(第一个分片包含308字节的数据, 第二个分片包含204个字节的数据, 这超过了308字节).

如果你在查找数据包的顺序号空间中的一些空洞(nt: hole,空洞, 指数据包之间的顺序号没有上下衔接上), 512这个数据就足够使你迷茫一阵(nt: 其实只要关注308就行,不必关注分片后的数据总量).

一个IP数据包如果带有非IP分片标志, 则显示时会在最后显示(DF).

时间戳

tcpdump的所有输出打印行中都会默认包含时间戳信息.
时间戳信息的显示格式如下

hh:mm:ss.frac (nt: 小时:分钟:秒.(nt: frac未知, 需补充))

此时间戳的精度与内核时间精度一致, 反映的是内核第一次看到对应数据包的时间(nt: saw, 即可对该数据包进行操作). 而数据包从物理线路传递到内核的时间, 以及内核花费在此包上的中断处理时间都没有算进来.

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 158,425评论 4 361
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 67,058评论 1 291
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 108,186评论 0 243
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 43,848评论 0 204
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 52,249评论 3 286
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 40,554评论 1 216
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 31,830评论 2 312
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 30,536评论 0 197
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 34,239评论 1 241
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 30,505评论 2 244
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 32,004评论 1 258
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 28,346评论 2 253
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 32,999评论 3 235
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 26,060评论 0 8
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 26,821评论 0 194
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 35,574评论 2 271
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 35,480评论 2 267

推荐阅读更多精彩内容

  • 简介 用简单的话来定义tcpdump,就是:dump the traffic on a network,根据使用者...
    保川阅读 5,903评论 1 13
  • 11.1 引言 UDP是一个简单的面向数据报的运输层协议:进程的每个输出操作都正好产生一个UDP数据报,并组装成一...
    张芳涛阅读 2,680评论 1 6
  • 1.这篇文章不是本人原创的,只是个人为了对这部分知识做一个整理和系统的输出而编辑成的,在此郑重地向本文所引用文章的...
    SOMCENT阅读 12,979评论 6 174
  • 个人认为,Goodboy1881先生的TCP /IP 协议详解学习博客系列博客是一部非常精彩的学习笔记,这虽然只是...
    贰零壹柒_fc10阅读 5,019评论 0 8
  • 同样的,本文篇幅也比较长,先来一张思维导图,带大家过一遍。 一、 计算机网络体系结构分层 二、 TCP/IP 基础...
    涤生_Woo阅读 64,454评论 38 1,038