Anonymous avatar Anonymous committed bea8a71

Changed to socket error code instead of message, backport of http://cherrypy.org/ticket/860.

Comments (0)

Files changed (1)

cherrypy/wsgiserver/__init__.py

     SSL = None
 
 import errno
+
+socket_error_eintr = plat_specific_errors("EINTR", "WSAEINTR")
+
 socket_errors_to_ignore = []
 # Not all of these names will be defined for every platform.
 for _ in ("EPIPE", "ETIMEDOUT", "ECONNREFUSED", "ECONNRESET",
           "EHOSTDOWN", "EHOSTUNREACH",
           "WSAECONNABORTED", "WSAECONNREFUSED", "WSAECONNRESET",
-          "WSAENETRESET", "WSAETIMEDOUT"):
+          "WSAENETRESET", "WSAETIMEDOUT", "EBADF", "WSAEBADF",
+          "ENOTSOCK", "WSAENOTSOCK"):
     if _ in dir(errno):
         socket_errors_to_ignore.append(getattr(errno, _))
 # de-dupe the list
 socket_errors_to_ignore = dict.fromkeys(socket_errors_to_ignore).keys()
 socket_errors_to_ignore.append("timed out")
 
+socket_errors_nonblocking = plat_specific_errors(
+        'EAGAIN', 'EWOULDBLOCK', 'WSAEWOULDBLOCK')
+
 comma_separated_headers = ['ACCEPT', 'ACCEPT-CHARSET', 'ACCEPT-ENCODING',
     'ACCEPT-LANGUAGE', 'ACCEPT-RANGES', 'ALLOW', 'CACHE-CONTROL',
     'CONNECTION', 'CONTENT-ENCODING', 'CONTENT-LANGUAGE', 'EXPECT',
             # accept() by default
             return
         except socket.error, x:
-            msg = x.args[1]
-            if msg in ("Bad file descriptor", "Socket operation on non-socket"):
+            if x.args[0] in socket_error_eintr:
+                # I *think* this is right. EINTR should occur when a signal
+                # is received during the accept() call; all docs say retry
+                # the call, and I *think* I'm reading it right that Python
+                # will then go ahead and poll for and handle the signal
+                # elsewhere. See http://www.cherrypy.org/ticket/707.
+                return
+            if x.args[0] in socket_errors_nonblocking:
+                # Just try again. See http://www.cherrypy.org/ticket/479.
+                return
+            if x.args[0] in socket_errors_to_ignore:
                 # Our socket was closed.
-                return
-            if msg == "Resource temporarily unavailable":
-                # Just try again. See http://www.cherrypy.org/ticket/479.
+                # See http://www.cherrypy.org/ticket/686.
                 return
             raise
     
                 try:
                     host, port = sock.getsockname()[:2]
                 except socket.error, x:
-                    if x.args[1] != "Bad file descriptor":
+                    if x.args[0] in socket_errors_to_ignore:
+                        # Changed to use error code and not message
+                        # See http://www.cherrypy.org/ticket/860.
                         raise
                 else:
                     # Note that we're explicitly NOT using AI_PASSIVE,
Tip: Filter by directory path e.g. /media app.js to search for public/media/app.js.
Tip: Use camelCasing e.g. ProjME to search for ProjectModifiedEvent.java.
Tip: Filter by extension type e.g. /repo .js to search for all .js files in the /repo directory.
Tip: Separate your search with spaces e.g. /ssh pom.xml to search for src/ssh/pom.xml.
Tip: Use ↑ and ↓ arrow keys to navigate and return to view the file.
Tip: You can also navigate files with Ctrl+j (next) and Ctrl+k (previous) and view the file with Ctrl+o.
Tip: You can also navigate files with Alt+j (next) and Alt+k (previous) and view the file with Alt+o.