传输层 TCP 协议保活机制总结(TCP 长连接)
什么是 TCP keepalive?
The keepalive concept is very simple: when you set up a TCP connection, you associate a set of timers.
为什么使用 TCP keepalive ?
TCP 是一个基于连接的协议,其连接状态是由一个状态机进行维护,连接完毕后,双方都会处于 established
状态,默认情况下,这之后的状态并不会主动进行变化。这意味着如果上层不进行任何调用,一直使 TCP 连接空闲,那么这个连接虽然没有任何数据,但仍然保持连接状态,一天、一星期、甚至一个月,即使在这期间:
- 对端主机系统奔溃
- 中间路由原因(如奔溃重启、NAT 转换表移除该记录)
TCP keepalive 的两个目标
Checking for dead peers
1 | _____ _____ |
Preventing disconnection due to network inactivity
1 | _____ _____ _____ |
Linux 使用 TCP keepalive
Linux 有内置的 keepalive 支持,配置如下:
1 | $ cat /proc/sys/net/ipv4/tcp_keepalive_time |
上述参数表示:默认情况下一条 TCP 连接在 2 小时(7200 秒)都没有报文交换后,会开始进行保活探测,若再经过 9*75 秒 = 11 分钟 15 秒的循环探测都未收到探测响应(即共计:2 小时 11 分钟 15 秒),就会自动断开 TCP 连接。
在探测过程中,对方主机会处于以下四种状态之一:
状态 | 处理方式 | |
---|---|---|
对方主机仍在工作,并且可达 | TCP 连接正常,将 keepalive 计时器重置 | |
对方主机崩溃,并且已经重启 | 重启后原连接已失效,对方主机由于不认识探测报文,会响应重置报文段(RST) | TCP 连接断开重连 |
对方主机已崩溃(已关机或者正在重启) | TCP 连接不正常,请求端经过指定次数的探测依然没得到响应 | TCP 连接断开重连 |
对方主机仍在工作,但由于网络原因不可达 | TCP 连接不正常,请求端经过指定次数的探测依然没得到响应 | TCP 连接断开重连 |
应用程序使用 TCP keepalive
参考
《TCP/IP 详解 卷 1: 协议》第二版,第 17 章:TCP Keepalive 保活机制》
https://tldp.org/HOWTO/TCP-Keepalive-HOWTO/index.html
https://en.wikipedia.org/wiki/Keepalive