不正アクセスからサーバを守るfail2ban。さくらのクラウド、VPSで使ってみよう!

こんにちは。さくらインターネットの前佛です。
今回は、サーバのログファイルを自動スキャンして、悪意のある SSH 通信を自動遮断するツール fail2ban の概要と使い方をご紹介します。

日々、不正アクセス

インターネット上のサーバは、SSH や HTTP など、公開しているポートに対する不正アクセスの試みに日々晒されています。不正アクセスは悪意を持った人からの攻撃だけではありません。マルウェアやワームなど、いわゆるボットからの攻撃にも日々晒されているのです。

そのため、誰でもアクセス可能なパブリックな環境にサーバを公開する場合、セキュリティに対して細心の注意を払う必要があります。

たとえば、近年話題になっている Linux 向けのマルウェアとしては XOR.DDoS が有名です。これは root ユーザのパスワードに対する総当たり攻撃(broute-force attach)を試みます。攻撃対象は公開されている SSH ポートに対してであり、もしも不正なログインが成功すると、自動的にマルウェアの構築あるいはダウンロードが試みられます。そして、不正ログインできたサーバを新たな攻撃元として、別のサーバに対する攻撃を繰り返していくものです。

このような攻撃に対しての備えは、理想としてはファイアウォールやルータ等を導入し、フィルタリング・ルールを厳格に運用すべきでしょう。しかしながら、環境によってはそのような対策を行えないこともあります。

具体的には SSH やメールの送受信など、複数のユーザが複数の環境から接続する必要性がある場合です。このような場合、SSH であればパスワードによる認証を防止する(公開鍵方式の認証しか受け付けない)や、root によるログインを禁止して対策をとる方法があります。

しかし、インターネットに公開しているサーバは SSH だけではありません。ウェブサイトを公開している場合であれば、ブログの管理画面のインターフェイスに対する不正なアクセス、あるいはデータベースの公開ポートに対する攻撃の兆候も日々見受けられるでしょう。

適切にセキュリティの設定を施していたとしても、サーバの再起動によって設定がリセットされたり、あるいは別の環境にシステムを移行したとき、思わず設定漏れにより攻撃に晒されてしまうリスクもあります。

このような脅威に対して、私たちサーバ管理者ができる対策の1つが、fail2ban の導入です。

不正攻撃のログ痕跡からアクセスを自動遮断する fail2ban

fial2ban はログファイルをスキャンし、悪意のある攻撃や兆候を元に、攻撃元の IP アドレスを自動で遮断(ban)するソフトウェアです。オープンソース・プロジェクトとして開発されており、GNU GPL v2 ライセンスの下、誰でも自由に使うことができます。

fail2ban の仕組み

fail2ban はクライアント・サーバ型のシステムであり Python 言語で書かれています。fail2ban-server(サーバ)はサーバ内に常駐し、対象のログファイル群を監視します。このサーバに対して設定や操作をするのが、fail2ban-client(クライアント)コマンドです。

fail2ban-1

fail2ban-serverはデーモンであり、ログファイル中の悪意のある攻撃や兆候を監視します。具体的な悪意のある兆候とは、特定のホストからの次のような行動です。

- パスワード認証の失敗が短時間に大量に続く
- exploits の実行と思われる兆候

これらの監視対象は /var/log/secure や /var/log/audit.log などのシステムログだけではありません。設定によって Apache のログファイル access_log なども参照します。fail2ban がログの何を監視するかの設定は、フィルタ(filter)と呼ぶ正規表現の文字列で予め指定しておきます。

そして、特定の攻撃の兆候を fail2ban が発見すると、アクション(action)と呼ばれる自動処理を実行します。この時、ファイアウォール・ルール(iptables等)を変更してアクセスの自動遮断や各種の設定変更、メール通知などを自動的に行うことができます。

fail2ban の設定とは、これらフィルタとアクション(1つまたは複数)を組みあわせたジェイル(jail)と呼ばれた指定を行うことです。この設定ファイル群は /etc/fail2ban/ 以下のディレクトリにあります。

覚えておいた方が望ましい注意点としては、ログの監視とアクションの実行までにはタイムラグがあることです。リアルタイムに状況を把握して反映するのではなく、数秒から数十秒かかる場合もあります(ログファイルによって差があります)。

以降では具体的な設定例を見ていきましょう。

SSH のフィルタ設定

さくらのクラウド、さくらのVPS(※)では fail2ban が標準で組み込まれています。特に何もしなくても、サーバを立ち上げた直後から SSH に対する攻撃の検出と、自動遮断機能が有効です。XOR.DDoS のような攻撃があれば、一定期間(デフォルトでは10分)は iptables によって接続できなくなります。
(※さくらのVPSでは、CentOS6/7を標準インストール機能でインストールした場合にfail2banが適用されます。CentOS6/7の標準インストール機能についてはこちらをご覧ください。)

この設定が有効化されているのは、 /etc/fail2ban/jail.conf 中の以下のファイルです。

bantime = 600
findtime = 600
maxretry = 5

