Blame SOURCES/CVE-2018-7159-reject-interior-blanks-in-Content-Length-backport.patch

89295e
diff -up http-parser-2.7.1/http_parser.c.cve http-parser-2.7.1/http_parser.c
89295e
--- http-parser-2.7.1/http_parser.c.cve	2019-03-23 08:58:04.459272497 +0100
89295e
+++ http-parser-2.7.1/http_parser.c	2019-03-23 08:58:21.204279947 +0100
89295e
@@ -376,6 +376,8 @@ enum header_states
89295e
 
89295e
   , h_connection
89295e
   , h_content_length
89295e
+  , h_content_length_num
89295e
+  , h_content_length_ws
89295e
   , h_transfer_encoding
89295e
   , h_upgrade
89295e
 
89295e
@@ -1478,6 +1480,7 @@ reexecute:
89295e
 
89295e
             parser->flags |= F_CONTENTLENGTH;
89295e
             parser->content_length = ch - '0';
89295e
+            parser->header_state = h_content_length_num;
89295e
             break;
89295e
 
89295e
           case h_connection:
89295e
@@ -1565,10 +1568,18 @@ reexecute:
89295e
               break;
89295e
 
89295e
             case h_content_length:
89295e
+              if (ch == ' ') break;
89295e
+              h_state = h_content_length_num;
89295e
+              /* FALLTHROUGH */
89295e
+
89295e
+            case h_content_length_num:
89295e
             {
89295e
               uint64_t t;
89295e
 
89295e
-              if (ch == ' ') break;
89295e
+              if (ch == ' ') {
89295e
+                h_state = h_content_length_ws;
89295e
+                break;
89295e
+              }
89295e
 
89295e
               if (UNLIKELY(!IS_NUM(ch))) {
89295e
                 SET_ERRNO(HPE_INVALID_CONTENT_LENGTH);
89295e
@@ -1591,6 +1602,12 @@ reexecute:
89295e
               break;
89295e
             }
89295e
 
89295e
+            case h_content_length_ws:
89295e
+              if (ch == ' ') break;
89295e
+              SET_ERRNO(HPE_INVALID_CONTENT_LENGTH);
89295e
+              parser->header_state = h_state;
89295e
+              goto error;
89295e
+
89295e
             /* Transfer-Encoding: chunked */
89295e
             case h_matching_transfer_encoding_chunked:
89295e
               parser->index++;
89295e
diff -up http-parser-2.7.1/test.c.cve http-parser-2.7.1/test.c
89295e
--- http-parser-2.7.1/test.c.cve	2019-03-23 08:57:50.851266439 +0100
89295e
+++ http-parser-2.7.1/test.c	2019-03-23 08:58:25.545281880 +0100
89295e
@@ -3947,6 +3947,27 @@ main (void)
89295e
   test_invalid_header_field_token_error(HTTP_RESPONSE);
89295e
   test_invalid_header_field_content_error(HTTP_RESPONSE);
89295e
 
89295e
+  test_simple_type(
89295e
+      "POST / HTTP/1.1\r\n"
89295e
+      "Content-Length:  42 \r\n"  // Note the surrounding whitespace.
89295e
+      "\r\n",
89295e
+      HPE_OK,
89295e
+      HTTP_REQUEST);
89295e
+
89295e
+  test_simple_type(
89295e
+      "POST / HTTP/1.1\r\n"
89295e
+      "Content-Length: 4 2\r\n"
89295e
+      "\r\n",
89295e
+      HPE_INVALID_CONTENT_LENGTH,
89295e
+      HTTP_REQUEST);
89295e
+
89295e
+  test_simple_type(
89295e
+      "POST / HTTP/1.1\r\n"
89295e
+      "Content-Length: 13 37\r\n"
89295e
+      "\r\n",
89295e
+      HPE_INVALID_CONTENT_LENGTH,
89295e
+      HTTP_REQUEST);
89295e
+
89295e
   //// RESPONSES
89295e
 
89295e
   for (i = 0; i < response_count; i++) {