Permalink
Browse files

unix: don't crash listener if remote end disconnects.

In some scenarios, Ansible's worker seems to exit early, resulting in
EPIPE during .recv() or .send(). Log an error and gracefully disconnect
in that case.
  • Loading branch information...
dw committed Sep 7, 2018
1 parent 80a18e1 commit 830966bf8a5b41f22aea936e2c6f5fc01232f00b
Showing with 24 additions and 7 deletions.
  1. +24 −7 mitogen/unix.py
@@ -78,22 +78,39 @@ def __init__(self, router, path=None, backlog=100):
self.receive_side = mitogen.core.Side(self, self._sock.fileno())
router.broker.start_receive(self)

def on_receive(self, broker):
sock, _ = self._sock.accept()
def _accept_client(self, sock):
sock.setblocking(True)
pid, = struct.unpack('>L', sock.recv(4))
try:
pid, = struct.unpack('>L', sock.recv(4))
except socket.error:
LOG.error('%r: failed to read remote identity: %s',
self, sys.exc_info()[1])
return

context_id = self._router.id_allocator.allocate()
context = mitogen.parent.Context(self._router, context_id)
stream = mitogen.core.Stream(self._router, context_id)
stream.accept(sock.fileno(), sock.fileno())
stream.name = u'unix_client.%d' % (pid,)
stream.auth_id = mitogen.context_id
stream.is_privileged = True

try:
sock.send(struct.pack('>LLL', context_id, mitogen.context_id,
os.getpid()))
except socket.error:
LOG.error('%r: failed to assign identity to PID %d: %s',
self, pid, sys.exc_info()[1])
return

stream.accept(sock.fileno(), sock.fileno())
self._router.register(context, stream)
sock.send(struct.pack('>LLL', context_id, mitogen.context_id,
os.getpid()))
sock.close()

def on_receive(self, broker):
sock, _ = self._sock.accept()
try:
self._accept_client(sock)
finally:
sock.close()


def connect(path, broker=None):

0 comments on commit 830966b

Please sign in to comment.