- bantime … 対象ホストを自動遮断(ban)する時間です。デフォルトは 600 秒(10分)です。
- findtime と maxretry … ログファイルを findtime で指定した時間、攻撃とみられる兆候が maxretry 回続けば自動遮断します。デフォルトでは 600 秒で5回の兆候があれば、自動遮断します。

このデフォルト値を変更したい場合は、設定ファイルの変更後、fail2ban の設定再読み込みを行います。

systemctl の例(CentOS7, Ubuntu 16.04 等):

# systemctl reload fail2ban

initの例:

# service fail2ban restart

また、ジェイルの設定は /etc/fail2ban/jail.d/ 以下ディレクトリにあるファイルで有効になっています。さくらのクラウド、さくらのVPSでは local.conf の中で以下の設定があるためです。他にもジェイルのルールを追加したい場合は、このファイルの中に設定を追加するか、あるいは別の設定ファイルを作成します。

[DEFAULT]
 banaction = firewallcmd-ipset
 backend = systemd

[sshd]
 enabled = true

fail2ban のフィルタやアクションが有効かどうかは、ログファイル /var/log/fail2ban.log をご覧ください。これは SSH に対する攻撃(実際には、ログイン失敗の記録を /var/log/secure から検出)が5回以上続いたログを検出したため、接続元(xxx.xxx.xxx.xxx は IP アドレスです)に対する自動遮断(ban)が有効化されています。

2016-09-19 05:01:22,382 fail2ban.filter [1134]: INFO [sshd] Found xxx.xxx.xxx.xxx
2016-09-19 05:01:22,443 fail2ban.filter [1134]: INFO [sshd] Found xxx.xxx.xxx.xxx
2016-09-19 05:01:22,504 fail2ban.filter [1134]: INFO [sshd] Found xxx.xxx.xxx.xxx
2016-09-19 05:02:51,918 fail2ban.filter [1134]: INFO [sshd] Found xxx.xxx.xxx.xxx
2016-09-19 05:02:51,979 fail2ban.filter [1134]: INFO [sshd] Found xxx.xxx.xxx.xxx
2016-09-19 05:02:52,043 fail2ban.filter [1134]: INFO [sshd] Found xxx.xxx.xxx.xxx
2016-09-19 05:02:52,256 fail2ban.actions [1134]: NOTICE [sshd] Ban xxx.xxx.xxx.xxx

自動遮断(ban)されたあと一定期間後に自動回復します。長期的に遮断したい場合などは、必要に応じて、bantime や findtime 値を変更下さい。

補足:SSH サーバをより安全にするために

fail2ban の役割は、あくまでも外部からの攻撃に対して自動的に遮断するものです。それ以前に、サーバを不正な攻撃から守るために必要な設定方法をご紹介します。

TCP Wrapper を使うアクセス制御

Linux の sshd は、標準で TCP wrapper を使ったアクセス制御を使えます。iptables のように IP アドレスやネットワークを指定した遮断と許可だけでなく、ホスト名やドメイン名で制御できるのが特徴です。

設定に使うファイルは /etc/hosts.allow と /etc/hosts.deny の2つです。基本的には hosts.deny に拒否するサービスとネットワークを記述し、接続を許可したい環境を hosts.allow に書く流れです。

例えば ***.example.jp というホスト名に対してのみ SSH 接続を許可する設定を考えてみましょう。 hosts.allow ファイルには、次のような記述を追加します。特定のホストまたはネットワークに対する SSH を許可するには、「 sshd: <接続元>」の記述を追加します。

sshd: .example.jp
sshd: <ipアドレス>

これだけでは制限は有効にはなりません。 hosts.deny には、次のように sshd に対する接続を拒否する設定を追加します。

sshd: all

POP3 サーバやその他 TCP Wrapper を使うアプリケーションが無い場合は、次のように全てのサービスを拒否する方法も1つです。

all: all

この記述を追加し、ファイルを保存した瞬間から設定が有効になります。特に sshd の再起動等は必要ありません。

SSH サーバの設定変更

よりセキュリティを高めるには、特に必要が無い限り、SSH サーバ側で root での SSH ログイン禁止と、公開鍵認証以外のログインを禁止することをお勧めします。これらの設定を有効にするには SSH サーバの設定ファイル /etc/ssh/sshd_config を編集します。

PermitRootLogin no
UseLogin no

設定を有効にするには SSH サーバの再起動が必要です。

systemctl の例(CentOS7, Ubuntu 16.04 等):

# systemctl restart sshd

initの例:

# service sshd restart

SSH サーバの再起動後、設定変更に誤りがあればログインできなくなります。そのため、ログインしたままリモートからのログインが可能かどうか設定されることをオススメします。

まとめ

fail2ban を使えば、外部のネットワークからの不正攻撃に対して、自動的に遮断することができます。さくらインターネットでは、さくらのクラウド、さくらのVPSで fail2ban を標準で導入しているだけでなく、abuse チームにおける不正攻撃の検出や対処にも活用しています。(こちらはまた別の記事でご紹介する予定です)

皆さんにも、ぜひ本記事をご参考にしていただき、サーバ環境におけるセキュリティ向上のお役に立てられればと思います。