TCP(传输控制协议)是一种面向连接的、可靠的传输层协议,其连接的建立和释放过程通过三次握手和四次挥手实现。以下是详细流程:
一、TCP连接建立(三次握手)
目的:确保双方(客户端和服务器)的发送和接收能力正常,并同步初始序列号(ISN)。
-
第一次握手(SYN)
- 客户端发送一个
SYN=1
(同步位)的报文,并随机生成一个初始序列号seq=x
。 - 客户端进入
SYN-SENT
状态。
- 客户端发送一个
-
第二次握手(SYN + ACK)
- 服务器收到
SYN
后,回复SYN=1
和ACK=1
(确认位),并生成自己的初始序列号seq=y
。 - 确认号
ack=x+1
(表示期望收到客户端的下一个数据包序号)。 - 服务器进入
SYN-RCVD
状态。
- 服务器收到
-
第三次握手(ACK)
- 客户端收到
SYN+ACK
后,发送ACK=1
,确认号ack=y+1
,序列号seq=x+1
。 - 服务器收到后,双方进入
ESTABLISHED
状态,连接建立完成。
- 客户端收到
关键点:
- 前两次握手后,服务器已确认客户端的发送能力和自己的接收能力正常;第三次握手后,客户端确认双方的收发能力均正常。
ISN
(初始序列号)是动态生成的,防止历史连接冲突。
二、TCP连接释放(四次挥手)
目的:双方安全关闭连接,确保数据完整传输。
-
第一次挥手(FIN)
- 主动关闭方(如客户端)发送
FIN=1
,序列号seq=u
(等于已发送数据的最后一个字节序号+1)。 - 客户端进入
FIN-WAIT-1
状态。
- 主动关闭方(如客户端)发送
-
第二次挥手(ACK)
- 被动关闭方(如服务器)收到
FIN
后,发送ACK=1
,确认号ack=u+1
。 - 服务器进入
CLOSE-WAIT
状态,客户端收到后进入FIN-WAIT-2
状态。 - 此时服务器可能仍有未发送完的数据(半关闭状态)。
- 被动关闭方(如服务器)收到
-
第三次挥手(FIN)
- 服务器完成数据发送后,发送
FIN=1
,序列号seq=v
(可能因数据传输而增长)。 - 服务器进入
LAST-ACK
状态。
- 服务器完成数据发送后,发送
-
第四次挥手(ACK)
- 客户端收到
FIN
后,发送ACK=1
,确认号ack=v+1
,序列号seq=u+1
。 - 客户端进入
TIME-WAIT
状态,等待2MSL(最大报文段生存时间)后关闭连接。 - 服务器收到
ACK
后立即关闭连接。
- 客户端收到
关键点:
- TIME-WAIT的作用:
- 确保最后一个
ACK
到达服务器(若丢失,服务器会重传FIN
)。 - 让网络中残留的旧报文失效,避免影响新连接。
- 确保最后一个
- 若服务器同时关闭连接(如收到
FIN
后无剩余数据),可能合并为三次挥手(第二次和第三次合并)。
三、常见问题
-
为什么握手是三次,挥手是四次?
- 握手时,服务器的
SYN
和ACK
可合并发送;但挥手时,服务器可能仍有数据需发送,需先ACK
再FIN
。
- 握手时,服务器的
-
TIME-WAIT为什么是2MSL?
- 确保足够时间让最后一个
ACK
到达,并让网络中旧报文消失(MSL是报文最大生存时间)。
- 确保足够时间让最后一个
-
SYN洪泛攻击:攻击者伪造大量
SYN
报文但不完成握手,耗尽服务器资源。解决方案:SYN Cookie
机制。
通过三次握手和四次挥手,TCP实现了可靠的双工连接管理,确保数据传输的完整性和有序性。
以下是TCP连接建立(三次握手)和释放(四次挥手)的示意图,使用ASCII字符绘制:
TCP三次握手(连接建立)
客户端(Client) 服务器(Server)| ||-------------- SYN (seq=x) ------------> || (SYN_SENT) | (LISTEN)| ||<----- SYN+ACK (seq=y, ack=x+1) --------- || | (SYN_RCVD)| ||----------- ACK (ack=y+1) --------------> || (ESTABLISHED) | (ESTABLISHED)| |
TCP四次挥手(连接释放)
客户端(主动关闭) 服务器(被动关闭)| ||-------------- FIN (seq=u) ------------> || (FIN_WAIT_1) | (CLOSE_WAIT)| ||<------------- ACK (ack=u+1) ------------ || (FIN_WAIT_2) || ||<------------ FIN (seq=v) --------------- || | (LAST_ACK)| ||------------- ACK (ack=v+1) ------------> || (TIME_WAIT) ───等待2MSL──> 关闭 | (CLOSED)| |
关键标注说明
-
三次握手
SYN
:同步序列号(seq=x/y
)。ACK
:确认号(ack=x+1/y+1
)。- 第三次握手后,双方进入
ESTABLISHED
状态。
-
四次挥手
- 主动关闭方发送
FIN
后进入FIN_WAIT_1
,收到ACK
后进入FIN_WAIT_2
。 - 被动关闭方发送
FIN
后进入LAST_ACK
,收到ACK
后立即关闭。 - 主动关闭方需等待
2MSL
(确保最后一个ACK
到达)。
- 主动关闭方发送
可视化要点
- 箭头方向:表示报文传输方向。
- 状态标注:括号内为通信双方的状态变化。
- TIME-WAIT:仅主动关闭方需要等待,防止报文丢失或混淆。