verify: new macro 'assume'
[gnulib.git] / lib / gethrxtime.c
1 /* gethrxtime -- get high resolution real time
2
3    Copyright (C) 2005-2007, 2009-2013 Free Software Foundation, Inc.
4
5    This program is free software: you can redistribute it and/or modify
6    it under the terms of the GNU General Public License as published by
7    the Free Software Foundation; either version 3 of the License, or
8    (at your option) any later version.
9
10    This program is distributed in the hope that it will be useful,
11    but WITHOUT ANY WARRANTY; without even the implied warranty of
12    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13    GNU General Public License for more details.
14
15    You should have received a copy of the GNU General Public License
16    along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
17
18 /* Written by Paul Eggert.  */
19
20 #include <config.h>
21
22 #define GETHRXTIME_INLINE _GL_EXTERN_INLINE
23 #include "gethrxtime.h"
24
25 #if ! (HAVE_ARITHMETIC_HRTIME_T && HAVE_DECL_GETHRTIME)
26
27 #include <sys/time.h>
28 #include "timespec.h"
29
30 /* Get the current time, as a count of the number of nanoseconds since
31    an arbitrary epoch (e.g., the system boot time).  Prefer a
32    high-resolution clock that is not subject to resetting or
33    drifting.  */
34
35 xtime_t
36 gethrxtime (void)
37 {
38 # if HAVE_NANOUPTIME
39   {
40     struct timespec ts;
41     nanouptime (&ts);
42     return xtime_make (ts.tv_sec, ts.tv_nsec);
43   }
44 # else
45
46 #  if defined CLOCK_MONOTONIC && HAVE_CLOCK_GETTIME
47   {
48     struct timespec ts;
49     if (clock_gettime (CLOCK_MONOTONIC, &ts) == 0)
50       return xtime_make (ts.tv_sec, ts.tv_nsec);
51   }
52 #  endif
53
54 #  if HAVE_MICROUPTIME
55   {
56     struct timeval tv;
57     microuptime (&tv);
58     return xtime_make (tv.tv_sec, 1000 * tv.tv_usec);
59   }
60
61 #  else
62   /* No monotonically increasing clocks are available; fall back on a
63      clock that might jump backwards, since it's the best we can do.  */
64   {
65     struct timespec ts;
66     gettime (&ts);
67     return xtime_make (ts.tv_sec, ts.tv_nsec);
68   }
69 #  endif
70 # endif
71 }
72
73 #endif