From: Christopher Faulet Date: Fri, 7 Dec 2018 13:51:20 +0000 (+0100) Subject: BUG/MINOR: stream-int: Process read0 even if no data was received in si_cs_recv X-Git-Tag: v1.9-dev10~11 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=f061e422f726c5c387bb8199117d12b7474f5d25;p=thirdparty%2Fhaproxy.git BUG/MINOR: stream-int: Process read0 even if no data was received in si_cs_recv The flag CS_FL_EOS can be set while no data was received. So the flas CS_FL_RCV_MORE is not set. In this case, the read0 was never processed by the stream interface. To be sure to process it, the test on CS_FL_RCV_MORE has been moved after the one on CS_FL_EOS. --- diff --git a/src/stream_interface.c b/src/stream_interface.c index b4efe0c429..81e1778eab 100644 --- a/src/stream_interface.c +++ b/src/stream_interface.c @@ -1089,19 +1089,6 @@ int si_cs_recv(struct conn_stream *cs) int read_poll = MAX_READ_POLL_LOOPS; int flags = 0; - /* stop immediately on errors. Note that we DON'T want to stop on - * POLL_ERR, as the poller might report a write error while there - * are still data available in the recv buffer. This typically - * happens when we send too large a request to a backend server - * which rejects it before reading it all. - */ - if (!(cs->flags & CS_FL_RCV_MORE)) { - if (!conn_xprt_ready(conn)) - return 0; - if (conn->flags & CO_FL_ERROR || cs->flags & CS_FL_ERROR) - return 1; // We want to make sure si_cs_wake() is called, so that process_strema is woken up, on failure - } - /* If another call to si_cs_recv() failed, and we subscribed to * recv events already, give up now. */ @@ -1116,6 +1103,18 @@ int si_cs_recv(struct conn_stream *cs) if (cs->flags & CS_FL_EOS) goto out_shutdown_r; + /* stop immediately on errors. Note that we DON'T want to stop on + * POLL_ERR, as the poller might report a write error while there + * are still data available in the recv buffer. This typically + * happens when we send too large a request to a backend server + * which rejects it before reading it all. + */ + if (!(cs->flags & CS_FL_RCV_MORE)) { + if (!conn_xprt_ready(conn)) + return 0; + if (conn->flags & CO_FL_ERROR || cs->flags & CS_FL_ERROR) + return 1; // We want to make sure si_cs_wake() is called, so that process_strema is woken up, on failure + } if ((ic->flags & (CF_STREAMER | CF_STREAMER_FAST)) && !co_data(ic) && global.tune.idle_timer &&