tcpdump及wireshark介绍

1,tcpdump

tcpdump采用命令行方式对接口的数据包进行筛选抓取,其丰富特性表现在灵活的表达式上。
不带任何选项的tcpdump,默认会抓取第一个网络接口,且只有将tcpdump进程终止才会停止抓包

1.1, tcpdump基本选项

它的命令格式为:

tcpdump [ -DenNqvX ] [ -c count ] [ -F file ] [ -i interface ] [ -r file ]
        [ -s snaplen ] [ -w file ] [ expression ]

抓包选项:
-c:指定要抓取的包数量。注意,是最终要获取这么多个包。例如,指定"-c 10"将获取10个包,但可能已经处理了100个包,只不过只有10个包是满足条件的包。
-i interface:指定tcpdump需要监听的接口。若未指定该选项,将从系统接口列表中搜寻编号最小的已配置好的接口(不包括loopback接口,要抓取loopback接口使用tcpdump -i lo),
            :一旦找到第一个符合条件的接口,搜寻马上结束。可以使用'any'关键字表示所有网络接口。
-n:对地址以数字方式显式,否则显式为主机名,也就是说-n选项不做主机名解析。
-nn:除了-n的作用外,还把端口显示为数值,否则显示端口服务名。
-N:不打印出host的域名部分。例如tcpdump将会打印'nic'而不是'nic.ddn.mil'。
-P:指定要抓取的包是流入还是流出的包。可以给定的值为"in"、"out"和"inout",默认为"inout"。
-s len:设置tcpdump的数据包抓取长度为len,如果不设置默认将会是65535字节。对于要抓取的数据包较大时,长度设置不够可能会产生包截断,若出现包截断,
      :输出行中会出现"[|proto]"的标志(proto实际会显示为协议名)。但是抓取len越长,包的处理时间越长,并且会减少tcpdump可缓存的数据包的数量,
      :从而会导致数据包的丢失,所以在能抓取我们想要的包的前提下,抓取长度越小越好。

输出选项:
-e:输出的每行中都将包括数据链路层头部信息,例如源MAC和目标MAC。
-q:快速打印输出。即打印很少的协议相关信息,从而输出行都比较简短。
-X:输出包的头部数据,会以16进制和ASCII两种方式同时输出。
-XX:输出包的头部数据,会以16进制和ASCII两种方式同时输出,更详细。
-v:当分析和打印的时候,产生详细的输出。
-vv:产生比-v更详细的输出。
-vvv:产生比-vv更详细的输出。

其他功能性选项:
-D:列出可用于抓包的接口。将会列出接口的数值编号和接口名,它们都可以用于"-i"后。
-F:从文件中读取抓包的表达式。若使用该选项,则命令行中给定的其他表达式都将失效。
-w:将抓包数据输出到文件中而不是标准输出。可以同时配合"-G time"选项使得输出文件每time秒就自动切换到另一个文件。可通过"-r"选项载入这些文件以进行分析和打印。
-r:从给定的数据包文件中读取数据。使用"-"表示从标准输入中读取。

所以常用的选项也就这几个:
tcpdump -D
tcpdump -c num -i eth -nn -XX -vvv

1.2, tcpdump过滤条件

1:过滤主机
// 抓取所有经过enp0s3,目的或源地址是 192.168.1.101 的网络数据
tcpdump -i enp0s3 host 192.168.1.101 

// 指定源地址
tcpdump -i enp0s3 src host 192.168.1.101

// 指定目的地址
tcpdump -i enp0s3 dst host 192.168.1.101

//如果想要获取主机192.168.1.101除了和主机192.168.1.102之外所有主机通信的ip包
tcpdump ip host 192.168.1.101 and !192.168.1.102

2:过滤端口
// 抓取所有经过 enp0s3,目的或源端口是22的网络数据
tcpdump -i enp0s3 port 22

// 指定源端口
tcpdump -i enp0s3 src port 22

// 指定目的端口
tcpdump -i enp0s3 dst port 22
 
3:网络过滤
tcpdump -i enp0s3 net 192.168
tcpdump -i enp0s3 src net 192.168
tcpdump -i enp0s3 dst net 192.168
 
4:协议过滤
tcpdump -i enp0s3 arp
tcpdump -i enp0s3 ip
tcpdump -i enp0s3 tcp
tcpdump -i enp0s3 udp
tcpdump -i enp0s3 icmp

