iptablesクイックスタート

一つの浮動IPをくれる普通のISPに繋ぐPCルータととしてDebian GNU/Linuxを使用する場合の、もっとも簡単な設定を紹介する。

2003/07/01:実際にこれ見て設定する人が現われてバグ報告くれましたー! つことであちこち修正してみたのでヨロ。

2003/07/30:さらにわかりにくいだのなんだの言われたので修正……

2003/07/31:なんかEUC以外のコードでスクリプトを保存する人がいたので一言付け加え……


カーネルの設定

めんどくさいだろ? Networking options のIP: Netfilter Configuration の中のオプションを全部有効にしちゃいな。EXPERIMENTALになってるものくらいは外しといたほうがいいかもしれないけどな。あ、あとFTP protocol supportとIRC Protocol supportはモジュールにしといたほうがいいぜ。FTPはどうも組み込みにすると妙に接続が遅くなるからたぶん効いてないんだろうし、IRCは引数にポート番号を入れてやる必要があるからな。さあ、コンフィギュレーションが終ったら、

$ make-kpkg clean; fakeroot make-kpkg --revision=router.0.1 kernel_image

でイッパツさ。

モジュールにしたFTPとIRCのために、ちょいと設定をしてやる。でも、めんどくさいだろ? 下に書いた通りに打ち込みな。打ち間違えんなよ? まんまターミナルにコピペしたっていいぜ。

# MODULE='ip_nat_irc,ip_conntrack_irc,ip_nat_ftp,ip_conntrack_ftp'; \
PORTS='6660,6661,6662,6663,6664,6665,6666,6667'; \
echo $MODULE | awk '{ gsub(/,/, "\n"); print }' >> /etc/modules; \
echo "options ip_nat_irc ports=$PORTS" > /etc/modutils/99iptables; \
echo "options ip_conntrack_irc ports=$PORTS" >> /etc/modutils/99iptables; \
update-modules

PPPの設定

# pppconfig --dialog

あとは適当に項目を埋めて設定完了さ。初期化コマンドはTAのWindows用*.iniファイルを読めば書いてある。

ponで接続、poffで切断だ。起動時に自動で切断するには、

# touch /etc/ppp/ppp_on_boot

としておけばいい。

なに? うちはADSLだからそれじゃうまく行かないだって? 知らねえよ、うちはADSLなんて開通してねえからな。他のサイト探してみてくれ!

パケットフィルタリングの設定

まずはルータとして作動させるために、

# echo 1 > /proc/sys/net/ipv4/ip_forward

とする。再起動した後も有効になるように、/etc/network/optionsにその他の設定と一緒にこう書く。

ip_forward=yes
spoofprotect=yes
syncookies=yes

そしたらいよいよフィルタの設定だ。こいつはシェルスクリプトを書いちまったほうがいい。実験したり消したりがカンタンになるからな。

下に書く内容を適当に、そうだな、fw.shとでもしてファイルに保存するんだ。え? どこに置くのかわからない? おいおい勘弁してくれよ。まあ、どこでも構わないんだが、どうしても自分で決められないなら、/usr/local/binにでも置くんだな。

#!/bin/sh

# 各種変数の設定
IPTABLES=`which iptables`
MODPROBE=`which modprobe`
LOCAL_NET='192.168.0.0/16'
CLIENT_A='192.168.0.2'

# フィルタの初期化
$IPTABLES -t filter -F FORWARD
$IPTABLES -t nat -F POSTROUTING
$IPTABLES -t nat -F PREROUTING
$IPTABLES -F INPUT
$IPTABLES -F FORWARD
$IPTABLES -F OUTPUT
# ユーザー定義フィルタの初期化と削除
$IPTABLES -F ppp-in
$IPTABLES -X ppp-in

# フィルタを削除したい時は下の行のコメントを外して実行する
#exit

# 基本ポリシーの設定
$IPTABLES -P INPUT ACCEPT
$IPTABLES -P OUTPUT ACCEPT
$IPTABLES -P FORWARD ACCEPT

############################### フィルタの定義 ################################
#フィルタ作成
$IPTABLES -N ppp-in

# 外側からsshで入りたい場合は下の行のコメントを外す
#$IPTABLES -A ppp-in -p tcp --dport ssh -j ACCEPT

# ルータ上で動いてるhttpサーバを外側に向けて公開したい場合は
# 下の行のコメントを外す
#$IPTABLES -A ppp-in -p tcp --dport 80 -j ACCEPT

