Rev 4177: Tighten breakin tests in http://bazaar.launchpad.net/%7Evila/bzr/integration

Vincent Ladeuil v.ladeuil+lp at free.fr
Fri Mar 20 17:21:40 GMT 2009


At http://bazaar.launchpad.net/%7Evila/bzr/integration

------------------------------------------------------------
revno: 4177
revision-id: v.ladeuil+lp at free.fr-20090320171951-6w7qeckyq37doxxg
parent: pqm at pqm.ubuntu.com-20090320162502-09zcxxom3xmdqhfa
parent: v.ladeuil+lp at free.fr-20090320150019-4dbvqrhlbhzvx4m1
committer: Vincent Ladeuil <v.ladeuil+lp at free.fr>
branch nick: integration
timestamp: Fri 2009-03-20 18:19:51 +0100
message:
  Tighten breakin tests
modified:
  bzrlib/tests/blackbox/test_breakin.py test_breakin.py-20070424043903-qyy6zm4pj3h4sbp3-1
    ------------------------------------------------------------
    revno: 4168.1.4
    revision-id: v.ladeuil+lp at free.fr-20090320150019-4dbvqrhlbhzvx4m1
    parent: v.ladeuil+lp at free.fr-20090320080427-kghpz6mrh9l7ywpq
    committer: Vincent Ladeuil <v.ladeuil+lp at free.fr>
    branch nick: fixes
    timestamp: Fri 2009-03-20 16:00:19 +0100
    message:
      More robust handling of test_breakin.
      
      * bzrlib/tests/blackbox/test_breakin.py:
      (TestBreakin.test_breakin): If the process doesn't quit
      peacefully, kill it to avoid leaks.
    modified:
      bzrlib/tests/blackbox/test_breakin.py test_breakin.py-20070424043903-qyy6zm4pj3h4sbp3-1
    ------------------------------------------------------------
    revno: 4168.1.3
    revision-id: v.ladeuil+lp at free.fr-20090320080427-kghpz6mrh9l7ywpq
    parent: v.ladeuil+lp at free.fr-20090320074951-t9osiw77vmmj0b8y
    parent: pqm at pqm.ubuntu.com-20090320074349-siii554u411pxpyz
    committer: Vincent Ladeuil <v.ladeuil+lp at free.fr>
    branch nick: fixes
    timestamp: Fri 2009-03-20 09:04:27 +0100
    message:
      Merge bzr.dev into fixes
    added:
      bzrlib/filters/                filters-20080416080515-mkxl29amuwrf6uir-1
      bzrlib/filters/__init__.py     __init__.py-20080416080515-mkxl29amuwrf6uir-2
      bzrlib/help_topics/en/content-filters.txt contentfilters.txt-20080516145112-7x1meuoci5w41isv-1
      bzrlib/tests/test_filters.py   test_filters.py-20080417120614-tc3zok0vvvprsc99-1
      bzrlib/tests/workingtree_implementations/test_content_filters.py test_content_filters-20080424071441-8navsrmrfdxpn90a-1
    modified:
      NEWS                           NEWS-20050323055033-4e00b5db738777ff
      bzrlib/builtins.py             builtins.py-20050830033751-fc01482b9ca23183
      bzrlib/bzrdir.py               bzrdir.py-20060131065624-156dfea39c4387cb
      bzrlib/export/__init__.py      __init__.py-20051114235828-1ba62cb4062304e6
      bzrlib/export/dir_exporter.py  dir_exporter.py-20051114235828-b51397f56bc7b117
      bzrlib/export/tar_exporter.py  tar_exporter.py-20051114235828-1f6349a2f090a5d0
      bzrlib/export/zip_exporter.py  zip_exporter.py-20051114235828-8f57f954fba6497e
      bzrlib/hashcache.py            hashcache.py-20050706091756-fe3a8cc1143ff24f
      bzrlib/help_topics/__init__.py help_topics.py-20060920210027-rnim90q9e0bwxvy4-1
      bzrlib/help_topics/en/debug-flags.txt debugflags.txt-20090312050229-rdspqbqq4fzbjtpe-1
      bzrlib/osutils.py              osutils.py-20050309040759-eeaff12fbf77ac86
      bzrlib/tests/__init__.py       selftest.py-20050531073622-8d0e3c8845c97a64
      bzrlib/tests/blackbox/test_cat.py test_cat.py-20051201162916-f0937e4e19ea24b3
      bzrlib/tests/blackbox/test_push.py test_push.py-20060329002750-929af230d5d22663
      bzrlib/tests/blackbox/test_selftest.py test_selftest.py-20060123024542-01c5f1bbcb596d78
      bzrlib/tests/ftp_server/__init__.py __init__.py-20090227130107-4gcpgvr00l7v3fsw-1
      bzrlib/tests/test_hashcache.py testhashcache.py-20050706091800-0288ab2659338981
      bzrlib/tests/test_osutils.py   test_osutils.py-20051201224856-e48ee24c12182989
      bzrlib/tests/workingtree_implementations/__init__.py __init__.py-20060203003124-b2aa5aca21a8bfad
      bzrlib/transform.py            transform.py-20060105172343-dd99e54394d91687
      bzrlib/transport/ftp/_gssapi.py _gssapi.py-20080611190840-7ejrtp884bk5eu72-2
      bzrlib/transport/log.py        log.py-20080902041816-vh8x5yt5nvdzvew3-5
      bzrlib/tree.py                 tree.py-20050309040759-9d5f2496be663e77
      bzrlib/ui/text.py              text.py-20051130153916-2e438cffc8afc478
      bzrlib/win32utils.py           win32console.py-20051021033308-123c6c929d04973d
      bzrlib/workingtree.py          workingtree.py-20050511021032-29b6ec0a681e02e3
      bzrlib/workingtree_4.py        workingtree_4.py-20070208044105-5fgpc5j3ljlh5q6c-1
      doc/developers/overview.txt    overview.txt-20080904022501-ww2ggomrs5elxfm0-1
    ------------------------------------------------------------
    revno: 4168.1.2
    revision-id: v.ladeuil+lp at free.fr-20090320074951-t9osiw77vmmj0b8y
    parent: v.ladeuil+lp at free.fr-20090320065607-j2vi19cy7x5uhmr9
    committer: Vincent Ladeuil <v.ladeuil+lp at free.fr>
    branch nick: fixes
    timestamp: Fri 2009-03-20 08:49:51 +0100
    message:
      Take Martin and John review comments into account and tighten the tests.
      
      * bzrlib/tests/blackbox/test_breakin.py:
      (TestBreakin.test_breakin): Restore the test and make its intent
      clearer.
      (TestBreakin.test_breakin_harder): Remove timing dependencies.
    modified:
      bzrlib/tests/blackbox/test_breakin.py test_breakin.py-20070424043903-qyy6zm4pj3h4sbp3-1
    ------------------------------------------------------------
    revno: 4168.1.1
    revision-id: v.ladeuil+lp at free.fr-20090320065607-j2vi19cy7x5uhmr9
    parent: pqm at pqm.ubuntu.com-20090319154145-159h7mmiivu3df6v
    committer: Vincent Ladeuil <v.ladeuil+lp at free.fr>
    branch nick: fixes
    timestamp: Fri 2009-03-20 07:56:07 +0100
    message:
      Commit fix in a new thread to handle review comments
    modified:
      bzrlib/tests/blackbox/test_breakin.py test_breakin.py-20070424043903-qyy6zm4pj3h4sbp3-1
