2、TCP/IP基础回顾:TCP三次握手与四次挥手、TCP保活机制(Keep-Alive)、Socket编程基础

SECS/GEM 通信链路建立在 TCP/IP 协议栈之上。理解 TCP 的连接建立、断开机制以及保活特性,是掌握链路保活与异常恢复的前提。本节将回顾 TCP 的核心机制,并介绍 Socket 编程的基本模型,为后续分析 SECS/GEM 通信行为奠定基础。

2.1 TCP 三次握手:连接建立

TCP 使用三次握手(Three-Way Handshake)在客户端与服务器之间建立可靠的连接。该过程确保双方均具备收发能力,并同步初始序列号(ISN)。

核心目的: 防止已失效的连接请求到达服务器后建立错误连接,同时协商通信参数。

握手流程

  1. SYN(客户端 → 服务器): 客户端发送 SYN 报文,携带初始序列号 seq=x,进入 SYN_SENT 状态。
  2. SYN+ACK(服务器 → 客户端): 服务器收到后回复 SYN+ACK,确认号 ack=x+1,并携带自己的序列号 seq=y,进入 SYN_RCVD 状态。
  3. ACK(客户端 → 服务器): 客户端发送 ACK 报文,确认号 ack=y+1,双方进入 ESTABLISHED 状态,连接建立完成。
TCP 三次握手流程 客户端 服务器 ① SYN (seq=x) ② SYN+ACK (seq=y, ack=x+1) ③ ACK (seq=x+1, ack=y+1) SYN_SENT → ESTABLISHED SYN_RCVD → ESTABLISHED 连接建立后,双方进入 ESTABLISHED 状态,开始数据传输

2.2 TCP 四次挥手:连接断开

TCP 连接断开采用四次挥手(Four-Way Wavehand),允许双方独立关闭各自的数据传输通道,确保数据完整交付。

挥手流程

步骤 报文方向 报文类型 状态变化
① 主动方 → 被动方 FIN (seq=u) 主动方: ESTABLISHED → FIN_WAIT_1
② 被动方 → 主动方 ACK (ack=u+1) 被动方: ESTABLISHED → CLOSE_WAIT
主动方: FIN_WAIT_1 → FIN_WAIT_2
③ 被动方 → 主动方 FIN (seq=v) 被动方: CLOSE_WAIT → LAST_ACK
④ 主动方 → 被动方 ACK (ack=v+1) 主动方: FIN_WAIT_2 → TIME_WAIT → CLOSED
被动方: LAST_ACK → CLOSED
注意: TIME_WAIT 状态持续 2MSL(最大报文段生存时间),目的是确保被动方收到最后的 ACK,并防止旧连接报文干扰新连接。在 SECS/GEM 场景中,频繁的连接断开可能导致大量 TIME_WAIT 堆积,需合理配置。
TCP 四次挥手流程 主动关闭方 被动关闭方 ① FIN (seq=u) ② ACK (ack=u+1) ③ FIN (seq=v) ④ ACK (ack=v+1) FIN_WAIT_1 → FIN_WAIT_2 → TIME_WAIT → CLOSED CLOSE_WAIT → LAST_ACK → CLOSED TIME_WAIT 持续 2MSL,确保被动方收到最终 ACK

2.3 TCP 保活机制(Keep-Alive)

TCP Keep-Alive 是一种检测空闲连接是否仍然有效的机制。当连接长时间无数据交换时,系统自动发送探测报文,确认对端是否存活。

核心参数

参数 Linux 默认值 说明
tcp_keepalive_time 7200 秒(2 小时) 连接空闲多久后开始发送探测报文
tcp_keepalive_intvl 75 秒 探测报文发送间隔
tcp_keepalive_probes 9 次 未收到响应前最多发送探测次数
SECS/GEM 实践提示: 默认 2 小时的空闲检测周期对半导体设备通信过长。通常建议将 tcp_keepalive_time 调整为 30~60 秒,以快速发现链路异常,减少设备宕机时间。

探测流程

  1. 连接空闲超过 tcp_keepalive_time 后,内核发送第一个探测报文(ACK 空包)。
  2. 若对端正常响应 ACK,连接被视为有效,保活计时器重置。
  3. 若对端无响应,按 tcp_keepalive_intvl 间隔重试,最多 tcp_keepalive_probes 次。
  4. 若所有探测均无响应,内核关闭连接,应用层收到错误通知(EPIPE 或 ECONNRESET)。
TCP Keep-Alive 探测流程 本地主机 对端主机 空闲 (tcp_keepalive_time) 空闲 探测报文 1 (ACK) 探测报文 2 (间隔 intvl) 探测报文 N (最多 probes 次) 无响应 → 内核关闭连接 → 应用层收到错误

2.4 Socket 编程基础

Socket 是应用层与 TCP/IP 协议栈之间的编程接口。SECS/GEM 通信通常基于 TCP Socket 实现,理解其基本 API 和状态转换至关重要。

TCP Socket 编程模型

阶段 服务器端 客户端
创建 socket() socket()
绑定 bind() 绑定地址和端口 —(可选,系统自动分配)
监听 listen() 进入监听状态 —
连接 accept() 接受客户端连接 connect() 发起连接
通信 send() / recv() send() / recv()
关闭 close() / shutdown() close() / shutdown()

Socket 状态转换与 SECS/GEM 关联

  • ESTABLISHED: 正常通信状态,SECS/GEM 消息在此状态下传输。
  • CLOSE_WAIT: 对端已关闭连接,本端未关闭。若应用层未及时调用 close(),会导致连接泄漏。
  • TIME_WAIT: 主动关闭后等待 2MSL。在 SECS/GEM 频繁重连场景中,大量 TIME_WAIT 可能耗尽端口资源。
  • 错误处理: recv() 返回 0 表示对端关闭;返回 -1 且 errno 为 ECONNRESET 表示连接被重置。
关键实践: 在 SECS/GEM 设备端,建议启用 TCP_NODELAY 选项禁用 Nagle 算法,减少消息延迟;同时设置 SO_KEEPALIVE 并调整保活参数,实现应用层心跳与 TCP 保活的双重检测。
TCP Socket 编程模型与状态转换 服务器 客户端 socket() → bind() → listen() → accept() → 阻塞等待 socket() → connect() 三次握手 ESTABLISHED send() / recv() 数据交换 四次挥手 close() → CLOSED close() → CLOSED SECS/GEM 基于此模型,需额外处理保活与异常恢复

2.5 小结

  • TCP 三次握手建立可靠连接,四次挥手确保数据完整关闭。
  • TCP Keep-Alive 提供内核级空闲连接检测,但默认参数不适合 SECS/GEM 场景,需调优。
  • Socket 编程模型是 SECS/GEM 通信的基础,理解状态转换有助于诊断连接异常。
  • 下一章将深入 SECS/GEM 协议栈,分析如何在应用层实现更精细的保活与恢复策略。