抓包分析TCP三次握手&四次挥手

三次握手

在这里插入图片描述
第一次握手
客户端向服务器发送请求报文段,标志位SYN = 1, ack = 0, 同时选择一个初始序号seq = i (0) 此时TCP客户进入 SYN_SEND(同步已发送) 状态 SYN 报文段要消耗一个序号
在这里插入图片描述
第二次握手
服务器端收到客户端发来的请求报文后,如果同意建立连接,则向客户端发送确认报文。
SYN=1, ACK=1, 确认号ack = i + 1 (1), 同时为自己选择一个初始序号 seq = k (0)
此时,TCP服务端进入**SYN_RCVD(同步收到)**状态.
在这里插入图片描述

第三次握手
TCP客户端进程收到服务端进程的确认后,还要向服务端给出确认。确认报文段的ACK=1, 确认号 ack = k + 1 (1), 而自己的序号为seq = i + 1 (1)
TCP 的标准规定,ACK报文段可以携带数据,但如果不携带数据则不消耗序号。 因此,如果不携带数据,下一个报文段的序号为 seq = i + 1 (1)
这时,TCP连接已经建立,客户端进入 ESTABLISHED 状态
在这里插入图片描述

四次挥手

在这里插入图片描述
第一次挥手
客户端进程发出连接释放报文,并停止发送数据(超时重传机制还在运行),FIN=1,其序列号为seq=u (1)(等于前面已经传送过来的数据的最后一个字节的序号加1),此时,客户端进入FIN-WAIT-1(终止等待1)状态。 TCP规定,FIN报文段即使不携带数据,也要消耗一个序号。
在这里插入图片描述

第二次挥手
服务器收到连接释放报文,发出确认报文,ACK=1, ack = u + 1, 并且带上自己的序列号seq = v
此时,服务端进入CLOSE_WAIT (关闭等待)状态. TCP 服务器通知高层的应用进程,客户端向服务器方向的连接释放了,这时候处于半关闭状态,即客户端已经没有数据要发送了,但是服务器若发送数据,客户端依然接受。这个状态还要持续一段时间,也就是整个CLOSE_WAIT状态持续的时间
在这里插入图片描述

客户端收到服务器的确认请求后,客户端进入**FIN_WAIT_2 **(终止等待2) 状态, 等待服务器发送连接释放报文. (在这之前还需要接受服务器发送的最后的数据)

第三次挥手
服务器将最后的数据发送完毕后,就向客户端发送连接释放报文,FIN=1,ack=u+1,由于在半关闭状态,服务器很可能又发送了一些数据,假定此时的序列号为seq=w,此时,服务器就进入了**LAST-ACK(最后确认)状态,等待客户端的确认
在这里插入图片描述
第四次挥手
客户端收到服务器的连接释放报文后,必须发出确认,ACK=1ack=w+1 (2), 而自己的序列号是seq=u+1,此时,客户端就进入了
TIME-WAIT(时间等待)状态.
注意此时TCP连接还没有释放,必须经过2∗MSL(最长报文段寿命)的时间后,当客户端撤销相应的TCB后,才进入CLOSED状态

服务器只要收到了客户端发出的确认,立即进入CLOSED状态
在这里插入图片描述

过程

添加链接描述在这里插入图片描述
(注:本文大部分内容复制粘贴一把梭

为什么不是两次握手?

两次握手的情况下, 如果客户端的连接请求报文在网络上滞留了一段时间. 当客户端重传报文和服务器通信结束后, 失效的请求可能会让服务器误认为是客户端新建的请求. 那么服务器就会建立连接, 同时向客户端发送确认报文, 这样就浪费了服务器的资源.
而三次握手, 服务器收到客户端的确认报文之后才会建立连接, 这样会节省服务器的资源.

为什么四次握手最后会有time_wait状态?

为了保证最后一个确认报文能传输到服务器. 因为服务器是收到客户端的ACK报文之后才进入到 CLOSED 的状态, 没有time_wait, 当客户端发完ACK报文, 立刻进入CLOSED状态, 当报文丢失的时候, 会导致服务器不能正常进入关闭状态.

猜你喜欢

转载自blog.csdn.net/weixin_41889284/article/details/88351379