mirror of
https://github.com/pybind/pybind11.git
synced 2026-03-14 20:27:47 +00:00
Re-enable Move Subinterpreter test for free-threaded Python 3.14 (#5940)
* Remove skip for Move Subinterpreter test on free-threaded Python 3.14+ * Fix deadlock by detaching from the main interpreter before joining the thread. * style: pre-commit fixes --------- Co-authored-by: b-pass <b-pass@users.noreply.github.com> Co-authored-by: pre-commit-ci[bot] <66853113+pre-commit-ci[bot]@users.noreply.github.com>
This commit is contained in:
committed by
GitHub
parent
7ae61bfb82
commit
799f591ec3
@@ -492,4 +492,8 @@ Best Practices for sub-interpreter safety
|
||||
So you must still consider the thread safety of your C++ code. Remember, in Python 3.12
|
||||
sub-interpreters must be destroyed on the same thread that they were created on.
|
||||
|
||||
- When using sub-interpreters in free-threaded python builds, note that creating and destroying
|
||||
sub-interpreters may initiate a "stop-the-world". Be sure to detach long-running C++ threads
|
||||
from Python thread state (similar to releasing the GIL) to avoid deadlocks.
|
||||
|
||||
- Familiarize yourself with :ref:`misc_concurrency`.
|
||||
|
||||
@@ -94,13 +94,6 @@ TEST_CASE("Single Subinterpreter") {
|
||||
|
||||
# if PY_VERSION_HEX >= 0x030D0000
|
||||
TEST_CASE("Move Subinterpreter") {
|
||||
// Test is skipped on free-threaded Python 3.14+ due to a hang in Py_EndInterpreter()
|
||||
// when the subinterpreter is destroyed from a different thread than it was created on.
|
||||
// See: https://github.com/pybind/pybind11/pull/5940
|
||||
# if PY_VERSION_HEX >= 0x030E0000 && defined(Py_GIL_DISABLED)
|
||||
PYBIND11_CATCH2_SKIP_IF(true, "Skipped on free-threaded Python 3.14+ (see PR #5940)");
|
||||
# endif
|
||||
|
||||
std::unique_ptr<py::subinterpreter> sub(new py::subinterpreter(py::subinterpreter::create()));
|
||||
|
||||
// on this thread, use the subinterpreter and import some non-trivial junk
|
||||
@@ -113,14 +106,21 @@ TEST_CASE("Move Subinterpreter") {
|
||||
py::module_::import("external_module");
|
||||
}
|
||||
|
||||
std::thread([&]() {
|
||||
auto t = std::thread([&]() {
|
||||
// Use it again
|
||||
{
|
||||
py::subinterpreter_scoped_activate activate(*sub);
|
||||
py::module_::import("external_module");
|
||||
}
|
||||
sub.reset();
|
||||
}).join();
|
||||
});
|
||||
|
||||
// on 3.14.1+ destructing a sub-interpreter does a stop-the-world. we need to detach our
|
||||
// thread state in order for that to be possible.
|
||||
{
|
||||
py::gil_scoped_release nogil;
|
||||
t.join();
|
||||
}
|
||||
|
||||
REQUIRE(!sub);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user