blob: b121b432f428d7f37dfde62cdec6ce9f13e53f3c [file] [log] [blame]
Alexander Belopolsky6fc4ade2010-08-05 17:34:27 +00001#include "Python.h"
Victor Stinner09225b72012-02-07 23:41:01 +01002#ifdef MS_WINDOWS
Minmin Gongf6605672020-05-18 09:22:53 -07003#include <winsock2.h> /* struct timeval */
Victor Stinner09225b72012-02-07 23:41:01 +01004#endif
Alexander Belopolsky6fc4ade2010-08-05 17:34:27 +00005
Victor Stinnerae586492014-09-02 23:18:25 +02006#if defined(__APPLE__)
7#include <mach/mach_time.h> /* mach_absolute_time(), mach_timebase_info() */
8#endif
9
Victor Stinnerc60542b2015-09-10 15:55:07 +020010#define _PyTime_check_mul_overflow(a, b) \
11 (assert(b > 0), \
12 (_PyTime_t)(a) < _PyTime_MIN / (_PyTime_t)(b) \
13 || _PyTime_MAX / (_PyTime_t)(b) < (_PyTime_t)(a))
14
Victor Stinnercb29f012015-03-27 13:31:18 +010015/* To millisecond (10^-3) */
Victor Stinner580ef132015-03-20 01:55:04 +010016#define SEC_TO_MS 1000
Victor Stinner580ef132015-03-20 01:55:04 +010017
Victor Stinnercb29f012015-03-27 13:31:18 +010018/* To microseconds (10^-6) */
19#define MS_TO_US 1000
Victor Stinner580ef132015-03-20 01:55:04 +010020#define SEC_TO_US (SEC_TO_MS * MS_TO_US)
21
Victor Stinnercb29f012015-03-27 13:31:18 +010022/* To nanoseconds (10^-9) */
23#define US_TO_NS 1000
24#define MS_TO_NS (MS_TO_US * US_TO_NS)
25#define SEC_TO_NS (SEC_TO_MS * MS_TO_NS)
26
Victor Stinner62d1c702015-04-01 17:47:07 +020027/* Conversion from nanoseconds */
28#define NS_TO_MS (1000 * 1000)
29#define NS_TO_US (1000)
30
Victor Stinner5d272cc2012-03-13 13:35:55 +010031static void
32error_time_t_overflow(void)
Victor Stinner643cd682012-03-02 22:54:03 +010033{
Victor Stinner5d272cc2012-03-13 13:35:55 +010034 PyErr_SetString(PyExc_OverflowError,
35 "timestamp out of range for platform time_t");
36}
37
Victor Stinner277c8402017-10-11 08:11:38 -070038static void
39_PyTime_overflow(void)
40{
41 PyErr_SetString(PyExc_OverflowError,
42 "timestamp too large to convert to C _PyTime_t");
43}
44
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -070045
Victor Stinnerc29b5852017-11-02 07:28:27 -070046_PyTime_t
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -070047_PyTime_MulDiv(_PyTime_t ticks, _PyTime_t mul, _PyTime_t div)
48{
49 _PyTime_t intpart, remaining;
50 /* Compute (ticks * mul / div) in two parts to prevent integer overflow:
51 compute integer part, and then the remaining part.
52
53 (ticks * mul) / div == (ticks / div) * mul + (ticks % div) * mul / div
54
55 The caller must ensure that "(div - 1) * mul" cannot overflow. */
56 intpart = ticks / div;
57 ticks %= div;
58 remaining = ticks * mul;
59 remaining /= div;
60 return intpart * mul + remaining;
61}
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -070062
63
Larry Hastings76ad59b2012-05-03 00:30:07 -070064time_t
Victor Stinner5d272cc2012-03-13 13:35:55 +010065_PyLong_AsTime_t(PyObject *obj)
66{
Benjamin Petersoned4aa832016-09-05 17:44:18 -070067#if SIZEOF_TIME_T == SIZEOF_LONG_LONG
Benjamin Petersonaf580df2016-09-06 10:46:49 -070068 long long val;
Victor Stinner5d272cc2012-03-13 13:35:55 +010069 val = PyLong_AsLongLong(obj);
70#else
71 long val;
Serhiy Storchakafad85aa2015-11-07 15:42:38 +020072 Py_BUILD_ASSERT(sizeof(time_t) <= sizeof(long));
Victor Stinner5d272cc2012-03-13 13:35:55 +010073 val = PyLong_AsLong(obj);
74#endif
75 if (val == -1 && PyErr_Occurred()) {
Victor Stinner277c8402017-10-11 08:11:38 -070076 if (PyErr_ExceptionMatches(PyExc_OverflowError)) {
Victor Stinner5d272cc2012-03-13 13:35:55 +010077 error_time_t_overflow();
Victor Stinner277c8402017-10-11 08:11:38 -070078 }
Victor Stinner5d272cc2012-03-13 13:35:55 +010079 return -1;
80 }
81 return (time_t)val;
82}
83
Larry Hastings6fe20b32012-04-19 15:07:49 -070084PyObject *
85_PyLong_FromTime_t(time_t t)
86{
Benjamin Petersoned4aa832016-09-05 17:44:18 -070087#if SIZEOF_TIME_T == SIZEOF_LONG_LONG
Benjamin Petersonaf580df2016-09-06 10:46:49 -070088 return PyLong_FromLongLong((long long)t);
Larry Hastings6fe20b32012-04-19 15:07:49 -070089#else
Serhiy Storchakafad85aa2015-11-07 15:42:38 +020090 Py_BUILD_ASSERT(sizeof(time_t) <= sizeof(long));
Larry Hastings6fe20b32012-04-19 15:07:49 -070091 return PyLong_FromLong((long)t);
92#endif
93}
94
Victor Stinnerce6aa742015-09-09 22:28:09 +020095/* Round to nearest with ties going to nearest even integer
96 (_PyTime_ROUND_HALF_EVEN) */
97static double
Victor Stinner7667f582015-09-09 01:02:23 +020098_PyTime_RoundHalfEven(double x)
Victor Stinner74474232015-09-02 01:43:56 +020099{
Victor Stinner7667f582015-09-09 01:02:23 +0200100 double rounded = round(x);
Victor Stinner277c8402017-10-11 08:11:38 -0700101 if (fabs(x-rounded) == 0.5) {
Victor Stinner7667f582015-09-09 01:02:23 +0200102 /* halfway case: round to even */
103 rounded = 2.0*round(x/2.0);
Victor Stinner277c8402017-10-11 08:11:38 -0700104 }
Victor Stinner7667f582015-09-09 01:02:23 +0200105 return rounded;
Victor Stinner74474232015-09-02 01:43:56 +0200106}
107
Victor Stinner9ae47df2015-09-09 22:28:58 +0200108static double
109_PyTime_Round(double x, _PyTime_round_t round)
110{
Victor Stinner1efbeba2015-09-10 11:48:00 +0200111 /* volatile avoids optimization changing how numbers are rounded */
112 volatile double d;
113
114 d = x;
Victor Stinner277c8402017-10-11 08:11:38 -0700115 if (round == _PyTime_ROUND_HALF_EVEN) {
Victor Stinner1efbeba2015-09-10 11:48:00 +0200116 d = _PyTime_RoundHalfEven(d);
Victor Stinner277c8402017-10-11 08:11:38 -0700117 }
118 else if (round == _PyTime_ROUND_CEILING) {
Victor Stinner1efbeba2015-09-10 11:48:00 +0200119 d = ceil(d);
Victor Stinner277c8402017-10-11 08:11:38 -0700120 }
Pablo Galindo2c15b292017-10-17 15:14:41 +0100121 else if (round == _PyTime_ROUND_FLOOR) {
Victor Stinner1efbeba2015-09-10 11:48:00 +0200122 d = floor(d);
Victor Stinner277c8402017-10-11 08:11:38 -0700123 }
Pablo Galindo2c15b292017-10-17 15:14:41 +0100124 else {
125 assert(round == _PyTime_ROUND_UP);
126 d = (d >= 0.0) ? ceil(d) : floor(d);
127 }
Victor Stinner1efbeba2015-09-10 11:48:00 +0200128 return d;
Victor Stinner9ae47df2015-09-09 22:28:58 +0200129}
130
Victor Stinner5d272cc2012-03-13 13:35:55 +0100131static int
Victor Stinner53e137c2015-09-02 00:49:16 +0200132_PyTime_DoubleToDenominator(double d, time_t *sec, long *numerator,
Victor Stinner277c8402017-10-11 08:11:38 -0700133 long idenominator, _PyTime_round_t round)
Victor Stinner53e137c2015-09-02 00:49:16 +0200134{
Victor Stinner277c8402017-10-11 08:11:38 -0700135 double denominator = (double)idenominator;
Benjamin Petersona853a8b2017-09-07 11:13:59 -0700136 double intpart;
Victor Stinner24b822e2015-09-02 11:58:56 +0200137 /* volatile avoids optimization changing how numbers are rounded */
Victor Stinner53e137c2015-09-02 00:49:16 +0200138 volatile double floatpart;
139
140 floatpart = modf(d, &intpart);
Victor Stinner53e137c2015-09-02 00:49:16 +0200141
142 floatpart *= denominator;
Victor Stinner9ae47df2015-09-09 22:28:58 +0200143 floatpart = _PyTime_Round(floatpart, round);
Victor Stinner67edcc92015-09-02 10:37:46 +0200144 if (floatpart >= denominator) {
145 floatpart -= denominator;
146 intpart += 1.0;
Victor Stinner53e137c2015-09-02 00:49:16 +0200147 }
Victor Stinneradfefa52015-09-04 23:57:25 +0200148 else if (floatpart < 0) {
149 floatpart += denominator;
150 intpart -= 1.0;
151 }
Victor Stinner67edcc92015-09-02 10:37:46 +0200152 assert(0.0 <= floatpart && floatpart < denominator);
Victor Stinner53e137c2015-09-02 00:49:16 +0200153
Benjamin Petersona853a8b2017-09-07 11:13:59 -0700154 if (!_Py_InIntegralTypeRange(time_t, intpart)) {
Victor Stinner53e137c2015-09-02 00:49:16 +0200155 error_time_t_overflow();
156 return -1;
157 }
Benjamin Petersona853a8b2017-09-07 11:13:59 -0700158 *sec = (time_t)intpart;
159 *numerator = (long)floatpart;
Victor Stinner277c8402017-10-11 08:11:38 -0700160 assert(0 <= *numerator && *numerator < idenominator);
Victor Stinner53e137c2015-09-02 00:49:16 +0200161 return 0;
162}
163
164static int
Victor Stinner5d272cc2012-03-13 13:35:55 +0100165_PyTime_ObjectToDenominator(PyObject *obj, time_t *sec, long *numerator,
Victor Stinner277c8402017-10-11 08:11:38 -0700166 long denominator, _PyTime_round_t round)
Victor Stinner5d272cc2012-03-13 13:35:55 +0100167{
Victor Stinner277c8402017-10-11 08:11:38 -0700168 assert(denominator >= 1);
Victor Stinnerbbdda212015-09-02 00:50:43 +0200169
Victor Stinner643cd682012-03-02 22:54:03 +0100170 if (PyFloat_Check(obj)) {
Victor Stinner53e137c2015-09-02 00:49:16 +0200171 double d = PyFloat_AsDouble(obj);
Han Lee829dacc2017-09-09 08:05:05 +0900172 if (Py_IS_NAN(d)) {
173 *numerator = 0;
174 PyErr_SetString(PyExc_ValueError, "Invalid value NaN (not a number)");
175 return -1;
176 }
Victor Stinner53e137c2015-09-02 00:49:16 +0200177 return _PyTime_DoubleToDenominator(d, sec, numerator,
178 denominator, round);
Victor Stinner643cd682012-03-02 22:54:03 +0100179 }
180 else {
Victor Stinner5d272cc2012-03-13 13:35:55 +0100181 *sec = _PyLong_AsTime_t(obj);
Victor Stinner67edcc92015-09-02 10:37:46 +0200182 *numerator = 0;
Victor Stinner277c8402017-10-11 08:11:38 -0700183 if (*sec == (time_t)-1 && PyErr_Occurred()) {
Victor Stinner5d272cc2012-03-13 13:35:55 +0100184 return -1;
Victor Stinner277c8402017-10-11 08:11:38 -0700185 }
Victor Stinner643cd682012-03-02 22:54:03 +0100186 return 0;
187 }
Victor Stinner5d272cc2012-03-13 13:35:55 +0100188}
Victor Stinner643cd682012-03-02 22:54:03 +0100189
Victor Stinner5d272cc2012-03-13 13:35:55 +0100190int
Victor Stinner3c1b3792014-02-17 00:02:43 +0100191_PyTime_ObjectToTime_t(PyObject *obj, time_t *sec, _PyTime_round_t round)
Victor Stinner5d272cc2012-03-13 13:35:55 +0100192{
193 if (PyFloat_Check(obj)) {
Benjamin Petersona853a8b2017-09-07 11:13:59 -0700194 double intpart;
Victor Stinner24b822e2015-09-02 11:58:56 +0200195 /* volatile avoids optimization changing how numbers are rounded */
Victor Stinner5786aef2015-09-03 16:33:16 +0200196 volatile double d;
Victor Stinner5d272cc2012-03-13 13:35:55 +0100197
Victor Stinner5d272cc2012-03-13 13:35:55 +0100198 d = PyFloat_AsDouble(obj);
Han Lee829dacc2017-09-09 08:05:05 +0900199 if (Py_IS_NAN(d)) {
200 PyErr_SetString(PyExc_ValueError, "Invalid value NaN (not a number)");
201 return -1;
202 }
203
Victor Stinner9ae47df2015-09-09 22:28:58 +0200204 d = _PyTime_Round(d, round);
Victor Stinner5d272cc2012-03-13 13:35:55 +0100205 (void)modf(d, &intpart);
206
Benjamin Petersona853a8b2017-09-07 11:13:59 -0700207 if (!_Py_InIntegralTypeRange(time_t, intpart)) {
Victor Stinner5d272cc2012-03-13 13:35:55 +0100208 error_time_t_overflow();
209 return -1;
210 }
Benjamin Petersona853a8b2017-09-07 11:13:59 -0700211 *sec = (time_t)intpart;
Victor Stinner5d272cc2012-03-13 13:35:55 +0100212 return 0;
213 }
214 else {
215 *sec = _PyLong_AsTime_t(obj);
Victor Stinner277c8402017-10-11 08:11:38 -0700216 if (*sec == (time_t)-1 && PyErr_Occurred()) {
Victor Stinner5d272cc2012-03-13 13:35:55 +0100217 return -1;
Victor Stinner277c8402017-10-11 08:11:38 -0700218 }
Victor Stinner5d272cc2012-03-13 13:35:55 +0100219 return 0;
220 }
221}
222
223int
Victor Stinner3c1b3792014-02-17 00:02:43 +0100224_PyTime_ObjectToTimespec(PyObject *obj, time_t *sec, long *nsec,
225 _PyTime_round_t round)
Victor Stinner5d272cc2012-03-13 13:35:55 +0100226{
Victor Stinner277c8402017-10-11 08:11:38 -0700227 return _PyTime_ObjectToDenominator(obj, sec, nsec, SEC_TO_NS, round);
Victor Stinner5d272cc2012-03-13 13:35:55 +0100228}
229
230int
Victor Stinner3c1b3792014-02-17 00:02:43 +0100231_PyTime_ObjectToTimeval(PyObject *obj, time_t *sec, long *usec,
232 _PyTime_round_t round)
Victor Stinner5d272cc2012-03-13 13:35:55 +0100233{
Victor Stinner277c8402017-10-11 08:11:38 -0700234 return _PyTime_ObjectToDenominator(obj, sec, usec, SEC_TO_US, round);
Victor Stinnercb29f012015-03-27 13:31:18 +0100235}
236
Victor Stinner4bfb4602015-03-27 22:27:24 +0100237_PyTime_t
Victor Stinner13019fd2015-04-03 13:10:54 +0200238_PyTime_FromSeconds(int seconds)
239{
240 _PyTime_t t;
241 /* ensure that integer overflow cannot happen, int type should have 32
242 bits, whereas _PyTime_t type has at least 64 bits (SEC_TO_MS takes 30
243 bits). */
Serhiy Storchakafad85aa2015-11-07 15:42:38 +0200244 Py_BUILD_ASSERT(INT_MAX <= _PyTime_MAX / SEC_TO_NS);
245 Py_BUILD_ASSERT(INT_MIN >= _PyTime_MIN / SEC_TO_NS);
Victor Stinner277c8402017-10-11 08:11:38 -0700246
247 t = (_PyTime_t)seconds;
Victor Stinnerbbdda212015-09-02 00:50:43 +0200248 assert((t >= 0 && t <= _PyTime_MAX / SEC_TO_NS)
249 || (t < 0 && t >= _PyTime_MIN / SEC_TO_NS));
250 t *= SEC_TO_NS;
Victor Stinner13019fd2015-04-03 13:10:54 +0200251 return t;
252}
253
254_PyTime_t
Victor Stinnerc29b5852017-11-02 07:28:27 -0700255_PyTime_FromNanoseconds(_PyTime_t ns)
Victor Stinner4bfb4602015-03-27 22:27:24 +0100256{
Victor Stinnerc29b5852017-11-02 07:28:27 -0700257 /* _PyTime_t already uses nanosecond resolution, no conversion needed */
258 return ns;
259}
260
261int
262_PyTime_FromNanosecondsObject(_PyTime_t *tp, PyObject *obj)
263{
264 long long nsec;
Victor Stinner4bfb4602015-03-27 22:27:24 +0100265 _PyTime_t t;
Victor Stinnerc29b5852017-11-02 07:28:27 -0700266
267 if (!PyLong_Check(obj)) {
268 PyErr_Format(PyExc_TypeError, "expect int, got %s",
269 Py_TYPE(obj)->tp_name);
270 return -1;
271 }
272
273 Py_BUILD_ASSERT(sizeof(long long) == sizeof(_PyTime_t));
274 nsec = PyLong_AsLongLong(obj);
275 if (nsec == -1 && PyErr_Occurred()) {
276 if (PyErr_ExceptionMatches(PyExc_OverflowError)) {
277 _PyTime_overflow();
278 }
279 return -1;
280 }
281
282 /* _PyTime_t already uses nanosecond resolution, no conversion needed */
283 t = (_PyTime_t)nsec;
284 *tp = t;
285 return 0;
Victor Stinner4bfb4602015-03-27 22:27:24 +0100286}
287
Victor Stinnera47b8812015-03-27 18:16:17 +0100288#ifdef HAVE_CLOCK_GETTIME
Victor Stinnercb29f012015-03-27 13:31:18 +0100289static int
Victor Stinnerc29b5852017-11-02 07:28:27 -0700290pytime_fromtimespec(_PyTime_t *tp, struct timespec *ts, int raise)
Victor Stinnercb29f012015-03-27 13:31:18 +0100291{
Victor Stinnerc29b5852017-11-02 07:28:27 -0700292 _PyTime_t t, nsec;
Victor Stinnercb0c6022015-03-28 05:24:19 +0100293 int res = 0;
294
Serhiy Storchakafad85aa2015-11-07 15:42:38 +0200295 Py_BUILD_ASSERT(sizeof(ts->tv_sec) <= sizeof(_PyTime_t));
Victor Stinnerc60542b2015-09-10 15:55:07 +0200296 t = (_PyTime_t)ts->tv_sec;
297
298 if (_PyTime_check_mul_overflow(t, SEC_TO_NS)) {
Victor Stinner277c8402017-10-11 08:11:38 -0700299 if (raise) {
Victor Stinnercb0c6022015-03-28 05:24:19 +0100300 _PyTime_overflow();
Victor Stinner277c8402017-10-11 08:11:38 -0700301 }
Victor Stinnercb0c6022015-03-28 05:24:19 +0100302 res = -1;
Victor Stinnerc29b5852017-11-02 07:28:27 -0700303 t = (t > 0) ? _PyTime_MAX : _PyTime_MIN;
Victor Stinnercb29f012015-03-27 13:31:18 +0100304 }
Victor Stinnerc29b5852017-11-02 07:28:27 -0700305 else {
306 t = t * SEC_TO_NS;
307 }
Victor Stinnercb29f012015-03-27 13:31:18 +0100308
Victor Stinnerc29b5852017-11-02 07:28:27 -0700309 nsec = ts->tv_nsec;
310 /* The following test is written for positive only nsec */
311 assert(nsec >= 0);
312 if (t > _PyTime_MAX - nsec) {
313 if (raise) {
314 _PyTime_overflow();
315 }
316 res = -1;
317 t = _PyTime_MAX;
318 }
319 else {
320 t += nsec;
321 }
Victor Stinnercb29f012015-03-27 13:31:18 +0100322
323 *tp = t;
Victor Stinnercb0c6022015-03-28 05:24:19 +0100324 return res;
Victor Stinnercb29f012015-03-27 13:31:18 +0100325}
Victor Stinnerc29b5852017-11-02 07:28:27 -0700326
327int
328_PyTime_FromTimespec(_PyTime_t *tp, struct timespec *ts)
Victor Stinnera47b8812015-03-27 18:16:17 +0100329{
Victor Stinnerc29b5852017-11-02 07:28:27 -0700330 return pytime_fromtimespec(tp, ts, 1);
331}
332#endif
333
334#if !defined(MS_WINDOWS)
335static int
336pytime_fromtimeval(_PyTime_t *tp, struct timeval *tv, int raise)
337{
338 _PyTime_t t, usec;
Victor Stinnercb0c6022015-03-28 05:24:19 +0100339 int res = 0;
Victor Stinnera47b8812015-03-27 18:16:17 +0100340
Serhiy Storchakafad85aa2015-11-07 15:42:38 +0200341 Py_BUILD_ASSERT(sizeof(tv->tv_sec) <= sizeof(_PyTime_t));
Victor Stinnerc60542b2015-09-10 15:55:07 +0200342 t = (_PyTime_t)tv->tv_sec;
343
344 if (_PyTime_check_mul_overflow(t, SEC_TO_NS)) {
Victor Stinner277c8402017-10-11 08:11:38 -0700345 if (raise) {
Victor Stinnercb0c6022015-03-28 05:24:19 +0100346 _PyTime_overflow();
Victor Stinner277c8402017-10-11 08:11:38 -0700347 }
Victor Stinnercb0c6022015-03-28 05:24:19 +0100348 res = -1;
Victor Stinnerc29b5852017-11-02 07:28:27 -0700349 t = (t > 0) ? _PyTime_MAX : _PyTime_MIN;
Victor Stinnera47b8812015-03-27 18:16:17 +0100350 }
Victor Stinnerc29b5852017-11-02 07:28:27 -0700351 else {
352 t = t * SEC_TO_NS;
353 }
Victor Stinnera47b8812015-03-27 18:16:17 +0100354
Victor Stinnerc29b5852017-11-02 07:28:27 -0700355 usec = (_PyTime_t)tv->tv_usec * US_TO_NS;
356 /* The following test is written for positive only usec */
357 assert(usec >= 0);
358 if (t > _PyTime_MAX - usec) {
359 if (raise) {
360 _PyTime_overflow();
361 }
362 res = -1;
363 t = _PyTime_MAX;
364 }
365 else {
366 t += usec;
367 }
Victor Stinnera47b8812015-03-27 18:16:17 +0100368
369 *tp = t;
Victor Stinnercb0c6022015-03-28 05:24:19 +0100370 return res;
Victor Stinnera47b8812015-03-27 18:16:17 +0100371}
Victor Stinnerc29b5852017-11-02 07:28:27 -0700372
373int
374_PyTime_FromTimeval(_PyTime_t *tp, struct timeval *tv)
375{
376 return pytime_fromtimeval(tp, tv, 1);
377}
Victor Stinnercb29f012015-03-27 13:31:18 +0100378#endif
379
Victor Stinnerfa09beb2015-03-30 21:36:10 +0200380static int
Victor Stinnera997c7b2017-10-10 02:51:50 -0700381_PyTime_FromDouble(_PyTime_t *t, double value, _PyTime_round_t round,
382 long unit_to_ns)
Victor Stinner53e137c2015-09-02 00:49:16 +0200383{
Victor Stinner24b822e2015-09-02 11:58:56 +0200384 /* volatile avoids optimization changing how numbers are rounded */
Victor Stinner5786aef2015-09-03 16:33:16 +0200385 volatile double d;
Victor Stinner53e137c2015-09-02 00:49:16 +0200386
387 /* convert to a number of nanoseconds */
388 d = value;
Victor Stinner9ae47df2015-09-09 22:28:58 +0200389 d *= (double)unit_to_ns;
390 d = _PyTime_Round(d, round);
Victor Stinner53e137c2015-09-02 00:49:16 +0200391
Benjamin Petersona853a8b2017-09-07 11:13:59 -0700392 if (!_Py_InIntegralTypeRange(_PyTime_t, d)) {
Victor Stinner53e137c2015-09-02 00:49:16 +0200393 _PyTime_overflow();
394 return -1;
395 }
Benjamin Petersona853a8b2017-09-07 11:13:59 -0700396 *t = (_PyTime_t)d;
Victor Stinner53e137c2015-09-02 00:49:16 +0200397 return 0;
398}
399
400static int
Victor Stinnerfa09beb2015-03-30 21:36:10 +0200401_PyTime_FromObject(_PyTime_t *t, PyObject *obj, _PyTime_round_t round,
Victor Stinner9ae47df2015-09-09 22:28:58 +0200402 long unit_to_ns)
Victor Stinnercb29f012015-03-27 13:31:18 +0100403{
404 if (PyFloat_Check(obj)) {
Victor Stinner53e137c2015-09-02 00:49:16 +0200405 double d;
Victor Stinnercb29f012015-03-27 13:31:18 +0100406 d = PyFloat_AsDouble(obj);
Han Lee829dacc2017-09-09 08:05:05 +0900407 if (Py_IS_NAN(d)) {
408 PyErr_SetString(PyExc_ValueError, "Invalid value NaN (not a number)");
409 return -1;
410 }
Victor Stinnera997c7b2017-10-10 02:51:50 -0700411 return _PyTime_FromDouble(t, d, round, unit_to_ns);
Victor Stinnercb29f012015-03-27 13:31:18 +0100412 }
413 else {
Benjamin Petersonaf580df2016-09-06 10:46:49 -0700414 long long sec;
415 Py_BUILD_ASSERT(sizeof(long long) <= sizeof(_PyTime_t));
Victor Stinner9c72f9b2015-09-10 09:10:14 +0200416
417 sec = PyLong_AsLongLong(obj);
Victor Stinnercb29f012015-03-27 13:31:18 +0100418 if (sec == -1 && PyErr_Occurred()) {
Victor Stinner277c8402017-10-11 08:11:38 -0700419 if (PyErr_ExceptionMatches(PyExc_OverflowError)) {
Victor Stinnercb29f012015-03-27 13:31:18 +0100420 _PyTime_overflow();
Victor Stinner277c8402017-10-11 08:11:38 -0700421 }
Victor Stinnercb29f012015-03-27 13:31:18 +0100422 return -1;
423 }
Victor Stinner9c72f9b2015-09-10 09:10:14 +0200424
Victor Stinnerc60542b2015-09-10 15:55:07 +0200425 if (_PyTime_check_mul_overflow(sec, unit_to_ns)) {
Victor Stinnercb29f012015-03-27 13:31:18 +0100426 _PyTime_overflow();
427 return -1;
428 }
Victor Stinnerc60542b2015-09-10 15:55:07 +0200429 *t = sec * unit_to_ns;
Victor Stinnercb29f012015-03-27 13:31:18 +0100430 return 0;
431 }
432}
433
Victor Stinnerfa09beb2015-03-30 21:36:10 +0200434int
435_PyTime_FromSecondsObject(_PyTime_t *t, PyObject *obj, _PyTime_round_t round)
436{
437 return _PyTime_FromObject(t, obj, round, SEC_TO_NS);
438}
439
440int
441_PyTime_FromMillisecondsObject(_PyTime_t *t, PyObject *obj, _PyTime_round_t round)
442{
443 return _PyTime_FromObject(t, obj, round, MS_TO_NS);
444}
445
Victor Stinner4bfb4602015-03-27 22:27:24 +0100446double
447_PyTime_AsSecondsDouble(_PyTime_t t)
448{
Victor Stinnerff0ed3e2015-09-10 13:25:17 +0200449 /* volatile avoids optimization changing how numbers are rounded */
450 volatile double d;
451
Victor Stinner3e2c8d82015-09-09 22:32:48 +0200452 if (t % SEC_TO_NS == 0) {
453 _PyTime_t secs;
454 /* Divide using integers to avoid rounding issues on the integer part.
455 1e-9 cannot be stored exactly in IEEE 64-bit. */
456 secs = t / SEC_TO_NS;
Victor Stinnerff0ed3e2015-09-10 13:25:17 +0200457 d = (double)secs;
Victor Stinner3e2c8d82015-09-09 22:32:48 +0200458 }
459 else {
Victor Stinnerff0ed3e2015-09-10 13:25:17 +0200460 d = (double)t;
461 d /= 1e9;
Victor Stinner3e2c8d82015-09-09 22:32:48 +0200462 }
Victor Stinnerff0ed3e2015-09-10 13:25:17 +0200463 return d;
Victor Stinner4bfb4602015-03-27 22:27:24 +0100464}
465
Victor Stinner992c43f2015-03-27 17:12:45 +0100466PyObject *
467_PyTime_AsNanosecondsObject(_PyTime_t t)
468{
Benjamin Petersonaf580df2016-09-06 10:46:49 -0700469 Py_BUILD_ASSERT(sizeof(long long) >= sizeof(_PyTime_t));
470 return PyLong_FromLongLong((long long)t);
Victor Stinner992c43f2015-03-27 17:12:45 +0100471}
472
Victor Stinnercb29f012015-03-27 13:31:18 +0100473static _PyTime_t
Victor Stinner7667f582015-09-09 01:02:23 +0200474_PyTime_Divide(const _PyTime_t t, const _PyTime_t k,
475 const _PyTime_round_t round)
Victor Stinnercb29f012015-03-27 13:31:18 +0100476{
Victor Stinner62d1c702015-04-01 17:47:07 +0200477 assert(k > 1);
Victor Stinner7667f582015-09-09 01:02:23 +0200478 if (round == _PyTime_ROUND_HALF_EVEN) {
479 _PyTime_t x, r, abs_r;
Victor Stinner74474232015-09-02 01:43:56 +0200480 x = t / k;
481 r = t % k;
Victor Stinner7667f582015-09-09 01:02:23 +0200482 abs_r = Py_ABS(r);
483 if (abs_r > k / 2 || (abs_r == k / 2 && (Py_ABS(x) & 1))) {
Victor Stinner277c8402017-10-11 08:11:38 -0700484 if (t >= 0) {
Victor Stinner74474232015-09-02 01:43:56 +0200485 x++;
Victor Stinner277c8402017-10-11 08:11:38 -0700486 }
487 else {
Victor Stinner74474232015-09-02 01:43:56 +0200488 x--;
Victor Stinner277c8402017-10-11 08:11:38 -0700489 }
Victor Stinner74474232015-09-02 01:43:56 +0200490 }
491 return x;
492 }
493 else if (round == _PyTime_ROUND_CEILING) {
Victor Stinner277c8402017-10-11 08:11:38 -0700494 if (t >= 0) {
Victor Stinnercb29f012015-03-27 13:31:18 +0100495 return (t + k - 1) / k;
Victor Stinner277c8402017-10-11 08:11:38 -0700496 }
497 else {
Victor Stinner7667f582015-09-09 01:02:23 +0200498 return t / k;
Victor Stinner277c8402017-10-11 08:11:38 -0700499 }
Victor Stinner7667f582015-09-09 01:02:23 +0200500 }
Pablo Galindo2c15b292017-10-17 15:14:41 +0100501 else if (round == _PyTime_ROUND_FLOOR){
Victor Stinner277c8402017-10-11 08:11:38 -0700502 if (t >= 0) {
Victor Stinner7667f582015-09-09 01:02:23 +0200503 return t / k;
Victor Stinner277c8402017-10-11 08:11:38 -0700504 }
505 else {
Victor Stinner62d1c702015-04-01 17:47:07 +0200506 return (t - (k - 1)) / k;
Victor Stinner277c8402017-10-11 08:11:38 -0700507 }
Victor Stinnercb29f012015-03-27 13:31:18 +0100508 }
Pablo Galindo2c15b292017-10-17 15:14:41 +0100509 else {
510 assert(round == _PyTime_ROUND_UP);
511 if (t >= 0) {
512 return (t + k - 1) / k;
513 }
514 else {
515 return (t - (k - 1)) / k;
516 }
517 }
Victor Stinnercb29f012015-03-27 13:31:18 +0100518}
519
520_PyTime_t
521_PyTime_AsMilliseconds(_PyTime_t t, _PyTime_round_t round)
522{
Victor Stinner62d1c702015-04-01 17:47:07 +0200523 return _PyTime_Divide(t, NS_TO_MS, round);
Victor Stinnercb29f012015-03-27 13:31:18 +0100524}
525
Victor Stinnerf5faad22015-03-28 03:52:05 +0100526_PyTime_t
527_PyTime_AsMicroseconds(_PyTime_t t, _PyTime_round_t round)
528{
Victor Stinner62d1c702015-04-01 17:47:07 +0200529 return _PyTime_Divide(t, NS_TO_US, round);
Victor Stinnerf5faad22015-03-28 03:52:05 +0100530}
531
Victor Stinnerea9c0dd2015-03-30 02:51:13 +0200532static int
Victor Stinner1e2b6882015-09-18 13:23:02 +0200533_PyTime_AsTimeval_impl(_PyTime_t t, _PyTime_t *p_secs, int *p_us,
534 _PyTime_round_t round)
Victor Stinnercb29f012015-03-27 13:31:18 +0100535{
536 _PyTime_t secs, ns;
Victor Stinner74474232015-09-02 01:43:56 +0200537 int usec;
Victor Stinner1e2b6882015-09-18 13:23:02 +0200538 int res = 0;
Victor Stinnercb29f012015-03-27 13:31:18 +0100539
540 secs = t / SEC_TO_NS;
541 ns = t % SEC_TO_NS;
542
Victor Stinner1e2b6882015-09-18 13:23:02 +0200543 usec = (int)_PyTime_Divide(ns, US_TO_NS, round);
544 if (usec < 0) {
545 usec += SEC_TO_US;
Victor Stinner277c8402017-10-11 08:11:38 -0700546 if (secs != _PyTime_MIN) {
Victor Stinner1e2b6882015-09-18 13:23:02 +0200547 secs -= 1;
Victor Stinner277c8402017-10-11 08:11:38 -0700548 }
549 else {
Victor Stinner1e2b6882015-09-18 13:23:02 +0200550 res = -1;
Victor Stinner277c8402017-10-11 08:11:38 -0700551 }
Victor Stinner1e2b6882015-09-18 13:23:02 +0200552 }
553 else if (usec >= SEC_TO_US) {
554 usec -= SEC_TO_US;
Victor Stinner277c8402017-10-11 08:11:38 -0700555 if (secs != _PyTime_MAX) {
Victor Stinner1e2b6882015-09-18 13:23:02 +0200556 secs += 1;
Victor Stinner277c8402017-10-11 08:11:38 -0700557 }
558 else {
Victor Stinner1e2b6882015-09-18 13:23:02 +0200559 res = -1;
Victor Stinner277c8402017-10-11 08:11:38 -0700560 }
Victor Stinner1e2b6882015-09-18 13:23:02 +0200561 }
562 assert(0 <= usec && usec < SEC_TO_US);
563
564 *p_secs = secs;
565 *p_us = usec;
566
567 return res;
568}
569
570static int
571_PyTime_AsTimevalStruct_impl(_PyTime_t t, struct timeval *tv,
572 _PyTime_round_t round, int raise)
573{
Victor Stinnerb7a8af22015-10-01 08:44:03 +0200574 _PyTime_t secs, secs2;
Victor Stinner1e2b6882015-09-18 13:23:02 +0200575 int us;
576 int res;
577
578 res = _PyTime_AsTimeval_impl(t, &secs, &us, round);
579
Victor Stinnercb29f012015-03-27 13:31:18 +0100580#ifdef MS_WINDOWS
Victor Stinnercb29f012015-03-27 13:31:18 +0100581 tv->tv_sec = (long)secs;
582#else
Victor Stinnercb29f012015-03-27 13:31:18 +0100583 tv->tv_sec = secs;
Victor Stinner9c72f9b2015-09-10 09:10:14 +0200584#endif
Victor Stinner1e2b6882015-09-18 13:23:02 +0200585 tv->tv_usec = us;
Victor Stinnercb29f012015-03-27 13:31:18 +0100586
Victor Stinnerb7a8af22015-10-01 08:44:03 +0200587 secs2 = (_PyTime_t)tv->tv_sec;
588 if (res < 0 || secs2 != secs) {
Victor Stinner277c8402017-10-11 08:11:38 -0700589 if (raise) {
Victor Stinner1e2b6882015-09-18 13:23:02 +0200590 error_time_t_overflow();
Victor Stinner277c8402017-10-11 08:11:38 -0700591 }
Victor Stinner1e2b6882015-09-18 13:23:02 +0200592 return -1;
Victor Stinner74474232015-09-02 01:43:56 +0200593 }
Victor Stinner1e2b6882015-09-18 13:23:02 +0200594 return 0;
Victor Stinnercb29f012015-03-27 13:31:18 +0100595}
596
Victor Stinnerea9c0dd2015-03-30 02:51:13 +0200597int
598_PyTime_AsTimeval(_PyTime_t t, struct timeval *tv, _PyTime_round_t round)
599{
Victor Stinner1e2b6882015-09-18 13:23:02 +0200600 return _PyTime_AsTimevalStruct_impl(t, tv, round, 1);
Victor Stinnerea9c0dd2015-03-30 02:51:13 +0200601}
602
603int
604_PyTime_AsTimeval_noraise(_PyTime_t t, struct timeval *tv, _PyTime_round_t round)
605{
Victor Stinner1e2b6882015-09-18 13:23:02 +0200606 return _PyTime_AsTimevalStruct_impl(t, tv, round, 0);
Victor Stinnerea9c0dd2015-03-30 02:51:13 +0200607}
608
Victor Stinner1e2b6882015-09-18 13:23:02 +0200609int
610_PyTime_AsTimevalTime_t(_PyTime_t t, time_t *p_secs, int *us,
611 _PyTime_round_t round)
612{
613 _PyTime_t secs;
614 int res;
615
616 res = _PyTime_AsTimeval_impl(t, &secs, us, round);
617
618 *p_secs = secs;
619
620 if (res < 0 || (_PyTime_t)*p_secs != secs) {
621 error_time_t_overflow();
622 return -1;
623 }
624 return 0;
625}
626
627
Victor Stinnerc3378382015-03-28 05:07:51 +0100628#if defined(HAVE_CLOCK_GETTIME) || defined(HAVE_KQUEUE)
Victor Stinner34dc0f42015-03-27 18:19:03 +0100629int
630_PyTime_AsTimespec(_PyTime_t t, struct timespec *ts)
631{
Victor Stinner95e9cef2015-03-28 01:26:47 +0100632 _PyTime_t secs, nsec;
633
634 secs = t / SEC_TO_NS;
Victor Stinner34dc0f42015-03-27 18:19:03 +0100635 nsec = t % SEC_TO_NS;
636 if (nsec < 0) {
637 nsec += SEC_TO_NS;
Victor Stinner95e9cef2015-03-28 01:26:47 +0100638 secs -= 1;
Victor Stinner34dc0f42015-03-27 18:19:03 +0100639 }
Victor Stinner95e9cef2015-03-28 01:26:47 +0100640 ts->tv_sec = (time_t)secs;
Victor Stinner29ee6742015-09-03 16:25:45 +0200641 assert(0 <= nsec && nsec < SEC_TO_NS);
642 ts->tv_nsec = nsec;
643
Victor Stinner95e9cef2015-03-28 01:26:47 +0100644 if ((_PyTime_t)ts->tv_sec != secs) {
Victor Stinner9c72f9b2015-09-10 09:10:14 +0200645 error_time_t_overflow();
Victor Stinner34dc0f42015-03-27 18:19:03 +0100646 return -1;
647 }
Victor Stinner34dc0f42015-03-27 18:19:03 +0100648 return 0;
649}
650#endif
651
Victor Stinnercb29f012015-03-27 13:31:18 +0100652static int
Victor Stinnerc379ade2015-11-10 12:11:39 +0100653pygettimeofday(_PyTime_t *tp, _Py_clock_info_t *info, int raise)
Victor Stinnera47b8812015-03-27 18:16:17 +0100654{
655#ifdef MS_WINDOWS
656 FILETIME system_time;
657 ULARGE_INTEGER large;
658
659 assert(info == NULL || raise);
660
661 GetSystemTimeAsFileTime(&system_time);
662 large.u.LowPart = system_time.dwLowDateTime;
663 large.u.HighPart = system_time.dwHighDateTime;
664 /* 11,644,473,600,000,000,000: number of nanoseconds between
665 the 1st january 1601 and the 1st january 1970 (369 years + 89 leap
666 days). */
667 *tp = large.QuadPart * 100 - 11644473600000000000;
668 if (info) {
669 DWORD timeAdjustment, timeIncrement;
670 BOOL isTimeAdjustmentDisabled, ok;
671
672 info->implementation = "GetSystemTimeAsFileTime()";
673 info->monotonic = 0;
674 ok = GetSystemTimeAdjustment(&timeAdjustment, &timeIncrement,
675 &isTimeAdjustmentDisabled);
676 if (!ok) {
677 PyErr_SetFromWindowsErr(0);
678 return -1;
679 }
680 info->resolution = timeIncrement * 1e-7;
681 info->adjustable = 1;
682 }
683
684#else /* MS_WINDOWS */
685 int err;
686#ifdef HAVE_CLOCK_GETTIME
687 struct timespec ts;
688#else
689 struct timeval tv;
690#endif
691
692 assert(info == NULL || raise);
693
694#ifdef HAVE_CLOCK_GETTIME
695 err = clock_gettime(CLOCK_REALTIME, &ts);
696 if (err) {
Victor Stinner277c8402017-10-11 08:11:38 -0700697 if (raise) {
Victor Stinnera47b8812015-03-27 18:16:17 +0100698 PyErr_SetFromErrno(PyExc_OSError);
Victor Stinner277c8402017-10-11 08:11:38 -0700699 }
Victor Stinnera47b8812015-03-27 18:16:17 +0100700 return -1;
701 }
Victor Stinnerc29b5852017-11-02 07:28:27 -0700702 if (pytime_fromtimespec(tp, &ts, raise) < 0) {
Victor Stinnera47b8812015-03-27 18:16:17 +0100703 return -1;
Victor Stinner277c8402017-10-11 08:11:38 -0700704 }
Victor Stinnera47b8812015-03-27 18:16:17 +0100705
706 if (info) {
707 struct timespec res;
708 info->implementation = "clock_gettime(CLOCK_REALTIME)";
709 info->monotonic = 0;
710 info->adjustable = 1;
Victor Stinner277c8402017-10-11 08:11:38 -0700711 if (clock_getres(CLOCK_REALTIME, &res) == 0) {
Victor Stinnera47b8812015-03-27 18:16:17 +0100712 info->resolution = res.tv_sec + res.tv_nsec * 1e-9;
Victor Stinner277c8402017-10-11 08:11:38 -0700713 }
714 else {
Victor Stinnera47b8812015-03-27 18:16:17 +0100715 info->resolution = 1e-9;
Victor Stinner277c8402017-10-11 08:11:38 -0700716 }
Victor Stinnera47b8812015-03-27 18:16:17 +0100717 }
718#else /* HAVE_CLOCK_GETTIME */
719
720 /* test gettimeofday() */
Victor Stinnera47b8812015-03-27 18:16:17 +0100721 err = gettimeofday(&tv, (struct timezone *)NULL);
Victor Stinnera47b8812015-03-27 18:16:17 +0100722 if (err) {
Victor Stinner277c8402017-10-11 08:11:38 -0700723 if (raise) {
Victor Stinnera47b8812015-03-27 18:16:17 +0100724 PyErr_SetFromErrno(PyExc_OSError);
Victor Stinner277c8402017-10-11 08:11:38 -0700725 }
Victor Stinnera47b8812015-03-27 18:16:17 +0100726 return -1;
727 }
Victor Stinnerc29b5852017-11-02 07:28:27 -0700728 if (pytime_fromtimeval(tp, &tv, raise) < 0) {
Victor Stinnera47b8812015-03-27 18:16:17 +0100729 return -1;
Victor Stinner277c8402017-10-11 08:11:38 -0700730 }
Victor Stinnera47b8812015-03-27 18:16:17 +0100731
732 if (info) {
733 info->implementation = "gettimeofday()";
734 info->resolution = 1e-6;
735 info->monotonic = 0;
736 info->adjustable = 1;
737 }
738#endif /* !HAVE_CLOCK_GETTIME */
739#endif /* !MS_WINDOWS */
740 return 0;
741}
742
Victor Stinner09e5cf22015-03-30 00:09:18 +0200743_PyTime_t
744_PyTime_GetSystemClock(void)
745{
746 _PyTime_t t;
Victor Stinnerc379ade2015-11-10 12:11:39 +0100747 if (pygettimeofday(&t, NULL, 0) < 0) {
Victor Stinner09e5cf22015-03-30 00:09:18 +0200748 /* should not happen, _PyTime_Init() checked the clock at startup */
Serhiy Storchakaeebaa9b2020-03-09 20:49:52 +0200749 Py_FatalError("pygettimeofday() failed");
Victor Stinner09e5cf22015-03-30 00:09:18 +0200750 }
751 return t;
752}
753
Victor Stinnera47b8812015-03-27 18:16:17 +0100754int
755_PyTime_GetSystemClockWithInfo(_PyTime_t *t, _Py_clock_info_t *info)
756{
Victor Stinnerc379ade2015-11-10 12:11:39 +0100757 return pygettimeofday(t, info, 1);
Victor Stinnera47b8812015-03-27 18:16:17 +0100758}
759
Victor Stinnera47b8812015-03-27 18:16:17 +0100760static int
Victor Stinner5ad58212015-09-03 00:14:58 +0200761pymonotonic(_PyTime_t *tp, _Py_clock_info_t *info, int raise)
Victor Stinnercb29f012015-03-27 13:31:18 +0100762{
Victor Stinnercb29f012015-03-27 13:31:18 +0100763#if defined(MS_WINDOWS)
Victor Stinnerc60542b2015-09-10 15:55:07 +0200764 ULONGLONG ticks;
765 _PyTime_t t;
Victor Stinnercb29f012015-03-27 13:31:18 +0100766
767 assert(info == NULL || raise);
768
Victor Stinnerc60542b2015-09-10 15:55:07 +0200769 ticks = GetTickCount64();
Serhiy Storchakafad85aa2015-11-07 15:42:38 +0200770 Py_BUILD_ASSERT(sizeof(ticks) <= sizeof(_PyTime_t));
Victor Stinnerc60542b2015-09-10 15:55:07 +0200771 t = (_PyTime_t)ticks;
Victor Stinnercb29f012015-03-27 13:31:18 +0100772
Victor Stinnerc60542b2015-09-10 15:55:07 +0200773 if (_PyTime_check_mul_overflow(t, MS_TO_NS)) {
Victor Stinnercb29f012015-03-27 13:31:18 +0100774 if (raise) {
775 _PyTime_overflow();
776 return -1;
777 }
778 /* Hello, time traveler! */
Serhiy Storchakaeebaa9b2020-03-09 20:49:52 +0200779 Py_FatalError("pymonotonic: integer overflow");
Victor Stinnercb29f012015-03-27 13:31:18 +0100780 }
Victor Stinnerc60542b2015-09-10 15:55:07 +0200781 *tp = t * MS_TO_NS;
Victor Stinnercb29f012015-03-27 13:31:18 +0100782
783 if (info) {
784 DWORD timeAdjustment, timeIncrement;
785 BOOL isTimeAdjustmentDisabled, ok;
Victor Stinnereb352292015-03-27 14:12:08 +0100786 info->implementation = "GetTickCount64()";
Victor Stinnercb29f012015-03-27 13:31:18 +0100787 info->monotonic = 1;
788 ok = GetSystemTimeAdjustment(&timeAdjustment, &timeIncrement,
789 &isTimeAdjustmentDisabled);
790 if (!ok) {
791 PyErr_SetFromWindowsErr(0);
792 return -1;
793 }
794 info->resolution = timeIncrement * 1e-7;
795 info->adjustable = 0;
796 }
797
798#elif defined(__APPLE__)
799 static mach_timebase_info_data_t timebase;
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -0700800 static uint64_t t0 = 0;
801 uint64_t ticks;
Victor Stinnercb29f012015-03-27 13:31:18 +0100802
803 if (timebase.denom == 0) {
804 /* According to the Technical Q&A QA1398, mach_timebase_info() cannot
805 fail: https://developer.apple.com/library/mac/#qa/qa1398/ */
806 (void)mach_timebase_info(&timebase);
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -0700807
808 /* Sanity check: should never occur in practice */
809 if (timebase.numer < 1 || timebase.denom < 1) {
810 PyErr_SetString(PyExc_RuntimeError,
811 "invalid mach_timebase_info");
812 return -1;
813 }
814
815 /* Check that timebase.numer and timebase.denom can be casted to
luzpaza5293b42017-11-05 07:37:50 -0600816 _PyTime_t. In practice, timebase uses uint32_t, so casting cannot
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -0700817 overflow. At the end, only make sure that the type is uint32_t
818 (_PyTime_t is 64-bit long). */
819 assert(sizeof(timebase.numer) < sizeof(_PyTime_t));
820 assert(sizeof(timebase.denom) < sizeof(_PyTime_t));
821
822 /* Make sure that (ticks * timebase.numer) cannot overflow in
823 _PyTime_MulDiv(), with ticks < timebase.denom.
824
825 Known time bases:
826
827 * always (1, 1) on Intel
828 * (1000000000, 33333335) or (1000000000, 25000000) on PowerPC
829
830 None of these time bases can overflow with 64-bit _PyTime_t, but
831 check for overflow, just in case. */
832 if ((_PyTime_t)timebase.numer > _PyTime_MAX / (_PyTime_t)timebase.denom) {
833 PyErr_SetString(PyExc_OverflowError,
834 "mach_timebase_info is too large");
835 return -1;
836 }
837
838 t0 = mach_absolute_time();
Victor Stinnercb29f012015-03-27 13:31:18 +0100839 }
840
Victor Stinnercb29f012015-03-27 13:31:18 +0100841 if (info) {
842 info->implementation = "mach_absolute_time()";
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -0700843 info->resolution = (double)timebase.numer / (double)timebase.denom * 1e-9;
Victor Stinnercb29f012015-03-27 13:31:18 +0100844 info->monotonic = 1;
845 info->adjustable = 0;
846 }
847
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -0700848 ticks = mach_absolute_time();
849 /* Use a "time zero" to reduce precision loss when converting time
850 to floatting point number, as in time.monotonic(). */
851 ticks -= t0;
852 *tp = _PyTime_MulDiv(ticks,
853 (_PyTime_t)timebase.numer,
854 (_PyTime_t)timebase.denom);
855
haneyc90e9602017-06-21 11:18:21 -0700856#elif defined(__hpux)
857 hrtime_t time;
858
859 time = gethrtime();
860 if (time == -1) {
861 if (raise) {
862 PyErr_SetFromErrno(PyExc_OSError);
863 }
864 return -1;
865 }
866
867 *tp = time;
868
869 if (info) {
870 info->implementation = "gethrtime()";
871 info->resolution = 1e-9;
872 info->monotonic = 1;
873 info->adjustable = 0;
874 }
875
Victor Stinnercb29f012015-03-27 13:31:18 +0100876#else
877 struct timespec ts;
878#ifdef CLOCK_HIGHRES
879 const clockid_t clk_id = CLOCK_HIGHRES;
880 const char *implementation = "clock_gettime(CLOCK_HIGHRES)";
881#else
882 const clockid_t clk_id = CLOCK_MONOTONIC;
883 const char *implementation = "clock_gettime(CLOCK_MONOTONIC)";
884#endif
885
886 assert(info == NULL || raise);
887
888 if (clock_gettime(clk_id, &ts) != 0) {
889 if (raise) {
890 PyErr_SetFromErrno(PyExc_OSError);
891 return -1;
892 }
893 return -1;
894 }
895
896 if (info) {
897 struct timespec res;
898 info->monotonic = 1;
899 info->implementation = implementation;
900 info->adjustable = 0;
901 if (clock_getres(clk_id, &res) != 0) {
902 PyErr_SetFromErrno(PyExc_OSError);
903 return -1;
904 }
905 info->resolution = res.tv_sec + res.tv_nsec * 1e-9;
906 }
Victor Stinnerc29b5852017-11-02 07:28:27 -0700907 if (pytime_fromtimespec(tp, &ts, raise) < 0) {
Victor Stinnercb29f012015-03-27 13:31:18 +0100908 return -1;
Victor Stinner277c8402017-10-11 08:11:38 -0700909 }
Victor Stinnercb29f012015-03-27 13:31:18 +0100910#endif
Victor Stinnercb29f012015-03-27 13:31:18 +0100911 return 0;
912}
913
914_PyTime_t
915_PyTime_GetMonotonicClock(void)
916{
917 _PyTime_t t;
Victor Stinner5ad58212015-09-03 00:14:58 +0200918 if (pymonotonic(&t, NULL, 0) < 0) {
Victor Stinnercb0c6022015-03-28 05:24:19 +0100919 /* should not happen, _PyTime_Init() checked that monotonic clock at
920 startup */
Serhiy Storchakaeebaa9b2020-03-09 20:49:52 +0200921 Py_FatalError("pymonotonic() failed");
Victor Stinnercb29f012015-03-27 13:31:18 +0100922 }
923 return t;
924}
925
Victor Stinner00111242014-08-29 16:31:59 +0200926int
Victor Stinner4bfb4602015-03-27 22:27:24 +0100927_PyTime_GetMonotonicClockWithInfo(_PyTime_t *tp, _Py_clock_info_t *info)
928{
Victor Stinner5ad58212015-09-03 00:14:58 +0200929 return pymonotonic(tp, info, 1);
Victor Stinner4bfb4602015-03-27 22:27:24 +0100930}
931
Victor Stinnera997c7b2017-10-10 02:51:50 -0700932
933#ifdef MS_WINDOWS
Victor Stinnercba9a0c2017-10-12 08:51:56 -0700934static int
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -0700935win_perf_counter(_PyTime_t *tp, _Py_clock_info_t *info)
Victor Stinnera997c7b2017-10-10 02:51:50 -0700936{
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -0700937 static LONGLONG frequency = 0;
938 static LONGLONG t0 = 0;
Victor Stinnera997c7b2017-10-10 02:51:50 -0700939 LARGE_INTEGER now;
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -0700940 LONGLONG ticksll;
941 _PyTime_t ticks;
Victor Stinnera997c7b2017-10-10 02:51:50 -0700942
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -0700943 if (frequency == 0) {
Victor Stinnera997c7b2017-10-10 02:51:50 -0700944 LARGE_INTEGER freq;
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -0700945 if (!QueryPerformanceFrequency(&freq)) {
Victor Stinnera997c7b2017-10-10 02:51:50 -0700946 PyErr_SetFromWindowsErr(0);
947 return -1;
948 }
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -0700949 frequency = freq.QuadPart;
950
951 /* Sanity check: should never occur in practice */
952 if (frequency < 1) {
953 PyErr_SetString(PyExc_RuntimeError,
954 "invalid QueryPerformanceFrequency");
955 return -1;
956 }
957
958 /* Check that frequency can be casted to _PyTime_t.
959
960 Make also sure that (ticks * SEC_TO_NS) cannot overflow in
961 _PyTime_MulDiv(), with ticks < frequency.
962
963 Known QueryPerformanceFrequency() values:
964
965 * 10,000,000 (10 MHz): 100 ns resolution
966 * 3,579,545 Hz (3.6 MHz): 279 ns resolution
967
968 None of these frequencies can overflow with 64-bit _PyTime_t, but
969 check for overflow, just in case. */
970 if (frequency > _PyTime_MAX
971 || frequency > (LONGLONG)_PyTime_MAX / (LONGLONG)SEC_TO_NS) {
972 PyErr_SetString(PyExc_OverflowError,
973 "QueryPerformanceFrequency is too large");
974 return -1;
975 }
976
977 QueryPerformanceCounter(&now);
978 t0 = now.QuadPart;
Victor Stinnera997c7b2017-10-10 02:51:50 -0700979 }
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -0700980
Victor Stinnera997c7b2017-10-10 02:51:50 -0700981 if (info) {
982 info->implementation = "QueryPerformanceCounter()";
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -0700983 info->resolution = 1.0 / (double)frequency;
Victor Stinnera997c7b2017-10-10 02:51:50 -0700984 info->monotonic = 1;
985 info->adjustable = 0;
986 }
987
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -0700988 QueryPerformanceCounter(&now);
989 ticksll = now.QuadPart;
990
991 /* Use a "time zero" to reduce precision loss when converting time
992 to floatting point number, as in time.perf_counter(). */
993 ticksll -= t0;
994
995 /* Make sure that casting LONGLONG to _PyTime_t cannot overflow,
996 both types are signed */
997 Py_BUILD_ASSERT(sizeof(ticksll) <= sizeof(ticks));
998 ticks = (_PyTime_t)ticksll;
999
1000 *tp = _PyTime_MulDiv(ticks, SEC_TO_NS, (_PyTime_t)frequency);
Victor Stinnercba9a0c2017-10-12 08:51:56 -07001001 return 0;
Victor Stinnera997c7b2017-10-10 02:51:50 -07001002}
1003#endif
1004
1005
1006int
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -07001007_PyTime_GetPerfCounterWithInfo(_PyTime_t *t, _Py_clock_info_t *info)
Victor Stinnera997c7b2017-10-10 02:51:50 -07001008{
1009#ifdef MS_WINDOWS
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -07001010 return win_perf_counter(t, info);
Victor Stinnera997c7b2017-10-10 02:51:50 -07001011#else
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -07001012 return _PyTime_GetMonotonicClockWithInfo(t, info);
Victor Stinnera997c7b2017-10-10 02:51:50 -07001013#endif
1014}
1015
1016
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -07001017_PyTime_t
1018_PyTime_GetPerfCounter(void)
Victor Stinnera997c7b2017-10-10 02:51:50 -07001019{
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -07001020 _PyTime_t t;
1021 if (_PyTime_GetPerfCounterWithInfo(&t, NULL)) {
Serhiy Storchakaeebaa9b2020-03-09 20:49:52 +02001022 Py_FatalError("_PyTime_GetPerfCounterWithInfo() failed");
Victor Stinnera997c7b2017-10-10 02:51:50 -07001023 }
1024 return t;
1025}
1026
1027
Victor Stinner4bfb4602015-03-27 22:27:24 +01001028int
Victor Stinner00111242014-08-29 16:31:59 +02001029_PyTime_Init(void)
Alexander Belopolsky6fc4ade2010-08-05 17:34:27 +00001030{
Victor Stinnercba9a0c2017-10-12 08:51:56 -07001031 /* check that time.time(), time.monotonic() and time.perf_counter() clocks
1032 are working properly to not have to check for exceptions at runtime. If
1033 a clock works once, it cannot fail in next calls. */
Victor Stinnercb29f012015-03-27 13:31:18 +01001034 _PyTime_t t;
Victor Stinnera997c7b2017-10-10 02:51:50 -07001035 if (_PyTime_GetSystemClockWithInfo(&t, NULL) < 0) {
Victor Stinner00111242014-08-29 16:31:59 +02001036 return -1;
Victor Stinnera997c7b2017-10-10 02:51:50 -07001037 }
1038 if (_PyTime_GetMonotonicClockWithInfo(&t, NULL) < 0) {
Victor Stinnercb29f012015-03-27 13:31:18 +01001039 return -1;
Victor Stinnera997c7b2017-10-10 02:51:50 -07001040 }
Victor Stinnerbdaeb7d2017-10-16 08:44:31 -07001041 if (_PyTime_GetPerfCounterWithInfo(&t, NULL) < 0) {
Victor Stinnera997c7b2017-10-10 02:51:50 -07001042 return -1;
1043 }
Victor Stinner00111242014-08-29 16:31:59 +02001044 return 0;
Alexander Belopolsky6fc4ade2010-08-05 17:34:27 +00001045}
Alexander Belopolsky3e7a3cb2016-09-28 17:31:35 -04001046
1047int
1048_PyTime_localtime(time_t t, struct tm *tm)
1049{
1050#ifdef MS_WINDOWS
1051 int error;
1052
1053 error = localtime_s(tm, &t);
1054 if (error != 0) {
1055 errno = error;
1056 PyErr_SetFromErrno(PyExc_OSError);
1057 return -1;
1058 }
1059 return 0;
1060#else /* !MS_WINDOWS */
Victor Stinner87094902019-04-09 19:12:26 +02001061
Michael Feltde6f38d2020-02-07 18:56:16 +01001062#if defined(_AIX) && (SIZEOF_TIME_T < 8)
Victor Stinner87094902019-04-09 19:12:26 +02001063 /* bpo-34373: AIX does not return NULL if t is too small or too large */
1064 if (t < -2145916800 /* 1902-01-01 */
1065 || t > 2145916800 /* 2038-01-01 */) {
Michael Felte2926b72018-12-28 14:57:37 +01001066 errno = EINVAL;
Michael Felte2926b72018-12-28 14:57:37 +01001067 PyErr_SetString(PyExc_OverflowError,
Victor Stinner87094902019-04-09 19:12:26 +02001068 "localtime argument out of range");
Michael Felte2926b72018-12-28 14:57:37 +01001069 return -1;
1070 }
1071#endif
Victor Stinner87094902019-04-09 19:12:26 +02001072
1073 errno = 0;
Alexander Belopolsky3e7a3cb2016-09-28 17:31:35 -04001074 if (localtime_r(&t, tm) == NULL) {
Victor Stinner277c8402017-10-11 08:11:38 -07001075 if (errno == 0) {
Alexander Belopolsky3e7a3cb2016-09-28 17:31:35 -04001076 errno = EINVAL;
Victor Stinner277c8402017-10-11 08:11:38 -07001077 }
Alexander Belopolsky3e7a3cb2016-09-28 17:31:35 -04001078 PyErr_SetFromErrno(PyExc_OSError);
1079 return -1;
1080 }
1081 return 0;
1082#endif /* MS_WINDOWS */
1083}
1084
1085int
1086_PyTime_gmtime(time_t t, struct tm *tm)
1087{
1088#ifdef MS_WINDOWS
1089 int error;
1090
1091 error = gmtime_s(tm, &t);
1092 if (error != 0) {
1093 errno = error;
1094 PyErr_SetFromErrno(PyExc_OSError);
1095 return -1;
1096 }
1097 return 0;
1098#else /* !MS_WINDOWS */
1099 if (gmtime_r(&t, tm) == NULL) {
1100#ifdef EINVAL
Victor Stinner277c8402017-10-11 08:11:38 -07001101 if (errno == 0) {
Alexander Belopolsky3e7a3cb2016-09-28 17:31:35 -04001102 errno = EINVAL;
Victor Stinner277c8402017-10-11 08:11:38 -07001103 }
Alexander Belopolsky3e7a3cb2016-09-28 17:31:35 -04001104#endif
1105 PyErr_SetFromErrno(PyExc_OSError);
1106 return -1;
1107 }
1108 return 0;
1109#endif /* MS_WINDOWS */
1110}