summaryrefslogtreecommitdiff
path: root/config/filter.d
diff options
context:
space:
mode:
Diffstat (limited to 'config/filter.d')
-rw-r--r--config/filter.d/apache-auth.conf40
-rw-r--r--config/filter.d/apache-botsearch.conf9
-rw-r--r--config/filter.d/apache-common.conf21
-rw-r--r--config/filter.d/apache-modsecurity.conf3
-rw-r--r--config/filter.d/apache-overflows.conf6
-rw-r--r--config/filter.d/apache-shellshock.conf6
-rw-r--r--config/filter.d/assp.conf2
-rw-r--r--config/filter.d/asterisk.conf26
-rw-r--r--config/filter.d/botsearch-common.conf2
-rw-r--r--config/filter.d/courier-auth.conf2
-rw-r--r--config/filter.d/courier-smtp.conf6
-rw-r--r--config/filter.d/cyrus-imap.conf2
-rw-r--r--config/filter.d/domino-smtp.conf47
-rw-r--r--config/filter.d/dovecot.conf15
-rw-r--r--config/filter.d/dropbear.conf8
-rw-r--r--config/filter.d/ejabberd-auth.conf4
-rw-r--r--config/filter.d/exim-common.conf4
-rw-r--r--config/filter.d/exim.conf11
-rw-r--r--config/filter.d/froxlor-auth.conf7
-rw-r--r--config/filter.d/haproxy-http-auth.conf2
-rw-r--r--config/filter.d/kerio.conf8
-rw-r--r--config/filter.d/mongodb-auth.conf49
-rw-r--r--config/filter.d/murmur.conf6
-rw-r--r--config/filter.d/mysqld-auth.conf2
-rw-r--r--config/filter.d/named-refused.conf8
-rw-r--r--config/filter.d/pam-generic.conf7
-rw-r--r--config/filter.d/postfix-rbl.conf19
-rw-r--r--config/filter.d/postfix-sasl.conf21
-rw-r--r--config/filter.d/postfix.conf60
-rw-r--r--config/filter.d/proftpd.conf15
-rw-r--r--config/filter.d/roundcube-auth.conf9
-rw-r--r--config/filter.d/sendmail-reject.conf47
-rw-r--r--config/filter.d/sshd-ddos.conf29
-rw-r--r--config/filter.d/sshd.conf86
-rw-r--r--config/filter.d/suhosin.conf2
-rw-r--r--config/filter.d/xinetd-fail.conf6
36 files changed, 400 insertions, 197 deletions
diff --git a/config/filter.d/apache-auth.conf b/config/filter.d/apache-auth.conf
index 8a63858d..d9a6fa5e 100644
--- a/config/filter.d/apache-auth.conf
+++ b/config/filter.d/apache-auth.conf
@@ -9,20 +9,21 @@ before = apache-common.conf
[Definition]
+prefregex = ^%(_apache_error_client)s (?:AH\d+: )?<F-CONTENT>.+</F-CONTENT>$
-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: )?invalid nonce .*? received - user attempted time travel(, referer: \S+)?\s*$
+# auth_type = ((?:Digest|Basic): )?
+auth_type = ([A-Z]\w+: )?
+
+failregex = ^client (?:denied by server configuration|used wrong authentication scheme)\b
+ ^user <F-USER>(?:\S*|.*?)</F-USER> (?:auth(?:oriz|entic)ation failure|not found|denied by provider)\b
+ ^Authorization of user <F-USER>(?:\S*|.*?)</F-USER> to access .*? failed\b
+ ^%(auth_type)suser <F-USER>(?:\S*|.*?)</F-USER>: password mismatch\b
+ ^%(auth_type)suser `<F-USER>(?:[^']*|.*?)</F-USER>' in realm `.+' (not found|denied by provider)\b
+ ^%(auth_type)sinvalid nonce .* received - length is not\b
+ ^%(auth_type)srealm mismatch - got `(?:[^']*|.*?)' but expected\b
+ ^%(auth_type)sunknown algorithm `(?:[^']*|.*?)' received\b
+ ^invalid qop `(?:[^']*|.*?)' received\b
+ ^%(auth_type)sinvalid nonce .*? received - user attempted time travel\b
ignoreregex =
@@ -43,14 +44,17 @@ ignoreregex =
# all of these expressions. Lots of submodules like mod_authz_* return back to mod_authz_core
# to return the actual failure.
#
+# Note that URI can contain spaces.
+#
# See also: http://wiki.apache.org/httpd/ListOfErrors
# Expressions that don't have tests and aren't common.
# more be added with https://issues.apache.org/bugzilla/show_bug.cgi?id=55284
-# ^%(_apache_error_client)s (AH01778: )?user .*: nonce expired \([\d.]+ seconds old - max lifetime [\d.]+\) - sending new nonce\s*$
-# ^%(_apache_error_client)s (AH01779: )?user .*: one-time-nonce mismatch - sending new nonce\s*$
-# ^%(_apache_error_client)s (AH02486: )?realm mismatch - got `.*' but no realm specified\s*$
+# ^user .*: nonce expired \([\d.]+ seconds old - max lifetime [\d.]+\) - sending new nonce\s*$
+# ^user .*: one-time-nonce mismatch - sending new nonce\s*$
+# ^realm mismatch - got `(?:[^']*|.*?)' but no realm specified\s*$
#
-# referer is always in error log messages if it exists added as per the log_error_core function in server/log.c
+# Because url/referer are foreign input, short form of regex used if long enough to idetify failure.
#
# Author: Cyril Jaquier
-# Major edits by Daniel Black
+# Major edits by Daniel Black and Ben Rubson.
+# Rewritten for v.0.10 by Sergey Brester (sebres).
diff --git a/config/filter.d/apache-botsearch.conf b/config/filter.d/apache-botsearch.conf
index 5687d405..7def09ac 100644
--- a/config/filter.d/apache-botsearch.conf
+++ b/config/filter.d/apache-botsearch.conf
@@ -23,13 +23,12 @@ before = apache-common.conf
[Definition]
-failregex = ^%(_apache_error_client)s ((AH001(28|30): )?File does not exist|(AH01264: )?script not found or unable to stat): <webroot><block>(, referer: \S+)?\s*$
- ^%(_apache_error_client)s script '<webroot><block>' not found or unable to stat(, referer: \S+)?\s*$
-
-ignoreregex =
+prefregex = ^%(_apache_error_client)s (?:AH\d+: )?<F-CONTENT>.+</F-CONTENT>$
+failregex = ^(?:File does not exist|script not found or unable to stat): <webroot><block>(, referer: \S+)?\s*$
+ ^script '<webroot><block>' not found or unable to stat(, referer: \S+)?\s*$
-[Init]
+ignoreregex =
# Webroot represents the webroot on which all other files are based
webroot = /var/www/
diff --git a/config/filter.d/apache-common.conf b/config/filter.d/apache-common.conf
index 3d1f902b..3eec83d0 100644
--- a/config/filter.d/apache-common.conf
+++ b/config/filter.d/apache-common.conf
@@ -3,12 +3,31 @@
[INCLUDES]
+before = common.conf
# Load customizations if any available
after = apache-common.local
[DEFAULT]
-_apache_error_client = \[\] \[(:?error|\S+:\S+)\]( \[pid \d+(:\S+ \d+)?\])? \[client <HOST>(:\d{1,5})?\]
+# Apache logging mode:
+# all - universal prefix (logfile, syslog)
+# logfile - logfile only
+# syslog - syslog only
+# Use `filter = apache-auth[logging=syslog]` to get more precise regex if apache logs into syslog (ErrorLog syslog).
+# Use `filter = apache-auth[logging=all]` to get universal regex matches both logging variants.
+logging = logfile
+
+# Apache logging prefixes (date-pattern prefix, server, process etc.):
+apache-prefix-syslog = %(__prefix_line)s
+apache-prefix-logfile = \[\]\s
+apache-prefix-all = (?:%(apache-prefix-logfile)s|%(apache-prefix-syslog)s)?
+
+# Setting for __prefix_line (only `logging=syslog`):
+_daemon = (?:apache\d*|httpd(?:/\w+)?)
+
+apache-prefix = <apache-prefix-<logging>>
+
+_apache_error_client = <apache-prefix>\[(:?error|\S+:\S+)\]( \[pid \d+(:\S+ \d+)?\])? \[client <HOST>(:\d{1,5})?\]
datepattern = {^LN-BEG}
diff --git a/config/filter.d/apache-modsecurity.conf b/config/filter.d/apache-modsecurity.conf
index ad7e9b24..e296227a 100644
--- a/config/filter.d/apache-modsecurity.conf
+++ b/config/filter.d/apache-modsecurity.conf
@@ -10,9 +10,10 @@ before = apache-common.conf
[Definition]
-failregex = ^%(_apache_error_client)s ModSecurity: (\[.*?\] )*Access denied with code [45]\d\d.*$
+failregex = ^%(_apache_error_client)s ModSecurity:\s+(?:\[(?:\w+ \"[^\"]*\"|[^\]]*)\]\s*)*Access denied with code [45]\d\d
ignoreregex =
# https://github.com/SpiderLabs/ModSecurity/wiki/ModSecurity-2-Data-Formats
# Author: Daniel Black
+# Sergey G. Brester aka sebres (review, optimization)
diff --git a/config/filter.d/apache-overflows.conf b/config/filter.d/apache-overflows.conf
index 74e44b8e..02a2ef20 100644
--- a/config/filter.d/apache-overflows.conf
+++ b/config/filter.d/apache-overflows.conf
@@ -8,11 +8,15 @@ before = apache-common.conf
[Definition]
-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\b|(?:AH00565: )?request failed: URI too long \(longer than \d+\)|request failed: erroneous characters after protocol string:|(?:AH00566: )?request failed: invalid characters in URI\b)
ignoreregex =
# DEV Notes:
+#
+# [sebres] Because this apache-log could contain very long URLs (and/or referrer),
+# the parsing of it anchored way may be very vulnerable (at least as regards
+# the system resources, see gh-1790). Thus rewritten without end-anchor ($).
#
# fgrep -r 'URI too long' httpd-2.*
# httpd-2.2.25/server/protocol.c: "request failed: URI too long (longer than %d)", r->server->limit_req_line);
diff --git a/config/filter.d/apache-shellshock.conf b/config/filter.d/apache-shellshock.conf
index 39df1704..e2707dc0 100644
--- a/config/filter.d/apache-shellshock.conf
+++ b/config/filter.d/apache-shellshock.conf
@@ -9,8 +9,10 @@ before = apache-common.conf
[Definition]
-failregex = ^%(_apache_error_client)s (AH01215: )?/bin/(ba)?sh: warning: HTTP_.*?: ignoring function definition attempt(, referer: \S+)?\s*$
- ^%(_apache_error_client)s (AH01215: )?/bin/(ba)?sh: error importing function definition for `HTTP_.*?'(, referer: \S+)?\s*$
+prefregex = ^%(_apache_error_client)s (AH01215: )?/bin/([bd]a)?sh: <F-CONTENT>.+</F-CONTENT>$
+
+failregex = ^warning: HTTP_[^:]+: ignoring function definition attempt(, referer: \S+)?\s*$
+ ^error importing function definition for `HTTP_[^']+'(, referer: \S+)?\s*$
ignoreregex =
diff --git a/config/filter.d/assp.conf b/config/filter.d/assp.conf
index 7cca81d2..9837f71d 100644
--- a/config/filter.d/assp.conf
+++ b/config/filter.d/assp.conf
@@ -8,7 +8,7 @@
#
[Definition]
-# Note: First three failregex matches below are for ASSP V1 with the remaining being designed for V2. Deleting the V1 regex is recommended but I left it in for compatibilty reasons.
+# Note: First three failregex matches below are for ASSP V1 with the remaining being designed for V2. Deleting the V1 regex is recommended but I left it in for compatibility reasons.
__assp_actions = (?:dropping|refusing)
diff --git a/config/filter.d/asterisk.conf b/config/filter.d/asterisk.conf
index df55d288..f382e258 100644
--- a/config/filter.d/asterisk.conf
+++ b/config/filter.d/asterisk.conf
@@ -11,23 +11,27 @@ before = common.conf
_daemon = asterisk
-__pid_re = (?:\[\d+\])
+__pid_re = (?:\s*\[\d+\])
iso8601 = \d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}\.\d+[+-]\d{4}
# All Asterisk log messages begin like this:
log_prefix= (?:NOTICE|SECURITY|WARNING)%(__pid_re)s:?(?:\[C-[\da-f]*\])? [^:]+:\d*(?:(?: in)? \w+:)?
-failregex = ^%(__prefix_line)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%(log_prefix)s Call from '[^']*' \(<HOST>:\d+\) to extension '[^']*' rejected because extension not found in context
- ^%(__prefix_line)s%(log_prefix)s Host <HOST> failed to authenticate as '[^']*'$
- ^%(__prefix_line)s%(log_prefix)s No registration for peer '[^']*' \(from <HOST>\)$
- ^%(__prefix_line)s%(log_prefix)s Host <HOST> failed MD5 authentication for '[^']*' \([^)]+\)$
- ^%(__prefix_line)s%(log_prefix)s Failed to authenticate (user|device) [^@]+@<HOST>\S*$
- ^%(__prefix_line)s%(log_prefix)s hacking attempt detected '<HOST>'$
- ^%(__prefix_line)s%(log_prefix)s SecurityEvent="(FailedACL|InvalidAccountID|ChallengeResponseFailed|InvalidPassword)",EventTV="([\d-]+|%(iso8601)s)",Severity="[\w]+",Service="[\w]+",EventVersion="\d+",AccountID="(\d*|<unknown>)",SessionID=".+",LocalAddress="IPV[46]/(UDP|TCP|WS)/[\da-fA-F:.]+/\d+",RemoteAddress="IPV[46]/(UDP|TCP|WS)/<HOST>/\d+"(,Challenge="[\w/]+")?(,ReceivedChallenge="\w+")?(,Response="\w+",ExpectedResponse="\w*")?(,ReceivedHash="[\da-f]+")?(,ACLName="\w+")?$
- ^%(__prefix_line)s%(log_prefix)s "Rejecting unknown SIP connection from <HOST>"$
- ^%(__prefix_line)s%(log_prefix)s Request (?:'[^']*' )?from '[^']*' failed for '<HOST>(?::\d+)?'\s\(callid: [^\)]*\) - (?:No matching endpoint found|Not match Endpoint(?: Contact)? ACL|(?:Failed|Error) to authenticate)\s*$
+prefregex = ^%(__prefix_line)s%(log_prefix)s <F-CONTENT>.+</F-CONTENT>$
+
+failregex = ^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)$
+ ^Call from '[^']*' \(<HOST>:\d+\) to extension '[^']*' rejected because extension not found in context
+ ^(?:Host )?<HOST> (?:failed (?:to authenticate\b|MD5 authentication\b)|tried to authenticate with nonexistent user\b)
+ ^No registration for peer '[^']*' \(from <HOST>\)$
+ ^Failed to authenticate (?:user|device) [^@]+@<HOST>\S*$
+ ^hacking attempt detected '<HOST>'$
+ ^SecurityEvent="(?:FailedACL|InvalidAccountID|ChallengeResponseFailed|InvalidPassword)"(?:(?:,(?!RemoteAddress=)\w+="[^"]*")*|.*?),RemoteAddress="IPV[46]/(UDP|TCP|WS)/<HOST>/\d+"(?:,(?!RemoteAddress=)\w+="[^"]*")*$
+ ^"Rejecting unknown SIP connection from <HOST>"$
+ ^Request (?:'[^']*' )?from '[^']*' failed for '<HOST>(?::\d+)?'\s\(callid: [^\)]*\) - (?:No matching endpoint found|Not match Endpoint(?: Contact)? ACL|(?:Failed|Error) to authenticate)\s*$
+
+# FreePBX (todo: make optional in v.0.10):
+# ^(%(__prefix_line)s|\[\]\s*WARNING%(__pid_re)s:?(?:\[C-[\da-f]*\])? )[^:]+: Friendly Scanner from <HOST>$
ignoreregex =
diff --git a/config/filter.d/botsearch-common.conf b/config/filter.d/botsearch-common.conf
index a673a310..6052fab1 100644
--- a/config/filter.d/botsearch-common.conf
+++ b/config/filter.d/botsearch-common.conf
@@ -5,7 +5,7 @@
# Block is the actual non-found directories to block
block = \/?(<webmail>|<phpmyadmin>|<wordpress>|cgi-bin|mysqladmin)[^,]*
-# These are just convient definitions that assist the blocking of stuff that
+# These are just convenient definitions that assist the blocking of stuff that
# isn't installed
webmail = roundcube|(ext)?mail|horde|(v-?)?webmail
diff --git a/config/filter.d/courier-auth.conf b/config/filter.d/courier-auth.conf
index 87ee55b4..1ac33736 100644
--- a/config/filter.d/courier-auth.conf
+++ b/config/filter.d/courier-auth.conf
@@ -11,7 +11,7 @@ before = common.conf
_daemon = (?:courier)?(?:imapd?|pop3d?)(?:login)?(?:-ssl)?
-failregex = ^%(__prefix_line)sLOGIN FAILED, user=.*, ip=\[<HOST>\]$
+failregex = ^%(__prefix_line)sLOGIN FAILED, (?:user|method)=.*, ip=\[<HOST>\]$
ignoreregex =
diff --git a/config/filter.d/courier-smtp.conf b/config/filter.d/courier-smtp.conf
index fc0afc26..888753c4 100644
--- a/config/filter.d/courier-smtp.conf
+++ b/config/filter.d/courier-smtp.conf
@@ -12,8 +12,10 @@ before = common.conf
_daemon = courieresmtpd
-failregex = ^%(__prefix_line)serror,relay=<HOST>,.*: 550 User (<.*> )?unknown\.?$
- ^%(__prefix_line)serror,relay=<HOST>,msg="535 Authentication failed\.",cmd:( AUTH \S+)?( [0-9a-zA-Z\+/=]+)?(?: \S+)$
+prefregex = ^%(__prefix_line)serror,relay=<HOST>,<F-CONTENT>.+</F-CONTENT>$
+
+failregex = ^[^:]*: 550 User (<.*> )?unknown\.?$
+ ^msg="535 Authentication failed\.",cmd:( AUTH \S+)?( [0-9a-zA-Z\+/=]+)?(?: \S+)$
ignoreregex =
diff --git a/config/filter.d/cyrus-imap.conf b/config/filter.d/cyrus-imap.conf
index 73764d9d..31dfda60 100644
--- a/config/filter.d/cyrus-imap.conf
+++ b/config/filter.d/cyrus-imap.conf
@@ -13,7 +13,7 @@ before = common.conf
_daemon = (?:cyrus/)?(?:imap(d|s)?|pop3(d|s)?)
-failregex = ^%(__prefix_line)sbadlogin: \S+ ?\[<HOST>\] \S+ .*?\[?SASL\(-13\): (authentication failure|user not found): .*\]?$
+failregex = ^%(__prefix_line)sbadlogin: [^\[]*\[<HOST>\] \S+ .*?\[?SASL\(-13\): (authentication failure|user not found): .*\]?$
ignoreregex =
diff --git a/config/filter.d/domino-smtp.conf b/config/filter.d/domino-smtp.conf
new file mode 100644
index 00000000..cdc17736
--- /dev/null
+++ b/config/filter.d/domino-smtp.conf
@@ -0,0 +1,47 @@
+# Fail2Ban configuration file for IBM Domino SMTP Server TASK to detect failed login attempts
+#
+# Author: Christian Brandlehner
+#
+# $Revision: 003 $
+#
+# Configuration:
+# Set the following Domino Server parameters in notes.ini:
+# console_log_enabled=1
+# log_sessions=2
+# You also have to use a date and time format supported by fail2ban. Recommended notes.ini configuration is:
+# DateOrder=DMY
+# DateSeparator=-
+# ClockType=24_Hour
+# TimeSeparator=:
+#
+# Depending on your locale you might have to tweak the date and time format so fail2ban can read the log
+
+#[INCLUDES]
+# Read common prefixes. If any customizations available -- read them from
+# common.local
+#before = common.conf
+
+[Definition]
+# Option: failregex
+# Notes.: regex to match the password failure 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
+#
+# Sample log entries (used different time formats and an extra sample with process info in front of date)
+# 01-23-2009 19:54:51 SMTP Server: Authentication failed for user postmaster ; connecting host 1.2.3.4
+# [28325:00010-3735542592] 22-06-2014 09:56:12 smtp: postmaster [1.2.3.4] authentication failure using internet password
+# 08-09-2014 06:14:27 smtp: postmaster [1.2.3.4] authentication failure using internet password
+# 08-09-2014 06:14:27 SMTP Server: Authentication failed for user postmaster ; connecting host 1.2.3.4
+
+__prefix = (?:\[[^\]]+\])?\s+
+failregex = ^%(__prefix)sSMTP Server: Authentication failed for user .*? \; connecting host <HOST>$
+ ^%(__prefix)ssmtp: (?:[^\[]+ )*\[<HOST>\] authentication failure using internet password\s*$
+# Option: ignoreregex
+# Notes.: regex to ignore. If this regex matches, the line is ignored.
+# Values: TEXT
+#
+
+ignoreregex =
+
diff --git a/config/filter.d/dovecot.conf b/config/filter.d/dovecot.conf
index 6f8510fc..42ab2c88 100644
--- a/config/filter.d/dovecot.conf
+++ b/config/filter.d/dovecot.conf
@@ -7,13 +7,15 @@ before = common.conf
[Definition]
-_daemon = (auth|dovecot(-auth)?|auth-worker)
+_auth_worker = (?:dovecot: )?auth(?:-worker)?
+_daemon = (dovecot(-auth)?|auth)
-failregex = ^%(__prefix_line)s(%(__pam_auth)s(\(dovecot:auth\))?:)?\s+authentication failure; logname=\S* uid=\S* euid=\S* tty=dovecot ruser=\S* rhost=<HOST>(\s+user=\S*)?\s*$
- ^%(__prefix_line)s(pop3|imap)-login: (Info: )?(Aborted login|Disconnected)(: Inactivity)? \(((auth failed, \d+ attempts)( in \d+ secs)?|tried to use (disabled|disallowed) \S+ auth)\):( user=<\S*>,)?( method=\S+,)? rip=<HOST>(, lip=(\d{1,3}\.){3}\d{1,3})?(, TLS( handshaking(: SSL_accept\(\) failed: error:[\dA-F]+:SSL routines:[TLS\d]+_GET_CLIENT_HELLO:unknown protocol)?)?(: Disconnected)?)?(, session=<\S+>)?\s*$
- ^%(__prefix_line)s(Info|dovecot: auth\(default\)|auth-worker\(\d+\)): pam\(\S+,<HOST>\): pam_authenticate\(\) failed: (User not known to the underlying authentication module: \d+ Time\(s\)|Authentication failure \(password mismatch\?\))\s*$
- ^%(__prefix_line)s(auth|auth-worker\(\d+\)): (pam|passwd-file)\(\S+,<HOST>\): unknown user\s*$
- ^%(__prefix_line)s(auth|auth-worker\(\d+\)): Info: ldap\(\S*,<HOST>,\S*\): invalid credentials\s*$
+prefregex = ^%(__prefix_line)s(%(_auth_worker)s(?:\([^\)]+\))?: )?(?:%(__pam_auth)s(?:\(dovecot:auth\))?: |(?:pop3|imap)-login: )?(?:Info: )?<F-CONTENT>.+</F-CONTENT>$
+
+failregex = ^authentication failure; logname=\S* uid=\S* euid=\S* tty=dovecot ruser=\S* rhost=<HOST>(?:\s+user=\S*)?\s*$
+ ^(?:Aborted login|Disconnected)(?::(?: [^ \(]+)+)? \((?:auth failed, \d+ attempts( in \d+ secs)?|tried to use (disabled|disallowed) \S+ auth)\):( user=<[^>]*>,)?( method=\S+,)? rip=<HOST>(?:, lip=\S+)?(?:, TLS(?: handshaking(?:: SSL_accept\(\) failed: error:[\dA-F]+:SSL routines:[TLS\d]+_GET_CLIENT_HELLO:unknown protocol)?)?(: Disconnected)?)?(, session=<\S+>)?\s*$
+ ^pam\(\S+,<HOST>\): pam_authenticate\(\) failed: (User not known to the underlying authentication module: \d+ Time\(s\)|Authentication failure \(password mismatch\?\))\s*$
+ ^[a-z\-]{3,15}\(\S*,<HOST>(?:,\S*)?\): (?:unknown user|invalid credentials)\s*$
ignoreregex =
@@ -31,3 +33,4 @@ datepattern = {^LN-BEG}TAI64N
# Author: Martin Waschbuesch
# Daniel Black (rewrote with begin and end anchors)
# Martin O'Neal (added LDAP authentication failure regex)
+# Sergey G. Brester aka sebres (reviewed, optimized, IPv6-compatibility)
diff --git a/config/filter.d/dropbear.conf b/config/filter.d/dropbear.conf
index 288b0882..930bb128 100644
--- a/config/filter.d/dropbear.conf
+++ b/config/filter.d/dropbear.conf
@@ -23,9 +23,11 @@ before = common.conf
_daemon = dropbear
-failregex = ^%(__prefix_line)s[Ll]ogin attempt for nonexistent user ('.*' )?from <HOST>:\d+$
- ^%(__prefix_line)s[Bb]ad (PAM )?password attempt for .+ from <HOST>(:\d+)?$
- ^%(__prefix_line)s[Ee]xit before auth \(user '.+', \d+ fails\): Max auth tries reached - user '.+' from <HOST>:\d+\s*$
+prefregex = ^%(__prefix_line)s<F-CONTENT>(?:[Ll]ogin|[Bb]ad|[Ee]xit).+</F-CONTENT>$
+
+failregex = ^[Ll]ogin attempt for nonexistent user ('.*' )?from <HOST>:\d+$
+ ^[Bb]ad (PAM )?password attempt for .+ from <HOST>(:\d+)?$
+ ^[Ee]xit before auth \(user '.+', \d+ fails\): Max auth tries reached - user '.+' from <HOST>:\d+\s*$
ignoreregex =
diff --git a/config/filter.d/ejabberd-auth.conf b/config/filter.d/ejabberd-auth.conf
index 56517489..48e82df5 100644
--- a/config/filter.d/ejabberd-auth.conf
+++ b/config/filter.d/ejabberd-auth.conf
@@ -16,8 +16,8 @@
# searched for other failures. This tag can be used multiple times.
# Values: TEXT
#
-failregex = ^=INFO REPORT==== ===\nI\(<0\.\d+\.0>:ejabberd_c2s:\d+\) : \([^)]+\) Failed authentication for .+ from IP <HOST> \({{(?:\d+,){3}\d+},\d+}\)$
- ^(?:\.\d+)? \[info\] <0\.\d+\.\d>@ejabberd_c2s:wait_for_feature_request:\d+ \([^\)]+\) Failed authentication for \S+ from IP <HOST>$
+failregex = ^=INFO REPORT==== ===\nI\(<0\.\d+\.0>:ejabberd_c2s:\d+\) : \([^)]+\) Failed authentication for \S+ from (?:IP )?<HOST>(?: \({{(?:\d+,){3}\d+},\d+}\))?$
+ ^(?:\.\d+)? \[info\] <0\.\d+\.\d>@ejabberd_c2s:\w+:\d+ \([^\)]+\) Failed (?:c2s \w+ )?authentication for \S+ from (?:IP )?(?:::FFFF:)?<HOST>(?:: |$)
# Option: ignoreregex
# Notes.: regex to ignore. If this regex matches, the line is ignored.
diff --git a/config/filter.d/exim-common.conf b/config/filter.d/exim-common.conf
index 0e1b74fa..b3b25750 100644
--- a/config/filter.d/exim-common.conf
+++ b/config/filter.d/exim-common.conf
@@ -9,7 +9,9 @@ after = exim-common.local
[Definition]
-host_info = (?:H=([\w.-]+ )?(?:\(\S+\) )?)?\[<HOST>\](?::\d+)? (?:I=\[\S+\](:\d+)? )?(?:U=\S+ )?(?:P=e?smtp )?
+host_info_pre = (?:H=([\w.-]+ )?(?:\(\S+\) )?)?
+host_info_suf = (?::\d+)?(?: I=\[\S+\](:\d+)?)?(?: U=\S+)?(?: P=e?smtp)?(?: F=(?:<>|[^@]+@\S+))?\s
+host_info = %(host_info_pre)s\[<HOST>\]%(host_info_suf)s
pid = (?: \[\d+\])?
# DEV Notes:
diff --git a/config/filter.d/exim.conf b/config/filter.d/exim.conf
index a1d699c0..2151a161 100644
--- a/config/filter.d/exim.conf
+++ b/config/filter.d/exim.conf
@@ -13,14 +13,17 @@ before = exim-common.conf
[Definition]
+# Fre-filter via "prefregex" is currently inactive because of too different failure syntax in exim-log (testing needed):
+#prefregex = ^%(pid)s <F-CONTENT>\b(?:\w+ authenticator failed|([\w\-]+ )?SMTP (?:(?:call|connection) from|protocol(?: synchronization)? error)|no MAIL in|(?:%(host_info_pre)s\[[^\]]+\]%(host_info_suf)s(?:sender verify fail|rejected RCPT|dropped|AUTH command))).+</F-CONTENT>$
+
failregex = ^%(pid)s %(host_info)ssender verify fail for <\S+>: (?:Unknown user|Unrouteable address|all relevant MX records point to non-existent hosts)\s*$
- ^%(pid)s \w+ authenticator failed for (\S+ )?\(\S+\) \[<HOST>\](?::\d+)?(?: I=\[\S+\](:\d+)?)?: 535 Incorrect authentication data( \(set_id=.*\)|: \d+ Time\(s\))?\s*$
- ^%(pid)s %(host_info)sF=(?:<>|[^@]+@\S+) rejected RCPT [^@]+@\S+: (?:relay not permitted|Sender verify failed|Unknown user)\s*$
+ ^%(pid)s \w+ authenticator failed for (?:[^\[\( ]* )?(?:\(\S*\) )?\[<HOST>\](?::\d+)?(?: I=\[\S+\](:\d+)?)?: 535 Incorrect authentication data( \(set_id=.*\)|: \d+ Time\(s\))?\s*$
+ ^%(pid)s %(host_info)srejected RCPT [^@]+@\S+: (?:relay not permitted|Sender verify failed|Unknown user|Unrouteable address)\s*$
^%(pid)s SMTP protocol synchronization error \([^)]*\): rejected (?:connection from|"\S+") %(host_info)s(?:next )?input=".*"\s*$
^%(pid)s SMTP call from \S+ %(host_info)sdropped: too many nonmail commands \(last was "\S+"\)\s*$
^%(pid)s SMTP protocol error in "AUTH \S*(?: \S*)?" %(host_info)sAUTH command used when not advertised\s*$
- ^%(pid)s no MAIL in SMTP connection from (?:\S* )?(?:\(\S*\) )?%(host_info)sD=\d+s(?: C=\S*)?\s*$
- ^%(pid)s \S+ SMTP connection from (?:\S* )?(?:\(\S*\) )?%(host_info)sclosed by DROP in ACL\s*$
+ ^%(pid)s no MAIL in SMTP connection from (?:[^\[\( ]* )?(?:\(\S*\) )?%(host_info)sD=\d\S+s(?: C=\S*)?\s*$
+ ^%(pid)s (?:[\w\-]+ )?SMTP connection from (?:[^\[\( ]* )?(?:\(\S*\) )?%(host_info)sclosed by DROP in ACL\s*$
ignoreregex =
diff --git a/config/filter.d/froxlor-auth.conf b/config/filter.d/froxlor-auth.conf
index 04003263..d8f3785c 100644
--- a/config/filter.d/froxlor-auth.conf
+++ b/config/filter.d/froxlor-auth.conf
@@ -25,8 +25,11 @@ _daemon = Froxlor
# (?:::f{4,6}:)?(?P<host>[\w\-.^_]+)
# Values: TEXT
#
-failregex = ^%(__prefix_line)s\[Login Action <HOST>\] Unknown user \S* tried to login.$
- ^%(__prefix_line)s\[Login Action <HOST>\] User \S* tried to login with wrong password.$
+
+prefregex = ^%(__prefix_line)s\[Login Action <HOST>\] <F-CONTENT>.+</F-CONTENT>$
+
+failregex = ^Unknown user \S* tried to login.$
+ ^User \S* tried to login with wrong password.$
# Option: ignoreregex
diff --git a/config/filter.d/haproxy-http-auth.conf b/config/filter.d/haproxy-http-auth.conf
index 298ca292..f92f9d67 100644
--- a/config/filter.d/haproxy-http-auth.conf
+++ b/config/filter.d/haproxy-http-auth.conf
@@ -28,7 +28,7 @@ _daemon = haproxy
# (?:::f{4,6}:)?(?P<host>[\w\-.^_]+)
# Values: TEXT
#
-failregex = ^%(__prefix_line)s<HOST>.*<NOSRV> -1/-1/-1/-1/\+*\d* 401
+failregex = ^%(__prefix_line)s<HOST>(?::\d+)?\s+.*<NOSRV> -1/-1/-1/-1/\+*\d* 401
# Option: ignoreregex
# Notes.: regex to ignore. If this regex matches, the line is ignored.
diff --git a/config/filter.d/kerio.conf b/config/filter.d/kerio.conf
index e0d94753..0fde0927 100644
--- a/config/filter.d/kerio.conf
+++ b/config/filter.d/kerio.conf
@@ -3,9 +3,14 @@
[Definition]
failregex = ^ SMTP Spam attack detected from <HOST>,
- ^ IP address <HOST> found in DNS blacklist \S+, mail from \S+ to \S+$
+ ^ IP address <HOST> found in DNS blacklist
^ Relay attempt from IP address <HOST>
^ Attempt to deliver to unknown recipient \S+, from \S+, IP address <HOST>$
+ ^ Failed SMTP login from <HOST>
+ ^ SMTP: User \S+ doesn't exist. Attempt from IP address <HOST>
+ ^ Client with IP address <HOST> has no reverse DNS entry, connection rejected before SMTP greeting$
+ ^ Administration login into Web Administration from <HOST> failed: IP address not allowed$
+ ^ Message from IP address <HOST>, sender \S+ rejected: sender domain does not exist$
ignoreregex =
@@ -14,5 +19,6 @@ datepattern = ^\[%%d/%%b/%%Y %%H:%%M:%%S\]
# DEV NOTES:
#
# Author: A.P. Lawrence
+# Updated by: M. Bischoff <https://github.com/herrbischoff>
#
# Based off: http://aplawrence.com/Kerio/fail2ban.html
diff --git a/config/filter.d/mongodb-auth.conf b/config/filter.d/mongodb-auth.conf
new file mode 100644
index 00000000..66c27abb
--- /dev/null
+++ b/config/filter.d/mongodb-auth.conf
@@ -0,0 +1,49 @@
+# Fail2Ban filter for unsuccesfull MongoDB authentication attempts
+#
+# Logfile /var/log/mongodb/mongodb.log
+#
+# add setting in /etc/mongodb.conf
+# logpath=/var/log/mongodb/mongodb.log
+#
+# and use of the authentication
+# auth = true
+#
+
+[Definition]
+#failregex = ^\s+\[initandlisten\] connection accepted from <HOST>:\d+ \#(?P<__connid>\d+) \(1 connection now open\)<SKIPLINES>\s+\[conn(?P=__connid)\] Failed to authenticate\s+
+failregex = ^\s+\[conn(?P<__connid>\d+)\] Failed to authenticate [^\n]+<SKIPLINES>\s+\[conn(?P=__connid)\] end connection <HOST>
+
+ignoreregex =
+
+
+[Init]
+maxlines = 10
+
+# DEV Notes:
+#
+# Regarding the multiline regex:
+#
+# There can be a nunber of non-related lines between the first and second part
+# of this regex maxlines of 10 is quite generious.
+#
+# Note the capture __connid, includes the connection ID, used in second part of regex.
+#
+# The first regex is commented out (but will match also), because it is better to use
+# the host from "end connection" line (uncommented above):
+# - it has the same prefix, searching begins directly with failure message
+# (so faster, because ignores success connections at all)
+# - it is not so vulnerable in case of possible race condition
+#
+# Log example:
+# 2016-10-20T09:54:27.108+0200 [initandlisten] connection accepted from 127.0.0.1:53276 #1 (1 connection now open)
+# 2016-10-20T09:54:27.109+0200 [conn1] authenticate db: test { authenticate: 1, nonce: "xxx", user: "root", key: "xxx" }
+# 2016-10-20T09:54:27.110+0200 [conn1] Failed to authenticate root@test with mechanism MONGODB-CR: AuthenticationFailed UserNotFound Could not find user root@test
+# 2016-11-09T09:54:27.894+0100 [conn1] end connection 127.0.0.1:53276 (0 connections now open)
+# 2016-11-09T11:55:58.890+0100 [initandlisten] connection accepted from 127.0.0.1:54266 #1510 (1 connection now open)
+# 2016-11-09T11:55:58.892+0100 [conn1510] authenticate db: admin { authenticate: 1, nonce: "xxx", user: "root", key: "xxx" }
+# 2016-11-09T11:55:58.892+0100 [conn1510] Failed to authenticate root@admin with mechanism MONGODB-CR: AuthenticationFailed key mismatch
+# 2016-11-09T11:55:58.894+0100 [conn1510] end connection 127.0.0.1:54266 (0 connections now open)
+#
+# Authors: Alexander Finkhäuser
+# Sergey G. Brester (sebres)
+
diff --git a/config/filter.d/murmur.conf b/config/filter.d/murmur.conf
index 507bbd2f..f5f100a6 100644
--- a/config/filter.d/murmur.conf
+++ b/config/filter.d/murmur.conf
@@ -17,8 +17,10 @@ _usernameregex = [^>]+
_prefix = \s+\d+ => <\d+:%(_usernameregex)s\(-1\)> Rejected connection from <HOST>:\d+:
-failregex = ^%(_prefix)s Invalid server password$
- ^%(_prefix)s Wrong certificate or password for existing user$
+prefregex = ^%(_prefix)s <F-CONTENT>.+</F-CONTENT>$
+
+failregex = ^Invalid server password$
+ ^Wrong certificate or password for existing user$
ignoreregex =
diff --git a/config/filter.d/mysqld-auth.conf b/config/filter.d/mysqld-auth.conf
index 3ad70cb7..31bd2056 100644
--- a/config/filter.d/mysqld-auth.conf
+++ b/config/filter.d/mysqld-auth.conf
@@ -1,4 +1,4 @@
-# Fail2Ban filter for unsuccesfull MySQL authentication attempts
+# Fail2Ban filter for unsuccesful MySQL authentication attempts
#
#
# To log wrong MySQL access attempts add to /etc/my.cnf in [mysqld]:
diff --git a/config/filter.d/named-refused.conf b/config/filter.d/named-refused.conf
index eec3d667..2e14d442 100644
--- a/config/filter.d/named-refused.conf
+++ b/config/filter.d/named-refused.conf
@@ -34,9 +34,11 @@ __daemon_combs_re=(?:%(__pid_re)s?:\s+%(__daemon_re)s|%(__daemon_re)s%(__pid_re)
# this can be optional (for instance if we match named native log files)
__line_prefix=(?:\s\S+ %(__daemon_combs_re)s\s+)?
-failregex = ^%(__line_prefix)s( error:)?\s*client <HOST>#\S+( \([\S.]+\))?: (view (internal|external): )?query(?: \(cache\))? '.*' denied\s*$
- ^%(__line_prefix)s( error:)?\s*client <HOST>#\S+( \([\S.]+\))?: zone transfer '\S+/AXFR/\w+' denied\s*$
- ^%(__line_prefix)s( error:)?\s*client <HOST>#\S+( \([\S.]+\))?: bad zone transfer request: '\S+/IN': non-authoritative zone \(NOTAUTH\)\s*$
+prefregex = ^%(__line_prefix)s( error:)?\s*client <HOST>#\S+( \([\S.]+\))?: <F-CONTENT>.+</F-CONTENT>$
+
+failregex = ^(view (internal|external): )?query(?: \(cache\))? '.*' denied\s*$
+ ^zone transfer '\S+/AXFR/\w+' denied\s*$
+ ^bad zone transfer request: '\S+/IN': non-authoritative zone \(NOTAUTH\)\s*$
ignoreregex =
diff --git a/config/filter.d/pam-generic.conf b/config/filter.d/pam-generic.conf
index e0d4e9c1..ff4ea802 100644
--- a/config/filter.d/pam-generic.conf
+++ b/config/filter.d/pam-generic.conf
@@ -16,7 +16,12 @@ _ttys_re=\S*
__pam_re=\(?%(__pam_auth)s(?:\(\S+\))?\)?:?
_daemon = \S+
-failregex = ^%(__prefix_line)s%(__pam_re)s\s+authentication failure; logname=\S* uid=\S* euid=\S* tty=%(_ttys_re)s ruser=\S* rhost=<HOST>(?:\s+user=.*)?\s*$
+prefregex = ^%(__prefix_line)s%(__pam_re)s\s+authentication failure; logname=\S* uid=\S* euid=\S* tty=%(_ttys_re)s <F-CONTENT>.+</F-CONTENT>$
+
+failregex = ^ruser=<F-USER>\S*</F-USER> rhost=<HOST>\s*$
+ ^ruser= rhost=<HOST>\s+user=<F-USER>\S*</F-USER>\s*$
+ ^ruser= rhost=<HOST>\s+user=<F-USER>.*?</F-USER>\s*$
+ ^ruser=<F-USER>.*?</F-USER> rhost=<HOST>\s*$
ignoreregex =
diff --git a/config/filter.d/postfix-rbl.conf b/config/filter.d/postfix-rbl.conf
deleted file mode 100644
index c3f8c332..00000000
--- a/config/filter.d/postfix-rbl.conf
+++ /dev/null
@@ -1,19 +0,0 @@
-# Fail2Ban filter for Postfix's RBL based Blocked hosts
-#
-#
-
-[INCLUDES]
-
-# Read common prefixes. If any customizations available -- read them from
-# common.local
-before = common.conf
-
-[Definition]
-
-_daemon = postfix(-\w+)?/smtpd
-
-failregex = ^%(__prefix_line)sNOQUEUE: reject: RCPT from \S+\[<HOST>\]: 454 4\.7\.1 Service unavailable; Client host \[\S+\] blocked using .* from=<\S*> to=<\S+> proto=ESMTP helo=<\S*>$
-
-ignoreregex =
-
-# Author: Lee Clemens
diff --git a/config/filter.d/postfix-sasl.conf b/config/filter.d/postfix-sasl.conf
deleted file mode 100644
index 1a24ca94..00000000
--- a/config/filter.d/postfix-sasl.conf
+++ /dev/null
@@ -1,21 +0,0 @@
-# Fail2Ban filter for postfix authentication failures
-#
-
-[INCLUDES]
-
-before = common.conf
-
-[Definition]
-
-_daemon = postfix(-\w+)?/(?:submission/|smtps/)?smtp[ds]
-
-failregex = ^%(__prefix_line)swarning: [-._\w]+\[<HOST>\]: SASL ((?i)LOGIN|PLAIN|(?:CRAM|DIGEST)-MD5) authentication failed(:[ A-Za-z0-9+/:]*={0,2})?\s*$
-
-ignoreregex = authentication failed: Connection lost to authentication server$
-
-[Init]
-
-journalmatch = _SYSTEMD_UNIT=postfix.service
-
-
-# Author: Yaroslav Halchenko
diff --git a/config/filter.d/postfix.conf b/config/filter.d/postfix.conf
index 3051409b..b86b3d4d 100644
--- a/config/filter.d/postfix.conf
+++ b/config/filter.d/postfix.conf
@@ -10,15 +10,57 @@ before = common.conf
[Definition]
-_daemon = postfix(-\w+)?/(?:submission/|smtps/)?smtp[ds]
-
-failregex = ^%(__prefix_line)sNOQUEUE: reject: RCPT from \S+\[<HOST>\]: 554 5\.7\.1 .*$
- ^%(__prefix_line)sNOQUEUE: reject: RCPT from \S+\[<HOST>\]: 450 4\.7\.1 Client host rejected: cannot find your hostname, (\[\S*\]); from=<\S*> to=<\S+> proto=ESMTP helo=<\S*>$
- ^%(__prefix_line)sNOQUEUE: reject: RCPT from \S+\[<HOST>\]: 450 4\.7\.1 : Helo command rejected: Host not found; from=<> to=<> proto=ESMTP helo= *$
- ^%(__prefix_line)sNOQUEUE: reject: EHLO from \S+\[<HOST>\]: 504 5\.5\.2 <\S+>: Helo command rejected: need fully-qualified hostname;
- ^%(__prefix_line)sNOQUEUE: reject: VRFY from \S+\[<HOST>\]: 550 5\.1\.1 .*$
- ^%(__prefix_line)sNOQUEUE: reject: RCPT from \S+\[<HOST>\]: 450 4\.1\.8 <\S*>: Sender address rejected: Domain not found; from=<\S*> to=<\S+> proto=ESMTP helo=<\S*>$
- ^%(__prefix_line)simproper command pipelining after \S+ from [^[]*\[<HOST>\]:?$
+_daemon = postfix(-\w+)?/\w+(?:/smtp[ds])?
+_port = (?::\d+)?
+
+prefregex = ^%(__prefix_line)s<mdpr-<mode>> <F-CONTENT>.+</F-CONTENT>$
+
+mdpr-normal = (?:NOQUEUE: reject:|improper command pipelining after \S+)
+mdre-normal=^RCPT from [^[]*\[<HOST>\]<_port>: 55[04] 5\.7\.1\s
+ ^RCPT from [^[]*\[<HOST>\]<_port>: 45[04] 4\.7\.1 (?:Service unavailable\b|Client host rejected: cannot find your (reverse )?hostname\b)
+ ^RCPT from [^[]*\[<HOST>\]<_port>: 450 4\.7\.1 (<[^>]*>)?: Helo command rejected: Host not found\b
+ ^EHLO from [^[]*\[<HOST>\]<_port>: 504 5\.5\.2 (<[^>]*>)?: Helo command rejected: need fully-qualified hostname\b
+ ^VRFY from [^[]*\[<HOST>\]<_port>: 550 5\.1\.1\s
+ ^RCPT from [^[]*\[<HOST>\]<_port>: 450 4\.1\.8 (<[^>]*>)?: Sender address rejected: Domain not found\b
+ ^from [^[]*\[<HOST>\]:?
+
+mdpr-auth = warning:
+mdre-auth = ^[^[]*\[<HOST>\]: SASL ((?i)LOGIN|PLAIN|(?:CRAM|DIGEST)-MD5) authentication failed:(?! Connection lost to authentication server| Invalid authentication mechanism)
+mdre-auth2= ^[^[]*\[<HOST>\]: SASL ((?i)LOGIN|PLAIN|(?:CRAM|DIGEST)-MD5) authentication failed:(?! Connection lost to authentication server)
+# todo: check/remove "Invalid authentication mechanism" from ignore list, if gh-1243 will get finished (see gh-1297).
+
+# Mode "rbl" currently included in mode "normal", but if needed for jail "postfix-rbl" only:
+mdpr-rbl = %(mdpr-normal)s
+mdre-rbl = ^RCPT from [^[]*\[<HOST>\]: [45]54 [45]\.7\.1 Service unavailable; Client host \[\S+\] blocked\b
+
+# Mode "rbl" currently included in mode "normal" (within 1st rule)
+mdpr-more = %(mdpr-normal)s
+mdre-more = %(mdre-normal)s
+
+mdpr-ddos = lost connection after(?! DATA) [A-Z]+
+mdre-ddos = ^from [^[]*\[<HOST>\]:?
+
+mdpr-extra = (?:%(mdpr-auth)s|%(mdpr-normal)s)
+mdre-extra = %(mdre-auth)s
+ %(mdre-normal)s
+
+mdpr-aggressive = (?:%(mdpr-auth)s|%(mdpr-normal)s|%(mdpr-ddos)s)
+mdre-aggressive = %(mdre-auth2)s
+ %(mdre-normal)s
+
+
+
+failregex = <mdre-<mode>>
+
+# Parameter "mode": more (default combines normal and rbl), auth, normal, rbl, ddos, extra or aggressive (combines all)
+# Usage example (for jail.local):
+# [postfix]
+# mode = aggressive
+# # or another jail (rewrite filter parameters of jail):
+# [postfix-rbl]
+# filter = postfix[mode=rbl]
+#
+mode = more
ignoreregex =
diff --git a/config/filter.d/proftpd.conf b/config/filter.d/proftpd.conf
index 4bc0ba01..a7bd2837 100644
--- a/config/filter.d/proftpd.conf
+++ b/config/filter.d/proftpd.conf
@@ -16,12 +16,19 @@ _daemon = proftpd
__suffix_failed_login = (User not authorized for login|No such user found|Incorrect password|Password expired|Account disabled|Invalid shell: '\S+'|User in \S+|Limit (access|configuration) denies login|Not a UserAlias|maximum login length exceeded).?
-failregex = ^%(__prefix_line)s%(__hostname)s \(\S+\[<HOST>\]\)[: -]+ USER .*: no such user found from \S+ \[\S+\] to \S+:\S+ *$
- ^%(__prefix_line)s%(__hostname)s \(\S+\[<HOST>\]\)[: -]+ USER .* \(Login failed\): %(__suffix_failed_login)s\s*$
- ^%(__prefix_line)s%(__hostname)s \(\S+\[<HOST>\]\)[: -]+ SECURITY VIOLATION: .* login attempted\. *$
- ^%(__prefix_line)s%(__hostname)s \(\S+\[<HOST>\]\)[: -]+ Maximum login attempts \(\d+\) exceeded *$
+
+prefregex = ^%(__prefix_line)s%(__hostname)s \(\S+\[<HOST>\]\)[: -]+ <F-CONTENT>(?:USER|SECURITY|Maximum).+</F-CONTENT>$
+
+
+failregex = ^USER .*: no such user found from \S+ \[\S+\] to \S+:\S+ *$
+ ^USER .* \(Login failed\): %(__suffix_failed_login)s\s*$
+ ^SECURITY VIOLATION: .* login attempted\. *$
+ ^Maximum login attempts \(\d+\) exceeded *$
ignoreregex =
+[Init]
+journalmatch = _SYSTEMD_UNIT=proftpd.service
+
# Author: Yaroslav Halchenko
# Daniel Black - hardening of regex
diff --git a/config/filter.d/roundcube-auth.conf b/config/filter.d/roundcube-auth.conf
index 886cf2d6..9912ff47 100644
--- a/config/filter.d/roundcube-auth.conf
+++ b/config/filter.d/roundcube-auth.conf
@@ -13,10 +13,15 @@ before = common.conf
[Definition]
-failregex = ^\s*(\[\])?(%(__hostname)s\s*(roundcube:)?\s*(<[\w]+>)? IMAP Error)?: (FAILED login|Login failed) for .*? from <HOST>(\. .* in .*?/rcube_imap\.php on line \d+ \(\S+ \S+\))?$
- ^\[\]:\s*(<[\w]+>)? Failed login for [\w\-\.\+]+(@[\w\-\.\+]+\.[a-zA-Z]{2,6})? from <HOST> in session \w+( \(error: \d\))?$
+prefregex = ^\s*(\[\])?(%(__hostname)s\s*(?:roundcube(?:\[(\d*)\])?:)?\s*(<[\w]+>)? IMAP Error)?: <F-CONTENT>.+</F-CONTENT>$
+
+failregex = ^(?:FAILED login|Login failed) for <F-USER>.*</F-USER> from <HOST>(?:(?:\([^\)]*\))?\. (?:(?! from ).)*(?: user=(?P=user))? in \S+\.php on line \d+ \(\S+ \S+\))?$
+ ^(?:<[\w]+> )?Failed login for <F-USER>.*</F-USER> from <HOST> in session \w+( \(error: \d\))?$
ignoreregex =
+
+journalmatch = SYSLOG_IDENTIFIER=roundcube
+
# DEV Notes:
#
# Source: https://github.com/roundcube/roundcubemail/blob/master/program/lib/Roundcube/rcube_imap.php#L180
diff --git a/config/filter.d/sendmail-reject.conf b/config/filter.d/sendmail-reject.conf
index 20d3648e..0793a99b 100644
--- a/config/filter.d/sendmail-reject.conf
+++ b/config/filter.d/sendmail-reject.conf
@@ -21,30 +21,45 @@ before = common.conf
_daemon = (?:(sm-(mta|acceptingconnections)|sendmail))
-failregex = ^%(__prefix_line)s\w{14}: ruleset=check_rcpt, arg1=(?P<email><\S+@\S+>), relay=(\S+ )?\[<HOST>\]( \(may be forged\))?, reject=(550 5\.7\.1 (?P=email)\.\.\. Relaying denied\. (IP name possibly forged \[(\d+\.){3}\d+\]|Proper authentication required\.|IP name lookup failed \[(\d+\.){3}\d+\])|553 5\.1\.8 (?P=email)\.\.\. Domain of sender address \S+ does not exist|550 5\.[71]\.1 (?P=email)\.\.\. (Rejected: .*|User unknown))$
- ^%(__prefix_line)sruleset=check_relay, arg1=(?P<dom>\S+), arg2=<HOST>, relay=((?P=dom) )?\[(\d+\.){3}\d+\]( \(may be forged\))?, reject=421 4\.3\.2 (Connection rate limit exceeded\.|Too many open connections\.)$
- ^%(__prefix_line)s\w{14}: rejecting commands from (\S* )?\[<HOST>\] due to pre-greeting traffic after \d+ seconds$
- ^%(__prefix_line)s\w{14}: (\S+ )?\[<HOST>\]: ((?i)expn|vrfy) \S+ \[rejected\]$
- ^(?P<__prefix>%(__prefix_line)s\w+: )<[^@]+@[^>]+>\.\.\. No such user here<SKIPLINES>(?P=__prefix)from=<[^@]+@[^>]+>, size=\d+, class=\d+, nrcpts=\d+, bodytype=\w+, proto=E?SMTP, daemon=MTA, relay=\S+ \[<HOST>\]$
+prefregex = ^<F-MLFID>%(__prefix_line)s(?:\w{14}: )?</F-MLFID><F-CONTENT>.+</F-CONTENT>$
+cmnfailre = ^ruleset=check_rcpt, arg1=(?P<email><\S+@\S+>), relay=(\S+ )?\[<HOST>\](?: \(may be forged\))?, reject=(550 5\.7\.1 (?P=email)\.\.\. Relaying denied\. (IP name possibly forged \[(\d+\.){3}\d+\]|Proper authentication required\.|IP name lookup failed \[(\d+\.){3}\d+\])|553 5\.1\.8 (?P=email)\.\.\. Domain of sender address \S+ does not exist|550 5\.[71]\.1 (?P=email)\.\.\. (Rejected: .*|User unknown))$
+ ^ruleset=check_relay, arg1=(?P<dom>\S+), arg2=<HOST>, relay=((?P=dom) )?\[(\d+\.){3}\d+\](?: \(may be forged\))?, reject=421 4\.3\.2 (Connection rate limit exceeded\.|Too many open connections\.)$
+ ^rejecting commands from (\S* )?\[<HOST>\] due to pre-greeting traffic after \d+ seconds$
+ ^(?:\S+ )?\[<HOST>\]: (?:(?i)expn|vrfy) \S+ \[rejected\]$
+ ^<[^@]+@[^>]+>\.\.\. No such user here$
+ ^<F-NOFAIL>from=<[^@]+@[^>]+></F-NOFAIL>, size=\d+, class=\d+, nrcpts=\d+, bodytype=\w+, proto=E?SMTP, daemon=MTA, relay=\S+ \[<HOST>\]$
-ignoreregex =
+mdre-normal =
+mdre-extra = ^(?:\S+ )?\[<HOST>\](?: \(may be forged\))? did not issue (?:[A-Z]{4}[/ ]?)+during connection to M(?:TA|SP)(?:-\w+)?$
-[Init]
+mdre-aggressive = %(mdre-extra)s
+
+failregex = %(cmnfailre)s
+ <mdre-<mode>>
+
+# Parameter "mode": normal (default), extra or aggressive
+# Usage example (for jail.local):
+# [sendmail-reject]
+# filter = sendmail-reject[mode=extra]
+#
+mode = normal
+
+ignoreregex =
-# "maxlines" is number of log lines to buffer for multi-line regex searches
-maxlines = 10
# DEV NOTES:
#
-# Regarding the last multiline regex:
+# Regarding the multiline regex:
#
-# There can be a nunber of non-related lines between the first and second part
-# of this regex maxlines of 10 is quite generious. Only one of the
-# "No such user" lines needs to be matched before the line with the HOST.
+# "No such user" lines generate a failure and needs to be matched together with
+# another line with the HOST, therefore no-failure line was added as regex, that
+# contains HOST (see line with tag <F-NOFAIL>).
#
-# Note the capture __prefix, includes both the __prefix_lines (which includes
-# the sendmail PID), but also the \w+ which the the sendmail assigned mail ID.
+# Note the capture <F-MLFID>, includes both the __prefix_lines (which includes
+# the sendmail PID), but also the `\w{14}` which the the sendmail assigned
+# mail ID (todo: check this is necessary, possible obsolete).
#
-# Author: Daniel Black and Fabian Wenk
+# Author: Daniel Black, Fabian Wenk and Sergey Brester aka sebres.
+# Rewritten using prefregex by Serg G. Brester.
diff --git a/config/filter.d/sshd-ddos.conf b/config/filter.d/sshd-ddos.conf
deleted file mode 100644
index 4f71c7f3..00000000
--- a/config/filter.d/sshd-ddos.conf
+++ /dev/null
@@ -1,29 +0,0 @@
-# Fail2Ban ssh filter for at attempted exploit
-#
-# The regex here also relates to a exploit:
-#
-# http://www.securityfocus.com/bid/17958/exploit
-# The example code here shows the pushing of the exploit straight after
-# reading the server version. This is where the client version string normally
-# pushed. As such the server will read this unparsible information as
-# "Did not receive identification string".
-
-[INCLUDES]
-
-# Read common prefixes. If any customizations available -- read them from
-# common.local
-before = common.conf
-
-[Definition]
-
-_daemon = sshd
-
-failregex = ^%(__prefix_line)sDid not receive identification string from <HOST>\s*$
-
-ignoreregex =
-
-[Init]
-
-journalmatch = _SYSTEMD_UNIT=sshd.service + _COMM=sshd
-
-# Author: Yaroslav Halchenko
diff --git a/config/filter.d/sshd.conf b/config/filter.d/sshd.conf
index a425de1f..95915fcc 100644
--- a/config/filter.d/sshd.conf
+++ b/config/filter.d/sshd.conf
@@ -14,32 +14,74 @@
# common.local
before = common.conf
-[Definition]
+[DEFAULT]
_daemon = sshd
-failregex = ^%(__prefix_line)s(?:error: PAM: )?[aA]uthentication (?:failure|error|failed) for .* from <HOST>( via \S+)?\s*$
- ^%(__prefix_line)s(?:error: PAM: )?User not known to the underlying authentication module for .* from <HOST>\s*$
- ^%(__prefix_line)sFailed \S+ for (?P<cond_inv>invalid user )?(?P<user>(?P<cond_user>\S+)|(?(cond_inv)(?:(?! from ).)*?|[^:]+)) from <HOST>(?: port \d+)?(?: ssh\d*)?(?(cond_user):|(?:(?:(?! from ).)*)$)
- ^%(__prefix_line)sROOT LOGIN REFUSED.* FROM <HOST>\s*$
- ^%(__prefix_line)s[iI](?:llegal|nvalid) user .* from <HOST>\s*$
- ^%(__prefix_line)sUser .+ from <HOST> not allowed because not listed in AllowUsers\s*$
- ^%(__prefix_line)sUser .+ from <HOST> not allowed because listed in DenyUsers\s*$
- ^%(__prefix_line)sUser .+ from <HOST> not allowed because not in any group\s*$
- ^%(__prefix_line)srefused connect from \S+ \(<HOST>\)\s*$
- ^%(__prefix_line)s(?:error: )?Received disconnect from <HOST>: 3: .*: Auth fail(?: \[preauth\])?$
- ^%(__prefix_line)sUser .+ from <HOST> not allowed because a group is listed in DenyGroups\s*$
- ^%(__prefix_line)sUser .+ from <HOST> not allowed because none of user's groups are listed in AllowGroups\s*$
- ^(?P<__prefix>%(__prefix_line)s)User .+ not allowed because account is locked<SKIPLINES>(?P=__prefix)(?:error: )?Received disconnect from <HOST>: 11: .+ \[preauth\]$
- ^(?P<__prefix>%(__prefix_line)s)Disconnecting: Too many authentication failures for .+? \[preauth\]<SKIPLINES>(?P=__prefix)(?:error: )?Connection closed by <HOST> \[preauth\]$
- ^(?P<__prefix>%(__prefix_line)s)Connection from <HOST> port \d+(?: on \S+ port \d+)?<SKIPLINES>(?P=__prefix)Disconnecting: Too many authentication failures for .+? \[preauth\]$
- ^%(__prefix_line)s(error: )?maximum authentication attempts exceeded for .* from <HOST>(?: port \d*)?(?: ssh\d*)? \[preauth\]$
- ^%(__prefix_line)spam_unix\(sshd:auth\):\s+authentication failure;\s*logname=\S*\s*uid=\d*\s*euid=\d*\s*tty=\S*\s*ruser=\S*\s*rhost=<HOST>\s.*$
+# optional prefix (logged from several ssh versions) like "error: ", "error: PAM: " or "fatal: "
+__pref = (?:(?:error|fatal): (?:PAM: )?)?
+# optional suffix (logged from several ssh versions) like " [preauth]"
+__suff = (?: \[preauth\])?\s*
+__on_port_opt = (?: port \d+)?(?: on \S+(?: port \d+)?)?
+
+[Definition]
+
+prefregex = ^<F-MLFID>%(__prefix_line)s</F-MLFID>%(__pref)s<F-CONTENT>.+</F-CONTENT>$
+
+cmnfailre = ^[aA]uthentication (?:failure|error|failed) for <F-USER>.*</F-USER> from <HOST>( via \S+)?\s*%(__suff)s$
+ ^User not known to the underlying authentication module for <F-USER>.*</F-USER> from <HOST>\s*%(__suff)s$
+ ^Failed \S+ for (?P<cond_inv>invalid user )?<F-USER>(?P<cond_user>\S+)|(?(cond_inv)(?:(?! from ).)*?|[^:]+)</F-USER> from <HOST>%(__on_port_opt)s(?: ssh\d*)?(?(cond_user): |(?:(?:(?! from ).)*)$)
+ ^<F-USER>ROOT</F-USER> LOGIN REFUSED.* FROM <HOST>\s*%(__suff)s$
+ ^[iI](?:llegal|nvalid) user <F-USER>.*?</F-USER> from <HOST>%(__on_port_opt)s\s*$
+ ^User <F-USER>.+</F-USER> from <HOST> not allowed because not listed in AllowUsers\s*%(__suff)s$
+ ^User <F-USER>.+</F-USER> from <HOST> not allowed because listed in DenyUsers\s*%(__suff)s$
+ ^User <F-USER>.+</F-USER> from <HOST> not allowed because not in any group\s*%(__suff)s$
+ ^refused connect from \S+ \(<HOST>\)\s*%(__suff)s$
+ ^Received <F-MLFFORGET>disconnect</F-MLFFORGET> from <HOST>%(__on_port_opt)s:\s*3: .*: Auth fail%(__suff)s$
+ ^User <F-USER>.+</F-USER> from <HOST> not allowed because a group is listed in DenyGroups\s*%(__suff)s$
+ ^User <F-USER>.+</F-USER> from <HOST> not allowed because none of user's groups are listed in AllowGroups\s*%(__suff)s$
+ ^pam_unix\(sshd:auth\):\s+authentication failure;\s*logname=\S*\s*uid=\d*\s*euid=\d*\s*tty=\S*\s*ruser=<F-USER>\S*</F-USER>\s*rhost=<HOST>\s.*%(__suff)s$
+ ^(error: )?maximum authentication attempts exceeded for <F-USER>.*</F-USER> from <HOST>%(__on_port_opt)s(?: ssh\d*)?%(__suff)s$
+ ^User <F-USER>.+</F-USER> not allowed because account is locked%(__suff)s
+ ^<F-MLFFORGET>Disconnecting</F-MLFFORGET>: Too many authentication failures(?: for <F-USER>.+?</F-USER>)?%(__suff)s
+ ^<F-NOFAIL>Received <F-MLFFORGET>disconnect</F-MLFFORGET></F-NOFAIL> from <HOST>: 11:
+ ^<F-NOFAIL>Connection <F-MLFFORGET>closed</F-MLFFORGET></F-NOFAIL> by <HOST>%(__suff)s$
+
+mdre-normal =
+
+mdre-ddos = ^Did not receive identification string from <HOST>%(__suff)s$
+ ^Connection <F-MLFFORGET>reset</F-MLFFORGET> by <HOST>%(__on_port_opt)s%(__suff)s
+ ^<F-NOFAIL>SSH: Server;Ltype:</F-NOFAIL> (?:Authname|Version|Kex);Remote: <HOST>-\d+;[A-Z]\w+:
+ ^Read from socket failed: Connection <F-MLFFORGET>reset</F-MLFFORGET> by peer%(__suff)s
+
+mdre-extra = ^Received <F-MLFFORGET>disconnect</F-MLFFORGET> from <HOST>%(__on_port_opt)s:\s*14: No supported authentication methods available%(__suff)s$
+ ^Unable to negotiate with <HOST>%(__on_port_opt)s: no matching (?:cipher|key exchange method) found.
+ ^Unable to negotiate a (?:cipher|key exchange method)%(__suff)s$
+
+mdre-aggressive = %(mdre-ddos)s
+ %(mdre-extra)s
+
+cfooterre = ^<F-NOFAIL>Connection from</F-NOFAIL> <HOST>
+
+failregex = %(cmnfailre)s
+ <mdre-<mode>>
+ %(cfooterre)s
+
+# Parameter "mode": normal (default), ddos, extra or aggressive (combines all)
+# Usage example (for jail.local):
+# [sshd]
+# mode = extra
+# # or another jail (rewrite filter parameters of jail):
+# [sshd-aggressive]
+# filter = sshd[mode=aggressive]
+#
+mode = normal
+
+#filter = sshd[mode=aggressive]
ignoreregex =
-# "maxlines" is number of log lines to buffer for multi-line regex searches
-maxlines = 10
+maxlines = 1
journalmatch = _SYSTEMD_UNIT=sshd.service + _COMM=sshd
@@ -52,5 +94,5 @@ datepattern = {^LN-BEG}
# and later catch-all's could contain user-provided input, which need to be greedily
# matched away first.
#
-# Author: Cyril Jaquier, Yaroslav Halchenko, Petr Voralek, Daniel Black
-
+# Author: Cyril Jaquier, Yaroslav Halchenko, Petr Voralek, Daniel Black and Sergey Brester aka sebres
+# Rewritten using prefregex (and introduced "mode" parameter) by Serg G. Brester.
diff --git a/config/filter.d/suhosin.conf b/config/filter.d/suhosin.conf
index f125eadc..46fbe381 100644
--- a/config/filter.d/suhosin.conf
+++ b/config/filter.d/suhosin.conf
@@ -17,7 +17,7 @@ _daemon = (?:lighttpd|suhosin)
_lighttpd_prefix = (?:\(mod_fastcgi\.c\.\d+\) FastCGI-stderr:\s)
-failregex = ^%(__prefix_line)s%(_lighttpd_prefix)s?ALERT - .* \(attacker '<HOST>', file '.*'(?:, line \d+)?\)$
+failregex = ^%(__prefix_line)s%(_lighttpd_prefix)s?ALERT - .*? \(attacker '<HOST>', file '[^']*'(?:, line \d+)?\)$
ignoreregex =
diff --git a/config/filter.d/xinetd-fail.conf b/config/filter.d/xinetd-fail.conf
index d75e3d66..b4093d98 100644
--- a/config/filter.d/xinetd-fail.conf
+++ b/config/filter.d/xinetd-fail.conf
@@ -14,8 +14,10 @@ before = common.conf
_daemon = xinetd
-failregex = ^%(__prefix_line)sFAIL: \S+ address from=<HOST>$
- ^%(__prefix_line)sFAIL: \S+ libwrap from=<HOST>$
+prefregex = ^%(__prefix_line)sFAIL: <F-CONTENT>.+</F-CONTENT>$
+
+failregex = ^\S+ address from=<HOST>$
+ ^\S+ libwrap from=<HOST>$
ignoreregex =