https://git.reactos.org/?p=reactos.git;a=commitdiff;h=208ef143d3ed2a55e7c1d57b8db776dabaa1073f

commit 208ef143d3ed2a55e7c1d57b8db776dabaa1073f
Author:     winesync <[email protected]>
AuthorDate: Tue Dec 8 18:31:47 2020 +0100
Commit:     Jérôme Gardou <[email protected]>
CommitDate: Tue Jan 5 11:03:13 2021 +0100

    [WINESYNC] wininet: Replacing header fields should fail if they do not 
exist yet.
    
    A lot of details are not properly covered by tests yet and were
    marked with FIXME comments. The implementation was written in such
    a way that it behaves identical to the old code in such situations.
    
    wine-staging patch by Michael Müller <[email protected]>
---
 dll/win32/wininet/http.c                           | 185 ++++++++---------
 ...ields_should_fail_if_they_do_not_exist_yet.diff | 225 +++++++++++++++++++++
 2 files changed, 318 insertions(+), 92 deletions(-)

diff --git a/dll/win32/wininet/http.c b/dll/win32/wininet/http.c
index 28d48c1eb6b..7f0c1073b3b 100644
--- a/dll/win32/wininet/http.c
+++ b/dll/win32/wininet/http.c
@@ -6116,127 +6116,128 @@ static LPWSTR * HTTP_InterpretHttpHeader(LPCWSTR 
buffer)
 
 static DWORD HTTP_ProcessHeader(http_request_t *request, LPCWSTR field, 
LPCWSTR value, DWORD dwModifier)
 {
-    LPHTTPHEADERW lphttpHdr = NULL;
+    LPHTTPHEADERW lphttpHdr;
     INT index;
     BOOL request_only = !!(dwModifier & HTTP_ADDHDR_FLAG_REQ);
-    DWORD res = ERROR_HTTP_INVALID_HEADER;
+    DWORD res = ERROR_SUCCESS;
 
     TRACE("--> %s: %s - 0x%08x\n", debugstr_w(field), debugstr_w(value), 
dwModifier);
 
     EnterCriticalSection( &request->headers_section );
 
-    /* REPLACE wins out over ADD */
-    if (dwModifier & HTTP_ADDHDR_FLAG_REPLACE)
-        dwModifier &= ~HTTP_ADDHDR_FLAG_ADD;
-
-    if (dwModifier & HTTP_ADDHDR_FLAG_ADD)
-        index = -1;
-    else
-        index = HTTP_GetCustomHeaderIndex(request, field, 0, request_only);
-
+    index = HTTP_GetCustomHeaderIndex(request, field, 0, request_only);
     if (index >= 0)
     {
-        if (dwModifier & HTTP_ADDHDR_FLAG_ADD_IF_NEW)
-        {
-            LeaveCriticalSection( &request->headers_section );
-            return ERROR_HTTP_INVALID_HEADER;
-        }
         lphttpHdr = &request->custHeaders[index];
-    }
-    else if (value)
-    {
-        HTTPHEADERW hdr;
 
-        hdr.lpszField = (LPWSTR)field;
-        hdr.lpszValue = (LPWSTR)value;
-        hdr.wFlags = hdr.wCount = 0;
+        /* replace existing header if FLAG_REPLACE is given */
+        if (dwModifier & HTTP_ADDHDR_FLAG_REPLACE)
+        {
+            HTTP_DeleteCustomHeader( request, index );
 
-        if (dwModifier & HTTP_ADDHDR_FLAG_REQ)
-            hdr.wFlags |= HDR_ISREQUEST;
+            if (value && value[0])
+            {
+                HTTPHEADERW hdr;
 
-        res = HTTP_InsertCustomHeader(request, &hdr);
-        LeaveCriticalSection( &request->headers_section );
-        return res;
-    }
-    /* no value to delete */
-    else
-    {
-        LeaveCriticalSection( &request->headers_section );
-        return ERROR_SUCCESS;
-    }
+                hdr.lpszField = (LPWSTR)field;
+                hdr.lpszValue = (LPWSTR)value;
+                hdr.wFlags = hdr.wCount = 0;
 
-    if (dwModifier & HTTP_ADDHDR_FLAG_REQ)
-           lphttpHdr->wFlags |= HDR_ISREQUEST;
-    else
-        lphttpHdr->wFlags &= ~HDR_ISREQUEST;
+                if (dwModifier & HTTP_ADDHDR_FLAG_REQ)
+                    hdr.wFlags |= HDR_ISREQUEST;
 
-    if (dwModifier & HTTP_ADDHDR_FLAG_REPLACE)
-    {
-        HTTP_DeleteCustomHeader( request, index );
+                res = HTTP_InsertCustomHeader( request, &hdr );
+            }
+
+            goto out;
+        }
 
-        if (value && value[0])
+        /* do not add new header if FLAG_ADD_IF_NEW is set */
+        if (dwModifier & HTTP_ADDHDR_FLAG_ADD_IF_NEW)
         {
-            HTTPHEADERW hdr;
+            res = ERROR_HTTP_INVALID_HEADER; /* FIXME */
+            goto out;
+        }
 
-            hdr.lpszField = (LPWSTR)field;
-            hdr.lpszValue = (LPWSTR)value;
-            hdr.wFlags = hdr.wCount = 0;
+        /* handle appending to existing header */
+        if (dwModifier & COALESCEFLAGS)
+        {
+            LPWSTR lpsztmp;
+            WCHAR ch = 0;
+            INT len = 0;
+            INT origlen = lstrlenW(lphttpHdr->lpszValue);
+            INT valuelen = lstrlenW(value);
 
+            /* FIXME: Should it really clear HDR_ISREQUEST? */
             if (dwModifier & HTTP_ADDHDR_FLAG_REQ)
-                hdr.wFlags |= HDR_ISREQUEST;
-
-            res = HTTP_InsertCustomHeader(request, &hdr);
-            LeaveCriticalSection( &request->headers_section );
-            return res;
-        }
+                lphttpHdr->wFlags |= HDR_ISREQUEST;
+            else
+                lphttpHdr->wFlags &= ~HDR_ISREQUEST;
 
-        LeaveCriticalSection( &request->headers_section );
-        return ERROR_SUCCESS;
-    }
-    else if (dwModifier & COALESCEFLAGS)
-    {
-        LPWSTR lpsztmp;
-        WCHAR ch = 0;
-        INT len = 0;
-        INT origlen = lstrlenW(lphttpHdr->lpszValue);
-        INT valuelen = lstrlenW(value);
+            if (dwModifier & HTTP_ADDHDR_FLAG_COALESCE_WITH_COMMA)
+            {
+                ch = ',';
+                lphttpHdr->wFlags |= HDR_COMMADELIMITED;
+            }
+            else if (dwModifier & HTTP_ADDHDR_FLAG_COALESCE_WITH_SEMICOLON)
+            {
+                ch = ';';
+                lphttpHdr->wFlags |= HDR_COMMADELIMITED;
+            }
 
-        if (dwModifier & HTTP_ADDHDR_FLAG_COALESCE_WITH_COMMA)
-        {
-            ch = ',';
-            lphttpHdr->wFlags |= HDR_COMMADELIMITED;
-        }
-        else if (dwModifier & HTTP_ADDHDR_FLAG_COALESCE_WITH_SEMICOLON)
-        {
-            ch = ';';
-            lphttpHdr->wFlags |= HDR_COMMADELIMITED;
-        }
+            len = origlen + valuelen + ((ch > 0) ? 2 : 0);
 
-        len = origlen + valuelen + ((ch > 0) ? 2 : 0);
+            lpsztmp = heap_realloc(lphttpHdr->lpszValue, 
(len+1)*sizeof(WCHAR));
+            if (lpsztmp)
+            {
+                lphttpHdr->lpszValue = lpsztmp;
+                /* FIXME: Increment lphttpHdr->wCount. Perhaps lpszValue 
should be an array */
+                if (ch > 0)
+                {
+                    lphttpHdr->lpszValue[origlen] = ch;
+                    origlen++;
+                    lphttpHdr->lpszValue[origlen] = ' ';
+                    origlen++;
+                }
 
-        lpsztmp = heap_realloc(lphttpHdr->lpszValue, (len+1)*sizeof(WCHAR));
-        if (lpsztmp)
-        {
-            lphttpHdr->lpszValue = lpsztmp;
-    /* FIXME: Increment lphttpHdr->wCount. Perhaps lpszValue should be an 
array */
-            if (ch > 0)
+                memcpy(&lphttpHdr->lpszValue[origlen], value, 
valuelen*sizeof(WCHAR));
+                lphttpHdr->lpszValue[len] = '\0';
+            }
+            else
             {
-                lphttpHdr->lpszValue[origlen] = ch;
-                origlen++;
-                lphttpHdr->lpszValue[origlen] = ' ';
-                origlen++;
+                WARN("heap_realloc (%d bytes) failed\n",len+1);
+                res = ERROR_OUTOFMEMORY;
             }
 
-            memcpy(&lphttpHdr->lpszValue[origlen], value, 
valuelen*sizeof(WCHAR));
-            lphttpHdr->lpszValue[len] = '\0';
-            res = ERROR_SUCCESS;
-        }
-        else
-        {
-            WARN("heap_realloc (%d bytes) failed\n",len+1);
-            res = ERROR_OUTOFMEMORY;
+            goto out;
         }
     }
+
+    /* FIXME: What about other combinations? */
+    if ((dwModifier & ~HTTP_ADDHDR_FLAG_REQ) == HTTP_ADDHDR_FLAG_REPLACE)
+    {
+        res = ERROR_HTTP_HEADER_NOT_FOUND;
+        goto out;
+    }
+
+    /* FIXME: What if value == ""? */
+    if (value)
+    {
+        HTTPHEADERW hdr;
+
+        hdr.lpszField = (LPWSTR)field;
+        hdr.lpszValue = (LPWSTR)value;
+        hdr.wFlags = hdr.wCount = 0;
+
+        if (dwModifier & HTTP_ADDHDR_FLAG_REQ)
+            hdr.wFlags |= HDR_ISREQUEST;
+
+        res = HTTP_InsertCustomHeader( request, &hdr );
+        goto out;
+    }
+
+    /* FIXME: What if value == NULL? */
+out:
     TRACE("<-- %d\n", res);
     LeaveCriticalSection( &request->headers_section );
     return res;
diff --git 
a/sdk/tools/winesync/wininet_staging/0005-wininet__Replacing_header_fields_should_fail_if_they_do_not_exist_yet.diff
 
b/sdk/tools/winesync/wininet_staging/0005-wininet__Replacing_header_fields_should_fail_if_they_do_not_exist_yet.diff
new file mode 100644
index 00000000000..9d5ab4e28a6
--- /dev/null
+++ 
b/sdk/tools/winesync/wininet_staging/0005-wininet__Replacing_header_fields_should_fail_if_they_do_not_exist_yet.diff
@@ -0,0 +1,225 @@
+diff --git a/dll/win32/wininet/http.c b/dll/win32/wininet/http.c
+index f7d9e29b96..09566b7cde 100644
+--- a/dll/win32/wininet/http.c
++++ b/dll/win32/wininet/http.c
+@@ -6112,127 +6112,128 @@ static LPWSTR * HTTP_InterpretHttpHeader(LPCWSTR 
buffer)
+ 
+ static DWORD HTTP_ProcessHeader(http_request_t *request, LPCWSTR field, 
LPCWSTR value, DWORD dwModifier)
+ {
+-    LPHTTPHEADERW lphttpHdr = NULL;
++    LPHTTPHEADERW lphttpHdr;
+     INT index;
+     BOOL request_only = !!(dwModifier & HTTP_ADDHDR_FLAG_REQ);
+-    DWORD res = ERROR_HTTP_INVALID_HEADER;
++    DWORD res = ERROR_SUCCESS;
+ 
+     TRACE("--> %s: %s - 0x%08x\n", debugstr_w(field), debugstr_w(value), 
dwModifier);
+ 
+     EnterCriticalSection( &request->headers_section );
+ 
+-    /* REPLACE wins out over ADD */
+-    if (dwModifier & HTTP_ADDHDR_FLAG_REPLACE)
+-        dwModifier &= ~HTTP_ADDHDR_FLAG_ADD;
+-
+-    if (dwModifier & HTTP_ADDHDR_FLAG_ADD)
+-        index = -1;
+-    else
+-        index = HTTP_GetCustomHeaderIndex(request, field, 0, request_only);
+-
++    index = HTTP_GetCustomHeaderIndex(request, field, 0, request_only);
+     if (index >= 0)
+     {
+-        if (dwModifier & HTTP_ADDHDR_FLAG_ADD_IF_NEW)
+-        {
+-            LeaveCriticalSection( &request->headers_section );
+-            return ERROR_HTTP_INVALID_HEADER;
+-        }
+         lphttpHdr = &request->custHeaders[index];
+-    }
+-    else if (value)
+-    {
+-        HTTPHEADERW hdr;
+ 
+-        hdr.lpszField = (LPWSTR)field;
+-        hdr.lpszValue = (LPWSTR)value;
+-        hdr.wFlags = hdr.wCount = 0;
++        /* replace existing header if FLAG_REPLACE is given */
++        if (dwModifier & HTTP_ADDHDR_FLAG_REPLACE)
++        {
++            HTTP_DeleteCustomHeader( request, index );
+ 
+-        if (dwModifier & HTTP_ADDHDR_FLAG_REQ)
+-            hdr.wFlags |= HDR_ISREQUEST;
++            if (value && value[0])
++            {
++                HTTPHEADERW hdr;
+ 
+-        res = HTTP_InsertCustomHeader(request, &hdr);
+-        LeaveCriticalSection( &request->headers_section );
+-        return res;
+-    }
+-    /* no value to delete */
+-    else
+-    {
+-        LeaveCriticalSection( &request->headers_section );
+-        return ERROR_SUCCESS;
+-    }
++                hdr.lpszField = (LPWSTR)field;
++                hdr.lpszValue = (LPWSTR)value;
++                hdr.wFlags = hdr.wCount = 0;
+ 
+-    if (dwModifier & HTTP_ADDHDR_FLAG_REQ)
+-          lphttpHdr->wFlags |= HDR_ISREQUEST;
+-    else
+-        lphttpHdr->wFlags &= ~HDR_ISREQUEST;
++                if (dwModifier & HTTP_ADDHDR_FLAG_REQ)
++                    hdr.wFlags |= HDR_ISREQUEST;
+ 
+-    if (dwModifier & HTTP_ADDHDR_FLAG_REPLACE)
+-    {
+-        HTTP_DeleteCustomHeader( request, index );
++                res = HTTP_InsertCustomHeader( request, &hdr );
++            }
++
++            goto out;
++        }
+ 
+-        if (value && value[0])
++        /* do not add new header if FLAG_ADD_IF_NEW is set */
++        if (dwModifier & HTTP_ADDHDR_FLAG_ADD_IF_NEW)
+         {
+-            HTTPHEADERW hdr;
++            res = ERROR_HTTP_INVALID_HEADER; /* FIXME */
++            goto out;
++        }
+ 
+-            hdr.lpszField = (LPWSTR)field;
+-            hdr.lpszValue = (LPWSTR)value;
+-            hdr.wFlags = hdr.wCount = 0;
++        /* handle appending to existing header */
++        if (dwModifier & COALESCEFLAGS)
++        {
++            LPWSTR lpsztmp;
++            WCHAR ch = 0;
++            INT len = 0;
++            INT origlen = lstrlenW(lphttpHdr->lpszValue);
++            INT valuelen = lstrlenW(value);
+ 
++            /* FIXME: Should it really clear HDR_ISREQUEST? */
+             if (dwModifier & HTTP_ADDHDR_FLAG_REQ)
+-                hdr.wFlags |= HDR_ISREQUEST;
+-
+-            res = HTTP_InsertCustomHeader(request, &hdr);
+-            LeaveCriticalSection( &request->headers_section );
+-            return res;
+-        }
++                lphttpHdr->wFlags |= HDR_ISREQUEST;
++            else
++                lphttpHdr->wFlags &= ~HDR_ISREQUEST;
+ 
+-        LeaveCriticalSection( &request->headers_section );
+-        return ERROR_SUCCESS;
+-    }
+-    else if (dwModifier & COALESCEFLAGS)
+-    {
+-        LPWSTR lpsztmp;
+-        WCHAR ch = 0;
+-        INT len = 0;
+-        INT origlen = lstrlenW(lphttpHdr->lpszValue);
+-        INT valuelen = lstrlenW(value);
++            if (dwModifier & HTTP_ADDHDR_FLAG_COALESCE_WITH_COMMA)
++            {
++                ch = ',';
++                lphttpHdr->wFlags |= HDR_COMMADELIMITED;
++            }
++            else if (dwModifier & HTTP_ADDHDR_FLAG_COALESCE_WITH_SEMICOLON)
++            {
++                ch = ';';
++                lphttpHdr->wFlags |= HDR_COMMADELIMITED;
++            }
+ 
+-        if (dwModifier & HTTP_ADDHDR_FLAG_COALESCE_WITH_COMMA)
+-        {
+-            ch = ',';
+-            lphttpHdr->wFlags |= HDR_COMMADELIMITED;
+-        }
+-        else if (dwModifier & HTTP_ADDHDR_FLAG_COALESCE_WITH_SEMICOLON)
+-        {
+-            ch = ';';
+-            lphttpHdr->wFlags |= HDR_COMMADELIMITED;
+-        }
++            len = origlen + valuelen + ((ch > 0) ? 2 : 0);
+ 
+-        len = origlen + valuelen + ((ch > 0) ? 2 : 0);
++            lpsztmp = heap_realloc(lphttpHdr->lpszValue, 
(len+1)*sizeof(WCHAR));
++            if (lpsztmp)
++            {
++                lphttpHdr->lpszValue = lpsztmp;
++                /* FIXME: Increment lphttpHdr->wCount. Perhaps lpszValue 
should be an array */
++                if (ch > 0)
++                {
++                    lphttpHdr->lpszValue[origlen] = ch;
++                    origlen++;
++                    lphttpHdr->lpszValue[origlen] = ' ';
++                    origlen++;
++                }
+ 
+-        lpsztmp = heap_realloc(lphttpHdr->lpszValue, (len+1)*sizeof(WCHAR));
+-        if (lpsztmp)
+-        {
+-            lphttpHdr->lpszValue = lpsztmp;
+-    /* FIXME: Increment lphttpHdr->wCount. Perhaps lpszValue should be an 
array */
+-            if (ch > 0)
++                memcpy(&lphttpHdr->lpszValue[origlen], value, 
valuelen*sizeof(WCHAR));
++                lphttpHdr->lpszValue[len] = '\0';
++            }
++            else
+             {
+-                lphttpHdr->lpszValue[origlen] = ch;
+-                origlen++;
+-                lphttpHdr->lpszValue[origlen] = ' ';
+-                origlen++;
++                WARN("heap_realloc (%d bytes) failed\n",len+1);
++                res = ERROR_OUTOFMEMORY;
+             }
+ 
+-            memcpy(&lphttpHdr->lpszValue[origlen], value, 
valuelen*sizeof(WCHAR));
+-            lphttpHdr->lpszValue[len] = '\0';
+-            res = ERROR_SUCCESS;
+-        }
+-        else
+-        {
+-            WARN("heap_realloc (%d bytes) failed\n",len+1);
+-            res = ERROR_OUTOFMEMORY;
++            goto out;
+         }
+     }
++
++    /* FIXME: What about other combinations? */
++    if ((dwModifier & ~HTTP_ADDHDR_FLAG_REQ) == HTTP_ADDHDR_FLAG_REPLACE)
++    {
++        res = ERROR_HTTP_HEADER_NOT_FOUND;
++        goto out;
++    }
++
++    /* FIXME: What if value == ""? */
++    if (value)
++    {
++        HTTPHEADERW hdr;
++
++        hdr.lpszField = (LPWSTR)field;
++        hdr.lpszValue = (LPWSTR)value;
++        hdr.wFlags = hdr.wCount = 0;
++
++        if (dwModifier & HTTP_ADDHDR_FLAG_REQ)
++            hdr.wFlags |= HDR_ISREQUEST;
++
++        res = HTTP_InsertCustomHeader( request, &hdr );
++        goto out;
++    }
++
++    /* FIXME: What if value == NULL? */
++out:
+     TRACE("<-- %d\n", res);
+     LeaveCriticalSection( &request->headers_section );
+     return res;

Reply via email to