Fix IgnoreSignals on socket.error
authorGuido Trotter <ultrotter@google.com>
Mon, 31 May 2010 09:36:14 +0000 (11:36 +0200)
committerGuido Trotter <ultrotter@google.com>
Tue, 1 Jun 2010 08:39:06 +0000 (09:39 +0100)
Some confusion arose handling EINTR on this function: in python 2.6
socket.error is an IOError, and thus:
  - It's an EnvironmentError
  - It has an .errno member

In 2.4 and 2.5 it's not, and so its errno variable must be extracted
from the args tuple. This patch fixes both the function, and the
unittests.

This is a cherry-pick of master commit
965d0e5ba37f3e88aa38230177ad1c66814bf927 with the portions not relevant
to 2.1 removed (changes to the RetryOnSignals function).

Signed-off-by: Guido Trotter <ultrotter@google.com>
Reviewed-by: Iustin Pop <iustin@google.com>

lib/utils.py
test/ganeti.utils_unittest.py

index e3dd435..2909f86 100644 (file)
@@ -2518,10 +2518,12 @@ def IgnoreSignals(fn, *args, **kwargs):
   """
   try:
     return fn(*args, **kwargs)
-  except (EnvironmentError, socket.error), err:
+  except EnvironmentError, err:
     if err.errno != errno.EINTR:
       raise
-  except select.error, err:
+  except (select.error, socket.error), err:
+    # In python 2.6 and above select.error is an IOError, so it's handled
+    # above, in 2.5 and below it's not, and it's handled here.
     if not (err.args and err.args[0] == errno.EINTR):
       raise
 
index 548d04e..a78115f 100755 (executable)
@@ -1836,9 +1836,7 @@ class TestIgnoreSignals(unittest.TestCase):
 
   def testIgnoreSignals(self):
     sock_err_intr = socket.error(errno.EINTR, "Message")
-    sock_err_intr.errno = errno.EINTR
     sock_err_inval = socket.error(errno.EINVAL, "Message")
-    sock_err_inval.errno = errno.EINVAL
 
     env_err_intr = EnvironmentError(errno.EINTR, "Message")
     env_err_inval = EnvironmentError(errno.EINVAL, "Message")