From 22be90b8db8393392e5b46b7dfff6f702db58687 Mon Sep 17 00:00:00 2001 From: Willy Tarreau Date: Wed, 11 May 2011 20:32:36 +0200 Subject: [PATCH] [OPTIM] stream_sock: avoid fast-forwarding of partial data Fast-forwarding between file descriptors is nice but can be counter-productive when only one part of the buffer is forwarded, because it can result in doubling the number of send() syscalls. This is what happens on HTTP chunking, because the chunk data are sent, then the CRLF + next chunk size are parsed and immediately scheduled for forwarding. This results in two send() for the same block while a single one would have done it. --- src/stream_sock.c | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/src/stream_sock.c b/src/stream_sock.c index b08134aef..5539cd205 100644 --- a/src/stream_sock.c +++ b/src/stream_sock.c @@ -473,8 +473,14 @@ int stream_sock_read(int fd) { } /* while (1) */ out_wakeup: - /* We might have some data the consumer is waiting for */ - if (!(b->flags & BF_OUT_EMPTY) && (b->cons->flags & SI_FL_WAIT_DATA)) { + /* We might have some data the consumer is waiting for. + * We can do fast-forwarding, but we avoid doing this for partial + * buffers, because it is very likely that it will be done again + * immediately afterwards once the following data is parsed (eg: + * HTTP chunking). + */ + if ((b->pipe || b->send_max == b->l) + && (b->cons->flags & SI_FL_WAIT_DATA)) { int last_len = b->pipe ? b->pipe->data : 0; b->cons->chk_snd(b->cons);