aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/Python/perf_trampoline.c
diff options
context:
space:
mode:
authorPablo Galindo Salgado <Pablogsal@gmail.com>2023-12-01 13:20:51 +0000
committerGitHub <noreply@github.com>2023-12-01 13:20:51 +0000
commita73aa48e6bec900be7edd3431deaa5fc1d809e6f (patch)
tree52409eeb740cb5da1f85aad195753a279b7bd980 /Python/perf_trampoline.c
parentbfb576ee23c133bec0ce7c26a8ecea76926b9d8e (diff)
downloadcpython-a73aa48e6bec900be7edd3431deaa5fc1d809e6f.tar.gz
cpython-a73aa48e6bec900be7edd3431deaa5fc1d809e6f.zip
gh-112367: Only free perf trampoline arenas at shutdown (#112368)
Signed-off-by: Pablo Galindo <pablogsal@gmail.com>
Diffstat (limited to 'Python/perf_trampoline.c')
-rw-r--r--Python/perf_trampoline.c40
1 files changed, 35 insertions, 5 deletions
diff --git a/Python/perf_trampoline.c b/Python/perf_trampoline.c
index 208ced6c101..540b650192e 100644
--- a/Python/perf_trampoline.c
+++ b/Python/perf_trampoline.c
@@ -216,10 +216,24 @@ perf_map_write_entry(void *state, const void *code_addr,
PyMem_RawFree(perf_map_entry);
}
+static void*
+perf_map_init_state(void)
+{
+ PyUnstable_PerfMapState_Init();
+ return NULL;
+}
+
+static int
+perf_map_free_state(void *state)
+{
+ PyUnstable_PerfMapState_Fini();
+ return 0;
+}
+
_PyPerf_Callbacks _Py_perfmap_callbacks = {
- NULL,
+ &perf_map_init_state,
&perf_map_write_entry,
- NULL,
+ &perf_map_free_state,
};
static int
@@ -415,7 +429,6 @@ _PyPerfTrampoline_SetCallbacks(_PyPerf_Callbacks *callbacks)
trampoline_api.write_state = callbacks->write_state;
trampoline_api.free_state = callbacks->free_state;
trampoline_api.state = NULL;
- perf_status = PERF_STATUS_OK;
#endif
return 0;
}
@@ -434,6 +447,7 @@ _PyPerfTrampoline_Init(int activate)
}
if (!activate) {
tstate->interp->eval_frame = NULL;
+ perf_status = PERF_STATUS_NO_INIT;
}
else {
tstate->interp->eval_frame = py_trampoline_evaluator;
@@ -444,6 +458,9 @@ _PyPerfTrampoline_Init(int activate)
if (extra_code_index == -1) {
return -1;
}
+ if (trampoline_api.state == NULL && trampoline_api.init_state != NULL) {
+ trampoline_api.state = trampoline_api.init_state();
+ }
perf_status = PERF_STATUS_OK;
}
#endif
@@ -454,16 +471,29 @@ int
_PyPerfTrampoline_Fini(void)
{
#ifdef PY_HAVE_PERF_TRAMPOLINE
+ if (perf_status != PERF_STATUS_OK) {
+ return 0;
+ }
PyThreadState *tstate = _PyThreadState_GET();
if (tstate->interp->eval_frame == py_trampoline_evaluator) {
tstate->interp->eval_frame = NULL;
}
- free_code_arenas();
+ if (perf_status == PERF_STATUS_OK) {
+ trampoline_api.free_state(trampoline_api.state);
+ }
extra_code_index = -1;
+ perf_status = PERF_STATUS_NO_INIT;
#endif
return 0;
}
+void _PyPerfTrampoline_FreeArenas(void) {
+#ifdef PY_HAVE_PERF_TRAMPOLINE
+ free_code_arenas();
+#endif
+ return;
+}
+
int
PyUnstable_PerfTrampoline_SetPersistAfterFork(int enable){
#ifdef PY_HAVE_PERF_TRAMPOLINE
@@ -477,8 +507,8 @@ PyStatus
_PyPerfTrampoline_AfterFork_Child(void)
{
#ifdef PY_HAVE_PERF_TRAMPOLINE
- PyUnstable_PerfMapState_Fini();
if (persist_after_fork) {
+ _PyPerfTrampoline_Fini();
char filename[256];
pid_t parent_pid = getppid();
snprintf(filename, sizeof(filename), "/tmp/perf-%d.map", parent_pid);