IT pass HikiWiki - [Memo2015][ITPASS] fail2ban のインストールと設定 Diff

  • Added parts are displayed like this.
  • Deleted parts are displayed like this.

{{toc}}

[((<ITPASSサーバ構築・運用ドキュメント>)) へ戻る]

= 概要

サーバへの不正アクセスを減らすため,
fail2ban のインストールと設定を行う.

もともと iptables というコマンドでアクセスの遮断を行うことはできる.
iptables でどのようなことができるかを, 一度 man で見てみると良いだろう.

しかし, いちいち不正アクセスを行ってきたアドレスやポートを割り出して
iptables コマンドを使って設定するのは面倒である.
そこでそのような設定を自動的に行えるようにしたのが fail2ban である.

= fail2ban のインストール

  $ sudo -s
  # apt-get update
  # apt-get install fail2ban

iptables -L でインストールされたことを確認した.
以下のように fail2ban の記述が表示された.

  # iptables -L

  Chain INPUT (policy ACCEPT)
  target     prot opt source               destination        
  fail2ban-ssh  tcp  --  anywhere             anywhere            multiport dports ssh    
  
  Chain FORWARD (policy ACCEPT)
  target     prot opt source               destination        
  
  Chain OUTPUT (policy ACCEPT)
  target     prot opt source               destination        
  
  Chain fail2ban-ssh (1 references)
  target     prot opt source               destination        
  RETURN     all  --  anywhere             anywhere            


= 設定ファイルの編集

fail2ban の設定ファイルは, /etc/fail2ban/jail.conf である.
以下の通り設定ファイルを編集した.

== ssh

ssh に関する設定を以下のようにを書き換えた.
enabled が true になっているとサービスが実行される. false は実行されない.

destemail = root@localhost

[ssh]
enabled = true
port    = ssh
filter  = sshd
logpath  = /var/log/auth.log
maxretry = 4

* ignoreip: 不正アクセスとして扱わないアクセス元を指定.
* bantime: 不正アクセスと認めたときに, アクセスを何秒遮断するか指定.
* findtime, maxretry: findtime 秒間のうちに maxretry 回失敗すると不正アクセスとみなされる.
* destemail: 不正アクセスが認められたときのメールの送り先.
* logpath: 監視をするログの場所を指定する.

== apache

apache に関する設定を以下のようにを書き換えた.

[apache]

enabled = true
port    = http,https
filter  = apache-auth
findtime= 60
logpath = /var/log/httpd-*error.log
maxretry = 60
bantime  = 1200

# default action is now multiport, so apache-multiport jail was left
# for compatibility with previous (<0.7.6-2) releases
[apache-multiport]

enabled   = true
port      = http,https
filter    = apache-auth
findtime  = 10
logpath = /var/log/httpd-*error.log
maxretry  = 60
bantime  = 1200

  [apache-nohome]
  enabled  = true
  port     = http,https
  filter   = apache-nohome
  findtime = 60
  logpath  = /var/log/httpd-*error.log
  maxretry = 60
  bantime  = 1200

apache ではエラーログを, apache-multiport ではアクセスログを監視する.
findtime, maxretry については, このぐらいが妥当と思われるが要請などがあれば適宜変えていくこと.


= failregex の追加

== apache

* /etc/fail2ban/filter.d/apache-auth.conf の failregex を以下のように編集した.
  * failregex を設定すると, その設定に対応したログのメッセージをカウントし, findtime 以内に maxretry 回, 同じ IP アドレスからのメッセージがカウントされるとその IP アドレスからのアクセスが ban される.
  * ignoreregex は failregex で設定したもののうち, カウントしたくないメッセージがある場合に設定する.
  * failregex の最後の行は access ログを監視するための構文である.
    * access ログは error ログとはメッセージの書式が異なるので, その上の 5 つとは書き方が異なる.
  * 1 つの html ページに画像がたくさん貼付けてあるとそれだけでカウントして ban してしまうことがある. そのため, png, jpg(jpeg), gif ファイルについては ignoreregex に追加している.


apache-auth.conf, apache-common.conf, apache-nohome.conf, apache-noscript.conf, apache-overflows.conf の中身を以下のように書き換えた.

* /etc/fail2ban/filter.d/apache-auth.conf
  * 1行目のみ異なっていたため書き換えた
  
  * 変更前
  
     failregex = ^%(_apache_error_client)s (AH01797: )?client denied by server configuration: (uri )?\S*(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH01617: )?user .*? authentication failure for "\S*": Password Mismatch(, referer: \S+)?$
                 ^%(_apache_error_client)s (AH01618: )?user .*? not found(: )?\S*(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH01614: )?client used wrong authentication scheme: \S*(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH\d+: )?Authorization of user \S+ to access \S* failed, reason: .*$
                 ^%(_apache_error_client)s (AH0179[24]: )?(Digest: )?user .*?: password mismatch: \S*(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH0179[01]: |Digest: )user `.*?' in realm `.+' (not found|denied by provider): \S*(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH01631: )?user .*?: authorization failure for "\S*":(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH01775: )?(Digest: )?invalid nonce .* received - length is not \S+(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH01788: )?(Digest: )?realm mismatch - got `.*?' but expected `.+'(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH01789: )?(Digest: )?unknown algorithm `.*?' received: \S*(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH01793: )?invalid qop `.*?' received: \S*(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH01777: )?(Digest: )?invalid nonce .*? received - user attempted time travel(, referer: \S+)?\s*$
     ignoreregex =

  * 変更後
     failregex = ^%(_apache_error_client)s (AH(01797|01630): )?client denied by server configuration: (uri )?\S*(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH01617: )?user .*? authentication failure for "\S*": Password Mismatch(, referer: \S+)?$
                 ^%(_apache_error_client)s (AH01618: )?user .*? not found(:)?\S*(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH01614: )?client used wrong authentication scheme: \S*(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH\d+: )?Authorization of user \S+ to access \S* failed, reason: .*$
                 ^%(_apache_error_client)s (AH0179[24]: )?(Digest: )?user .*?: password mismatch: \S*(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH0179[01]: |Digest: )user `.*?' in realm `.+' (not found|denied by provider): \S*(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH01631: )?user .*?:authorization failure for "\S*":(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH01775: )?(Digest: )?invalid nonce .* received - length is not \S+(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH01788: )?(Digest: )?realm mismatch - got `.*?' but expected `.+'(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH01789: )?(Digest: )?unknown algorithm `.*?' received: \S*(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH01793: )?invalid qop `.*?'received: \S*(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s (AH01777: )?(Digest: )?invalidnonce .*? received - user attempted time travel(, referer: \S+)?\s*$
     ignoreregex = ^<HOST> -.*GET.*(jpg|jpeg|gif|png).*

* /etc/fail2ban/filter.d/apache-common.conf
  * はじめから記載されていた

     apache_error_client = \[[^]]*\] \[(:?error|\S+:\S+)\]( \[pid \d+(:\S+\d+)?\])? \[client <HOST>(:\d{1,5})?\]


* /etc/fail2ban/filter.d/apache-nohome.conf
  * 変更前

     failregex = ^%(_apache_error_client)s (AH00128: )?File does not exist: .*/~.*

  * 変更後

     failregex = ^%(_apache_error_client)s (AH00128: )?File does not exist:


* /etc/fail2ban/filter.d/apache-noscript.conf
  * はじめから記載されていた

     failregex = ^%(_apache_error_client)s ((AH001(28|30): )?File does not exist|(AH01264: )?script not found or unable to stat):/\S*(php([45]|[.-]cgi)?|\.asp|\.exe|\.pl)(, referer: \S+)?\s*$
                 ^%(_apache_error_client)s script'/\S*(php([45]|[.-]cgi)?|\.asp|\.exe|\.pl)\S*' not found or unable to stat(, referer: \S+)?\s*$

