外观
一句话答案
三次握手建立连接(SYN→SYN+ACK→ACK),四次挥手关闭连接(FIN→ACK→FIN→ACK),确保双方可靠通信。
核心要点
三次握手过程:
客户端 服务端
│── SYN(seq=x)──────────────→│ 第1次:客户端请求建立连接
│← SYN-ACK(seq=y, ack=x+1)──│ 第2次:服务端确认,同时发起自己的 SYN
│── ACK(ack=y+1)────────────→│ 第3次:客户端确认服务端的 SYN
│ │
├──────── 连接建立,可以传数据 ──┤为什么需要三次,而不是两次?
防止"历史失效连接请求"造成资源浪费:
场景(只有两次握手的问题):
T1: 客户端发出 SYN1(因网络延迟,迟迟未到达服务端)
T2: 客户端超时,重发 SYN2,正常建立连接,用完后关闭
T3: 延迟的 SYN1 终于到达服务端
→ 两次握手:服务端收到 SYN1,发 SYN-ACK,认为连接建立
→ 服务端分配资源,等待客户端数据
→ 客户端早已关闭,不会响应(连接对客户端来说是"失效的")
→ 服务端的资源白白占用(直到超时释放)三次握手的第三次 ACK 的作用:
- 让服务端确认客户端"此时仍然活着且愿意建立连接"
- 如果第三次 ACK 没来(历史 SYN),服务端的 SYN-ACK 没有响应,服务端不会维持连接状态
三次握手还确认了双方的初始序列号(ISN):
- 服务端知道客户端的初始序列号(x)
- 客户端知道服务端的初始序列号(y)
- 双方都能确认对方"收到了我的 SYN",保证了双向通信能力
为什么不需要四次?
- 服务端可以在一个报文里同时发 SYN + ACK(合并为 SYN-ACK),节省一次握手
追问与易错
追问方向:
- 为什么握手三次不是两次?(防止历史连接/服务端资源浪费)
- 为什么挥手需要四次?(半关闭状态,服务端可能还有数据要发)
- SYN Flood 攻击原理和防护?(伪造源 IP 发大量 SYN,用 SYN Cookie 防护)
易错点:
- ❌ "三次握手是为了可靠"——更准确说是为了同步双方的初始序列号
- ❌ "第三次握手不能携带数据"——可以的,此时客户端已确认连接建立
💡 记忆锚点
三次握手像打电话:A说"听到吗?"(SYN)→ B说"听到了,你呢?"(SYN+ACK)→ A说"我也听到了"(ACK)。两次不够是因为B无法确认A能收到自己的话,可能对着一个已经挂掉的旧来电白白说话(历史失效SYN问题)。四次挥手多一次是因为B说"知道了"之后可能还有话没说完(半关闭),说完才能挂。