# ポートフォワード(NAT)の設定例
#
# CLIENT_Aで立ち上がってるウェブサーバを外に公開する場合
#$IPTABLES -A ppp-in -p tcp --dport 80 -j ACCEPT
#$IPTABLES -t nat -A PREROUTING -p tcp -i ppp0 --dport 80 -j DNAT \
#       --to-destination $CLIENT_A
#
# CLIENT_AでAoE等のDirectPlayを用いたゲームをする場合
#$IPTABLES -A ppp-in -p tcp --dport 2300:2400 -j ACCEPT
#$IPTABLES -A ppp-in -p udp --dport 2300:2400 -j ACCEPT
#$IPTABLES -t nat -A PREROUTING -p tcp -i ppp0 --dport 2300:2400 -j DNAT \
#       --to-destination $CLIENT_A
#$IPTABLES -t nat -A PREROUTING -p udp -i ppp0 --dport 2300:2400 -j DNAT \
#       --to-destination $CLIENT_A
#$IPTABLES -A ppp-in -p tcp --dport 47624 -j ACCEPT
#$IPTABLES -A ppp-in -p udp --dport 47624 -j ACCEPT
#$IPTABLES -t nat -A PREROUTING -p tcp -i ppp0 --dport 47624 -j DNAT \
#       --to-destination $CLIENT_A
#$IPTABLES -t nat -A PREROUTING -p udp -i ppp0 --dport 47624 -j DNAT \
#       --to-destination $CLIENT_A

# 確立してるセッションのパケットと、その関連パケットは通す
$IPTABLES -A ppp-in -m state --state ESTABLISHED,RELATED -j ACCEPT \
       --modprobe=$MODPROBE

# その他のパケットは叩き落す
$IPTABLES -A ppp-in -j DROP

##############################################################################

# ローカル側からデフォルトフリーの設定
$IPTABLES -A INPUT -s $LOCAL_NET -j ACCEPT
$IPTABLES -A FORWARD -s $LOCAL_NET -j ACCEPT

# IPマスカレーディング
$IPTABLES -t nat -A POSTROUTING -s $LOCAL_NET -d ! $LOCAL_NET -j MASQUERADE

# 作成したフィルタを当てる
$IPTABLES -A INPUT -i ppp0 -j ppp-in
$IPTABLES -A FORWARD -i ppp0 -j ppp-in

念のために言っておくが、日本語のコメントが含まれてるのでEUC-JPで保存するんだぜ。改行コードもLFだ。UNIX標準に合わせねーとトラブルの元だ。それも踏まえて、ちゃんと保存したかい? そしたら、

# sh /usr/local/bin/fw.sh

これで設定が完了ってわけさ。

あとはこの設定を保存して、再起動時にも自動で当たるようにしてやらなくちゃいけねえ。

# /etc/init.d/iptables save active

これでいいはずだ。ちゃんとフィルタが自動で当たらない時は、dpkg-reconfigure iptables とか apt-get install --reinstall iptables とか試してみてくれ。

FTPとIRC

FTPは最初にアクセスする接続とファイルを転送する接続が別個に確立するようになってる。だからルータ経由するときはPASVモードなんかを使う必要があった。しかし、最初に突っ込んで置いたFTP用モジュールを使えばそんな心配はいらない。FTPの接続が確立されていれば、データの接続はその関連(RELATED)パケットとしてアクセスを許可し、自動的にNATしてくれる。関連パケットかどうかを見極める仕事をするのがあのモジュールってわけだ。

IRCのモジュールは、同じようにIRCの接続を見てDCCパケットを関連パケットとして認識してくれる。なので他のルータのようにDCC送信のためにポートを開けてポート転送する必要は無い。ただし、FTPと違ってIRCサーバのポートは6660-6669がよく使われる。だからモジュールにこのIRCサーバへのポートを指定してやって、関連パケット認識の手伝いをしてやらなきゃならねえ。上の例だとIRCサーバの6660,6661,6662,6663,6664,6665,6666,6667のいずれかのポートに接続してればDCC SENDが通る。他のポートを使いたかったら、適当に書き換えてくれ。ただし、クライアントによってはこの方法じゃうまくいかないこともある。俺が確認した範囲じゃ、lieceはOKだがirchatはダメだ。irchatはポートの指定が(たぶん)できないので、ポート転送という手段も使えない。ルータにplumでも立てて、DCC中継の設定をしてやるのが一番簡単のようだ。

ま、こんなとこだ。あとはがんばってくんな!


Sugano "狐志庵" Yoshihisa(E) <koshian@misao.gr.jp>
Back to HOME