From 48a7ece8d0e065240153a85089f544383e16137f Mon Sep 17 00:00:00 2001 From: Julian Andres Klode Date: Tue, 27 Jul 2021 16:40:38 +0200 Subject: Convert to monotonic clock This yields more accurate delays and avoids issues with clock skew. --- apt-pkg/acquire-item.cc | 6 +++--- apt-pkg/acquire-item.h | 5 +++-- apt-pkg/acquire-worker.cc | 5 +++-- apt-pkg/acquire.cc | 32 ++++++++++++++++++-------------- apt-pkg/acquire.h | 7 ++++++- 5 files changed, 33 insertions(+), 22 deletions(-) diff --git a/apt-pkg/acquire-item.cc b/apt-pkg/acquire-item.cc index 20d80edc0..eb8053feb 100644 --- a/apt-pkg/acquire-item.cc +++ b/apt-pkg/acquire-item.cc @@ -290,7 +290,7 @@ public: std::vector BadAlternativeSites; std::vector PastRedirections; std::unordered_map CustomFields; - time_t FetchAfter = 0; + time_point FetchAfter = {}; Private() { @@ -1121,11 +1121,11 @@ std::string pkgAcquire::Item::HashSum() const /*{{{*/ return hs != NULL ? hs->toStr() : ""; } /*}}}*/ -void pkgAcquire::Item::FetchAfter(time_t FetchAfter) /*{{{*/ +void pkgAcquire::Item::FetchAfter(time_point FetchAfter) /*{{{*/ { d->FetchAfter = FetchAfter; } -time_t pkgAcquire::Item::FetchAfter() +pkgAcquire::time_point pkgAcquire::Item::FetchAfter() { return d->FetchAfter; } diff --git a/apt-pkg/acquire-item.h b/apt-pkg/acquire-item.h index 33106226f..22da9815d 100644 --- a/apt-pkg/acquire-item.h +++ b/apt-pkg/acquire-item.h @@ -301,8 +301,9 @@ class APT_PUBLIC pkgAcquire::Item : public WeakPointable /*{{{*/ /** \brief The priority of the item, used for queuing */ int APT_HIDDEN Priority(); - void APT_HIDDEN FetchAfter(time_t FetchAfter); - time_t APT_HIDDEN FetchAfter(); + /** \brief internal clock definitions to avoid typing all that all over the place */ + void APT_HIDDEN FetchAfter(time_point FetchAfter); + time_point APT_HIDDEN FetchAfter(); protected: /** \brief The acquire object with which this item is associated. */ diff --git a/apt-pkg/acquire-worker.cc b/apt-pkg/acquire-worker.cc index 5272ae0cb..7be51d114 100644 --- a/apt-pkg/acquire-worker.cc +++ b/apt-pkg/acquire-worker.cc @@ -632,7 +632,7 @@ void pkgAcquire::Worker::HandleFailure(std::vector const &It pkgAcquire::MethodConfig *const Config, pkgAcquireStatus *const Log, std::string const &Message, bool const errTransient, bool const errAuthErr) { - time_t currentTime = time(nullptr); + auto currentTime = clock::now(); for (auto const Owner : ItmOwners) { std::string NewURI; @@ -644,7 +644,8 @@ void pkgAcquire::Worker::HandleFailure(std::vector const &It if (_config->FindB("Acquire::Retries::Delay", true)) { auto Iter = _config->FindI("Acquire::Retries", 3) - Owner->Retries - 1; - Owner->FetchAfter(currentTime + (1 << Iter)); + auto Dur = std::chrono::seconds(1 << Iter); + Owner->FetchAfter(currentTime + Dur); } else { diff --git a/apt-pkg/acquire.cc b/apt-pkg/acquire.cc index 5b3d5906b..e97f5e6f3 100644 --- a/apt-pkg/acquire.cc +++ b/apt-pkg/acquire.cc @@ -53,6 +53,14 @@ using namespace std; +// helper to convert time_point to a timeval +static struct timeval SteadyDurationToTimeVal(std::chrono::steady_clock::duration Time) +{ + auto const Time_sec = std::chrono::duration_cast(Time); + auto const Time_usec = std::chrono::duration_cast(Time - Time_sec); + return {Time_sec.count(), Time_usec.count()}; +} + std::string pkgAcquire::URIEncode(std::string const &part) /*{{{*/ { // The "+" is encoded as a workaround for an S3 bug (LP#1003633 and LP#1086997) @@ -717,8 +725,8 @@ pkgAcquire::RunResult pkgAcquire::Run(int PulseIntervall) SetFds(Highest,&RFds,&WFds); // Shorten the select() cycle in case we have items about to become ready - time_t now = time(nullptr); - time_t fetchAfter = 0; + auto now = clock::now(); + auto fetchAfter = time_point{}; for (Queue *I = Queues; I != nullptr; I = I->Next) { if (I->Items == nullptr) @@ -726,7 +734,7 @@ pkgAcquire::RunResult pkgAcquire::Run(int PulseIntervall) auto f = I->Items->GetFetchAfter(); - if (f == 0 || I->Items->Owner->Status != pkgAcquire::Item::StatIdle) + if (f == time_point() || I->Items->Owner->Status != pkgAcquire::Item::StatIdle) continue; if (f <= now) @@ -735,16 +743,15 @@ pkgAcquire::RunResult pkgAcquire::Run(int PulseIntervall) fetchAfter = now; // need to time out in select() below assert(I->Items->Owner->Status != pkgAcquire::Item::StatIdle); } - else if (f < fetchAfter || fetchAfter == 0) + else if (f < fetchAfter || fetchAfter == time_point{}) { fetchAfter = f; } } - if (fetchAfter && (fetchAfter - now) < (tv.tv_sec + tv.tv_usec / 1e6)) + if (fetchAfter != time_point{} && (fetchAfter - now) < std::chrono::seconds(tv.tv_sec) + std::chrono::microseconds(tv.tv_usec)) { - tv.tv_sec = fetchAfter - now; - tv.tv_usec = 0; + tv = SteadyDurationToTimeVal(fetchAfter - now); } int Res; @@ -1191,7 +1198,7 @@ bool pkgAcquire::Queue::Cycle() // Look for a queable item QItem *I = Items; int ActivePriority = 0; - time_t currentTime = time(nullptr); + auto currentTime = clock::now(); while (PipeDepth < static_cast(MaxPipeDepth)) { for (; I != 0; I = I->Next) { @@ -1281,9 +1288,9 @@ APT_PURE int pkgAcquire::Queue::QItem::GetPriority() const /*{{{*/ return Priority; } /*}}}*/ -APT_PURE time_t pkgAcquire::Queue::QItem::GetFetchAfter() const /*{{{*/ +APT_PURE pkgAcquire::time_point pkgAcquire::Queue::QItem::GetFetchAfter() const /*{{{*/ { - time_t FetchAfter = 0; + time_point FetchAfter{}; for (auto const &O : Owners) FetchAfter = std::max(FetchAfter, O->FetchAfter()); @@ -1347,10 +1354,7 @@ pkgAcquireStatus::pkgAcquireStatus() : d(NULL), Percent(-1), Update(true), MoreP as well as the current CPS estimate. */ static struct timeval GetTimevalFromSteadyClock() { - auto const Time = std::chrono::steady_clock::now().time_since_epoch(); - auto const Time_sec = std::chrono::duration_cast(Time); - auto const Time_usec = std::chrono::duration_cast(Time - Time_sec); - return { Time_sec.count(), Time_usec.count() }; + return SteadyDurationToTimeVal(std::chrono::steady_clock::now().time_since_epoch()); } bool pkgAcquireStatus::Pulse(pkgAcquire *Owner) { diff --git a/apt-pkg/acquire.h b/apt-pkg/acquire.h index 303554041..09bb408bc 100644 --- a/apt-pkg/acquire.h +++ b/apt-pkg/acquire.h @@ -69,6 +69,7 @@ #include #include +#include #include #include @@ -92,6 +93,10 @@ class metaIndex; class APT_PUBLIC pkgAcquire { private: + /** \brief The monotonic clock used by the Acquire system */ + using clock = std::chrono::steady_clock; + /** \brief Time point on our monotonic clock */ + using time_point = std::chrono::time_point; /** \brief FD of the Lock file we acquire in Setup (if any) */ int LockFD; /** \brief dpointer placeholder (for later in case we need it) */ @@ -459,7 +464,7 @@ class APT_PUBLIC pkgAcquire::Queue /** @return the maximum priority of this item */ int APT_HIDDEN GetPriority() const; /** @return the maximum time to fetch this item at */ - time_t APT_HIDDEN GetFetchAfter() const; + time_point APT_HIDDEN GetFetchAfter() const; }; /** \brief The name of this queue. */ -- cgit v1.2.3-70-g09d2