summaryrefslogtreecommitdiff
path: root/include/haproxy/clock.h
Commit message (Collapse)AuthorAgeFilesLines
* MINOR: clock: provide a function to automatically adjust now_offsetWilly Tarreau2023-05-171-0/+1
| | | | | | | | | Right now there's no way to enforce a specific value of now_ms upon startup in order to compensate for the time it takes to load a config, specifically when dealing with the health check startup. For this we'd need to force the now_offset value to compensate for the last known value of the current date. This patch exposes a function to do exactly this.
* MINOR: clock: measure the total boot timeWilly Tarreau2023-05-171-0/+1
| | | | | | | | | | | | | | | Some huge configs take a significant amount of time to start and this can cause some trouble (e.g. health checks getting delayed and grouped, process not responding to the CLI etc). For example, some configs might start fast in certain environments and slowly in other ones just due to the use of a wrong DNS server that delays all libc's resolutions. Let's first start by measuring it by keeping a copy of the most recently known ready date, once before calling check_config_validity() and then refine it when leaving this function. A last call is finally performed just before deciding to split between master and worker processes, and it covers the whole boot. It's trivial to collect and even allows to get rid of a call to clock_update_date() in function check_config_validity() that was used in hope to better schedule future events.
* MINOR: clock: replace the timeval start_time with start_time_nsWilly Tarreau2023-04-281-1/+1
| | | | | | Now that "now" is no more a timeval, there's no point keeping a copy of it as a timeval, let's also switch start_time to nanoseconds, it simplifies operations.
* MEDIUM: clock: replace timeval "now" with integer "now_ns"Willy Tarreau2023-04-281-2/+2
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | This puts an end to the occasional confusion between the "now" date that is internal, monotonic and not synchronized with the system's date, and "date" which is the system's date and not necessarily monotonic. Variable "now" was removed and replaced with a 64-bit integer "now_ns" which is a counter of nanoseconds. It wraps every 585 years, so if all goes well (i.e. if humanity does not need haproxy anymore in 500 years), it will just never wrap. This implies that now_ns is never nul and that the zero value can reliably be used as "not set yet" for a timestamp if needed. This will also simplify date checks where it becomes possible again to do "date1<date2". All occurrences of "tv_to_ns(&now)" were simply replaced by "now_ns". Due to the intricacies between now, global_now and now_offset, all 3 had to be turned to nanoseconds at once. It's not a problem since all of them were solely used in 3 functions in clock.c, but they make the patch look bigger than it really is. The clock_update_local_date() and clock_update_global_date() functions are now much simpler as there's no need anymore to perform conversions nor to round the timeval up or down. The wrapping continues to happen by presetting the internal offset in the short future so that the 32-bit now_ms continues to wrap 20 seconds after boot. The start_time used to calculate uptime can still be turned to nanoseconds now. One interrogation concerns global_now_ms which is used only for the freq counters. It's unclear whether there's more value in using two variables that need to be synchronized sequentially like today or to just use global_now_ns divided by 1 million. Both approaches will work equally well on modern systems, the difference might come from smaller ones. Better not change anyhting for now. One benefit of the new approach is that we now have an internal date with a resolution of the nanosecond and the precision of the microsecond, which can be useful to extend some measurements given that timestamps also have this resolution.
* MINOR: clock: add now_cpu_time_fast() functionAurelien DARRAGON2023-04-191-0/+1
| | | | | | | | | Same as now_cpu_time(), but for fast queries (less accurate) Relies on now_cpu_time() and now_mono_time_fast() is used as a cache expiration hint to prevent now_cpu_time() from being called too often since it is known to be quite expensive. Depends on commit "MINOR: clock: add now_mono_time_fast() function"
* MINOR: clock: add now_mono_time_fast() functionAurelien DARRAGON2023-04-191-0/+1
| | | | | | | | Same as now_mono_time(), but for fast queries (less accurate) Relies on coarse clock source (also known as fast clock source on some systems). Fallback to now_mono_time() if coarse source is not supported on the system.
* BUG/MINOR: clock: do not mix wall-clock and monotonic time in uptime calculationWilly Tarreau2023-02-081-0/+1
| | | | | | | | | | | | | | | | | | | | | | | | | | We've had a start date even before the internal monotonic clock existed, but once the monotonic clock was added, the start date was not updated to distinguish the wall clock time units and the internal monotonic time units. The distinction is important because both clocks do not necessarily progress at the same speed. The very rare occurrences of the wall-clock date are essentially for human consumption and communication with third parties (e.g. report the start date in "show info" for monitoring purposes). However currently this one is also used to measure the distance to "now" as being the process' uptime. This is actually not correct. It only works because for now the two dates are initialized at the exact same instant at boot but could still be wrong if the system's date shows a big jump backwards during startup for example. In addition the current situation prevents us from enforcing an abritrary offset at boot to reveal some heisenbugs. This patch adds a new "start_time" at boot that is set from "now" and is used in uptime calculations. "start_date" instead is now set from "date" and will always reflect the system date for human consumption (e.g. in "show info"). This way we're now sure that any drift of the internal clock relative to the system date will not impact the reported uptime. This could possibly be backported though it's unlikely that anyone has ever noticed the problem.
* MINOR: clock: split local and global date updatesWilly Tarreau2022-09-211-1/+8
| | | | | | | | | | Pollers that support busy polling spend a lot of time (and cause contention) updating the global date when they're looping over themselves while it serves no purpose: what's needed is only an update on the local date to know when to stop looping. This patch splits clock_pudate_date() into a pair of local and global update functions, so that pollers can be easily improved.
* MINOR: clock: move the clock_ids to clock.cWilly Tarreau2021-10-081-2/+1
| | | | | | | | | This removes the knowledge of clockid_t from anywhere but clock.c, thus eliminating a source of includes burden. The unused clock_id field was removed from thread_info, and the definition setting of clockid_t was removed from compat.h. The most visible change is that the function now_cpu_time_thread() now takes the thread number instead of a tinfo pointer.
* REORG: clock/wdt: move wdt timer initialization to clock.cWilly Tarreau2021-10-081-0/+1
| | | | | | | | | The code that deals with timer creation for the WDT was moved to clock.c and is called with the few relevant arguments. This removes the need for awareness of clock_id from wdt.c and as such saves us from having to share it outside. The timer_t is also known only from both ends but not from the public API so that we don't have to create a fake timer_t anymore on systems which do not support it (e.g. macos).
* REORG: clock: move the clock_id initialization to clock.cWilly Tarreau2021-10-081-0/+1
| | | | | | | This was previously open-coded in run_thread_poll_loop(). Now that we have clock.c dedicated to such stuff, let's move the code there so that we don't need to keep such ifdefs nor to depend on the clock_id.
* CLEANUP: clock: stop exporting before_poll and after_pollWilly Tarreau2021-10-081-2/+0
| | | | We don't need to export them anymore so let's make them static.
* REORG: clock: move the updates of cpu/mono time to clock.cWilly Tarreau2021-10-081-0/+3
| | | | | | | | The entering_poll/leaving_poll/measure_idle functions that were hard to classify and used to move to various locations have now been placed into clock.c since it's precisely about time-keeping. The functions were renamed to clock_*. The samp_time and idle_time values are now static since there is no reason for them to be read from outside.
* REORG: time: move time-keeping code and variables to clock.cWilly Tarreau2021-10-081-0/+45
There is currently a problem related to time keeping. We're mixing the functions to perform calculations with the os-dependent code needed to retrieve and adjust the local time. This patch extracts from time.{c,h} the parts that are solely dedicated to time keeping. These are the "now" or "before_poll" variables for example, as well as the various now_*() functions that make use of gettimeofday() and clock_gettime() to retrieve the current time. The "tv_*" functions moved there were also more appropriately renamed to "clock_*". Other parts used to compute stolen time are in other files, they will have to be picked next.