FreePBX Fail2ban Script PJSIP TLS not banning

Hello,

Is anyone here have a working Fail2ban filters for PJSIP TLS?

Tried this link and others from the internet but still no luck. Fail2ban doesn’t do anything.

Thank you in advance. Appreciate your help.

As the link you posted suggested, check the log line in question against the Asterisk jail’s filters with fail2ban-regex, if you are using 0.9 or less (fail2ban-client version) the filters may need patching.

Hi dicko,

My Fail2ban current version is v0.8.14

By manually running fail2ban-regex got several matches but Fail2ban doesn’t ban it.
Brute force the UCP login page and got banned and no issue on that.

Only when brute forcing the pjsip authentication trying to register on the softphone

Asterisk logs:
[2022-04-25 16:06:00] NOTICE[6807]: res_pjsip/pjsip_distributor.c:676 log_failed_request: Request ‘REGISTER’ from ‘sip:[email protected]’ failed for ‘123.51.226.52:54415’ (callid: UmSGfIJ_7r-bIDs0c0mgyQ…) - Failed to authenticate

Using the Asterisk filter in fail2ban. I believe this log falls into this regex below:

^(%(__prefix_line)s|[]\s*)%(log_prefix)s Request ‘[^’]’ from ‘[^’]’ failed for ‘:\d+’ (.+) - Failed to authenticate$

Thank you,

Hi

What the version please.

> rpm -qa fail2ban*

Here is the output @franckdanard
fail2ban-fpbx-0.8.14-78.sng7.noarch

Are the matches repeated enough and often enough to meet the ‘bantime’ criteria?

Hi dicko,

Fail2ban doesn’t do anything, attacker can send multiple failed authentication in PJSIP TLS.

Tried this regex below, the one you gave in other post which related also to this concern.

Log result in asterisk full If the extension is existing in the server.
[2022-04-25 16:06:00] NOTICE[6807]: res_pjsip/pjsip_distributor.c:676 log_failed_request: Request ‘REGISTER’ from ‘sip:[email protected]’ failed for ‘123.51.226.52:54415’ (callid: UmSGfIJ_7r-bIDs0c0mgyQ…) - Failed to authenticate

Trying to block the above logfile using this REGEX:
^Request (?:’[^’]’ )?from ‘(?:[^’]|.?)’ failed for ‘(?::\d+)?’\s(callid: [^)]) - (?:No matching endpoint found|Not match Endpoint(?: Contact)? ACL|(?:Failed|Error) to authenticate)\s*$

The REGEX above I encountered an error starting on the HOST part
Tried it here to debug: https://regex101.com/

Im not sure what was causing the issue there but I tried several way to get the HOST but nothing works.


Another thing that I want to block is if the attacker trying to brute force using the non-existing extension

Logfile result on the full asterisk:
[2022-04-25 18:18:59] WARNING[13635]: res_pjsip_registrar.c:1189 registrar_on_rx_request: Endpoint ‘anonymous’ (123.53.212.53:54415) has no configured AORs

Hope you guys can help me generate the REGEX for this as I’m not very familiar how to do it.

Appreciate your help.

As you are using the ‘Distro’ version of f2b, I will leave that up to those others that do.

1 Like

I will open a ticket for this case.

Hi @dicko yes using fail2ban-fpbx-0.8.14-78.sng7.noarch

@franckdanard yes please, thank you.

Thank you for your help guys.

Hi

Do you have any other sample logs?
E.g: with No matching endpoint found and with |Not match Endpoint

Hi @franckdanard it seems that before when you try to register non existing extension on the asterisk logs shows with No matching endpoint.

Tried it now and it show this:

Logfile result on the full asterisk:
[2022-04-25 18:18:59] WARNING[13635]: res_pjsip_registrar.c:1189 registrar_on_rx_request: Endpoint ‘anonymous’ (123.53.212.53:54415) has no configured AORs

Can you create REGEX for this for us to try please?

Yes sure.
No prob
And this one works now.

Nothing about No matching endpoint found and with Not match Endpoint ?

# fail2ban-regex /var/log/asterisk/f2b.test /etc/fail2ban/filter.d/asterisk.conf

Running tests
=============

Use   failregex file : /etc/fail2ban/filter.d/asterisk.conf
Use         log file : /var/log/asterisk/f2b.test


Results
=======

