[PATCH V2] cmdserver: include pid of server handling requests in hello message

Yuya Nishihara yuya at tcha.org
Fri Oct 17 22:55:50 CDT 2014


# HG changeset patch
# User Yuya Nishihara <yuya at tcha.org>
# Date 1413602690 -32400
#      Sat Oct 18 12:24:50 2014 +0900
# Node ID 2d222b13ef0f18f4e0083ebbf2948cc5ff9631cd
# Parent  f484be02bd351fbd084d93f5ba4180e2b22cd4eb
cmdserver: include pid of server handling requests in hello message

Because unix-mode server forks child process per connection, client does not
know the pid of the server that will handle requests.  The pid is necessary
to interrupt hung process:

 1. client connects to socket server
 2. server accepts the connection, forks, and tells pid
 3. client requests "runcommand pull"
    .. hung ..
 4. client sends SIGINT to the (forked) server
 5. server returns from I/O wait

Note that getsockopt(SO_PEERCRED) of Linux cannot be used because the server
fork()s after accept().

diff --git a/mercurial/commandserver.py b/mercurial/commandserver.py
--- a/mercurial/commandserver.py
+++ b/mercurial/commandserver.py
@@ -232,6 +232,8 @@ class server(object):
         hellomsg = 'capabilities: ' + ' '.join(sorted(self.capabilities))
         hellomsg += '\n'
         hellomsg += 'encoding: ' + encoding.encoding
+        hellomsg += '\n'
+        hellomsg += 'pid: %d' % os.getpid()
 
         # write the hello msg in -one- chunk
         self.cout.write(hellomsg)
diff --git a/tests/test-commandserver.t b/tests/test-commandserver.t
--- a/tests/test-commandserver.t
+++ b/tests/test-commandserver.t
@@ -16,7 +16,7 @@
   ...     # run an arbitrary command to make sure the next thing the server
   ...     # sends isn't part of the hello message
   ...     runcommand(server, ['id'])
-  o, 'capabilities: getencoding runcommand\nencoding: *' (glob)
+  o, 'capabilities: getencoding runcommand\nencoding: *\npid: *' (glob)
   *** runcommand id
   000000000000 tip
 
@@ -531,7 +531,7 @@ start without repository:
   ...     # run an arbitrary command to make sure the next thing the server
   ...     # sends isn't part of the hello message
   ...     runcommand(server, ['id'])
-  o, 'capabilities: getencoding runcommand\nencoding: *' (glob)
+  o, 'capabilities: getencoding runcommand\nencoding: *\npid: *' (glob)
   *** runcommand id
   abort: there is no Mercurial repository here (.hg not found)
    [255]
@@ -562,7 +562,7 @@ unix domain socket:
   ...     print '%c, %r' % (ch, data)
   ...     runcommand(conn, ['id'])
   >>> check(hellomessage, server.connect)
-  o, 'capabilities: getencoding runcommand\nencoding: *' (glob)
+  o, 'capabilities: getencoding runcommand\nencoding: *\npid: *' (glob)
   *** runcommand id
   eff892de26ec tip bm1/bm2/bm3
   >>> def unknowncommand(conn):


More information about the Mercurial-devel mailing list