Skip to content

Commit 9aeee56

Browse files
Merge PR "[AUTO-CHERRYPICK] [AutoPR- Security] Patch pyOpenSSL for CVE-2026-27459, CVE-2026-27448 [HIGH] - branch 3.0-dev" #16245
Co-authored-by: Azure Linux Security Servicing Account <azurelinux-security@microsoft.com>
1 parent 959bf6e commit 9aeee56

3 files changed

Lines changed: 159 additions & 1 deletion

File tree

Lines changed: 109 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,109 @@
1+
From ba1d5fdf7bc8aa1b4dc157722161e79f3c290ab1 Mon Sep 17 00:00:00 2001
2+
From: Alex Gaynor <alex.gaynor@gmail.com>
3+
Date: Mon, 16 Feb 2026 21:04:37 -0500
4+
Subject: [PATCH] Handle exceptions in set_tlsext_servername_callback callbacks
5+
(#1478)
6+
7+
When the servername callback raises an exception, call sys.excepthook
8+
with the exception info and return SSL_TLSEXT_ERR_ALERT_FATAL to abort
9+
the handshake. Previously, exceptions would propagate uncaught through
10+
the CFFI callback boundary.
11+
12+
https://claude.ai/code/session_01P7y1XmWkdtC5UcmZwGDvGi
13+
14+
Co-authored-by: Claude <noreply@anthropic.com>
15+
Signed-off-by: Azure Linux Security Servicing Account <azurelinux-security@microsoft.com>
16+
Upstream-reference: https://github.com/pyca/pyopenssl/commit/d41a814759a9fb49584ca8ab3f7295de49a85aa0.patch
17+
---
18+
src/OpenSSL/SSL.py | 7 ++++++-
19+
tests/test_ssl.py | 50 ++++++++++++++++++++++++++++++++++++++++++++++
20+
2 files changed, 56 insertions(+), 1 deletion(-)
21+
22+
diff --git a/src/OpenSSL/SSL.py b/src/OpenSSL/SSL.py
23+
index 4ca5950..8f9d21e 100644
24+
--- a/src/OpenSSL/SSL.py
25+
+++ b/src/OpenSSL/SSL.py
26+
@@ -1,5 +1,6 @@
27+
import os
28+
import socket
29+
+import sys
30+
import typing
31+
from errno import errorcode
32+
from functools import partial, wraps
33+
@@ -1621,7 +1622,11 @@ class Context:
34+
35+
@wraps(callback)
36+
def wrapper(ssl, alert, arg): # type: ignore[no-untyped-def]
37+
- callback(Connection._reverse_mapping[ssl])
38+
+ try:
39+
+ callback(Connection._reverse_mapping[ssl])
40+
+ except Exception:
41+
+ sys.excepthook(*sys.exc_info())
42+
+ return _lib.SSL_TLSEXT_ERR_ALERT_FATAL
43+
return 0
44+
45+
self._tlsext_servername_callback = _ffi.callback(
46+
diff --git a/tests/test_ssl.py b/tests/test_ssl.py
47+
index 3a0cddf..df142d6 100644
48+
--- a/tests/test_ssl.py
49+
+++ b/tests/test_ssl.py
50+
@@ -1854,6 +1854,56 @@ class TestServerNameCallback:
51+
52+
assert args == [(server, b"foo1.example.com")]
53+
54+
+ def test_servername_callback_exception(
55+
+ self, monkeypatch: pytest.MonkeyPatch
56+
+ ) -> None:
57+
+ """
58+
+ When the callback passed to `Context.set_tlsext_servername_callback`
59+
+ raises an exception, ``sys.excepthook`` is called with the exception
60+
+ and the handshake fails with an ``Error``.
61+
+ """
62+
+ exc = TypeError("server name callback failed")
63+
+
64+
+ def servername(conn: Connection) -> None:
65+
+ raise exc
66+
+
67+
+ excepthook_calls: list[
68+
+ tuple[type[BaseException], BaseException, object]
69+
+ ] = []
70+
+
71+
+ def custom_excepthook(
72+
+ exc_type: type[BaseException],
73+
+ exc_value: BaseException,
74+
+ exc_tb: object,
75+
+ ) -> None:
76+
+ excepthook_calls.append((exc_type, exc_value, exc_tb))
77+
+
78+
+ context = Context(SSLv23_METHOD)
79+
+ context.set_tlsext_servername_callback(servername)
80+
+
81+
+ # Necessary to actually accept the connection
82+
+ context.use_privatekey(load_privatekey(FILETYPE_PEM, server_key_pem))
83+
+ context.use_certificate(
84+
+ load_certificate(FILETYPE_PEM, server_cert_pem)
85+
+ )
86+
+
87+
+ # Do a little connection to trigger the logic
88+
+ server = Connection(context, None)
89+
+ server.set_accept_state()
90+
+
91+
+ client = Connection(Context(SSLv23_METHOD), None)
92+
+ client.set_connect_state()
93+
+ client.set_tlsext_host_name(b"foo1.example.com")
94+
+
95+
+ monkeypatch.setattr(sys, "excepthook", custom_excepthook)
96+
+ with pytest.raises(Error):
97+
+ interact_in_memory(server, client)
98+
+
99+
+ assert len(excepthook_calls) == 1
100+
+ assert excepthook_calls[0][0] is TypeError
101+
+ assert excepthook_calls[0][1] is exc
102+
+ assert excepthook_calls[0][2] is not None
103+
+
104+
105+
class TestApplicationLayerProtoNegotiation:
106+
"""
107+
--
108+
2.45.4
109+
Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,44 @@
1+
From 5724d85b852c2035f69d6b47a04feb7d0cb8185e Mon Sep 17 00:00:00 2001
2+
From: Alex Gaynor <alex.gaynor@gmail.com>
3+
Date: Wed, 18 Feb 2026 07:46:15 -0500
4+
Subject: [PATCH] Fix buffer overflow in DTLS cookie generation callback
5+
(#1479)
6+
7+
The cookie generate callback copied user-returned bytes into a
8+
fixed-size native buffer without enforcing a maximum length. A
9+
callback returning more than DTLS1_COOKIE_LENGTH bytes would overflow
10+
the OpenSSL-provided buffer, corrupting adjacent memory.
11+
12+
Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
13+
Signed-off-by: Azure Linux Security Servicing Account <azurelinux-security@microsoft.com>
14+
Upstream-reference: https://github.com/pyca/pyopenssl/commit/57f09bb4bb051d3bc2a1abd36e9525313d5cd408.patch
15+
---
16+
src/OpenSSL/SSL.py | 7 +++++++
17+
1 file changed, 7 insertions(+)
18+
19+
diff --git a/src/OpenSSL/SSL.py b/src/OpenSSL/SSL.py
20+
index 8f9d21e..5b382be 100644
21+
--- a/src/OpenSSL/SSL.py
22+
+++ b/src/OpenSSL/SSL.py
23+
@@ -711,11 +711,18 @@ class _CookieGenerateCallbackHelper(_CallbackExceptionHelper):
24+
def __init__(self, callback: _CookieGenerateCallback) -> None:
25+
_CallbackExceptionHelper.__init__(self)
26+
27+
+ max_cookie_len = getattr(_lib, "DTLS1_COOKIE_LENGTH", 255)
28+
+
29+
@wraps(callback)
30+
def wrapper(ssl, out, outlen): # type: ignore[no-untyped-def]
31+
try:
32+
conn = Connection._reverse_mapping[ssl]
33+
cookie = callback(conn)
34+
+ if len(cookie) > max_cookie_len:
35+
+ raise ValueError(
36+
+ f"Cookie too long (got {len(cookie)} bytes, "
37+
+ f"max {max_cookie_len})"
38+
+ )
39+
out[0 : len(cookie)] = cookie
40+
outlen[0] = len(cookie)
41+
return 1
42+
--
43+
2.45.4
44+

SPECS/pyOpenSSL/pyOpenSSL.spec

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,13 +3,15 @@
33
Summary: Python wrapper module around the OpenSSL library
44
Name: pyOpenSSL
55
Version: 24.2.1
6-
Release: 1%{?dist}
6+
Release: 2%{?dist}
77
License: ASL 2.0
88
Vendor: Microsoft Corporation
99
Distribution: Azure Linux
1010
Group: Development/Languages/Python
1111
URL: https://github.com/pyca/pyopenssl
1212
Source0: %{pypi_source %{srcname} %{version}}
13+
Patch0: CVE-2026-27448.patch
14+
Patch1: CVE-2026-27459.patch
1315
BuildArch: noarch
1416

1517
%description
@@ -61,6 +63,9 @@ LANG=en_US.UTF-8 PYTHONPATH=%{buildroot}%{python3_sitelib} \
6163
%{python3_sitelib}/*
6264

6365
%changelog
66+
* Thu Mar 19 2026 Azure Linux Security Servicing Account <azurelinux-security@microsoft.com> - 24.2.1-2
67+
- Patch for CVE-2026-27459, CVE-2026-27448
68+
6469
* Fri Aug 16 2023 Daniel McIlvaney <damcilva@microsoft.com> - 24.2.1-1
6570
- Selectively take upstream changes from F41 to update to 24.2.1 to support our
6671
version of python-cryptography.

0 commit comments

Comments
 (0)