From 198ef8b1de3ddac116baeaf5b86f2f8335e69e62 Mon Sep 17 00:00:00 2001 From: Christopher Faulet Date: Tue, 15 Dec 2020 13:32:55 +0100 Subject: [PATCH] BUG/MEDIUM: http-ana: Never for sending data in TUNNEL mode When a channel is set in TUNNEL mode, we now always set the CF_NEVER_WAIT flag, to be sure to never wait for sending data. It is important because in TUNNEL mode, we have no idea if more data are expected or not. Setting this flag prevent the MSG_MORE flag to be set on the connection. It is only a problem with the HTX, since the 2.2. On previous versions, the MSG_MORE flag is only set on the mux initiative. In fact, the problem arises because there is an ambiguity in tunnel mode about the HTX_FL_EOI flag. In this mode, from the mux point of view, while the SHUTR is not received more data are expected. But from the channel point of view, we want to send data asap. At short term, this fix is good enough and is valid anyway. But for the long term more reliable solution must be found. At least, the to_forward field must regain its original meaning. This patch must be backported as far as 2.2. --- src/http_ana.c | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-) diff --git a/src/http_ana.c b/src/http_ana.c index db98a5469..dd6ac4167 100644 --- a/src/http_ana.c +++ b/src/http_ana.c @@ -4225,8 +4225,11 @@ static void http_end_request(struct stream *s) end: chn->analysers &= AN_REQ_FLT_END; - if (txn->req.msg_state == HTTP_MSG_TUNNEL && HAS_REQ_DATA_FILTERS(s)) + if (txn->req.msg_state == HTTP_MSG_TUNNEL) { + chn->flags |= CF_NEVER_WAIT; + if (HAS_REQ_DATA_FILTERS(s)) chn->analysers |= AN_REQ_FLT_XFER_DATA; + } channel_auto_close(chn); channel_auto_read(chn); DBG_TRACE_LEAVE(STRM_EV_HTTP_ANA, s, txn); @@ -4280,7 +4283,6 @@ static void http_end_response(struct stream *s) */ if (txn->flags & TX_CON_WANT_TUN) { channel_auto_read(chn); - chn->flags |= CF_NEVER_WAIT; if (b_data(&chn->buf)) { DBG_TRACE_DEVEL("waiting to flush the respone", STRM_EV_HTTP_ANA, s, txn); return; @@ -4340,8 +4342,11 @@ static void http_end_response(struct stream *s) end: chn->analysers &= AN_RES_FLT_END; - if (txn->rsp.msg_state == HTTP_MSG_TUNNEL && HAS_RSP_DATA_FILTERS(s)) - chn->analysers |= AN_RES_FLT_XFER_DATA; + if (txn->rsp.msg_state == HTTP_MSG_TUNNEL) { + chn->flags |= CF_NEVER_WAIT; + if (HAS_RSP_DATA_FILTERS(s)) + chn->analysers |= AN_RES_FLT_XFER_DATA; + } channel_auto_close(chn); channel_auto_read(chn); DBG_TRACE_LEAVE(STRM_EV_HTTP_ANA, s, txn);