Skip to content

Commit 6b1b90f

Browse files
gh-155725: Remove PyGILState_Ensure usage from tracemalloc (#156409)
1 parent ec8a420 commit 6b1b90f

6 files changed

Lines changed: 303 additions & 139 deletions

File tree

Include/internal/pycore_pystate.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -359,6 +359,10 @@ struct PyInterpreterView {
359359
PyAPI_FUNC(Py_ssize_t) _PyInterpreterState_GuardCountdown(PyInterpreterState *interp);
360360
PyAPI_FUNC(PyInterpreterState *) _PyInterpreterGuard_GetInterpreter(PyInterpreterGuard *guard);
361361

362+
extern int _PyInterpreterGuard_TryAcquire(PyInterpreterState *interp,
363+
PyInterpreterGuard *guard);
364+
extern void _PyInterpreterGuard_Release(PyInterpreterGuard *guard);
365+
362366
#ifdef __cplusplus
363367
}
364368
#endif

Include/internal/pycore_tracemalloc.h

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -44,9 +44,10 @@ struct
4444
__attribute__((packed))
4545
#endif
4646
tracemalloc_frame {
47-
/* filename cannot be NULL: "<unknown>" is used if the Python frame
48-
filename is NULL */
49-
PyObject *filename;
47+
/* Interned NUL terminated UTF-8 (surrogatepass) string.
48+
Cannot be NULL: "<unknown>" is used if the Python frame filename
49+
cannot be captured. */
50+
const char *filename;
5051
unsigned int lineno;
5152
};
5253

@@ -85,7 +86,7 @@ struct _tracemalloc_runtime_state {
8586
Protected by TABLES_LOCK(). */
8687
size_t peak_traced_memory;
8788
/* Hash table used as a set to intern filenames:
88-
PyObject* => PyObject*.
89+
char* (NUL terminated UTF-8 string) => NULL.
8990
Protected by the TABLES_LOCK(). */
9091
_Py_hashtable_t *filenames;
9192
/* Buffer to store a new traceback in traceback_new().

Lib/test/test_tracemalloc.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1056,8 +1056,8 @@ def test_track(self):
10561056
self.check_track(False)
10571057

10581058
def test_track_without_gil(self):
1059-
# check that calling _PyTraceMalloc_Track() without holding the GIL
1060-
# works too
1059+
# check that calling PyTraceMalloc_Track() without the GIL
1060+
# (detached thread state) still captures the Python traceback
10611061
self.check_track(True)
10621062

10631063
def test_track_already_tracked(self):
Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
:mod:`tracemalloc` no longer acquires the :term:`GIL` nor creates a
2+
temporary thread state to trace memory allocations: traceback frames now
3+
store plain UTF-8 strings instead of Python str objects, and tracebacks are
4+
captured using the Python thread state already associated with the calling
5+
thread, even if it is not attached. Threads without a Python thread state
6+
record the traceback as ``<unknown>``.

Python/pystate.c

Lines changed: 21 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3419,8 +3419,8 @@ PyInterpreterGuard_FromCurrent(void)
34193419
return guard;
34203420
}
34213421

3422-
void
3423-
PyInterpreterGuard_Close(PyInterpreterGuard *guard)
3422+
static void
3423+
release_interp_guard(PyInterpreterGuard *guard)
34243424
{
34253425
PyInterpreterState *interp = guard->interp;
34263426
assert(interp != NULL);
@@ -3432,9 +3432,28 @@ PyInterpreterGuard_Close(PyInterpreterGuard *guard)
34323432
}
34333433

34343434
assert(old_value > 0);
3435+
}
3436+
3437+
void
3438+
PyInterpreterGuard_Close(PyInterpreterGuard *guard)
3439+
{
3440+
release_interp_guard(guard);
34353441
PyMem_RawFree(guard);
34363442
}
34373443

3444+
int
3445+
_PyInterpreterGuard_TryAcquire(PyInterpreterState *interp,
3446+
PyInterpreterGuard *guard)
3447+
{
3448+
return try_acquire_interp_guard(interp, guard);
3449+
}
3450+
3451+
void
3452+
_PyInterpreterGuard_Release(PyInterpreterGuard *guard)
3453+
{
3454+
release_interp_guard(guard);
3455+
}
3456+
34383457
PyInterpreterView *
34393458
PyInterpreterView_FromCurrent(void)
34403459
{

0 commit comments

Comments
 (0)