/* TODO support trailer parsing in this function */
/* TODO support buffer wrapping */
- BUG_ON(b_head(buf) + len >= b_wrap(buf));
+ BUG_ON(b_head(buf) + len > b_wrap(buf));
ret = qpack_decode_fs((const unsigned char *)b_head(buf), len, tmp,
list, sizeof(list) / sizeof(list[0]));
if (ret < 0) {
TRACE_ENTER(H3_EV_RX_FRAME|H3_EV_RX_HDR, qcs->qcc->conn, qcs);
/* TODO support buffer wrapping */
- BUG_ON(b_head(buf) + len >= b_wrap(buf));
+ BUG_ON(b_head(buf) + len > b_wrap(buf));
ret = qpack_decode_fs((const unsigned char *)b_head(buf), len, tmp,
list, sizeof(list) / sizeof(list[0]));
if (ret < 0) {
TRACE_ENTER(H3_EV_RX_FRAME|H3_EV_RX_HDR, qcs->qcc->conn, qcs);
/* TODO support buffer wrapping */
- BUG_ON(b_head(buf) + len >= b_wrap(buf));
+ BUG_ON(b_head(buf) + len > b_wrap(buf));
ret = qpack_decode_fs((const unsigned char *)b_head(buf), len, tmp,
list, sizeof(list) / sizeof(list[0]));
if (ret < 0) {
flen = h3s->demux_frame_len;
ftype = h3s->demux_frame_type;
- /* Do not demux incomplete frames except H3 DATA which can be
- * fragmented in multiple HTX blocks.
+ /* Current HTTP/3 parser can currently only parse fully
+ * received and aligned frames. The only exception is for DATA
+ * frames as they can frequently be larger than bufsize.
*/
- if (flen > b_data(b) && ftype != H3_FT_DATA) {
+ if (ftype != H3_FT_DATA) {
/* Reject frames bigger than bufsize.
*
* TODO HEADERS should in complement be limited with H3
qcc_report_glitch(qcs->qcc, 1);
goto err;
}
- break;
+
+ /* TODO extend parser to support the realignment of a frame. */
+ if (b_head(b) + b_data(b) > b_wrap(b)) {
+ TRACE_ERROR("cannot parse unaligned data frame", H3_EV_RX_FRAME, qcs->qcc->conn, qcs);
+ qcc_set_error(qcs->qcc, H3_ERR_EXCESSIVE_LOAD, 1);
+ qcc_report_glitch(qcs->qcc, 1);
+ goto err;
+ }
+
+ /* Only parse full HTTP/3 frames. */
+ if (flen > b_data(b)) {
+ TRACE_PROTO("pause parsing on incomplete payload", H3_EV_RX_FRAME, qcs->qcc->conn, qcs);
+ break;
+ }
}
last_stream_frame = (fin && flen == b_data(b));