Failregex: 4 total
|-  #) [# of hits] regular expression
|   9) [1] ^(\s*(<[^.]+\.[^.]+>)?\s*(?:\S+ )?(?:kernel: \[ *\d+\.\d+\] )?(?:@vserver_\S+ )?(?:(?:\[\d+\])?:\s+[\[\(]?asterisk(?:\(\S+\))?[\]\)]?:?|[\[\(]?asterisk(?:\(\S+\))?[\]\)]?:?(?:\[\d+\])?:?)?\s(?:\[ID \d+ \S+\])?\s*|\[\]\s*)(?:NOTICE|SECURITY|WARNING)(?:\[\d+\]):?(?:\[C-[\da-f]*\])? \S+:\d*( in \w+:)? .+Request '[^']*' from '[^']*' failed for '<HOST>:\d+' \(.+\) \- Failed to authenticate$
|  11) [1] ^(\s*(<[^.]+\.[^.]+>)?\s*(?:\S+ )?(?:kernel: \[ *\d+\.\d+\] )?(?:@vserver_\S+ )?(?:(?:\[\d+\])?:\s+[\[\(]?asterisk(?:\(\S+\))?[\]\)]?:?|[\[\(]?asterisk(?:\(\S+\))?[\]\)]?:?(?:\[\d+\])?:?)?\s(?:\[ID \d+ \S+\])?\s*|\[\]\s*)(?:NOTICE|SECURITY|WARNING)(?:\[\d+\]):?(?:\[C-[\da-f]*\])? \S+:\d*( in \w+:)? .+Endpoint 'anonymous' \(<HOST>:\d+\) has no configured AORs$
|  12) [1] ^(\s*(<[^.]+\.[^.]+>)?\s*(?:\S+ )?(?:kernel: \[ *\d+\.\d+\] )?(?:@vserver_\S+ )?(?:(?:\[\d+\])?:\s+[\[\(]?asterisk(?:\(\S+\))?[\]\)]?:?|[\[\(]?asterisk(?:\(\S+\))?[\]\)]?:?(?:\[\d+\])?:?)?\s(?:\[ID \d+ \S+\])?\s*|\[\]\s*)(?:NOTICE|SECURITY|WARNING)(?:\[\d+\]):?(?:\[C-[\da-f]*\])? \S+:\d*( in \w+:)? SecurityEvent="(FailedACL|InvalidAccountID|ChallengeResponseFailed|InvalidPassword)",EventTV="([\d-]+|\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}\.\d+[+-]\d{4})",Severity="[\w]+",Service="[\w]+",EventVersion="\d+",AccountID="(\d*|anonymous)",SessionID="[\w\.]+",LocalAddress="IPV[46]/(UDP|TCP|WS|WSS|TLS)/[\da-fA-F:.]+/\d+",RemoteAddress="IPV[46]/(UDP|TCP|WS|TLS)/<HOST>/\d+"(,Challenge="[\w/]+")?(,ReceivedChallenge="\w+")?(,Response="\w+",ExpectedResponse="\w*")?(,ReceivedHash="[\da-f]+")?(,ACLName="\w+")?$
|  14) [1] ^(\s*(<[^.]+\.[^.]+>)?\s*(?:\S+ )?(?:kernel: \[ *\d+\.\d+\] )?(?:@vserver_\S+ )?(?:(?:\[\d+\])?:\s+[\[\(]?asterisk(?:\(\S+\))?[\]\)]?:?|[\[\(]?asterisk(?:\(\S+\))?[\]\)]?:?(?:\[\d+\])?:?)?\s(?:\[ID \d+ \S+\])?\s*|\[\]\s*WARNING(?:\[\d+\]):?(?:\[C-[\da-f]*\])? )Ext\. s: "Rejecting unknown SIP connection from <HOST>.*"$
`-

Ignoreregex: 0 total

Date template hits:
|- [# of hits] date format
|  [4] Year-Month-Day Hour:Minute:Second
`-

Lines: 4 lines, 0 ignored, 4 matched, 0 missed

You can use this kind of cmd line above to test the logs in another file as f2b.test

I updated one and added two regex filters.
I just need to add those with No matching endpoint found and with Not match Endpoint.

If you don’t have one, then no prob.
I will publish a new version of fail2ban-fpbx and if you see there is something to add, please update me.

I built a new RPM version : fail2ban-fpbx-0.8.14-79
Wait the publishing on stable repos.
Need to be validate by the QA team before. :slight_smile:

1 Like

