[Python-checkins] bpo-43311: Create GIL autoTSSkey ealier (GH-24819)

vstinner webhook-mailer at python.org
Wed Mar 10 14:01:00 EST 2021


https://github.com/python/cpython/commit/87f649a409da9d99682e78a55a83fc43225a8729
commit: 87f649a409da9d99682e78a55a83fc43225a8729
branch: master
author: Victor Stinner <vstinner at python.org>
committer: vstinner <vstinner at python.org>
date: 2021-03-10T20:00:46+01:00
summary:

bpo-43311: Create GIL autoTSSkey ealier (GH-24819)

At Python startup, call _PyGILState_Init() before
PyInterpreterState_New() which calls _PyThreadState_GET(). When
Python is built using --with-experimental-isolated-subinterpreters,
_PyThreadState_GET() uses autoTSSkey.

files:
M Include/internal/pycore_pylifecycle.h
M Python/pylifecycle.c
M Python/pystate.c

diff --git a/Include/internal/pycore_pylifecycle.h b/Include/internal/pycore_pylifecycle.h
index 75f4cdbf9a735..a7d84a9b5883c 100644
--- a/Include/internal/pycore_pylifecycle.h
+++ b/Include/internal/pycore_pylifecycle.h
@@ -8,6 +8,8 @@ extern "C" {
 #  error "this header requires Py_BUILD_CORE define"
 #endif
 
+#include "pycore_runtime.h"       // _PyRuntimeState
+
 /* Forward declarations */
 struct _PyArgv;
 struct pyruntimestate;
@@ -88,7 +90,8 @@ extern void _PyWarnings_Fini(PyInterpreterState *interp);
 extern void _PyAST_Fini(PyInterpreterState *interp);
 extern void _PyAtExit_Fini(PyInterpreterState *interp);
 
-extern PyStatus _PyGILState_Init(PyThreadState *tstate);
+extern PyStatus _PyGILState_Init(_PyRuntimeState *runtime);
+extern PyStatus _PyGILState_SetTstate(PyThreadState *tstate);
 extern void _PyGILState_Fini(PyInterpreterState *interp);
 
 PyAPI_FUNC(void) _PyGC_DumpShutdownStats(PyInterpreterState *interp);
diff --git a/Python/pylifecycle.c b/Python/pylifecycle.c
index d03c6c07f7108..1b8c4357362d2 100644
--- a/Python/pylifecycle.c
+++ b/Python/pylifecycle.c
@@ -577,7 +577,7 @@ init_interp_create_gil(PyThreadState *tstate)
     _PyEval_FiniGIL(tstate->interp);
 
     /* Auto-thread-state API */
-    status = _PyGILState_Init(tstate);
+    status = _PyGILState_SetTstate(tstate);
     if (_PyStatus_EXCEPTION(status)) {
         return status;
     }
@@ -597,12 +597,19 @@ pycore_create_interpreter(_PyRuntimeState *runtime,
                           const PyConfig *config,
                           PyThreadState **tstate_p)
 {
+    /* Auto-thread-state API */
+    PyStatus status = _PyGILState_Init(runtime);
+    if (_PyStatus_EXCEPTION(status)) {
+        return status;
+    }
+
     PyInterpreterState *interp = PyInterpreterState_New();
     if (interp == NULL) {
         return _PyStatus_ERR("can't make main interpreter");
     }
+    assert(_Py_IsMainInterpreter(interp));
 
-    PyStatus status = _PyConfig_Copy(&interp->config, config);
+    status = _PyConfig_Copy(&interp->config, config);
     if (_PyStatus_EXCEPTION(status)) {
         return status;
     }
diff --git a/Python/pystate.c b/Python/pystate.c
index e7c085d1f83a9..c8b2530f68dfe 100644
--- a/Python/pystate.c
+++ b/Python/pystate.c
@@ -1327,7 +1327,21 @@ PyThreadState_IsCurrent(PyThreadState *tstate)
    Py_Initialize/Py_FinalizeEx
 */
 PyStatus
-_PyGILState_Init(PyThreadState *tstate)
+_PyGILState_Init(_PyRuntimeState *runtime)
+{
+    struct _gilstate_runtime_state *gilstate = &runtime->gilstate;
+    if (PyThread_tss_create(&gilstate->autoTSSkey) != 0) {
+        return _PyStatus_NO_MEMORY();
+    }
+    // PyThreadState_New() calls _PyGILState_NoteThreadState() which does
+    // nothing before autoInterpreterState is set.
+    assert(gilstate->autoInterpreterState == NULL);
+    return _PyStatus_OK();
+}
+
+
+PyStatus
+_PyGILState_SetTstate(PyThreadState *tstate)
 {
     if (!_Py_IsMainInterpreter(tstate->interp)) {
         /* Currently, PyGILState is shared by all interpreters. The main
@@ -1341,9 +1355,6 @@ _PyGILState_Init(PyThreadState *tstate)
 
     struct _gilstate_runtime_state *gilstate = &tstate->interp->runtime->gilstate;
 
-    if (PyThread_tss_create(&gilstate->autoTSSkey) != 0) {
-        return _PyStatus_NO_MEMORY();
-    }
     gilstate->autoInterpreterState = tstate->interp;
     assert(PyThread_tss_get(&gilstate->autoTSSkey) == NULL);
     assert(tstate->gilstate_counter == 0);



More information about the Python-checkins mailing list