最新消息:

TFO(TCP Fast Open)介绍

IT技术 ipcpu 7596浏览

一、TFO概述

为了改善web应用相应时延,google发布了通过修改TCP协议利用三次握手时进行数据交换的TFO(TCP fast open,RFC 7413)。

TFO允许在TCP握手期间发送和接收初始SYN分组中的数据。如果客户端和服务器都支持TFO功能,则可以减少建立到同一服务器的多个TCP连接的延迟。这是通过在初始TCP握手之后在客户端上存储TFO cookie来实现的。如果客户端稍后重新连接,则此TFO cookie将发送到服务器,从而允许连续的TCP握手跳过一个往返延迟,从而减少延迟。

二、TFO原理图

普通的TCP连接过程如下图所示

而TFO的连接过程如下

当客户端断开一段时间后,再次连接过程如下

可以看出使用TFO后,连接时间少了一个RTT的延迟。

三、TFO的开启

TFO功能在Linux 3.7 内核中开始集成,因此RHEL7/CentOS7是支持的,但默认没有开启,使用以下方式开启:

echo 3 > /proc/sys/net/ipv4/tcp_fastopen
#3的意思是开启TFO客户端和服务器端
#1表示开启客户端,2表示开启服务器端

除了内核的支持,应用程序也要开启支持,例如nginx(1.5.8+)开启方法如下:

 server {
        listen 80 backlog=4096 fastopen=256 default;
        server_name _;

四、TFO的客户端支持情况

Linux 3.7 以后的内核,可以手动开启。3.13以后的内核默认开启(默认为1)。
Windows10 默认开启1607+(自动更新打开的情况下)
windows默认的Edge浏览器14352以后的版本。
Chrome浏览器在Linux、 Android上的版本。在windows上版本不支持。
Firefox浏览器默认关闭,可以手动开启。
Apple的 iOS 9 和 OS X 10.11 可以支持,但可能默认未启用。
linux下的curl 7.49以后的版本支持。

五、TFO的测试

我们在服务器端开启TFO,并配置nginx支持TFO。
客户端开启TFO,升级curl到7.61版本。然后使用curl访问HTTP页面进行测试。
客户端如下

# curl -s -o/dev/null --tcp-fastopen http://10.140.10.16/
使用ip tcp_metrics show可以看到cookie
# ip tcp_metrics show | grep "fo_cookie"
10.140.10.16 age 41.955sec tw_ts 282422045/42sec ago rtt 250us rttvar 250us cwnd 10 metric_5 2380 metric_6 1190 fo_mss 1460 fo_cookie 1640a20f99195995

服务器端抓包如下,可以看到发出的cookie,1640a20f99195995。

20:17:10.533466 IP 10.140.12.45.28722 > 10.140.10.16.80: Flags [S], seq 1532602092, win 29200, options [mss 1460,sackOK,TS val 982198124 ecr 0,nop,wscale 9,tfo cookiereq,nop,nop], length 0
20:17:10.533518 IP 10.140.10.16.80 > 10.140.12.45.28722: Flags [S.], seq 108109466, ack 1532602093, win 28960, options [mss 1460,sackOK,TS val 282422044 ecr 982198124,nop,wscale 9,tfo cookie 1640a20f99195995,nop,nop], length 0


使用以下命令可以查看TFO连接的统计信息

# grep '^TcpExt:' /proc/net/netstat | cut -d ' ' -f 87-92 | column -t
TCPOFOMerge TCPChallengeACK TCPSYNChallenge TCPFastOpenActive TCPFastOpenActiveFail TCPFastOpenPassive
9306 29958 2457 0 0 11

六、其他问题

以下问题尚未解决:

  1. 客户端的TFOcookie多长时间后删除,谁来维护和删除?
  2. nginx的TFO队列具体是什么意思?队列满了会怎样?数值设定多少合适?
    队列是RFC7413中的一种对服务器的安全保护机制,超出队列的数据包,会降级到普通的无cookie连接方式,即TFO功能失效。但这个数值具体设置多少不太好定。

七、参考资料

http://martinbj2008.github.io/2016/11/23/what-is-tfo/
https://zhuanlan.zhihu.com/p/36239657
http://abcdxyzk.github.io/blog/2018/07/30/kernel-tcp_metric/
https://tools.ietf.org/html/rfc7413

转载请注明:IPCPU-网络之路 » TFO(TCP Fast Open)介绍