summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorBill Stoddard <stoddard@apache.org>2001-07-05 16:58:03 +0200
committerBill Stoddard <stoddard@apache.org>2001-07-05 16:58:03 +0200
commit6e2195d7df32117a99f4574e2eedfc137366cb60 (patch)
treea984a841723b1416a50479f677db34d38289af0f
parentinstall the man pages when we install everything else. (diff)
downloadapache2-6e2195d7df32117a99f4574e2eedfc137366cb60.tar.xz
apache2-6e2195d7df32117a99f4574e2eedfc137366cb60.zip
Do non-blocking reads from pipes in the content-length filter.
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@89501 13f79535-47bb-0310-9956-ffa450edef68
-rw-r--r--CHANGES2
-rw-r--r--server/protocol.c29
2 files changed, 26 insertions, 5 deletions
diff --git a/CHANGES b/CHANGES
index ce8f24ef5c..2a2585e79c 100644
--- a/CHANGES
+++ b/CHANGES
@@ -1,4 +1,6 @@
Changes with Apache 2.0.20-dev
+ *) Get non-blocking CGI pipe reads working with the bucket brigades.
+ [Bill Stoddard]
*) Fix seg fault on Windows when serving files cached with mod_file_cache.
[Bill Stoddard]
diff --git a/server/protocol.c b/server/protocol.c
index 31c60d97b5..b4eececce8 100644
--- a/server/protocol.c
+++ b/server/protocol.c
@@ -862,22 +862,41 @@ AP_CORE_DECLARE_NONSTD(apr_status_t) ap_content_length_filter(ap_filter_t *f,
APR_BRIGADE_FOREACH(e, b) {
const char *ignored;
- apr_size_t length;
+ apr_size_t len;
if (APR_BUCKET_IS_EOS(e) || APR_BUCKET_IS_FLUSH(e)) {
send_it = 1;
}
if (e->length == -1) { /* if length unknown */
- rv = apr_bucket_read(e, &ignored, &length, APR_BLOCK_READ);
+ rv = apr_bucket_read(e, &ignored, &len, APR_NONBLOCK_READ);
+ if (rv == APR_EAGAIN) {
+ /* If the protocol level implies support for chunked encoding,
+ * flush the filter chain to the network then do a blocking
+ * read. This is replicating the behaviour of ap_send_fb
+ * in Apache 1.3.
+ */
+ if (r->proto_num >= HTTP_VERSION(1,1)) {
+ apr_bucket_brigade *split;
+ split = apr_brigade_split(b, e);
+ rv = ap_fflush(f, b);
+ if (rv != APR_SUCCESS)
+ return rv;
+ b = split;
+ ctx->curr_len = 0;
+ }
+ rv = apr_bucket_read(e, &ignored, &len, APR_BLOCK_READ);
+ }
if (rv != APR_SUCCESS) {
+ ap_log_rerror(APLOG_MARK, APLOG_ERR, rv, r, "ap_content_length_filter: "
+ "apr_bucket_read() failed");
return rv;
}
}
else {
- length = e->length;
+ len = e->length;
}
- ctx->curr_len += length;
- r->bytes_sent += length;
+ ctx->curr_len += len;
+ r->bytes_sent += len;
}
if ((ctx->curr_len < AP_MIN_BYTES_TO_WRITE) && !send_it) {