[PATCH 2 of 3] killdaemons: use posixfile to avoid intermittent unlink errors on Windows

Matt Harbison mharbison72 at gmail.com
Mon May 15 00:08:31 EDT 2017


# HG changeset patch
# User Matt Harbison <matt_harbison at yahoo.com>
# Date 1494808413 14400
#      Sun May 14 20:33:33 2017 -0400
# Node ID 809709930080937b6b56e5cad285798f29a10280
# Parent  024271e90987e5794dab6eb00844467065fae7e4
killdaemons: use posixfile to avoid intermittent unlink errors on Windows

This is the aforementioned fix for the occasional cleanup error with #serve
enabled.  There are a handful of tests that neglect to kill the daemons they
spawned, and this code is doing a last ditch reap of them.  The test that got
flagged was non-deterministic, and I've seen up to 3 fail in the same run.

The problem with trying to import the mercurial module is that while it is
available for running the individual *.t files, it is not in sys.path for
run-tests.py itself.  I couldn't think of any other way to make this work, and
not affect sys.path for the indiviual tests.  (The main source tree _is_ in
PYTHONPATH when this is imported from run-tests.py.)

diff --git a/tests/killdaemons.py b/tests/killdaemons.py
--- a/tests/killdaemons.py
+++ b/tests/killdaemons.py
@@ -7,6 +7,16 @@
 import sys
 import time
 
+# PYTHONPATH contains the hg source tree when invoked from ./run-tests, but
+# sys.path does not, and importing mercurial fails.  The first import works from
+# the .t files without editing the path.
+try:
+    from mercurial.util import posixfile
+except ImportError:
+    srctree = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
+    sys.path.insert(1, srctree)
+    from mercurial.util import posixfile
+
 if os.name =='nt':
     import ctypes
 
@@ -81,18 +91,17 @@
         logfn = lambda s: s
     # Kill off any leftover daemon processes
     try:
-        fp = open(pidfile)
-        for line in fp:
-            try:
-                pid = int(line)
-                if pid <= 0:
-                    raise ValueError
-            except ValueError:
-                logfn('# Not killing daemon process %s - invalid pid'
-                      % line.rstrip())
-                continue
-            kill(pid, logfn, tryhard)
-        fp.close()
+        with posixfile(pidfile) as fp:
+            for line in fp:
+                try:
+                    pid = int(line)
+                    if pid <= 0:
+                        raise ValueError
+                except ValueError:
+                    logfn('# Not killing daemon process %s - invalid pid'
+                          % line.rstrip())
+                    continue
+                kill(pid, logfn, tryhard)
         if remove:
             os.unlink(pidfile)
     except IOError:


More information about the Mercurial-devel mailing list