-------------- next part --------------
=== modified file 'bzrlib/tests/blackbox/test_breakin.py'
--- a/bzrlib/tests/blackbox/test_breakin.py	2009-02-23 15:29:35 +0000
+++ b/bzrlib/tests/blackbox/test_breakin.py	2009-03-20 15:00:19 +0000
@@ -16,13 +16,17 @@
 
 """Blackbox tests for debugger breakin"""
 
+import errno
 import os
 import signal
 import subprocess
 import sys
 import time
 
-from bzrlib import tests
+from bzrlib import (
+    errors,
+    tests,
+    )
 
 
 class TestBreakin(tests.TestCase):
@@ -44,6 +48,34 @@
             raise tests.TestNotApplicable(
                 '%s raises a popup on OSX' % self.id())
 
+    def _wait_for_process(self, pid, sig=None):
+        # We don't know quite how long waiting for the process 'pid' will take,
+        # but if it's more than 10s then it's probably not going to work.
+        for i in range(100):
+            time.sleep(0.1)
+            if sig is not None:
+                os.kill(pid, sig)
+            # Use WNOHANG to ensure we don't get blocked, doing so, we may
+            # leave the process continue after *we* die...
+            try:
+                # note: waitpid is different on win32, but this test only runs
+                # on unix
+                pid_killed, returncode = os.waitpid(pid, os.WNOHANG)
+                if (pid_killed, returncode) != (0, 0):
+                    if sig is not None:
+                        # high bit in low byte says if core was dumped; we
+                        # don't care
+                        status, sig = (returncode >> 8, returncode & 0x7f)
+                        return True, sig
+            except OSError, e:
+                if e.errno in (errno.ECHILD, errno.ESRCH):
+                    # The process doesn't exist anymore
+                    return True, None
+                else:
+                    raise
+
+        return False, None
+
     # port 0 means to allocate any port
     _test_process_args = ['serve', '--port', 'localhost:0']
 
