]> git.ipfire.org Git - thirdparty/Python/cpython.git/commitdiff
gh-126703: Fix possible use after free in pycfunction freelist (GH-132319)
authorKen Jin <kenjin@python.org>
Wed, 9 Apr 2025 14:49:33 +0000 (22:49 +0800)
committerGitHub <noreply@github.com>
Wed, 9 Apr 2025 14:49:33 +0000 (22:49 +0800)
Misc/NEWS.d/next/Core_and_Builtins/2025-04-09-13-47-33.gh-issue-126703.kXiQHj.rst [new file with mode: 0644]
Objects/methodobject.c

diff --git a/Misc/NEWS.d/next/Core_and_Builtins/2025-04-09-13-47-33.gh-issue-126703.kXiQHj.rst b/Misc/NEWS.d/next/Core_and_Builtins/2025-04-09-13-47-33.gh-issue-126703.kXiQHj.rst
new file mode 100644 (file)
index 0000000..d0461e1
--- /dev/null
@@ -0,0 +1 @@
+Fix possible use after free in cases where a method's definition has the same lifetime as its ``self``.
index 1f459dea44192cdc0eab5dde83ca93e15920ba10..189b026ab33559df3006a10c22b7015a176193e3 100644 (file)
@@ -173,12 +173,16 @@ meth_dealloc(PyObject *self)
     if (m->m_weakreflist != NULL) {
         PyObject_ClearWeakRefs((PyObject*) m);
     }
+    // We need to access ml_flags here rather than later.
+    // `m->m_ml` might have the same lifetime
+    // as `m_self` when it's dynamically allocated.
+    int ml_flags = m->m_ml->ml_flags;
     // Dereference class before m_self: PyCFunction_GET_CLASS accesses
     // PyMethodDef m_ml, which could be kept alive by m_self
     Py_XDECREF(PyCFunction_GET_CLASS(m));
     Py_XDECREF(m->m_self);
     Py_XDECREF(m->m_module);
-    if (m->m_ml->ml_flags & METH_METHOD) {
+    if (ml_flags & METH_METHOD) {
         assert(Py_IS_TYPE(self, &PyCMethod_Type));
         _Py_FREELIST_FREE(pycmethodobject, m, PyObject_GC_Del);
     }