From 521dac80867a67e794ad6613d01e0dae04ea208a Mon Sep 17 00:00:00 2001 From: Tamino Bauknecht Date: Mon, 23 Oct 2023 01:11:38 +0200 Subject: [PATCH] sleeper_thread: Make sleep_for more robust In the previous fix for a passed max duration, the assumption was made that at maximum one second will pass between the duration assignment and the std::condition_variable::sleep_for() call. This implementation makes the behavior more predictable by using sleep_until() instead to emulate the sleep_for() behavior. --- include/util/sleeper_thread.hpp | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/include/util/sleeper_thread.hpp b/include/util/sleeper_thread.hpp index 4eee0aec..62d12931 100644 --- a/include/util/sleeper_thread.hpp +++ b/include/util/sleeper_thread.hpp @@ -67,13 +67,13 @@ class SleeperThread { auto sleep_for(std::chrono::system_clock::duration dur) { std::unique_lock lk(mutex_); CancellationGuard cancel_lock; - using timepoint = std::chrono::system_clock::time_point; - static_assert(std::numeric_limits::max() >= - std::numeric_limits::max()); - if (std::chrono::system_clock::now() >= timepoint::max() - dur) { - dur = timepoint::max() - std::chrono::system_clock::now() - std::chrono::seconds(1); + constexpr auto max_time_point = std::chrono::steady_clock::time_point::max(); + auto wait_end = max_time_point; + auto now = std::chrono::steady_clock::now(); + if (now < max_time_point - dur) { + wait_end = now + dur; } - return condvar_.wait_for(lk, dur, [this] { return signal_ || !do_run_; }); + return condvar_.wait_until(lk, wait_end, [this] { return signal_ || !do_run_; }); } auto sleep_until(