]> git.proxmox.com Git - mirror_frr.git/blobdiff - lib/monotime.h
Merge pull request #12798 from donaldsharp/rib_match_multicast
[mirror_frr.git] / lib / monotime.h
index dda763784fe528fcf99705a42352dc5c040d7145..f7ae1bbbe1a95a92cf0b07e0e1799e6925ee039c 100644 (file)
@@ -1,17 +1,6 @@
+// SPDX-License-Identifier: ISC
 /*
  * Copyright (c) 2017  David Lamparter, for NetDEF, Inc.
- *
- * Permission to use, copy, modify, and distribute this software for any
- * purpose with or without fee is hereby granted, provided that the above
- * copyright notice and this permission notice appear in all copies.
- *
- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
  */
 
 #ifndef _FRR_MONOTIME_H
@@ -25,6 +14,9 @@
 extern "C" {
 #endif
 
+struct fbuf;
+struct printfrr_eargs;
+
 #ifndef TIMESPEC_TO_TIMEVAL
 /* should be in sys/time.h on BSD & Linux libcs */
 #define TIMESPEC_TO_TIMEVAL(tv, ts)                                            \
@@ -42,6 +34,31 @@ extern "C" {
        } while (0)
 #endif
 
+/* Linux/glibc is sadly missing these timespec helpers */
+#ifndef timespecadd
+#define timespecadd(tsp, usp, vsp)                                             \
+       do {                                                                   \
+               (vsp)->tv_sec = (tsp)->tv_sec + (usp)->tv_sec;                 \
+               (vsp)->tv_nsec = (tsp)->tv_nsec + (usp)->tv_nsec;              \
+               if ((vsp)->tv_nsec >= 1000000000L) {                           \
+                       (vsp)->tv_sec++;                                       \
+                       (vsp)->tv_nsec -= 1000000000L;                         \
+               }                                                              \
+       } while (0)
+#endif
+
+#ifndef timespecsub
+#define timespecsub(tsp, usp, vsp)                                             \
+       do {                                                                   \
+               (vsp)->tv_sec = (tsp)->tv_sec - (usp)->tv_sec;                 \
+               (vsp)->tv_nsec = (tsp)->tv_nsec - (usp)->tv_nsec;              \
+               if ((vsp)->tv_nsec < 0) {                                      \
+                       (vsp)->tv_sec--;                                       \
+                       (vsp)->tv_nsec += 1000000000L;                         \
+               }                                                              \
+       } while (0)
+#endif
+
 static inline time_t monotime(struct timeval *tvo)
 {
        struct timespec ts;
@@ -53,9 +70,9 @@ static inline time_t monotime(struct timeval *tvo)
        return ts.tv_sec;
 }
 
-#define ONE_DAY_SECOND 60*60*24
-#define ONE_WEEK_SECOND ONE_DAY_SECOND*7
-#define ONE_YEAR_SECOND ONE_DAY_SECOND*365
+#define ONE_DAY_SECOND (60 * 60 * 24)
+#define ONE_WEEK_SECOND (ONE_DAY_SECOND * 7)
+#define ONE_YEAR_SECOND (ONE_DAY_SECOND * 365)
 
 /* the following two return microseconds, not time_t!
  *
@@ -132,6 +149,53 @@ static inline const char *frrtime_to_interval(time_t t, char *buf,
        return buf;
 }
 
+enum {
+       /* n/a - input was seconds precision, don't print any fractional */
+       TIMEFMT_SECONDS = (1 << 0),
+       /* caller is directly invoking printfrr_time and has pre-specified
+        * I/Iu/Is/M/Mu/Ms/R/Ru/Rs (for printing timers)
+        */
+       TIMEFMT_PRESELECT = (1 << 1),
+       /* don't print any output - this is needed for invoking printfrr_time
+        * from another printfrr extensions to skip over flag characters
+        */
+       TIMEFMT_SKIP = (1 << 2),
+       /* use spaces in appropriate places */
+       TIMEFMT_SPACE = (1 << 3),
+
+       /* input interpretations: */
+       TIMEFMT_REALTIME = (1 << 8),
+       TIMEFMT_MONOTONIC = (1 << 9),
+       TIMEFMT_SINCE = (1 << 10),
+       TIMEFMT_UNTIL = (1 << 11),
+
+       TIMEFMT_ABSOLUTE = TIMEFMT_REALTIME | TIMEFMT_MONOTONIC,
+       TIMEFMT_ANCHORS = TIMEFMT_SINCE | TIMEFMT_UNTIL,
+
+       /* calendaric formats: */
+       TIMEFMT_ISO8601 = (1 << 16),
+
+       /* interval formats: */
+       /* 't' - use [t]raditional 3-block format */
+       TIMEFMT_BASIC = (1 << 24),
+       /* 'm' - select mm:ss */
+       TIMEFMT_MMSS = (1 << 25),
+       /* 'h' - select hh:mm:ss */
+       TIMEFMT_HHMMSS = (1 << 26),
+       /* 'd' - print as decimal number of seconds */
+       TIMEFMT_DECIMAL = (1 << 27),
+       /* 'mx'/'hx' - replace zero value with "--:--" or "--:--:--" */
+       TIMEFMT_DASHES = (1 << 31),
+
+       /* helpers for reference */
+       TIMEFMT_TIMER_DEADLINE =
+               TIMEFMT_PRESELECT | TIMEFMT_MONOTONIC | TIMEFMT_UNTIL,
+       TIMEFMT_TIMER_INTERVAL = TIMEFMT_PRESELECT,
+};
+
+extern ssize_t printfrr_time(struct fbuf *buf, struct printfrr_eargs *ea,
+                            const struct timespec *ts, unsigned int flags);
+
 #ifdef __cplusplus
 }
 #endif