Commit ebcd9361a2 for openssl.org
commit ebcd9361a255943407553f8812f66e9ab1be7022
Author: Neil Horman <nhorman@openssl.org>
Date: Tue Aug 25 14:23:50 2026 -0400
don't double count full databgram length on unvalidated connections
If a connection is coalescing frames, we pass through
ossl_quic_handle_frames multiple times, each time accounting the full
datagram length to the connection, erroneously amplifying our
unvalidated credit.
Fix it by moving where we account unvalidated credit. If we move the
adding of unvalidated credit to port_default_packet_handler, we can add
the datagram length to the channels unvalidated credit before it gets
broken up into multiple OSSL_QRX_PKT structures.
Fixes CVE-2026-35191
Reviewed-by: Saša NedvÄ›dický <sashan@openssl.org>
Reviewed-by: Tomas Mraz <tomas@openssl.foundation>
Reviewed-by: Andrew Dinh <andrewd@openssl.org>
Merge-date: Tue Sep 29 11:52:14 2026
diff --git a/ssl/quic/quic_port.c b/ssl/quic/quic_port.c
index a0d9076470..e2beb5bdf7 100644
--- a/ssl/quic/quic_port.c
+++ b/ssl/quic/quic_port.c
@@ -1658,6 +1658,7 @@ static void port_default_packet_handler(QUIC_URXE *e, void *arg,
&& ossl_quic_lcidm_lookup(port->lcidm, dcid, NULL,
(void **)&ch)) {
assert(ch != NULL);
+ ossl_quic_tx_packetiser_add_unvalidated_credit(ch->txp, e->data_len);
ossl_quic_channel_inject(ch, e);
return;
}
@@ -1869,6 +1870,7 @@ static void port_default_packet_handler(QUIC_URXE *e, void *arg,
* Time to reinject packets from qrx to channel before
* qrx will be destroyed here.
*/
+ ossl_quic_tx_packetiser_add_unvalidated_credit(new_ch->txp, e->data_len);
while (ossl_qrx_read_pkt(qrx_src, &qrx_pkt) == 1)
ossl_quic_channel_inject_pkt(new_ch, qrx_pkt);
ossl_qrx_update_pn_space(qrx_src, new_ch->qrx);
diff --git a/ssl/quic/quic_rx_depack.c b/ssl/quic/quic_rx_depack.c
index 59d16b2f36..704ac4a495 100644
--- a/ssl/quic/quic_rx_depack.c
+++ b/ssl/quic/quic_rx_depack.c
@@ -1462,7 +1462,6 @@ int ossl_quic_handle_frames(QUIC_CHANNEL *ch, OSSL_QRX_PKT *qpacket)
PACKET pkt;
OSSL_ACKM_RX_PKT ackm_data;
uint32_t enc_level;
- size_t dgram_len = qpacket->datagram_len;
if (ch == NULL)
return 0;
@@ -1497,8 +1496,6 @@ int ossl_quic_handle_frames(QUIC_CHANNEL *ch, OSSL_QRX_PKT *qpacket)
*/
if (enc_level == QUIC_ENC_LEVEL_HANDSHAKE)
ossl_quic_tx_packetiser_set_validated(ch->txp);
- else
- ossl_quic_tx_packetiser_add_unvalidated_credit(ch->txp, dgram_len);
/* Now that special cases are out of the way, parse frames */
if (!PACKET_buf_init(&pkt, qpacket->hdr->data, qpacket->hdr->len)