use core::future::Future;
use core::ops::DerefMut;
#[cfg(feature = "std")]
use std::time::Duration;
#[cfg(all(feature = "alloc", feature = "std"))]
use crate::Runtime;
pub trait MutexLike<T: Send + 'static>: Send + Sync {
type Guard<'guard>: DerefMut<Target = T> + Send
where
Self: 'guard;
fn lock(&self) -> impl Future<Output = Self::Guard<'_>> + Send;
}
pub trait NotifyLike: Send + Sync {
fn notify_one(&self);
fn notified(&self) -> impl Future<Output = ()> + Send + '_;
}
pub trait JoinSetLike<T>: Send {
fn spawn<F>(&mut self, future: F)
where
F: Future<Output = T> + Send + 'static;
fn join_next(&mut self) -> impl Future<Output = Option<Result<T, JoinError>>> + Send + '_;
fn abort_all(&mut self);
}
#[derive(Debug)]
pub enum JoinError {
Panicked,
Cancelled,
}
#[cfg(all(feature = "alloc", feature = "std"))]
pub trait RuntimeFactory: Runtime {
type Mutex<T: Send + 'static>: MutexLike<T>;
type Notify: NotifyLike;
type JoinSet<T: Send + 'static>: JoinSetLike<T>;
type Sleep: Future<Output = ()> + Send;
fn new_mutex<T: Send + 'static>(value: T) -> Self::Mutex<T>;
fn new_notify() -> Self::Notify;
fn new_join_set<T: Send + 'static>() -> Self::JoinSet<T>;
fn sleep(duration: Duration) -> Self::Sleep;
}
pub trait LocalMutexLike<T: 'static> {
type Guard<'guard>: DerefMut<Target = T>
where
Self: 'guard;
fn lock(&self) -> impl Future<Output = Self::Guard<'_>>;
}
pub trait LocalNotifyLike {
fn notify_one(&self);
fn notified(&self) -> impl Future<Output = ()> + '_;
}
#[cfg(all(feature = "alloc", feature = "std"))]
pub trait LocalRuntimeFactory: Runtime {
type LocalMutex<T: 'static>: LocalMutexLike<T>;
type LocalNotify: LocalNotifyLike;
fn new_local_mutex<T: 'static>(value: T) -> Self::LocalMutex<T>;
fn new_local_notify() -> Self::LocalNotify;
}
#[cfg(test)]
#[allow(clippy::unwrap_used, clippy::expect_used)]
mod tests {
use super::*;
#[test]
fn join_error_is_debug_constructible() {
let _ = format!("{:?}", JoinError::Panicked);
let _ = format!("{:?}", JoinError::Cancelled);
}
}