[OPTIM] stream_sock_read must check for null-reads more often

With small HTTP messages, stream_sock_read() tends to wake the
task up for a message read without indicating that it may be
the last one. The reason is that level-triggered pollers generally
don't report HUP with data, but only afterwards, so stream_sock_read
has no chance to detect this condition and needs a respin.

So now we return on incomplete buffers only when the buffer is known
as a streamer, because here it generally makes sense. The net result
is that the number of calls in a single HTTP session has dropped
from 5 to 3, with one less wake up and several less calls to
stream_sock_data_update().
This commit is contained in:
Willy Tarreau 2008-08-28 09:47:43 +02:00
parent 3a16b2c9cd
commit 2bea3a1155

View File

@ -180,22 +180,34 @@ int stream_sock_read(int fd) {
//fputc('!', stderr);
}
}
/* unfortunately, on level-triggered events, POLL_HUP
* is generally delivered AFTER the system buffer is
* empty, so this one might never match.
*/
if (fdtab[fd].ev & FD_POLL_HUP)
goto out_shutdown_r;
break;
/* if a streamer has read few data, it may be because we
* have exhausted system buffers. It's not worth trying
* again.
*/
if (b->flags & BF_STREAMER)
break;
}
/* generally if we read something smaller than 1 or 2 MSS,
* it means that it's not worth trying to read again. It may
* also happen on headers, but the application then can stop
* reading before we start polling.
* it means that either we have exhausted the system's
* buffers (streamer or question-response protocol) or that
* the connection will be closed. Streamers are easily
* detected so we return early. For other cases, it's still
* better to perform a last read to be sure, because it may
* save one complete poll/read/wakeup cycle in case of shutdown.
*/
if (ret < MIN_RET_FOR_READ_LOOP)
if (ret < MIN_RET_FOR_READ_LOOP && b->flags & BF_STREAMER)
break;
if (--read_poll <= 0)
break;
}
else if (ret == 0) {
/* connection closed */