* /etc/fail2ban/filter.d/apache-overflows.conf

  * 変更前
  
     failregex = ^%(_apache_error_client)s ((AH0013[456]: )?Invalid (method|URI) in request .*( - possible attempt to establish SSL connection on non-SSL port)?|(AH00565: )?request failed: URI too long \(longer than \d+\)|request failed: erroneous characters after protocol string: .*|AH00566: request failed: invalid characters in URI)(, referer: \S+)?$

  * 変更後

     failregex = ^%(_apache_error_client)s ((AH0013[456]: )?Invalid
     (method|URI) in request .*( - possible attempt to establish SSL
     connection on non-SSL port)?|(AH00565: )?request failed: URI too long
     \(longer than \d+\)|request failed: erroneous characters after protocol
     string: .*|AH00566: request failed: invalid characters in URI)(,referer: \S+)?$


* /etc/fail2ban/filter.d/apache-auth.conf を /etc/fail2ban/filter.d/apache-ddos.conf と /etc/fail2ban/filter.d/apache-auth.conf に分割した.

   cp /etc/fail2ban/filter.d/apache-auth.conf /etc/fail2ban/filter.d/apache-ddos.conf

* /etc/fail2ban/filter.d/apache-ddos.conf のfailregex を以下のように書き換えた.

   failregex =^<HOST> -.*GET.*


* /etc/fail2ban/jail.conf の [apache] より下に以下を追加する.

   [apache-ddos]
   enabled  = true
   port     = http,https
   filter   = apache-ddos
   findtime= 60
   logpath  = /var/log/httpd-*access.log
   maxretry = 60
   bantime  = 1200


== ssh

* /etc/fail2ban/filter.d/sshd.conf の failregex を編集する.

  * 以下の1行を追記する.

     ^%(__prefix_line)s[iI] .* [[]<HOST>[]] .* POSSIBLE BREAK-IN ATTEMPT\s*S

= ログレベルの確認

* /etc/fail2ban/fail2ban.conf の中のログレベルが 3 になっていることを確認した.
#(デフォルトになっているはずなので, 作業する必要はないが, 確認しておくこと)

  * ban, unban の記録がログに出力されるレベル
# Option:  loglevel
# Notes.:  Set the log level output.
#          1 = ERROR
#          2 = WARN
#          3 = INFO
#          4 = DEBUG
# Values:  NUM  Default:  3
#
loglevel = 3



= fail2ban の起動

以下のコマンドで fail2ban を起動した.

  # /etc/init.d/fail2ban start

fail2ban が動いているか確認した.

# /etc/init.d/fail2ban status
Status of authentication failure monitor:fail2ban is running.

* サービスの停止・開始・再起動は
  ((<[ITPASS2011a]サービスの開始・停止>)) を参照のこと.

= 動作テスト

== ssh

情報実験機など (固定 IP が望ましい) から, 存在しないユーザ名で tako に ssh を行い, 動作をチェックを行った.

$ ssh hoge@133.30.109.21
  hoge@133.30.109.21's password:
  Permission denied, please try again.
(これを繰り返した)


maxretry 回目には接続が切られ, 何も表示されなくなる (動作テストを行うマシンによって表示は異なる. メッセージが表示される場合もある). tako で iptables -L をして, リストに加えられているかを確認した.  

root@tako-itpass:~# iptables -L
Chain INPUT (policy ACCEPT)
target     prot opt source               destination        
fail2ban-ssh  tcp  --  anywhere             anywhere            multiport dports ssh
(省略)
Chain fail2ban-ssh (1 references)
target     prot opt source                             destination        
DROP       all  --  133.30.109.80 anywhere  <-- これ          
RETURN     all  --  anywhere                           anywhere            

