diff --git a/ChangeLog b/ChangeLog index d42ea111..85fbaa54 100644 --- a/ChangeLog +++ b/ChangeLog @@ -14,6 +14,8 @@ ver. 0.8.14 (2014/??/??) - take-care-of-the-elderly - minor fixes for claimed Python 2.4 and 2.5 compatibility - Handle case when inotify watch is auto deleted on file deletion to stop error messages + - tests - fixed few "leaky" file descriptors when files were not closed while + being removed physically ver. 0.8.13 (2014/03/15) - maintenance-only-from-now-on diff --git a/server/filtergamin.py b/server/filtergamin.py index 196396c5..296ba700 100644 --- a/server/filtergamin.py +++ b/server/filtergamin.py @@ -125,7 +125,7 @@ class FilterGamin(FileFilter): self.__cleanup() ## - # Desallocates the resources used by Gamin. + # Free up the resources used by Gamin. def __cleanup(self): for path in self.getLogPath(): diff --git a/server/filterpyinotify.py b/server/filterpyinotify.py index 68675df4..8a9e4529 100644 --- a/server/filterpyinotify.py +++ b/server/filterpyinotify.py @@ -69,6 +69,7 @@ class FilterPyinotify(FileFilter): # Pyinotify watch manager self.__monitor = pyinotify.WatchManager() self.__watches = dict() + self.__notifier = None logSys.debug("Created FilterPyinotify") @@ -190,9 +191,10 @@ class FilterPyinotify(FileFilter): def stop(self): super(FilterPyinotify, self).stop() - # Stop the notifier thread - self.__notifier.stop() - self.__notifier.join() # to not exit before notifier does + # Stop the notifier thread if it was ran and notifier was created + if self.__notifier is not None: + self.__notifier.stop() + self.__notifier.join() # to not exit before notifier does self.__cleanup() # for pedantic ones ## diff --git a/testcases/actionstestcase.py b/testcases/actionstestcase.py index 15877749..ae123417 100644 --- a/testcases/actionstestcase.py +++ b/testcases/actionstestcase.py @@ -35,9 +35,10 @@ class ExecuteActions(unittest.TestCase): """Call before every test case.""" self.__jail = DummyJail() self.__actions = Actions(self.__jail) - self.__tmpfile, self.__tmpfilename = tempfile.mkstemp() + self.__tmpfile, self.__tmpfilename = tempfile.mkstemp('fail2ban', 'executeactions') def tearDown(self): + os.close(self.__tmpfile) os.remove(self.__tmpfilename) def defaultActions(self): diff --git a/testcases/filtertestcase.py b/testcases/filtertestcase.py index f244808a..58162201 100644 --- a/testcases/filtertestcase.py +++ b/testcases/filtertestcase.py @@ -280,11 +280,15 @@ class LogFileFilterPoll(unittest.TestCase): class LogFileMonitor(LogCaptureTestCase): """Few more tests for FilterPoll API """ + + _setup_idx = 0 # to ease tracking of dangling opened files + def setUp(self): """Call before every test case.""" LogCaptureTestCase.setUp(self) self.filter = self.name = 'NA' - _, self.name = tempfile.mkstemp('fail2ban', 'monitorfailures') + _, self.name = tempfile.mkstemp('fail2ban', 'monitorfailures-%d-' % LogFileMonitor._setup_idx) + LogFileMonitor._setup_idx += 1 self.file = open(self.name, 'a') self.filter = FilterPoll(None) self.filter.addLogPath(self.name) @@ -555,7 +559,7 @@ def get_monitor_failures_testcase(Filter_): # now create a new one to override old one _copy_lines_between_files(GetFailures.FILENAME_01, self.name + '.new', - n=100).close() + n=100, skip=3).close() os.rename(self.name + '.new', self.name) self.assert_correct_last_attempt(GetFailures.FAILURES_01) self.assertEqual(self.filter.failManager.getFailTotal(), 6)