[Spice-devel] [PATCH spice-server v4 18/20] red-stream: Fix SSL connection for Windows

Frediano Ziglio fziglio at redhat.com
Wed Feb 6 13:58:54 UTC 2019


Set correctly errno to make callers handle correctly encrypted
traffic.

Signed-off-by: Frediano Ziglio <fziglio at redhat.com>
---
 server/red-stream.c | 29 +++++++++++++++++++++++++----
 1 file changed, 25 insertions(+), 4 deletions(-)

diff --git a/server/red-stream.c b/server/red-stream.c
index 3641f0ce..d9e32845 100644
--- a/server/red-stream.c
+++ b/server/red-stream.c
@@ -158,15 +158,37 @@ static ssize_t stream_read_cb(RedStream *s, void *buf, size_t size)
     return socket_read(s->socket, buf, size);
 }
 
+static ssize_t stream_ssl_error(RedStream *s, int return_code)
+{
+    SPICE_GNUC_UNUSED int ssl_error;
+
+    ssl_error = SSL_get_error(s->priv->ssl, return_code);
+
+    // OpenSSL can to return SSL_ERROR_WANT_READ if we attempt to read
+    // data and the socket did not receive all SSL packet.
+    // Under Windows errno is not set so potentially caller can detect
+    // the wrong error so we need to set errno.
+#ifdef _WIN32
+    if (ssl_error == SSL_ERROR_WANT_READ || ssl_error == SSL_ERROR_WANT_WRITE) {
+        errno = EAGAIN;
+    } else {
+        errno = EPIPE;
+    }
+#endif
+
+    // red_peer_receive is expected to receive -1 on errors while
+    // OpenSSL documentation just state a <0 value
+    return -1;
+}
+
 static ssize_t stream_ssl_write_cb(RedStream *s, const void *buf, size_t size)
 {
     int return_code;
-    SPICE_GNUC_UNUSED int ssl_error;
 
     return_code = SSL_write(s->priv->ssl, buf, size);
 
     if (return_code < 0) {
-        ssl_error = SSL_get_error(s->priv->ssl, return_code);
+        return stream_ssl_error(s, return_code);
     }
 
     return return_code;
@@ -175,12 +197,11 @@ static ssize_t stream_ssl_write_cb(RedStream *s, const void *buf, size_t size)
 static ssize_t stream_ssl_read_cb(RedStream *s, void *buf, size_t size)
 {
     int return_code;
-    SPICE_GNUC_UNUSED int ssl_error;
 
     return_code = SSL_read(s->priv->ssl, buf, size);
 
     if (return_code < 0) {
-        ssl_error = SSL_get_error(s->priv->ssl, return_code);
+        return stream_ssl_error(s, return_code);
     }
 
     return return_code;
-- 
2.20.1



More information about the Spice-devel mailing list