Hi @franckdanard Awesome! Appreciate your help with this :slight_smile:

Hopefully they will release it soon in public.

Sure, I’ll keep this post updated for other logs that needs to be detected by fail2ban-fpbx

1 Like

Hi @franckdanard

Tried manually your REGEX and it works but when I applied this in asterisk.conf and monitor the fail2ban logs by using this command:
tail -f /var/log/fail2ban-logs
then register softphone using invalid credential via PJSIP TLS the logs doesn’t show anything like the fail2ban before like if Fail2ban found invalid attempt, it show in logs Found 122.22.50.123

It just like this

The intruder can still send registration multiple times even already reached the maxretry which is set to 5 times

The REGEX you gave is working and matched but not sure why fail2ban-fpbx doesn’t detect and ban it.

It should work with this:

# All Asterisk log messages begin like this:
log_prefix= (?:NOTICE|SECURITY|WARNING)%(__pid_re)s:?(?:\[C-[\da-f]*\])? \S+:\d*( in \w+:)?

failregex = ^(%(__prefix_line)s|\[\]\s*)%(log_prefix)s Registration from '[^']*' failed for '<HOST>(:\d+)?' - (Wrong password|Username/auth name mismatch|No matching peer found|Not a local domain|Device does not match ACL|Peer is not supposed to register|ACL error \(permit/deny\)|Not a local domain)$
            ^(%(__prefix_line)s|\[\]\s*)%(log_prefix)s Call from '[^']*' \(<HOST>:\d+\) to extension '[^']*' rejected because extension not found in context
            ^(%(__prefix_line)s|\[\]\s*)%(log_prefix)s Host <HOST> failed to authenticate as '[^']*'$
            ^(%(__prefix_line)s|\[\]\s*)%(log_prefix)s No registration for peer '[^']*' \(from <HOST>\)$
            ^(%(__prefix_line)s|\[\]\s*)%(log_prefix)s Host <HOST> failed MD5 authentication for '[^']*' \([^)]+\)$
            ^(%(__prefix_line)s|\[\]\s*)%(log_prefix)s Failed to authenticate (user|device) [^@]+@<HOST>\S*$
            ^(%(__prefix_line)s|\[\]\s*)%(log_prefix)s hacking attempt detected '<HOST>'$
            ^(%(__prefix_line)s|\[\]\s*)%(log_prefix)s <HOST> tried to authenticate with nonexistent user.+$
            ^(%(__prefix_line)s|\[\]\s*)%(log_prefix)s <HOST> failed to authenticate as.+$
            ^(%(__prefix_line)s|\[\]\s*)%(log_prefix)s .+Request '[^']*' from '[^']*' failed for '<HOST>:\d+' \(.+\) \- Failed to authenticate$   
            ^(%(__prefix_line)s|\[\]\s*)%(log_prefix)s .+Request from '[^']*' failed for '<HOST>:\d+' .+ No matching endpoint found$
            ^(%(__prefix_line)s|\[\]\s*)%(log_prefix)s .+Endpoint 'anonymous' \(<HOST>:\d+\) has no configured AORs$
            ^(%(__prefix_line)s|\[\]\s*)%(log_prefix)s SecurityEvent="(FailedACL|InvalidAccountID|ChallengeResponseFailed|InvalidPassword)",EventTV="([\d-]+|%(iso8601)s)",Severity="[\w]+",Service="[\w]+",EventVersion="\d+",AccountID="(\d*|anonymous)",SessionID="[\w\.]+",LocalAddress="IPV[46]/(UDP|TCP|WS|WSS|TLS)/[\da-fA-F:.]+/\d+",RemoteAddress="IPV[46]/(UDP|TCP|WS|TLS)/<HOST>/\d+"(,Challenge="[\w/]+")?(,ReceivedChallenge="\w+")?(,Response="\w+",ExpectedResponse="\w*")?(,ReceivedHash="[\da-f]+")?(,ACLName="\w+")?$
# These WARNINGS do not have a file attribute, as they're generated dynamicly
            ^(%(__prefix_line)s|\[\]\s*WARNING%(__pid_re)s:?(?:\[C-[\da-f]*\])? )[^:]+: Friendly Scanner from <HOST>$
            ^(%(__prefix_line)s|\[\]\s*WARNING%(__pid_re)s:?(?:\[C-[\da-f]*\])? )Ext\. s: "Rejecting unknown SIP connection from <HOST>.*"$