If a user used ^Z to stop the program, poll() in socket.recv would return
EAGAIN due to SIGSTOP. This patch changes luxi.Transport.Recv to ignore EAGAIN.

Signed-off-by: Michael Hanselmann <[email protected]>
---
 daemons/ganeti-masterd |    1 +
 lib/luxi.py            |   15 +++++++++++----
 2 files changed, 12 insertions(+), 4 deletions(-)

diff --git a/daemons/ganeti-masterd b/daemons/ganeti-masterd
index 6a73e4e..b9e62c7 100755
--- a/daemons/ganeti-masterd
+++ b/daemons/ganeti-masterd
@@ -195,6 +195,7 @@ class ClientRqHandler(SocketServer.BaseRequestHandler):
 
   def send_message(self, msg):
     #print "sending", msg
+    # TODO: sendall is not guaranteed to send everything
     self.request.sendall(msg + self.EOM)
 
 
diff --git a/lib/luxi.py b/lib/luxi.py
index 85c3aa5..ff947ea 100644
--- a/lib/luxi.py
+++ b/lib/luxi.py
@@ -186,6 +186,7 @@ class Transport:
       raise EncodingError("Message terminator found in payload")
     self._CheckSocket()
     try:
+      # TODO: sendall is not guaranteed to send everything
       self.socket.sendall(msg + self.eom)
     except socket.timeout, err:
       raise TimeoutError("Sending timeout: %s" % str(err))
@@ -204,10 +205,16 @@ class Transport:
     while not self._msgs:
       if time.time() > etime:
         raise TimeoutError("Extended receive timeout")
-      try:
-        data = self.socket.recv(4096)
-      except socket.timeout, err:
-        raise TimeoutError("Receive timeout: %s" % str(err))
+      while True:
+        try:
+          data = self.socket.recv(4096)
+        except socket.error, err:
+          if err.args and err.args[0] == errno.EAGAIN:
+            continue
+          raise
+        except socket.timeout, err:
+          raise TimeoutError("Receive timeout: %s" % str(err))
+        break
       if not data:
         raise ConnectionClosedError("Connection closed while reading")
       new_msgs = (self._buffer + data).split(self.eom)
-- 
1.6.3.3

Reply via email to