From: Amaury Denoyelle Date: Tue, 11 Feb 2025 13:35:52 +0000 (+0100) Subject: BUG/MINOR: quic: fix CRYPTO payload size calcul for encoding X-Git-Tag: v3.2-dev6~40 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=e6a223542ae87880b3e8261daffbe362730f9e55;p=thirdparty%2Fhaproxy.git BUG/MINOR: quic: fix CRYPTO payload size calcul for encoding Function max_stream_data_size() is used to determine the payload length of a CRYPTO frame. It takes into account that the CRYPTO length field is a variable length integer. Implemented calcul was incorrect as it reserved too much space as a frame header. This error is mostly due because max_stream_data_size() reuses max_available_room() which also reserve space for a variable length integer. This results in CRYPTO frames shorter of 1 to 2 bytes than the maximum achievable value, which produces in the end datagram shorter than the MTU. Fix max_stream_data_size() implementation. It is now merely a wrapper on max_available_room(). This ensures that CRYPTO frame encoding is now properly optimized to use the MTU available. This should be backported up to 2.6. --- diff --git a/src/quic_tx.c b/src/quic_tx.c index 82b3f5fa0..e17e66c66 100644 --- a/src/quic_tx.c +++ b/src/quic_tx.c @@ -1369,30 +1369,13 @@ static inline size_t max_available_room(size_t sz, size_t *len_sz) */ static inline size_t max_stream_data_size(size_t sz, size_t ilen, size_t dlen) { - size_t ret, len_sz, dlen_sz; + size_t ret, dlen_sz; - /* - * The length of variable-length QUIC integers are powers of two. - * Look for the first 3length" field value which match our need. - * As we must put bytes in our buffer, the minimum value for - * is the number of bytes required to encode . - */ - for (len_sz = quic_int_getsize(ilen); - len_sz <= QUIC_VARINT_MAX_SIZE; - len_sz <<= 1) { - if (sz < len_sz + ilen) - return 0; - - ret = max_available_room(sz - len_sz - ilen, &dlen_sz); - if (!ret) - return 0; - - /* Check that <*len_sz> matches value */ - if (len_sz + ilen + dlen_sz + ret <= quic_max_int(len_sz)) - return ret < dlen ? ret : dlen; - } + ret = max_available_room(sz - ilen, &dlen_sz); + if (!ret) + return 0; - return 0; + return ret < dlen ? ret : dlen; } /* Return the length in bytes of packet number depending on