作者基于自己的理解稍微整理了一下三次握手和四次挥手的机制,如有不对的地方,还请在评论区指教一下,谢谢。
C:客户端
S:服务端
三次握手:
- C向S发送一个请求,SYN同步序号,并初始化一个序列号x
- S接收后,向C发送一个ACK确认号,和一个SYN同步序列号,初始化一个序列号y,并将x+1作为确认号和y序列号都发送过去
- C接收后,会发送一个ACK确认号,并将y+1发送过去
为什么要发序号?
可以保证数据不丢失
为什么服务器还要发送SYN握手信号?
SYN信号是为了建立并确认通信
为什么是三次握手而不是两次握手?
并不是说必须得三次握手,而是至少三次握手。
当握手是两次时,会出现什么问题?
客户端向服务器发送了一次建立TCP请求,但是因为网络问题而滞缓了。导致长时间没有发送到服务器,这时候,客户端因为没有收到服务器的确认信号,就用了重传机制,这次正常的传送到了。服务器和客户端愉快的建立了TCP连接并处理完后关闭了连接。
但是!这时候第一次请求突然送到服务器这里来了。服务器就以为客户端还要建立连接,于是再次发送确认信号。在两次握手的规则下,客户端即使不想建立连接,但还是建立了。(很尴尬)这样会造成不必要的资源损失。
但是!如果这时候是三次握手的话,客户端就不会发送确认信号,这时候就不会建立TCP连接(皆大欢喜,皆大欢喜!)
四次挥手:
主动断开连接:
- C向S发送一个FIN信号,并初始化序列号SEQ = x
- S向C发送一个ACK信号,表明知道要断开了,并加上确认号x+1,C进入半关闭状态
- S这时还需要发送一定的数据(可能),C仍然会接受数据
- S向C发送一个FIN+ACK信号,表明确实要断开了,加上初始化的序列号SEQ = y
- C向S发送一个ACK信号,确认断开,加上确认号y+1
为什么客户端最后还要等待2MSL?
MSL是最大分段寿命,TCP允许修改MSL的数值
- 为了保证客户端最后一个ACK信号能够被确认收到。如果这个ACK信号丢失了,那么服务器会以为客户端没收到FIN+ACK信号,所以还会重传一次。这时候客户端就知道了,它会再传一次ACK,以确保服务器不再发FIN+ACK
- 发送完最后一个确认报文后,在2MSL时间内可以使旧连接的报文段消失,这样新连接就不会出现旧连接的报文