diff options
| author | Mica White <botahamec@outlook.com> | 2025-03-09 20:49:56 -0400 |
|---|---|---|
| committer | Mica White <botahamec@outlook.com> | 2025-03-09 20:49:56 -0400 |
| commit | 58abf5872023aca7ee6459fa3b2e067d57923ba5 (patch) | |
| tree | 196cadda0dd4386668477ef286f9c9b09480e713 /src/thread/scope.rst | |
| parent | 4ba03be97e6cc7e790bbc9bfc18caaa228c8a262 (diff) | |
Finish testing and fixing
Diffstat (limited to 'src/thread/scope.rst')
| -rw-r--r-- | src/thread/scope.rst | 47 |
1 files changed, 47 insertions, 0 deletions
diff --git a/src/thread/scope.rst b/src/thread/scope.rst new file mode 100644 index 0000000..09319cb --- /dev/null +++ b/src/thread/scope.rst @@ -0,0 +1,47 @@ +use std::marker::PhantomData; + +use crate::{Keyable, ThreadKey}; + +use super::{Scope, ScopedJoinHandle}; + +pub fn scope<'env, F, T>(key: impl Keyable, f: F) -> T +where + F: for<'scope> FnOnce(&'scope Scope<'scope, 'env>) -> T, +{ + let scope = Scope(PhantomData); + let t = f(&scope); + drop(key); + t +} + +impl<'scope> Scope<'scope, '_> { + #[allow(clippy::unused_self)] + pub fn spawn<T: Send + 'scope>( + &self, + f: impl FnOnce(ThreadKey) -> T + Send + 'scope, + ) -> std::io::Result<ScopedJoinHandle<'scope, T>> { + unsafe { + // safety: the lifetimes ensure that the data lives long enough + let handle = std::thread::Builder::new().spawn_unchecked(|| { + // safety: the thread just started, so the key cannot be acquired yet + let key = ThreadKey::get().unwrap_unchecked(); + f(key) + })?; + + Ok(ScopedJoinHandle { + handle, + _phantom: PhantomData, + }) + } + } +} + +impl<T> ScopedJoinHandle<'_, T> { + pub fn is_finished(&self) -> bool { + self.handle.is_finished() + } + + pub fn join(self) -> std::thread::Result<T> { + self.handle.join() + } +} |
