]> git.proxmox.com Git - mirror_frr.git/commitdiff
lib: try CLOCK_THREAD_CPUTIME_ID
authorDavid Lamparter <equinox@diac24.net>
Tue, 13 Apr 2021 18:49:26 +0000 (20:49 +0200)
committerDavid Lamparter <equinox@opensourcerouting.org>
Thu, 24 Jun 2021 14:42:59 +0000 (16:42 +0200)
This might be faster if at some point in the future the Linux vDSO
supports CLOCK_THREAD_CPUTIME_ID without making a syscall.  (Same
applies for other OSes.)

Signed-off-by: David Lamparter <equinox@diac24.net>
configure.ac
lib/thread.c
lib/thread.h

index 9ba95fe98bdc47e73aad6ea7cceb1b94070114bc..0ea209bbfad614c5ae28d6c945a291ec173169b8 100644 (file)
@@ -2229,6 +2229,10 @@ AC_CHECK_DECL([CLOCK_MONOTONIC],
         AC_DEFINE([HAVE_CLOCK_MONOTONIC], [1], [Have monotonic clock])
 ], [AC_MSG_RESULT([no])], [FRR_INCLUDES])
 
+AC_CHECK_DECL([CLOCK_THREAD_CPUTIME_ID], [
+        AC_DEFINE([HAVE_CLOCK_THREAD_CPUTIME_ID], [1], [Have cpu-time clock])
+], [AC_MSG_RESULT([no])], [FRR_INCLUDES])
+
 AC_SEARCH_LIBS([clock_nanosleep], [rt], [
   AC_DEFINE([HAVE_CLOCK_NANOSLEEP], [1], [Have clock_nanosleep()])
 ])
index dd5c1fed4071dd945e6b418e9d486963b784e748..835aa38115addab24ba83d13fbff433543c7a360 100644 (file)
@@ -1821,9 +1821,14 @@ static unsigned long timeval_elapsed(struct timeval a, struct timeval b)
 unsigned long thread_consumed_time(RUSAGE_T *now, RUSAGE_T *start,
                                   unsigned long *cputime)
 {
+#ifdef HAVE_CLOCK_THREAD_CPUTIME_ID
+       *cputime = (now->cpu.tv_sec - start->cpu.tv_sec) * TIMER_SECOND_MICRO
+                  + (now->cpu.tv_nsec - start->cpu.tv_nsec) / 1000;
+#else
        /* This is 'user + sys' time.  */
        *cputime = timeval_elapsed(now->cpu.ru_utime, start->cpu.ru_utime)
                   + timeval_elapsed(now->cpu.ru_stime, start->cpu.ru_stime);
+#endif
        return timeval_elapsed(now->real, start->real);
 }
 
@@ -1856,14 +1861,25 @@ void thread_set_yield_time(struct thread *thread, unsigned long yield_time)
 
 void thread_getrusage(RUSAGE_T *r)
 {
+       monotime(&r->real);
+       if (!cputime_enabled) {
+               memset(&r->cpu, 0, sizeof(r->cpu));
+               return;
+       }
+
+#ifdef HAVE_CLOCK_THREAD_CPUTIME_ID
+       /* not currently implemented in Linux's vDSO, but maybe at some point
+        * in the future?
+        */
+       clock_gettime(CLOCK_THREAD_CPUTIME_ID, &r->cpu);
+#else /* !HAVE_CLOCK_THREAD_CPUTIME_ID */
 #if defined RUSAGE_THREAD
 #define FRR_RUSAGE RUSAGE_THREAD
 #else
 #define FRR_RUSAGE RUSAGE_SELF
 #endif
-       monotime(&r->real);
-       if (cputime_enabled)
-               getrusage(FRR_RUSAGE, &(r->cpu));
+       getrusage(FRR_RUSAGE, &(r->cpu));
+#endif
 }
 
 /*
index 737ed005c5a95f791bc2f43db5350c5be05b4d4d..abd94ff4f05910c82a4cc78a7851739068a9cfda 100644 (file)
@@ -41,7 +41,11 @@ extern unsigned long cputime_threshold;
 extern unsigned long walltime_threshold;
 
 struct rusage_t {
+#ifdef HAVE_CLOCK_THREAD_CPUTIME_ID
+       struct timespec cpu;
+#else
        struct rusage cpu;
+#endif
        struct timeval real;
 };
 #define RUSAGE_T        struct rusage_t