Skip to content

Instantly share code, notes, and snippets.

@ngoldbaum
Last active September 30, 2024 19:44
Show Gist options
  • Save ngoldbaum/30f37d70cda2d990c285d13823ded168 to your computer and use it in GitHub Desktop.
Save ngoldbaum/30f37d70cda2d990c285d13823ded168 to your computer and use it in GitHub Desktop.
pub fn with_critical_section<F, R>(object: &Bound<'_, PyAny>, f: F) -> R
where
F: FnOnce() -> R,
{
#[cfg(Py_GIL_DISABLED)]
{
struct Guard(crate::ffi::PyCriticalSection);
impl Drop for Guard {
fn drop(&mut self) {
unsafe {
crate::ffi::PyCriticalSection_End(&mut self.0);
}
}
}
let _guard = unsafe {
let mut section = std::mem::zeroed();
crate::ffi::PyCriticalSection_Begin(&mut section, object.as_ptr());
Guard(section)
};
f()
}
#[cfg(not(Py_GIL_DISABLED))]
{
f()
}
}
#[test]
fn test_critical_section() {
let dict = Python::with_gil(|py| -> Py<PyDict> { PyDict::new(py).unbind() });
let barrier = Barrier::new(2);
std::thread::scope(|s| {
s.spawn(|| {
Python::with_gil(|py| {
let d = dict.bind(py);
with_critical_section(d, || {
barrier.wait();
std::thread::sleep(std::time::Duration::from_millis(10));
d.set_item(42, 42).unwrap();
})
});
});
s.spawn(|| {
barrier.wait();
Python::with_gil(|py| {
let d = dict.bind(py);
assert_eq!(
d.get_item(42).unwrap().unwrap().extract::<usize>().unwrap(),
42
);
});
});
});
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment