mirror of
http://git.haproxy.org/git/haproxy.git/
synced 2024-12-17 17:04:35 +00:00
MEDIUM: http: start to centralize the forwarding code
Doing so avoids calling channel_forward() for each part of the chunk parsing and lowers the number of calls to channel_forward() to only one per buffer, resulting in about 11% performance increase on small chunks forwarding rate.
This commit is contained in:
parent
168ebc5e2b
commit
c623c17b13
@ -6219,28 +6219,28 @@ int http_response_forward_body(struct session *s, struct channel *res, int an_bi
|
||||
while (1) {
|
||||
http_silent_debug(__LINE__, s);
|
||||
|
||||
/* we may have some pending data starting at res->buf->p */
|
||||
if (s->comp_algo == NULL) {
|
||||
if (msg->chunk_len || msg->next) {
|
||||
msg->chunk_len += msg->next;
|
||||
msg->chunk_len -= channel_forward(res, msg->chunk_len);
|
||||
msg->next = 0;
|
||||
msg->sov = 0;
|
||||
}
|
||||
}
|
||||
|
||||
switch (msg->msg_state - HTTP_MSG_DATA) {
|
||||
case HTTP_MSG_DATA - HTTP_MSG_DATA: /* must still forward */
|
||||
if (compressing) {
|
||||
/* we may have some pending data starting at res->buf->p */
|
||||
if (unlikely(s->comp_algo)) {
|
||||
ret = http_compression_buffer_add_data(s, res->buf, tmpbuf);
|
||||
if (ret < 0)
|
||||
goto aborted_xfer;
|
||||
|
||||
if (res->to_forward || msg->chunk_len) {
|
||||
res->flags |= CF_WAKE_WRITE;
|
||||
goto missing_data;
|
||||
}
|
||||
}
|
||||
|
||||
if (res->to_forward || msg->chunk_len) {
|
||||
if (msg->chunk_len > res->buf->i - msg->next) {
|
||||
res->flags |= CF_WAKE_WRITE;
|
||||
goto missing_data;
|
||||
}
|
||||
else {
|
||||
msg->next += msg->chunk_len;
|
||||
msg->chunk_len = 0;
|
||||
}
|
||||
|
||||
/* nothing left to forward */
|
||||
if (msg->flags & HTTP_MSGF_TE_CHNK) {
|
||||
@ -6296,11 +6296,6 @@ int http_response_forward_body(struct session *s, struct channel *res, int an_bi
|
||||
http_capture_bad_message(&s->be->invalid_rep, s, msg, HTTP_MSG_TRAILERS, s->fe);
|
||||
goto return_bad_res;
|
||||
}
|
||||
/* forwarding trailers */
|
||||
channel_forward(res, msg->next);
|
||||
msg->next = 0;
|
||||
msg->sov = 0;
|
||||
|
||||
/* we're in HTTP_MSG_DONE now, fall through */
|
||||
|
||||
default:
|
||||
@ -6311,6 +6306,12 @@ int http_response_forward_body(struct session *s, struct channel *res, int an_bi
|
||||
compressing = 0;
|
||||
}
|
||||
|
||||
/* we may have some pending data starting at res->buf->p
|
||||
* such as a last chunk of data or trailers.
|
||||
*/
|
||||
b_adv(res->buf, msg->next);
|
||||
msg->next = 0;
|
||||
|
||||
ret = msg->msg_state;
|
||||
/* for keep-alive we don't want to forward closes on DONE */
|
||||
if ((txn->flags & TX_CON_WANT_MSK) == TX_CON_WANT_KAL ||
|
||||
@ -6339,11 +6340,18 @@ int http_response_forward_body(struct session *s, struct channel *res, int an_bi
|
||||
}
|
||||
|
||||
missing_data:
|
||||
/* we may have some pending data starting at res->buf->p */
|
||||
if (unlikely(compressing)) {
|
||||
http_compression_buffer_end(s, &res->buf, &tmpbuf, msg->msg_state >= HTTP_MSG_TRAILERS);
|
||||
compressing = 0;
|
||||
}
|
||||
|
||||
if ((s->comp_algo == NULL || msg->msg_state >= HTTP_MSG_TRAILERS)) {
|
||||
b_adv(res->buf, msg->next);
|
||||
msg->next = 0;
|
||||
msg->chunk_len -= channel_forward(res, msg->chunk_len);
|
||||
}
|
||||
|
||||
if (res->flags & CF_SHUTW)
|
||||
goto aborted_xfer;
|
||||
|
||||
@ -6367,16 +6375,6 @@ int http_response_forward_body(struct session *s, struct channel *res, int an_bi
|
||||
if (!s->req->analysers)
|
||||
goto return_bad_res;
|
||||
|
||||
/* forward any pending data starting at res->buf->p */
|
||||
if (s->comp_algo == NULL) {
|
||||
if (msg->chunk_len || msg->next) {
|
||||
msg->chunk_len += msg->next;
|
||||
msg->chunk_len -= channel_forward(res, msg->chunk_len);
|
||||
msg->next = 0;
|
||||
msg->sov = 0;
|
||||
}
|
||||
}
|
||||
|
||||
/* When TE: chunked is used, we need to get there again to parse remaining
|
||||
* chunks even if the server has closed, so we don't want to set CF_DONTCLOSE.
|
||||
* Similarly, with keep-alive on the client side, we don't want to forward a
|
||||
@ -6413,6 +6411,12 @@ int http_response_forward_body(struct session *s, struct channel *res, int an_bi
|
||||
compressing = 0;
|
||||
}
|
||||
|
||||
/* we may have some pending data starting at res->buf->p */
|
||||
if (s->comp_algo == NULL) {
|
||||
b_adv(res->buf, msg->next);
|
||||
msg->next = 0;
|
||||
}
|
||||
|
||||
txn->rsp.msg_state = HTTP_MSG_ERROR;
|
||||
/* don't send any error message as we're in the body */
|
||||
stream_int_retnclose(res->cons, NULL);
|
||||
|
Loading…
Reference in New Issue
Block a user