/* Forward all headers of an HTX message, starting from the SL to the EOH. This
- * function also updates the first block position.
+ * function returns the position of the block after the EOH, if
+ * found. Otherwise, it returns -1.
*/
-static inline void channel_htx_fwd_headers(struct channel *chn, struct htx *htx)
+static inline int32_t channel_htx_fwd_headers(struct channel *chn, struct htx *htx)
{
int32_t pos;
size_t data = 0;
struct htx_blk *blk = htx_get_blk(htx, pos);
data += htx_get_blksz(blk);
if (htx_get_blk_type(blk) == HTX_BLK_EOH) {
- htx->first = htx_get_next(htx, pos);
+ pos = htx_get_next(htx, pos);
break;
}
}
c_adv(chn, data);
+ return pos;
}
/* Forward <data> bytes of payload of an HTX message. This function also updates
{
struct filter *filter;
unsigned long long *strm_off = &FLT_STRM_OFF(s, msg->chn);
- int ret = len - co_data(msg->chn);
+ unsigned int out = co_data(msg->chn);
+ int ret = len - out;
list_for_each_entry(filter, &strm_flt(s)->filters, list) {
/* Call "data" filters only */
unsigned long long *flt_off = &FLT_OFF(filter, msg->chn);
unsigned int offset = *flt_off - *strm_off;
- ret = FLT_OPS(filter)->http_payload(s, filter, msg, offset, ret - offset);
+ ret = FLT_OPS(filter)->http_payload(s, filter, msg, out + offset, ret - offset);
if (ret < 0)
goto end;
*flt_off += ret;
ret = flt_http_payload(s, msg, htx->data);
if (ret < 0)
goto return_bad_req;
- channel_htx_fwd_payload(req, htx, ret);
+ c_adv(req, ret);
if (htx->data != co_data(req) || htx->extra)
goto missing_data_or_waiting;
}
else {
- channel_htx_fwd_all(req, htx);
+ c_adv(req, htx->data - co_data(req));
if (msg->flags & HTTP_MSGF_XFER_LEN)
channel_htx_forward_forever(req, htx);
}
if (txn->status < 200 &&
(txn->status == 100 || txn->status >= 102)) {
FLT_STRM_CB(s, flt_http_reset(s, msg));
- channel_htx_fwd_headers(rep, htx);
+ htx->first = channel_htx_fwd_headers(rep, htx);
msg->msg_state = HTTP_MSG_RPBEFORE;
txn->status = 0;
s->logs.t_data = -1; /* was not a response yet */
ret = flt_http_payload(s, msg, htx->data);
if (ret < 0)
goto return_bad_res;
- channel_htx_fwd_payload(res, htx, ret);
+ c_adv(res, ret);
if (htx->data != co_data(res) || htx->extra)
goto missing_data_or_waiting;
}
else {
- channel_htx_fwd_all(res, htx);
+ c_adv(res, htx->data - co_data(res));
if (msg->flags & HTTP_MSGF_XFER_LEN)
channel_htx_forward_forever(res, htx);
}