BUG/MINOR: mworker: prevent incorrect values in uptime
Since the recent changes on the clocks, now.tv_sec is not to be used
between processes because it's a clock which is local to the process and
does not contain a real unix timestamp. This patch fixes the issue by
using "data.tv_sec" which is the wall clock instead of "now.tv_sec'.
It prevents having incoherent timestamps.
It also introduces some checks on negatives values in order to never
displays a netative value if it was computed from a wrong value set by a
previous haproxy version.
It must be backported as far as 2.0.
diff --git a/src/haproxy.c b/src/haproxy.c
index fe612b0..804e092 100644
--- a/src/haproxy.c
+++ b/src/haproxy.c
@@ -2147,7 +2147,7 @@
}
tmproc->options |= PROC_O_TYPE_MASTER; /* master */
tmproc->pid = pid;
- tmproc->timestamp = start_time.tv_sec;
+ tmproc->timestamp = start_date.tv_sec;
proc_self = tmproc;
LIST_APPEND(&proc_list, &tmproc->list);
@@ -3563,7 +3563,7 @@
if (child->reloads == 0 &&
child->options & PROC_O_TYPE_WORKER &&
child->pid == -1) {
- child->timestamp = now.tv_sec;
+ child->timestamp = date.tv_sec;
child->pid = ret;
child->version = strdup(haproxy_version);
break;
diff --git a/src/mworker.c b/src/mworker.c
index 8b3be19..4bc224e 100644
--- a/src/mworker.c
+++ b/src/mworker.c
@@ -530,13 +530,16 @@
struct stconn *sc = appctx_sc(appctx);
struct mworker_proc *child;
int old = 0;
- int up = now.tv_sec - proc_self->timestamp;
+ int up = date.tv_sec - proc_self->timestamp;
char *uptime = NULL;
char *reloadtxt = NULL;
if (unlikely(sc_ic(sc)->flags & CF_SHUTW))
return 1;
+ if (up < 0) /* must never be negative because of clock drift */
+ up = 0;
+
chunk_reset(&trash);
memprintf(&reloadtxt, "%d [failed: %d]", proc_self->reloads, proc_self->failedreloads);
@@ -550,7 +553,9 @@
chunk_appendf(&trash, "# workers\n");
list_for_each_entry(child, &proc_list, list) {
- up = now.tv_sec - child->timestamp;
+ up = date.tv_sec - child->timestamp;
+ if (up < 0) /* must never be negative because of clock drift */
+ up = 0;
if (!(child->options & PROC_O_TYPE_WORKER))
continue;
@@ -571,7 +576,9 @@
chunk_appendf(&trash, "# old workers\n");
list_for_each_entry(child, &proc_list, list) {
- up = now.tv_sec - child->timestamp;
+ up = date.tv_sec - child->timestamp;
+ if (up <= 0) /* must never be negative because of clock drift */
+ up = 0;
if (!(child->options & PROC_O_TYPE_WORKER))
continue;
@@ -589,7 +596,9 @@
chunk_appendf(&trash, "# programs\n");
old = 0;
list_for_each_entry(child, &proc_list, list) {
- up = now.tv_sec - child->timestamp;
+ up = date.tv_sec - child->timestamp;
+ if (up < 0) /* must never be negative because of clock drift */
+ up = 0;
if (!(child->options & PROC_O_TYPE_PROG))
continue;
@@ -606,7 +615,9 @@
if (old) {
chunk_appendf(&trash, "# old programs\n");
list_for_each_entry(child, &proc_list, list) {
- up = now.tv_sec - child->timestamp;
+ up = date.tv_sec - child->timestamp;
+ if (up < 0) /* must never be negative because of clock drift */
+ up = 0;
if (!(child->options & PROC_O_TYPE_PROG))
continue;