5:常用表达式

非 : ! or "not" (without the quotes)
且 : && or "and"
或 : || or "or"

// 抓取目的地址是192.168.1.254或192.168.1.200端口是80的TCP数据
tcpdump -i enp0s3 '((tcp) and (port 80) and ((dst host 192.168.1.254) or (dst host 192.168.1.200)))'

// 抓取目标MAC地址是00:01:02:03:04:05的ICMP数据
tcpdump  '((icmp) and ((ether dst host 00:01:02:03:04:05)))'

// 抓取目的网络是192.168,但目的主机不是192.168.1.200的TCP数据
tcpdump  '((tcp) and ((dst net 192.168) and (not dst host 192.168.1.200)))'

1.3, tcpdump抓包示例

[root@server2 ~]# tcpdump -c 2 -q -XX -vvv -nn -i eth0 tcp dst port 22
tcpdump: listening on eth0, link-type EN10MB (Ethernet), capture size 65535 bytes
12:15:54.788812 IP (tos 0x0, ttl 64, id 19303, offset 0, flags [DF], proto TCP (6), length 40)
    192.168.100.1.5788 > 192.168.100.62.22: tcp 0
        0x0000:  000c 2908 9234 0050 56c0 0008 0800 4500  ..)..4.PV.....E.
        0x0010:  0028 4b67 4000 4006 a5d8 c0a8 6401 c0a8  .(Kg@[email protected]...
        0x0020:  643e 169c 0016 2426 5fd6 1fec 2b62 5010  d>....$&_...+bP.
        0x0030:  0803 7844 0000 0000 0000 0000            ..xD........
12:15:54.842641 IP (tos 0x0, ttl 64, id 19304, offset 0, flags [DF], proto TCP (6), length 40)
    192.168.100.1.5788 > 192.168.100.62.22: tcp 0
        0x0000:  000c 2908 9234 0050 56c0 0008 0800 4500  ..)..4.PV.....E.
        0x0010:  0028 4b68 4000 4006 a5d7 c0a8 6401 c0a8  .(Kh@[email protected]...
        0x0020:  643e 169c 0016 2426 5fd6 1fec 2d62 5010  d>....$&_...-bP.
        0x0030:  0801 7646 0000 0000 0000 0000            ..vF........
2 packets captured
2 packets received by filter
0 packets dropped by kernel

MAC包头占有14字节,即:
000c 2908 9234 :目的mac
0050 56c0 0008 :源mac
0800:type是ipv4

IP包头占有20个字节,即:
4500:4代表ipv4,5说明IP头长20字节,00为服务类型
0028 :IP数据报文总长40字节,包含头部以及数据
4b68 :唯一地标识主机发送的每一份数据报
4000 :第2,3个bit是两个标志DF和MF,后5个是Fragment Offset
4006 :40代表TTL=64,06为tcp协议
a5d7 :checksum
c0a8 6401 :源ip是192.168.100.1
c0a8 643e:目的ip是192.168.100.62

TCP包头占有20个字节,即:
169c :本地端口号5788
0016:目的端口号22
2426 5fd6 :顺序号(Sequence Number),简写为SEQ
1fec 2d62 :确认号(Acknowledgment Number),简写为ACKNUM
5010:5代表tcp头长20字节,最后6bit分别是URG,ACK, PSH,RST,SYN,FIN
0801 :窗口值,用来控制实现流量控制
7646:检验和,TCP的检验和是强制的
0000:紧急指针

1.4, tcpdump高级过滤包头

proto[x:y] : 过滤从x字节开始的y字节数。比如ip[2:2]过滤出3、4字节(第一字节从0开始)

当然,前提是必须了解tcp/ip包头的头部信息。TCP/IP协议栈中各层包头的介绍:
https://blog.csdn.net/qq_15437629/article/details/79560742

1,一般的IP头是20字节,但IP头有选项设置,不能直接从偏移21字节处读取数据。IP头有个长度字段可以知道头长度是否大于20字节。通常第一个字节的二进制值是:01000101,分成两个部分:
0100 = 4 表示IP版本; 0101 = 5 表示IP头32 bit的块数,5 x 32 bits = 160 bits or 20 bytes。如果第一字节第二部分的值大于5,那么表示头有IP选项:

tcpdump  'ip[0] & 0x0f > 5'

2,分片标记 -Exercise: Is DF bit (don’t fragment) set?

当发送端的MTU大于到目的路径链路上的MTU时就会被分片,分片信息在IP头的第七和第八字节:

Bit 0: 保留,必须是0
Bit 1: (DF) 0 = 可能分片, 1 = 不分片
Bit 2: (MF) 0 = 最后的分片, 1 = 还有分片
Fragment Offset字段只有在分片的时候才使用。
要抓带DF位标记的不分片的包,第七字节的值应该是: 64

tcpdump  'ip[6] = 64'

// 匹配分片(包括最后分片)
tcpdump  '((ip[6:2] > 0) and (not ip[6] = 64))'

3,匹配TCP数据包的特殊标记

TCP标记定义在TCP头的第十四个字节


+-+-+-+-+-+-+-+-+
|C|E|U|A|P|R|S|F|
|W|C|R|C|S|S|Y|I|
|R|E|G|K|H|T|N|N|
+-+-+-+-+-+-+-+-+
TCP 3次握手中过程如下:
1、源端发送 SYN
2、目标端口应答 SYN,ACK
3、源端发送 ACK

// 只抓取SYN包,第十四字节是二进制的00000010,也就是十进制的2
tcpdump 'tcp[13] = 2'

// 抓取 SYN,ACK  (00010010 or 18)
tcpdump 'tcp[13] = 18'

//  抓取SYN或者SYN-ACK
tcpdump 'tcp[13] & 2 = 2'

2,wireshark分析数据包

Wireshark是一款最流行和强大的开源数据包抓包与分析工具,使用tcpdump命令抓包保存pcap文件即可用wireshark打开分析。

在这里插入图片描述
上图中标出三块区域,红色框内,是用来显示简单的数据包信息,我们用tcpdump抓包如时候,默认情况是显示成这样的;深蓝框内,是用来显示选中的数据包的详细信息,是按照TCP/IP四层结构显示的,第一行是数据链路层的信息,第二行是网络层信息(IP协议),第三行是传输层信息(TCP协议),第四层是应用层信息(HTTP协议),可以展开第一行用来观察具体的内容;最后一个区域淡蓝色框中,是用来显示此数据包的真实面目。

下面列举一些常用的过滤规则:

过滤IP 
ip.src==192.168.1.102 or ip.dst==192.168.1.102 

过滤端口 
tcp.dstport == 80 // 只显tcp协议的目标端口80 
tcp.srcport == 80 // 只显tcp协议的来源端口80 
也可以写成tcp.port eq 80 or udp.port eq 80 这样的模式

过滤协议 
单独写上tcp、udp、xml、http就可以过滤出具体协议的报文。你也可以用tcp or xml这样格式来过滤。 
我们还可以更加具体过滤协议的内容,如tcp.flags.syn == 0x02 表示显示包含TCP SYN标志的封包。

过滤mac地址 
eth.src eq A0:00:00:04:C5:84 // 过滤来源mac地址 
eth.dst==A0:00:00:04:C5:84 // 过滤目的mac地址

http模式过滤 
http.request.method == “GET” 
http.request.method == “POST” 
http.request.uri == “/img/logo-edu.gif” 
http contains “GET” 
http contains “HTTP/1.” 
// GET包 
http.request.method == “GET” && http contains “Host: ” 
http.request.method == “GET” && http contains “User-Agent: ” 
// POST包 
http.request.method == “POST” && http contains “Host: ” 
http.request.method == “POST” && http contains “User-Agent: ” 
// 响应包 
http contains “HTTP/1.1 200 OK” && http contains “Content-Type: ” 
http contains “HTTP/1.0 200 OK” && http contains “Content-Type: “

过滤内容 
contains:包含某字符串 
ip.src==192.168.1.107 and udp contains 02:12:21:00:22 
ip.src==192.168.1.107 and tcp contains “GET” 

下面介绍一些常见的场景:

2.1,tcp三次握手

在这里插入图片描述
从图可知,连接建立伊始,客户机发了3个SYN报文,这也许是为了更快建立连接(假设有个请求报文段丢失,也不至于要等一段时间,重发报文)。接下来分析TCP连接建立过程:

  1. 客户端通过TCP首部发送一个SYN包请求,seq =0
  2. 服务器发送ACK(=SYN+1)包确认应答,并发送SYN包请求连接,seq=0,ack=1
  3. 客户端针对SYN包发送ACK包确认应答,ack=1
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章