Merge branch '0.10' into 0.11

pull/2093/head
sebres 2018-03-02 21:42:07 +01:00
commit ccb1daf30a
4 changed files with 31 additions and 20 deletions

View File

@ -76,6 +76,10 @@ class RequestHandler(asynchat.async_chat):
#logSys.debug("Received raw data: " + str(data))
self.__buffer.append(data)
# exception identifies deserialization errors (exception by load in pickle):
class LoadError(Exception):
pass
##
# Handles a new request.
#
@ -93,7 +97,12 @@ class RequestHandler(asynchat.async_chat):
self.close_when_done()
return
# Deserialize
message = loads(message)
try:
message = loads(message)
except Exception as e:
logSys.error('PROTO-error: load message failed: %s', e,
exc_info=logSys.getEffectiveLevel()<logging.DEBUG)
raise RequestHandler.LoadError(e)
# Gives the message to the transmitter.
if self.__transmitter:
message = self.__transmitter.proceed(message)
@ -104,8 +113,9 @@ class RequestHandler(asynchat.async_chat):
# Sends the response to the client.
self.push(message + CSPROTO.END)
except Exception as e:
logSys.error("Caught unhandled exception: %r", e,
exc_info=logSys.getEffectiveLevel()<=logging.DEBUG)
if not isinstance(e, RequestHandler.LoadError): # pragma: no cover - normally unreachable
logSys.error("Caught unhandled exception: %r", e,
exc_info=logSys.getEffectiveLevel()<=logging.DEBUG)
# Sends the response to the client.
message = dumps("ERROR: %s" % e, HIGHEST_PROTOCOL)
self.push(message + CSPROTO.END)
@ -200,23 +210,21 @@ class AsyncServer(asyncore.dispatcher):
def handle_accept(self):
try:
conn, addr = self.accept()
except socket.error as e: # pragma: no cover
except Exception as e: # pragma: no cover
self.__errCount['accept'] += 1
if self.__errCount['accept'] < 20:
logSys.warning("Socket error: %s", e)
logSys.warning("Accept socket error: %s", e,
exc_info=(self.__errCount['accept'] <= 1))
elif self.__errCount['accept'] == 20:
logSys.error("Too many acceptor errors - stop logging errors")
elif self.__errCount['accept'] > 100:
if (
e.args[0] == errno.EMFILE # [Errno 24] Too many open files
(isinstance(e, socket.error) and e.args[0] == errno.EMFILE) # [Errno 24] Too many open files
or sum(self.__errCount.itervalues()) > 1000
):
logSys.critical("Too many errors - critical count reached %r", err_count)
logSys.critical("Too many errors - critical count reached %r", self.__errCount)
self.stop()
return
except TypeError as e: # pragma: no cover
logSys.warning("Type error: %s", e)
return
if self.__errCount['accept']:
self.__errCount['accept'] -= 1;
AsyncServer.__markCloseOnExec(conn)
@ -265,6 +273,13 @@ class AsyncServer(asyncore.dispatcher):
stopflg = False
if self.__active:
self.__loop = False
# shutdown socket here:
if self.socket:
try:
self.socket.shutdown(socket.SHUT_RDWR)
except socket.error: # pragma: no cover - normally unreachable
pass
# close connection:
asyncore.dispatcher.close(self)
# If not the loop thread (stops self in handler), wait (a little bit)
# for the server leaves loop, before remove socket
@ -284,14 +299,8 @@ class AsyncServer(asyncore.dispatcher):
def stop_communication(self):
if self.__transmitter:
logSys.debug("Stop communication")
logSys.debug("Stop communication, shutdown")
self.__transmitter = None
# shutdown socket here:
if self.socket:
try:
self.socket.shutdown(socket.SHUT_RDWR)
except socket.error: # pragma: no cover - normally unreachable
pass
##
# Stops the server.

View File

@ -102,7 +102,7 @@ class Utils():
def unset(self, k):
try:
del self._cache[k]
except KeyError: # pragma: no cover
except KeyError:
pass

View File

@ -1640,6 +1640,8 @@ class DNSUtilsTests(unittest.TestCase):
c.set(i, i)
for i in xrange(5):
self.assertEqual(c.get(i), i)
# remove unavailable key:
c.unset('a'); c.unset('a')
def testCacheMaxSize(self):
c = Utils.Cache(maxCount=5, maxTime=60)

View File

@ -57,7 +57,7 @@ class Socket(LogCaptureTestCase):
LogCaptureTestCase.setUp(self)
super(Socket, self).setUp()
self.server = AsyncServer(self)
sock_fd, sock_name = tempfile.mkstemp('fail2ban.sock', 'socket')
sock_fd, sock_name = tempfile.mkstemp('fail2ban.sock', 'f2b-socket')
os.close(sock_fd)
os.remove(sock_name)
self.sock_name = sock_name
@ -120,7 +120,7 @@ class Socket(LogCaptureTestCase):
# test wrong message:
self.assertEqual(client.send([[TestMsg()]]), 'ERROR: test unpickle error')
self.assertLogged("Caught unhandled exception", "test unpickle error", all=True)
self.assertLogged("PROTO-error: load message failed:", "test unpickle error", all=True)
# test good message again:
self.assertEqual(client.send(testMessage), testMessage)