Locked

CentOS_TIPS_002

iptables ip_conntrack/nf_conntrack 拡張

中規模/大規模なサイトや、proxy/NAT/ロードバランサ等で使用していると、以下のようなログを目にする/した事があるかもしれません。

ip_conntrack: table full, dropping packet

この場合、iptablesによって管理されているコネクションのテーブルが不足しているかもしれません。
(iptablesのルールによっては、そちらの整理で回避出来る場合もあります。)

必要に応じて(出来れば予め)確認/拡張しましょう。

ip_conntrack/nf_conntrack確認

現在値/最大値を確認します。現在値については、監視システム等で定常的に取得しておくと良いでしょう。

  • CentOS5の場合

$ cat /proc/net/stat/ip_conntrack
entries  searched found new invalid ignore delete delete_list insert insert_failed drop early_drop icmp_error  expect_new expect_create expect_delete
00000001  00000000 000158e5 0000544b 00000002 00000000 000054a7 000054a7 0000544b 00000000 00000000 00000000 00000000  00000000 00000000 00000000

$ cat /proc/sys/net/ipv4/ip_conntrack_max
65536

entriesの項が示す値(16進)が現在値です。
/proc/net/stat/ip_conntrackはインターフェース設定次第で複数行ある場合がありますが、特に設定しなければentriesの項は同じ値(テーブルが共通)のはずです。

  • CentOS6/CentOS7の場合

$ cat /proc/sys/net/netfilter/nf_conntrack_count
5

$ cat /proc/sys/net/netfilter/nf_conntrack_max
65536

CentOS3の時代辺りでは、/proc下でテーブルのカウンタ値を取得出来なかったせいか、テーブルのエントリを直接参照するような集計方法を見掛けますが、このような方法は避けるべきでしょう。
理由は、root権限でなければ実行出来ないことからも想像できるかと思いますが、テーブルへのアクセスが競合するためです。

  • CentOS5の場合(実行は要注意)

# cat /proc/net/ip_conntrack | wc -l
1
  • CentOS6/CentOS7の場合(実行は要注意)

# cat /proc/net/nf_conntrack | wc -l
5

テーブルの不足が確認出来た場合、メモリに余裕があれば単純に拡張してしまうのが最善ですが、拡張が困難/iptablesのルールを精査する場合は、上記のエントリを(サービスへの影響を覚悟の上)テキストで取得しておき、設定されているルールを見直す事になるでしょう。

ip_conntrack_max/nf_conntrack_max拡張設定

sysctlコマンドで値を設定してもいいのですが、hashsizeを変更して関連するパラメータにも反映されるようにした方が良いでしょう。
confファイルに記述する場合は再起動が必要です。一時的に拡張する場合はmodprobeコマンドで適用します。

  • CentOS5の場合

$ sysctl net.ipv4.ip_conntrack_max
net.ipv4.ip_conntrack_max = 65536

--- a/modprobe.conf
+++ b/modprobe.conf
@@ -17,0 +18 @@
+options ip_conntrack hashsize=32768

再起動後。

$ sysctl net.ipv4.ip_conntrack_max
net.ipv4.ip_conntrack_max = 262144
  • CentOS6/CentOS7の場合

$ sysctl net.nf_conntrack_max
net.nf_conntrack_max = 65536

--- /dev/null
+++ /etc/modprobe.d/nf_conntrack.conf
@@ -0,0 +1 @@
+options nf_conntrack hashsize=32768

再起動後。

$ sysctl net.nf_conntrack_max
net.nf_conntrack_max = 262144

hashsize の変更適用により、以下のパラメータが変動します。

-net.netfilter.nf_conntrack_max = 65536
-net.netfilter.nf_conntrack_buckets = 16384
+net.netfilter.nf_conntrack_max = 262144
+net.netfilter.nf_conntrack_buckets = 32768

-net.netfilter.nf_conntrack_expect_max = 256
+net.netfilter.nf_conntrack_expect_max = 512

-net.nf_conntrack_max = 65536
+net.nf_conntrack_max = 262144

  • 動的に適用する場合

# modprobe nf_conntrack hashsize=32768

使用メモリ算出

オブジェクトサイズ * エントリ数のメモリを必要とします。
slab のため swap 不可なので、拡張の際には、余裕がある事を計算/確認しておきましょう。
オブジェクトサイズは /proc/slabinfo 内のエントリで確認出来ます。カーネルによって微妙にサイズが変わりますが、概ね200バイトから400バイト程度です。

$ grep conntrack /proc/slabinfo | grep -v expect | tr -s " " | cut -d" " -f4
304