]> git.kaiwu.me - nginx.git/commitdiff
Request body: optimized handling of small chunks.
authorMaxim Dounin <mdounin@mdounin.ru>
Thu, 6 Aug 2020 02:02:57 +0000 (05:02 +0300)
committerMaxim Dounin <mdounin@mdounin.ru>
Thu, 6 Aug 2020 02:02:57 +0000 (05:02 +0300)
If there is a previous buffer, copy small chunks into it instead of
allocating additional buffer.

src/http/ngx_http_request_body.c

index 106ac3dc6e4e711aac17302ec2ac1cac623009a3..71d7e9ab873cfb9abe45aed305652dbc7e5ea3fb 100644 (file)
@@ -1027,6 +1027,8 @@ ngx_http_request_body_chunked_filter(ngx_http_request_t *r, ngx_chain_t *in)
 
     for (cl = in; cl; cl = cl->next) {
 
+        b = NULL;
+
         for ( ;; ) {
 
             ngx_log_debug7(NGX_LOG_DEBUG_EVENT, r->connection->log, 0,
@@ -1061,6 +1063,29 @@ ngx_http_request_body_chunked_filter(ngx_http_request_t *r, ngx_chain_t *in)
                     return NGX_HTTP_REQUEST_ENTITY_TOO_LARGE;
                 }
 
+                if (b
+                    && rb->chunked->size <= 128
+                    && cl->buf->last - cl->buf->pos >= rb->chunked->size)
+                {
+                    r->headers_in.content_length_n += rb->chunked->size;
+
+                    if (rb->chunked->size < 8) {
+
+                        while (rb->chunked->size) {
+                            *b->last++ = *cl->buf->pos++;
+                            rb->chunked->size--;
+                        }
+
+                    } else {
+                        ngx_memmove(b->last, cl->buf->pos, rb->chunked->size);
+                        b->last += rb->chunked->size;
+                        cl->buf->pos += rb->chunked->size;
+                        rb->chunked->size = 0;
+                    }
+
+                    continue;
+                }
+
                 tl = ngx_chain_get_free_buf(r->pool, &rb->free);
                 if (tl == NULL) {
                     return NGX_HTTP_INTERNAL_SERVER_ERROR;