From ed256361417ceaf6693f76a32675397055eda147 Mon Sep 17 00:00:00 2001 From: Minh Vu Date: Sun, 9 Aug 2026 16:45:35 +0200 Subject: [PATCH] time: wake `DelayQueue` when cleared (#8320) --- tokio-util/src/time/delay_queue.rs | 8 ++++++++ tokio-util/tests/time_delay_queue.rs | 14 ++++++++++++++ 2 files changed, 22 insertions(+) diff --git a/tokio-util/src/time/delay_queue.rs b/tokio-util/src/time/delay_queue.rs index 3c7d65ed4..b53d18046 100644 --- a/tokio-util/src/time/delay_queue.rs +++ b/tokio-util/src/time/delay_queue.rs @@ -1031,10 +1031,18 @@ impl DelayQueue { /// # } /// ``` pub fn clear(&mut self) { + let had_entries = !self.slab.is_empty(); + self.slab.clear(); self.expired = Stack::default(); self.wheel = Wheel::new(); self.delay = None; + + if had_entries { + if let Some(waker) = self.waker.take() { + waker.wake(); + } + } } /// Returns the number of elements the queue can hold without reallocating. diff --git a/tokio-util/tests/time_delay_queue.rs b/tokio-util/tests/time_delay_queue.rs index 74360b39e..a2db75c00 100644 --- a/tokio-util/tests/time_delay_queue.rs +++ b/tokio-util/tests/time_delay_queue.rs @@ -915,6 +915,20 @@ async fn wake_after_remove_last() { assert!(assert_ready!(poll!(queue)).is_none()); } +#[tokio::test(start_paused = true)] +async fn wake_after_clear() { + let mut queue = task::spawn(DelayQueue::new()); + queue.insert("foo", ms(1000)); + + assert_pending!(poll!(queue)); + assert!(!queue.is_woken()); + + queue.clear(); + + assert!(queue.is_woken()); + assert!(assert_ready!(poll!(queue)).is_none()); +} + fn ms(n: u64) -> Duration { Duration::from_millis(n) }