差分

移動先: 案内検索

SIP-Fail2ban

5,164 バイト追加, 2020年8月7日 (金) 19:40
CentOS 8
IAXでのFail2banは'''[[IAX-Fail2ban]]'''を参照してください。
==fail2ban==
ログファイルとiptablesを利用したファイアウォールの一種。Brute Forceアタックの対策に使いやすい。<br>
:http://www.fail2ban.org/
:http://sourceforge.net/projects/fail2ban/
==動作条件==iptablesおよびpythonを必要とします。最新のFail2banではAsteriskにも対応しています。pythonとiptablesが必要。yum install python iptablesなどで入れておいて下さい。==インストールCentOS==まずSFからfail2banをダウンロードし、展開します。CentOSではepelからyumでインストールすることが可能です。 tar jxvf fail2banyum install -y epel-0.8.4.tar.bz2展開したディレクトリでインストールを実行します。release cd fail2banyum --0.8.4 python ./setup.pyスタートアップ・スクリプトをコピーしておきます(CentOSなどRedHat系の場合の例)。 cp files/redhatenablerepo=epel -initd /etc/init.d/y install fail2ban==設定=====Asteriskのログフォーマットを変更する===Fail2banはそのままではAsteriskのログの日付を認識できないため、Asteriskのログフォーマットを変更します。yumでインストールした最新のFail2BanはAsteriskのログフォーマットを変更し、ローカル設定ファイルを作成するだけで使用することができます。<brBR>/etc/asterisk/loggerまずAsteriskのlogger.confを編集し、日付のフォーマット変更を行います。<br>confを修正し [general]セクションにある ; Customize the display of debug message time stamps ; this example is the ISO 8601 date format (yyyy-mm-dd HH:MM:SS) ; see strftime(3) Linux manual for format specifiers
dateformat=%F %T
のコメントを外すか、もしこのエントリがなければ記述します。設定を変更したら、Asteriskを再起動するか、loggerモジュールのリロードを行って、変更を有効にします。これによりAsteriskのログの日付形式が以下のように変わりますので、確認してください。 [2010-12-30 09:25:25] NOTICE[17537] chan_sip.c:.....===Asterisk用の定義ファイルを作る===dateformatの箇所のコメント(;)を外して有効にし、Asteriskを再起動します。<br>/etc/fail2ban/filterに以下の内容のjail.d ディレクトリに asterisk.conf という名前で以下のようなファイルを作ります。ここで指定したメッセージがBAN基準として使われるメッセージとなります。<br>localというファイルを作成します。ファイルがある場合には修正します。<br> [DEFAULT]Asterisk 1.8系の場合 ignoreip = # Fail2Ban configuration filebackend = polling #bantime = 3600 #; 1hour # $Revision: 250 $maxretry= 5 #usedns = no
[INCLUDESasterisk] enabled = truefail2banを起動すると監視が始まります。  ===起動の確認===iptables -Lでiptablesの状態を確認するとfail2banでbanされたIPアドレス等が確認できます。 Chain f2b-asterisk-tcp (1 references) target prot opt source destination REJECT all -- 46.17.42.180 anywhere reject-with icmp-port-unreachable RETURN all -- anywhere anywhere
# Read common prefixesChain f2b-asterisk-udp (1 references) target prot opt source destination REJECT all -- 46.17.42. If any customizations available 180 anywhere reject-with icmp-port-unreachable RETURN all -- read them from anywhere anywhereデフォルトではban時間は1時間です。 ==INVITEによるBrute force攻撃への対策==REGISTERメッセージによる攻撃以外に、INVITEによるBrute force攻撃も確認されています。 この攻撃時に出力されるログメッセージは以下のようなものになります。  # commonFailed to authenticate user "Anonymous" <sip:anonymous@192.168.local1.2>;tag=as105e401c  このログメッセージの攻撃元IPアドレスが、FROMヘッダに記載されているIPアドレスになっています。 このままでは、NAT配下のサーバーからの攻撃や、FROMヘッダが偽装された場合にfail2banで対応することができません。 そこで、Asteriskへパッチを当てて、実際の攻撃元IPアドレスを表示するように修正します。 ===Asteriskへパッチを当てる=== 次のようなパッチをAsteriskに適用します。 このパッチはAsterisk-1.4.40を対象にしていますが、1.6系、1.8系にも同様の修正で対応できます。  --- asterisk-1.4.40.orig/channels/chan_sip.c 2011-01-05 02:11:48.000000000 +0900 #before +++ asterisk-1.4.40/channels/chan_sip.c 2011-03-10 17:59:26.000000000 +0900 @@ -15456,7 +15456,7 @@ ast_log(LOG_NOTICE, "Sending fake auth rejection for user %s\n", get_header(req, "From")); transmit_fake_auth_response(p, SIP_INVITE, req, XMIT_RELIABLE); } else { - ast_log(LOG_NOTICE, "Failed to authenticate user %s\n", get_header(req, "From")); + ast_log(LOG_NOTICE, "Failed to authenticate user %s (%s:%d)\n", get_header(req, "From"), ast_inet_ntoa(sin->sin_addr), ntohs(sin->sin_port)); transmit_response_reliable(p, "403 Forbidden", req); } p->invitestate = common.confINV_COMPLETED;
こちらは Asterisk-1.8.23.0 用です。Asterisk-11.5.1 でもほぼ同じコードが使えます。
 
