内核参数详解
长期更新
SYN_RECV
服务端收到sys,还未发出syn+ack
1.net.ipv4.tcp_synack_retries
默认值5,linux对应1+2+4+..32=2^6-1=63s
2.net.ipv4.tcp_syncookies
应该设置为1,防止SYN Flood。
处在SYN_RECV的TCP连接称为半连接,存储在SYN队列。大量SYN_RECV会导致队列溢出,后续请求将被内核直接丢弃,也就是SYN Flood攻击。
开启syncookies后,当SYN队列满了后,TCP会通过原地址端口,目的地址端口和时间戳打造一个特别的Sequence Number(又叫cookie)发回去,如果是攻击者则不会有响应,如果是正常连接则把这个SYNCookie发回来,然后服务器端可以通过cookie建立连接(即使不在SYN队列)。
别用tcp_syncookies来处理正常大负载连接,因为syncookies是妥协版的TCP协议,不严谨。对于正常的请求可调整三个TCP参数。
1.tcp_max_syn_backlog 减少重试次数
2.tcp_max_syn_backlog 增大syn连接数
3.tcp_abort_on_overflow 处理不过来拒绝连接
CLOSE_WAIT
被动关闭的一方收到FIN后发送ACK处于CLOSE_WAIT状态。出现这种状态比较多时,一般都是没有及时close()导致的,默认将持续2小时。
TIME_WAIT
主动关闭一方,socket将在TIME_WAIT等待2msl时间。
1.net.ipv4.tcp_fin_timeout
默认值60,TCP保持在FIN_WAIT2状态的时间,超时后直接处于CLOSED,所以降低tcp_fin_timeout有助于减少TIME_WAIT数量。注意:虽然shutdown(SHUD_WR)也会处于FIN_WAIT2状态,但超时并不起作用。
2.net.ipv4.tcp_tw_recycle
默认值0,打开快速TIME_WAIT socket回收。
如果tcp_timestamps开启的话,会缓存每个连接的最新时间戳,如果后续请求时间戳小于缓存的时间戳,即视为无效,相应的包被丢弃。所以如果是nat或负载均衡环境下,就可能出现数据包丢弃的现象。
3.net.ipv4.tcp_tw_resue
默认值0,是否重用TIME_WAIT状态的socket用于新的连接
这个选项要比tcp_tw_recycle安全,从协议的角度看,复用是安全的。
网上查找的复用条件:
1.tcp_timestamps选项必须打开(客户端也必须打开)
2.重用TIME_WAIT的条件是收到最后一个包