solar_data_structures/
sync.rs

1pub use parking_lot::{
2    MappedMutexGuard, MappedRwLockReadGuard, MappedRwLockWriteGuard, Mutex, RwLock,
3    RwLockReadGuard, RwLockWriteGuard,
4};
5
6/// Executes the given expressions in parallel.
7#[macro_export]
8macro_rules! parallel {
9    ($sess:expr, $first:expr $(, $blocks:expr)+ $(,)?) => {
10        $sess.scope(|scope| {
11            $(
12                scope.spawn(|_| $blocks);
13            )+
14            $first;
15        })
16    };
17}
18
19/// A dynamic fork-join scope.
20///
21/// See [`rayon::scope`] for more details.
22pub struct Scope<'r, 'scope>(Option<&'r rayon::Scope<'scope>>);
23
24impl<'r, 'scope> Scope<'r, 'scope> {
25    /// Creates a new scope.
26    #[inline]
27    fn new(scope: Option<&'r rayon::Scope<'scope>>) -> Self {
28        Self(scope)
29    }
30
31    /// Spawns a job into the fork-join scope `self`.
32    #[inline]
33    pub fn spawn<BODY>(&self, body: BODY)
34    where
35        BODY: FnOnce(Scope<'_, 'scope>) + Send + 'scope,
36    {
37        match self.0 {
38            Some(scope) => scope.spawn(|scope| body(Scope::new(Some(scope)))),
39            None => body(Scope::new(None)),
40        }
41    }
42}
43
44/// Creates a new fork-join scope.
45///
46/// See [`rayon::scope`] for more details.
47#[inline]
48pub fn scope<'scope, OP, R>(enabled: bool, op: OP) -> R
49where
50    OP: FnOnce(Scope<'_, 'scope>) -> R + Send,
51    R: Send,
52{
53    if enabled { rayon::scope(|scope| op(Scope::new(Some(scope)))) } else { op(Scope::new(None)) }
54}