| 1 | use core::pin::Pin; |
| 2 | |
| 3 | use pin_project_lite::pin_project; |
| 4 | |
| 5 | pin_project! { |
| 6 | /// UnfoldState used for stream and sink unfolds |
| 7 | #[project = UnfoldStateProj] |
| 8 | #[project_replace = UnfoldStateProjReplace] |
| 9 | #[derive (Debug)] |
| 10 | pub(crate) enum UnfoldState<T, R> { |
| 11 | Value { |
| 12 | value: T, |
| 13 | }, |
| 14 | Future { |
| 15 | #[pin] |
| 16 | future: R, |
| 17 | }, |
| 18 | Empty, |
| 19 | } |
| 20 | } |
| 21 | |
| 22 | impl<T, R> UnfoldState<T, R> { |
| 23 | pub(crate) fn project_future(self: Pin<&mut Self>) -> Option<Pin<&mut R>> { |
| 24 | match self.project() { |
| 25 | UnfoldStateProj::Future { future: Pin<&mut R> } => Some(future), |
| 26 | _ => None, |
| 27 | } |
| 28 | } |
| 29 | |
| 30 | pub(crate) fn take_value(self: Pin<&mut Self>) -> Option<T> { |
| 31 | match &*self { |
| 32 | Self::Value { .. } => match self.project_replace(Self::Empty) { |
| 33 | UnfoldStateProjReplace::Value { value: T } => Some(value), |
| 34 | _ => unreachable!(), |
| 35 | }, |
| 36 | _ => None, |
| 37 | } |
| 38 | } |
| 39 | } |
| 40 | |