]> git.ipfire.org Git - thirdparty/Python/cpython.git/commitdiff
[3.13] gh-122201: Lock mutex when setting handling_thread to NULL (GH-122204) (#122319)
authorMiss Islington (bot) <31488909+miss-islington@users.noreply.github.com>
Fri, 26 Jul 2024 17:30:08 +0000 (19:30 +0200)
committerGitHub <noreply@github.com>
Fri, 26 Jul 2024 17:30:08 +0000 (17:30 +0000)
In the free-threaded build, we need to lock pending->mutex when clearing
the handling_thread in order not to race with a concurrent
make_pending_calls in the same interpreter.
(cherry picked from commit c557ae97d6bd9d04164a19b4fe136610e54dbdd8)

Co-authored-by: Sam Gross <colesbury@gmail.com>
Python/ceval_gil.c
Tools/tsan/suppressions_free_threading.txt

index dc3baf79ccba6294bb05d33f58297625f9e81abf..0b45caba0d49ff8bd8efebd9ee88535f8f54a477 100644 (file)
@@ -901,6 +901,18 @@ unsignal_pending_calls(PyThreadState *tstate, PyInterpreterState *interp)
 #endif
 }
 
+static void
+clear_pending_handling_thread(struct _pending_calls *pending)
+{
+#ifdef Py_GIL_DISABLED
+    PyMutex_Lock(&pending->mutex);
+    pending->handling_thread = NULL;
+    PyMutex_Unlock(&pending->mutex);
+#else
+    pending->handling_thread = NULL;
+#endif
+}
+
 static int
 make_pending_calls(PyThreadState *tstate)
 {
@@ -933,7 +945,7 @@ make_pending_calls(PyThreadState *tstate)
 
     int32_t npending;
     if (_make_pending_calls(pending, &npending) != 0) {
-        pending->handling_thread = NULL;
+        clear_pending_handling_thread(pending);
         /* There might not be more calls to make, but we play it safe. */
         signal_pending_calls(tstate, interp);
         return -1;
@@ -945,7 +957,7 @@ make_pending_calls(PyThreadState *tstate)
 
     if (_Py_IsMainThread() && _Py_IsMainInterpreter(interp)) {
         if (_make_pending_calls(pending_main, &npending) != 0) {
-            pending->handling_thread = NULL;
+            clear_pending_handling_thread(pending);
             /* There might not be more calls to make, but we play it safe. */
             signal_pending_calls(tstate, interp);
             return -1;
@@ -956,7 +968,7 @@ make_pending_calls(PyThreadState *tstate)
         }
     }
 
-    pending->handling_thread = NULL;
+    clear_pending_handling_thread(pending);
     return 0;
 }
 
index c2380143cf5c3282ff10c684161f808c3327e933..56cb33bfe64bcd9258673fa0209a5792fb633d09 100644 (file)
@@ -28,7 +28,6 @@ race_top:assign_version_tag
 race_top:new_reference
 race_top:_multiprocessing_SemLock_acquire_impl
 race_top:list_get_item_ref
-race_top:make_pending_calls
 race_top:_Py_slot_tp_getattr_hook
 race_top:add_threadstate
 race_top:dump_traceback