・外部からの接続パケットは基本的にすべて破棄
・内部からの接続パケットは基本的にすべて破棄
・ループバックアドレスに関してはすべて許可
・メンテナンスホストからのping、メンテナンスホストへのpingを許可
・メンテナンスホストからのssh(TCP 22)を許可
・サーバからメンテナンスホストへのsshは許可しない
サーバに接続する端末をメンテナンスホストとして固定して、そこからのssh接続のみを許可するようにします。ssh以外に、運用上サーバの死活を監視する目的でpingコマンドを使用する可能性があるため、ICMPを許可します。
テンプレート1の内容を説明します。適宜、以下のリンクでリストを表示させるかテンプレートをダウンロードしてください。
3、4行目でメンテナンスホスト(trusthost)とサーバ(myhost)のIPアドレスを指定します。これらの値は何度も使用するため、シェルスクリプトの利点を生かして変数として埋め込みます。この2行は皆さんの環境に合わせて、適宜書き換えてください。
5行目で不特定クライアントを指定します。これ以外にも不特定クライアントを表す方法はありますが、本連載ではこの表記を用います。
10、11行目は、既存のiptablesの設定をリセットしています。
15行目からようやく設定らしくなります。まず、すべての送受信パケットを破棄(DROP)します。iptablesの基本は、いったんネットワークをふさいだ後、用途に応じて穴を開けるようにルールを追加していきます。ここでは、次の3つに大別されるパケットを破棄します。
「チェイン」という言葉に戸惑うかもしれません。これは、「フィルタルールを集めてモジュール化したもの」と理解しておけばいいでしょう。チェインを用いることで、頻繁に使用される細かいルールをいちいち定義する必要がなくなります。
15行目の「-P INPUT」は、INPUTチェインで定義されたパケットの破棄(DROP)を指定しています。同様に、16行目の「-P OUTPUT」でOUTPUTチェイン、17行目の「-P FORWARD」でFORWARDチェインの破棄を設定します。
21、22行目で、ループバックインターフェイスを経由するすべての送受信パケットの通過を許可します。「-i」で受信側インターフェイス、「-o」で送信側インターフェイスを指定します。これでサーバからサーバ自身へのローカル接続をすべて許可することができます。
26、27行目は、メンテナンスホストからサーバへのpingを許可するルールの追加です。pingは、「request」(26行目)とそれに答える「reply」(27行目)が対で必要なことを忘れないようにしてください。
31、32行目は、サーバからメンテナンスホストへのpingを許可するルールです。送信と受信が入れ替わるため、26、27行目におけるソースホスト(「-s ホストまたはネットワーク」)とディスティネーションホストの指定(「-d ホストまたはネットワーク」)、INPUT/OUTPUTチェインが入れ替わっています。
36、37行目が肝心のsshの設定です。今回は、単にソースIPアドレスだけで制限を掛けています。
36 iptables -A INPUT -p tcp -s $trusthost -d $myhost --dport 22 -j ACCEPT 37 iptables -A OUTPUT -p tcp -s $myhost --sport 22 -d $trusthost -j ACCEPT
-p tcp プロトコルがTCP
-s $trusthost ソースIPアドレスが$trusthost
-d $myhost ディスティネーションIPアドレスが$myhost
--dport 22 ディスティネーションポートが22
--sport 22 ソースポートが22
-j ACCEPT ACCEPTする
41行目以降で監視の設定を行います。37行目までで特に指定しなかったパケットに関しては、指定したルールでログファイルにその旨を記録するようにします。まず41行目で新たなチェイン「LOGGING」を独自に定義します。
42行目では、「--log-level」でログレベルをwarningに設定し、「--log-prefix」でログの頭に「DROP:」を付けるようにしています。このままではすべての無効パケットを記録してしまい、サーバに新たな負荷を掛ける可能性があります。そこで、「-m limit」で閾値を設け、閾値の範囲内で検出された不正パケットのログを出力します。limitのデフォルトは、同一パターンの不正パケットに対し、1時間に最大3回のログ出力、連続した場合には5回の出力を行います。
43行目で無効パケットの破棄(DROP)を指定し、ログ出力の後に破棄されるようにします。
44、45行目で、INPUTおよびOUTPUTチェインに対し、このLOGGINGが行われるように設定します。
シェルスクリプトの準備ができたら、既存フィルタのリセットを含めてフィルタの適用を行います。
# sh template1.sh
設定内容をチェインごとに表示することもできます。シェルスクリプトで設定したとおりになっているかどうかを確認します。
# iptables -nL Chain INPUT (policy DROP) target prot opt source destination ACCEPT all -- 0.0.0.0/0 0.0.0.0/0 ACCEPT icmp -- 192.168.10.100 192.168.20.200 icmp type 8 ACCEPT icmp -- 192.168.10.100 192.168.20.200 icmp type 0 ACCEPT tcp -- 192.168.10.100 192.168.20.200 tcp dpt:22 LOGGING all -- 0.0.0.0/0 0.0.0.0/0 Chain FORWARD (policy DROP) target prot opt source destination Chain OUTPUT (policy DROP) target prot opt source destination ACCEPT all -- 0.0.0.0/0 0.0.0.0/0 ACCEPT icmp -- 192.168.20.200 192.168.10.100 icmp type 0 ACCEPT icmp -- 192.168.20.200 192.168.10.100 icmp type 8 ACCEPT tcp -- 192.168.20.200 192.168.10.100 tcp spt:22 LOGGING all -- 0.0.0.0/0 0.0.0.0/0 Chain LOGGING (2 references) target prot opt source destination LOG all -- 0.0.0.0/0 0.0.0.0/0 limit: avg 3/hour burst 5 LOG flags 0 level 4 prefix `DROP:' DROP all -- 0.0.0.0/0 0.0.0.0/0
ログは/var/log/messagesに出力されます。dmesgコマンドで確認することもできます。
# tail /var/log/messages | grep DROP Mar 4 20:34:12 localhost kernel: DROP:IN= OUT=eth0 SRC=192.168.XX.XX DST=XX.XX.XX.XX LEN=84 TOS=0x00 PREC=0x00 TTL=64 ID=0 DF PROTO=ICMP TYPE=8 CODE=0 ID=11786 SEQ=1 Mar 7 02:13:54 localhost kernel: DROP:IN=eth0 OUT= MAC=:XX:XX:XX:XX: XX:XX:XX:XX:XX:XX:XX:XX:XX:XX SRC=192.168.XX.XX DST=192.168.XX.XX LEN=52 TOS=0x00 PREC=0x00 TTL=64 ID=13425 DF PROTO=TCP SPT=2825 DPT=22 WINDOW=65535 RES=0x00 SYN URGP=0 (以下略)
テンプレート1では、メンテナンスホストを1台のクライアントに限定しています。これを、192.168.10.0〜192.168.10.255のようにネットワーク単位で指定することも可能です。その場合は、3行目を次のように変更します。
3 trusthost='192.168.10.0/24'
このほか、ホストの指定にホスト名を使うこともできますが、ホスト名解決のためにDNSを利用できるようにiptablesの設定を修正する必要があります。また、ホスト名偽装の危険性も生じるため、IPアドレスを使用する方が望ましいでしょう。
Copyright © ITmedia, Inc. All Rights Reserved.