From b9d19562c0e88e31f43c10126dc91cad9e720953 Mon Sep 17 00:00:00 2001 From: Tomas Mraz Date: Tue, 14 Oct 2025 13:28:30 +0200 Subject: [PATCH] bss_dgram.c: Fix potential buffer overread and remove asserts MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit Reviewed-by: Matt Caswell Reviewed-by: Saša Nedvědický (Merged from https://github.com/openssl/openssl/pull/28896) --- crypto/bio/bss_dgram.c | 28 +++++++++++++++++++--------- 1 file changed, 19 insertions(+), 9 deletions(-) diff --git a/crypto/bio/bss_dgram.c b/crypto/bio/bss_dgram.c index 84cc45b546f..c67077f5714 100644 --- a/crypto/bio/bss_dgram.c +++ b/crypto/bio/bss_dgram.c @@ -810,12 +810,16 @@ static long dgram_ctrl(BIO *b, int cmd, long num, void *ptr) } # else socklen_t sz = sizeof(struct timeval); + if ((ret = getsockopt(b->num, SOL_SOCKET, SO_RCVTIMEO, ptr, &sz)) < 0) { ERR_raise_data(ERR_LIB_SYS, get_last_socket_error(), "calling getsockopt()"); + } else if (!ossl_assert((size_t)sz == sizeof(struct timeval))) { + ERR_raise_data(ERR_LIB_BIO, ERR_R_INTERNAL_ERROR, + "Unexpected getsockopt(SO_RCVTIMEO) return size"); + ret = -1; } else { - OPENSSL_assert((size_t)sz <= sizeof(struct timeval)); ret = (int)sz; } # endif @@ -865,8 +869,11 @@ static long dgram_ctrl(BIO *b, int cmd, long num, void *ptr) ptr, &sz)) < 0) { ERR_raise_data(ERR_LIB_SYS, get_last_socket_error(), "calling getsockopt()"); + } else if (!ossl_assert((size_t)sz == sizeof(struct timeval))) { + ERR_raise_data(ERR_LIB_BIO, ERR_R_INTERNAL_ERROR, + "Unexpected getsockopt(SO_SNDTIMEO) return size"); + ret = -1; } else { - OPENSSL_assert((size_t)sz <= sizeof(struct timeval)); ret = (int)sz; } # endif @@ -2015,7 +2022,10 @@ static int dgram_sctp_read(BIO *b, char *out, int outl) if (msg.msg_flags & MSG_NOTIFICATION) { union sctp_notification snp; - memcpy(&snp, out, sizeof(snp)); + if (n < (int)sizeof(snp.sn_header)) + return -1; + memset(&snp, 0, sizeof(snp)); + memcpy(&snp, out, (size_t)n < sizeof(snp) ? (size_t)n : sizeof(snp)); if (snp.sn_header.sn_type == SCTP_SENDER_DRY_EVENT) { # ifdef SCTP_EVENT struct sctp_event event; @@ -2064,7 +2074,6 @@ static int dgram_sctp_read(BIO *b, char *out, int outl) data->handle_notifications(b, data->notification_context, (void *)out); - memset(&snp, 0, sizeof(snp)); memset(out, 0, outl); } else { ret += n; @@ -2089,8 +2098,8 @@ static int dgram_sctp_read(BIO *b, char *out, int outl) */ optlen = (socklen_t) sizeof(int); ret = getsockopt(b->num, SOL_SOCKET, SO_RCVBUF, &optval, &optlen); - if (ret >= 0) - OPENSSL_assert(optval >= 18445); + if (ret >= 0 && !ossl_assert(optval >= 18445)) + return -1; /* * Test if SCTP doesn't partially deliver below max record size @@ -2100,13 +2109,14 @@ static int dgram_sctp_read(BIO *b, char *out, int outl) ret = getsockopt(b->num, IPPROTO_SCTP, SCTP_PARTIAL_DELIVERY_POINT, &optval, &optlen); - if (ret >= 0) - OPENSSL_assert(optval >= 18445); + if (ret >= 0 && !ossl_assert(optval >= 18445)) + return -1; /* * Partially delivered notification??? Probably a bug.... */ - OPENSSL_assert(!(msg.msg_flags & MSG_NOTIFICATION)); + if (!ossl_assert((msg.msg_flags & MSG_NOTIFICATION) == 0)) + return -1; /* * Everything seems ok till now, so it's most likely a message -- 2.47.3