ConoHaの仕様変更からのセキュリティの話
注)これ以降の萌えはありません。
あんずちゃんが良い人はこちら→もう怖くない!ファイアーウォール(iptables)(このはとあんずのVPS勉強室)
事は、2015年3月20日 18:28にGMOインターネット社よりユーザへ送信された、緊急メンテナンスのアナウンスになります。
日ごろはConoHaをご愛顧いただきありがとうございます。
ConoHaのサービスにおきまして、セキュリティ対策の一環として、
下記のとおり通信制御の設定を追加いたします。変更日 :2015年03月20日(金) 19時00分頃
作業内容 :以下の作業を実施します。1.内部から外部、外部から内部の通信を制限。
22番ポート/UDP
80番ポート/UDP
1900番ポート/UDP2.内部からのブロードキャスト通信を制限。
解釈として、
- インターネットからインスタンスへのinboundの強制的な制限。
- インスタンスからインターネットへのoutgointの強制的な制限。
上記のように解釈する事ができます。
しかし、2.に関しては情報が不足しており、インスタンスからインスタンスへのローカルネットワークにおいてもブロードキャストパケットが制限されたとも受け取る事が出来ます。(一般的にL2 over L3では、実装上の仕様により、ブロードキャストパケット及びマルチキャストパケットが制限されます。)
今回は1.についてピックアップし、 LinuxBoxの必要最小限のセキュリティについて考えてみたいと思います。
今回の緊急メンテナンスの目的と背景
今回、1.のメンテナンスでは、以下の3つのポートを上位ルータでブロックしています。
- 22/udp
- 80/udp
- 1900/udp
このうち、22/udp及び80/udpについては、一般的には使用されていませんが、公式のウェルノンポートとして定義されており、Apache等のhttpd及びsshdがlistenしてもおかしくありません。(尚、手持ちの環境ではApache, sshd共にudpはLISTENしていませんでした。)
udpの場合、tcpのようにいちいちハンドシェークをする必要が無い為、攻撃者にとってはポートスキャンの次に有利な方法です。
1900/udpについては、別途解説します。
例えば、以下のようにLISTENしているポートを調べる事ができます。
また、併せて、これらのポートへの通信をOSレイヤーでコントロールする機能が、iptables(Linux)であり、ipfw(FreeBSD)であり、WindowsFireWall(Windows)です。
# netstat -anp Active Internet connections (servers and established) Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name tcp 0 0 0.0.0.0:22 0.0.0.0:* LISTEN 779/sshd tcp 0 0 0.0.0.0:3306 0.0.0.0:* LISTEN 2691/mysqld tcp 0 0 172.31.xxx.xxx:22 xxx.xxx.xxx.xxx:49286 ESTABLISHED 2289/sshd tcp 0 0 172.31.xxx.xxx:22 xxx.xxx.xxx.xxx:45029 ESTABLISHED 2341/sshd tcp 0 0 :::80 :::* LISTEN 2763/httpd ※一部省略、WebServerとして稼働中のCentOS機より取得。
UPnP対応機器を踏み台にされる事の停止(1900/udp)
1900/udpは、ウェルノンポートの1つで、「Microsoft SSDP Enables discovery of UPnP devices」とMicrosoftが定義・実装しています。
TCPやUDPにおけるポート番号の一覧(WikiPedia)
UPnPとは、簡単に言うと対応ルータへパケットを送信する事により、ポートフォワーディングを設定する事が可能な機能です。
UPnPに対応したネットワーク機器を踏み台としたSSDPリフレクター攻撃に対する注意喚起について(CyberPolice)
ここで言うUPnP対応ルータとは、ConoHaの上位ルータではなく、インスタンスに実装されているUPnPプロトコルの実装がターゲットとなります。これは、一般的には設定が施されたWindowsFirewallがターゲットとなります。
ConoHaの上位ルータは、インスタンスから観えるARPテーブルより、CiscoSystemsの機器がインストールされている事と推測します。
(http://www.coffer.com/mac_find/?string=00%3A00%3A0c)
Cisco IOSの場合、UPnPは実装されていません。
これらの背景を基に、Linuxのセキュリティ対策を施す。
先に幾つかOSレイヤーでのファイヤウォールを挙げましたが、今回はLinux上での実装であるiptablesを用いて、容易にファイヤーウォールを構築してみたいと思います。
セキュリティ対策のキホンのキホン
さて、たまにインスタンスやサーバを乗っ取られてしまい、Abuse(迷惑行為)レポートがホスティング業者から送付される場合があります。
この場合、既に後の祭りであり、おおよそ以下の事が進行した後です。
- SSHのパスワード認証が破られる。
- Perl・Python等標準インストールされやすいプログラミング言語を用いて、Botが設置される。
- Botがインターネット上に対し、22/tcp等へディクショナリーアタックを行う。
また、Apache等が動いていてrootに昇格できてしまった場合、サイトの改ざん・ログの改ざん等も攻撃者は可能です。
たとえば、パケットc…(ごふごふ)、桜h…(ごふごふ)、SAKURAインターネット社の場合、ユーザがOS再インストールの上、再度セキュリティ対策を施す事をAbuse対策の上でマストとしています。
また、クラウド忍j…(げふんげふん)、AWSも対策内容をリポートする事をマストとしています。
では、必要最小限の対策とはなにか。
- 必要ではないデーモンは動作させない。
- 必要ではないポートを公開しない。
- パスワード認証を廃止し、公開鍵認証を用いる。(例:パスワードログイン・BASIC認証→SSH公開鍵/秘密鍵・クライアントSSL証明書)
- OS・デーモン・アプリケーションをアップデートし、必要なセキュリティ対策を採る。
難しいように想えますが、基本は1つです。『とにかく攻撃者に攻撃を面倒にさせる』という事です。
先にも書きましたが、一般的なインターネット上でのUnixHostの乗っ取りには、「デフォルトのパスワード認証のままだった」「つい社内公開と思ってファイヤーウォールを設定していなかった」といった場合が多いのです。
また特に、3.(SSH公開鍵認証)については原理がわかりにくく、「めんどくさい」「よくわからない」という声が途絶えないのが現状ですが、ConoHaの他、AWSでも鍵認証を標準で採用しており、必要最小限の設定の一部がホスティングベンダーにより施されていることになります。
僕の場合、新規に環境を作る時には、下記をセットにして行います。
- OSのインストールはminimal(最小限)のみ。
- sudo権限を、普段使いする一般ユーザ(=自分)のみに。(※絶対にrootで運用しない!)
- sshd_configのテンプレート化、公開鍵の設置
- iptablesのテンプレート設置・カスタマイズ
本当は相互監視やログ管理も盛り込みたいのですが、そろそろ初期セットアップにAnsibleを使わないとキツいですw
iptablesの初期設定をしてみる。
CentOSの標準インストール状態を基準に、以下のコマンドをコピペで実行する事で、eth0(Internet)からのsshのみを受け付けるようになります。
# cat <<_EOF_ > /etc/sysconfig/iptables *filter :INPUT DROP [12:1740] :FORWARD DROP [0:0] :OUTPUT ACCEPT [113:15743] -A INPUT -i lo -j ACCEPT -A INPUT -i eth0 -m state --state RELATED,ESTABLISHED -j ACCEPT -A INPUT -i eth0 -p tcp -m state --state NEW -m tcp --dport 22 -j ACCEPT COMMIT _EOF_ # /etc/init.d/iptables restart # chkconfig iptables on
【解説】
:INPUT DROP [12:1740] // デフォルト動作:外部から入ってくるパケットを全て捨てる :FORWARD DROP [0:0] // デフォルト動作:ルータ動作として転送するパケットを全て捨てる :OUTPUT ACCEPT [113:15743] // デフォルト動作:外部へ出て行くパケットを全て許可する -A INPUT -i lo -j ACCEPT // ループバックインターフェースの通信を全て許可 -A INPUT -i eth0 -m state --state RELATED,ESTABLISHED -j ACCEPT // ハンドシェークが終わったtcpセッションを維持 -A INPUT -i eth0 -p tcp -m state --state NEW -m tcp --dport 22 -j ACCEPT // SSHの新規セッションを許可
また、特定IPアドレスからのみアクセスを許可する場合は、たとえば22/tcpの部分を以下のように書き換えます。
-A INPUT -i eth0 -p tcp -m state --state NEW -m tcp --dport 22 -s 8.8.8.8/32 -j ACCEPT
「-s
」とは、ソースIPアドレス、つまりアクセス元のIPアドレスを示します。
「8.8.8.8
」はIPアドレス。/32
の場合はIPアドレスそのものを、/30
より短い場合はネットワークアドレスを示します。
「/32
」とは、サブネット、つまりIPアドレスの範囲を示します。ここでは割愛しますが、1個の場合は「/32
」と記述します。
icmpプロトコル(Ping)を通す・通さないは正直難しいところですが、自分はトラブルシュートの時の足掛かりにするため、意図的に開けています。(今回は記述していません。)
その他、iptablesの設定をしていく事で、アタックを学習して動的にフィルタしたり、任意の設定のルータを構築する事も出来るようになります。
おわりに
お姉さま、昨今容易にLinuxホストを建てる輩が…(げふげふ)、
もとい、クラウドやVPSなどで容易にLinuxホストを手に入れられる時代になりましたが、残念ながらインターネットは自由の世界、言い換えれば無法地帯です。
Linuxホストをインターネットに晒せばすぐに攻撃されてしまいます。
今回のように、上位のファイヤーウォールで事前に対策してくれるのは、とても有り難い事です。
実は数年前、データセンタに新規のラックを借りて新規のグローバルIPをアサインして貰った事があるのですが(もちろん仕事ですよ!)、ファイヤーウォールが稼働した30分後にログを観ると、既に外部からの攻撃が始まっていました。(もちろん、最初から塞いでいましたが…)
TrendMicro DeepSecurity等の商用製品を使ってアプリケーションレイヤーで防御する事も可能ですが、それ以前に基本的なスキルとして、このエントリ程度のスキルは身につけて欲しいものです、はい。
p.s.
社内でロシエルさんファンと出会えました!ちょっと嬉しいです。
元記事はこちらです。
「ConoHaの仕様変更からのセキュリティの話」