[PATCH 2/3] winhttp: Status and reason are optional in the close response.

Hans Leidekker hans at codeweavers.com
Thu Jun 25 04:00:24 CDT 2020


Signed-off-by: Hans Leidekker <hans at codeweavers.com>
---
 dlls/winhttp/request.c | 25 ++++++++++---------------
 1 file changed, 10 insertions(+), 15 deletions(-)

diff --git a/dlls/winhttp/request.c b/dlls/winhttp/request.c
index 623fdf5db5..c15be38592 100644
--- a/dlls/winhttp/request.c
+++ b/dlls/winhttp/request.c
@@ -3310,7 +3310,7 @@ static DWORD receive_bytes( struct netconn *netconn, char *buf, DWORD len, DWORD
 {
     DWORD err;
     if ((err = netconn_recv( netconn, buf, len, 0, (int *)ret_len ))) return err;
-    if (len && !*ret_len) return ERROR_WINHTTP_INVALID_SERVER_RESPONSE;
+    if (*ret_len != len) return ERROR_WINHTTP_INVALID_SERVER_RESPONSE;
     return ERROR_SUCCESS;
 }
 
@@ -3341,8 +3341,7 @@ static DWORD receive_frame( struct netconn *netconn, DWORD *ret_len, enum socket
     char hdr[2];
 
     if ((ret = receive_bytes( netconn, hdr, sizeof(hdr), &count ))) return ret;
-    if (count != sizeof(hdr) || (hdr[0] & RESERVED_BIT) || (hdr[1] & MASK_BIT) ||
-        (map_opcode( hdr[0] & 0xf, FALSE ) == ~0u))
+    if ((hdr[0] & RESERVED_BIT) || (hdr[1] & MASK_BIT) || (map_opcode( hdr[0] & 0xf, FALSE ) == ~0u))
     {
         return ERROR_WINHTTP_INVALID_SERVER_RESPONSE;
     }
@@ -3353,14 +3352,12 @@ static DWORD receive_frame( struct netconn *netconn, DWORD *ret_len, enum socket
     {
         USHORT len16;
         if ((ret = receive_bytes( netconn, (char *)&len16, sizeof(len16), &count ))) return ret;
-        if (count != sizeof(len16)) return ERROR_WINHTTP_INVALID_SERVER_RESPONSE;
         len = RtlUshortByteSwap( len16 );
     }
     else if (len == 127)
     {
         ULONGLONG len64;
         if ((ret = receive_bytes( netconn, (char *)&len64, sizeof(len64), &count ))) return ret;
-        if (count != sizeof(len64)) return ERROR_WINHTTP_INVALID_SERVER_RESPONSE;
         if ((len64 = RtlUlonglongByteSwap( len64 )) > ~0u) return ERROR_NOT_SUPPORTED;
         len = len64;
     }
@@ -3548,23 +3545,21 @@ static DWORD socket_close( struct socket *socket, USHORT status, const void *rea
     }
 
     if ((ret = receive_frame( netconn, &count, &socket->opcode ))) goto done;
-    if (socket->opcode != SOCKET_OPCODE_CLOSE || (count && count > sizeof(socket->reason)))
+    if (socket->opcode != SOCKET_OPCODE_CLOSE ||
+        (count && (count < sizeof(socket->status) || count > sizeof(socket->status) + sizeof(socket->reason))))
     {
         ret = ERROR_WINHTTP_INVALID_SERVER_RESPONSE;
         goto done;
     }
 
-    if ((ret = receive_bytes( netconn, (char *)&socket->status, sizeof(socket->status), &count ))) goto done;
-    if (count != sizeof(socket->status))
+    if (count)
     {
-        ret = ERROR_WINHTTP_INVALID_SERVER_RESPONSE;
-        goto done;
-    }
-    socket->status = RtlUshortByteSwap( socket->status );
-    if (!(ret = receive_bytes( netconn, socket->reason, sizeof(socket->reason), &socket->reason_len )))
-    {
-        socket->state = SOCKET_STATE_CLOSED;
+        DWORD reason_len = count - sizeof(socket->status);
+        if ((ret = receive_bytes( netconn, (char *)&socket->status, sizeof(socket->status), &count ))) goto done;
+        socket->status = RtlUshortByteSwap( socket->status );
+        if ((ret = receive_bytes( netconn, socket->reason, reason_len, &socket->reason_len ))) goto done;
     }
+    socket->state = SOCKET_STATE_CLOSED;
 
 done:
     if (async)
-- 
2.20.1




More information about the wine-devel mailing list