查看 tcp 的网络链接状况nginx
netstat -anp |grep tcp
复制代码
TCP快速打开(TCP Fast Open,TFO)是对TCP的一种简化握手手续的拓展,用于提升两端点间链接的打开速度。简而言之,就是在TCP的三次握手过程当中传输实际有用的数据安全
三次握手的过程当中,当用户首次访问server时,发送syn包,server根据用户IP生成cookie,并与syn+ack一同发回client;client再次访问server时,在syn包携带TCP cookie;若是server校验合法,则在用户回复ack前就能够直接发送数据;不然按照正常三次握手进行。bash
TFO提升性能的关键是省去了热请求的三次握手,这在充斥着小对象的移动应用场景中可以极大提高性能。服务器
sysctl -w net.ipv4.tcp_fastopen=1
其中数字包含含义以下:
0: 关闭
1: 做为客户端时使用 TFO
2: 做为服务端时使用 TFO
3. 所有使用TFO
复制代码
因须要相关代码支持开启 TCP_FASTOPEN 选项, 因此没法正常抓nginx请求包, 此图来源于网络.cookie
从上面的示例中能够看到 TFO 的其中一个优势就是能够提升网络的利用率,尤为是有频繁网络创建的情景,TFO 的优点尤为明显。可是,除此以外,TFO 还有一个很大的优势就是能够防止 SYN泛洪攻击。网络
Message Flow:tcp
Requesting Fast Open Cookie in connection 1:
TCP A (Client) TCP B (Server)
______________ ______________
CLOSED LISTEN
#1 SYN-SENT ----- <SYN,CookieOpt=NIL> ----------> SYN-RCVD
#2 ESTABLISHED <---- <SYN,ACK,CookieOpt=C> ---------- SYN-RCVD
(caches cookie C)
Performing TCP Fast Open in connection 2:
TCP A (Client) TCP B (Server)
______________ ______________
CLOSED LISTEN
#1 SYN-SENT ----- <SYN=x,CookieOpt=C,DATA_A> ----> SYN-RCVD
#2 ESTABLISHED <---- <SYN=y,ACK=x+len(DATA_A)+1> ---- SYN-RCVD
#3 ESTABLISHED <---- <ACK=x+len(DATA_A)+1,DATA_B>---- SYN-RCVD
#4 ESTABLISHED ----- <ACK=y+1>--------------------> ESTABLISHED
#5 ESTABLISHED --- <ACK=y+len(DATA_B)+1>----------> ESTABLISHED
复制代码
TCP SYN泛洪发生在OSI第四层,这种方式利用TCP协议的特性,就是三次握手。攻击者发送TCP SYN,SYN是TCP三次握手中的第一个数据包,而当服务器返回ACK后,该攻击者就不对其进行再确认,那这个TCP链接就处于挂起状态,也就是所谓的半链接状态,服务器收不到再确认的话,还会重复发送ACK给攻击者。这样更加会浪费服务器的资源。攻击者就对服务器发送很是大量的这种TCP链接,因为每个都无法完成三次握手,因此在服务器上,这些TCP链接会由于挂起状态而消耗CPU和内存,最后服务器可能死机,就没法为正经常使用户提供服务了。(来源:百度百科)性能
经过上图流程, 咱们发如今 SYN 中间实际上是维护了一个队列, SYN 攻击就是短期内伪造不一样 IP 地址的 SYN 报文, 快速占满 backlog 队列, 使服务不能提供正常服务.优化
咱们观察图中, 在 server 端维护着两个队列, 分别是 syns queue 和 accept queue, 这两个队列的大小可使用 tcp_max_syn_backlog 和 somaxconn 两个内核配置.spa
tcp_max_syn_backlog 是指定所能接受SYN同步包的最大客户端数量,即半链接上限
somaxconn 是指服务端所能accept即处理数据的最大客户端数量,即完成链接上限
复制代码
其中还有两个内核参数咱们常常接触:
tcp_abort_on_overflow
当 tcp 创建链接的 3 路握手完成后,将链接置入 ESTABLISHED 状态并交付给应用程序的 backlog 队列时,会检查 backlog 队列是否已满。若已满,一般行为是将链接还原至 SYN_ACK 状态,以形成 3 路握手最后的 ACK 包意外丢失假象 —— 这样在客户端等待超时后可重发 ACK —— 以再次尝试进入 ESTABLISHED 状态 —— 做为一种修复/重试机制。若是启用 tcp_abort_on_overflow 则在检查到 backlog 队列已满时,直接发 RST 包给客户端终止此链接 —— 此时客户端程序会收到 104 Connection reset by peer 错误。
tcp_syncookies
在 tcp 创建链接的 3 次握手过程当中,当服务端收到最初的 SYN 请求时,会检查应用程序的 syn_backlog 队列是否已满。若已满,一般行为是丢弃此 SYN 包。若未满,会再检查应用程序的 backlog 队列是否已满。若已满而且系统根据历史记录判断该应用程序不会较快消耗链接时,则丢弃此 SYN 包。若是启用 tcp_syncookies 则在检查到 syn_backlog 队列已满时,不丢弃该 SYN 包,而改用 syncookie 技术进行 3 次握手。 (当队列未满时, 不会使用此方式).
文中部分图片和知识来源于网络.
部分 TCP 内核参数完全了解(blog.csdn.net/rain_qingti…)
更多精彩内容关注公众号 (呆呆熊的技术路) :