You are viewing a plain text version of this content. The canonical link for it is here.
Posted to cvs@httpd.apache.org by rp...@apache.org on 2005/10/21 23:54:32 UTC

svn commit: r327592 - in /httpd/httpd/branches/2.2.x: CHANGES modules/proxy/mod_proxy_http.c

Author: rpluem
Date: Fri Oct 21 14:54:27 2005
New Revision: 327592

URL: http://svn.apache.org/viewcvs?rev=327592&view=rev
Log:
Merge r327590 from trunk:

* Fix PR37145 (data loss with httpd-2.0.55 reverse proxy method=post) by
  exchanging APR_BRIGADE_CONCAT with ap_save_brigade to ensure that
  transient buckets get setaside correctly between various iterations of
  ap_get_brigade calls.

Reviewed by: Joe Orton, William Rowe, Jim Jagielski, Jeff Trawick

Modified:
    httpd/httpd/branches/2.2.x/CHANGES
    httpd/httpd/branches/2.2.x/modules/proxy/mod_proxy_http.c

Modified: httpd/httpd/branches/2.2.x/CHANGES
URL: http://svn.apache.org/viewcvs/httpd/httpd/branches/2.2.x/CHANGES?rev=327592&r1=327591&r2=327592&view=diff
==============================================================================
--- httpd/httpd/branches/2.2.x/CHANGES [utf-8] (original)
+++ httpd/httpd/branches/2.2.x/CHANGES [utf-8] Fri Oct 21 14:54:27 2005
@@ -1,6 +1,10 @@
                                                         -*- coding: utf-8 -*-
 Changes with Apache 2.1.9
 
+  *) mod_proxy_http: Prevent data corruption of POST request bodies when
+     client accesses proxied resources with SSL. PR37145.
+     [Ruediger Pluem, William Rowe]
+
   *) mod_ssl: Fix issue which could cause spurious warnings about use
      of name-based vhosts.  PR 37051.  [Joe Orton]
 

Modified: httpd/httpd/branches/2.2.x/modules/proxy/mod_proxy_http.c
URL: http://svn.apache.org/viewcvs/httpd/httpd/branches/2.2.x/modules/proxy/mod_proxy_http.c?rev=327592&r1=327591&r2=327592&view=diff
==============================================================================
--- httpd/httpd/branches/2.2.x/modules/proxy/mod_proxy_http.c (original)
+++ httpd/httpd/branches/2.2.x/modules/proxy/mod_proxy_http.c Fri Oct 21 14:54:27 2005
@@ -247,7 +247,21 @@
              * take care of that now
              */
             bb = header_brigade;
-            APR_BRIGADE_CONCAT(bb, input_brigade);
+
+            /*
+             * Save input_brigade in bb brigade. (At least) in the SSL case
+             * input_brigade contains transient buckets whose data would get
+             * overwritten during the next call of ap_get_brigade in the loop.
+             * ap_save_brigade ensures these buckets to be set aside.
+             * Calling ap_save_brigade with NULL as filter is OK, because
+             * bb brigade already has been created and does not need to get
+             * created by ap_save_brigade.
+             */
+            status = ap_save_brigade(NULL, &bb, &input_brigade, p);
+            if (status != APR_SUCCESS) {
+                return status;
+            }
+
             header_brigade = NULL;
         }
         else {
@@ -354,7 +368,21 @@
              * take care of that now
              */
             bb = header_brigade;
-            APR_BRIGADE_CONCAT(bb, input_brigade);
+
+            /*
+             * Save input_brigade in bb brigade. (At least) in the SSL case
+             * input_brigade contains transient buckets whose data would get
+             * overwritten during the next call of ap_get_brigade in the loop.
+             * ap_save_brigade ensures these buckets to be set aside.
+             * Calling ap_save_brigade with NULL as filter is OK, because
+             * bb brigade already has been created and does not need to get
+             * created by ap_save_brigade.
+             */
+            status = ap_save_brigade(NULL, &bb, &input_brigade, p);
+            if (status != APR_SUCCESS) {
+                return status;
+            }
+
             header_brigade = NULL;
         }
         else {
@@ -476,7 +504,21 @@
             apr_brigade_cleanup(input_brigade);
         }
         else {
-            APR_BRIGADE_CONCAT(body_brigade, input_brigade);
+
+            /*
+             * Save input_brigade in body_brigade. (At least) in the SSL case
+             * input_brigade contains transient buckets whose data would get
+             * overwritten during the next call of ap_get_brigade in the loop.
+             * ap_save_brigade ensures these buckets to be set aside.
+             * Calling ap_save_brigade with NULL as filter is OK, because
+             * body_brigade already has been created and does not need to get
+             * created by ap_save_brigade.
+             */
+            status = ap_save_brigade(NULL, &body_brigade, &input_brigade, p);
+            if (status != APR_SUCCESS) {
+                return status;
+            }
+
         }
         
         bytes_spooled += bytes;
@@ -832,8 +874,26 @@
         }
 
         apr_brigade_length(temp_brigade, 1, &bytes);
-        APR_BRIGADE_CONCAT(input_brigade, temp_brigade);
         bytes_read += bytes;
+
+        /*
+         * Save temp_brigade in input_brigade. (At least) in the SSL case
+         * temp_brigade contains transient buckets whose data would get
+         * overwritten during the next call of ap_get_brigade in the loop.
+         * ap_save_brigade ensures these buckets to be set aside.
+         * Calling ap_save_brigade with NULL as filter is OK, because
+         * input_brigade already has been created and does not need to get
+         * created by ap_save_brigade.
+         */
+        status = ap_save_brigade(NULL, &input_brigade, &temp_brigade, p);
+        if (status != APR_SUCCESS) {
+            ap_log_error(APLOG_MARK, APLOG_ERR, status, r->server,
+                         "proxy: processing prefetched request body failed"
+                         " to %pI (%s) from %s (%s)",
+                         p_conn->addr, p_conn->hostname ? p_conn->hostname: "",
+                         c->remote_ip, c->remote_host ? c->remote_host: "");
+            return status;
+        }
 
     /* Ensure we don't hit a wall where we have a buffer too small
      * for ap_get_brigade's filters to fetch us another bucket,