TCP断开连接为什么需要4次挥手?

程序员小迷 2024-04-19 17:17:02

一、断开连接过程

由于TCP连接是全双工的,因此每个方向都必须单独关闭。客户端在数据发送完毕后发送一个结束数据段FIN,且服务端也返回确认数据段ACK,此时结束了客户端到服务端的连接;然后客户端接收到服务端发送的FIN,且服务端也收到了客户端发送的ACK之后,自此双方的数据通信完全结束。简单说来是 "先关读,后关写",一共需要四个阶段:服务器读通道关闭->客户机写通道关闭->客户机读通道关闭->服务器写通道关闭。

4次挥手中的每次"挥手"(即报文交换)都是对之前动作的确认,确保了数据的可靠传输直到连接完全关闭。例如,客户端发送FIN后进入FIN-WAIT-1状态,等待服务端的ACK;服务端收到FIN后发送ACK,并进入CLOSE-WAIT状态继续发送剩余数据,之后再发送FIN;客户端收到ACK后进入FIN-WAIT-2状态,收到服务端的FIN后发送最后一个ACK,并进入TIME-WAIT状态等待可能滞后的服务端数据报文,确认没有未送达的数据后,连接最终关闭。

二、需要4次挥手的原因

1.双方均可主动关闭:

与三次握手类似,4次挥手确保了双方都能够有序地关闭连接。双方都可以主动发起关闭连接的过程。

2.确认数据接收:

通过4次挥手过程中的ACK报文,每一方都确认收到了对方的FIN报文,确保了数据被可靠传输。

3.避免数据丢失:

在关闭连接之前,必须保证已经发送的数据被对方接收,同时也要允许对方发送的数据被本端接收。4次挥手过程提供了这样的机制,确保数据不会因为连接的关闭而丢失。

4.全双工通信:

TCP是全双工协议,意味着数据可以在两个方向上同时传输。因此,每个方向上的连接都需要独立关闭。每个方向上都要经历一次"我已完成发送"(FIN,Finish)的信号交换和对方对此的确认(ACK,Acknowledgment)。由于关闭连接涉及两个方向,所以至少需要两次这样的信号交换,总共4次挥手。这就是为什么需要两次FIN和两次ACK的原因。

5.关闭顺序的灵活性: 任一端(客户端或服务端)都可以主动发起关闭连接的请求。当一方(例如客户端)完成数据发送并准备关闭连接时,它会发送一个FIN报文给另一方(服务端)。服务端收到FIN后,确认已收到(发送ACK),但此时服务端可能还在发送数据或需要一些时间来清理资源。服务端完成数据发送后,也会发送自己的FIN报文给客户端,客户端再回复ACK确认。这种双向的关闭过程确保双方都同意关闭,并且各自的数据传输都已经结束。

6.等待足够时间:

在第4次挥手中,最初发送FIN报文的一方在发送ACK报文后,需要等待一段时间2*MSL(MSL:Maximum Segment  Lifetime报文段最大生存时间,它是任何报文段被丢弃前在网络内的最长时间),以确保对方收到了这个ACK报文。这个过程称为TIME_WAIT状态,它有助于确保远程端正确关闭连接,并允许迟到的数据包到达。

7.资源释放:

4次挥手过程还负责适当地释放在建立连接时分配的资源,如端口号、内存缓冲区等。

8.保持一致性:

4次挥手保持了与三次握手过程的一致性。虽然它们的目的不同(三次握手用于建立连接,4次挥手用于断开连接),但都是为了保证TCP连接的可靠性和稳定性。

三、总结

总的来说,4次挥手是TCP协议为了确保连接可靠、有序地关闭而设计的,它允许双方都能完成数据的发送和确认,避免了数据丢失,并且确保了资源的合理释放。

致力于C、C++、Java、Kotlin、Android、Shell、JavaScript、TypeScript、Python等编程技术的技巧经验分享。

若作品对您有帮助,请关注、分享、点赞、收藏、在看、喜欢。您的支持是我们为您提供帮助的最大动力。

0 阅读:0

程序员小迷

简介:致力于Android、iOS、C、Java等编程技术的技巧经验分享