X-Git-Url: https://git.tokkee.org/?a=blobdiff_plain;f=src%2Fcore%2Ftime.c;h=d0ed0b8dd9917d11596fa54da2f65071026c968f;hb=bbd1b997cf153d54878efebc182bd88f1c64d45c;hp=877feb1de9cfe95824063b46e64c5a28b8445680;hpb=39a45905e0b237e458b1826ff9b4fad1c4a59550;p=sysdb.git diff --git a/src/core/time.c b/src/core/time.c index 877feb1..d0ed0b8 100644 --- a/src/core/time.c +++ b/src/core/time.c @@ -29,16 +29,29 @@ # include "config.h" #endif /* HAVE_CONFIG_H */ +#include "sysdb.h" #include "core/time.h" #include +#include +#include #include /* * public API */ +/* 1 second (in nano-seconds) */ +#define SEC 1000000000L + +const sdb_time_t SDB_INTERVAL_YEAR = 3652425L * 24L * 60L * 60L * 100000L; +const sdb_time_t SDB_INTERVAL_MONTH = 30436875L * 24L * 60L * 60L * 1000L; +const sdb_time_t SDB_INTERVAL_DAY = 24L * 60L * 60L * SEC; +const sdb_time_t SDB_INTERVAL_HOUR = 60L * 60L * SEC; +const sdb_time_t SDB_INTERVAL_MINUTE = 60L * SEC; +const sdb_time_t SDB_INTERVAL_SECOND = SEC; + sdb_time_t sdb_gettime(void) { @@ -79,5 +92,87 @@ sdb_strftime(char *s, size_t len, const char *format, sdb_time_t t) return strftime(s, len, format, &tm); } /* sdb_strftime */ +size_t +sdb_strfinterval(char *s, size_t len, sdb_time_t interval) +{ + size_t n = 0; + size_t i; + + /* special case the optional fractional part for seconds */ + bool have_seconds = 0; + + struct { + sdb_time_t interval; + const char *suffix; + } specs[] = { + { SDB_INTERVAL_YEAR, "Y" }, + { SDB_INTERVAL_MONTH, "M" }, + { SDB_INTERVAL_DAY, "D" }, + { SDB_INTERVAL_HOUR, "h" }, + { SDB_INTERVAL_MINUTE, "m" }, + { SDB_INTERVAL_SECOND, "" }, + }; + +#define LEN (len > n ? len - n : 0) + for (i = 0; i < SDB_STATIC_ARRAY_LEN(specs); ++i) { + if (interval >= specs[i].interval) { + n += snprintf(s + n, LEN, "%"PRIsdbTIME"%s", + interval / specs[i].interval, specs[i].suffix); + interval %= specs[i].interval; + if (specs[i].interval == SDB_INTERVAL_SECOND) + have_seconds = 1; + } + } + + if (interval) { + n += snprintf(s + n, LEN, ".%09"PRIsdbTIME, interval); + have_seconds = 1; + + /* removing trailing zeroes */ + if (n <= len) + while (s[n - 1] == '0') + s[n--] = '\0'; + } + + if (! n) { + n = snprintf(s, len, "0"); + have_seconds = 1; + } + + if (have_seconds) + n += snprintf(s + n, LEN, "s"); +#undef LEN + + if (len) + s[len - 1] = '\0'; + return n; +} /* sdb_strfinterval */ + +sdb_time_t +sdb_strpunit(const char *s) +{ + struct { + const char *s; + sdb_time_t unit; + } units[] = { + { "Y", SDB_INTERVAL_YEAR }, + { "M", SDB_INTERVAL_MONTH }, + { "D", SDB_INTERVAL_DAY }, + { "h", SDB_INTERVAL_HOUR }, + { "m", SDB_INTERVAL_MINUTE }, + { "s", SDB_INTERVAL_SECOND }, + { "ms", SDB_INTERVAL_SECOND / 1000L }, + { "us", SDB_INTERVAL_SECOND / 1000000L }, + { "ns", 1 }, + }; + + size_t i; + + for (i = 0; i < SDB_STATIC_ARRAY_LEN(units); ++i) + if (! strcmp(s, units[i].s)) + return units[i].unit; + return 0; +} /* sdb_strpunit */ + /* vim: set tw=78 sw=4 ts=4 noexpandtab : */