--- asterisk-1.8.23.0/channels/chan_sip.c.orig 2013-08-02 11:41:03.233638321 +0900
+++ asterisk-1.8.23.0/channels/chan_sip.c 2013-12-06 14:51:08.698990909 +0900
@@ -22673,7 +22673,7 @@
return 0;
}
if (res < 0) { /* Something failed in authentication */
- ast_log(LOG_NOTICE, "Failed to authenticate device %s\n", get_header(req, "From"));
+ ast_log(LOG_NOTICE, "Failed to authenticate device %s (%s)\n", get_header(req, "From"), ast_sockaddr_stringify(addr));
transmit_response(p, "403 Forbidden", req);
sip_scheddestroy(p, DEFAULT_TRANS_TIMEOUT);
return 0;
@@ -23334,7 +23334,7 @@
goto request_invite_cleanup;
}
if (res < 0) { /* Something failed in authentication */
- ast_log(LOG_NOTICE, "Failed to authenticate device %s\n", get_header(req, "From"));
+ ast_log(LOG_NOTICE, "Failed to authenticate device %s (%s)\n", get_header(req, "From"), ast_sockaddr_stringify(addr));
transmit_response_reliable(p, "403 Forbidden", req);
p->invitestate = INV_COMPLETED;
sip_scheddestroy(p, DEFAULT_TRANS_TIMEOUT);
@@ -25164,7 +25164,7 @@
p->lastinvite = seqno;
return 0;
} else if (auth_result < 0) {
- ast_log(LOG_NOTICE, "Failed to authenticate device %s\n", get_header(req, "From"));
+ ast_log(LOG_NOTICE, "Failed to authenticate device %s (%s)\n", get_header(req, "From"), ast_sockaddr_stringify(addr));
transmit_response(p, "403 Forbidden", req);
sip_scheddestroy(p, DEFAULT_TRANS_TIMEOUT);
ast_string_field_set(p, theirtag, NULL);
@@ -25384,7 +25384,7 @@
if (res == AUTH_CHALLENGE_SENT) /* authpeer = NULL here */
return 0;
if (res != AUTH_SUCCESSFUL) {
- ast_log(LOG_NOTICE, "Failed to authenticate device %s\n", get_header(req, "From"));
+ ast_log(LOG_NOTICE, "Failed to authenticate device %s (%s)\n", get_header(req, "From"), ast_sockaddr_stringify(addr));
transmit_response(p, "403 Forbidden", req);
pvt_set_needdestroy(p, "authentication failed"); Asterisk 11.23.1用パッチです。  [Definition]--- channels/chan_sip.c.orig 2016-09-09 01:28:35.000000000 +0900 +++ channels/chan_sip.c 2016-10-28 23:26:38.985774935 +0900 @@ -18751,7 +18751,7 @@ static void receive_message(struct sip_p return; } if (res < 0) { /* Something failed in authentication */ - ast_log(LOG_NOTICE, "Failed to authenticate device %s\n", sip_get_header(req, "From")); + ast_log(LOG_NOTICE, "Failed to authenticate device %s (%s)\n", sip_get_header(req, "From"), ast_sockaddr_stringify(addr)); transmit_response(p, "403 Forbidden", req); sip_scheddestroy(p, DEFAULT_TRANS_TIMEOUT); return; @@ -24963,7 +24963,7 @@ static int handle_request_options(struct return 0; } if (res < 0) { /* Something failed in authentication */ - ast_log(LOG_NOTICE, "Failed to authenticate device %s\n", sip_get_header(req, "From")); + ast_log(LOG_NOTICE, "Failed to authenticate device %s (%s)\n", sip_get_header(req, "From"), ast_sockaddr_stringify(addr)); transmit_response(p, "403 Forbidden", req); sip_scheddestroy(p, DEFAULT_TRANS_TIMEOUT); return 0; @@ -25798,7 +25798,7 @@ static int handle_request_invite(struct goto request_invite_cleanup; } if (res < 0) { /* Something failed in authentication */ - ast_log(LOG_NOTICE, "Failed to authenticate device %s\n", sip_get_header(req, "From")); + ast_log(LOG_NOTICE, "Failed to authenticate device %s (%s)\n", sip_get_header(req, "From"), ast_sockaddr_stringify(addr)); transmit_response_reliable(p, "403 Forbidden", req); p->invitestate = INV_COMPLETED; sip_scheddestroy(p, DEFAULT_TRANS_TIMEOUT); @@ -27788,7 +27788,7 @@ static int handle_request_publish(struct p->lastinvite = seqno; return 0; } else if (auth_result < 0) { - ast_log(LOG_NOTICE, "Failed to authenticate device %s\n", sip_get_header(req, "From")); + ast_log(LOG_NOTICE, "Failed to authenticate device %s (%s)\n", sip_get_header(req, "From"), ast_sockaddr_stringify(addr)); transmit_response(p, "403 Forbidden", req); sip_scheddestroy(p, DEFAULT_TRANS_TIMEOUT); ast_string_field_set(p, theirtag, NULL); @@ -28003,7 +28003,7 @@ static int handle_request_subscribe(stru if (res == AUTH_CHALLENGE_SENT) /* authpeer = NULL here */ return 0; if (res != AUTH_SUCCESSFUL) { - ast_log(LOG_NOTICE, "Failed to authenticate device %s for SUBSCRIBE\n", sip_get_header(req, "From")); + ast_log(LOG_NOTICE, "Failed to authenticate device %s (%s) for SUBSCRIBE\n", sip_get_header(req, "From"), ast_sockaddr_stringify(addr)); transmit_response(p, "403 Forbidden", req);
pvt_set_needdestroy(p, "authentication failed");   パッチを当てて、Asteriskをコンパイルし直し、再起動します。 すると、先ほどの攻撃時のログは以下のように出力されるようになります。  #_daemon Failed to authenticate user "Anonymous" <sip:anonymous@192.168.1.2>;tag=as105e401c (123.45.67.89:5060) ログの( )内に攻撃元の実IPアドレスが表示されるようになり、これを元にfail2banで攻撃を検知することができます。 ===fail2banへ設定を追加=== 修正したログに合わせたフィルタ設定をfail2banに追加します。 /etc/fail2ban/filter.d/asterisk.conf の failregex の項目に以下を追加します。  NOTICE.* .*: Failed to authenticate user .* \(<HOST>:.*\) フィルタ追加後、fail2banを再起動し設定完了です。 ==securityログの設定==/etc/asterisk/logger.confに [logfiles] security = > securityを追加(コメント解除)して、/var/log/asterisk/securityにできるログをfail2banに監視させる方法もあります。 ==ステータス確認==fail2ban-client コマンドで問い合わせるのがいいです。 # コマンド一覧 fail2ban-client
# Option: failregex # Notes.: regex to match the password failures messages in the logfile. The # host must be matched by a group named "host". The tag "<HOST>" can # be used for standard IP/hostname matching and is only an alias for # (?:::f{4,6}:)?(?P<host>\S+) # Values: TEXT有効なjail一覧 #fail2ban-client status
failregex = Registration from '.*' failed for '<HOST>(:[0-9]{1,5})?' - Wrong password Registration from '.*' failed for '<HOST>(:[0-9]{1,5})?' - No matching peer found Registration from '.*' failed for '<HOST>(:[0-9]{1,5})?' - Username/auth name mismatch# jail名"asterisk"のステータス Registration from '.*' failed for '<HOST>(:[0-9]{1,5})?' - Device does not match ACL Registration from '.*' failed for '<HOST>(:[0-9]{1,5})?' - Peer is not supposed to register Registration from '.*' failed for '<HOST>(:[0-9]{1,5})?' fail2ban- Not a local domainclient status asterisk
# Option: ignoreregex手動でban/unban # Notesfail2ban-client set asterisk banip 11.: regex to ignore22. If this regex matches, the line is ignored33.44 # Values: TEXTfail2ban-client set asterisk unbanip 11.22.33.44 #banされてることになっていても、actionが正しく書けていないと実際にはfirewalldやiptablesなどに反映されず、攻撃されっぱなしもあり得るので、挙動確認が大事です。<br> ignoreregex =fail2ban-server コマンドは直接叩いてはいけないようです。<br>Asterisk 1または、ログファイル /var/log/fail2ban.6とそれ以前の場合log を見てもいいです。 # Fail2Ban configuration file #== CentOS 8 == # # $Revision: 250 $Asterisk16, CentOS 8でも同様にepelからdnfでインストールすることが可能です。<BR> #CentOS 8では、iptablesではなく、nftables及びfirewalldが使用されていますが、問題なく対応しています。 dnf install -y epel-release [INCLUDES] # Read common prefixes. If any customizations available dnf -- read them from # common.local #before enablerepo= common.conf [Definition] #_daemon = asterisk epel -y install fail2ban fail2ban-systemd # Option: failregex # NotesAsteriskのlogger.: regex to match the password failures messages in the logfileconfの変更、/etc/fail2ban/jail. The localの作成は上記、[[# host must be matched by a group named "host". The tag "CentOS|以前のCentOS]]と同様にしてください。<HOSTBR>" can # be used for standard IP/hostname matching and is only an alias forしかし、2020年8月7日時点では、ここでfail2banを起動しても # (?2020-08-07 16:39::f{454,6}981 fail2ban.transmitter [58697]:)?(?P<host>\S+) # Values: TEXT # failregex = Registration from WARNING Command ['.*server-stream' failed for , [['<HOST>set' - Wrong password Registration from , '.*syslogsocket' failed for , '<HOST>auto' - No matching peer found] (略) Registration from Received ValueError('.*Action firewallcmd-rich-rules already exists' failed for ,) 2020-08-07 16:39:54,981 fail2ban [58697]: ERROR NOK: ('<HOST>Action firewallcmd-rich-rules already exists' - Username/auth name mismatch,) Registration from '.*' failed for '<HOST>' - Device does not match ACL Registration from 'というエラーが出て動きません。さしあたりの回避策として/etc/fail2ban/jail.*' failed for '<HOST>' d/00- Peer is not supposed to register Registration from 'firewalld.*' failed for '<HOST>' - Not a local domainconfを次のように変更します。 (略) # Option: [DEFAULT] ignoreregexbanaction = firewallcmd-ipset # Notes.: regex to ignore. If this regex matches, the line is ignored.banaction_allports = firewallcmd-ipset # Values: TEXTbanaction = firewallcmd-rich-rules[actiontype=<multiport>] #banaction_allports = firewallcmd-rich-rules[actiontype=<allports>] これでfail2banを起動すると監視が始まります。 ignoreregex =systemctl enable fail2banAsterisk 1.8とそれ以前ではログのホスト部分にポート番号を含む、含まないの違いがあるためfailregexの記述を変える必要がありますので注意してください。この部分に合致するメッセージが、ログファイルに現れたならばBAN基準になりますので注意して記述します。これ意外にも、引っかけたいメッセージがある場合にはそれも記述するとよいでしょう。<br> systemctl start fail2ban
===BANのアクションを作成する===ここではTCP/UDPの5060ポート、つまりSIPだけをBAN対象としたいためアクションをSIP用に作成します。 /etc/fail2ban/action.d で以下のようにしてアクションを作成します。<br>まず cp iptables稼働状態の確認としては、上記fail2ban-allports.conf iptables-sip.confを行って、全ポート用のアクションをコピーします。次に iptables-sip.conf を編集し、以下のようにBANとUNBANのエントリを修正します。 # Option: actionban # Notes.: command executed when banning an IP. Take care that the # command is executed with Fail2Ban user rights. # Tags: <ip> IP address # <failures> number of failures # <time> unix timestamp of the ban time # Values: CMD #clientコマンドまたは、次のコマンドが使用できます。 actionban = iptables -I fail2ban-<name> 1 -s <ip> -p udp --dport 5060 -j DROP # Option: actionunban # Notes.: command executed when unbanning an IP. Take care that the # command is executed with Fail2Ban user rights. # Tags: <ip> IP address # <failures> number of failures # <time> unix timestamp of the ban time # Values: CMD # actionunban = iptables -D fail2ban-<name> -s <ip> -p udp --dport 5060 -j DROP-p udp と ipset --dport 5073 を actionban と actionunban に追記します。list
===fail2banの設定ファイルを修正===/etc/fail2ban にある jail.conf ファイルの最後に以下を追加します。 Asterisk 16及び[asterisk-iptables[Asterisk pjsip|pjsip]] enabled = true filter = asterisk action = iptables-sipを使用していると、Asteriskにパッチを当てる等しなくても[[name=ASTERISK, protocol=all#INVITEによるBrute force攻撃への対策|INVITEによるBrute force攻撃] sendmail-whois[name=ASTERISK, dest=root, sender=fail2ban@example.net] logpath = /var/log/asterisk/messages maxretry = 5 findtime = 600 bantime = 604800*actionBAN処理のアクションを定義します。この例ではiptables-sipを実行します。その後、sendmail-whois で BANしたIPアドレスのwhois情報を dest= で指定された宛先に送ります。このとき使用されるメールのFrom:はfail2ban@exampleになりますので、適切なものに書き換えます。*logpathAsteriskのログファイルへのパスを記述します。*maxretry何回以上失敗したらBANするかの指定です。*findtimeこの時間内にmaxretryで指定した回数以上失敗するとBANします。上の例では600秒(10分)の間に、5回以上の失敗があった場合にはBANされます。*bantimeここで指定された期間がBAN期間になります。指定は秒数です。上の例では 60x60x24x7=604800、つまり1週間になります。==fail2banを起動する== /etc/init.d/fail2ban start起動したら期待の動作をするかどうかを、よく確認してください。試しに故意に間違えたパスワードで5回以上ログインをしてみるなどです。<br>起動に問題がなければ、fail2banが自動起動されるように登録しておけば良いでしょう。 chkconfig --add fail2ban===起動の確認===iptables -L -v で確認すると 61638 8222K fail2ban-ASTERISK all -- any any anywhere anywhere Chain fail2ban-ASTERISK (1 references) pkts bytes target prot opt in out source destination 61627 8216K RETURN all -- any any anywhere anywhereのようなエントリがあるはずです。<br>BANされるとメールが送られ 11 6424 DROP udp -- any any xxx.xxx.xxx.xx anywhere udp dpt:5060のようなDROPのエントリが追加されているはずです。も防御できるようです。

案内メニュー

VoIp-Info.jp

HP Directplus -HP公式オンラインストア-