付けっぱなしだったテスト用サーバー
ある開発者が、新しいページを試すためにポートを開け、そのまま休暇に出ました。ポートは3か月開いたままで、その裏のプログラムは一度も更新されませんでした。
誰も必要としないポートは、誰も見張っていない扉です。閉じるのに、費用はかかりません。
このレッスンのゴール
メモ
サーバーが待ち受けているものを見つけ、要らないものを閉じ、更新を確かめられる。
重要な言葉
| ことば | いみ | れい |
|---|---|---|
| ポート | マシンの番号付きの扉。1つのプログラムがそこで待つ | 22 |
| 待ち受け | ポートで、誰かが接続してくるのを待つこと | |
| ループバック | アドレス 127.0.0.1。同じマシンからしか届かない | |
| 原則拒否 | どのルールも許していないものは、すべて断ること | |
| パッチ | 既知の欠陥を直す更新 | |
| 攻撃対象領域 | 攻撃者が届いて試せる範囲のすべて |
学生が入力するセルは、このプレビューでは空白です。
待ち受けているものは攻撃できる
待ち受けているプログラムは、どれも入口になりえます。少ないほど、攻撃者が試せることも減ります。
最初の仕事は、見ることです。空のフォルダから、自分用の小さな Web サーバーを2つ起動します。1つはネットワークに開き、もう1つはこのマシンだけに開きます。
今、待ち受けているものを並べる
ss -ltnここでは表示のみで、実行されません。無料アカウントを作成すると、実行ボタンで自分のラボのターミナルに入力できます。
配信する空のフォルダを作る
mkdir -p empty-siteここでは表示のみで、実行されません。無料アカウントを作成すると、実行ボタンで自分のラボのターミナルに入力できます。
ネットワークに開いたサーバーを8088で起動
(timeout 120 python3 -m http.server 8088 --bind 0.0.0.0 --directory empty-site >/dev/null 2>&1 &)ここでは表示のみで、実行されません。無料アカウントを作成すると、実行ボタンで自分のラボのターミナルに入力できます。
このマシンだけのサーバーを8089で起動
(timeout 120 python3 -m http.server 8089 --bind 127.0.0.1 --directory empty-site >/dev/null 2>&1 &)ここでは表示のみで、実行されません。無料アカウントを作成すると、実行ボタンで自分のラボのターミナルに入力できます。
2つを比べる
ss -ltn | grep -E ':808[89]'ここでは表示のみで、実行されません。無料アカウントを作成すると、実行ボタンで自分のラボのターミナルに入力できます。
Local Address の列の読み方
最後の Run は2行を書きました。1行には 0.0.0.0:8088、もう1行には 127.0.0.1:8089 があります。
アドレス 0.0.0.0 は、マシンがつながっているすべてのネットワークを意味します。127.0.0.1 は、このマシンだけを意味します。2つ目のサーバーには、外のネットワークから届かないので、ファイアウォールのルールも要りません。
2つのサーバーは、2分たつと自分で止まります。
ルールでポートを断れる
プログラムが広く待ち受けなければならなくても、届かせたくないことがあります。マシン上のファイアウォールのルールで、断れます。
今から、ポート8088だけのルールを、自分用のテーブル practice に足します。端末は影響を受けず、何も保存されません。Run が nft: command not found と言ったら、sudo apt-get install -y nftables で入れます。
1つのルールでポート8088を断る
sudo nft 'add table inet practice; add chain inet practice guard { type filter hook input priority 0 ; policy accept ; }; add rule inet practice guard tcp dport 8088 reject with tcp reset'ここでは表示のみで、実行されません。無料アカウントを作成すると、実行ボタンで自分のラボのターミナルに入力できます。
今度は8088に問い合わせる
curl -sS -m 3 http://127.0.0.1:8088/ 2>&1 | head -n 1ここでは表示のみで、実行されません。無料アカウントを作成すると、実行ボタンで自分のラボのターミナルに入力できます。
ルールの無い8089に問い合わせる
curl -s -o /dev/null -w '%{http_code}\n' http://127.0.0.1:8089/ここでは表示のみで、実行されません。無料アカウントを作成すると、実行ボタンで自分のラボのターミナルに入力できます。
2つの答えが言うこと
1つ目の curl は、curl: (7) Failed to connect to 127.0.0.1 port 8088 と書き、そのあとに時間の注記が続きました。ルールが、すぐに接続を断ったのです。2つ目は 200 を書いたので、8089は今も答えます。
本物のファイアウォールは、逆から始めます。方針は原則拒否で、必要なポートごとに、許すルールを1つずつ置きます。
例: Web サーバーの原則拒否
| ポート | 用途 | ルール |
|---|---|---|
| 22 | 管理者の SSH | 許す。事務所のアドレスからだけ |
| 443 | Web サイト | 許す。どこからでも |
| 8088 | 忘れられたテスト用ページ | ルールなし。だから断られる |
学生が入力するセルは、このプレビューでは空白です。
練習用のテーブルを消す
sudo nft delete table inet practiceここでは表示のみで、実行されません。無料アカウントを作成すると、実行ボタンで自分のラボのターミナルに入力できます。
使い捨てのサーバーを2つとも止める
pkill -f 'http.server 808'ここでは表示のみで、実行されません。無料アカウントを作成すると、実行ボタンで自分のラボのターミナルに入力できます。
パッチは、他の人が見つけた欠陥を塞ぐ
攻撃の多くは、すでに直し方がある欠陥を使います。更新が遅れたサーバーは、攻撃しやすいのです。
何も変えずに、見ることができます。-s は模擬の意味で、やることを書くだけで、何もしません。数は日によって変わるので、ここでは数を書きません。
openssl の新しい版は出ているか
apt-cache policy openssl | head -n 3ここでは表示のみで、実行されません。無料アカウントを作成すると、実行ボタンで自分のラボのターミナルに入力できます。
更新はいくつ入るか
sudo apt-get -s upgrade | grep -c '^Inst'ここでは表示のみで、実行されません。無料アカウントを作成すると、実行ボタンで自分のラボのターミナルに入力できます。
よくある間違い
注意
誰もそこにあると知らないから、ポートは安全だと思う人が多くいます。スキャナーは、数分ですべてのポートを試します。ポートが安全なのは、待ち受けるプログラムがないとき、またはルールが断るときです。知られていないことは、対策ではありません。
発展: 予定を決めて更新する
ls /etc/apt/apt.conf.d を実行し、名前に auto-upgrades が付くファイルを探します。あれば cat で読みます。マシンが自分でセキュリティ更新を入れるかどうかが書いてあります。
2文を書きましょう。サーバーに自分で更新させる理由を1つ、学校が先に更新を試したがる理由を1つです。