rtx 0.1.0

RTx is a zero-cost runtime-abstraction intended for use by Rust libraries to enable the Freedom of Choice between asynchronous runtimes.
// Sourced from https://github.com/rust-lang/futures-rs/blob/9ec770782cf2e98c93ee43f9568088396687b05b/futures-util/src/future/future/catch_unwind.rs

use std::panic::{catch_unwind, AssertUnwindSafe};
use std::pin::Pin;

use futures_core::future::Future;
use futures_core::task::{Context, Poll};
use pin_project_lite::pin_project;

pin_project! {
    #[derive(Debug)]
    #[must_use = "futures do nothing unless you `.await` or poll them"]
    pub struct CatchUnwind<Fut> {
        #[pin]
        future: Fut,
    }
}

impl<Fut> CatchUnwind<Fut>
where
    // `Send` should imply `UnwindSafe` but it doesn't for historical reasons.
    // Tokio assumes this implication, however, as does every lock API outside of `std`.
    Fut: Future + Send,
{
    pub(super) fn new(future: Fut) -> Self {
        Self { future }
    }
}

impl<Fut> Future for CatchUnwind<Fut>
where
    Fut: Future + Send,
{
    type Output = super::Result<Fut::Output>;

    fn poll(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Self::Output> {
        let f = self.project().future;
        catch_unwind(AssertUnwindSafe(|| f.poll(cx)))?.map(Ok)
    }
}