From 2fa4092c2829dd14e50c430ae2f23551d23c6c1d Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Thu, 4 Apr 2013 02:56:56 +0200 Subject: util: make time formatting a bit smarter Instead of outputting "5h 55s 50ms 3us" we'll now output "5h 55.050003s". Also, while outputting the accuracy is configurable. Basically we now try use "dot notation" for all time values > 1min. For >= 1s we use 's' as unit, otherwise for >= 1ms we use 'ms' as unit, and finally 'us'. This should give reasonably values in most cases. --- src/shared/dbus-common.c | 2 +- src/shared/label.c | 2 +- src/shared/time-util.c | 67 +++++++++++++++++++++++++++++++++++++++++------- src/shared/time-util.h | 2 +- src/shared/watchdog.c | 2 +- 5 files changed, 62 insertions(+), 13 deletions(-) (limited to 'src/shared') diff --git a/src/shared/dbus-common.c b/src/shared/dbus-common.c index 0e38933d8a..5afce7627a 100644 --- a/src/shared/dbus-common.c +++ b/src/shared/dbus-common.c @@ -1097,7 +1097,7 @@ int generic_print_property(const char *name, DBusMessageIter *iter, bool all) { } else if (strstr(name, "USec")) { char timespan[FORMAT_TIMESPAN_MAX]; - printf("%s=%s\n", name, format_timespan(timespan, sizeof(timespan), u)); + printf("%s=%s\n", name, format_timespan(timespan, sizeof(timespan), u, 0)); } else printf("%s=%llu\n", name, (unsigned long long) u); diff --git a/src/shared/label.c b/src/shared/label.c index a8bf6bd4f9..1fe4574633 100644 --- a/src/shared/label.c +++ b/src/shared/label.c @@ -82,7 +82,7 @@ int label_init(const char *prefix) { l = after_mallinfo.uordblks > before_mallinfo.uordblks ? after_mallinfo.uordblks - before_mallinfo.uordblks : 0; log_debug("Successfully loaded SELinux database in %s, size on heap is %iK.", - format_timespan(timespan, sizeof(timespan), after_timestamp - before_timestamp), + format_timespan(timespan, sizeof(timespan), after_timestamp - before_timestamp, 0), (l+1023)/1024); } #endif diff --git a/src/shared/time-util.c b/src/shared/time-util.c index 476b847ead..b6a2bec156 100644 --- a/src/shared/time-util.c +++ b/src/shared/time-util.c @@ -225,7 +225,7 @@ char *format_timestamp_relative(char *buf, size_t l, usec_t t) { return buf; } -char *format_timespan(char *buf, size_t l, usec_t t) { +char *format_timespan(char *buf, size_t l, usec_t t, usec_t accuracy) { static const struct { const char *suffix; usec_t usec; @@ -243,6 +243,7 @@ char *format_timespan(char *buf, size_t l, usec_t t) { unsigned i; char *p = buf; + bool something = false; assert(buf); assert(l > 0); @@ -250,17 +251,23 @@ char *format_timespan(char *buf, size_t l, usec_t t) { if (t == (usec_t) -1) return NULL; - if (t == 0) { - snprintf(p, l, "0"); - p[l-1] = 0; - return p; - } - /* The result of this function can be parsed with parse_sec */ for (i = 0; i < ELEMENTSOF(table); i++) { int k; size_t n; + bool done = false; + usec_t a, b; + + if (t == 0 || t < accuracy) { + if (!something) { + snprintf(p, l, "0"); + p[l-1] = 0; + return p; + } + + break; + } if (t < table[i].usec) continue; @@ -268,13 +275,55 @@ char *format_timespan(char *buf, size_t l, usec_t t) { if (l <= 1) break; - k = snprintf(p, l, "%s%llu%s", p > buf ? " " : "", (unsigned long long) (t / table[i].usec), table[i].suffix); + a = t / table[i].usec; + b = t % table[i].usec; + + /* Let's see if we should shows this in dot notation */ + if (t < USEC_PER_MINUTE && b > 0) { + usec_t cc; + int j; + + j = 0; + for (cc = table[i].usec; cc > 1; cc /= 10) + j++; + + for (cc = accuracy; cc > 1; cc /= 10) { + b /= 10; + j--; + } + + if (j > 0) { + k = snprintf(p, l, + "%s%llu.%0*llu%s", + p > buf ? " " : "", + (unsigned long long) a, + j, + (unsigned long long) b, + table[i].suffix); + + t = 0; + done = true; + } + } + + /* No? Then let's show it normally */ + if (!done) { + k = snprintf(p, l, + "%s%llu%s", + p > buf ? " " : "", + (unsigned long long) a, + table[i].suffix); + + t = b; + } + n = MIN((size_t) k, l); l -= n; p += n; - t %= table[i].usec; + + something = true; } *p = 0; diff --git a/src/shared/time-util.h b/src/shared/time-util.h index a02cdfc79f..3fc339507c 100644 --- a/src/shared/time-util.h +++ b/src/shared/time-util.h @@ -74,7 +74,7 @@ struct timeval *timeval_store(struct timeval *tv, usec_t u); char *format_timestamp(char *buf, size_t l, usec_t t); char *format_timestamp_relative(char *buf, size_t l, usec_t t); -char *format_timespan(char *buf, size_t l, usec_t t); +char *format_timespan(char *buf, size_t l, usec_t t, usec_t accuracy); void dual_timestamp_serialize(FILE *f, const char *name, dual_timestamp *t); void dual_timestamp_deserialize(const char *value, dual_timestamp *t); diff --git a/src/shared/watchdog.c b/src/shared/watchdog.c index 13265e7692..ddbe7afd3c 100644 --- a/src/shared/watchdog.c +++ b/src/shared/watchdog.c @@ -60,7 +60,7 @@ static int update_timeout(void) { } watchdog_timeout = (usec_t) sec * USEC_PER_SEC; - log_info("Set hardware watchdog to %s.", format_timespan(buf, sizeof(buf), watchdog_timeout)); + log_info("Set hardware watchdog to %s.", format_timespan(buf, sizeof(buf), watchdog_timeout, 0)); flags = WDIOS_ENABLECARD; r = ioctl(watchdog_fd, WDIOC_SETOPTIONS, &flags); -- cgit v1.2.3-54-g00ecf