diff options
Diffstat (limited to 'buckets/apr_brigade.c')
-rw-r--r-- | buckets/apr_brigade.c | 12 |
1 files changed, 9 insertions, 3 deletions
diff --git a/buckets/apr_brigade.c b/buckets/apr_brigade.c index 18c8f125..01e25c68 100644 --- a/buckets/apr_brigade.c +++ b/buckets/apr_brigade.c @@ -422,7 +422,12 @@ APU_DECLARE(apr_status_t) apr_brigade_write(apr_bucket_brigade *b, apr_size_t remaining = APR_BUCKET_BUFF_SIZE; char *buf = NULL; - if (!APR_BRIGADE_EMPTY(b) && APR_BUCKET_IS_HEAP(e)) { + /* + * If the last bucket is a heap bucket and its buffer is not shared with + * another bucket, we may write into that bucket. + */ + if (!APR_BRIGADE_EMPTY(b) && APR_BUCKET_IS_HEAP(e) + && ((apr_bucket_heap *)(e->data))->refcount.refcount == 1) { apr_bucket_heap *h = e->data; /* HEAP bucket start offsets are always in-memory, safe to cast */ @@ -512,10 +517,11 @@ APU_DECLARE(apr_status_t) apr_brigade_writev(apr_bucket_brigade *b, i = 0; /* If there is a heap bucket at the end of the brigade - * already, copy into the existing bucket. + * already, and its refcount is 1, copy into the existing bucket. */ e = APR_BRIGADE_LAST(b); - if (!APR_BRIGADE_EMPTY(b) && APR_BUCKET_IS_HEAP(e)) { + if (!APR_BRIGADE_EMPTY(b) && APR_BUCKET_IS_HEAP(e) + && ((apr_bucket_heap *)(e->data))->refcount.refcount == 1) { apr_bucket_heap *h = e->data; apr_size_t remaining = h->alloc_len - (e->length + (apr_size_t)e->start); |