故障現象
同一台物理機上的多台虛擬機同時出現應用服務超時、無法訪問等現象,ping虛擬機和物理機丟包嚴重。
故障原因
物理機上某台虛擬機建立了大量連接,導致物理機連接追蹤表被大量ESTABLISHED連接記錄塞滿,進而出現丟包現象。
處理方法
調整物理機內核參數,增大最大連接追蹤記錄數、減小ESTABLISHED、TIME_WAIT、CLOSE_WAIT、FIN_WAIT等連接記錄的超時時間。
排查過程
一開始從業務層面排查,分析是否有某台虛擬機占用帶寬的情況,但是排查監控和實時流量並沒有發現問題,未果。第二次出現問題時,在宿主機上ping故障虛擬機,出現“ping: sendmsg: Operation not permitted”的報錯:
# ping 172.16.3.5 PING 172.16.3.5 (172.16.3.5) 56(84) bytes of data. ping: sendmsg: Operation not permitted ping: sendmsg: Operation not permitted ping: sendmsg: Operation not permitted ping: sendmsg: Operation not permitted
查看內核日志,報錯如下:
# dmesg | tail [64802472.971773] nf_conntrack: table full, dropping packet [64802472.972242] nf_conntrack: table full, dropping packet [64802472.973668] nf_conntrack: table full, dropping packet [64802472.978622] nf_conntrack: table full, dropping packet [64802472.988458] nf_conntrack: table full, dropping packet [64802472.991945] nf_conntrack: table full, dropping packet [64802472.998772] nf_conntrack: table full, dropping packet [64802472.999542] nf_conntrack: table full, dropping packet [64802473.001464] nf_conntrack: table full, dropping packet [64802473.001768] nf_conntrack: table full, dropping packet
發現是由於連接追蹤表滿導致丟包。其實這個問題出現過一次,當時是存在大量TIME_WAIT連接記錄所致,現在這個問題是存在大量ESTABLISHED連接記錄所致:
# cat /proc/net/nf_conntrack | awk '/^.*tcp.*$/ {count[$6]++} END {for(state in count) print state, count[state]}' LAST_ACK 36 SYN_RECV 52 CLOSE_WAIT 350 CLOSE 844 ESTABLISHED 246265 FIN_WAIT 4 SYN_SENT 993 TIME_WAIT 9996
找到問題所在就好辦了,通過調整相關內核參數解決:
# sysctl -a | grep nf_conntrack net.nf_conntrack_max = 2097152 net.netfilter.nf_conntrack_max = 2097152 net.netfilter.nf_conntrack_tcp_timeout_fin_wait = 30 net.netfilter.nf_conntrack_tcp_timeout_time_wait = 30 net.netfilter.nf_conntrack_tcp_timeout_close_wait = 60 net.netfilter.nf_conntrack_tcp_timeout_established = 3600
將以上參數寫入/etc/sysctl.conf中,執行sysctl -p生效。
另外還有net.netfilter.nf_conntrack_buckets參數,指定哈希表的大小。在4.8及以上的內核可以通過sysctl修改,在4.8之前的內核中是只讀的,只能通過修改/sys/module/nf_conntrack/parameters/hashsize來修改。
參考資料
nf_conntrack: table full, dropping packet. 終結篇
[踩坑總結] nf_conntrack: table full, dropping packet