monoio/macros/
pin.rs

1/// Pins a value on the stack.
2///
3/// Calls to `async fn` return anonymous [`Future`] values that are `!Unpin`.
4/// These values must be pinned before they can be polled. Calling `.await` will
5/// handle this, but consumes the future. If it is required to call `.await` on
6/// a `&mut _` reference, the caller is responsible for pinning the future.
7///
8/// Pinning may be done by allocating with [`Box::pin`] or by using the stack
9/// with the `pin!` macro.
10///
11/// The following will **fail to compile**:
12///
13/// ```compile_fail
14/// use monoio::pin;
15/// async fn my_async_fn() {
16///     // async logic here
17/// }
18///
19/// #[monoio::main]
20/// async fn main() {
21///     let mut future = pin!(my_async_fn());
22///     (&mut future).await;
23/// }
24/// ```
25///
26/// To make this work requires pinning:
27///
28/// ```
29/// use monoio::pin;
30///
31/// async fn my_async_fn() {
32///     // async logic here
33/// }
34///
35/// #[monoio::main]
36/// async fn main() {
37///     let future = my_async_fn();
38///     pin!(future);
39///
40///     (&mut future).await;
41/// }
42/// ```
43///
44/// Pinning is useful when using `select!` and stream operators that require `T:
45/// Stream + Unpin`.
46///
47/// [`Future`]: trait@std::future::Future
48/// [`Box::pin`]: std::boxed::Box::pin
49///
50/// # Usage
51///
52/// The `pin!` macro takes **identifiers** as arguments. It does **not** work
53/// with expressions.
54///
55/// The following does not compile as an expression is passed to `pin!`.
56///
57/// ```compile_fail
58/// use monoio::pin;
59/// async fn my_async_fn() {
60///     // async logic here
61/// }
62///
63/// #[monoio::main]
64/// async fn main() {
65///     let mut future = pin!(my_async_fn());
66///     (&mut future).await;
67/// }
68/// ```
69///
70/// Because assigning to a variable followed by pinning is common, there is also
71/// a variant of the macro that supports doing both in one go.
72///
73/// ```
74/// use monoio::{pin, select};
75///
76/// async fn my_async_fn() {
77///     // async logic here
78/// }
79///
80/// #[monoio::main]
81/// async fn main() {
82///     pin! {
83///         let future1 = my_async_fn();
84///         let future2 = my_async_fn();
85///     }
86///
87///     select! {
88///         _ = &mut future1 => {}
89///         _ = &mut future2 => {}
90///     }
91/// }
92/// ```
93#[deprecated(note = "use std::pin::pin instead")]
94#[macro_export]
95macro_rules! pin {
96    ($($x:ident),*) => { $(
97        // Move the value to ensure that it is owned
98        let mut $x = $x;
99        // Shadow the original binding so that it can't be directly accessed
100        // ever again.
101        #[allow(unused_mut)]
102        let mut $x = unsafe {
103            $crate::macros::support::Pin::new_unchecked(&mut $x)
104        };
105    )* };
106    ($(
107            let $x:ident = $init:expr;
108    )*) => {
109        $(
110            let $x = $init;
111            $crate::pin!($x);
112        )*
113    };
114}