]> git.lizzy.rs Git - rust.git/blob - library/core/src/task/poll.rs
9cf89623d888e2d30227f0d8185837157bef6478
[rust.git] / library / core / src / task / poll.rs
1 #![stable(feature = "futures_api", since = "1.36.0")]
2
3 use crate::convert;
4 use crate::ops::{self, ControlFlow};
5 use crate::result::Result;
6
7 /// Indicates whether a value is available or if the current task has been
8 /// scheduled to receive a wakeup instead.
9 #[must_use = "this `Poll` may be a `Pending` variant, which should be handled"]
10 #[derive(Copy, Clone, Debug, Eq, PartialEq, Ord, PartialOrd, Hash)]
11 #[stable(feature = "futures_api", since = "1.36.0")]
12 pub enum Poll<T> {
13     /// Represents that a value is immediately ready.
14     #[lang = "Ready"]
15     #[stable(feature = "futures_api", since = "1.36.0")]
16     Ready(#[stable(feature = "futures_api", since = "1.36.0")] T),
17
18     /// Represents that a value is not ready yet.
19     ///
20     /// When a function returns `Pending`, the function *must* also
21     /// ensure that the current task is scheduled to be awoken when
22     /// progress can be made.
23     #[lang = "Pending"]
24     #[stable(feature = "futures_api", since = "1.36.0")]
25     Pending,
26 }
27
28 impl<T> Poll<T> {
29     /// Changes the ready value of this `Poll` with the closure provided.
30     #[stable(feature = "futures_api", since = "1.36.0")]
31     pub fn map<U, F>(self, f: F) -> Poll<U>
32     where
33         F: FnOnce(T) -> U,
34     {
35         match self {
36             Poll::Ready(t) => Poll::Ready(f(t)),
37             Poll::Pending => Poll::Pending,
38         }
39     }
40
41     /// Returns `true` if this is `Poll::Ready`
42     #[inline]
43     #[rustc_const_stable(feature = "const_poll", since = "1.49.0")]
44     #[stable(feature = "futures_api", since = "1.36.0")]
45     pub const fn is_ready(&self) -> bool {
46         matches!(*self, Poll::Ready(_))
47     }
48
49     /// Returns `true` if this is `Poll::Pending`
50     #[inline]
51     #[rustc_const_stable(feature = "const_poll", since = "1.49.0")]
52     #[stable(feature = "futures_api", since = "1.36.0")]
53     pub const fn is_pending(&self) -> bool {
54         !self.is_ready()
55     }
56 }
57
58 impl<T, E> Poll<Result<T, E>> {
59     /// Changes the success value of this `Poll` with the closure provided.
60     #[stable(feature = "futures_api", since = "1.36.0")]
61     pub fn map_ok<U, F>(self, f: F) -> Poll<Result<U, E>>
62     where
63         F: FnOnce(T) -> U,
64     {
65         match self {
66             Poll::Ready(Ok(t)) => Poll::Ready(Ok(f(t))),
67             Poll::Ready(Err(e)) => Poll::Ready(Err(e)),
68             Poll::Pending => Poll::Pending,
69         }
70     }
71
72     /// Changes the error value of this `Poll` with the closure provided.
73     #[stable(feature = "futures_api", since = "1.36.0")]
74     pub fn map_err<U, F>(self, f: F) -> Poll<Result<T, U>>
75     where
76         F: FnOnce(E) -> U,
77     {
78         match self {
79             Poll::Ready(Ok(t)) => Poll::Ready(Ok(t)),
80             Poll::Ready(Err(e)) => Poll::Ready(Err(f(e))),
81             Poll::Pending => Poll::Pending,
82         }
83     }
84 }
85
86 impl<T, E> Poll<Option<Result<T, E>>> {
87     /// Changes the success value of this `Poll` with the closure provided.
88     #[stable(feature = "poll_map", since = "1.51.0")]
89     pub fn map_ok<U, F>(self, f: F) -> Poll<Option<Result<U, E>>>
90     where
91         F: FnOnce(T) -> U,
92     {
93         match self {
94             Poll::Ready(Some(Ok(t))) => Poll::Ready(Some(Ok(f(t)))),
95             Poll::Ready(Some(Err(e))) => Poll::Ready(Some(Err(e))),
96             Poll::Ready(None) => Poll::Ready(None),
97             Poll::Pending => Poll::Pending,
98         }
99     }
100
101     /// Changes the error value of this `Poll` with the closure provided.
102     #[stable(feature = "poll_map", since = "1.51.0")]
103     pub fn map_err<U, F>(self, f: F) -> Poll<Option<Result<T, U>>>
104     where
105         F: FnOnce(E) -> U,
106     {
107         match self {
108             Poll::Ready(Some(Ok(t))) => Poll::Ready(Some(Ok(t))),
109             Poll::Ready(Some(Err(e))) => Poll::Ready(Some(Err(f(e)))),
110             Poll::Ready(None) => Poll::Ready(None),
111             Poll::Pending => Poll::Pending,
112         }
113     }
114 }
115
116 #[stable(feature = "futures_api", since = "1.36.0")]
117 impl<T> From<T> for Poll<T> {
118     /// Convert to a `Ready` variant.
119     ///
120     /// # Example
121     ///
122     /// ```
123     /// # use core::task::Poll;
124     /// assert_eq!(Poll::from(true), Poll::Ready(true));
125     /// ```
126     fn from(t: T) -> Poll<T> {
127         Poll::Ready(t)
128     }
129 }
130
131 #[stable(feature = "futures_api", since = "1.36.0")]
132 #[cfg(bootstrap)]
133 impl<T, E> ops::TryV1 for Poll<Result<T, E>> {
134     type Output = Poll<T>;
135     type Error = E;
136
137     #[inline]
138     fn into_result(self) -> Result<Self::Output, Self::Error> {
139         match self {
140             Poll::Ready(Ok(x)) => Ok(Poll::Ready(x)),
141             Poll::Ready(Err(e)) => Err(e),
142             Poll::Pending => Ok(Poll::Pending),
143         }
144     }
145
146     #[inline]
147     fn from_error(e: Self::Error) -> Self {
148         Poll::Ready(Err(e))
149     }
150
151     #[inline]
152     fn from_ok(x: Self::Output) -> Self {
153         x.map(Ok)
154     }
155 }
156
157 #[unstable(feature = "try_trait_v2", issue = "84277")]
158 impl<T, E> ops::TryV2 for Poll<Result<T, E>> {
159     type Output = Poll<T>;
160     type Residual = Result<convert::Infallible, E>;
161
162     #[inline]
163     fn from_output(c: Self::Output) -> Self {
164         c.map(Ok)
165     }
166
167     #[inline]
168     fn branch(self) -> ControlFlow<Self::Residual, Self::Output> {
169         match self {
170             Poll::Ready(Ok(x)) => ControlFlow::Continue(Poll::Ready(x)),
171             Poll::Ready(Err(e)) => ControlFlow::Break(Err(e)),
172             Poll::Pending => ControlFlow::Continue(Poll::Pending),
173         }
174     }
175 }
176
177 #[unstable(feature = "try_trait_v2", issue = "84277")]
178 impl<T, E, F: From<E>> ops::FromResidual<Result<convert::Infallible, E>> for Poll<Result<T, F>> {
179     #[inline]
180     fn from_residual(x: Result<convert::Infallible, E>) -> Self {
181         match x {
182             Err(e) => Poll::Ready(Err(From::from(e))),
183         }
184     }
185 }
186
187 #[stable(feature = "futures_api", since = "1.36.0")]
188 #[cfg(bootstrap)]
189 impl<T, E> ops::TryV1 for Poll<Option<Result<T, E>>> {
190     type Output = Poll<Option<T>>;
191     type Error = E;
192
193     #[inline]
194     fn into_result(self) -> Result<Self::Output, Self::Error> {
195         match self {
196             Poll::Ready(Some(Ok(x))) => Ok(Poll::Ready(Some(x))),
197             Poll::Ready(Some(Err(e))) => Err(e),
198             Poll::Ready(None) => Ok(Poll::Ready(None)),
199             Poll::Pending => Ok(Poll::Pending),
200         }
201     }
202
203     #[inline]
204     fn from_error(e: Self::Error) -> Self {
205         Poll::Ready(Some(Err(e)))
206     }
207
208     #[inline]
209     fn from_ok(x: Self::Output) -> Self {
210         x.map(|x| x.map(Ok))
211     }
212 }
213
214 #[unstable(feature = "try_trait_v2", issue = "84277")]
215 impl<T, E> ops::TryV2 for Poll<Option<Result<T, E>>> {
216     type Output = Poll<Option<T>>;
217     type Residual = Result<convert::Infallible, E>;
218
219     #[inline]
220     fn from_output(c: Self::Output) -> Self {
221         c.map(|x| x.map(Ok))
222     }
223
224     #[inline]
225     fn branch(self) -> ControlFlow<Self::Residual, Self::Output> {
226         match self {
227             Poll::Ready(Some(Ok(x))) => ControlFlow::Continue(Poll::Ready(Some(x))),
228             Poll::Ready(Some(Err(e))) => ControlFlow::Break(Err(e)),
229             Poll::Ready(None) => ControlFlow::Continue(Poll::Ready(None)),
230             Poll::Pending => ControlFlow::Continue(Poll::Pending),
231         }
232     }
233 }
234
235 #[unstable(feature = "try_trait_v2", issue = "84277")]
236 impl<T, E, F: From<E>> ops::FromResidual<Result<convert::Infallible, E>>
237     for Poll<Option<Result<T, F>>>
238 {
239     #[inline]
240     fn from_residual(x: Result<convert::Infallible, E>) -> Self {
241         match x {
242             Err(e) => Poll::Ready(Some(Err(From::from(e)))),
243         }
244     }
245 }