Skip to content

fix: reset gil_safe_call_once_and_store cache on interpreter finalize - #6162

Open
henryiii wants to merge 2 commits into
pybind:masterfrom
henryiii:fix/gil-safe-call-once-restart
Open

fix: reset gil_safe_call_once_and_store cache on interpreter finalize#6162
henryiii wants to merge 2 commits into
pybind:masterfrom
henryiii:fix/gil-safe-call-once-restart

Conversation

@henryiii

@henryiii henryiii commented Sep 2, 2026

Copy link
Copy Markdown
Collaborator

🤖 AI text below 🤖

Description

When subinterpreter support is enabled, gil_safe_call_once_and_store keeps the stored value in the
state dict of the interpreter, and caches a pointer to it plus an "initialized" flag in the module.
Nothing cleared that cache when the interpreter was finalized. After
finalize_interpreter(); initialize_interpreter(); the fast path gave freed memory back to the
caller. py::register_exception uses this class, thus re-importing an embedded module which
registers an exception used the freed exception object.

The per-interpreter storage now knows its owner and resets the cached pointer and the flag from its
destructor. The interpreter destroys the storage during finalization, thus the fast path becomes
invalid at the correct time and the next call stores the value again.

New Catch2 tests in tests/test_with_catch/test_interpreter.cpp restart the interpreter and then
use the stored value. Before the fix, the callable was not called again for the new interpreter, and
the re-imported exception module had no exception attribute.

Suggested changelog entry:

  • Fixed a use-after-free in py::gil_safe_call_once_and_store (and therefore in
    py::register_exception) when an embedded interpreter is finalized and then initialized again.

The old reference was released into the new interpreter's allocator, which
crashed on Python 3.12. This was also the cause of the enum test skip.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant