python / python/cpython

Segfault calling: `SSLObject.group()` before a session has been established

未關閉
#155,782 3 則留言 0 個 reaction 已指派 1 人 在 GitHub 檢視

@picnixz 已經在處理了。

開始於 2026年8月15日。

3.15 extension-modules topic-SSL type-crash
主要語言
Python
星號
77.2k
分支
36k
PR 合併指標
PR 指標待擷取

描述

Crash report

What happened?
Python 3.16.0a0 (heads/main-dirty:716cbae, Aug 13 2026, 11:31:04) [Clang 22.1.8 ] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> import ssl
...
... context = ssl.SSLContext(ssl.PROTOCOL_TLS_CLIENT)
... ssl_object = context.wrap_bio(ssl.MemoryBIO(), ssl.MemoryBIO())
... print(ssl_object.group())
...
Segmentation fault

Here's the script:

import ssl

context = ssl.SSLContext(ssl.PROTOCOL_TLS_CLIENT)
ssl_object = context.wrap_bio(ssl.MemoryBIO(), ssl.MemoryBIO())
print(ssl_object.group())
LLDB Stack
(lldb) run
Process 92 launched: '/pfm/py/bin/python3' (aarch64)
Process 92 stopped
* thread #1, name = 'python3', stop reason = signal SIGSEGV: address not mapped to object (fault address=0x308)
    frame #0: 0x0000fffff77c4e1c libssl.so.3`SSL_get0_group_name + 156
libssl.so.3`SSL_get0_group_name:
->  0xfffff77c4e1c <+156>: ldr    w1, [x0, #0x308]
    0xfffff77c4e20 <+160>: ldr    x0, [x2, #0x8]
    0xfffff77c4e24 <+164>: adrp   x16, 235
    0xfffff77c4e28 <+168>: ldr    x16, [x16, #0x670]
(lldb) bt
* thread #1, name = 'python3', stop reason = signal SIGSEGV: address not mapped to object (fault address=0x308)
  * frame #0: 0x0000fffff77c4e1c libssl.so.3`SSL_get0_group_name + 156
    frame #1: 0x0000fffff7903fc0 _ssl.cpython-316d-aarch64-linux-gnu.so`_ssl__SSLSocket_group_impl(self=0x0000fffff7a59b70) at _ssl.c:2230:18 [inlined]
    frame #2: 0x0000fffff7903fac _ssl.cpython-316d-aarch64-linux-gnu.so`_ssl__SSLSocket_group(self=0x0000fffff7a59b70, _unused_ignored=0x0000000000000000) at _ssl.c.h:219:20
    frame #3: 0x0000aaaaaaedb49c python3`method_vectorcall_NOARGS(func=0x0000fffff7a098b0, args=0x0000ffffffffcc40, nargsf=9223372036854775809, kwnames=0x0000000000000000) at descrobject.c:448:24
    frame #4: 0x0000aaaaaaeb0b64 python3`_PyObject_VectorcallTstate(tstate=0x0000aaaaab7f98e0, callable=0x0000fffff7a098b0, args=0x0000ffffffffcc40, nargsf=9223372036854775809, kwnames=0x0000000000000000) at pycore_call.h:144:11
    frame #5: 0x0000aaaaab2d7d64 python3`PyObject_Vectorcall(callable=<unavailable>, args=0x0000ffffffffcc40, nargsf=<unavailable>, kwnames=0x0000000000000000) at call.c:327:12 [inlined]
    frame #6: 0x0000aaaaab2d7d54 python3`_Py_VectorCallInstrumentation_StackRefSteal(callable=<unavailable>, arguments=0x0000fffff7fe90f8, total_args=<unavailable>, kwnames=(bits = 1), call_instrumentation=false, frame=0x0000fffff7fe9098, this_instr=0x0000fffff7adb3d6, tstate=0x0000aaaaab7f98e0) at ceval.c:768:11
    frame #7: 0x0000aaaaab28436c python3`_PyEval_EvalFrameDefault(tstate=<unavailable>, frame=<unavailable>, throwflag=<unavailable>) at generated_cases.c.h:1906:35
    frame #8: 0x0000aaaaab270f54 python3`_PyEval_EvalFrame(tstate=0x0000aaaaab7f98e0, frame=0x0000fffff7fe9020, throwflag=0) at pycore_ceval.h:122:16 [inlined]
    frame #9: 0x0000aaaaab270f2c python3`_PyEval_Vector(tstate=<unavailable>, func=<unavailable>, locals=0x0000fffff7acd610, args=<unavailable>, argcount=<unavailable>, kwnames=0x0000000000000000) at ceval.c:2172:12
    frame #10: 0x0000aaaaab2708f0 python3`PyEval_EvalCode(co=0x0000fffff7c95a80, globals=0x0000fffff7acd610, locals=0x0000fffff7acd610) at ceval.c:679:21

Python side call site:
https://github.com/python/cpython/blob/5d91cf6487eb5aa37107598c792573f61ebe310f/Modules/_ssl.c#L2227-L2230

This looks pretty much like an OpenSSL bug.

The openssl docs say:

If SSL_get0_group_name() returns NULL, an error occurred; possibly no TLS session has been established

strongly implying that we should get NULL return rather than a null dereference.

There's a fix been added to pyopenssl:
https://github.com/pyca/pyopenssl/pull/1442#discussion_r2356925889

And I've just raised an openssl bug:
https://github.com/openssl/openssl/issues/32379

The intended behaviour is in the PR review comments:

What happens if the handshake hasn't been initiated or completed yet? If this returns NULL in that case, it would be good to mention it.

Good point, I'm not actually sure if it would return NULL or just break. I will make sure it returns NULL and update the doc to reflect it.

The Python function was introduced by:

commit 377b78761814e7d848361e642d376881739d5a29
Author: Ron Frederick <ronf@timeheart.net>
Date:   Mon Jul 28 10:33:31 2025 -0700

    gh-136306: Add support for getting and setting SSL groups (#136307)

tagging: @ronf

This issue has been in openssl 3.2 up to master.

While this is really an upstream issue, it seems reasonable to consider a python level fix, the conditions for this happening are quite easy to detect, and it means that python has a fix immediately?

CPython versions tested on:

CPython main branch

Operating systems tested on:

Linux

Output from running 'python -VV' on the command line:

Python 3.16.0a0 (heads/main-dirty:716cbae, Aug 13 2026, 11:31:04) [Clang 22.1.8 ]

Linked PRs
  • gh-155829

貢獻指南

開啟貢獻指南

從這裡開始

  1. 先讀完整個 Issue,再讀專案的貢獻指南。
  2. 在 Issue 下留言說明你要接手 —— 這能避免兩個人做同樣的事。
  3. Fork 儲存庫,在一個分支上完成修改。
  4. 送出 Pull Request,並在描述裡引用這個 Issue 編號。

評估

這個 Issue 還沒有評估資料。

把新 issue 寄到你的電子郵件信箱

精選適合新手參與的 GitHub issue 摘要。