fail2ban のログに記録されているか確認した. 以下のような警告がログ /var/log/fail2ban.log に記載されていた.

  2015-11-04 13:42:40,373 fail2ban.actions[7841]: WARNING [ssh] Ban 133.30.109.80
  2015-11-04 13:52:41,078 fail2ban.actions[7841]: WARNING [ssh] Unban 133.30.109.80

== apache

* 動作が確認しやすいように findtime や maxretry, 画像ファイルにアクセスしてテストする場合は ignoreregex の値を適宜変更すること.
* 固定 IP の計算機から行うことを推奨する.
  * DHCP で IP が配られる環境から行わざるをえない時は, 他の人が接続していないか確認すること.


=== error のテスト

* fail2ban を再起動し, ブラウザを立ち上げ, tako-itpass.scitec.kobe-u.ac.jp/ 以下の others にパーミッションがないところ, (例えば ITPASS 実習の ppt/odp ファイル) や itpass ドメイン以下の実在しない URL を入力して, findtime 以内に maxretry 回以上アクセスした.
#  ((* 単なる itpass ではなく直接 tako にアクセスすること(URL に 133.30.109.21 と入力してもOK) *))
#* runtime error になれば OK.
* iptables -L を見て, アクセスした IP アドレスが ban されていることを確認した.
* /var/log/fail2ban.log についても確認した

   2015-11-04 13:53:12,089 fail2ban.actions[7841]: WARNING [apache-ddos] Ban 133.30.109.80
   2015-11-04 13:54:10,163 fail2ban.actions[7841]: WARNING [apache-ddos] Unban 133.30.109.80

=== access のテスト

* ブラウザから tako-itpass.scitec.kobe-u.ac.jp 以下のファイルに findtime 以内に maxretry 回更新した.
#* runtime error になれば OK.
* iptables -L を見て, アクセスした IP アドレスが ban されていることを確認した.
* /var/log/fail2ban.log についても確認した

   2015-11-04 14:30:13,922 fail2ban.actions[8127]: WARNING [apache-ddos] Ban 133.30.109.80
   2015-11-04 14:31:13,997 fail2ban.actions[8127]: WARNING [apache-ddos] Unban 133.30.109.80
  
#((*確認できたら変更した変数の値をもとに戻して fail2ban を再起動すること*))

= 挙動がシステムログメールに記載されるように設定

== スクリプトの設置

* ika の ~itpass/ftp/server/2011/system_report/loginfail を tako の /etc/cron.local/daily/800_loginfail にコピーされていることを確認した.
      
== テスト

* 情報実験機など (固定IPが望ましい) から maxretry 回, 存在しない名前でログインして ban されたことを確認した (同じ日に ssh でテストしているならこの作業はしなくてよい).
* 次の日のメールのシステムログに出力されていることを確認する.

=== /etc/cron.local/daily/800_loginfail の修正

Ban/Unban がメールのシステムログに出力されていなかったので /etc/cron.local/daily/800_loginfail の修正を行った

* 変更前
   yesterday2=`date "+%Y-%m_%d" --date "1 days ago"`

* 変更後
   yesterday2=`date "+%Y-%m-%d" --date "1 days ago"`

変更後, ログメールの送信テストを行い, ログが出力されていることを確認した.

== fail2ban の動作確認

*  fail2ban のフィルターの動作確認を行う.

    # fail2ban-regex /var/log/auth.log /etc/fail2ban/filter.d/sshd.conf

* 表示内容を確認し, フィルターにかかっていることを確認する.

= 参考

* ((<Debian clusters|URL:http://debianclusters.org/index.php/Fail2Ban:_Preventing_Brute_Force_SSH>))
* ((<THE ART OF WEB|URL:http://www.the-art-of-web.com/system/logs/>))
* ((<fail2ban wiki|URL:http://www.fail2ban.org/wiki/index.php/Talk:Apache>))
* ((<[ITPASS2012]サービスの開始・停止>))

[((<ITPASSサーバ構築・運用ドキュメント>)) へ戻る]