]> granicus.if.org Git - apache/commitdiff
Clean up an edge case where obs-fold continuation preceeds the first header,
authorWilliam A. Rowe Jr <wrowe@apache.org>
Wed, 3 Aug 2016 22:42:26 +0000 (22:42 +0000)
committerWilliam A. Rowe Jr <wrowe@apache.org>
Wed, 3 Aug 2016 22:42:26 +0000 (22:42 +0000)
as with r1755098, but this time ensure the previous header processing logic
ensures there was a previous header as identified by jchampion.

This patch restructures the loop for legibility with a loop continuation,
allowing us to flatten all of this hard-to-follow code. The subsequent
patch will be a whitespace-only change for formatting.

git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1755123 13f79535-47bb-0310-9956-ffa450edef68

server/protocol.c

index 60be6fb12ae6f74e2d4c274c37b5773de25a7435..2f623b1c803245e3e597e0f13ead99d18b216469 100644 (file)
@@ -835,15 +835,25 @@ AP_DECLARE(void) ap_get_mime_headers_core(request_rec *r, apr_bucket_brigade *bb
             return;
         }
 
-        if (last_field != NULL) {
-            if ((len > 0) && ((*field == '\t') || *field == ' ')) {
+        if ((len > 0) && ((*field == '\t') || *field == ' ')) {
+
+            apr_size_t fold_len;
+
+            if (last_field == NULL) {
+                r->status = HTTP_BAD_REQUEST;
+                ap_log_rerror(APLOG_MARK, APLOG_INFO, 0, r, APLOGNO(03442)
+                              "Line folding encounterd before first"
+                              " header line");
+                return;
+            }
+
                 /* This line is a continuation of the preceding line(s),
                  * so append it to the line that we've set aside.
                  * Note: this uses a power-of-two allocator to avoid
                  * doing O(n) allocs and using O(n^2) space for
                  * continuations that span many many lines.
                  */
-                apr_size_t fold_len = last_len + len + 1; /* trailing null */
+                fold_len = last_len + len + 1; /* trailing null */
 
                 if (fold_len >= (apr_size_t)(r->server->limit_req_fieldsize)) {
                     const char *field_escaped;
@@ -885,8 +895,11 @@ AP_DECLARE(void) ap_get_mime_headers_core(request_rec *r, apr_bucket_brigade *bb
                 }
                 last_len += len;
                 folded = 1;
-            }
-            else /* not a continuation line */ {
+                continue;
+        }
+        else if (last_field != NULL) {
+
+                /* not a continuation line */
 
                 if (r->server->limit_req_fields
                     && (++fields_read > r->server->limit_req_fields)) {
@@ -1008,8 +1021,7 @@ AP_DECLARE(void) ap_get_mime_headers_core(request_rec *r, apr_bucket_brigade *bb
                  * now part of r->headers_in
                  */
                 alloc_len = 0;
-
-            } /* end if current line is not a continuation starting with tab */
+                /* end of logic where current line was not a continuation line */
         }
 
         /* Found a blank line, stop. */