文中图片均来自于
https://www.bilibili.com/video/BV1c4411d7jb?p=65&vd_source=61258a05469482a4381c086011c25c18
1.使用TCP客户进程的应用进程通知其 主动关闭TCP连接
客户端 发送 连接释放报文(FIN=1,ACK=1,seq=u,ack=v),发送完毕后,客户端进入FIN-WAIT-1(终止等待1)状态
FIN,终止标志位,TCP规定当FIN=1时,即使报文段不携带数据,也要消耗一个序号
seq=u,u的取值为 客户端已传送过的数据的最后一个字节的序号+1
ack=v,v的取值为 客户端已经收到的服务端发送的数据的最后一个字节的序号+1
2.服务端收到 连接释放报文,发送 一个普通的确认收到报文(ACK=1,seq=v,ack=u+1),发送完毕后,服务端进入CLOSE-WAIT(关闭等待)状态。当客户端收到确认报文后,进入FIN-WAIT(终止等待2)状态。
服务端通知应用进程,客户端要断开与自己的连接,此时从客户端到服务端的TCP连接释放。
此时的TCP连接属于半关闭状态,客户端已经没有数据要发送,但服务端如果还有数据要发送,客户端需要接收
seq=v,报文段数据载荷第一个字节的序号为v
ack=u+1,u+1号之前的数据得到了确认,期望收到下一个报文段数据载荷中第一个字节 序号为u+1的数据
3.当使用TCP服务进程的应用进程没有数据要发送时,应用进程通知TCP服务进程释放连接
服务端发送 连接释放报文(FIN=1,ACK=1,seq=w,ack=u+1),发送完毕后,服务端进入LAST-ACK(最后确认)状态
seq=w,w的取值为 服务端已传送过的数据的最后一个字节的序号+1
ack=u+1,u+1号之前的数据得到了确认,期望收到下一个报文段数据载荷中第一个字节 序号为u+1的数据
4.客户端收到 连接释放报文,发送 一个普通的确认收到报文(ACK=1,seq=u+1,ack=w+1),发送完毕后,客户端进入TIME-WAIT(时间等待)状态。在等待2MSL时间后,期间没有收到服务端的报文,认为服务端已经正常关闭,自己也进入CLOSED(关闭)状态。服务端收到 连接释放报文后,进入CLOSED(关闭)状态
MSL(Maximum Segment Lifetime 最长报文段寿命)
seq=u+1,u为客户端已经发送过的数据的最后一个字节序号为u
ack=w+1,w+1号之前的数据得到了确认,期望收到下一个报文段数据载荷中第一个字节 序号为w+1的数据
5.11.1 相关问题
- TCP挥手为什么需要四次
当客户端数据发送完毕,发送连接释放报文给服务端,表示要释放连接。
服务端收到后,发送 确认收到报文。此时服务端可能还有数据没有发送给客户端,客户端在收到确认报文后,进入半关闭状态,需要接收服务端发送的报文。
当服务端的数据发送完毕,服务端对应的应用进程会通知服务端释放连接,服务端发送 连接释放报文,客户端收到 并发送确认收到报文,服务端收到后进入关闭状态,客户端等待2MSL后,也进入关闭状态。
上述四次握手才能实现释放连接的功能
- TCP四次挥手过程中,客户端为什么需要等待2MSL,才能进入关闭状态
1.保证客户端发送的确认报文能够到达服务端
如果客户端在发送完 确认收到报文后,直接进入关闭状态 可能出现以下场景
客户端发送的确认收到报文,在传送过程中丢失,服务端的连接释放报文对应的重传计时器超时,向客户端再次发送 连接释放报文,但客户端已经关闭,不会理睬该报文,则服务端会持续发送 连接释放报文
在设置等待时间后,确认报文如果丢失,客户端就能收到服务端重传的连接释放报文
2.防止已失效的连接请求报文段出现在本连接中
客户端在发送完确认收到报文后,经过2MSL的时间,就可以使本连接持续的时间内所产生的所有报文段在网络中消失。这样下一个连接中不会出现旧连接的请求报文段