Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

hang instead of pthread_exit during interpreter shutdown #4874

Open
wants to merge 13 commits into
base: main
Choose a base branch
from

Conversation

arielb1
Copy link

@arielb1 arielb1 commented Jan 26, 2025

This mimics the Python 3.14 behavior and avoids crashes in Rust 1.84.

See python/cpython#87135 and rust-lang/rust#135929 and the related pyo3-log issue vorner/pyo3-log#30

By submitting these contributions you agree for them to be dual-licensed under PyO3's MIT OR Apache-2.0 license.

Copy link

codspeed-hq bot commented Jan 27, 2025

CodSpeed Performance Report

Merging #4874 will not alter performance

Comparing arielb1:safe-exit (c6cf08f) with main (f89b5f7)

Summary

✅ 84 untouched benchmarks

@arielb1 arielb1 force-pushed the safe-exit branch 4 times, most recently from 80f138a to 704ef0b Compare January 27, 2025 23:24
@arielb1
Copy link
Author

arielb1 commented Jan 27, 2025

Yay it passes tests.

src/lib.rs Outdated Show resolved Hide resolved
Comment on lines 113 to 137
#[cfg(not(Py_3_14))]
pub unsafe extern "C" fn PyGILState_Ensure() -> PyGILState_STATE {
let guard = HangThread;
let ret: PyGILState_STATE = raw::PyGILState_Ensure();
std::mem::forget(guard);
ret
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Disclaimer: I'm really no expert here.

According to my understanding of the C-unwind this is still UB. Specifically here is mentioned that forced unwinding (like pthread_exit) can not rely on Drop and thus crossing such framed is considered UB.

Given that this was UB before as well, but this one works, maybe that's better 🤷 (We really need a Python API to do this properly)

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So bjorn claimed this way is unspecified behavior but should work. I think it's better then the C++ version.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks, I think that makes sense to me. I guess we aren't guaranteed that drop will run, but in case it is not run, we are in the same situation as currently (presumably a crash). So given this (currently) works in practice it seems like a net win to me.

I think it's better then the C++ version.

Definitely agree here, I was not really a fan of adding a C++ toolchain dependency 👍

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

added a comment

@@ -3,7 +3,7 @@

from pyo3_pytests import othermod

INTEGER32_ST = st.integers(min_value=(-(2**31)), max_value=(2**31 - 1))
INTEGER32_ST = st.integers(min_value=(-(2**30)), max_value=(2**30 - 1))
Copy link
Author

@arielb1 arielb1 Jan 28, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this change here is to avoid the test failing due to a high rate of assume failure (filter_too_much).

@arielb1
Copy link
Author

arielb1 commented Jan 29, 2025

split the test_double fix to #4879

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.

3 participants