+
+ #[test]
+ #[cfg(feature = "std")]
+ fn multi_poll_stores_single_waker() {
+ // When a `Future` is `poll()`ed multiple times, only the last `Waker` should be called,
+ // but previously we'd store all `Waker`s until they're all woken at once. This tests a few
+ // cases to ensure `Future`s avoid storing an endless set of `Waker`s.
+ let notifier = Notifier::new();
+ let future_state = Arc::clone(¬ifier.get_future().state);
+ assert_eq!(future_state.lock().unwrap().std_future_callbacks.len(), 0);
+
+ // Test that simply polling a future twice doesn't result in two pending `Waker`s.
+ let mut future_a = notifier.get_future();
+ assert_eq!(Pin::new(&mut future_a).poll(&mut Context::from_waker(&create_waker().1)), Poll::Pending);
+ assert_eq!(future_state.lock().unwrap().std_future_callbacks.len(), 1);
+ assert_eq!(Pin::new(&mut future_a).poll(&mut Context::from_waker(&create_waker().1)), Poll::Pending);
+ assert_eq!(future_state.lock().unwrap().std_future_callbacks.len(), 1);
+
+ // If we poll a second future, however, that will store a second `Waker`.
+ let mut future_b = notifier.get_future();
+ assert_eq!(Pin::new(&mut future_b).poll(&mut Context::from_waker(&create_waker().1)), Poll::Pending);
+ assert_eq!(future_state.lock().unwrap().std_future_callbacks.len(), 2);
+
+ // but when we drop the `Future`s, the pending Wakers will also be dropped.
+ mem::drop(future_a);
+ assert_eq!(future_state.lock().unwrap().std_future_callbacks.len(), 1);
+ mem::drop(future_b);
+ assert_eq!(future_state.lock().unwrap().std_future_callbacks.len(), 0);
+
+ // Further, after polling a future twice, if the notifier is woken all Wakers are dropped.
+ let mut future_a = notifier.get_future();
+ assert_eq!(Pin::new(&mut future_a).poll(&mut Context::from_waker(&create_waker().1)), Poll::Pending);
+ assert_eq!(future_state.lock().unwrap().std_future_callbacks.len(), 1);
+ assert_eq!(Pin::new(&mut future_a).poll(&mut Context::from_waker(&create_waker().1)), Poll::Pending);
+ assert_eq!(future_state.lock().unwrap().std_future_callbacks.len(), 1);
+ notifier.notify();
+ assert_eq!(future_state.lock().unwrap().std_future_callbacks.len(), 0);
+ assert_eq!(Pin::new(&mut future_a).poll(&mut Context::from_waker(&create_waker().1)), Poll::Ready(()));
+ assert_eq!(future_state.lock().unwrap().std_future_callbacks.len(), 0);
+ }