parent: don't wait for SIGTERM to complete.

pull/204/head
David Wilson 7 years ago
parent dc4433ace6
commit e56608ab91

@ -603,13 +603,20 @@ class Stream(mitogen.core.Stream):
return return
raise raise
self._reaped = True
if pid: if pid:
LOG.debug('%r: child process exit status was %d', self, status) LOG.debug('%r: child process exit status was %d', self, status)
else: return
LOG.debug('%r: child process still alive, sending SIGTERM', self)
# For processes like sudo we cannot actually send sudo a signal,
# because it is setuid, so this is best-effort only.
LOG.debug('%r: child process still alive, sending SIGTERM', self)
try:
os.kill(self.pid, signal.SIGTERM) os.kill(self.pid, signal.SIGTERM)
os.waitpid(self.pid, 0) except OSError:
self._reaped = True e = sys.exc_info()[1]
if e.args[0] != errno.EPERM:
raise
def on_disconnect(self, broker): def on_disconnect(self, broker):
self._reap_child() self._reap_child()

@ -10,6 +10,23 @@ import testlib
import mitogen.parent import mitogen.parent
def wait_for_child(pid, timeout=1.0):
deadline = time.time() + timeout
while timeout < time.time():
try:
target_pid, status = os.waitpid(pid, os.WNOHANG)
if target_pid == pid:
return
except OSError:
e = sys.exc_info()[1]
if e.args[0] == errno.ECHILD:
return
time.sleep(0.05)
assert False, "wait_for_child() timed out"
class ReapChildTest(testlib.RouterMixin, testlib.TestCase): class ReapChildTest(testlib.RouterMixin, testlib.TestCase):
def test_connect_timeout(self): def test_connect_timeout(self):
# Ensure the child process is reaped if the connection times out. # Ensure the child process is reaped if the connection times out.
@ -24,6 +41,7 @@ class ReapChildTest(testlib.RouterMixin, testlib.TestCase):
self.assertRaises(mitogen.core.TimeoutError, self.assertRaises(mitogen.core.TimeoutError,
lambda: stream.connect() lambda: stream.connect()
) )
wait_for_child(stream.pid)
e = self.assertRaises(OSError, e = self.assertRaises(OSError,
lambda: os.kill(stream.pid, 0) lambda: os.kill(stream.pid, 0)
) )
@ -80,6 +98,7 @@ class ContextTest(testlib.RouterMixin, unittest2.TestCase):
local = self.router.local() local = self.router.local()
pid = local.call(os.getpid) pid = local.call(os.getpid)
local.shutdown(wait=True) local.shutdown(wait=True)
wait_for_child(pid)
self.assertRaises(OSError, lambda: os.kill(pid, 0)) self.assertRaises(OSError, lambda: os.kill(pid, 0))

Loading…
Cancel
Save