网络抓包分析
1,网络抓包介绍
1、Tcpdump简介
tcpdump 命令是基于unix系统的命令行的数据报嗅探工具,可以抓取流动在网卡上的数据包。它的原理大概如下:**linux 抓包是通过注册一种虚拟的底层网络协议来完成对网络报文(准确的是网络设备)消息的处理权。**当网卡接收到一个网络报文之后,它会遍历系统中所有已经注册的网络协议,如以太网协议、x25协议处理模块来尝试进行报文的解析处理。当抓包模块把自己伪装成一个网络协议的时候,系统在收到报文的时候就会给这个伪协议一次机会,让它对网卡收到的包进行一次处理,此时该模块就会趁机对报文进行窥探,也就是将报文完完整整的复制一份,假装是自己接收的报文,汇报给抓包模块。
2、Wireshark 简介
Wireshark 是一个网络协议检测工具,支持Windows平台、Unix平台、Mac平台,一般只在图形界面平台下使用Wireshark,如果是Linux的话,直接使用 tcpdump了,因为一般而言 Linux 都自带的 tcpdump,或者用 tcpdump 抓包以后用 Wireshark 打开分析。
在Mac平台下,Wireshark 通过 WinPcap 进行抓包,封装的很好,使用起来很方便,可以很容易的制定抓包过滤器或者显示过滤器,具体简单使用下面会介绍。Wireshark是一个免费的工具。
所以,tcpdump是用来抓取数据非常方便,Wireshark则是用于分析抓取到的数据比较方便。
2、Tcpdump 语法
1、查看本地网卡状态
[root@qfedu.com ~]# netstat -i
Kernel Interface table
Iface MTU RX-OK RX-ERR RX-DRP RX-OVR TX-OK TX-ERR TX-DRP TX-OVR Flg
docker0 1500 40409 0 0 0 20376 0 0 0 BMU
eth0 1500 22999894941 0 0 0 25581016784 0 0 0 BMRU
lo 65536 850291094 0 0 0 850291094 0 0 0 LRU
-
Iface:存在的网卡。
-
MTU:最大传输单元。
-
RX-OK RX-ERR RX-DRP RX-OVR:正确接收数据报的数量以及发生错误、流式、碰撞的总数。
-
TX-OK TX-ERR TX-DRP TX-OVR:正确发送数据报的数量以及发生错误、流式、碰撞的总数。
[root@qfedu.com ~]# tcpdump --help tcpdump version 4.9.0 libpcap version 1.5.3 OpenSSL 1.0.1e-fips 11 Feb 2013 Usage: tcpdump [-aAbdDefhHIJKlLnNOpqStuUvxX#] [ -B size ] [ -c count ] [ -C file_size ] [ -E algo:secret ] [ -F file ] [ -G seconds ] [ -i interface ] [ -j tstamptype ] [ -M secret ] [ --number ] [ -Q|-P in|out|inout ] [ -r file ] [ -s snaplen ] [ --time-stamp-precision precision ] [ --immediate-mode ] [ -T type ] [ --version ] [ -V file ] [ -w file ] [ -W filecount ] [ -y datalinktype ] [ -z postrotate-command ] [ -Z user ] [ expression ]
2、 Tcpdump 抓包分类
1、类型的关键字
- host:指明一台主机。如:host 192.168.152.110
- net:指明一个网络地址,如:net 192.168.152.0
- port:指明端口号:如:port 8090
2、确定方向的关键字
- src:ip包的源地址,如:src 192.168.152.110
- dst:ip包的目标地址。如:dst 192.168.152.110
3、协议的关键字(缺省是所有协议的信息包)
- fddi、ip、arp、rarp、tcp、udp。
4、其它关键字
- gateway、broadcast、less、greater。
5、常用表达式
- ! or not
- && or and
- || or or
3、Tcpdump 参数详解
- A:以ascii编码打印每个报文(不包括链路的头)。
- a:将网络地址和广播地址转变成名字。
- c:抓取指定数目的包。
- C:用于判断用 -w 选项将报文写入的文件的大小是否超过这个值,如果超过了就新建文件(文件名后缀是1、2、3依次增加);
- d:将匹配信息包的代码以人们能够理解的汇编格式给出;
- dd:将匹配信息包的代码以c语言程序段的格式给出;
- ddd:将匹配信息包的代码以十进制的形式给出;
- D:列出当前主机的所有网卡编号和名称,可以用于选项 -i;
- e:在输出行打印出数据链路层的头部信息;
- f:将外部的Internet地址以数字的形式打印出来;
- F<表达文件>:从指定的文件中读取表达式,忽略其它的表达式;
- i<网络界面>:监听主机的该网卡上的数据流,如果没有指定,就会使用最小网卡编号的网卡(在选项-D可知道,但是不包括环路接口),linux 2.2 内核及之后的版本支持 any 网卡,用于指代任意网卡;
- l:如果没有使用 -w 选项,就可以将报文打印到 标准输出终端(此时这是默认);
- n:显示ip,而不是主机名;
- nn:显示port,而不是服务名;
- N:不列出域名;
- O:不将数据包编码最佳化;
- p:不让网络界面进入混杂模式;
- q:快速输出,仅列出少数的传输协议信息;
- r<数据包文件>:从指定的文件中读取包(这些包一般通过-w选项产生);
- s<数据包大小>:指定抓包显示一行的宽度,-s0表示可按包长显示完整的包,经常和-A一起用,默认截取长度为60个字节,但一般ethernet MTU都是1500字节。所以,要抓取大于60字节的包时,使用默认参数就会导致包数据丢失;
- S:用绝对而非相对数值列出TCP关联数;
- t:在输出的每一行不打印时间戳;
- tt:在输出的每一行显示未经格式化的时间戳记;
- T<数据包类型>:将监听到的包直接解释为指定的类型的报文,常见的类型有rpc (远程过程调用)和snmp(简单网络管理协议);
- v:输出一个稍微详细的信息,例如在ip包中可以包括ttl和服务类型的信息;
- vv:输出详细的报文信息;
- x/-xx/-X/-XX:以十六进制显示包内容,几个选项只有细微的差别,详见man手册;
- w<数据包文件>:直接将包写入文件中,并不分析和打印出来;
- expression:用于筛选的逻辑表达式;
4、Tcpdump 参数含义
[root@qfedu.com ~]# tcpdump host 192.168.152.110 -i eth0 -c 10 -l -n
tcpdump: verbose output suppressed, use -v or -vv for full protocol decode
listening on ens5f0, link-type EN10MB (Ethernet), capture size 262144 bytes
10:59:51.071567 IP 192.168.152.21.ssh > 192.168.152.110.7608: Flags [P.], seq 1715331653:1715331865, ack 2259278754, win 65535, length 212
10:59:51.071699 IP 192.168.152.21.ssh > 192.168.152.110.7608: Flags [P.], seq 212:408, ack 1, win 65535, length 196
10:59:51.071794 IP 192.168.152.21.ssh > 192.168.152.110.7608: Flags [P.], seq 408:572, ack 1, win 65535, length 164
10:59:51.071861 IP 192.168.152.21.ssh > 192.168.152.110.7608: Flags [P.], seq 572:736, ack 1, win 65535, length 164
10:59:51.071910 IP 192.168.152.21.ssh > 192.168.152.110.7608: Flags [P.], seq 736:900, ack 1, win 65535, length 164
10:59:51.071958 IP 192.168.152.21.ssh > 192.168.152.110.7608: Flags [P.], seq 900:1064, ack 1, win 65535, length 164
10:59:51.072006 IP 192.168.152.21.ssh > 192.168.152.110.7608: Flags [P.], seq 1064:1228, ack 1, win 65535, length 164
10:59:51.072053 IP 192.168.152.21.ssh > 192.168.152.110.7608: Flags [P.], seq 1228:1392, ack 1, win 65535, length 164
10:59:51.072141 IP 192.168.152.21.ssh > 192.168.152.110.7608: Flags [P.], seq 1392:1556, ack 1, win 65535, length 164
10:59:51.077438 IP 192.168.152.110.7608 > 10.1.87.25.ssh: Flags [.], ack 212, win 63360, length 0
10 packets captured
13 packets received by filter
0 packets dropped by kernel
1、第一行:`tcpdump: verbose output suppressed, use -v or -vv for full protocol decode`
使用选项`v`和`vv`,可以看出更全的详细内容。
2、第二行:`listening on ens5f0, link-type EN10MB (Ethernet), capture size 262144 bytes`,说明监听的是`ens5f0`这个NIC设备的网络包,且它的链路层是基于以太网的,要抓的包大小限制`262144`,装包大小限制可以用利用`-s`来控制。
3、第三行:`10:59:51.071567 IP 192.168.152.21.ssh > 192.168.152.110.7608: Flags [P.], seq 1715331653:1715331865, ack 2259278754, win 65535, length 212`。
- `10:59:51.071567`:抓包时间为时、分、秒、微妙。
- `IP 192.168.152.21.ssh > 192.168.152.110.7608: Flags [P.], seq 1715331653:1715331865, ack 2259278754, win 65535, length 212`,这里用`man dump`这个命令引用说明:
上面视图简单的解释就是该包`192.168.152.21`传到`192.168.152.110`,通过的端口是`22`(ssh的端口)向`7608`,前几个是使用的是`PUSH`的标识,最后一个是返回的`ACK`标识。
5、Tcpdump 命令实践
1、直接启动tcpdump,将抓取所有经过第一个网络接口上的数据包
[root@qfedu.com ~]# tcpdump
2、抓取所有经过指定网络接口上的数据包
[root@qfedu.com ~]# tcpdump -i eth0
3、抓取所有经过 eth0,目的或源地址是 192.168.152.255 的网络数据:
[root@qfedu.com ~]# tcpdump -i eth0 host 192.168.152.100
4、抓取主机192.168.152.255和主机192.168.152.61或192.168.152.95的通信:
[root@qfedu.com ~]# tcpdump host 192.168.152.100 and 192.168.152.101 (或者用 or)
5、抓取主机192.168.1523.210除了和主机192.168.152.61之外所有主机通信的数据包:
[root@qfedu.com ~]# tcpdump -n host 192.168.152.100 and ! 192.168.152.101
6、抓取主机192.168.152.255除了和主机192.168.152.61之外所有主机通信的ip包
[root@qfedu.com ~]# tcpdump ip -n host 192.168.152.100 and ! 192.168.152.101
7、抓取主机192.168.152.3发送的所有数据:
[root@qfedu.com ~]# tcpdump -i eth0 src host 192.168.152.100 (注意数据流向)
8、抓取主机192.168.152.3接收的所有数据:
[root@qfedu.com ~]# tcpdump -i eth0 dst host 192.168.152.100 (注意数据流向)
9、抓取主机192.168.152.3所有在TCP 80端口的数据包:
[root@qfedu.com ~]# tcpdump -i eth0 host 192.168.152.3 and tcp port 80
10、抓取HTTP主机192.168.152.3在80端口接收到的数据包:
[root@qfedu.com ~]# tcpdump -i eth0 host 192.168.152.3 and dst port 80
11、抓取所有经过 eth0,目的或源端口是 25 的网络数据
[root@qfedu.com ~]# tcpdump -i eth0 port 25
#源端口
[root@qfedu.com ~]# tcpdump -i eth0 src port 25
#目的端口
[root@qfedu.com ~]# tcpdump -i eth0 dst port 25 # 网络过滤
12、抓取所有经过 eth0,网络是 192.168上的数据包
[root@qfedu.com ~]# tcpdump-i eth0 net 192.168
[root@qfedu.com ~]# tcpdump -i enh0 src net 192.168
[root@qfedu.com ~]# tcpdump -i eth0 dst net 192.168
[root@qfedu.com ~]# tcpdump-i eth0 net 192.168.152
[root@qfedu.com ~]# tcpdump -i eth0 net 192.168.152.0/24
13、协议过滤
[root@qfedu.com ~]# tcpdump -i eth0 arp
[root@qfedu.com ~]# tcpdump-i eth0 ip
[root@qfedu.com ~]# tcpdump -i eth0
[root@qfedu.com ~]# tcptcpdump -i eth0 udp
[root@qfedu.com ~]# tcpdump -i eth0 icmp
14、抓取所有经过 eth0,目的地址是 192.168.152.254 或 192.168.152.200 端口是 80 的 TCP 数据
[root@qfedu.com ~]# tcpdump -i eth0 '((tcp) and (port 80) and ((dst host 192.168.152.254) or (dst host 192.168.152.200)))
15、抓取所有经过 eth0,目标 MAC 地址是 00:01:02:03:04:05 的 ICMP 数据
[root@qfedu.com ~]# tcpdump -i eth1 '((icmp) and ((ether dst host 00:01:02:03:04:05)))
16、抓取所有经过 eth0,目的网络是 192.168,但目的主机不是 192.168.152.200 的 TCP 数据
[root@qfedu.com ~]# tcpdump -i eth0 '((tcp) and ((dst net 192.168) and (not dst host 192.168.152.200)))'
17、只抓 SYN 包
[root@qfedu.com ~]# tcpdump -i eth0 'tcp[tcpflags] =tcp-syn
18、抓 SYN, ACK
[root@qfedu.com ~]# tcpdump -i eth0 'tcp[tcpflags]'
19、抓 SMTP 数据,抓取数据区开始为”MAIL”的包,”MAIL”的十六进制为 0x4d41494c
[root@qfedu.com ~]# tcpdump -i eth0 '((port 25) and (tcp[(tcp[12]>>2):4] = 0x4d41494c))'
20、抓 HTTP GET 数据,”GET “的十六进制是 0x47455420
[root@qfedu.com ~]# tcpdump -i eth0 'tcp[(tcp[12]>x2):4] =0x47455429'
# 0x4745为"GET"前两个字母"GE",0x4854为"HTTP"前两个字母"HT"
[root@qfedu.com ~]# tcpdump -XvvennSs 0 -i eth0 tcp[20:2]=0x4745 or tcp[20:2]=0x4854
21、抓 SSH 返回,”SSH-“的十六进制是 0x5353482D
[root@qfedu.com ~]# tcpdump -i eth0 'tcp[(tcp[12]2):4]-0x5353482D'
# 抓老版本的SSH返回信息,如"SSH-1.99.."
[root@qfedu.com ~]# tcpdump -i eth0 (tcp (tcp[12]>>2):4] = 0x5353482D) and (tcp[((tcp[12]>2)+4):2] = 0x312E3)'
22、高级包头过滤如前两个的包头过滤,首先了解如何从包头过滤信息:
proto[x:y] # :过滤从x字节开始的y字节数。比如ip[2:2]过滤出3、4字节(第二字专从研始排)
操作符: >, =,
抓取端口大于1024的TCP数据包
[root@qfedu.com ~]# tcpdump -i eth0 'tcp[0:2] > 1024‘
23、抓 DNS 请求数据
[root@qfedu.com ~]# tcpdump -i eth0 udp dst port 53
24、其他-c 参数对于运维人员来说也比较常用,因为流量比较大的服务器,靠人工 CTRL+C 还是抓的太多,于是可以用-c 参数指定抓多少个包。
[root@qfedu.com ~]# time tcpdump -nn -i eth0 'tcp[tcpflags] = tcp-syn' -C 10000 > /dev/null
上面的命令计算抓10000个SYN包花费多少时间,可以判断访问量大概是多少。实时抓取端口号8000的GET包,然后写入GET.log
[root@qfedu.com ~]# tcpdump -i eth0 '((port 8000) and (tcp[(tcp[12]>>2):4]=0x47455420))' -nnAL -w /tmp/GET.log
6、Tcpdump 抓包示例
想抓取访问某个网站时的网络数据。比如网站 http://www.baidu.com/ 怎么做?
1、通过tcpdump截获主机 www.baidu.com 发送与接收所有的数据包
[root@qfedu.com ~]# tcpdump -i eth0 host www.baidu.com
2、访问这个网站
[root@qfedu.com ~]# wget www.baidu.cn
查看控制台输出
确认序列号ack为何是1。这是相对值,如何显示绝对值
[root@qfedu.com ~]# tcpdump -S -i eth0 host www.baidu.com
[root@qfedu.com ~]# wget www.baidu.com
再次查看控制输出
3、想要看到详细的http报文。怎么做?
[root@qfedu.com ~]# tcpdump -A -i eth0 host www.baidu.com
将抓取的结果存到文件,比如文件file1
[root@qfedu.com ~]# tcpdump -A -i eth0 -w filel host www.baidu.com
如何读取这个文件的基本信息
[root@qfedu.com ~]# tcpdump -r filel
想要了解更多,比如上面的http报文
[root@qfedu.com ~]# tcpdump -A -r filel
也同时想要将确认序列号ack打印成绝对值
[root@qfedu.com ~]# tcpdump -AS -r filel
注:无参数的选项比如-A,-S,-e,等。均可以共用一个减号 'src host www.baidu.cn' 属于expression ,如果太长,可以用单引号括起来:
[root@qfedu.com ~]# tcpdump -i eth0 'src host www. baidu.com'
4、分析抓取到的报文
16:50:11.916308 IP 192.168.152.3.52346 > 61.135.169.121.http: Flags [P.], seq 1888894293:1888894434, ack 2526934942, win 8192, Length 14 1: HTTP: GET/ HTTP/1.1
第一列是时间戳:时、分、秒、微秒
第二列是网际网路协议的名称
第三列是报文发送方的十进制的网际网路协议地址,以及紧跟其后的端口号(偶尔会是某个协议名如http,如果在此处仍然显示端口号加上-n选项
第四列是大于号
第五列是报文接收方的十进制的网际网路协议地址,以及紧跟其后的端口号(偶尔会是某个协议名如http,如果在此处仍然显示端口号加上-n选项)
第六列是冒号第七列是Flags标识,可能的取值是[S.] [] [P.] [F.]
第八、九、.…列是tcp协议报文头的一些变量值:
seq是请求同步的序列号
ack是已经同步的序列号
win是当前可用窗口大小
length是tcp协议报文体的长度
如果加入了-5选项,会看到的seg, ack是两个冒号分割的值,分别表示变更前后的值。
7、Tcpdump 抓取 TCP 包分析
TCP传输控制协议是面向连接的可靠的传输层协议,在进行数据传输之前,需要在传输数据的两端(客户端和服务器端)创建一个连接,这个连接由一对插口地址唯一标识,即是在IP报文首部的源IP地址、目的IP地址,以及TCP数据报首部的源端口地址和目的端口地址。TCP首部结构如下:
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-42excr6h-1608122997108)(assets/image-20200304004851192.png)]
注意:通常情况下,一个正常的TCP连接,都会有三个阶段:1、TCP三次握手;2、数据传送;3、TCP四次挥手
其中在TCP连接和断开连接过程中的关键部分如下:
-
源端口号:即发送方的端口号,在TCP连接过程中,对于客户端,端口号往往由内核分配,无需进程指定;
-
目的端口号:即发送目的的端口号;
-
序号:即为发送的数据段首个字节的序号;
-
确认序号:在收到对方发来的数据报,发送确认时期待对方下一次发送的数据序号;
-
SYN:同步序列编号,Synchronize Sequence Numbers;
-
ACK:确认编号,Acknowledgement Number;
-
FIN:结束标志,FINish;
1、TCP三次握手
三次握手的过程如下:
- step1. 由客户端向服务器端发起TCP连接请求。Client发送:同步序列编号SYN置为1,发送序号Seq为一个随机数,这里假设为X,确认序号ACK置为0;
- step2. 服务器端接收到连接请求。Server响应:同步序列编号SYN置为1,并将确认序号ACK置为X+1,然后生成一个随机数Y作为发送序号Seq(因为所确认的数据报的确认序号未初始化);
- step3. 客户端对接收到的确认进行确认。Client发送:将确认序号ACK置为Y+1,然后将发送序号Seq置为X+1(即为接收到的数据报的确认序号);
为什么是三次握手而不是两次对于step3的作用,假设一种情况,客户端A向服务器B发送一个连接请求数据报,然后这个数据报在网络中滞留导致其迟到了,虽然迟到了,但是服务器仍然会接收并发回一个确认数据报。但是A却因为久久收不到B的确认而将发送的请求连接置为失效,等到一段时间后,接到B发送过来的确认,A认为自己现在没有发送连接,而B却一直以为连接成功了,于是一直在等待A的动作,而A将不会有任何的动作了。这会导致服务器资源白白浪费掉了,因此,两次握手是不行的,因此需要再加上一次,对B发过来的确认再进行一次确认,即确认这次连接是有效的,从而建立连接。
对于双方,发送序号的初始化为何值有的系统中是显式的初始化序号是0,但是这种已知的初始化值是非常危险的,因为这会使得一些黑客钻漏洞,发送一些数据报来破坏连接。因此,初始化序号因为取随机数会更好一些,并且是越随机越安全。
1.Tcpdump抓TCP三次握手抓包分析
[root@qfedu.com ~]# tcpdump host 192.168.152.3 -i lo and tcp port 8080
# 接着再运行:
[root@qfedu.com ~]# curl http://192.168.152.3:8080/atbg/doc
2.控制台输出
# TCP三次握手start
16:00:13.486776 IP 192.168.152.3.61725 > 192.168.152.3.8080: Flags [S], seq 1944916150,win 65535,options [mss 16344 ,nop ,wscale 5 , nop,nop,TS val 906474698 ecr O,sackoK,eol], length 0
16:00:13.486850 IP 192.168.152.3.8080 > 192.168.152.3.61725: Flags [S.], seq 1119565918, ack 1944916151, win 65535, options_ [mss 16344 ,nop,wscale 5,nop ,nop,TS val 906474698 ecr 906474698, sackOK, eol], length 0
16:00:13.486860 IP 192.168.152.3.61725 > 192.168.152.3.8080: Flags [.],ack 1119565919,win 12759,options [nop ,nop,TS val 906474698 ecr 906474698], length0
16:00:13. 486868 IP 192.168.152.3.8080 > 192.168.152.3.61725: Flags [.], ack 1944916151, win 12759, options [nop ,nop,TS val 906474698 ecr 906474698], length0
# TCP三次握手end
#传输数据start
16:00:13.486923 IP 192.168.152.3.61725 > 192.168.152..3.8080: Flags [P.], seq 1944916151:1944916238,ack 1119565919, win 12759,options [nop,nop,TS val 906474698 ecr 906474698], length 87: HTTP: GET /atbg/doc HTTP/1.1
16:00:13. .486944 IP 192.168.152.3.8080 > 192.168.152.3.61725: FLags [.],ack 1944916238, win 12756,options [nop ,nop,TS val 906474698 ecr 906474698], length0
16:00:13.489750 IP 192.168.152.3.8080 > 192.168.152.3.61725: Flags [P.], seq 1119565919:1119571913, ack 1944916238, win 12756, options [nop , nop,p,ts val 906474701 ecr 906474698], length 5994: HTTP: HTTP/1.1 200 0K
16:00:13.489784 IP 192.168.152.3.61725 > 192.168.152.3.8080: FLags [.],ack 1119571913, win 12572, options [nop,nop,TS val 906474701 ecr 906474701], length❷
#传输数据end
# TCP四次挥手start
16:00:13.490836 IP 192.168.152.3.61725 > 192.168.152.3.8080: Flags_ [F.], seq 1944916238, ack 1119571913,win 12572,options [nop,nop,TS val 906474702 ecr906474701],length 0
16:00:13490869 IP 192.168.152.3. 8080 > 10.37. 63.3.61725: Flags [.],ack 1944916239, win 12756, options [nop ,nop,TS val 906474702 ecr 906474702], length0
16:00:13.490875 IP 192.168.152.3.61725 > 192.168.152.3.8080: Flags [.], ack_ 1119571913, win 12572, options [nop,nop,TS val 906474702 ecr 906474702], length0
16:00:13.491004 IP 192.168.152.3.8080 > 192.168.152.3.61725: Flags [F.],seq 1119571913, ack 1944916239,win 12756, options [nop,nop,TS val 906474702 ecr906474702],length
16:00:13.491081 IP 10.37. 63.3.61725 > 192.168.152.3. 8080: Flags [.],ack 1119571914, win 12572, options [nop ,nop,TS val 906474702 ecr 906474702], length0
# TCP四次挥手end
每一行中间都有这个包所携带的标志:
- S=SYN,发起连接标志。
- P=PUSH,传送数据标志。
- F=FIN,关闭连接标志。
- ack,表示确认包。
- RST=RESET,异常关闭连接。
- .,表示没有任何标志。
第1行:16:00:13.486776,从192.168.152.3(client)的临时端口61725向192.168.152.3(server)的8080监听端口发起连接,client初始包序号seq为1944916150,滑动窗口大小为65535字节(滑动窗口即tcp接收缓冲区的大小,用于tcp拥塞控制),mss大小为16344(即可接收的最大包长度,通常为MTU减40字节,IP头和TCP头各20字节)。【seq=1944916150,ack=0,syn=1】
第2行:16:00:13.486850,server响应连接,同时带上第一个包的ack信息,为client端的初始包序号seq加1,即1944916151,即server端下次等待接受这个包序号的包,用于tcp字节流的顺序控制。Server端的初始包序号seq为1119565918,mss也是16344。【seq=1119565918,ack=1944916151,syn=1】
第3行:15:46:13.084161,client再次发送确认连接,tcp连接三次握手完成,等待传输数据包。【ack=1119565919,seq=1944916151】
2、TCP四次挥手
连接双方在完成数据传输之后就需要断开连接。由于TCP连接是属于全双工的,即连接双方可以在一条TCP连接上互相传输数据,因此在断开时存在一个半关闭状态,即有有一方失去发送数据的能力,却还能接收数据。因此,断开连接需要分为四次。主要过程如下:
- step1. 主机A向主机B发起断开连接请求,之后主机A进入FIN-WAIT-1状态;
- step2. 主机B收到主机A的请求后,向主机A发回确认,然后进入CLOSE-WAIT状态;
- step3. 主机A收到B的确认之后,进入FIN-WAIT-2状态,此时便是半关闭状态,即主机A失去发送能力,但是主机B却还能向A发送数据,并且A可以接收数据。此时主机B占主导位置了,如果需要继续关闭则需要主机B来操作了;
- step4. 主机B向A发出断开连接请求,然后进入LAST-ACK状态;
- step5. 主机A接收到请求后发送确认,进入TIME-WAIT状态,等待2MSL之后进入CLOSED状态,而主机B则在接受到确认后进入CLOSED状态;
为何主机A在发送了最后的确认后没有进入CLOSED状态,反而进入了一个等待2MSL的TIME-WAIT主要作用有两个:
第一,确保主机A最后发送的确认能够到达主机B。如果处于LAST-ACK状态的主机B一直收不到来自主机A的确认,它会重传断开连接请求,然后主机A就可以有足够的时间去再次发送确认。但是这也只能尽最大力量来确保能够正常断开,如果主机A的确认总是在网络中滞留失效,从而超过了2MSL,最后也无法正常断开;
第二,如果主机A在发送了确认之后立即进入CLOSED状态。假设之后主机A再次向主机B发送一条连接请求,而这条连接请求比之前的确认报文更早地到达主机B,则会使得主机B以为这条连接请求是在旧的连接中A发出的报文,并不看成是一条新的连接请求了,即使得这个连接请求失效了,增加2MSL的时间可以使得这个失效的连接请求报文作废,这样才不影响下次新的连接请求中出现失效的连接请求。
为什么断开连接请求报文只有三个,而不是四个因为在TCP连接过程中,确认的发送有一个延时(即经受延时的确认),一端在发送确认的时候将等待一段时间,如果自己在这段事件内也有数据要发送,就跟确认一起发送,如果没有,则确认单独发送。而我们的抓包实验中,由服务器端先断开连接,之后客户端在确认的延迟时间内,也有请求断开连接需要发送,于是就与上次确认一起发送,因此就只有三个数据报了。
3、Wireshark 分析 Tcpdump 抓包结果
1、Tcpdump 抓包
tcpdump host 10.37.63.3 -i lo and port 8080 -n -w ./Desktop/tcpdump_10.37.63.3_8080_20160525.cap
# 然后再执行curl
curl http://10.37.63.3:8080/atbg/doc
2、Wireshark 分析
使用Wireshark打开tcpdump_10.37.63.3_8080_20160525.cap文件
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ymVN4l2x-1608122997113)(assets/image-20200304005033561.png)]
- No. 1-4 行:TCP三次握手环节;
- No. 5-8 行:TCP传输数据环节;
- No. 9-13 行:TCP四次挥手环节;
3、查看 http 请求和响应的方法
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-3ugKxuCe-1608122997115)(assets/image-20200304005118038.png)]
弹窗如下图所示,上面红色部分为请求信息,下面蓝色部分为响应信息:
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-xL0WCm3P-1608122997117)(assets/image-20200304005147620.png)]
以上是 Wireshark 分析 tcpdump 的简单使用,Wireshark更强大的是过滤器工具,大家可以自行去多研究学习Wireshark.