On Dec 17, 2005, at 11:32 AM, Ruediger Pluem wrote:

Index: server/core_filters.c
===================================================================
--- server/core_filters.c       (Revision 357328)
+++ server/core_filters.c       (Arbeitskopie)
@@ -315,8 +315,10 @@
apr_size_t *bytes_written,
                                              conn_rec *c);

-static void remove_empty_buckets(apr_bucket_brigade *bb);
+static void detect_error_bucket(apr_bucket *bucket, conn_rec *c);

+static void remove_empty_buckets(apr_bucket_brigade *bb, conn_rec *c);
+
 static apr_status_t send_brigade_blocking(apr_socket_t *s,
                                           apr_bucket_brigade *bb,
                                           apr_size_t *bytes_written,
@@ -487,7 +489,7 @@
     if (bb == NULL) {
         return;
     }
-    remove_empty_buckets(bb);
+    remove_empty_buckets(bb, c);
     if (!APR_BRIGADE_EMPTY(bb)) {
         c->data_in_output_filters = 1;
         if (make_a_copy) {
@@ -526,7 +528,7 @@
     struct iovec vec[MAX_IOVEC_TO_WRITE];
     apr_size_t nvec = 0;

-    remove_empty_buckets(bb);
+    remove_empty_buckets(bb, c);

     for (bucket = APR_BRIGADE_FIRST(bb);
          bucket != APR_BRIGADE_SENTINEL(bb);
@@ -596,16 +598,26 @@
         }
     }

-    remove_empty_buckets(bb);
+    remove_empty_buckets(bb, c);

     return APR_SUCCESS;
 }

-static void remove_empty_buckets(apr_bucket_brigade *bb)
+static void detect_error_bucket(apr_bucket *bucket, conn_rec *c)
 {
+    if (AP_BUCKET_IS_ERROR(bucket)
+ && (((ap_bucket_error *)(bucket->data))->status == HTTP_BAD_GATEWAY)) {
+        /* stream aborted and we have not ended it yet */
+        c->keepalive = AP_CONN_CLOSE;
+    }
+}
+
+static void remove_empty_buckets(apr_bucket_brigade *bb, conn_rec *c)
+{
     apr_bucket *bucket;
while (((bucket = APR_BRIGADE_FIRST(bb)) != APR_BRIGADE_SENTINEL(bb)) && (APR_BUCKET_IS_METADATA(bucket) || (bucket->length == 0))) {
+        detect_error_bucket(bucket, c);
         APR_BUCKET_REMOVE(bucket);
         apr_bucket_destroy(bucket);
     }
@@ -678,6 +690,7 @@
             for (i = offset; i < nvec; ) {
                 apr_bucket *bucket = APR_BRIGADE_FIRST(bb);
                 if (APR_BUCKET_IS_METADATA(bucket)) {
+                    detect_error_bucket(bucket, c);
                     APR_BUCKET_REMOVE(bucket);
                     apr_bucket_destroy(bucket);
                 }


I still think that having this http "specific" error mode
"hidden" within the core output filter is misguided. Instead,
a specific http output filter is, imo, a better place.

Even so, I say let's fold this into trunk as is, and
then work on abstracting it out.

Reply via email to