emacs-diffs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Emacs-diffs] master dda6201: Fix asynchronous TLS connections on MS-Win


From: Eli Zaretskii
Subject: [Emacs-diffs] master dda6201: Fix asynchronous TLS connections on MS-Windows
Date: Thu, 10 Mar 2016 14:44:08 +0000

branch: master
commit dda6201a972a344c3cf2f35e61511f2cd62670f2
Author: Alain Schneble <address@hidden>
Commit: Eli Zaretskii <address@hidden>

    Fix asynchronous TLS connections on MS-Windows
    
    * src/w32.c (sys_write): Don't switch the socket to blocking mode
    if the connection attempt is in progress.  Instead, return either
    EWOULDBLOCK immediately if the connection is in progress, or the
    error code produced by '_sys_wait_connect' if the connection
    failed.  Switching the socket to blocking mode was found to
    interfere with GnuTLS handshake.  (Bug#22789)
---
 src/w32.c |   34 ++++++++++++++++++++++++++--------
 1 files changed, 26 insertions(+), 8 deletions(-)

diff --git a/src/w32.c b/src/w32.c
index ccf7cc3..c553152 100644
--- a/src/w32.c
+++ b/src/w32.c
@@ -8772,6 +8772,30 @@ sys_write (int fd, const void * buffer, unsigned int 
count)
       unsigned long nblock = 0;
       if (winsock_lib == NULL) emacs_abort ();
 
+      child_process *cp = fd_info[fd].cp;
+
+      /* If this is a non-blocking socket whose connection is in
+        progress or terminated with an error already, return the
+        proper error code to the caller. */
+      if (cp != NULL && (fd_info[fd].flags & FILE_CONNECT) != 0)
+       {
+         /* In case connection is in progress, ENOTCONN that would
+            result from calling pfn_send is not what callers expect. */
+         if (cp->status != STATUS_CONNECT_FAILED)
+           {
+             errno = EWOULDBLOCK;
+             return -1;
+           }
+         /* In case connection failed, use the actual error code
+            stashed by '_sys_wait_connect' in cp->errcode. */
+         else if (cp->errcode != 0)
+           {
+             pfn_WSASetLastError (cp->errcode);
+             set_errno ();
+             return -1;
+           }
+       }
+
       /* TODO: implement select() properly so non-blocking I/O works. */
       /* For now, make sure the write blocks.  */
       if (fd_info[fd].flags & FILE_NDELAY)
@@ -8782,14 +8806,8 @@ sys_write (int fd, const void * buffer, unsigned int 
count)
       if (nchars == SOCKET_ERROR)
         {
          set_errno ();
-         /* If this is a non-blocking socket whose connection is in
-            progress, return the proper error code to the caller;
-            ENOTCONN is not what they expect . */
-         if (errno == ENOTCONN && (fd_info[fd].flags & FILE_CONNECT) != 0)
-           errno = EWOULDBLOCK;
-         else
-           DebPrint (("sys_write.send failed with error %d on socket %ld\n",
-                      pfn_WSAGetLastError (), SOCK_HANDLE (fd)));
+         DebPrint (("sys_write.send failed with error %d on socket %ld\n",
+                    pfn_WSAGetLastError (), SOCK_HANDLE (fd)));
        }
 
       /* Set the socket back to non-blocking if it was before,



reply via email to

[Prev in Thread] Current Thread [Next in Thread]