1 #define _GNU_SOURCE
2 #include <sys/syscall.h>
3 #include <sys/types.h>
4 #include <stdlib.h>
5 #include <stdio.h>
6 #include <errno.h>
7 #include <unistd.h>
8 #include <time.h>
9
ts_subtract(struct timespec * result,const struct timespec * time1,const struct timespec * time2)10 void ts_subtract(struct timespec *result,
11 const struct timespec *time1, const struct timespec *time2) {
12 *result = *time1;
13 result->tv_sec -= time2->tv_sec ;
14 if (result->tv_nsec < time2->tv_nsec) {
15 /* borrow a second */
16 result->tv_nsec += 1000000000L;
17 result->tv_sec--;
18 }
19 result->tv_nsec -= time2->tv_nsec;
20 }
21
usage(const char * cmd)22 void usage(const char *cmd) {
23 fprintf(stderr, "usage: %s <iterations>\n", cmd);
24 }
25
main(int argc,char * argv[])26 int main (int argc, char *argv[]) {
27 struct timespec start_time, end_time, elapsed_time;
28 uid_t uid;
29 long iterations, i;
30 double per_call;
31
32 if (argc != 2) {
33 usage(argv[0]);
34 return 1;
35 }
36
37 iterations = atol(argv[1]);
38 if (iterations < 0) {
39 usage(argv[0]);
40 return 1;
41 }
42
43 if (clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &start_time)) {
44 perror("clock_gettime");
45 return errno;
46 }
47
48 for (i = iterations; i; i--)
49 uid = syscall(SYS_getuid);
50
51 if (clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &end_time)) {
52 perror("clock_gettime");
53 return errno;
54 }
55
56 ts_subtract(&elapsed_time, &end_time, &start_time);
57 per_call = (elapsed_time.tv_sec * 1000000000.0L + elapsed_time.tv_nsec) /
58 (double)iterations;
59 printf("%ld calls in %ld.%09ld s (%lf ns/call)\n", iterations,
60 elapsed_time.tv_sec, elapsed_time.tv_nsec, per_call);
61
62 return 0;
63 }
64