@@ -57,12 +89,26 @@
         proc.stderr.readline()
         # first sigquit pops into debugger
         os.kill(proc.pid, signal.SIGQUIT)
+        # Wait for the debugger to acknowledge the signal reception
+        err = proc.stderr.readline()
+        self.assertContainsRe(err, r'entering debugger')
+        # Now that the debugger is entered, we can ask him to quit
         proc.stdin.write("q\n")
-        time.sleep(.5)
-        err = proc.stderr.readline()
-        self.assertContainsRe(err, r'entering debugger')
+        # We wait a bit to let the child process handles our query and avoid
+        # triggering deadlocks leading to hangs on multi-core hosts...
+        dead, sig = self._wait_for_process(proc.pid)
+        if not dead:
+            # The process didn't finish, let's kill it before reporting failure
+            dead, sig = self._wait_for_process(proc.pid, signal.SIGKILL)
+            if dead:
+                raise tests.KnownFailure(
+                    "subprocess wasn't terminated, it had to be killed")
+            else:
+                self.fail("subprocess %d wasn't terminated by repeated SIGKILL",
+                          proc.pid)
 
     def test_breakin_harder(self):
+        """SIGQUITting twice ends the process."""
         self._dont_SIGQUIT_on_darwin()
         proc = self.start_bzr_subprocess(self._test_process_args,
                 env_changes=dict(BZR_SIGQUIT_PDB=None))
@@ -70,23 +116,14 @@
         proc.stderr.readline()
         # break into the debugger
         os.kill(proc.pid, signal.SIGQUIT)
-        # now send a second sigquit, which should cause it to exit.  That
-        # won't happen until the original signal has been noticed by the
-        # child and it's run its signal handler.  We don't know quite how long
-        # this will take, but if it's more than 10s then it's probably not
-        # going to work.
-        for i in range(100):
-            time.sleep(0.1)
-            os.kill(proc.pid, signal.SIGQUIT)
-            # note: waitpid is different on win32, but this test only runs on
-            # unix
-            r = os.waitpid(proc.pid, os.WNOHANG)
-            if r != (0, 0):
-                # high bit says if core was dumped; we don't care
-                self.assertEquals(r[1] & 0x7f, signal.SIGQUIT)
-                break
-        else:
-            self.fail("subprocess wasn't terminated by repeated SIGQUIT")
+        # Wait for the debugger to acknowledge the signal reception (since we
+        # want to send a second signal, we ensure it doesn't get lost by
+        # validating the first get received and produce its effect).
+        err = proc.stderr.readline()
+        self.assertContainsRe(err, r'entering debugger')
+        dead, sig = self._wait_for_process(proc.pid, signal.SIGQUIT)
+        self.assertTrue((dead and sig == signal.SIGQUIT),
+                        msg="subprocess wasn't terminated by repeated SIGQUIT")
 
     def test_breakin_disabled(self):
         self._dont_SIGQUIT_on_darwin()



More information about the bazaar-commits mailing list