* nis/ypclnt.c (__xdr_ypresp_all): Minor optimization in string
[glibc.git] / sysdeps / unix / clock_gettime.c
blobf698f0151b07ad18164aa298165337f9fce94110
1 /* clock_gettime -- Get the current time from a POSIX clockid_t. Unix version.
2 Copyright (C) 1999-2004, 2005 Free Software Foundation, Inc.
3 This file is part of the GNU C Library.
5 The GNU C Library is free software; you can redistribute it and/or
6 modify it under the terms of the GNU Lesser General Public
7 License as published by the Free Software Foundation; either
8 version 2.1 of the License, or (at your option) any later version.
10 The GNU C Library 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 GNU
13 Lesser General Public License for more details.
15 You should have received a copy of the GNU Lesser General Public
16 License along with the GNU C Library; if not, write to the Free
17 Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
18 02111-1307 USA. */
20 #include <errno.h>
21 #include <stdint.h>
22 #include <time.h>
23 #include <sys/time.h>
24 #include <libc-internal.h>
25 #include <ldsodefs.h>
28 #if HP_TIMING_AVAIL
29 /* Clock frequency of the processor. We make it a 64-bit variable
30 because some jokers are already playing with processors with more
31 than 4GHz. */
32 static hp_timing_t freq;
35 /* This function is defined in the thread library. */
36 extern int __pthread_clock_gettime (clockid_t clock_id, hp_timing_t freq,
37 struct timespec *tp)
38 __attribute__ ((__weak__));
40 static int
41 hp_timing_gettime (clockid_t clock_id, struct timespec *tp)
43 hp_timing_t tsc;
45 if (__builtin_expect (freq == 0, 0))
47 /* This can only happen if we haven't initialized the `freq'
48 variable yet. Do this now. We don't have to protect this
49 code against multiple execution since all of them should
50 lead to the same result. */
51 freq = __get_clockfreq ();
52 if (__builtin_expect (freq == 0, 0))
53 /* Something went wrong. */
54 return -1;
57 if (clock_id != CLOCK_PROCESS_CPUTIME_ID
58 && __pthread_clock_gettime != NULL)
59 return __pthread_clock_gettime (clock_id, freq, tp);
61 /* Get the current counter. */
62 HP_TIMING_NOW (tsc);
64 /* Compute the offset since the start time of the process. */
65 tsc -= GL(dl_cpuclock_offset);
67 /* Compute the seconds. */
68 tp->tv_sec = tsc / freq;
70 /* And the nanoseconds. This computation should be stable until
71 we get machines with about 16GHz frequency. */
72 tp->tv_nsec = ((tsc % freq) * UINT64_C (1000000000)) / freq;
74 return 0;
76 #endif
79 static inline int
80 realtime_gettime (struct timespec *tp)
82 struct timeval tv;
83 int retval = gettimeofday (&tv, NULL);
84 if (retval == 0)
85 /* Convert into `timespec'. */
86 TIMEVAL_TO_TIMESPEC (&tv, tp);
87 return retval;
91 /* Get current value of CLOCK and store it in TP. */
92 int
93 clock_gettime (clockid_t clock_id, struct timespec *tp)
95 int retval = -1;
96 struct timeval tv;
98 switch (clock_id)
100 #ifdef SYSDEP_GETTIME
101 SYSDEP_GETTIME;
102 #endif
104 #ifndef HANDLED_REALTIME
105 case CLOCK_REALTIME:
106 retval = gettimeofday (&tv, NULL);
107 if (retval == 0)
108 TIMEVAL_TO_TIMESPEC (&tv, tp);
109 break;
110 #endif
112 default:
113 #ifdef SYSDEP_GETTIME_CPU
114 SYSDEP_GETTIME_CPU;
115 #endif
116 #if HP_TIMING_AVAIL
117 if ((clock_id & ((1 << CLOCK_IDFIELD_SIZE) - 1))
118 == CLOCK_THREAD_CPUTIME_ID)
119 retval = hp_timing_gettime (clock_id, tp);
120 else
121 #endif
122 __set_errno (EINVAL);
123 break;
125 #if HP_TIMING_AVAIL && !defined HANDLED_CPUTIME
126 case CLOCK_PROCESS_CPUTIME_ID:
127 retval = hp_timing_gettime (clock_id, tp);
128 break;
129 #endif
132 return retval;
134 librt_hidden_def (clock_gettime)