From: Miss Islington (bot) <31488909+miss-islington@users.noreply.github.com> Date: Mon, 1 Jun 2026 14:57:52 +0000 (+0200) Subject: [3.14] gh-150157: Fix critical section for PyDict_Next() in _pickle.c (GH-150158... X-Git-Url: http://git.ipfire.org/gitweb/index.cgi?a=commitdiff_plain;h=c15f0664c85ad0a4ab06682a0caed3aab0b062a6;p=thirdparty%2FPython%2Fcpython.git [3.14] gh-150157: Fix critical section for PyDict_Next() in _pickle.c (GH-150158) (GH-150710) (cherry picked from commit c5516e7e371f7b273eb37c7b65f14ef14ee81f11) Co-authored-by: Thomas Kowalski --- diff --git a/Misc/NEWS.d/next/Library/2026-05-21-20-47-45.gh-issue-150157.ZvmO-bQZ.rst b/Misc/NEWS.d/next/Library/2026-05-21-20-47-45.gh-issue-150157.ZvmO-bQZ.rst new file mode 100644 index 000000000000..3a12e26cf736 --- /dev/null +++ b/Misc/NEWS.d/next/Library/2026-05-21-20-47-45.gh-issue-150157.ZvmO-bQZ.rst @@ -0,0 +1,3 @@ +Fix a crash in free-threaded builds that occurs when pickling by name +objects without a ``__module__`` attribute while :data:`sys.modules` +is concurrently being modified. diff --git a/Modules/_pickle.c b/Modules/_pickle.c index 75e1c4dea85e..9a6f24ec8649 100644 --- a/Modules/_pickle.c +++ b/Modules/_pickle.c @@ -1947,22 +1947,34 @@ whichmodule(PickleState *st, PyObject *global, PyObject *global_name, PyObject * return NULL; } if (PyDict_CheckExact(modules)) { + PyObject *found_name = NULL; + int error = 0; i = 0; + Py_BEGIN_CRITICAL_SECTION(modules); while (PyDict_Next(modules, &i, &module_name, &module)) { Py_INCREF(module_name); Py_INCREF(module); if (_checkmodule(module_name, module, global, dotted_path) == 0) { Py_DECREF(module); - Py_DECREF(modules); - return module_name; + found_name = module_name; + break; } Py_DECREF(module); Py_DECREF(module_name); if (PyErr_Occurred()) { - Py_DECREF(modules); - return NULL; + error = 1; + break; } } + Py_END_CRITICAL_SECTION(); + if (error) { + Py_DECREF(modules); + return NULL; + } + if (found_name != NULL) { + Py_DECREF(modules); + return found_name; + } } else { PyObject *iterator = PyObject_GetIter(modules);