mirror of https://github.com/fail2ban/fail2ban
Regex compiled in multi-line parsing mode only if `maxlines` > 1 (buffering), if however expected - prefix `(?m)` could be used in regex to enable it;
Removed warning "Mutliline regex set for jail ... but maxlines not greater than 1", because can be expected situation now: non multi-line entry from systemd-filter containing new-lines (that should be ignored by anchors resp. entry parsed as single string); small code review;pull/1733/head
parent
61c1bdfe79
commit
bc888e0753
|
@ -111,9 +111,8 @@ class Regex:
|
||||||
#
|
#
|
||||||
if regex.lstrip() == '':
|
if regex.lstrip() == '':
|
||||||
raise RegexException("Cannot add empty regex")
|
raise RegexException("Cannot add empty regex")
|
||||||
flags = re.MULTILINE if (multiline or "\n" in regex or r"\n" in regex) else 0
|
|
||||||
try:
|
try:
|
||||||
self._regexObj = re.compile(regex, flags)
|
self._regexObj = re.compile(regex, re.MULTILINE if multiline else 0)
|
||||||
self._regex = regex
|
self._regex = regex
|
||||||
except sre_constants.error:
|
except sre_constants.error:
|
||||||
raise RegexException("Unable to compile regular expression '%s'" %
|
raise RegexException("Unable to compile regular expression '%s'" %
|
||||||
|
@ -122,11 +121,6 @@ class Regex:
|
||||||
def __str__(self):
|
def __str__(self):
|
||||||
return "%s(%r)" % (self.__class__.__name__, self._regex)
|
return "%s(%r)" % (self.__class__.__name__, self._regex)
|
||||||
|
|
||||||
@property
|
|
||||||
def flags(self):
|
|
||||||
"""Returns the regex matching flags combination of the compiled regex object"""
|
|
||||||
return self._regexObj.flags
|
|
||||||
|
|
||||||
##
|
##
|
||||||
# Replaces "<HOST>", "<IP4>", "<IP6>", "<FID>" with default regular expression for host
|
# Replaces "<HOST>", "<IP4>", "<IP6>", "<FID>" with default regular expression for host
|
||||||
#
|
#
|
||||||
|
|
|
@ -166,12 +166,6 @@ class Filter(JailThread):
|
||||||
regex = FailRegex(value, prefRegex=self.__prefRegex, multiline=multiLine,
|
regex = FailRegex(value, prefRegex=self.__prefRegex, multiline=multiLine,
|
||||||
useDns=self.__useDns)
|
useDns=self.__useDns)
|
||||||
self.__failRegex.append(regex)
|
self.__failRegex.append(regex)
|
||||||
regexExpr = regex.getRegex()
|
|
||||||
# check new lines present in regex (was compiled as multiline), incorrect by `maxlines=1`:
|
|
||||||
if (regex.flags & re.MULTILINE) and not multiLine:
|
|
||||||
logSys.warning(
|
|
||||||
"Mutliline regex set for jail %r "
|
|
||||||
"but maxlines not greater than 1", self.jailName)
|
|
||||||
except RegexException as e:
|
except RegexException as e:
|
||||||
logSys.error(e)
|
logSys.error(e)
|
||||||
raise e
|
raise e
|
||||||
|
|
|
@ -1479,8 +1479,8 @@ class GetFailures(LogCaptureTestCase):
|
||||||
output = [("192.0.43.10", 2, 1124013599.0),
|
output = [("192.0.43.10", 2, 1124013599.0),
|
||||||
("192.0.43.11", 1, 1124013598.0)]
|
("192.0.43.11", 1, 1124013598.0)]
|
||||||
self.filter.addLogPath(GetFailures.FILENAME_MULTILINE, autoSeek=False)
|
self.filter.addLogPath(GetFailures.FILENAME_MULTILINE, autoSeek=False)
|
||||||
self.filter.addFailRegex("^.*rsyncd\[(?P<pid>\d+)\]: connect from .+ \(<HOST>\)$<SKIPLINES>^.+ rsyncd\[(?P=pid)\]: rsync error: .*$")
|
|
||||||
self.filter.setMaxLines(100)
|
self.filter.setMaxLines(100)
|
||||||
|
self.filter.addFailRegex("^.*rsyncd\[(?P<pid>\d+)\]: connect from .+ \(<HOST>\)$<SKIPLINES>^.+ rsyncd\[(?P=pid)\]: rsync error: .*$")
|
||||||
self.filter.setMaxRetry(1)
|
self.filter.setMaxRetry(1)
|
||||||
|
|
||||||
self.filter.getFailures(GetFailures.FILENAME_MULTILINE)
|
self.filter.getFailures(GetFailures.FILENAME_MULTILINE)
|
||||||
|
@ -1497,9 +1497,9 @@ class GetFailures(LogCaptureTestCase):
|
||||||
def testGetFailuresMultiLineIgnoreRegex(self):
|
def testGetFailuresMultiLineIgnoreRegex(self):
|
||||||
output = [("192.0.43.10", 2, 1124013599.0)]
|
output = [("192.0.43.10", 2, 1124013599.0)]
|
||||||
self.filter.addLogPath(GetFailures.FILENAME_MULTILINE, autoSeek=False)
|
self.filter.addLogPath(GetFailures.FILENAME_MULTILINE, autoSeek=False)
|
||||||
|
self.filter.setMaxLines(100)
|
||||||
self.filter.addFailRegex("^.*rsyncd\[(?P<pid>\d+)\]: connect from .+ \(<HOST>\)$<SKIPLINES>^.+ rsyncd\[(?P=pid)\]: rsync error: .*$")
|
self.filter.addFailRegex("^.*rsyncd\[(?P<pid>\d+)\]: connect from .+ \(<HOST>\)$<SKIPLINES>^.+ rsyncd\[(?P=pid)\]: rsync error: .*$")
|
||||||
self.filter.addIgnoreRegex("rsync error: Received SIGINT")
|
self.filter.addIgnoreRegex("rsync error: Received SIGINT")
|
||||||
self.filter.setMaxLines(100)
|
|
||||||
self.filter.setMaxRetry(1)
|
self.filter.setMaxRetry(1)
|
||||||
|
|
||||||
self.filter.getFailures(GetFailures.FILENAME_MULTILINE)
|
self.filter.getFailures(GetFailures.FILENAME_MULTILINE)
|
||||||
|
@ -1513,9 +1513,9 @@ class GetFailures(LogCaptureTestCase):
|
||||||
("192.0.43.11", 1, 1124013598.0),
|
("192.0.43.11", 1, 1124013598.0),
|
||||||
("192.0.43.15", 1, 1124013598.0)]
|
("192.0.43.15", 1, 1124013598.0)]
|
||||||
self.filter.addLogPath(GetFailures.FILENAME_MULTILINE, autoSeek=False)
|
self.filter.addLogPath(GetFailures.FILENAME_MULTILINE, autoSeek=False)
|
||||||
|
self.filter.setMaxLines(100)
|
||||||
self.filter.addFailRegex("^.*rsyncd\[(?P<pid>\d+)\]: connect from .+ \(<HOST>\)$<SKIPLINES>^.+ rsyncd\[(?P=pid)\]: rsync error: .*$")
|
self.filter.addFailRegex("^.*rsyncd\[(?P<pid>\d+)\]: connect from .+ \(<HOST>\)$<SKIPLINES>^.+ rsyncd\[(?P=pid)\]: rsync error: .*$")
|
||||||
self.filter.addFailRegex("^.* sendmail\[.*, msgid=<(?P<msgid>[^>]+).*relay=\[<HOST>\].*$<SKIPLINES>^.+ spamd: result: Y \d+ .*,mid=<(?P=msgid)>(,bayes=[.\d]+)?(,autolearn=\S+)?\s*$")
|
self.filter.addFailRegex("^.* sendmail\[.*, msgid=<(?P<msgid>[^>]+).*relay=\[<HOST>\].*$<SKIPLINES>^.+ spamd: result: Y \d+ .*,mid=<(?P=msgid)>(,bayes=[.\d]+)?(,autolearn=\S+)?\s*$")
|
||||||
self.filter.setMaxLines(100)
|
|
||||||
self.filter.setMaxRetry(1)
|
self.filter.setMaxRetry(1)
|
||||||
|
|
||||||
self.filter.getFailures(GetFailures.FILENAME_MULTILINE)
|
self.filter.getFailures(GetFailures.FILENAME_MULTILINE)
|
||||||
|
|
|
@ -40,7 +40,7 @@ TEST_CONFIG_DIR = os.path.join(os.path.dirname(__file__), "config")
|
||||||
TEST_FILES_DIR = os.path.join(os.path.dirname(__file__), "files")
|
TEST_FILES_DIR = os.path.join(os.path.dirname(__file__), "files")
|
||||||
|
|
||||||
# regexp to test greedy catch-all should be not-greedy:
|
# regexp to test greedy catch-all should be not-greedy:
|
||||||
RE_HOST = Regex('<HOST>').getRegex()
|
RE_HOST = Regex._resolveHostTag('<HOST>')
|
||||||
RE_WRONG_GREED = re.compile(r'\.[+\*](?!\?)[^\$\^]*' + re.escape(RE_HOST) + r'.*(?:\.[+\*].*|[^\$])$')
|
RE_WRONG_GREED = re.compile(r'\.[+\*](?!\?)[^\$\^]*' + re.escape(RE_HOST) + r'.*(?:\.[+\*].*|[^\$])$')
|
||||||
|
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue