blob: 09b557958a02facd9d5c94de48b8a5ccbf6e7d6c [file] [log] [blame]
Tim Peters2a799bf2002-12-16 20:18:38 +00001/* C implementation for the date/time type documented at
2 * http://www.zope.org/Members/fdrake/DateTimeWiki/FrontPage
3 */
4
5#include "Python.h"
Tim Peters2a799bf2002-12-16 20:18:38 +00006#include "structmember.h"
7
8#include <time.h>
9
Victor Stinner09e5cf22015-03-30 00:09:18 +020010#ifdef MS_WINDOWS
11# include <winsock2.h> /* struct timeval */
12#endif
13
Tim Peters9ddf40b2004-06-20 22:41:32 +000014/* Differentiate between building the core module and building extension
15 * modules.
16 */
Guido van Rossum360e4b82007-05-14 22:51:27 +000017#ifndef Py_BUILD_CORE
Tim Peters9ddf40b2004-06-20 22:41:32 +000018#define Py_BUILD_CORE
Guido van Rossum360e4b82007-05-14 22:51:27 +000019#endif
Tim Peters2a799bf2002-12-16 20:18:38 +000020#include "datetime.h"
Tim Peters9ddf40b2004-06-20 22:41:32 +000021#undef Py_BUILD_CORE
Tim Peters2a799bf2002-12-16 20:18:38 +000022
Larry Hastings61272b72014-01-07 12:41:53 -080023/*[clinic input]
Larry Hastings44e2eaa2013-11-23 15:37:55 -080024module datetime
Larry Hastingsc2047262014-01-25 20:43:29 -080025class datetime.datetime "PyDateTime_DateTime *" "&PyDateTime_DateTimeType"
Larry Hastings61272b72014-01-07 12:41:53 -080026[clinic start generated code]*/
Larry Hastings581ee362014-01-28 05:00:08 -080027/*[clinic end generated code: output=da39a3ee5e6b4b0d input=78142cb64b9e98bc]*/
Larry Hastings44e2eaa2013-11-23 15:37:55 -080028
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030029#include "clinic/_datetimemodule.c.h"
30
Tim Peters2a799bf2002-12-16 20:18:38 +000031/* We require that C int be at least 32 bits, and use int virtually
32 * everywhere. In just a few cases we use a temp long, where a Python
33 * API returns a C long. In such cases, we have to ensure that the
34 * final result fits in a C int (this can be an issue on 64-bit boxes).
35 */
36#if SIZEOF_INT < 4
Alexander Belopolskycf86e362010-07-23 19:25:47 +000037# error "_datetime.c requires that C int have at least 32 bits"
Tim Peters2a799bf2002-12-16 20:18:38 +000038#endif
39
40#define MINYEAR 1
41#define MAXYEAR 9999
Alexander Belopolskyf03a6162010-05-27 21:42:58 +000042#define MAXORDINAL 3652059 /* date(9999,12,31).toordinal() */
Tim Peters2a799bf2002-12-16 20:18:38 +000043
44/* Nine decimal digits is easy to communicate, and leaves enough room
45 * so that two delta days can be added w/o fear of overflowing a signed
46 * 32-bit int, and with plenty of room left over to absorb any possible
47 * carries from adding seconds.
48 */
49#define MAX_DELTA_DAYS 999999999
50
51/* Rename the long macros in datetime.h to more reasonable short names. */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000052#define GET_YEAR PyDateTime_GET_YEAR
53#define GET_MONTH PyDateTime_GET_MONTH
54#define GET_DAY PyDateTime_GET_DAY
55#define DATE_GET_HOUR PyDateTime_DATE_GET_HOUR
56#define DATE_GET_MINUTE PyDateTime_DATE_GET_MINUTE
57#define DATE_GET_SECOND PyDateTime_DATE_GET_SECOND
58#define DATE_GET_MICROSECOND PyDateTime_DATE_GET_MICROSECOND
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -040059#define DATE_GET_FOLD PyDateTime_DATE_GET_FOLD
Tim Peters2a799bf2002-12-16 20:18:38 +000060
61/* Date accessors for date and datetime. */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000062#define SET_YEAR(o, v) (((o)->data[0] = ((v) & 0xff00) >> 8), \
63 ((o)->data[1] = ((v) & 0x00ff)))
64#define SET_MONTH(o, v) (PyDateTime_GET_MONTH(o) = (v))
65#define SET_DAY(o, v) (PyDateTime_GET_DAY(o) = (v))
Tim Peters2a799bf2002-12-16 20:18:38 +000066
67/* Date/Time accessors for datetime. */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000068#define DATE_SET_HOUR(o, v) (PyDateTime_DATE_GET_HOUR(o) = (v))
69#define DATE_SET_MINUTE(o, v) (PyDateTime_DATE_GET_MINUTE(o) = (v))
70#define DATE_SET_SECOND(o, v) (PyDateTime_DATE_GET_SECOND(o) = (v))
71#define DATE_SET_MICROSECOND(o, v) \
72 (((o)->data[7] = ((v) & 0xff0000) >> 16), \
73 ((o)->data[8] = ((v) & 0x00ff00) >> 8), \
74 ((o)->data[9] = ((v) & 0x0000ff)))
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -040075#define DATE_SET_FOLD(o, v) (PyDateTime_DATE_GET_FOLD(o) = (v))
Tim Peters2a799bf2002-12-16 20:18:38 +000076
77/* Time accessors for time. */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000078#define TIME_GET_HOUR PyDateTime_TIME_GET_HOUR
79#define TIME_GET_MINUTE PyDateTime_TIME_GET_MINUTE
80#define TIME_GET_SECOND PyDateTime_TIME_GET_SECOND
81#define TIME_GET_MICROSECOND PyDateTime_TIME_GET_MICROSECOND
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -040082#define TIME_GET_FOLD PyDateTime_TIME_GET_FOLD
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000083#define TIME_SET_HOUR(o, v) (PyDateTime_TIME_GET_HOUR(o) = (v))
84#define TIME_SET_MINUTE(o, v) (PyDateTime_TIME_GET_MINUTE(o) = (v))
85#define TIME_SET_SECOND(o, v) (PyDateTime_TIME_GET_SECOND(o) = (v))
86#define TIME_SET_MICROSECOND(o, v) \
87 (((o)->data[3] = ((v) & 0xff0000) >> 16), \
88 ((o)->data[4] = ((v) & 0x00ff00) >> 8), \
89 ((o)->data[5] = ((v) & 0x0000ff)))
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -040090#define TIME_SET_FOLD(o, v) (PyDateTime_TIME_GET_FOLD(o) = (v))
Tim Peters2a799bf2002-12-16 20:18:38 +000091
92/* Delta accessors for timedelta. */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000093#define GET_TD_DAYS(o) (((PyDateTime_Delta *)(o))->days)
94#define GET_TD_SECONDS(o) (((PyDateTime_Delta *)(o))->seconds)
95#define GET_TD_MICROSECONDS(o) (((PyDateTime_Delta *)(o))->microseconds)
Tim Peters2a799bf2002-12-16 20:18:38 +000096
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000097#define SET_TD_DAYS(o, v) ((o)->days = (v))
98#define SET_TD_SECONDS(o, v) ((o)->seconds = (v))
Tim Peters2a799bf2002-12-16 20:18:38 +000099#define SET_TD_MICROSECONDS(o, v) ((o)->microseconds = (v))
100
Tim Petersa032d2e2003-01-11 00:15:54 +0000101/* p is a pointer to a time or a datetime object; HASTZINFO(p) returns
102 * p->hastzinfo.
103 */
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000104#define HASTZINFO(p) (((_PyDateTime_BaseTZInfo *)(p))->hastzinfo)
105#define GET_TIME_TZINFO(p) (HASTZINFO(p) ? \
106 ((PyDateTime_Time *)(p))->tzinfo : Py_None)
107#define GET_DT_TZINFO(p) (HASTZINFO(p) ? \
108 ((PyDateTime_DateTime *)(p))->tzinfo : Py_None)
Tim Peters3f606292004-03-21 23:38:41 +0000109/* M is a char or int claiming to be a valid month. The macro is equivalent
110 * to the two-sided Python test
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000111 * 1 <= M <= 12
Tim Peters3f606292004-03-21 23:38:41 +0000112 */
113#define MONTH_IS_SANE(M) ((unsigned int)(M) - 1 < 12)
114
Tim Peters2a799bf2002-12-16 20:18:38 +0000115/* Forward declarations. */
116static PyTypeObject PyDateTime_DateType;
117static PyTypeObject PyDateTime_DateTimeType;
Tim Peters2a799bf2002-12-16 20:18:38 +0000118static PyTypeObject PyDateTime_DeltaType;
119static PyTypeObject PyDateTime_TimeType;
120static PyTypeObject PyDateTime_TZInfoType;
Alexander Belopolsky4e749a12010-06-14 14:15:50 +0000121static PyTypeObject PyDateTime_TimeZoneType;
Tim Peters2a799bf2002-12-16 20:18:38 +0000122
Victor Stinnerb67f0962017-02-10 10:34:02 +0100123static int check_tzinfo_subclass(PyObject *p);
124
Martin v. Löwise75fc142013-11-07 18:46:53 +0100125_Py_IDENTIFIER(as_integer_ratio);
126_Py_IDENTIFIER(fromutc);
127_Py_IDENTIFIER(isoformat);
128_Py_IDENTIFIER(strftime);
129
Tim Peters2a799bf2002-12-16 20:18:38 +0000130/* ---------------------------------------------------------------------------
131 * Math utilities.
132 */
133
134/* k = i+j overflows iff k differs in sign from both inputs,
135 * iff k^i has sign bit set and k^j has sign bit set,
136 * iff (k^i)&(k^j) has sign bit set.
137 */
138#define SIGNED_ADD_OVERFLOWED(RESULT, I, J) \
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000139 ((((RESULT) ^ (I)) & ((RESULT) ^ (J))) < 0)
Tim Peters2a799bf2002-12-16 20:18:38 +0000140
141/* Compute Python divmod(x, y), returning the quotient and storing the
142 * remainder into *r. The quotient is the floor of x/y, and that's
143 * the real point of this. C will probably truncate instead (C99
144 * requires truncation; C89 left it implementation-defined).
145 * Simplification: we *require* that y > 0 here. That's appropriate
146 * for all the uses made of it. This simplifies the code and makes
147 * the overflow case impossible (divmod(LONG_MIN, -1) is the only
148 * overflow case).
149 */
150static int
151divmod(int x, int y, int *r)
152{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000153 int quo;
Tim Peters2a799bf2002-12-16 20:18:38 +0000154
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000155 assert(y > 0);
156 quo = x / y;
157 *r = x - quo * y;
158 if (*r < 0) {
159 --quo;
160 *r += y;
161 }
162 assert(0 <= *r && *r < y);
163 return quo;
Tim Peters2a799bf2002-12-16 20:18:38 +0000164}
165
Alexander Belopolsky1790bc42010-05-31 17:33:47 +0000166/* Nearest integer to m / n for integers m and n. Half-integer results
167 * are rounded to even.
168 */
169static PyObject *
170divide_nearest(PyObject *m, PyObject *n)
171{
172 PyObject *result;
173 PyObject *temp;
174
Mark Dickinsonfa68a612010-06-07 18:47:09 +0000175 temp = _PyLong_DivmodNear(m, n);
Alexander Belopolsky1790bc42010-05-31 17:33:47 +0000176 if (temp == NULL)
177 return NULL;
178 result = PyTuple_GET_ITEM(temp, 0);
179 Py_INCREF(result);
180 Py_DECREF(temp);
181
182 return result;
183}
184
Tim Peters2a799bf2002-12-16 20:18:38 +0000185/* ---------------------------------------------------------------------------
186 * General calendrical helper functions
187 */
188
189/* For each month ordinal in 1..12, the number of days in that month,
190 * and the number of days before that month in the same year. These
191 * are correct for non-leap years only.
192 */
Serhiy Storchaka2d06e842015-12-25 19:53:18 +0200193static const int _days_in_month[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000194 0, /* unused; this vector uses 1-based indexing */
195 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31
Tim Peters2a799bf2002-12-16 20:18:38 +0000196};
197
Serhiy Storchaka2d06e842015-12-25 19:53:18 +0200198static const int _days_before_month[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000199 0, /* unused; this vector uses 1-based indexing */
200 0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334
Tim Peters2a799bf2002-12-16 20:18:38 +0000201};
202
203/* year -> 1 if leap year, else 0. */
204static int
205is_leap(int year)
206{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000207 /* Cast year to unsigned. The result is the same either way, but
208 * C can generate faster code for unsigned mod than for signed
209 * mod (especially for % 4 -- a good compiler should just grab
210 * the last 2 bits when the LHS is unsigned).
211 */
212 const unsigned int ayear = (unsigned int)year;
213 return ayear % 4 == 0 && (ayear % 100 != 0 || ayear % 400 == 0);
Tim Peters2a799bf2002-12-16 20:18:38 +0000214}
215
216/* year, month -> number of days in that month in that year */
217static int
218days_in_month(int year, int month)
219{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000220 assert(month >= 1);
221 assert(month <= 12);
222 if (month == 2 && is_leap(year))
223 return 29;
224 else
225 return _days_in_month[month];
Tim Peters2a799bf2002-12-16 20:18:38 +0000226}
227
Martin Panter46f50722016-05-26 05:35:26 +0000228/* year, month -> number of days in year preceding first day of month */
Tim Peters2a799bf2002-12-16 20:18:38 +0000229static int
230days_before_month(int year, int month)
231{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000232 int days;
Tim Peters2a799bf2002-12-16 20:18:38 +0000233
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000234 assert(month >= 1);
235 assert(month <= 12);
236 days = _days_before_month[month];
237 if (month > 2 && is_leap(year))
238 ++days;
239 return days;
Tim Peters2a799bf2002-12-16 20:18:38 +0000240}
241
242/* year -> number of days before January 1st of year. Remember that we
243 * start with year 1, so days_before_year(1) == 0.
244 */
245static int
246days_before_year(int year)
247{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000248 int y = year - 1;
249 /* This is incorrect if year <= 0; we really want the floor
250 * here. But so long as MINYEAR is 1, the smallest year this
Alexander Belopolsky59a289d2010-10-13 22:54:34 +0000251 * can see is 1.
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000252 */
Alexander Belopolsky59a289d2010-10-13 22:54:34 +0000253 assert (year >= 1);
254 return y*365 + y/4 - y/100 + y/400;
Tim Peters2a799bf2002-12-16 20:18:38 +0000255}
256
257/* Number of days in 4, 100, and 400 year cycles. That these have
258 * the correct values is asserted in the module init function.
259 */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000260#define DI4Y 1461 /* days_before_year(5); days in 4 years */
261#define DI100Y 36524 /* days_before_year(101); days in 100 years */
262#define DI400Y 146097 /* days_before_year(401); days in 400 years */
Tim Peters2a799bf2002-12-16 20:18:38 +0000263
264/* ordinal -> year, month, day, considering 01-Jan-0001 as day 1. */
265static void
266ord_to_ymd(int ordinal, int *year, int *month, int *day)
267{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000268 int n, n1, n4, n100, n400, leapyear, preceding;
Tim Peters2a799bf2002-12-16 20:18:38 +0000269
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000270 /* ordinal is a 1-based index, starting at 1-Jan-1. The pattern of
271 * leap years repeats exactly every 400 years. The basic strategy is
272 * to find the closest 400-year boundary at or before ordinal, then
273 * work with the offset from that boundary to ordinal. Life is much
274 * clearer if we subtract 1 from ordinal first -- then the values
275 * of ordinal at 400-year boundaries are exactly those divisible
276 * by DI400Y:
277 *
278 * D M Y n n-1
279 * -- --- ---- ---------- ----------------
280 * 31 Dec -400 -DI400Y -DI400Y -1
281 * 1 Jan -399 -DI400Y +1 -DI400Y 400-year boundary
282 * ...
283 * 30 Dec 000 -1 -2
284 * 31 Dec 000 0 -1
285 * 1 Jan 001 1 0 400-year boundary
286 * 2 Jan 001 2 1
287 * 3 Jan 001 3 2
288 * ...
289 * 31 Dec 400 DI400Y DI400Y -1
290 * 1 Jan 401 DI400Y +1 DI400Y 400-year boundary
291 */
292 assert(ordinal >= 1);
293 --ordinal;
294 n400 = ordinal / DI400Y;
295 n = ordinal % DI400Y;
296 *year = n400 * 400 + 1;
Tim Peters2a799bf2002-12-16 20:18:38 +0000297
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000298 /* Now n is the (non-negative) offset, in days, from January 1 of
299 * year, to the desired date. Now compute how many 100-year cycles
300 * precede n.
301 * Note that it's possible for n100 to equal 4! In that case 4 full
302 * 100-year cycles precede the desired day, which implies the
303 * desired day is December 31 at the end of a 400-year cycle.
304 */
305 n100 = n / DI100Y;
306 n = n % DI100Y;
Tim Peters2a799bf2002-12-16 20:18:38 +0000307
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000308 /* Now compute how many 4-year cycles precede it. */
309 n4 = n / DI4Y;
310 n = n % DI4Y;
Tim Peters2a799bf2002-12-16 20:18:38 +0000311
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000312 /* And now how many single years. Again n1 can be 4, and again
313 * meaning that the desired day is December 31 at the end of the
314 * 4-year cycle.
315 */
316 n1 = n / 365;
317 n = n % 365;
Tim Peters2a799bf2002-12-16 20:18:38 +0000318
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000319 *year += n100 * 100 + n4 * 4 + n1;
320 if (n1 == 4 || n100 == 4) {
321 assert(n == 0);
322 *year -= 1;
323 *month = 12;
324 *day = 31;
325 return;
326 }
Tim Peters2a799bf2002-12-16 20:18:38 +0000327
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000328 /* Now the year is correct, and n is the offset from January 1. We
329 * find the month via an estimate that's either exact or one too
330 * large.
331 */
332 leapyear = n1 == 3 && (n4 != 24 || n100 == 3);
333 assert(leapyear == is_leap(*year));
334 *month = (n + 50) >> 5;
335 preceding = (_days_before_month[*month] + (*month > 2 && leapyear));
336 if (preceding > n) {
337 /* estimate is too large */
338 *month -= 1;
339 preceding -= days_in_month(*year, *month);
340 }
341 n -= preceding;
342 assert(0 <= n);
343 assert(n < days_in_month(*year, *month));
Tim Peters2a799bf2002-12-16 20:18:38 +0000344
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000345 *day = n + 1;
Tim Peters2a799bf2002-12-16 20:18:38 +0000346}
347
348/* year, month, day -> ordinal, considering 01-Jan-0001 as day 1. */
349static int
350ymd_to_ord(int year, int month, int day)
351{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000352 return days_before_year(year) + days_before_month(year, month) + day;
Tim Peters2a799bf2002-12-16 20:18:38 +0000353}
354
355/* Day of week, where Monday==0, ..., Sunday==6. 1/1/1 was a Monday. */
356static int
357weekday(int year, int month, int day)
358{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000359 return (ymd_to_ord(year, month, day) + 6) % 7;
Tim Peters2a799bf2002-12-16 20:18:38 +0000360}
361
362/* Ordinal of the Monday starting week 1 of the ISO year. Week 1 is the
363 * first calendar week containing a Thursday.
364 */
365static int
366iso_week1_monday(int year)
367{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000368 int first_day = ymd_to_ord(year, 1, 1); /* ord of 1/1 */
369 /* 0 if 1/1 is a Monday, 1 if a Tue, etc. */
370 int first_weekday = (first_day + 6) % 7;
371 /* ordinal of closest Monday at or before 1/1 */
372 int week1_monday = first_day - first_weekday;
Tim Peters2a799bf2002-12-16 20:18:38 +0000373
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000374 if (first_weekday > 3) /* if 1/1 was Fri, Sat, Sun */
375 week1_monday += 7;
376 return week1_monday;
Tim Peters2a799bf2002-12-16 20:18:38 +0000377}
378
379/* ---------------------------------------------------------------------------
380 * Range checkers.
381 */
382
383/* Check that -MAX_DELTA_DAYS <= days <= MAX_DELTA_DAYS. If so, return 0.
384 * If not, raise OverflowError and return -1.
385 */
386static int
387check_delta_day_range(int days)
388{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000389 if (-MAX_DELTA_DAYS <= days && days <= MAX_DELTA_DAYS)
390 return 0;
391 PyErr_Format(PyExc_OverflowError,
392 "days=%d; must have magnitude <= %d",
393 days, MAX_DELTA_DAYS);
394 return -1;
Tim Peters2a799bf2002-12-16 20:18:38 +0000395}
396
397/* Check that date arguments are in range. Return 0 if they are. If they
398 * aren't, raise ValueError and return -1.
399 */
400static int
401check_date_args(int year, int month, int day)
402{
403
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000404 if (year < MINYEAR || year > MAXYEAR) {
Victor Stinnerb67f0962017-02-10 10:34:02 +0100405 PyErr_Format(PyExc_ValueError, "year %i is out of range", year);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000406 return -1;
407 }
408 if (month < 1 || month > 12) {
409 PyErr_SetString(PyExc_ValueError,
410 "month must be in 1..12");
411 return -1;
412 }
413 if (day < 1 || day > days_in_month(year, month)) {
414 PyErr_SetString(PyExc_ValueError,
415 "day is out of range for month");
416 return -1;
417 }
418 return 0;
Tim Peters2a799bf2002-12-16 20:18:38 +0000419}
420
421/* Check that time arguments are in range. Return 0 if they are. If they
422 * aren't, raise ValueError and return -1.
423 */
424static int
Alexander Belopolsky47649ab2016-08-08 17:05:40 -0400425check_time_args(int h, int m, int s, int us, int fold)
Tim Peters2a799bf2002-12-16 20:18:38 +0000426{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000427 if (h < 0 || h > 23) {
428 PyErr_SetString(PyExc_ValueError,
429 "hour must be in 0..23");
430 return -1;
431 }
432 if (m < 0 || m > 59) {
433 PyErr_SetString(PyExc_ValueError,
434 "minute must be in 0..59");
435 return -1;
436 }
437 if (s < 0 || s > 59) {
438 PyErr_SetString(PyExc_ValueError,
439 "second must be in 0..59");
440 return -1;
441 }
442 if (us < 0 || us > 999999) {
443 PyErr_SetString(PyExc_ValueError,
444 "microsecond must be in 0..999999");
445 return -1;
446 }
Alexander Belopolsky47649ab2016-08-08 17:05:40 -0400447 if (fold != 0 && fold != 1) {
448 PyErr_SetString(PyExc_ValueError,
449 "fold must be either 0 or 1");
450 return -1;
451 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000452 return 0;
Tim Peters2a799bf2002-12-16 20:18:38 +0000453}
454
455/* ---------------------------------------------------------------------------
456 * Normalization utilities.
457 */
458
459/* One step of a mixed-radix conversion. A "hi" unit is equivalent to
460 * factor "lo" units. factor must be > 0. If *lo is less than 0, or
461 * at least factor, enough of *lo is converted into "hi" units so that
462 * 0 <= *lo < factor. The input values must be such that int overflow
463 * is impossible.
464 */
465static void
466normalize_pair(int *hi, int *lo, int factor)
467{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000468 assert(factor > 0);
469 assert(lo != hi);
470 if (*lo < 0 || *lo >= factor) {
471 const int num_hi = divmod(*lo, factor, lo);
472 const int new_hi = *hi + num_hi;
473 assert(! SIGNED_ADD_OVERFLOWED(new_hi, *hi, num_hi));
474 *hi = new_hi;
475 }
476 assert(0 <= *lo && *lo < factor);
Tim Peters2a799bf2002-12-16 20:18:38 +0000477}
478
479/* Fiddle days (d), seconds (s), and microseconds (us) so that
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000480 * 0 <= *s < 24*3600
481 * 0 <= *us < 1000000
Tim Peters2a799bf2002-12-16 20:18:38 +0000482 * The input values must be such that the internals don't overflow.
483 * The way this routine is used, we don't get close.
484 */
485static void
486normalize_d_s_us(int *d, int *s, int *us)
487{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000488 if (*us < 0 || *us >= 1000000) {
489 normalize_pair(s, us, 1000000);
490 /* |s| can't be bigger than about
491 * |original s| + |original us|/1000000 now.
492 */
Tim Peters2a799bf2002-12-16 20:18:38 +0000493
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000494 }
495 if (*s < 0 || *s >= 24*3600) {
496 normalize_pair(d, s, 24*3600);
497 /* |d| can't be bigger than about
498 * |original d| +
499 * (|original s| + |original us|/1000000) / (24*3600) now.
500 */
501 }
502 assert(0 <= *s && *s < 24*3600);
503 assert(0 <= *us && *us < 1000000);
Tim Peters2a799bf2002-12-16 20:18:38 +0000504}
505
506/* Fiddle years (y), months (m), and days (d) so that
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000507 * 1 <= *m <= 12
508 * 1 <= *d <= days_in_month(*y, *m)
Tim Peters2a799bf2002-12-16 20:18:38 +0000509 * The input values must be such that the internals don't overflow.
510 * The way this routine is used, we don't get close.
511 */
Alexander Belopolskyf03a6162010-05-27 21:42:58 +0000512static int
Tim Peters2a799bf2002-12-16 20:18:38 +0000513normalize_y_m_d(int *y, int *m, int *d)
514{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000515 int dim; /* # of days in month */
Tim Peters2a799bf2002-12-16 20:18:38 +0000516
Alexander Belopolsky59a289d2010-10-13 22:54:34 +0000517 /* In actual use, m is always the month component extracted from a
518 * date/datetime object. Therefore it is always in [1, 12] range.
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000519 */
Alexander Belopolsky59a289d2010-10-13 22:54:34 +0000520
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000521 assert(1 <= *m && *m <= 12);
Tim Peters2a799bf2002-12-16 20:18:38 +0000522
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000523 /* Now only day can be out of bounds (year may also be out of bounds
524 * for a datetime object, but we don't care about that here).
525 * If day is out of bounds, what to do is arguable, but at least the
526 * method here is principled and explainable.
527 */
528 dim = days_in_month(*y, *m);
529 if (*d < 1 || *d > dim) {
530 /* Move day-1 days from the first of the month. First try to
531 * get off cheap if we're only one day out of range
532 * (adjustments for timezone alone can't be worse than that).
533 */
534 if (*d == 0) {
535 --*m;
536 if (*m > 0)
537 *d = days_in_month(*y, *m);
538 else {
539 --*y;
540 *m = 12;
541 *d = 31;
542 }
543 }
544 else if (*d == dim + 1) {
545 /* move forward a day */
546 ++*m;
547 *d = 1;
548 if (*m > 12) {
549 *m = 1;
550 ++*y;
551 }
552 }
553 else {
554 int ordinal = ymd_to_ord(*y, *m, 1) +
555 *d - 1;
Alexander Belopolskyf03a6162010-05-27 21:42:58 +0000556 if (ordinal < 1 || ordinal > MAXORDINAL) {
557 goto error;
558 } else {
559 ord_to_ymd(ordinal, y, m, d);
560 return 0;
561 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000562 }
563 }
564 assert(*m > 0);
565 assert(*d > 0);
Alexander Belopolskyf03a6162010-05-27 21:42:58 +0000566 if (MINYEAR <= *y && *y <= MAXYEAR)
567 return 0;
568 error:
569 PyErr_SetString(PyExc_OverflowError,
570 "date value out of range");
571 return -1;
572
Tim Peters2a799bf2002-12-16 20:18:38 +0000573}
574
575/* Fiddle out-of-bounds months and days so that the result makes some kind
576 * of sense. The parameters are both inputs and outputs. Returns < 0 on
577 * failure, where failure means the adjusted year is out of bounds.
578 */
579static int
580normalize_date(int *year, int *month, int *day)
581{
Alexander Belopolskyf03a6162010-05-27 21:42:58 +0000582 return normalize_y_m_d(year, month, day);
Tim Peters2a799bf2002-12-16 20:18:38 +0000583}
584
585/* Force all the datetime fields into range. The parameters are both
586 * inputs and outputs. Returns < 0 on error.
587 */
588static int
589normalize_datetime(int *year, int *month, int *day,
590 int *hour, int *minute, int *second,
591 int *microsecond)
592{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000593 normalize_pair(second, microsecond, 1000000);
594 normalize_pair(minute, second, 60);
595 normalize_pair(hour, minute, 60);
596 normalize_pair(day, hour, 24);
597 return normalize_date(year, month, day);
Tim Peters2a799bf2002-12-16 20:18:38 +0000598}
599
600/* ---------------------------------------------------------------------------
Tim Petersb0c854d2003-05-17 15:57:00 +0000601 * Basic object allocation: tp_alloc implementations. These allocate
602 * Python objects of the right size and type, and do the Python object-
603 * initialization bit. If there's not enough memory, they return NULL after
604 * setting MemoryError. All data members remain uninitialized trash.
605 *
606 * We abuse the tp_alloc "nitems" argument to communicate whether a tzinfo
Tim Peters03eaf8b2003-05-18 02:24:46 +0000607 * member is needed. This is ugly, imprecise, and possibly insecure.
608 * tp_basicsize for the time and datetime types is set to the size of the
609 * struct that has room for the tzinfo member, so subclasses in Python will
610 * allocate enough space for a tzinfo member whether or not one is actually
611 * needed. That's the "ugly and imprecise" parts. The "possibly insecure"
612 * part is that PyType_GenericAlloc() (which subclasses in Python end up
613 * using) just happens today to effectively ignore the nitems argument
614 * when tp_itemsize is 0, which it is for these type objects. If that
615 * changes, perhaps the callers of tp_alloc slots in this file should
616 * be changed to force a 0 nitems argument unless the type being allocated
617 * is a base type implemented in this file (so that tp_alloc is time_alloc
618 * or datetime_alloc below, which know about the nitems abuse).
Tim Petersb0c854d2003-05-17 15:57:00 +0000619 */
620
621static PyObject *
Martin v. Löwis18e16552006-02-15 17:27:45 +0000622time_alloc(PyTypeObject *type, Py_ssize_t aware)
Tim Petersb0c854d2003-05-17 15:57:00 +0000623{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000624 PyObject *self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000625
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000626 self = (PyObject *)
627 PyObject_MALLOC(aware ?
628 sizeof(PyDateTime_Time) :
629 sizeof(_PyDateTime_BaseTime));
630 if (self == NULL)
631 return (PyObject *)PyErr_NoMemory();
Christian Heimesecb4e6a2013-12-04 09:34:29 +0100632 (void)PyObject_INIT(self, type);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000633 return self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000634}
635
636static PyObject *
Martin v. Löwis18e16552006-02-15 17:27:45 +0000637datetime_alloc(PyTypeObject *type, Py_ssize_t aware)
Tim Petersb0c854d2003-05-17 15:57:00 +0000638{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000639 PyObject *self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000640
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000641 self = (PyObject *)
642 PyObject_MALLOC(aware ?
643 sizeof(PyDateTime_DateTime) :
644 sizeof(_PyDateTime_BaseDateTime));
645 if (self == NULL)
646 return (PyObject *)PyErr_NoMemory();
Christian Heimesecb4e6a2013-12-04 09:34:29 +0100647 (void)PyObject_INIT(self, type);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000648 return self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000649}
650
651/* ---------------------------------------------------------------------------
652 * Helpers for setting object fields. These work on pointers to the
653 * appropriate base class.
654 */
655
656/* For date and datetime. */
657static void
658set_date_fields(PyDateTime_Date *self, int y, int m, int d)
659{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000660 self->hashcode = -1;
661 SET_YEAR(self, y);
662 SET_MONTH(self, m);
663 SET_DAY(self, d);
Tim Petersb0c854d2003-05-17 15:57:00 +0000664}
665
666/* ---------------------------------------------------------------------------
667 * Create various objects, mostly without range checking.
668 */
669
670/* Create a date instance with no range checking. */
671static PyObject *
672new_date_ex(int year, int month, int day, PyTypeObject *type)
673{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000674 PyDateTime_Date *self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000675
Victor Stinnerb67f0962017-02-10 10:34:02 +0100676 if (check_date_args(year, month, day) < 0) {
677 return NULL;
678 }
679
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000680 self = (PyDateTime_Date *) (type->tp_alloc(type, 0));
681 if (self != NULL)
682 set_date_fields(self, year, month, day);
683 return (PyObject *) self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000684}
685
686#define new_date(year, month, day) \
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000687 new_date_ex(year, month, day, &PyDateTime_DateType)
Tim Petersb0c854d2003-05-17 15:57:00 +0000688
689/* Create a datetime instance with no range checking. */
690static PyObject *
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -0400691new_datetime_ex2(int year, int month, int day, int hour, int minute,
692 int second, int usecond, PyObject *tzinfo, int fold, PyTypeObject *type)
Tim Petersb0c854d2003-05-17 15:57:00 +0000693{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000694 PyDateTime_DateTime *self;
695 char aware = tzinfo != Py_None;
Tim Petersb0c854d2003-05-17 15:57:00 +0000696
Victor Stinnerb67f0962017-02-10 10:34:02 +0100697 if (check_date_args(year, month, day) < 0) {
698 return NULL;
699 }
700 if (check_time_args(hour, minute, second, usecond, fold) < 0) {
701 return NULL;
702 }
703 if (check_tzinfo_subclass(tzinfo) < 0) {
704 return NULL;
705 }
706
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000707 self = (PyDateTime_DateTime *) (type->tp_alloc(type, aware));
708 if (self != NULL) {
709 self->hastzinfo = aware;
710 set_date_fields((PyDateTime_Date *)self, year, month, day);
711 DATE_SET_HOUR(self, hour);
712 DATE_SET_MINUTE(self, minute);
713 DATE_SET_SECOND(self, second);
714 DATE_SET_MICROSECOND(self, usecond);
715 if (aware) {
716 Py_INCREF(tzinfo);
717 self->tzinfo = tzinfo;
718 }
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -0400719 DATE_SET_FOLD(self, fold);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000720 }
721 return (PyObject *)self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000722}
723
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -0400724static PyObject *
725new_datetime_ex(int year, int month, int day, int hour, int minute,
726 int second, int usecond, PyObject *tzinfo, PyTypeObject *type)
727{
728 return new_datetime_ex2(year, month, day, hour, minute, second, usecond,
729 tzinfo, 0, type);
730}
731
732#define new_datetime(y, m, d, hh, mm, ss, us, tzinfo, fold) \
733 new_datetime_ex2(y, m, d, hh, mm, ss, us, tzinfo, fold, \
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000734 &PyDateTime_DateTimeType)
Tim Petersb0c854d2003-05-17 15:57:00 +0000735
736/* Create a time instance with no range checking. */
737static PyObject *
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -0400738new_time_ex2(int hour, int minute, int second, int usecond,
739 PyObject *tzinfo, int fold, PyTypeObject *type)
Tim Petersb0c854d2003-05-17 15:57:00 +0000740{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000741 PyDateTime_Time *self;
742 char aware = tzinfo != Py_None;
Tim Petersb0c854d2003-05-17 15:57:00 +0000743
Victor Stinnerb67f0962017-02-10 10:34:02 +0100744 if (check_time_args(hour, minute, second, usecond, fold) < 0) {
745 return NULL;
746 }
747 if (check_tzinfo_subclass(tzinfo) < 0) {
748 return NULL;
749 }
750
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000751 self = (PyDateTime_Time *) (type->tp_alloc(type, aware));
752 if (self != NULL) {
753 self->hastzinfo = aware;
754 self->hashcode = -1;
755 TIME_SET_HOUR(self, hour);
756 TIME_SET_MINUTE(self, minute);
757 TIME_SET_SECOND(self, second);
758 TIME_SET_MICROSECOND(self, usecond);
759 if (aware) {
760 Py_INCREF(tzinfo);
761 self->tzinfo = tzinfo;
762 }
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -0400763 TIME_SET_FOLD(self, fold);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000764 }
765 return (PyObject *)self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000766}
767
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -0400768static PyObject *
769new_time_ex(int hour, int minute, int second, int usecond,
770 PyObject *tzinfo, PyTypeObject *type)
771{
772 return new_time_ex2(hour, minute, second, usecond, tzinfo, 0, type);
773}
774
775#define new_time(hh, mm, ss, us, tzinfo, fold) \
776 new_time_ex2(hh, mm, ss, us, tzinfo, fold, &PyDateTime_TimeType)
Tim Petersb0c854d2003-05-17 15:57:00 +0000777
778/* Create a timedelta instance. Normalize the members iff normalize is
779 * true. Passing false is a speed optimization, if you know for sure
780 * that seconds and microseconds are already in their proper ranges. In any
781 * case, raises OverflowError and returns NULL if the normalized days is out
782 * of range).
783 */
784static PyObject *
785new_delta_ex(int days, int seconds, int microseconds, int normalize,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000786 PyTypeObject *type)
Tim Petersb0c854d2003-05-17 15:57:00 +0000787{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000788 PyDateTime_Delta *self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000789
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000790 if (normalize)
791 normalize_d_s_us(&days, &seconds, &microseconds);
792 assert(0 <= seconds && seconds < 24*3600);
793 assert(0 <= microseconds && microseconds < 1000000);
Tim Petersb0c854d2003-05-17 15:57:00 +0000794
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000795 if (check_delta_day_range(days) < 0)
796 return NULL;
Tim Petersb0c854d2003-05-17 15:57:00 +0000797
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000798 self = (PyDateTime_Delta *) (type->tp_alloc(type, 0));
799 if (self != NULL) {
800 self->hashcode = -1;
801 SET_TD_DAYS(self, days);
802 SET_TD_SECONDS(self, seconds);
803 SET_TD_MICROSECONDS(self, microseconds);
804 }
805 return (PyObject *) self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000806}
807
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000808#define new_delta(d, s, us, normalize) \
809 new_delta_ex(d, s, us, normalize, &PyDateTime_DeltaType)
Tim Petersb0c854d2003-05-17 15:57:00 +0000810
Alexander Belopolsky4e749a12010-06-14 14:15:50 +0000811
812typedef struct
813{
814 PyObject_HEAD
815 PyObject *offset;
816 PyObject *name;
817} PyDateTime_TimeZone;
818
Victor Stinner6ced7c42011-03-21 18:15:42 +0100819/* The interned UTC timezone instance */
Alexander Belopolsky1bcbaab2010-10-14 17:03:51 +0000820static PyObject *PyDateTime_TimeZone_UTC;
Alexander Belopolskya4415142012-06-08 12:33:09 -0400821/* The interned Epoch datetime instance */
822static PyObject *PyDateTime_Epoch;
Alexander Belopolskya11d8c02010-07-06 23:19:45 +0000823
Alexander Belopolsky4e749a12010-06-14 14:15:50 +0000824/* Create new timezone instance checking offset range. This
825 function does not check the name argument. Caller must assure
826 that offset is a timedelta instance and name is either NULL
827 or a unicode object. */
828static PyObject *
Alexander Belopolsky1bcbaab2010-10-14 17:03:51 +0000829create_timezone(PyObject *offset, PyObject *name)
Alexander Belopolsky4e749a12010-06-14 14:15:50 +0000830{
831 PyDateTime_TimeZone *self;
832 PyTypeObject *type = &PyDateTime_TimeZoneType;
833
834 assert(offset != NULL);
835 assert(PyDelta_Check(offset));
836 assert(name == NULL || PyUnicode_Check(name));
837
Alexander Belopolsky1bcbaab2010-10-14 17:03:51 +0000838 self = (PyDateTime_TimeZone *)(type->tp_alloc(type, 0));
839 if (self == NULL) {
840 return NULL;
841 }
842 Py_INCREF(offset);
843 self->offset = offset;
844 Py_XINCREF(name);
845 self->name = name;
846 return (PyObject *)self;
847}
848
849static int delta_bool(PyDateTime_Delta *self);
850
851static PyObject *
852new_timezone(PyObject *offset, PyObject *name)
853{
854 assert(offset != NULL);
855 assert(PyDelta_Check(offset));
856 assert(name == NULL || PyUnicode_Check(name));
857
858 if (name == NULL && delta_bool((PyDateTime_Delta *)offset) == 0) {
859 Py_INCREF(PyDateTime_TimeZone_UTC);
860 return PyDateTime_TimeZone_UTC;
861 }
Alexander Belopolsky4e749a12010-06-14 14:15:50 +0000862 if ((GET_TD_DAYS(offset) == -1 && GET_TD_SECONDS(offset) == 0) ||
863 GET_TD_DAYS(offset) < -1 || GET_TD_DAYS(offset) >= 1) {
864 PyErr_Format(PyExc_ValueError, "offset must be a timedelta"
865 " strictly between -timedelta(hours=24) and"
Alexander Belopolsky31227ca2012-06-22 13:23:21 -0400866 " timedelta(hours=24),"
867 " not %R.", offset);
Alexander Belopolsky4e749a12010-06-14 14:15:50 +0000868 return NULL;
869 }
870
Alexander Belopolsky1bcbaab2010-10-14 17:03:51 +0000871 return create_timezone(offset, name);
Alexander Belopolsky4e749a12010-06-14 14:15:50 +0000872}
873
Tim Petersb0c854d2003-05-17 15:57:00 +0000874/* ---------------------------------------------------------------------------
Tim Peters2a799bf2002-12-16 20:18:38 +0000875 * tzinfo helpers.
876 */
877
Tim Peters855fe882002-12-22 03:43:39 +0000878/* Ensure that p is None or of a tzinfo subclass. Return 0 if OK; if not
879 * raise TypeError and return -1.
880 */
881static int
882check_tzinfo_subclass(PyObject *p)
883{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000884 if (p == Py_None || PyTZInfo_Check(p))
885 return 0;
886 PyErr_Format(PyExc_TypeError,
887 "tzinfo argument must be None or of a tzinfo subclass, "
888 "not type '%s'",
889 Py_TYPE(p)->tp_name);
890 return -1;
Tim Peters855fe882002-12-22 03:43:39 +0000891}
892
Tim Peters2a799bf2002-12-16 20:18:38 +0000893/* If self has a tzinfo member, return a BORROWED reference to it. Else
894 * return NULL, which is NOT AN ERROR. There are no error returns here,
895 * and the caller must not decref the result.
896 */
897static PyObject *
898get_tzinfo_member(PyObject *self)
899{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000900 PyObject *tzinfo = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +0000901
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000902 if (PyDateTime_Check(self) && HASTZINFO(self))
903 tzinfo = ((PyDateTime_DateTime *)self)->tzinfo;
904 else if (PyTime_Check(self) && HASTZINFO(self))
905 tzinfo = ((PyDateTime_Time *)self)->tzinfo;
Tim Peters2a799bf2002-12-16 20:18:38 +0000906
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000907 return tzinfo;
Tim Peters2a799bf2002-12-16 20:18:38 +0000908}
909
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000910/* Call getattr(tzinfo, name)(tzinfoarg), and check the result. tzinfo must
911 * be an instance of the tzinfo class. If the method returns None, this
912 * returns None. If the method doesn't return None or timedelta, TypeError is
913 * raised and this returns NULL. If it returns a timedelta and the value is
914 * out of range or isn't a whole number of minutes, ValueError is raised and
915 * this returns NULL. Else result is returned.
Tim Peters2a799bf2002-12-16 20:18:38 +0000916 */
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000917static PyObject *
Serhiy Storchakaef1585e2015-12-25 20:01:53 +0200918call_tzinfo_method(PyObject *tzinfo, const char *name, PyObject *tzinfoarg)
Tim Peters2a799bf2002-12-16 20:18:38 +0000919{
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000920 PyObject *offset;
Tim Peters2a799bf2002-12-16 20:18:38 +0000921
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000922 assert(tzinfo != NULL);
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000923 assert(PyTZInfo_Check(tzinfo) || tzinfo == Py_None);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000924 assert(tzinfoarg != NULL);
Tim Peters2a799bf2002-12-16 20:18:38 +0000925
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000926 if (tzinfo == Py_None)
927 Py_RETURN_NONE;
928 offset = PyObject_CallMethod(tzinfo, name, "O", tzinfoarg);
929 if (offset == Py_None || offset == NULL)
930 return offset;
931 if (PyDelta_Check(offset)) {
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000932 if ((GET_TD_DAYS(offset) == -1 && GET_TD_SECONDS(offset) == 0) ||
933 GET_TD_DAYS(offset) < -1 || GET_TD_DAYS(offset) >= 1) {
934 Py_DECREF(offset);
935 PyErr_Format(PyExc_ValueError, "offset must be a timedelta"
936 " strictly between -timedelta(hours=24) and"
937 " timedelta(hours=24).");
938 return NULL;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000939 }
940 }
941 else {
942 PyErr_Format(PyExc_TypeError,
943 "tzinfo.%s() must return None or "
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000944 "timedelta, not '%.200s'",
945 name, Py_TYPE(offset)->tp_name);
Raymond Hettinger5a2146a2014-07-25 14:59:48 -0700946 Py_DECREF(offset);
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000947 return NULL;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000948 }
Tim Peters2a799bf2002-12-16 20:18:38 +0000949
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000950 return offset;
Tim Peters2a799bf2002-12-16 20:18:38 +0000951}
952
953/* Call tzinfo.utcoffset(tzinfoarg), and extract an integer from the
954 * result. tzinfo must be an instance of the tzinfo class. If utcoffset()
955 * returns None, call_utcoffset returns 0 and sets *none to 1. If uctoffset()
Tim Peters397301e2003-01-02 21:28:08 +0000956 * doesn't return None or timedelta, TypeError is raised and this returns -1.
Alexander Belopolsky018d3532017-07-31 10:26:50 -0400957 * If utcoffset() returns an out of range timedelta,
958 * ValueError is raised and this returns -1. Else *none is
959 * set to 0 and the offset is returned (as timedelta, positive east of UTC).
Tim Peters2a799bf2002-12-16 20:18:38 +0000960 */
Tim Peters855fe882002-12-22 03:43:39 +0000961static PyObject *
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000962call_utcoffset(PyObject *tzinfo, PyObject *tzinfoarg)
963{
964 return call_tzinfo_method(tzinfo, "utcoffset", tzinfoarg);
Tim Peters855fe882002-12-22 03:43:39 +0000965}
966
Tim Peters2a799bf2002-12-16 20:18:38 +0000967/* Call tzinfo.dst(tzinfoarg), and extract an integer from the
968 * result. tzinfo must be an instance of the tzinfo class. If dst()
969 * returns None, call_dst returns 0 and sets *none to 1. If dst()
Alexander Belopolsky018d3532017-07-31 10:26:50 -0400970 * doesn't return None or timedelta, TypeError is raised and this
Walter Dörwaldf0dfc7a2003-10-20 14:01:56 +0000971 * returns -1. If dst() returns an invalid timedelta for a UTC offset,
Tim Peters397301e2003-01-02 21:28:08 +0000972 * ValueError is raised and this returns -1. Else *none is set to 0 and
Alexander Belopolsky018d3532017-07-31 10:26:50 -0400973 * the offset is returned (as timedelta, positive east of UTC).
Tim Peters2a799bf2002-12-16 20:18:38 +0000974 */
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000975static PyObject *
976call_dst(PyObject *tzinfo, PyObject *tzinfoarg)
Tim Peters2a799bf2002-12-16 20:18:38 +0000977{
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000978 return call_tzinfo_method(tzinfo, "dst", tzinfoarg);
Tim Peters2a799bf2002-12-16 20:18:38 +0000979}
980
Tim Petersbad8ff02002-12-30 20:52:32 +0000981/* Call tzinfo.tzname(tzinfoarg), and return the result. tzinfo must be
Tim Peters855fe882002-12-22 03:43:39 +0000982 * an instance of the tzinfo class or None. If tzinfo isn't None, and
Tim Petersbad8ff02002-12-30 20:52:32 +0000983 * tzname() doesn't return None or a string, TypeError is raised and this
Guido van Rossume3d1d412007-05-23 21:24:35 +0000984 * returns NULL. If the result is a string, we ensure it is a Unicode
985 * string.
Tim Peters2a799bf2002-12-16 20:18:38 +0000986 */
987static PyObject *
Tim Petersbad8ff02002-12-30 20:52:32 +0000988call_tzname(PyObject *tzinfo, PyObject *tzinfoarg)
Tim Peters2a799bf2002-12-16 20:18:38 +0000989{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000990 PyObject *result;
Martin v. Löwisbd928fe2011-10-14 10:20:37 +0200991 _Py_IDENTIFIER(tzname);
Tim Peters2a799bf2002-12-16 20:18:38 +0000992
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000993 assert(tzinfo != NULL);
994 assert(check_tzinfo_subclass(tzinfo) >= 0);
995 assert(tzinfoarg != NULL);
Tim Peters2a799bf2002-12-16 20:18:38 +0000996
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000997 if (tzinfo == Py_None)
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000998 Py_RETURN_NONE;
Tim Peters2a799bf2002-12-16 20:18:38 +0000999
Victor Stinner20401de2016-12-09 15:24:31 +01001000 result = _PyObject_CallMethodIdObjArgs(tzinfo, &PyId_tzname,
1001 tzinfoarg, NULL);
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001002
1003 if (result == NULL || result == Py_None)
1004 return result;
1005
1006 if (!PyUnicode_Check(result)) {
1007 PyErr_Format(PyExc_TypeError, "tzinfo.tzname() must "
1008 "return None or a string, not '%s'",
1009 Py_TYPE(result)->tp_name);
1010 Py_DECREF(result);
1011 result = NULL;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001012 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001013
1014 return result;
Tim Peters00237032002-12-27 02:21:51 +00001015}
1016
Tim Peters2a799bf2002-12-16 20:18:38 +00001017/* repr is like "someclass(arg1, arg2)". If tzinfo isn't None,
1018 * stuff
1019 * ", tzinfo=" + repr(tzinfo)
1020 * before the closing ")".
1021 */
1022static PyObject *
1023append_keyword_tzinfo(PyObject *repr, PyObject *tzinfo)
1024{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001025 PyObject *temp;
Tim Peters2a799bf2002-12-16 20:18:38 +00001026
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001027 assert(PyUnicode_Check(repr));
1028 assert(tzinfo);
1029 if (tzinfo == Py_None)
1030 return repr;
1031 /* Get rid of the trailing ')'. */
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02001032 assert(PyUnicode_READ_CHAR(repr, PyUnicode_GET_LENGTH(repr)-1) == ')');
1033 temp = PyUnicode_Substring(repr, 0, PyUnicode_GET_LENGTH(repr) - 1);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001034 Py_DECREF(repr);
1035 if (temp == NULL)
1036 return NULL;
1037 repr = PyUnicode_FromFormat("%U, tzinfo=%R)", temp, tzinfo);
1038 Py_DECREF(temp);
1039 return repr;
Tim Peters2a799bf2002-12-16 20:18:38 +00001040}
1041
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04001042/* repr is like "someclass(arg1, arg2)". If fold isn't 0,
1043 * stuff
1044 * ", fold=" + repr(tzinfo)
1045 * before the closing ")".
1046 */
1047static PyObject *
1048append_keyword_fold(PyObject *repr, int fold)
1049{
1050 PyObject *temp;
1051
1052 assert(PyUnicode_Check(repr));
1053 if (fold == 0)
1054 return repr;
1055 /* Get rid of the trailing ')'. */
1056 assert(PyUnicode_READ_CHAR(repr, PyUnicode_GET_LENGTH(repr)-1) == ')');
1057 temp = PyUnicode_Substring(repr, 0, PyUnicode_GET_LENGTH(repr) - 1);
1058 Py_DECREF(repr);
1059 if (temp == NULL)
1060 return NULL;
1061 repr = PyUnicode_FromFormat("%U, fold=%d)", temp, fold);
1062 Py_DECREF(temp);
1063 return repr;
1064}
1065
Tim Peters2a799bf2002-12-16 20:18:38 +00001066/* ---------------------------------------------------------------------------
1067 * String format helpers.
1068 */
1069
1070static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00001071format_ctime(PyDateTime_Date *date, int hours, int minutes, int seconds)
Tim Peters2a799bf2002-12-16 20:18:38 +00001072{
Serhiy Storchaka2d06e842015-12-25 19:53:18 +02001073 static const char * const DayNames[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001074 "Mon", "Tue", "Wed", "Thu", "Fri", "Sat", "Sun"
1075 };
Serhiy Storchaka2d06e842015-12-25 19:53:18 +02001076 static const char * const MonthNames[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001077 "Jan", "Feb", "Mar", "Apr", "May", "Jun",
1078 "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"
1079 };
Tim Peters2a799bf2002-12-16 20:18:38 +00001080
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001081 int wday = weekday(GET_YEAR(date), GET_MONTH(date), GET_DAY(date));
Tim Peters2a799bf2002-12-16 20:18:38 +00001082
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001083 return PyUnicode_FromFormat("%s %s %2d %02d:%02d:%02d %04d",
1084 DayNames[wday], MonthNames[GET_MONTH(date)-1],
1085 GET_DAY(date), hours, minutes, seconds,
1086 GET_YEAR(date));
Tim Peters2a799bf2002-12-16 20:18:38 +00001087}
1088
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001089static PyObject *delta_negative(PyDateTime_Delta *self);
1090
Alexander Belopolsky018d3532017-07-31 10:26:50 -04001091/* Add formatted UTC offset string to buf. buf has no more than
Tim Peters2a799bf2002-12-16 20:18:38 +00001092 * buflen bytes remaining. The UTC offset is gotten by calling
1093 * tzinfo.uctoffset(tzinfoarg). If that returns None, \0 is stored into
1094 * *buf, and that's all. Else the returned value is checked for sanity (an
1095 * integer in range), and if that's OK it's converted to an hours & minutes
1096 * string of the form
Alexander Belopolsky018d3532017-07-31 10:26:50 -04001097 * sign HH sep MM [sep SS [. UUUUUU]]
Tim Peters2a799bf2002-12-16 20:18:38 +00001098 * Returns 0 if everything is OK. If the return value from utcoffset() is
1099 * bogus, an appropriate exception is set and -1 is returned.
1100 */
1101static int
Tim Peters328fff72002-12-20 01:31:27 +00001102format_utcoffset(char *buf, size_t buflen, const char *sep,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001103 PyObject *tzinfo, PyObject *tzinfoarg)
Tim Peters2a799bf2002-12-16 20:18:38 +00001104{
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001105 PyObject *offset;
Alexander Belopolsky018d3532017-07-31 10:26:50 -04001106 int hours, minutes, seconds, microseconds;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001107 char sign;
Tim Peters2a799bf2002-12-16 20:18:38 +00001108
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001109 assert(buflen >= 1);
Amaury Forgeot d'Arc9c74b142008-06-18 00:47:36 +00001110
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001111 offset = call_utcoffset(tzinfo, tzinfoarg);
1112 if (offset == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001113 return -1;
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001114 if (offset == Py_None) {
1115 Py_DECREF(offset);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001116 *buf = '\0';
1117 return 0;
1118 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001119 /* Offset is normalized, so it is negative if days < 0 */
1120 if (GET_TD_DAYS(offset) < 0) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001121 sign = '-';
Serhiy Storchakaf01e4082016-04-10 18:12:01 +03001122 Py_SETREF(offset, delta_negative((PyDateTime_Delta *)offset));
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001123 if (offset == NULL)
1124 return -1;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001125 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001126 else {
1127 sign = '+';
1128 }
1129 /* Offset is not negative here. */
Alexander Belopolsky018d3532017-07-31 10:26:50 -04001130 microseconds = GET_TD_MICROSECONDS(offset);
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001131 seconds = GET_TD_SECONDS(offset);
1132 Py_DECREF(offset);
1133 minutes = divmod(seconds, 60, &seconds);
1134 hours = divmod(minutes, 60, &minutes);
Alexander Belopolsky018d3532017-07-31 10:26:50 -04001135 if (microseconds) {
1136 PyOS_snprintf(buf, buflen, "%c%02d%s%02d%s%02d.%06d", sign,
1137 hours, sep, minutes, sep, seconds, microseconds);
1138 return 0;
1139 }
1140 if (seconds) {
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04001141 PyOS_snprintf(buf, buflen, "%c%02d%s%02d%s%02d", sign, hours,
1142 sep, minutes, sep, seconds);
Alexander Belopolsky018d3532017-07-31 10:26:50 -04001143 return 0;
1144 }
1145 PyOS_snprintf(buf, buflen, "%c%02d%s%02d", sign, hours, sep, minutes);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001146 return 0;
Tim Peters2a799bf2002-12-16 20:18:38 +00001147}
1148
Guido van Rossumd8595fe2007-05-23 21:36:49 +00001149static PyObject *
1150make_Zreplacement(PyObject *object, PyObject *tzinfoarg)
1151{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001152 PyObject *temp;
1153 PyObject *tzinfo = get_tzinfo_member(object);
1154 PyObject *Zreplacement = PyUnicode_FromStringAndSize(NULL, 0);
Martin v. Löwisbd928fe2011-10-14 10:20:37 +02001155 _Py_IDENTIFIER(replace);
Victor Stinner9e30aa52011-11-21 02:49:52 +01001156
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001157 if (Zreplacement == NULL)
1158 return NULL;
1159 if (tzinfo == Py_None || tzinfo == NULL)
1160 return Zreplacement;
Neal Norwitzaea70e02007-08-12 04:32:26 +00001161
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001162 assert(tzinfoarg != NULL);
1163 temp = call_tzname(tzinfo, tzinfoarg);
1164 if (temp == NULL)
1165 goto Error;
1166 if (temp == Py_None) {
1167 Py_DECREF(temp);
1168 return Zreplacement;
1169 }
Neal Norwitzaea70e02007-08-12 04:32:26 +00001170
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001171 assert(PyUnicode_Check(temp));
1172 /* Since the tzname is getting stuffed into the
1173 * format, we have to double any % signs so that
1174 * strftime doesn't treat them as format codes.
1175 */
1176 Py_DECREF(Zreplacement);
Martin v. Löwisafe55bb2011-10-09 10:38:36 +02001177 Zreplacement = _PyObject_CallMethodId(temp, &PyId_replace, "ss", "%", "%%");
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001178 Py_DECREF(temp);
1179 if (Zreplacement == NULL)
1180 return NULL;
1181 if (!PyUnicode_Check(Zreplacement)) {
1182 PyErr_SetString(PyExc_TypeError,
1183 "tzname.replace() did not return a string");
1184 goto Error;
1185 }
1186 return Zreplacement;
Guido van Rossumd8595fe2007-05-23 21:36:49 +00001187
1188 Error:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001189 Py_DECREF(Zreplacement);
1190 return NULL;
Guido van Rossumd8595fe2007-05-23 21:36:49 +00001191}
1192
Christian Heimesdd15f6c2008-03-16 00:07:10 +00001193static PyObject *
1194make_freplacement(PyObject *object)
1195{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001196 char freplacement[64];
1197 if (PyTime_Check(object))
1198 sprintf(freplacement, "%06d", TIME_GET_MICROSECOND(object));
1199 else if (PyDateTime_Check(object))
1200 sprintf(freplacement, "%06d", DATE_GET_MICROSECOND(object));
1201 else
1202 sprintf(freplacement, "%06d", 0);
Christian Heimesdd15f6c2008-03-16 00:07:10 +00001203
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001204 return PyBytes_FromStringAndSize(freplacement, strlen(freplacement));
Christian Heimesdd15f6c2008-03-16 00:07:10 +00001205}
1206
Tim Peters2a799bf2002-12-16 20:18:38 +00001207/* I sure don't want to reproduce the strftime code from the time module,
1208 * so this imports the module and calls it. All the hair is due to
Christian Heimesdd15f6c2008-03-16 00:07:10 +00001209 * giving special meanings to the %z, %Z and %f format codes via a
1210 * preprocessing step on the format string.
Tim Petersbad8ff02002-12-30 20:52:32 +00001211 * tzinfoarg is the argument to pass to the object's tzinfo method, if
1212 * needed.
Tim Peters2a799bf2002-12-16 20:18:38 +00001213 */
1214static PyObject *
Tim Petersbad8ff02002-12-30 20:52:32 +00001215wrap_strftime(PyObject *object, PyObject *format, PyObject *timetuple,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001216 PyObject *tzinfoarg)
Tim Peters2a799bf2002-12-16 20:18:38 +00001217{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001218 PyObject *result = NULL; /* guilty until proved innocent */
Tim Peters2a799bf2002-12-16 20:18:38 +00001219
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001220 PyObject *zreplacement = NULL; /* py string, replacement for %z */
1221 PyObject *Zreplacement = NULL; /* py string, replacement for %Z */
1222 PyObject *freplacement = NULL; /* py string, replacement for %f */
Tim Peters2a799bf2002-12-16 20:18:38 +00001223
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001224 const char *pin; /* pointer to next char in input format */
1225 Py_ssize_t flen; /* length of input format */
1226 char ch; /* next char in input format */
Tim Peters2a799bf2002-12-16 20:18:38 +00001227
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001228 PyObject *newfmt = NULL; /* py string, the output format */
1229 char *pnew; /* pointer to available byte in output format */
1230 size_t totalnew; /* number bytes total in output format buffer,
1231 exclusive of trailing \0 */
1232 size_t usednew; /* number bytes used so far in output format buffer */
Tim Peters2a799bf2002-12-16 20:18:38 +00001233
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001234 const char *ptoappend; /* ptr to string to append to output buffer */
1235 Py_ssize_t ntoappend; /* # of bytes to append to output buffer */
Tim Peters2a799bf2002-12-16 20:18:38 +00001236
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001237 assert(object && format && timetuple);
1238 assert(PyUnicode_Check(format));
1239 /* Convert the input format to a C string and size */
Serhiy Storchaka06515832016-11-20 09:13:07 +02001240 pin = PyUnicode_AsUTF8AndSize(format, &flen);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001241 if (!pin)
1242 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001243
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001244 /* Scan the input format, looking for %z/%Z/%f escapes, building
1245 * a new format. Since computing the replacements for those codes
1246 * is expensive, don't unless they're actually used.
1247 */
1248 if (flen > INT_MAX - 1) {
1249 PyErr_NoMemory();
1250 goto Done;
1251 }
Amaury Forgeot d'Arc9c74b142008-06-18 00:47:36 +00001252
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001253 totalnew = flen + 1; /* realistic if no %z/%Z */
1254 newfmt = PyBytes_FromStringAndSize(NULL, totalnew);
1255 if (newfmt == NULL) goto Done;
1256 pnew = PyBytes_AsString(newfmt);
1257 usednew = 0;
Tim Peters2a799bf2002-12-16 20:18:38 +00001258
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001259 while ((ch = *pin++) != '\0') {
1260 if (ch != '%') {
1261 ptoappend = pin - 1;
1262 ntoappend = 1;
1263 }
1264 else if ((ch = *pin++) == '\0') {
1265 /* There's a lone trailing %; doesn't make sense. */
1266 PyErr_SetString(PyExc_ValueError, "strftime format "
1267 "ends with raw %");
1268 goto Done;
1269 }
1270 /* A % has been seen and ch is the character after it. */
1271 else if (ch == 'z') {
1272 if (zreplacement == NULL) {
1273 /* format utcoffset */
1274 char buf[100];
1275 PyObject *tzinfo = get_tzinfo_member(object);
1276 zreplacement = PyBytes_FromStringAndSize("", 0);
1277 if (zreplacement == NULL) goto Done;
1278 if (tzinfo != Py_None && tzinfo != NULL) {
1279 assert(tzinfoarg != NULL);
1280 if (format_utcoffset(buf,
1281 sizeof(buf),
1282 "",
1283 tzinfo,
1284 tzinfoarg) < 0)
1285 goto Done;
1286 Py_DECREF(zreplacement);
1287 zreplacement =
1288 PyBytes_FromStringAndSize(buf,
1289 strlen(buf));
1290 if (zreplacement == NULL)
1291 goto Done;
1292 }
1293 }
1294 assert(zreplacement != NULL);
1295 ptoappend = PyBytes_AS_STRING(zreplacement);
1296 ntoappend = PyBytes_GET_SIZE(zreplacement);
1297 }
1298 else if (ch == 'Z') {
1299 /* format tzname */
1300 if (Zreplacement == NULL) {
1301 Zreplacement = make_Zreplacement(object,
1302 tzinfoarg);
1303 if (Zreplacement == NULL)
1304 goto Done;
1305 }
1306 assert(Zreplacement != NULL);
1307 assert(PyUnicode_Check(Zreplacement));
Serhiy Storchaka06515832016-11-20 09:13:07 +02001308 ptoappend = PyUnicode_AsUTF8AndSize(Zreplacement,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001309 &ntoappend);
Alexander Belopolskye239d232010-12-08 23:31:48 +00001310 if (ptoappend == NULL)
1311 goto Done;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001312 }
1313 else if (ch == 'f') {
1314 /* format microseconds */
1315 if (freplacement == NULL) {
1316 freplacement = make_freplacement(object);
1317 if (freplacement == NULL)
1318 goto Done;
1319 }
1320 assert(freplacement != NULL);
1321 assert(PyBytes_Check(freplacement));
1322 ptoappend = PyBytes_AS_STRING(freplacement);
1323 ntoappend = PyBytes_GET_SIZE(freplacement);
1324 }
1325 else {
1326 /* percent followed by neither z nor Z */
1327 ptoappend = pin - 2;
1328 ntoappend = 2;
1329 }
Tim Peters2a799bf2002-12-16 20:18:38 +00001330
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001331 /* Append the ntoappend chars starting at ptoappend to
1332 * the new format.
1333 */
1334 if (ntoappend == 0)
1335 continue;
1336 assert(ptoappend != NULL);
1337 assert(ntoappend > 0);
1338 while (usednew + ntoappend > totalnew) {
Mark Dickinsonc04ddff2012-10-06 18:04:49 +01001339 if (totalnew > (PY_SSIZE_T_MAX >> 1)) { /* overflow */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001340 PyErr_NoMemory();
1341 goto Done;
1342 }
Mark Dickinsonc04ddff2012-10-06 18:04:49 +01001343 totalnew <<= 1;
1344 if (_PyBytes_Resize(&newfmt, totalnew) < 0)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001345 goto Done;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001346 pnew = PyBytes_AsString(newfmt) + usednew;
1347 }
1348 memcpy(pnew, ptoappend, ntoappend);
1349 pnew += ntoappend;
1350 usednew += ntoappend;
1351 assert(usednew <= totalnew);
1352 } /* end while() */
Tim Peters2a799bf2002-12-16 20:18:38 +00001353
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001354 if (_PyBytes_Resize(&newfmt, usednew) < 0)
1355 goto Done;
1356 {
1357 PyObject *format;
1358 PyObject *time = PyImport_ImportModuleNoBlock("time");
Martin v. Löwisafe55bb2011-10-09 10:38:36 +02001359
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001360 if (time == NULL)
1361 goto Done;
1362 format = PyUnicode_FromString(PyBytes_AS_STRING(newfmt));
1363 if (format != NULL) {
Victor Stinner20401de2016-12-09 15:24:31 +01001364 result = _PyObject_CallMethodIdObjArgs(time, &PyId_strftime,
1365 format, timetuple, NULL);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001366 Py_DECREF(format);
1367 }
1368 Py_DECREF(time);
1369 }
Tim Peters2a799bf2002-12-16 20:18:38 +00001370 Done:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001371 Py_XDECREF(freplacement);
1372 Py_XDECREF(zreplacement);
1373 Py_XDECREF(Zreplacement);
1374 Py_XDECREF(newfmt);
1375 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001376}
1377
Tim Peters2a799bf2002-12-16 20:18:38 +00001378/* ---------------------------------------------------------------------------
1379 * Wrap functions from the time module. These aren't directly available
1380 * from C. Perhaps they should be.
1381 */
1382
1383/* Call time.time() and return its result (a Python float). */
1384static PyObject *
Guido van Rossumbd43e912002-12-16 20:34:55 +00001385time_time(void)
Tim Peters2a799bf2002-12-16 20:18:38 +00001386{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001387 PyObject *result = NULL;
1388 PyObject *time = PyImport_ImportModuleNoBlock("time");
Tim Peters2a799bf2002-12-16 20:18:38 +00001389
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001390 if (time != NULL) {
Martin v. Löwisbd928fe2011-10-14 10:20:37 +02001391 _Py_IDENTIFIER(time);
Martin v. Löwisafe55bb2011-10-09 10:38:36 +02001392
Victor Stinnerad8c83a2016-09-05 17:53:15 -07001393 result = _PyObject_CallMethodId(time, &PyId_time, NULL);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001394 Py_DECREF(time);
1395 }
1396 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001397}
1398
1399/* Build a time.struct_time. The weekday and day number are automatically
1400 * computed from the y,m,d args.
1401 */
1402static PyObject *
1403build_struct_time(int y, int m, int d, int hh, int mm, int ss, int dstflag)
1404{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001405 PyObject *time;
Victor Stinner2b635972016-12-09 00:38:16 +01001406 PyObject *result;
1407 _Py_IDENTIFIER(struct_time);
1408 PyObject *args;
1409
Tim Peters2a799bf2002-12-16 20:18:38 +00001410
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001411 time = PyImport_ImportModuleNoBlock("time");
Victor Stinner2b635972016-12-09 00:38:16 +01001412 if (time == NULL) {
1413 return NULL;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001414 }
Victor Stinner2b635972016-12-09 00:38:16 +01001415
1416 args = Py_BuildValue("iiiiiiiii",
1417 y, m, d,
1418 hh, mm, ss,
1419 weekday(y, m, d),
1420 days_before_month(y, m) + d,
1421 dstflag);
1422 if (args == NULL) {
1423 Py_DECREF(time);
1424 return NULL;
1425 }
1426
1427 result = _PyObject_CallMethodIdObjArgs(time, &PyId_struct_time,
1428 args, NULL);
1429 Py_DECREF(time);
Victor Stinnerddc120f2016-12-09 15:35:40 +01001430 Py_DECREF(args);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001431 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001432}
1433
1434/* ---------------------------------------------------------------------------
1435 * Miscellaneous helpers.
1436 */
1437
Mark Dickinsone94c6792009-02-02 20:36:42 +00001438/* For various reasons, we need to use tp_richcompare instead of tp_reserved.
Tim Peters2a799bf2002-12-16 20:18:38 +00001439 * The comparisons here all most naturally compute a cmp()-like result.
1440 * This little helper turns that into a bool result for rich comparisons.
1441 */
1442static PyObject *
1443diff_to_bool(int diff, int op)
1444{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001445 PyObject *result;
1446 int istrue;
Tim Peters2a799bf2002-12-16 20:18:38 +00001447
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001448 switch (op) {
1449 case Py_EQ: istrue = diff == 0; break;
1450 case Py_NE: istrue = diff != 0; break;
1451 case Py_LE: istrue = diff <= 0; break;
1452 case Py_GE: istrue = diff >= 0; break;
1453 case Py_LT: istrue = diff < 0; break;
1454 case Py_GT: istrue = diff > 0; break;
1455 default:
Barry Warsawb2e57942017-09-14 18:13:16 -07001456 Py_UNREACHABLE();
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001457 }
1458 result = istrue ? Py_True : Py_False;
1459 Py_INCREF(result);
1460 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001461}
1462
Tim Peters07534a62003-02-07 22:50:28 +00001463/* Raises a "can't compare" TypeError and returns NULL. */
1464static PyObject *
1465cmperror(PyObject *a, PyObject *b)
1466{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001467 PyErr_Format(PyExc_TypeError,
1468 "can't compare %s to %s",
1469 Py_TYPE(a)->tp_name, Py_TYPE(b)->tp_name);
1470 return NULL;
Tim Peters07534a62003-02-07 22:50:28 +00001471}
1472
Tim Peters2a799bf2002-12-16 20:18:38 +00001473/* ---------------------------------------------------------------------------
Tim Peters2a799bf2002-12-16 20:18:38 +00001474 * Cached Python objects; these are set by the module init function.
1475 */
1476
1477/* Conversion factors. */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001478static PyObject *us_per_ms = NULL; /* 1000 */
1479static PyObject *us_per_second = NULL; /* 1000000 */
1480static PyObject *us_per_minute = NULL; /* 1e6 * 60 as Python int */
Serhiy Storchaka95949422013-08-27 19:40:23 +03001481static PyObject *us_per_hour = NULL; /* 1e6 * 3600 as Python int */
1482static PyObject *us_per_day = NULL; /* 1e6 * 3600 * 24 as Python int */
1483static PyObject *us_per_week = NULL; /* 1e6*3600*24*7 as Python int */
Tim Peters2a799bf2002-12-16 20:18:38 +00001484static PyObject *seconds_per_day = NULL; /* 3600*24 as Python int */
1485
Tim Peters2a799bf2002-12-16 20:18:38 +00001486/* ---------------------------------------------------------------------------
1487 * Class implementations.
1488 */
1489
1490/*
1491 * PyDateTime_Delta implementation.
1492 */
1493
1494/* Convert a timedelta to a number of us,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001495 * (24*3600*self.days + self.seconds)*1000000 + self.microseconds
Serhiy Storchaka95949422013-08-27 19:40:23 +03001496 * as a Python int.
Tim Peters2a799bf2002-12-16 20:18:38 +00001497 * Doing mixed-radix arithmetic by hand instead is excruciating in C,
1498 * due to ubiquitous overflow possibilities.
1499 */
1500static PyObject *
1501delta_to_microseconds(PyDateTime_Delta *self)
1502{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001503 PyObject *x1 = NULL;
1504 PyObject *x2 = NULL;
1505 PyObject *x3 = NULL;
1506 PyObject *result = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001507
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001508 x1 = PyLong_FromLong(GET_TD_DAYS(self));
1509 if (x1 == NULL)
1510 goto Done;
1511 x2 = PyNumber_Multiply(x1, seconds_per_day); /* days in seconds */
1512 if (x2 == NULL)
1513 goto Done;
1514 Py_DECREF(x1);
1515 x1 = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001516
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001517 /* x2 has days in seconds */
1518 x1 = PyLong_FromLong(GET_TD_SECONDS(self)); /* seconds */
1519 if (x1 == NULL)
1520 goto Done;
1521 x3 = PyNumber_Add(x1, x2); /* days and seconds in seconds */
1522 if (x3 == NULL)
1523 goto Done;
1524 Py_DECREF(x1);
1525 Py_DECREF(x2);
Brett Cannonb94767f2011-02-22 20:15:44 +00001526 /* x1 = */ x2 = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001527
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001528 /* x3 has days+seconds in seconds */
1529 x1 = PyNumber_Multiply(x3, us_per_second); /* us */
1530 if (x1 == NULL)
1531 goto Done;
1532 Py_DECREF(x3);
1533 x3 = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001534
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001535 /* x1 has days+seconds in us */
1536 x2 = PyLong_FromLong(GET_TD_MICROSECONDS(self));
1537 if (x2 == NULL)
1538 goto Done;
1539 result = PyNumber_Add(x1, x2);
Serhiy Storchaka4ffd4652017-10-23 17:12:28 +03001540 assert(result == NULL || PyLong_CheckExact(result));
Tim Peters2a799bf2002-12-16 20:18:38 +00001541
1542Done:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001543 Py_XDECREF(x1);
1544 Py_XDECREF(x2);
1545 Py_XDECREF(x3);
1546 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001547}
1548
Serhiy Storchaka95949422013-08-27 19:40:23 +03001549/* Convert a number of us (as a Python int) to a timedelta.
Tim Peters2a799bf2002-12-16 20:18:38 +00001550 */
1551static PyObject *
Tim Petersb0c854d2003-05-17 15:57:00 +00001552microseconds_to_delta_ex(PyObject *pyus, PyTypeObject *type)
Tim Peters2a799bf2002-12-16 20:18:38 +00001553{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001554 int us;
1555 int s;
1556 int d;
1557 long temp;
Tim Peters2a799bf2002-12-16 20:18:38 +00001558
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001559 PyObject *tuple = NULL;
1560 PyObject *num = NULL;
1561 PyObject *result = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001562
Serhiy Storchaka4ffd4652017-10-23 17:12:28 +03001563 assert(PyLong_CheckExact(pyus));
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001564 tuple = PyNumber_Divmod(pyus, us_per_second);
1565 if (tuple == NULL)
1566 goto Done;
Tim Peters2a799bf2002-12-16 20:18:38 +00001567
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001568 num = PyTuple_GetItem(tuple, 1); /* us */
1569 if (num == NULL)
1570 goto Done;
1571 temp = PyLong_AsLong(num);
1572 num = NULL;
1573 if (temp == -1 && PyErr_Occurred())
1574 goto Done;
1575 assert(0 <= temp && temp < 1000000);
1576 us = (int)temp;
1577 if (us < 0) {
1578 /* The divisor was positive, so this must be an error. */
1579 assert(PyErr_Occurred());
1580 goto Done;
1581 }
Tim Peters2a799bf2002-12-16 20:18:38 +00001582
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001583 num = PyTuple_GetItem(tuple, 0); /* leftover seconds */
1584 if (num == NULL)
1585 goto Done;
1586 Py_INCREF(num);
1587 Py_DECREF(tuple);
Tim Peters2a799bf2002-12-16 20:18:38 +00001588
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001589 tuple = PyNumber_Divmod(num, seconds_per_day);
1590 if (tuple == NULL)
1591 goto Done;
1592 Py_DECREF(num);
Tim Peters2a799bf2002-12-16 20:18:38 +00001593
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001594 num = PyTuple_GetItem(tuple, 1); /* seconds */
1595 if (num == NULL)
1596 goto Done;
1597 temp = PyLong_AsLong(num);
1598 num = NULL;
1599 if (temp == -1 && PyErr_Occurred())
1600 goto Done;
1601 assert(0 <= temp && temp < 24*3600);
1602 s = (int)temp;
Tim Peters0b0f41c2002-12-19 01:44:38 +00001603
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001604 if (s < 0) {
1605 /* The divisor was positive, so this must be an error. */
1606 assert(PyErr_Occurred());
1607 goto Done;
1608 }
Tim Peters2a799bf2002-12-16 20:18:38 +00001609
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001610 num = PyTuple_GetItem(tuple, 0); /* leftover days */
1611 if (num == NULL)
1612 goto Done;
1613 Py_INCREF(num);
1614 temp = PyLong_AsLong(num);
1615 if (temp == -1 && PyErr_Occurred())
1616 goto Done;
1617 d = (int)temp;
1618 if ((long)d != temp) {
1619 PyErr_SetString(PyExc_OverflowError, "normalized days too "
1620 "large to fit in a C int");
1621 goto Done;
1622 }
1623 result = new_delta_ex(d, s, us, 0, type);
Tim Peters2a799bf2002-12-16 20:18:38 +00001624
1625Done:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001626 Py_XDECREF(tuple);
1627 Py_XDECREF(num);
1628 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001629}
1630
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001631#define microseconds_to_delta(pymicros) \
1632 microseconds_to_delta_ex(pymicros, &PyDateTime_DeltaType)
Tim Petersb0c854d2003-05-17 15:57:00 +00001633
Tim Peters2a799bf2002-12-16 20:18:38 +00001634static PyObject *
1635multiply_int_timedelta(PyObject *intobj, PyDateTime_Delta *delta)
1636{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001637 PyObject *pyus_in;
1638 PyObject *pyus_out;
1639 PyObject *result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001640
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001641 pyus_in = delta_to_microseconds(delta);
1642 if (pyus_in == NULL)
1643 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001644
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001645 pyus_out = PyNumber_Multiply(pyus_in, intobj);
1646 Py_DECREF(pyus_in);
1647 if (pyus_out == NULL)
1648 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001649
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001650 result = microseconds_to_delta(pyus_out);
1651 Py_DECREF(pyus_out);
1652 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001653}
1654
1655static PyObject *
Oren Milman865e4b42017-09-19 15:58:11 +03001656get_float_as_integer_ratio(PyObject *floatobj)
1657{
1658 PyObject *ratio;
1659
1660 assert(floatobj && PyFloat_Check(floatobj));
1661 ratio = _PyObject_CallMethodId(floatobj, &PyId_as_integer_ratio, NULL);
1662 if (ratio == NULL) {
1663 return NULL;
1664 }
1665 if (!PyTuple_Check(ratio)) {
1666 PyErr_Format(PyExc_TypeError,
1667 "unexpected return type from as_integer_ratio(): "
1668 "expected tuple, got '%.200s'",
1669 Py_TYPE(ratio)->tp_name);
1670 Py_DECREF(ratio);
1671 return NULL;
1672 }
1673 if (PyTuple_Size(ratio) != 2) {
1674 PyErr_SetString(PyExc_ValueError,
1675 "as_integer_ratio() must return a 2-tuple");
1676 Py_DECREF(ratio);
1677 return NULL;
1678 }
1679 return ratio;
1680}
1681
Serhiy Storchakadb12ef72017-10-04 20:30:09 +03001682/* op is 0 for multiplication, 1 for division */
Oren Milman865e4b42017-09-19 15:58:11 +03001683static PyObject *
Serhiy Storchakadb12ef72017-10-04 20:30:09 +03001684multiply_truedivide_timedelta_float(PyDateTime_Delta *delta, PyObject *floatobj, int op)
Alexander Belopolsky1790bc42010-05-31 17:33:47 +00001685{
1686 PyObject *result = NULL;
1687 PyObject *pyus_in = NULL, *temp, *pyus_out;
1688 PyObject *ratio = NULL;
1689
1690 pyus_in = delta_to_microseconds(delta);
1691 if (pyus_in == NULL)
1692 return NULL;
Oren Milman865e4b42017-09-19 15:58:11 +03001693 ratio = get_float_as_integer_ratio(floatobj);
1694 if (ratio == NULL) {
Alexander Belopolsky1790bc42010-05-31 17:33:47 +00001695 goto error;
Oren Milman865e4b42017-09-19 15:58:11 +03001696 }
Serhiy Storchakadb12ef72017-10-04 20:30:09 +03001697 temp = PyNumber_Multiply(pyus_in, PyTuple_GET_ITEM(ratio, op));
Alexander Belopolsky1790bc42010-05-31 17:33:47 +00001698 Py_DECREF(pyus_in);
1699 pyus_in = NULL;
1700 if (temp == NULL)
1701 goto error;
Serhiy Storchakadb12ef72017-10-04 20:30:09 +03001702 pyus_out = divide_nearest(temp, PyTuple_GET_ITEM(ratio, !op));
Alexander Belopolsky1790bc42010-05-31 17:33:47 +00001703 Py_DECREF(temp);
1704 if (pyus_out == NULL)
1705 goto error;
1706 result = microseconds_to_delta(pyus_out);
1707 Py_DECREF(pyus_out);
1708 error:
1709 Py_XDECREF(pyus_in);
1710 Py_XDECREF(ratio);
1711
1712 return result;
1713}
1714
1715static PyObject *
Tim Peters2a799bf2002-12-16 20:18:38 +00001716divide_timedelta_int(PyDateTime_Delta *delta, PyObject *intobj)
1717{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001718 PyObject *pyus_in;
1719 PyObject *pyus_out;
1720 PyObject *result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001721
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001722 pyus_in = delta_to_microseconds(delta);
1723 if (pyus_in == NULL)
1724 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001725
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001726 pyus_out = PyNumber_FloorDivide(pyus_in, intobj);
1727 Py_DECREF(pyus_in);
1728 if (pyus_out == NULL)
1729 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001730
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001731 result = microseconds_to_delta(pyus_out);
1732 Py_DECREF(pyus_out);
1733 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001734}
1735
1736static PyObject *
Mark Dickinson7c186e22010-04-20 22:32:49 +00001737divide_timedelta_timedelta(PyDateTime_Delta *left, PyDateTime_Delta *right)
1738{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001739 PyObject *pyus_left;
1740 PyObject *pyus_right;
1741 PyObject *result;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001742
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001743 pyus_left = delta_to_microseconds(left);
1744 if (pyus_left == NULL)
1745 return NULL;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001746
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001747 pyus_right = delta_to_microseconds(right);
1748 if (pyus_right == NULL) {
1749 Py_DECREF(pyus_left);
1750 return NULL;
1751 }
Mark Dickinson7c186e22010-04-20 22:32:49 +00001752
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001753 result = PyNumber_FloorDivide(pyus_left, pyus_right);
1754 Py_DECREF(pyus_left);
1755 Py_DECREF(pyus_right);
1756 return result;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001757}
1758
1759static PyObject *
1760truedivide_timedelta_timedelta(PyDateTime_Delta *left, PyDateTime_Delta *right)
1761{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001762 PyObject *pyus_left;
1763 PyObject *pyus_right;
1764 PyObject *result;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001765
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001766 pyus_left = delta_to_microseconds(left);
1767 if (pyus_left == NULL)
1768 return NULL;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001769
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001770 pyus_right = delta_to_microseconds(right);
1771 if (pyus_right == NULL) {
1772 Py_DECREF(pyus_left);
1773 return NULL;
1774 }
Mark Dickinson7c186e22010-04-20 22:32:49 +00001775
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001776 result = PyNumber_TrueDivide(pyus_left, pyus_right);
1777 Py_DECREF(pyus_left);
1778 Py_DECREF(pyus_right);
1779 return result;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001780}
1781
1782static PyObject *
Alexander Belopolsky1790bc42010-05-31 17:33:47 +00001783truedivide_timedelta_int(PyDateTime_Delta *delta, PyObject *i)
1784{
1785 PyObject *result;
1786 PyObject *pyus_in, *pyus_out;
1787 pyus_in = delta_to_microseconds(delta);
1788 if (pyus_in == NULL)
1789 return NULL;
1790 pyus_out = divide_nearest(pyus_in, i);
1791 Py_DECREF(pyus_in);
1792 if (pyus_out == NULL)
1793 return NULL;
1794 result = microseconds_to_delta(pyus_out);
1795 Py_DECREF(pyus_out);
1796
1797 return result;
1798}
1799
1800static PyObject *
Tim Peters2a799bf2002-12-16 20:18:38 +00001801delta_add(PyObject *left, PyObject *right)
1802{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001803 PyObject *result = Py_NotImplemented;
Tim Peters2a799bf2002-12-16 20:18:38 +00001804
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001805 if (PyDelta_Check(left) && PyDelta_Check(right)) {
1806 /* delta + delta */
1807 /* The C-level additions can't overflow because of the
1808 * invariant bounds.
1809 */
1810 int days = GET_TD_DAYS(left) + GET_TD_DAYS(right);
1811 int seconds = GET_TD_SECONDS(left) + GET_TD_SECONDS(right);
1812 int microseconds = GET_TD_MICROSECONDS(left) +
1813 GET_TD_MICROSECONDS(right);
1814 result = new_delta(days, seconds, microseconds, 1);
1815 }
Tim Peters2a799bf2002-12-16 20:18:38 +00001816
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001817 if (result == Py_NotImplemented)
1818 Py_INCREF(result);
1819 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001820}
1821
1822static PyObject *
1823delta_negative(PyDateTime_Delta *self)
1824{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001825 return new_delta(-GET_TD_DAYS(self),
1826 -GET_TD_SECONDS(self),
1827 -GET_TD_MICROSECONDS(self),
1828 1);
Tim Peters2a799bf2002-12-16 20:18:38 +00001829}
1830
1831static PyObject *
1832delta_positive(PyDateTime_Delta *self)
1833{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001834 /* Could optimize this (by returning self) if this isn't a
1835 * subclass -- but who uses unary + ? Approximately nobody.
1836 */
1837 return new_delta(GET_TD_DAYS(self),
1838 GET_TD_SECONDS(self),
1839 GET_TD_MICROSECONDS(self),
1840 0);
Tim Peters2a799bf2002-12-16 20:18:38 +00001841}
1842
1843static PyObject *
1844delta_abs(PyDateTime_Delta *self)
1845{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001846 PyObject *result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001847
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001848 assert(GET_TD_MICROSECONDS(self) >= 0);
1849 assert(GET_TD_SECONDS(self) >= 0);
Tim Peters2a799bf2002-12-16 20:18:38 +00001850
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001851 if (GET_TD_DAYS(self) < 0)
1852 result = delta_negative(self);
1853 else
1854 result = delta_positive(self);
Tim Peters2a799bf2002-12-16 20:18:38 +00001855
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001856 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001857}
1858
1859static PyObject *
1860delta_subtract(PyObject *left, PyObject *right)
1861{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001862 PyObject *result = Py_NotImplemented;
Tim Peters2a799bf2002-12-16 20:18:38 +00001863
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001864 if (PyDelta_Check(left) && PyDelta_Check(right)) {
1865 /* delta - delta */
Alexander Belopolskyb6f5ec72011-04-05 20:07:38 -04001866 /* The C-level additions can't overflow because of the
1867 * invariant bounds.
1868 */
1869 int days = GET_TD_DAYS(left) - GET_TD_DAYS(right);
1870 int seconds = GET_TD_SECONDS(left) - GET_TD_SECONDS(right);
1871 int microseconds = GET_TD_MICROSECONDS(left) -
1872 GET_TD_MICROSECONDS(right);
1873 result = new_delta(days, seconds, microseconds, 1);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001874 }
Tim Peters2a799bf2002-12-16 20:18:38 +00001875
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001876 if (result == Py_NotImplemented)
1877 Py_INCREF(result);
1878 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001879}
1880
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001881static int
1882delta_cmp(PyObject *self, PyObject *other)
1883{
1884 int diff = GET_TD_DAYS(self) - GET_TD_DAYS(other);
1885 if (diff == 0) {
1886 diff = GET_TD_SECONDS(self) - GET_TD_SECONDS(other);
1887 if (diff == 0)
1888 diff = GET_TD_MICROSECONDS(self) -
1889 GET_TD_MICROSECONDS(other);
1890 }
1891 return diff;
1892}
1893
Tim Peters2a799bf2002-12-16 20:18:38 +00001894static PyObject *
Guido van Rossum19960592006-08-24 17:29:38 +00001895delta_richcompare(PyObject *self, PyObject *other, int op)
Tim Peters2a799bf2002-12-16 20:18:38 +00001896{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001897 if (PyDelta_Check(other)) {
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001898 int diff = delta_cmp(self, other);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001899 return diff_to_bool(diff, op);
1900 }
1901 else {
Brian Curtindfc80e32011-08-10 20:28:54 -05001902 Py_RETURN_NOTIMPLEMENTED;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001903 }
Tim Peters2a799bf2002-12-16 20:18:38 +00001904}
1905
1906static PyObject *delta_getstate(PyDateTime_Delta *self);
1907
Benjamin Peterson8f67d082010-10-17 20:54:53 +00001908static Py_hash_t
Tim Peters2a799bf2002-12-16 20:18:38 +00001909delta_hash(PyDateTime_Delta *self)
1910{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001911 if (self->hashcode == -1) {
1912 PyObject *temp = delta_getstate(self);
1913 if (temp != NULL) {
1914 self->hashcode = PyObject_Hash(temp);
1915 Py_DECREF(temp);
1916 }
1917 }
1918 return self->hashcode;
Tim Peters2a799bf2002-12-16 20:18:38 +00001919}
1920
1921static PyObject *
1922delta_multiply(PyObject *left, PyObject *right)
1923{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001924 PyObject *result = Py_NotImplemented;
Tim Peters2a799bf2002-12-16 20:18:38 +00001925
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001926 if (PyDelta_Check(left)) {
1927 /* delta * ??? */
1928 if (PyLong_Check(right))
1929 result = multiply_int_timedelta(right,
1930 (PyDateTime_Delta *) left);
Alexander Belopolsky1790bc42010-05-31 17:33:47 +00001931 else if (PyFloat_Check(right))
Serhiy Storchakadb12ef72017-10-04 20:30:09 +03001932 result = multiply_truedivide_timedelta_float(
1933 (PyDateTime_Delta *) left, right, 0);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001934 }
1935 else if (PyLong_Check(left))
1936 result = multiply_int_timedelta(left,
Alexander Belopolsky1790bc42010-05-31 17:33:47 +00001937 (PyDateTime_Delta *) right);
1938 else if (PyFloat_Check(left))
Serhiy Storchakadb12ef72017-10-04 20:30:09 +03001939 result = multiply_truedivide_timedelta_float(
1940 (PyDateTime_Delta *) right, left, 0);
Tim Peters2a799bf2002-12-16 20:18:38 +00001941
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001942 if (result == Py_NotImplemented)
1943 Py_INCREF(result);
1944 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001945}
1946
1947static PyObject *
1948delta_divide(PyObject *left, PyObject *right)
1949{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001950 PyObject *result = Py_NotImplemented;
Tim Peters2a799bf2002-12-16 20:18:38 +00001951
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001952 if (PyDelta_Check(left)) {
1953 /* delta * ??? */
1954 if (PyLong_Check(right))
1955 result = divide_timedelta_int(
1956 (PyDateTime_Delta *)left,
1957 right);
1958 else if (PyDelta_Check(right))
1959 result = divide_timedelta_timedelta(
1960 (PyDateTime_Delta *)left,
1961 (PyDateTime_Delta *)right);
1962 }
Tim Peters2a799bf2002-12-16 20:18:38 +00001963
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001964 if (result == Py_NotImplemented)
1965 Py_INCREF(result);
1966 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001967}
1968
Mark Dickinson7c186e22010-04-20 22:32:49 +00001969static PyObject *
1970delta_truedivide(PyObject *left, PyObject *right)
1971{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001972 PyObject *result = Py_NotImplemented;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001973
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001974 if (PyDelta_Check(left)) {
1975 if (PyDelta_Check(right))
1976 result = truedivide_timedelta_timedelta(
1977 (PyDateTime_Delta *)left,
1978 (PyDateTime_Delta *)right);
Alexander Belopolsky1790bc42010-05-31 17:33:47 +00001979 else if (PyFloat_Check(right))
Serhiy Storchakadb12ef72017-10-04 20:30:09 +03001980 result = multiply_truedivide_timedelta_float(
1981 (PyDateTime_Delta *)left, right, 1);
Alexander Belopolsky1790bc42010-05-31 17:33:47 +00001982 else if (PyLong_Check(right))
1983 result = truedivide_timedelta_int(
1984 (PyDateTime_Delta *)left, right);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001985 }
Mark Dickinson7c186e22010-04-20 22:32:49 +00001986
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001987 if (result == Py_NotImplemented)
1988 Py_INCREF(result);
1989 return result;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001990}
1991
1992static PyObject *
1993delta_remainder(PyObject *left, PyObject *right)
1994{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001995 PyObject *pyus_left;
1996 PyObject *pyus_right;
1997 PyObject *pyus_remainder;
1998 PyObject *remainder;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001999
Brian Curtindfc80e32011-08-10 20:28:54 -05002000 if (!PyDelta_Check(left) || !PyDelta_Check(right))
2001 Py_RETURN_NOTIMPLEMENTED;
Mark Dickinson7c186e22010-04-20 22:32:49 +00002002
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002003 pyus_left = delta_to_microseconds((PyDateTime_Delta *)left);
2004 if (pyus_left == NULL)
2005 return NULL;
Mark Dickinson7c186e22010-04-20 22:32:49 +00002006
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002007 pyus_right = delta_to_microseconds((PyDateTime_Delta *)right);
2008 if (pyus_right == NULL) {
2009 Py_DECREF(pyus_left);
2010 return NULL;
2011 }
Mark Dickinson7c186e22010-04-20 22:32:49 +00002012
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002013 pyus_remainder = PyNumber_Remainder(pyus_left, pyus_right);
2014 Py_DECREF(pyus_left);
2015 Py_DECREF(pyus_right);
2016 if (pyus_remainder == NULL)
2017 return NULL;
Mark Dickinson7c186e22010-04-20 22:32:49 +00002018
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002019 remainder = microseconds_to_delta(pyus_remainder);
2020 Py_DECREF(pyus_remainder);
2021 if (remainder == NULL)
2022 return NULL;
Mark Dickinson7c186e22010-04-20 22:32:49 +00002023
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002024 return remainder;
Mark Dickinson7c186e22010-04-20 22:32:49 +00002025}
2026
2027static PyObject *
2028delta_divmod(PyObject *left, PyObject *right)
2029{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002030 PyObject *pyus_left;
2031 PyObject *pyus_right;
2032 PyObject *divmod;
2033 PyObject *delta;
2034 PyObject *result;
Mark Dickinson7c186e22010-04-20 22:32:49 +00002035
Brian Curtindfc80e32011-08-10 20:28:54 -05002036 if (!PyDelta_Check(left) || !PyDelta_Check(right))
2037 Py_RETURN_NOTIMPLEMENTED;
Mark Dickinson7c186e22010-04-20 22:32:49 +00002038
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002039 pyus_left = delta_to_microseconds((PyDateTime_Delta *)left);
2040 if (pyus_left == NULL)
2041 return NULL;
Mark Dickinson7c186e22010-04-20 22:32:49 +00002042
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002043 pyus_right = delta_to_microseconds((PyDateTime_Delta *)right);
2044 if (pyus_right == NULL) {
2045 Py_DECREF(pyus_left);
2046 return NULL;
2047 }
Mark Dickinson7c186e22010-04-20 22:32:49 +00002048
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002049 divmod = PyNumber_Divmod(pyus_left, pyus_right);
2050 Py_DECREF(pyus_left);
2051 Py_DECREF(pyus_right);
2052 if (divmod == NULL)
2053 return NULL;
Mark Dickinson7c186e22010-04-20 22:32:49 +00002054
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002055 assert(PyTuple_Size(divmod) == 2);
2056 delta = microseconds_to_delta(PyTuple_GET_ITEM(divmod, 1));
2057 if (delta == NULL) {
2058 Py_DECREF(divmod);
2059 return NULL;
2060 }
2061 result = PyTuple_Pack(2, PyTuple_GET_ITEM(divmod, 0), delta);
2062 Py_DECREF(delta);
2063 Py_DECREF(divmod);
2064 return result;
Mark Dickinson7c186e22010-04-20 22:32:49 +00002065}
2066
Tim Peters2a799bf2002-12-16 20:18:38 +00002067/* Fold in the value of the tag ("seconds", "weeks", etc) component of a
2068 * timedelta constructor. sofar is the # of microseconds accounted for
2069 * so far, and there are factor microseconds per current unit, the number
2070 * of which is given by num. num * factor is added to sofar in a
2071 * numerically careful way, and that's the result. Any fractional
2072 * microseconds left over (this can happen if num is a float type) are
2073 * added into *leftover.
2074 * Note that there are many ways this can give an error (NULL) return.
2075 */
2076static PyObject *
2077accum(const char* tag, PyObject *sofar, PyObject *num, PyObject *factor,
2078 double *leftover)
2079{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002080 PyObject *prod;
2081 PyObject *sum;
Tim Peters2a799bf2002-12-16 20:18:38 +00002082
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002083 assert(num != NULL);
Tim Peters2a799bf2002-12-16 20:18:38 +00002084
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002085 if (PyLong_Check(num)) {
Serhiy Storchaka4ffd4652017-10-23 17:12:28 +03002086 prod = PyNumber_Multiply(factor, num);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002087 if (prod == NULL)
2088 return NULL;
Serhiy Storchaka4ffd4652017-10-23 17:12:28 +03002089 assert(PyLong_CheckExact(prod));
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002090 sum = PyNumber_Add(sofar, prod);
2091 Py_DECREF(prod);
Serhiy Storchaka4ffd4652017-10-23 17:12:28 +03002092 assert(sum == NULL || PyLong_CheckExact(sum));
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002093 return sum;
2094 }
Tim Peters2a799bf2002-12-16 20:18:38 +00002095
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002096 if (PyFloat_Check(num)) {
2097 double dnum;
2098 double fracpart;
2099 double intpart;
2100 PyObject *x;
2101 PyObject *y;
Tim Peters2a799bf2002-12-16 20:18:38 +00002102
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002103 /* The Plan: decompose num into an integer part and a
2104 * fractional part, num = intpart + fracpart.
2105 * Then num * factor ==
2106 * intpart * factor + fracpart * factor
2107 * and the LHS can be computed exactly in long arithmetic.
2108 * The RHS is again broken into an int part and frac part.
2109 * and the frac part is added into *leftover.
2110 */
2111 dnum = PyFloat_AsDouble(num);
2112 if (dnum == -1.0 && PyErr_Occurred())
2113 return NULL;
2114 fracpart = modf(dnum, &intpart);
2115 x = PyLong_FromDouble(intpart);
2116 if (x == NULL)
2117 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002118
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002119 prod = PyNumber_Multiply(x, factor);
2120 Py_DECREF(x);
2121 if (prod == NULL)
2122 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002123
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002124 sum = PyNumber_Add(sofar, prod);
2125 Py_DECREF(prod);
2126 if (sum == NULL)
2127 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002128
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002129 if (fracpart == 0.0)
2130 return sum;
2131 /* So far we've lost no information. Dealing with the
2132 * fractional part requires float arithmetic, and may
2133 * lose a little info.
2134 */
Serhiy Storchaka4ffd4652017-10-23 17:12:28 +03002135 assert(PyLong_CheckExact(factor));
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002136 dnum = PyLong_AsDouble(factor);
Tim Peters2a799bf2002-12-16 20:18:38 +00002137
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002138 dnum *= fracpart;
2139 fracpart = modf(dnum, &intpart);
2140 x = PyLong_FromDouble(intpart);
2141 if (x == NULL) {
2142 Py_DECREF(sum);
2143 return NULL;
2144 }
Tim Peters2a799bf2002-12-16 20:18:38 +00002145
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002146 y = PyNumber_Add(sum, x);
2147 Py_DECREF(sum);
2148 Py_DECREF(x);
2149 *leftover += fracpart;
Serhiy Storchaka4ffd4652017-10-23 17:12:28 +03002150 assert(y == NULL || PyLong_CheckExact(y));
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002151 return y;
2152 }
Tim Peters2a799bf2002-12-16 20:18:38 +00002153
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002154 PyErr_Format(PyExc_TypeError,
2155 "unsupported type for timedelta %s component: %s",
2156 tag, Py_TYPE(num)->tp_name);
2157 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002158}
2159
2160static PyObject *
2161delta_new(PyTypeObject *type, PyObject *args, PyObject *kw)
2162{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002163 PyObject *self = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002164
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002165 /* Argument objects. */
2166 PyObject *day = NULL;
2167 PyObject *second = NULL;
2168 PyObject *us = NULL;
2169 PyObject *ms = NULL;
2170 PyObject *minute = NULL;
2171 PyObject *hour = NULL;
2172 PyObject *week = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002173
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002174 PyObject *x = NULL; /* running sum of microseconds */
2175 PyObject *y = NULL; /* temp sum of microseconds */
2176 double leftover_us = 0.0;
Tim Peters2a799bf2002-12-16 20:18:38 +00002177
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002178 static char *keywords[] = {
2179 "days", "seconds", "microseconds", "milliseconds",
2180 "minutes", "hours", "weeks", NULL
2181 };
Tim Peters2a799bf2002-12-16 20:18:38 +00002182
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002183 if (PyArg_ParseTupleAndKeywords(args, kw, "|OOOOOOO:__new__",
2184 keywords,
2185 &day, &second, &us,
2186 &ms, &minute, &hour, &week) == 0)
2187 goto Done;
Tim Peters2a799bf2002-12-16 20:18:38 +00002188
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002189 x = PyLong_FromLong(0);
2190 if (x == NULL)
2191 goto Done;
Tim Peters2a799bf2002-12-16 20:18:38 +00002192
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002193#define CLEANUP \
2194 Py_DECREF(x); \
2195 x = y; \
2196 if (x == NULL) \
2197 goto Done
Tim Peters2a799bf2002-12-16 20:18:38 +00002198
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002199 if (us) {
Serhiy Storchakaba85d692017-03-30 09:09:41 +03002200 y = accum("microseconds", x, us, _PyLong_One, &leftover_us);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002201 CLEANUP;
2202 }
2203 if (ms) {
2204 y = accum("milliseconds", x, ms, us_per_ms, &leftover_us);
2205 CLEANUP;
2206 }
2207 if (second) {
2208 y = accum("seconds", x, second, us_per_second, &leftover_us);
2209 CLEANUP;
2210 }
2211 if (minute) {
2212 y = accum("minutes", x, minute, us_per_minute, &leftover_us);
2213 CLEANUP;
2214 }
2215 if (hour) {
2216 y = accum("hours", x, hour, us_per_hour, &leftover_us);
2217 CLEANUP;
2218 }
2219 if (day) {
2220 y = accum("days", x, day, us_per_day, &leftover_us);
2221 CLEANUP;
2222 }
2223 if (week) {
2224 y = accum("weeks", x, week, us_per_week, &leftover_us);
2225 CLEANUP;
2226 }
2227 if (leftover_us) {
2228 /* Round to nearest whole # of us, and add into x. */
Alexander Belopolsky790d2692013-08-04 14:51:35 -04002229 double whole_us = round(leftover_us);
Victor Stinner69cc4872015-09-08 23:58:54 +02002230 int x_is_odd;
Alexander Belopolsky790d2692013-08-04 14:51:35 -04002231 PyObject *temp;
2232
Victor Stinner69cc4872015-09-08 23:58:54 +02002233 whole_us = round(leftover_us);
2234 if (fabs(whole_us - leftover_us) == 0.5) {
2235 /* We're exactly halfway between two integers. In order
2236 * to do round-half-to-even, we must determine whether x
2237 * is odd. Note that x is odd when it's last bit is 1. The
2238 * code below uses bitwise and operation to check the last
2239 * bit. */
Serhiy Storchakaba85d692017-03-30 09:09:41 +03002240 temp = PyNumber_And(x, _PyLong_One); /* temp <- x & 1 */
Victor Stinner69cc4872015-09-08 23:58:54 +02002241 if (temp == NULL) {
2242 Py_DECREF(x);
2243 goto Done;
2244 }
2245 x_is_odd = PyObject_IsTrue(temp);
2246 Py_DECREF(temp);
2247 if (x_is_odd == -1) {
2248 Py_DECREF(x);
2249 goto Done;
2250 }
2251 whole_us = 2.0 * round((leftover_us + x_is_odd) * 0.5) - x_is_odd;
2252 }
Alexander Belopolsky790d2692013-08-04 14:51:35 -04002253
Victor Stinner36a5a062013-08-28 01:53:39 +02002254 temp = PyLong_FromLong((long)whole_us);
Alexander Belopolsky790d2692013-08-04 14:51:35 -04002255
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002256 if (temp == NULL) {
2257 Py_DECREF(x);
2258 goto Done;
2259 }
2260 y = PyNumber_Add(x, temp);
2261 Py_DECREF(temp);
2262 CLEANUP;
2263 }
Tim Peters2a799bf2002-12-16 20:18:38 +00002264
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002265 self = microseconds_to_delta_ex(x, type);
2266 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00002267Done:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002268 return self;
Tim Peters2a799bf2002-12-16 20:18:38 +00002269
2270#undef CLEANUP
2271}
2272
2273static int
Jack Diederich4dafcc42006-11-28 19:15:13 +00002274delta_bool(PyDateTime_Delta *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00002275{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002276 return (GET_TD_DAYS(self) != 0
2277 || GET_TD_SECONDS(self) != 0
2278 || GET_TD_MICROSECONDS(self) != 0);
Tim Peters2a799bf2002-12-16 20:18:38 +00002279}
2280
2281static PyObject *
2282delta_repr(PyDateTime_Delta *self)
2283{
Utkarsh Upadhyaycc5a65c2017-07-25 23:51:33 +02002284 PyObject *args = PyUnicode_FromString("");
Tim Peters2a799bf2002-12-16 20:18:38 +00002285
Utkarsh Upadhyaycc5a65c2017-07-25 23:51:33 +02002286 if (args == NULL) {
2287 return NULL;
2288 }
2289
2290 const char *sep = "";
2291
2292 if (GET_TD_DAYS(self) != 0) {
2293 Py_SETREF(args, PyUnicode_FromFormat("days=%d", GET_TD_DAYS(self)));
2294 if (args == NULL) {
2295 return NULL;
2296 }
2297 sep = ", ";
2298 }
2299
2300 if (GET_TD_SECONDS(self) != 0) {
2301 Py_SETREF(args, PyUnicode_FromFormat("%U%sseconds=%d", args, sep,
2302 GET_TD_SECONDS(self)));
2303 if (args == NULL) {
2304 return NULL;
2305 }
2306 sep = ", ";
2307 }
2308
2309 if (GET_TD_MICROSECONDS(self) != 0) {
2310 Py_SETREF(args, PyUnicode_FromFormat("%U%smicroseconds=%d", args, sep,
2311 GET_TD_MICROSECONDS(self)));
2312 if (args == NULL) {
2313 return NULL;
2314 }
2315 }
2316
2317 if (PyUnicode_GET_LENGTH(args) == 0) {
2318 Py_SETREF(args, PyUnicode_FromString("0"));
2319 if (args == NULL) {
2320 return NULL;
2321 }
2322 }
2323
2324 PyObject *repr = PyUnicode_FromFormat("%s(%S)", Py_TYPE(self)->tp_name,
2325 args);
2326 Py_DECREF(args);
2327 return repr;
Tim Peters2a799bf2002-12-16 20:18:38 +00002328}
2329
2330static PyObject *
2331delta_str(PyDateTime_Delta *self)
2332{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002333 int us = GET_TD_MICROSECONDS(self);
2334 int seconds = GET_TD_SECONDS(self);
2335 int minutes = divmod(seconds, 60, &seconds);
2336 int hours = divmod(minutes, 60, &minutes);
2337 int days = GET_TD_DAYS(self);
Tim Peters2a799bf2002-12-16 20:18:38 +00002338
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002339 if (days) {
2340 if (us)
2341 return PyUnicode_FromFormat("%d day%s, %d:%02d:%02d.%06d",
2342 days, (days == 1 || days == -1) ? "" : "s",
2343 hours, minutes, seconds, us);
2344 else
2345 return PyUnicode_FromFormat("%d day%s, %d:%02d:%02d",
2346 days, (days == 1 || days == -1) ? "" : "s",
2347 hours, minutes, seconds);
2348 } else {
2349 if (us)
2350 return PyUnicode_FromFormat("%d:%02d:%02d.%06d",
2351 hours, minutes, seconds, us);
2352 else
2353 return PyUnicode_FromFormat("%d:%02d:%02d",
2354 hours, minutes, seconds);
2355 }
Tim Peters2a799bf2002-12-16 20:18:38 +00002356
Tim Peters2a799bf2002-12-16 20:18:38 +00002357}
2358
Tim Peters371935f2003-02-01 01:52:50 +00002359/* Pickle support, a simple use of __reduce__. */
2360
Tim Petersb57f8f02003-02-01 02:54:15 +00002361/* __getstate__ isn't exposed */
Tim Peters2a799bf2002-12-16 20:18:38 +00002362static PyObject *
2363delta_getstate(PyDateTime_Delta *self)
2364{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002365 return Py_BuildValue("iii", GET_TD_DAYS(self),
2366 GET_TD_SECONDS(self),
2367 GET_TD_MICROSECONDS(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002368}
2369
Tim Peters2a799bf2002-12-16 20:18:38 +00002370static PyObject *
Antoine Pitroube6859d2009-11-25 23:02:32 +00002371delta_total_seconds(PyObject *self)
2372{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002373 PyObject *total_seconds;
2374 PyObject *total_microseconds;
Mark Dickinson0381e3f2010-05-08 14:35:02 +00002375
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002376 total_microseconds = delta_to_microseconds((PyDateTime_Delta *)self);
2377 if (total_microseconds == NULL)
2378 return NULL;
Mark Dickinson0381e3f2010-05-08 14:35:02 +00002379
Alexander Belopolskydf7027b2013-08-04 15:18:58 -04002380 total_seconds = PyNumber_TrueDivide(total_microseconds, us_per_second);
Mark Dickinson0381e3f2010-05-08 14:35:02 +00002381
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002382 Py_DECREF(total_microseconds);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002383 return total_seconds;
Antoine Pitroube6859d2009-11-25 23:02:32 +00002384}
2385
2386static PyObject *
Tim Peters2a799bf2002-12-16 20:18:38 +00002387delta_reduce(PyDateTime_Delta* self)
2388{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002389 return Py_BuildValue("ON", Py_TYPE(self), delta_getstate(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002390}
2391
2392#define OFFSET(field) offsetof(PyDateTime_Delta, field)
2393
2394static PyMemberDef delta_members[] = {
Guido van Rossum177e41a2003-01-30 22:06:23 +00002395
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002396 {"days", T_INT, OFFSET(days), READONLY,
2397 PyDoc_STR("Number of days.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002398
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002399 {"seconds", T_INT, OFFSET(seconds), READONLY,
2400 PyDoc_STR("Number of seconds (>= 0 and less than 1 day).")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002401
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002402 {"microseconds", T_INT, OFFSET(microseconds), READONLY,
2403 PyDoc_STR("Number of microseconds (>= 0 and less than 1 second).")},
2404 {NULL}
Tim Peters2a799bf2002-12-16 20:18:38 +00002405};
2406
2407static PyMethodDef delta_methods[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002408 {"total_seconds", (PyCFunction)delta_total_seconds, METH_NOARGS,
2409 PyDoc_STR("Total seconds in the duration.")},
Antoine Pitroube6859d2009-11-25 23:02:32 +00002410
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002411 {"__reduce__", (PyCFunction)delta_reduce, METH_NOARGS,
2412 PyDoc_STR("__reduce__() -> (cls, state)")},
Guido van Rossum177e41a2003-01-30 22:06:23 +00002413
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002414 {NULL, NULL},
Tim Peters2a799bf2002-12-16 20:18:38 +00002415};
2416
Serhiy Storchaka2d06e842015-12-25 19:53:18 +02002417static const char delta_doc[] =
Tim Peters2a799bf2002-12-16 20:18:38 +00002418PyDoc_STR("Difference between two datetime values.");
2419
2420static PyNumberMethods delta_as_number = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002421 delta_add, /* nb_add */
2422 delta_subtract, /* nb_subtract */
2423 delta_multiply, /* nb_multiply */
2424 delta_remainder, /* nb_remainder */
2425 delta_divmod, /* nb_divmod */
2426 0, /* nb_power */
2427 (unaryfunc)delta_negative, /* nb_negative */
2428 (unaryfunc)delta_positive, /* nb_positive */
2429 (unaryfunc)delta_abs, /* nb_absolute */
2430 (inquiry)delta_bool, /* nb_bool */
2431 0, /*nb_invert*/
2432 0, /*nb_lshift*/
2433 0, /*nb_rshift*/
2434 0, /*nb_and*/
2435 0, /*nb_xor*/
2436 0, /*nb_or*/
2437 0, /*nb_int*/
2438 0, /*nb_reserved*/
2439 0, /*nb_float*/
2440 0, /*nb_inplace_add*/
2441 0, /*nb_inplace_subtract*/
2442 0, /*nb_inplace_multiply*/
2443 0, /*nb_inplace_remainder*/
2444 0, /*nb_inplace_power*/
2445 0, /*nb_inplace_lshift*/
2446 0, /*nb_inplace_rshift*/
2447 0, /*nb_inplace_and*/
2448 0, /*nb_inplace_xor*/
2449 0, /*nb_inplace_or*/
2450 delta_divide, /* nb_floor_divide */
2451 delta_truedivide, /* nb_true_divide */
2452 0, /* nb_inplace_floor_divide */
2453 0, /* nb_inplace_true_divide */
Tim Peters2a799bf2002-12-16 20:18:38 +00002454};
2455
2456static PyTypeObject PyDateTime_DeltaType = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002457 PyVarObject_HEAD_INIT(NULL, 0)
2458 "datetime.timedelta", /* tp_name */
2459 sizeof(PyDateTime_Delta), /* tp_basicsize */
2460 0, /* tp_itemsize */
2461 0, /* tp_dealloc */
2462 0, /* tp_print */
2463 0, /* tp_getattr */
2464 0, /* tp_setattr */
2465 0, /* tp_reserved */
2466 (reprfunc)delta_repr, /* tp_repr */
2467 &delta_as_number, /* tp_as_number */
2468 0, /* tp_as_sequence */
2469 0, /* tp_as_mapping */
2470 (hashfunc)delta_hash, /* tp_hash */
2471 0, /* tp_call */
2472 (reprfunc)delta_str, /* tp_str */
2473 PyObject_GenericGetAttr, /* tp_getattro */
2474 0, /* tp_setattro */
2475 0, /* tp_as_buffer */
2476 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
2477 delta_doc, /* tp_doc */
2478 0, /* tp_traverse */
2479 0, /* tp_clear */
2480 delta_richcompare, /* tp_richcompare */
2481 0, /* tp_weaklistoffset */
2482 0, /* tp_iter */
2483 0, /* tp_iternext */
2484 delta_methods, /* tp_methods */
2485 delta_members, /* tp_members */
2486 0, /* tp_getset */
2487 0, /* tp_base */
2488 0, /* tp_dict */
2489 0, /* tp_descr_get */
2490 0, /* tp_descr_set */
2491 0, /* tp_dictoffset */
2492 0, /* tp_init */
2493 0, /* tp_alloc */
2494 delta_new, /* tp_new */
2495 0, /* tp_free */
Tim Peters2a799bf2002-12-16 20:18:38 +00002496};
2497
2498/*
2499 * PyDateTime_Date implementation.
2500 */
2501
2502/* Accessor properties. */
2503
2504static PyObject *
2505date_year(PyDateTime_Date *self, void *unused)
2506{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002507 return PyLong_FromLong(GET_YEAR(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002508}
2509
2510static PyObject *
2511date_month(PyDateTime_Date *self, void *unused)
2512{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002513 return PyLong_FromLong(GET_MONTH(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002514}
2515
2516static PyObject *
2517date_day(PyDateTime_Date *self, void *unused)
2518{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002519 return PyLong_FromLong(GET_DAY(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002520}
2521
2522static PyGetSetDef date_getset[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002523 {"year", (getter)date_year},
2524 {"month", (getter)date_month},
2525 {"day", (getter)date_day},
2526 {NULL}
Tim Peters2a799bf2002-12-16 20:18:38 +00002527};
2528
2529/* Constructors. */
2530
Martin v. Löwis02cbf4a2006-02-27 17:20:04 +00002531static char *date_kws[] = {"year", "month", "day", NULL};
Tim Peters12bf3392002-12-24 05:41:27 +00002532
Tim Peters2a799bf2002-12-16 20:18:38 +00002533static PyObject *
2534date_new(PyTypeObject *type, PyObject *args, PyObject *kw)
2535{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002536 PyObject *self = NULL;
2537 PyObject *state;
2538 int year;
2539 int month;
2540 int day;
Tim Peters2a799bf2002-12-16 20:18:38 +00002541
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002542 /* Check for invocation from pickle with __getstate__ state */
2543 if (PyTuple_GET_SIZE(args) == 1 &&
2544 PyBytes_Check(state = PyTuple_GET_ITEM(args, 0)) &&
2545 PyBytes_GET_SIZE(state) == _PyDateTime_DATE_DATASIZE &&
2546 MONTH_IS_SANE(PyBytes_AS_STRING(state)[2]))
2547 {
2548 PyDateTime_Date *me;
Tim Peters70533e22003-02-01 04:40:04 +00002549
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002550 me = (PyDateTime_Date *) (type->tp_alloc(type, 0));
2551 if (me != NULL) {
2552 char *pdata = PyBytes_AS_STRING(state);
2553 memcpy(me->data, pdata, _PyDateTime_DATE_DATASIZE);
2554 me->hashcode = -1;
2555 }
2556 return (PyObject *)me;
2557 }
Guido van Rossum177e41a2003-01-30 22:06:23 +00002558
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002559 if (PyArg_ParseTupleAndKeywords(args, kw, "iii", date_kws,
2560 &year, &month, &day)) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002561 self = new_date_ex(year, month, day, type);
2562 }
2563 return self;
Tim Peters2a799bf2002-12-16 20:18:38 +00002564}
2565
2566/* Return new date from localtime(t). */
2567static PyObject *
Victor Stinner5d272cc2012-03-13 13:35:55 +01002568date_local_from_object(PyObject *cls, PyObject *obj)
Tim Peters2a799bf2002-12-16 20:18:38 +00002569{
Alexander Belopolsky6d88fa52016-09-10 15:58:31 -04002570 struct tm tm;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002571 time_t t;
Tim Peters2a799bf2002-12-16 20:18:38 +00002572
Victor Stinnere4a994d2015-03-30 01:10:14 +02002573 if (_PyTime_ObjectToTime_t(obj, &t, _PyTime_ROUND_FLOOR) == -1)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002574 return NULL;
Victor Stinner5d272cc2012-03-13 13:35:55 +01002575
Alexander Belopolsky3e7a3cb2016-09-28 17:31:35 -04002576 if (_PyTime_localtime(t, &tm) != 0)
Victor Stinner21f58932012-03-14 00:15:40 +01002577 return NULL;
Victor Stinner21f58932012-03-14 00:15:40 +01002578
2579 return PyObject_CallFunction(cls, "iii",
Alexander Belopolsky6d88fa52016-09-10 15:58:31 -04002580 tm.tm_year + 1900,
2581 tm.tm_mon + 1,
2582 tm.tm_mday);
Tim Peters2a799bf2002-12-16 20:18:38 +00002583}
2584
2585/* Return new date from current time.
2586 * We say this is equivalent to fromtimestamp(time.time()), and the
2587 * only way to be sure of that is to *call* time.time(). That's not
2588 * generally the same as calling C's time.
2589 */
2590static PyObject *
2591date_today(PyObject *cls, PyObject *dummy)
2592{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002593 PyObject *time;
2594 PyObject *result;
Martin v. Löwisbd928fe2011-10-14 10:20:37 +02002595 _Py_IDENTIFIER(fromtimestamp);
Tim Peters2a799bf2002-12-16 20:18:38 +00002596
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002597 time = time_time();
2598 if (time == NULL)
2599 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002600
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002601 /* Note well: today() is a class method, so this may not call
2602 * date.fromtimestamp. For example, it may call
2603 * datetime.fromtimestamp. That's why we need all the accuracy
2604 * time.time() delivers; if someone were gonzo about optimization,
2605 * date.today() could get away with plain C time().
2606 */
Victor Stinner20401de2016-12-09 15:24:31 +01002607 result = _PyObject_CallMethodIdObjArgs(cls, &PyId_fromtimestamp,
2608 time, NULL);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002609 Py_DECREF(time);
2610 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00002611}
2612
2613/* Return new date from given timestamp (Python timestamp -- a double). */
2614static PyObject *
2615date_fromtimestamp(PyObject *cls, PyObject *args)
2616{
Victor Stinner5d272cc2012-03-13 13:35:55 +01002617 PyObject *timestamp;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002618 PyObject *result = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002619
Victor Stinner5d272cc2012-03-13 13:35:55 +01002620 if (PyArg_ParseTuple(args, "O:fromtimestamp", &timestamp))
2621 result = date_local_from_object(cls, timestamp);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002622 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00002623}
2624
2625/* Return new date from proleptic Gregorian ordinal. Raises ValueError if
2626 * the ordinal is out of range.
2627 */
2628static PyObject *
2629date_fromordinal(PyObject *cls, PyObject *args)
2630{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002631 PyObject *result = NULL;
2632 int ordinal;
Tim Peters2a799bf2002-12-16 20:18:38 +00002633
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002634 if (PyArg_ParseTuple(args, "i:fromordinal", &ordinal)) {
2635 int year;
2636 int month;
2637 int day;
Tim Peters2a799bf2002-12-16 20:18:38 +00002638
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002639 if (ordinal < 1)
2640 PyErr_SetString(PyExc_ValueError, "ordinal must be "
2641 ">= 1");
2642 else {
2643 ord_to_ymd(ordinal, &year, &month, &day);
2644 result = PyObject_CallFunction(cls, "iii",
2645 year, month, day);
2646 }
2647 }
2648 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00002649}
2650
2651/*
2652 * Date arithmetic.
2653 */
2654
2655/* date + timedelta -> date. If arg negate is true, subtract the timedelta
2656 * instead.
2657 */
2658static PyObject *
2659add_date_timedelta(PyDateTime_Date *date, PyDateTime_Delta *delta, int negate)
2660{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002661 PyObject *result = NULL;
2662 int year = GET_YEAR(date);
2663 int month = GET_MONTH(date);
2664 int deltadays = GET_TD_DAYS(delta);
2665 /* C-level overflow is impossible because |deltadays| < 1e9. */
2666 int day = GET_DAY(date) + (negate ? -deltadays : deltadays);
Tim Peters2a799bf2002-12-16 20:18:38 +00002667
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002668 if (normalize_date(&year, &month, &day) >= 0)
2669 result = new_date(year, month, day);
2670 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00002671}
2672
2673static PyObject *
2674date_add(PyObject *left, PyObject *right)
2675{
Brian Curtindfc80e32011-08-10 20:28:54 -05002676 if (PyDateTime_Check(left) || PyDateTime_Check(right))
2677 Py_RETURN_NOTIMPLEMENTED;
2678
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002679 if (PyDate_Check(left)) {
2680 /* date + ??? */
2681 if (PyDelta_Check(right))
2682 /* date + delta */
2683 return add_date_timedelta((PyDateTime_Date *) left,
2684 (PyDateTime_Delta *) right,
2685 0);
2686 }
2687 else {
2688 /* ??? + date
2689 * 'right' must be one of us, or we wouldn't have been called
2690 */
2691 if (PyDelta_Check(left))
2692 /* delta + date */
2693 return add_date_timedelta((PyDateTime_Date *) right,
2694 (PyDateTime_Delta *) left,
2695 0);
2696 }
Brian Curtindfc80e32011-08-10 20:28:54 -05002697 Py_RETURN_NOTIMPLEMENTED;
Tim Peters2a799bf2002-12-16 20:18:38 +00002698}
2699
2700static PyObject *
2701date_subtract(PyObject *left, PyObject *right)
2702{
Brian Curtindfc80e32011-08-10 20:28:54 -05002703 if (PyDateTime_Check(left) || PyDateTime_Check(right))
2704 Py_RETURN_NOTIMPLEMENTED;
2705
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002706 if (PyDate_Check(left)) {
2707 if (PyDate_Check(right)) {
2708 /* date - date */
2709 int left_ord = ymd_to_ord(GET_YEAR(left),
2710 GET_MONTH(left),
2711 GET_DAY(left));
2712 int right_ord = ymd_to_ord(GET_YEAR(right),
2713 GET_MONTH(right),
2714 GET_DAY(right));
2715 return new_delta(left_ord - right_ord, 0, 0, 0);
2716 }
2717 if (PyDelta_Check(right)) {
2718 /* date - delta */
2719 return add_date_timedelta((PyDateTime_Date *) left,
2720 (PyDateTime_Delta *) right,
2721 1);
2722 }
2723 }
Brian Curtindfc80e32011-08-10 20:28:54 -05002724 Py_RETURN_NOTIMPLEMENTED;
Tim Peters2a799bf2002-12-16 20:18:38 +00002725}
2726
2727
2728/* Various ways to turn a date into a string. */
2729
2730static PyObject *
2731date_repr(PyDateTime_Date *self)
2732{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002733 return PyUnicode_FromFormat("%s(%d, %d, %d)",
2734 Py_TYPE(self)->tp_name,
2735 GET_YEAR(self), GET_MONTH(self), GET_DAY(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002736}
2737
2738static PyObject *
2739date_isoformat(PyDateTime_Date *self)
2740{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002741 return PyUnicode_FromFormat("%04d-%02d-%02d",
2742 GET_YEAR(self), GET_MONTH(self), GET_DAY(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002743}
2744
Tim Peterse2df5ff2003-05-02 18:39:55 +00002745/* str() calls the appropriate isoformat() method. */
Tim Peters2a799bf2002-12-16 20:18:38 +00002746static PyObject *
2747date_str(PyDateTime_Date *self)
2748{
Victor Stinnerad8c83a2016-09-05 17:53:15 -07002749 return _PyObject_CallMethodId((PyObject *)self, &PyId_isoformat, NULL);
Tim Peters2a799bf2002-12-16 20:18:38 +00002750}
2751
2752
2753static PyObject *
2754date_ctime(PyDateTime_Date *self)
2755{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002756 return format_ctime(self, 0, 0, 0);
Tim Peters2a799bf2002-12-16 20:18:38 +00002757}
2758
2759static PyObject *
2760date_strftime(PyDateTime_Date *self, PyObject *args, PyObject *kw)
2761{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002762 /* This method can be inherited, and needs to call the
2763 * timetuple() method appropriate to self's class.
2764 */
2765 PyObject *result;
2766 PyObject *tuple;
2767 PyObject *format;
Martin v. Löwisbd928fe2011-10-14 10:20:37 +02002768 _Py_IDENTIFIER(timetuple);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002769 static char *keywords[] = {"format", NULL};
Tim Peters2a799bf2002-12-16 20:18:38 +00002770
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002771 if (! PyArg_ParseTupleAndKeywords(args, kw, "U:strftime", keywords,
2772 &format))
2773 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002774
Victor Stinnerad8c83a2016-09-05 17:53:15 -07002775 tuple = _PyObject_CallMethodId((PyObject *)self, &PyId_timetuple, NULL);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002776 if (tuple == NULL)
2777 return NULL;
2778 result = wrap_strftime((PyObject *)self, format, tuple,
2779 (PyObject *)self);
2780 Py_DECREF(tuple);
2781 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00002782}
2783
Eric Smith1ba31142007-09-11 18:06:02 +00002784static PyObject *
2785date_format(PyDateTime_Date *self, PyObject *args)
2786{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002787 PyObject *format;
Eric Smith1ba31142007-09-11 18:06:02 +00002788
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002789 if (!PyArg_ParseTuple(args, "U:__format__", &format))
2790 return NULL;
Eric Smith1ba31142007-09-11 18:06:02 +00002791
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002792 /* if the format is zero length, return str(self) */
Victor Stinner9e30aa52011-11-21 02:49:52 +01002793 if (PyUnicode_GetLength(format) == 0)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002794 return PyObject_Str((PyObject *)self);
Eric Smith1ba31142007-09-11 18:06:02 +00002795
Victor Stinner20401de2016-12-09 15:24:31 +01002796 return _PyObject_CallMethodIdObjArgs((PyObject *)self, &PyId_strftime,
2797 format, NULL);
Eric Smith1ba31142007-09-11 18:06:02 +00002798}
2799
Tim Peters2a799bf2002-12-16 20:18:38 +00002800/* ISO methods. */
2801
2802static PyObject *
2803date_isoweekday(PyDateTime_Date *self)
2804{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002805 int dow = weekday(GET_YEAR(self), GET_MONTH(self), GET_DAY(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002806
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002807 return PyLong_FromLong(dow + 1);
Tim Peters2a799bf2002-12-16 20:18:38 +00002808}
2809
2810static PyObject *
2811date_isocalendar(PyDateTime_Date *self)
2812{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002813 int year = GET_YEAR(self);
2814 int week1_monday = iso_week1_monday(year);
2815 int today = ymd_to_ord(year, GET_MONTH(self), GET_DAY(self));
2816 int week;
2817 int day;
Tim Peters2a799bf2002-12-16 20:18:38 +00002818
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002819 week = divmod(today - week1_monday, 7, &day);
2820 if (week < 0) {
2821 --year;
2822 week1_monday = iso_week1_monday(year);
2823 week = divmod(today - week1_monday, 7, &day);
2824 }
2825 else if (week >= 52 && today >= iso_week1_monday(year + 1)) {
2826 ++year;
2827 week = 0;
2828 }
2829 return Py_BuildValue("iii", year, week + 1, day + 1);
Tim Peters2a799bf2002-12-16 20:18:38 +00002830}
2831
2832/* Miscellaneous methods. */
2833
Tim Peters2a799bf2002-12-16 20:18:38 +00002834static PyObject *
Guido van Rossum19960592006-08-24 17:29:38 +00002835date_richcompare(PyObject *self, PyObject *other, int op)
Tim Peters2a799bf2002-12-16 20:18:38 +00002836{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002837 if (PyDate_Check(other)) {
2838 int diff = memcmp(((PyDateTime_Date *)self)->data,
2839 ((PyDateTime_Date *)other)->data,
2840 _PyDateTime_DATE_DATASIZE);
2841 return diff_to_bool(diff, op);
2842 }
Brian Curtindfc80e32011-08-10 20:28:54 -05002843 else
2844 Py_RETURN_NOTIMPLEMENTED;
Tim Peters2a799bf2002-12-16 20:18:38 +00002845}
2846
2847static PyObject *
2848date_timetuple(PyDateTime_Date *self)
2849{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002850 return build_struct_time(GET_YEAR(self),
2851 GET_MONTH(self),
2852 GET_DAY(self),
2853 0, 0, 0, -1);
Tim Peters2a799bf2002-12-16 20:18:38 +00002854}
2855
Tim Peters12bf3392002-12-24 05:41:27 +00002856static PyObject *
2857date_replace(PyDateTime_Date *self, PyObject *args, PyObject *kw)
2858{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002859 PyObject *clone;
2860 PyObject *tuple;
2861 int year = GET_YEAR(self);
2862 int month = GET_MONTH(self);
2863 int day = GET_DAY(self);
Tim Peters12bf3392002-12-24 05:41:27 +00002864
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002865 if (! PyArg_ParseTupleAndKeywords(args, kw, "|iii:replace", date_kws,
2866 &year, &month, &day))
2867 return NULL;
2868 tuple = Py_BuildValue("iii", year, month, day);
2869 if (tuple == NULL)
2870 return NULL;
2871 clone = date_new(Py_TYPE(self), tuple, NULL);
2872 Py_DECREF(tuple);
2873 return clone;
Tim Peters12bf3392002-12-24 05:41:27 +00002874}
2875
Benjamin Peterson8f67d082010-10-17 20:54:53 +00002876static Py_hash_t
Guido van Rossumfd53fd62007-08-24 04:05:13 +00002877generic_hash(unsigned char *data, int len)
2878{
Gregory P. Smith5831bd22012-01-14 14:31:13 -08002879 return _Py_HashBytes(data, len);
Guido van Rossumfd53fd62007-08-24 04:05:13 +00002880}
2881
2882
2883static PyObject *date_getstate(PyDateTime_Date *self);
Tim Peters2a799bf2002-12-16 20:18:38 +00002884
Benjamin Peterson8f67d082010-10-17 20:54:53 +00002885static Py_hash_t
Tim Peters2a799bf2002-12-16 20:18:38 +00002886date_hash(PyDateTime_Date *self)
2887{
Benjamin Petersondec2df32016-09-09 17:46:24 -07002888 if (self->hashcode == -1) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002889 self->hashcode = generic_hash(
2890 (unsigned char *)self->data, _PyDateTime_DATE_DATASIZE);
Benjamin Petersondec2df32016-09-09 17:46:24 -07002891 }
Guido van Rossum254348e2007-11-21 19:29:53 +00002892
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002893 return self->hashcode;
Tim Peters2a799bf2002-12-16 20:18:38 +00002894}
2895
2896static PyObject *
2897date_toordinal(PyDateTime_Date *self)
2898{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002899 return PyLong_FromLong(ymd_to_ord(GET_YEAR(self), GET_MONTH(self),
2900 GET_DAY(self)));
Tim Peters2a799bf2002-12-16 20:18:38 +00002901}
2902
2903static PyObject *
2904date_weekday(PyDateTime_Date *self)
2905{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002906 int dow = weekday(GET_YEAR(self), GET_MONTH(self), GET_DAY(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002907
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002908 return PyLong_FromLong(dow);
Tim Peters2a799bf2002-12-16 20:18:38 +00002909}
2910
Tim Peters371935f2003-02-01 01:52:50 +00002911/* Pickle support, a simple use of __reduce__. */
Tim Peters2a799bf2002-12-16 20:18:38 +00002912
Tim Petersb57f8f02003-02-01 02:54:15 +00002913/* __getstate__ isn't exposed */
Tim Peters2a799bf2002-12-16 20:18:38 +00002914static PyObject *
Guido van Rossumfd53fd62007-08-24 04:05:13 +00002915date_getstate(PyDateTime_Date *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00002916{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002917 PyObject* field;
2918 field = PyBytes_FromStringAndSize((char*)self->data,
2919 _PyDateTime_DATE_DATASIZE);
2920 return Py_BuildValue("(N)", field);
Tim Peters2a799bf2002-12-16 20:18:38 +00002921}
2922
2923static PyObject *
Guido van Rossum177e41a2003-01-30 22:06:23 +00002924date_reduce(PyDateTime_Date *self, PyObject *arg)
Tim Peters2a799bf2002-12-16 20:18:38 +00002925{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002926 return Py_BuildValue("(ON)", Py_TYPE(self), date_getstate(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002927}
2928
2929static PyMethodDef date_methods[] = {
Guido van Rossum177e41a2003-01-30 22:06:23 +00002930
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002931 /* Class methods: */
Guido van Rossum177e41a2003-01-30 22:06:23 +00002932
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002933 {"fromtimestamp", (PyCFunction)date_fromtimestamp, METH_VARARGS |
2934 METH_CLASS,
2935 PyDoc_STR("timestamp -> local date from a POSIX timestamp (like "
2936 "time.time()).")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002937
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002938 {"fromordinal", (PyCFunction)date_fromordinal, METH_VARARGS |
2939 METH_CLASS,
2940 PyDoc_STR("int -> date corresponding to a proleptic Gregorian "
2941 "ordinal.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002942
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002943 {"today", (PyCFunction)date_today, METH_NOARGS | METH_CLASS,
2944 PyDoc_STR("Current date or datetime: same as "
2945 "self.__class__.fromtimestamp(time.time()).")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002946
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002947 /* Instance methods: */
Tim Peters2a799bf2002-12-16 20:18:38 +00002948
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002949 {"ctime", (PyCFunction)date_ctime, METH_NOARGS,
2950 PyDoc_STR("Return ctime() style string.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002951
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002952 {"strftime", (PyCFunction)date_strftime, METH_VARARGS | METH_KEYWORDS,
2953 PyDoc_STR("format -> strftime() style string.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002954
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002955 {"__format__", (PyCFunction)date_format, METH_VARARGS,
2956 PyDoc_STR("Formats self with strftime.")},
Eric Smith1ba31142007-09-11 18:06:02 +00002957
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002958 {"timetuple", (PyCFunction)date_timetuple, METH_NOARGS,
2959 PyDoc_STR("Return time tuple, compatible with time.localtime().")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002960
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002961 {"isocalendar", (PyCFunction)date_isocalendar, METH_NOARGS,
2962 PyDoc_STR("Return a 3-tuple containing ISO year, week number, and "
2963 "weekday.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002964
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002965 {"isoformat", (PyCFunction)date_isoformat, METH_NOARGS,
2966 PyDoc_STR("Return string in ISO 8601 format, YYYY-MM-DD.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002967
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002968 {"isoweekday", (PyCFunction)date_isoweekday, METH_NOARGS,
2969 PyDoc_STR("Return the day of the week represented by the date.\n"
2970 "Monday == 1 ... Sunday == 7")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002971
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002972 {"toordinal", (PyCFunction)date_toordinal, METH_NOARGS,
2973 PyDoc_STR("Return proleptic Gregorian ordinal. January 1 of year "
2974 "1 is day 1.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002975
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002976 {"weekday", (PyCFunction)date_weekday, METH_NOARGS,
2977 PyDoc_STR("Return the day of the week represented by the date.\n"
2978 "Monday == 0 ... Sunday == 6")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002979
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002980 {"replace", (PyCFunction)date_replace, METH_VARARGS | METH_KEYWORDS,
2981 PyDoc_STR("Return date with new specified fields.")},
Tim Peters12bf3392002-12-24 05:41:27 +00002982
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002983 {"__reduce__", (PyCFunction)date_reduce, METH_NOARGS,
2984 PyDoc_STR("__reduce__() -> (cls, state)")},
Guido van Rossum177e41a2003-01-30 22:06:23 +00002985
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002986 {NULL, NULL}
Tim Peters2a799bf2002-12-16 20:18:38 +00002987};
2988
Serhiy Storchaka2d06e842015-12-25 19:53:18 +02002989static const char date_doc[] =
Raymond Hettinger3a4231d2004-12-19 20:13:24 +00002990PyDoc_STR("date(year, month, day) --> date object");
Tim Peters2a799bf2002-12-16 20:18:38 +00002991
2992static PyNumberMethods date_as_number = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002993 date_add, /* nb_add */
2994 date_subtract, /* nb_subtract */
2995 0, /* nb_multiply */
2996 0, /* nb_remainder */
2997 0, /* nb_divmod */
2998 0, /* nb_power */
2999 0, /* nb_negative */
3000 0, /* nb_positive */
3001 0, /* nb_absolute */
3002 0, /* nb_bool */
Tim Peters2a799bf2002-12-16 20:18:38 +00003003};
3004
3005static PyTypeObject PyDateTime_DateType = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003006 PyVarObject_HEAD_INIT(NULL, 0)
3007 "datetime.date", /* tp_name */
3008 sizeof(PyDateTime_Date), /* tp_basicsize */
3009 0, /* tp_itemsize */
3010 0, /* tp_dealloc */
3011 0, /* tp_print */
3012 0, /* tp_getattr */
3013 0, /* tp_setattr */
3014 0, /* tp_reserved */
3015 (reprfunc)date_repr, /* tp_repr */
3016 &date_as_number, /* tp_as_number */
3017 0, /* tp_as_sequence */
3018 0, /* tp_as_mapping */
3019 (hashfunc)date_hash, /* tp_hash */
3020 0, /* tp_call */
3021 (reprfunc)date_str, /* tp_str */
3022 PyObject_GenericGetAttr, /* tp_getattro */
3023 0, /* tp_setattro */
3024 0, /* tp_as_buffer */
3025 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
3026 date_doc, /* tp_doc */
3027 0, /* tp_traverse */
3028 0, /* tp_clear */
3029 date_richcompare, /* tp_richcompare */
3030 0, /* tp_weaklistoffset */
3031 0, /* tp_iter */
3032 0, /* tp_iternext */
3033 date_methods, /* tp_methods */
3034 0, /* tp_members */
3035 date_getset, /* tp_getset */
3036 0, /* tp_base */
3037 0, /* tp_dict */
3038 0, /* tp_descr_get */
3039 0, /* tp_descr_set */
3040 0, /* tp_dictoffset */
3041 0, /* tp_init */
3042 0, /* tp_alloc */
3043 date_new, /* tp_new */
3044 0, /* tp_free */
Tim Peters2a799bf2002-12-16 20:18:38 +00003045};
3046
3047/*
Tim Peters2a799bf2002-12-16 20:18:38 +00003048 * PyDateTime_TZInfo implementation.
3049 */
3050
3051/* This is a pure abstract base class, so doesn't do anything beyond
3052 * raising NotImplemented exceptions. Real tzinfo classes need
3053 * to derive from this. This is mostly for clarity, and for efficiency in
Tim Petersa9bc1682003-01-11 03:39:11 +00003054 * datetime and time constructors (their tzinfo arguments need to
Tim Peters2a799bf2002-12-16 20:18:38 +00003055 * be subclasses of this tzinfo class, which is easy and quick to check).
3056 *
3057 * Note: For reasons having to do with pickling of subclasses, we have
3058 * to allow tzinfo objects to be instantiated. This wasn't an issue
3059 * in the Python implementation (__init__() could raise NotImplementedError
3060 * there without ill effect), but doing so in the C implementation hit a
3061 * brick wall.
3062 */
3063
3064static PyObject *
3065tzinfo_nogo(const char* methodname)
3066{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003067 PyErr_Format(PyExc_NotImplementedError,
3068 "a tzinfo subclass must implement %s()",
3069 methodname);
3070 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00003071}
3072
3073/* Methods. A subclass must implement these. */
3074
Tim Peters52dcce22003-01-23 16:36:11 +00003075static PyObject *
Tim Peters2a799bf2002-12-16 20:18:38 +00003076tzinfo_tzname(PyDateTime_TZInfo *self, PyObject *dt)
3077{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003078 return tzinfo_nogo("tzname");
Tim Peters2a799bf2002-12-16 20:18:38 +00003079}
3080
Tim Peters52dcce22003-01-23 16:36:11 +00003081static PyObject *
Tim Peters2a799bf2002-12-16 20:18:38 +00003082tzinfo_utcoffset(PyDateTime_TZInfo *self, PyObject *dt)
3083{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003084 return tzinfo_nogo("utcoffset");
Tim Peters2a799bf2002-12-16 20:18:38 +00003085}
3086
Tim Peters52dcce22003-01-23 16:36:11 +00003087static PyObject *
Tim Peters2a799bf2002-12-16 20:18:38 +00003088tzinfo_dst(PyDateTime_TZInfo *self, PyObject *dt)
3089{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003090 return tzinfo_nogo("dst");
Tim Peters2a799bf2002-12-16 20:18:38 +00003091}
3092
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003093
3094static PyObject *add_datetime_timedelta(PyDateTime_DateTime *date,
3095 PyDateTime_Delta *delta,
3096 int factor);
3097static PyObject *datetime_utcoffset(PyObject *self, PyObject *);
3098static PyObject *datetime_dst(PyObject *self, PyObject *);
3099
Tim Peters52dcce22003-01-23 16:36:11 +00003100static PyObject *
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003101tzinfo_fromutc(PyDateTime_TZInfo *self, PyObject *dt)
Tim Peters52dcce22003-01-23 16:36:11 +00003102{
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003103 PyObject *result = NULL;
3104 PyObject *off = NULL, *dst = NULL;
3105 PyDateTime_Delta *delta = NULL;
Tim Peters52dcce22003-01-23 16:36:11 +00003106
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003107 if (!PyDateTime_Check(dt)) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003108 PyErr_SetString(PyExc_TypeError,
3109 "fromutc: argument must be a datetime");
3110 return NULL;
3111 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003112 if (GET_DT_TZINFO(dt) != (PyObject *)self) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003113 PyErr_SetString(PyExc_ValueError, "fromutc: dt.tzinfo "
3114 "is not self");
3115 return NULL;
3116 }
Tim Peters52dcce22003-01-23 16:36:11 +00003117
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003118 off = datetime_utcoffset(dt, NULL);
3119 if (off == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003120 return NULL;
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003121 if (off == Py_None) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003122 PyErr_SetString(PyExc_ValueError, "fromutc: non-None "
3123 "utcoffset() result required");
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003124 goto Fail;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003125 }
Tim Peters52dcce22003-01-23 16:36:11 +00003126
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003127 dst = datetime_dst(dt, NULL);
3128 if (dst == NULL)
3129 goto Fail;
3130 if (dst == Py_None) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003131 PyErr_SetString(PyExc_ValueError, "fromutc: non-None "
3132 "dst() result required");
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003133 goto Fail;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003134 }
Tim Peters52dcce22003-01-23 16:36:11 +00003135
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003136 delta = (PyDateTime_Delta *)delta_subtract(off, dst);
3137 if (delta == NULL)
3138 goto Fail;
3139 result = add_datetime_timedelta((PyDateTime_DateTime *)dt, delta, 1);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003140 if (result == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003141 goto Fail;
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003142
3143 Py_DECREF(dst);
3144 dst = call_dst(GET_DT_TZINFO(dt), result);
3145 if (dst == NULL)
3146 goto Fail;
3147 if (dst == Py_None)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003148 goto Inconsistent;
Alexander Belopolskyc79447b2015-09-27 21:41:55 -04003149 if (delta_bool((PyDateTime_Delta *)dst) != 0) {
Serhiy Storchakaf01e4082016-04-10 18:12:01 +03003150 Py_SETREF(result, add_datetime_timedelta((PyDateTime_DateTime *)result,
Serhiy Storchaka576f1322016-01-05 21:27:54 +02003151 (PyDateTime_Delta *)dst, 1));
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003152 if (result == NULL)
3153 goto Fail;
3154 }
3155 Py_DECREF(delta);
3156 Py_DECREF(dst);
3157 Py_DECREF(off);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003158 return result;
Tim Peters52dcce22003-01-23 16:36:11 +00003159
3160Inconsistent:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003161 PyErr_SetString(PyExc_ValueError, "fromutc: tz.dst() gave"
3162 "inconsistent results; cannot convert");
Tim Peters52dcce22003-01-23 16:36:11 +00003163
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003164 /* fall thru to failure */
Tim Peters52dcce22003-01-23 16:36:11 +00003165Fail:
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003166 Py_XDECREF(off);
3167 Py_XDECREF(dst);
3168 Py_XDECREF(delta);
3169 Py_XDECREF(result);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003170 return NULL;
Tim Peters52dcce22003-01-23 16:36:11 +00003171}
3172
Tim Peters2a799bf2002-12-16 20:18:38 +00003173/*
3174 * Pickle support. This is solely so that tzinfo subclasses can use
Guido van Rossum177e41a2003-01-30 22:06:23 +00003175 * pickling -- tzinfo itself is supposed to be uninstantiable.
Tim Peters2a799bf2002-12-16 20:18:38 +00003176 */
3177
Guido van Rossum177e41a2003-01-30 22:06:23 +00003178static PyObject *
3179tzinfo_reduce(PyObject *self)
3180{
Victor Stinnerd1584d32016-08-23 00:11:04 +02003181 PyObject *args, *state;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003182 PyObject *getinitargs, *getstate;
Martin v. Löwisbd928fe2011-10-14 10:20:37 +02003183 _Py_IDENTIFIER(__getinitargs__);
3184 _Py_IDENTIFIER(__getstate__);
Tim Peters2a799bf2002-12-16 20:18:38 +00003185
Martin v. Löwis1ee1b6f2011-10-10 18:11:30 +02003186 getinitargs = _PyObject_GetAttrId(self, &PyId___getinitargs__);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003187 if (getinitargs != NULL) {
Victor Stinnerd1584d32016-08-23 00:11:04 +02003188 args = _PyObject_CallNoArg(getinitargs);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003189 Py_DECREF(getinitargs);
3190 if (args == NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003191 return NULL;
3192 }
3193 }
3194 else {
3195 PyErr_Clear();
Victor Stinnerd1584d32016-08-23 00:11:04 +02003196
3197 args = PyTuple_New(0);
3198 if (args == NULL) {
3199 return NULL;
3200 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003201 }
Guido van Rossum177e41a2003-01-30 22:06:23 +00003202
Martin v. Löwis1ee1b6f2011-10-10 18:11:30 +02003203 getstate = _PyObject_GetAttrId(self, &PyId___getstate__);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003204 if (getstate != NULL) {
Victor Stinnerd1584d32016-08-23 00:11:04 +02003205 state = _PyObject_CallNoArg(getstate);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003206 Py_DECREF(getstate);
3207 if (state == NULL) {
3208 Py_DECREF(args);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003209 return NULL;
3210 }
3211 }
3212 else {
3213 PyObject **dictptr;
3214 PyErr_Clear();
3215 state = Py_None;
3216 dictptr = _PyObject_GetDictPtr(self);
Serhiy Storchaka5ab81d72016-12-16 16:18:57 +02003217 if (dictptr && *dictptr && PyDict_GET_SIZE(*dictptr)) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003218 state = *dictptr;
Victor Stinnerd1584d32016-08-23 00:11:04 +02003219 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003220 Py_INCREF(state);
3221 }
Guido van Rossum177e41a2003-01-30 22:06:23 +00003222
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003223 if (state == Py_None) {
3224 Py_DECREF(state);
3225 return Py_BuildValue("(ON)", Py_TYPE(self), args);
3226 }
3227 else
3228 return Py_BuildValue("(ONN)", Py_TYPE(self), args, state);
Guido van Rossum177e41a2003-01-30 22:06:23 +00003229}
Tim Peters2a799bf2002-12-16 20:18:38 +00003230
3231static PyMethodDef tzinfo_methods[] = {
Guido van Rossum177e41a2003-01-30 22:06:23 +00003232
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003233 {"tzname", (PyCFunction)tzinfo_tzname, METH_O,
3234 PyDoc_STR("datetime -> string name of time zone.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00003235
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003236 {"utcoffset", (PyCFunction)tzinfo_utcoffset, METH_O,
Sean Reifscheiderdeda8cb2010-06-04 01:51:38 +00003237 PyDoc_STR("datetime -> timedelta showing offset from UTC, negative "
3238 "values indicating West of UTC")},
Tim Peters2a799bf2002-12-16 20:18:38 +00003239
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003240 {"dst", (PyCFunction)tzinfo_dst, METH_O,
Alexander Belopolsky018d3532017-07-31 10:26:50 -04003241 PyDoc_STR("datetime -> DST offset as timedelta positive east of UTC.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00003242
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003243 {"fromutc", (PyCFunction)tzinfo_fromutc, METH_O,
Alexander Belopolsky2f194b92010-07-03 03:35:27 +00003244 PyDoc_STR("datetime in UTC -> datetime in local time.")},
Tim Peters52dcce22003-01-23 16:36:11 +00003245
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003246 {"__reduce__", (PyCFunction)tzinfo_reduce, METH_NOARGS,
3247 PyDoc_STR("-> (cls, state)")},
Guido van Rossum177e41a2003-01-30 22:06:23 +00003248
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003249 {NULL, NULL}
Tim Peters2a799bf2002-12-16 20:18:38 +00003250};
3251
Serhiy Storchaka2d06e842015-12-25 19:53:18 +02003252static const char tzinfo_doc[] =
Tim Peters2a799bf2002-12-16 20:18:38 +00003253PyDoc_STR("Abstract base class for time zone info objects.");
3254
Neal Norwitz227b5332006-03-22 09:28:35 +00003255static PyTypeObject PyDateTime_TZInfoType = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003256 PyVarObject_HEAD_INIT(NULL, 0)
3257 "datetime.tzinfo", /* tp_name */
3258 sizeof(PyDateTime_TZInfo), /* tp_basicsize */
3259 0, /* tp_itemsize */
3260 0, /* tp_dealloc */
3261 0, /* tp_print */
3262 0, /* tp_getattr */
3263 0, /* tp_setattr */
3264 0, /* tp_reserved */
3265 0, /* tp_repr */
3266 0, /* tp_as_number */
3267 0, /* tp_as_sequence */
3268 0, /* tp_as_mapping */
3269 0, /* tp_hash */
3270 0, /* tp_call */
3271 0, /* tp_str */
3272 PyObject_GenericGetAttr, /* tp_getattro */
3273 0, /* tp_setattro */
3274 0, /* tp_as_buffer */
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003275 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003276 tzinfo_doc, /* tp_doc */
3277 0, /* tp_traverse */
3278 0, /* tp_clear */
3279 0, /* tp_richcompare */
3280 0, /* tp_weaklistoffset */
3281 0, /* tp_iter */
3282 0, /* tp_iternext */
3283 tzinfo_methods, /* tp_methods */
3284 0, /* tp_members */
3285 0, /* tp_getset */
3286 0, /* tp_base */
3287 0, /* tp_dict */
3288 0, /* tp_descr_get */
3289 0, /* tp_descr_set */
3290 0, /* tp_dictoffset */
3291 0, /* tp_init */
3292 0, /* tp_alloc */
3293 PyType_GenericNew, /* tp_new */
3294 0, /* tp_free */
Tim Peters2a799bf2002-12-16 20:18:38 +00003295};
3296
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003297static char *timezone_kws[] = {"offset", "name", NULL};
3298
3299static PyObject *
3300timezone_new(PyTypeObject *type, PyObject *args, PyObject *kw)
3301{
3302 PyObject *offset;
3303 PyObject *name = NULL;
Serhiy Storchakaf8d7d412016-10-23 15:12:25 +03003304 if (PyArg_ParseTupleAndKeywords(args, kw, "O!|U:timezone", timezone_kws,
3305 &PyDateTime_DeltaType, &offset, &name))
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003306 return new_timezone(offset, name);
3307
3308 return NULL;
3309}
3310
3311static void
3312timezone_dealloc(PyDateTime_TimeZone *self)
3313{
3314 Py_CLEAR(self->offset);
3315 Py_CLEAR(self->name);
3316 Py_TYPE(self)->tp_free((PyObject *)self);
3317}
3318
3319static PyObject *
3320timezone_richcompare(PyDateTime_TimeZone *self,
3321 PyDateTime_TimeZone *other, int op)
3322{
Brian Curtindfc80e32011-08-10 20:28:54 -05003323 if (op != Py_EQ && op != Py_NE)
3324 Py_RETURN_NOTIMPLEMENTED;
Georg Brandl0085a242012-09-22 09:23:12 +02003325 if (Py_TYPE(other) != &PyDateTime_TimeZoneType) {
Raymond Hettinger5a2146a2014-07-25 14:59:48 -07003326 if (op == Py_EQ)
3327 Py_RETURN_FALSE;
3328 else
3329 Py_RETURN_TRUE;
Georg Brandl0085a242012-09-22 09:23:12 +02003330 }
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003331 return delta_richcompare(self->offset, other->offset, op);
3332}
3333
Benjamin Peterson8f67d082010-10-17 20:54:53 +00003334static Py_hash_t
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003335timezone_hash(PyDateTime_TimeZone *self)
3336{
3337 return delta_hash((PyDateTime_Delta *)self->offset);
3338}
3339
3340/* Check argument type passed to tzname, utcoffset, or dst methods.
3341 Returns 0 for good argument. Returns -1 and sets exception info
3342 otherwise.
3343 */
3344static int
3345_timezone_check_argument(PyObject *dt, const char *meth)
3346{
3347 if (dt == Py_None || PyDateTime_Check(dt))
3348 return 0;
3349 PyErr_Format(PyExc_TypeError, "%s(dt) argument must be a datetime instance"
3350 " or None, not %.200s", meth, Py_TYPE(dt)->tp_name);
3351 return -1;
3352}
3353
3354static PyObject *
Alexander Belopolskya11d8c02010-07-06 23:19:45 +00003355timezone_repr(PyDateTime_TimeZone *self)
3356{
3357 /* Note that although timezone is not subclassable, it is convenient
3358 to use Py_TYPE(self)->tp_name here. */
3359 const char *type_name = Py_TYPE(self)->tp_name;
3360
3361 if (((PyObject *)self) == PyDateTime_TimeZone_UTC)
3362 return PyUnicode_FromFormat("%s.utc", type_name);
3363
3364 if (self->name == NULL)
3365 return PyUnicode_FromFormat("%s(%R)", type_name, self->offset);
3366
3367 return PyUnicode_FromFormat("%s(%R, %R)", type_name, self->offset,
3368 self->name);
3369}
3370
3371
3372static PyObject *
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003373timezone_str(PyDateTime_TimeZone *self)
3374{
Alexander Belopolsky018d3532017-07-31 10:26:50 -04003375 int hours, minutes, seconds, microseconds;
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003376 PyObject *offset;
3377 char sign;
3378
3379 if (self->name != NULL) {
3380 Py_INCREF(self->name);
3381 return self->name;
3382 }
Victor Stinner90fd8952015-09-08 00:12:49 +02003383 if ((PyObject *)self == PyDateTime_TimeZone_UTC ||
Alexander Belopolsky7827a5b2015-09-06 13:07:21 -04003384 (GET_TD_DAYS(self->offset) == 0 &&
3385 GET_TD_SECONDS(self->offset) == 0 &&
3386 GET_TD_MICROSECONDS(self->offset) == 0))
3387 return PyUnicode_FromString("UTC");
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003388 /* Offset is normalized, so it is negative if days < 0 */
3389 if (GET_TD_DAYS(self->offset) < 0) {
3390 sign = '-';
3391 offset = delta_negative((PyDateTime_Delta *)self->offset);
3392 if (offset == NULL)
3393 return NULL;
3394 }
3395 else {
3396 sign = '+';
3397 offset = self->offset;
3398 Py_INCREF(offset);
3399 }
3400 /* Offset is not negative here. */
Alexander Belopolsky018d3532017-07-31 10:26:50 -04003401 microseconds = GET_TD_MICROSECONDS(offset);
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003402 seconds = GET_TD_SECONDS(offset);
3403 Py_DECREF(offset);
3404 minutes = divmod(seconds, 60, &seconds);
3405 hours = divmod(minutes, 60, &minutes);
Alexander Belopolsky018d3532017-07-31 10:26:50 -04003406 if (microseconds != 0) {
3407 return PyUnicode_FromFormat("UTC%c%02d:%02d:%02d.%06d",
3408 sign, hours, minutes,
3409 seconds, microseconds);
3410 }
3411 if (seconds != 0) {
3412 return PyUnicode_FromFormat("UTC%c%02d:%02d:%02d",
3413 sign, hours, minutes, seconds);
3414 }
Victor Stinner6ced7c42011-03-21 18:15:42 +01003415 return PyUnicode_FromFormat("UTC%c%02d:%02d", sign, hours, minutes);
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003416}
3417
3418static PyObject *
3419timezone_tzname(PyDateTime_TimeZone *self, PyObject *dt)
3420{
3421 if (_timezone_check_argument(dt, "tzname") == -1)
3422 return NULL;
3423
3424 return timezone_str(self);
3425}
3426
3427static PyObject *
3428timezone_utcoffset(PyDateTime_TimeZone *self, PyObject *dt)
3429{
3430 if (_timezone_check_argument(dt, "utcoffset") == -1)
3431 return NULL;
3432
3433 Py_INCREF(self->offset);
3434 return self->offset;
3435}
3436
3437static PyObject *
3438timezone_dst(PyObject *self, PyObject *dt)
3439{
3440 if (_timezone_check_argument(dt, "dst") == -1)
3441 return NULL;
3442
3443 Py_RETURN_NONE;
3444}
3445
3446static PyObject *
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003447timezone_fromutc(PyDateTime_TimeZone *self, PyDateTime_DateTime *dt)
3448{
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003449 if (!PyDateTime_Check(dt)) {
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003450 PyErr_SetString(PyExc_TypeError,
3451 "fromutc: argument must be a datetime");
3452 return NULL;
3453 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003454 if (!HASTZINFO(dt) || dt->tzinfo != (PyObject *)self) {
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003455 PyErr_SetString(PyExc_ValueError, "fromutc: dt.tzinfo "
3456 "is not self");
3457 return NULL;
3458 }
3459
3460 return add_datetime_timedelta(dt, (PyDateTime_Delta *)self->offset, 1);
3461}
3462
Alexander Belopolsky1b7046b2010-06-23 21:40:15 +00003463static PyObject *
3464timezone_getinitargs(PyDateTime_TimeZone *self)
3465{
3466 if (self->name == NULL)
3467 return Py_BuildValue("(O)", self->offset);
3468 return Py_BuildValue("(OO)", self->offset, self->name);
3469}
3470
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003471static PyMethodDef timezone_methods[] = {
3472 {"tzname", (PyCFunction)timezone_tzname, METH_O,
3473 PyDoc_STR("If name is specified when timezone is created, returns the name."
Alexander Belopolskyb39a0c22010-06-15 19:24:52 +00003474 " Otherwise returns offset as 'UTC(+|-)HH:MM'.")},
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003475
3476 {"utcoffset", (PyCFunction)timezone_utcoffset, METH_O,
Alexander Belopolskyb39a0c22010-06-15 19:24:52 +00003477 PyDoc_STR("Return fixed offset.")},
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003478
3479 {"dst", (PyCFunction)timezone_dst, METH_O,
Alexander Belopolskyb39a0c22010-06-15 19:24:52 +00003480 PyDoc_STR("Return None.")},
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003481
3482 {"fromutc", (PyCFunction)timezone_fromutc, METH_O,
3483 PyDoc_STR("datetime in UTC -> datetime in local time.")},
3484
Alexander Belopolsky1b7046b2010-06-23 21:40:15 +00003485 {"__getinitargs__", (PyCFunction)timezone_getinitargs, METH_NOARGS,
3486 PyDoc_STR("pickle support")},
3487
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003488 {NULL, NULL}
3489};
3490
Serhiy Storchaka2d06e842015-12-25 19:53:18 +02003491static const char timezone_doc[] =
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003492PyDoc_STR("Fixed offset from UTC implementation of tzinfo.");
3493
3494static PyTypeObject PyDateTime_TimeZoneType = {
3495 PyVarObject_HEAD_INIT(NULL, 0)
3496 "datetime.timezone", /* tp_name */
3497 sizeof(PyDateTime_TimeZone), /* tp_basicsize */
3498 0, /* tp_itemsize */
3499 (destructor)timezone_dealloc, /* tp_dealloc */
3500 0, /* tp_print */
3501 0, /* tp_getattr */
3502 0, /* tp_setattr */
3503 0, /* tp_reserved */
Alexander Belopolskya11d8c02010-07-06 23:19:45 +00003504 (reprfunc)timezone_repr, /* tp_repr */
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003505 0, /* tp_as_number */
3506 0, /* tp_as_sequence */
3507 0, /* tp_as_mapping */
3508 (hashfunc)timezone_hash, /* tp_hash */
3509 0, /* tp_call */
3510 (reprfunc)timezone_str, /* tp_str */
3511 0, /* tp_getattro */
3512 0, /* tp_setattro */
3513 0, /* tp_as_buffer */
3514 Py_TPFLAGS_DEFAULT, /* tp_flags */
3515 timezone_doc, /* tp_doc */
3516 0, /* tp_traverse */
3517 0, /* tp_clear */
3518 (richcmpfunc)timezone_richcompare,/* tp_richcompare */
3519 0, /* tp_weaklistoffset */
3520 0, /* tp_iter */
3521 0, /* tp_iternext */
3522 timezone_methods, /* tp_methods */
3523 0, /* tp_members */
3524 0, /* tp_getset */
3525 &PyDateTime_TZInfoType, /* tp_base */
3526 0, /* tp_dict */
3527 0, /* tp_descr_get */
3528 0, /* tp_descr_set */
3529 0, /* tp_dictoffset */
3530 0, /* tp_init */
3531 0, /* tp_alloc */
3532 timezone_new, /* tp_new */
3533};
3534
Tim Peters2a799bf2002-12-16 20:18:38 +00003535/*
Tim Peters37f39822003-01-10 03:49:02 +00003536 * PyDateTime_Time implementation.
Tim Peters2a799bf2002-12-16 20:18:38 +00003537 */
3538
Tim Peters37f39822003-01-10 03:49:02 +00003539/* Accessor properties.
Tim Peters2a799bf2002-12-16 20:18:38 +00003540 */
3541
3542static PyObject *
Tim Peters37f39822003-01-10 03:49:02 +00003543time_hour(PyDateTime_Time *self, void *unused)
Tim Peters2a799bf2002-12-16 20:18:38 +00003544{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003545 return PyLong_FromLong(TIME_GET_HOUR(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00003546}
3547
Tim Peters37f39822003-01-10 03:49:02 +00003548static PyObject *
3549time_minute(PyDateTime_Time *self, void *unused)
3550{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003551 return PyLong_FromLong(TIME_GET_MINUTE(self));
Tim Peters37f39822003-01-10 03:49:02 +00003552}
3553
3554/* The name time_second conflicted with some platform header file. */
3555static PyObject *
3556py_time_second(PyDateTime_Time *self, void *unused)
3557{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003558 return PyLong_FromLong(TIME_GET_SECOND(self));
Tim Peters37f39822003-01-10 03:49:02 +00003559}
3560
3561static PyObject *
3562time_microsecond(PyDateTime_Time *self, void *unused)
3563{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003564 return PyLong_FromLong(TIME_GET_MICROSECOND(self));
Tim Peters37f39822003-01-10 03:49:02 +00003565}
3566
3567static PyObject *
3568time_tzinfo(PyDateTime_Time *self, void *unused)
3569{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003570 PyObject *result = HASTZINFO(self) ? self->tzinfo : Py_None;
3571 Py_INCREF(result);
3572 return result;
Tim Peters37f39822003-01-10 03:49:02 +00003573}
3574
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04003575static PyObject *
3576time_fold(PyDateTime_Time *self, void *unused)
3577{
3578 return PyLong_FromLong(TIME_GET_FOLD(self));
3579}
3580
Tim Peters37f39822003-01-10 03:49:02 +00003581static PyGetSetDef time_getset[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003582 {"hour", (getter)time_hour},
3583 {"minute", (getter)time_minute},
3584 {"second", (getter)py_time_second},
3585 {"microsecond", (getter)time_microsecond},
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04003586 {"tzinfo", (getter)time_tzinfo},
3587 {"fold", (getter)time_fold},
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003588 {NULL}
Tim Peters2a799bf2002-12-16 20:18:38 +00003589};
3590
3591/*
3592 * Constructors.
3593 */
3594
Martin v. Löwis02cbf4a2006-02-27 17:20:04 +00003595static char *time_kws[] = {"hour", "minute", "second", "microsecond",
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04003596 "tzinfo", "fold", NULL};
Tim Peters12bf3392002-12-24 05:41:27 +00003597
Tim Peters2a799bf2002-12-16 20:18:38 +00003598static PyObject *
Tim Peters37f39822003-01-10 03:49:02 +00003599time_new(PyTypeObject *type, PyObject *args, PyObject *kw)
Tim Peters2a799bf2002-12-16 20:18:38 +00003600{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003601 PyObject *self = NULL;
3602 PyObject *state;
3603 int hour = 0;
3604 int minute = 0;
3605 int second = 0;
3606 int usecond = 0;
3607 PyObject *tzinfo = Py_None;
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04003608 int fold = 0;
Tim Peters2a799bf2002-12-16 20:18:38 +00003609
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003610 /* Check for invocation from pickle with __getstate__ state */
3611 if (PyTuple_GET_SIZE(args) >= 1 &&
3612 PyTuple_GET_SIZE(args) <= 2 &&
3613 PyBytes_Check(state = PyTuple_GET_ITEM(args, 0)) &&
3614 PyBytes_GET_SIZE(state) == _PyDateTime_TIME_DATASIZE &&
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04003615 (0x7F & ((unsigned char) (PyBytes_AS_STRING(state)[0]))) < 24)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003616 {
3617 PyDateTime_Time *me;
3618 char aware;
Tim Peters70533e22003-02-01 04:40:04 +00003619
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003620 if (PyTuple_GET_SIZE(args) == 2) {
3621 tzinfo = PyTuple_GET_ITEM(args, 1);
3622 if (check_tzinfo_subclass(tzinfo) < 0) {
3623 PyErr_SetString(PyExc_TypeError, "bad "
3624 "tzinfo state arg");
3625 return NULL;
3626 }
3627 }
3628 aware = (char)(tzinfo != Py_None);
3629 me = (PyDateTime_Time *) (type->tp_alloc(type, aware));
3630 if (me != NULL) {
3631 char *pdata = PyBytes_AS_STRING(state);
Tim Peters70533e22003-02-01 04:40:04 +00003632
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003633 memcpy(me->data, pdata, _PyDateTime_TIME_DATASIZE);
3634 me->hashcode = -1;
3635 me->hastzinfo = aware;
3636 if (aware) {
3637 Py_INCREF(tzinfo);
3638 me->tzinfo = tzinfo;
3639 }
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04003640 if (pdata[0] & (1 << 7)) {
3641 me->data[0] -= 128;
3642 me->fold = 1;
3643 }
3644 else {
3645 me->fold = 0;
3646 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003647 }
3648 return (PyObject *)me;
3649 }
Guido van Rossum177e41a2003-01-30 22:06:23 +00003650
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04003651 if (PyArg_ParseTupleAndKeywords(args, kw, "|iiiiO$i", time_kws,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003652 &hour, &minute, &second, &usecond,
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04003653 &tzinfo, &fold)) {
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04003654 self = new_time_ex2(hour, minute, second, usecond, tzinfo, fold,
3655 type);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003656 }
3657 return self;
Tim Peters2a799bf2002-12-16 20:18:38 +00003658}
3659
3660/*
3661 * Destructor.
3662 */
3663
3664static void
Tim Peters37f39822003-01-10 03:49:02 +00003665time_dealloc(PyDateTime_Time *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00003666{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003667 if (HASTZINFO(self)) {
3668 Py_XDECREF(self->tzinfo);
3669 }
3670 Py_TYPE(self)->tp_free((PyObject *)self);
Tim Peters2a799bf2002-12-16 20:18:38 +00003671}
3672
3673/*
Tim Peters855fe882002-12-22 03:43:39 +00003674 * Indirect access to tzinfo methods.
Tim Peters2a799bf2002-12-16 20:18:38 +00003675 */
3676
Tim Peters2a799bf2002-12-16 20:18:38 +00003677/* These are all METH_NOARGS, so don't need to check the arglist. */
3678static PyObject *
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003679time_utcoffset(PyObject *self, PyObject *unused) {
3680 return call_utcoffset(GET_TIME_TZINFO(self), Py_None);
Tim Peters2a799bf2002-12-16 20:18:38 +00003681}
3682
3683static PyObject *
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003684time_dst(PyObject *self, PyObject *unused) {
3685 return call_dst(GET_TIME_TZINFO(self), Py_None);
Tim Peters855fe882002-12-22 03:43:39 +00003686}
3687
3688static PyObject *
Tim Peters37f39822003-01-10 03:49:02 +00003689time_tzname(PyDateTime_Time *self, PyObject *unused) {
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003690 return call_tzname(GET_TIME_TZINFO(self), Py_None);
Tim Peters2a799bf2002-12-16 20:18:38 +00003691}
3692
3693/*
Tim Peters37f39822003-01-10 03:49:02 +00003694 * Various ways to turn a time into a string.
Tim Peters2a799bf2002-12-16 20:18:38 +00003695 */
3696
3697static PyObject *
Tim Peters37f39822003-01-10 03:49:02 +00003698time_repr(PyDateTime_Time *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00003699{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003700 const char *type_name = Py_TYPE(self)->tp_name;
3701 int h = TIME_GET_HOUR(self);
3702 int m = TIME_GET_MINUTE(self);
3703 int s = TIME_GET_SECOND(self);
3704 int us = TIME_GET_MICROSECOND(self);
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04003705 int fold = TIME_GET_FOLD(self);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003706 PyObject *result = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00003707
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003708 if (us)
3709 result = PyUnicode_FromFormat("%s(%d, %d, %d, %d)",
3710 type_name, h, m, s, us);
3711 else if (s)
3712 result = PyUnicode_FromFormat("%s(%d, %d, %d)",
3713 type_name, h, m, s);
3714 else
3715 result = PyUnicode_FromFormat("%s(%d, %d)", type_name, h, m);
3716 if (result != NULL && HASTZINFO(self))
3717 result = append_keyword_tzinfo(result, self->tzinfo);
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04003718 if (result != NULL && fold)
3719 result = append_keyword_fold(result, fold);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003720 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00003721}
3722
Tim Peters37f39822003-01-10 03:49:02 +00003723static PyObject *
3724time_str(PyDateTime_Time *self)
3725{
Victor Stinnerad8c83a2016-09-05 17:53:15 -07003726 return _PyObject_CallMethodId((PyObject *)self, &PyId_isoformat, NULL);
Tim Peters37f39822003-01-10 03:49:02 +00003727}
Tim Peters2a799bf2002-12-16 20:18:38 +00003728
3729static PyObject *
Alexander Belopolskya2998a62016-03-06 14:58:43 -05003730time_isoformat(PyDateTime_Time *self, PyObject *args, PyObject *kw)
Tim Peters2a799bf2002-12-16 20:18:38 +00003731{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003732 char buf[100];
Alexander Belopolskya2998a62016-03-06 14:58:43 -05003733 char *timespec = NULL;
3734 static char *keywords[] = {"timespec", NULL};
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003735 PyObject *result;
Ezio Melotti3f5db392013-01-27 06:20:14 +02003736 int us = TIME_GET_MICROSECOND(self);
Alexander Belopolskya2998a62016-03-06 14:58:43 -05003737 static char *specs[][2] = {
3738 {"hours", "%02d"},
3739 {"minutes", "%02d:%02d"},
3740 {"seconds", "%02d:%02d:%02d"},
3741 {"milliseconds", "%02d:%02d:%02d.%03d"},
3742 {"microseconds", "%02d:%02d:%02d.%06d"},
3743 };
3744 size_t given_spec;
Tim Peters2a799bf2002-12-16 20:18:38 +00003745
Alexander Belopolskya2998a62016-03-06 14:58:43 -05003746 if (!PyArg_ParseTupleAndKeywords(args, kw, "|s:isoformat", keywords, &timespec))
3747 return NULL;
3748
3749 if (timespec == NULL || strcmp(timespec, "auto") == 0) {
3750 if (us == 0) {
3751 /* seconds */
3752 given_spec = 2;
3753 }
3754 else {
3755 /* microseconds */
3756 given_spec = 4;
3757 }
3758 }
3759 else {
3760 for (given_spec = 0; given_spec < Py_ARRAY_LENGTH(specs); given_spec++) {
3761 if (strcmp(timespec, specs[given_spec][0]) == 0) {
3762 if (given_spec == 3) {
3763 /* milliseconds */
3764 us = us / 1000;
3765 }
3766 break;
3767 }
3768 }
3769 }
3770
3771 if (given_spec == Py_ARRAY_LENGTH(specs)) {
3772 PyErr_Format(PyExc_ValueError, "Unknown timespec value");
3773 return NULL;
3774 }
3775 else {
3776 result = PyUnicode_FromFormat(specs[given_spec][1],
3777 TIME_GET_HOUR(self), TIME_GET_MINUTE(self),
3778 TIME_GET_SECOND(self), us);
3779 }
Tim Peters37f39822003-01-10 03:49:02 +00003780
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003781 if (result == NULL || !HASTZINFO(self) || self->tzinfo == Py_None)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003782 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00003783
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003784 /* We need to append the UTC offset. */
3785 if (format_utcoffset(buf, sizeof(buf), ":", self->tzinfo,
3786 Py_None) < 0) {
3787 Py_DECREF(result);
3788 return NULL;
3789 }
3790 PyUnicode_AppendAndDel(&result, PyUnicode_FromString(buf));
3791 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00003792}
3793
Tim Peters37f39822003-01-10 03:49:02 +00003794static PyObject *
3795time_strftime(PyDateTime_Time *self, PyObject *args, PyObject *kw)
3796{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003797 PyObject *result;
3798 PyObject *tuple;
3799 PyObject *format;
3800 static char *keywords[] = {"format", NULL};
Tim Peters37f39822003-01-10 03:49:02 +00003801
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003802 if (! PyArg_ParseTupleAndKeywords(args, kw, "U:strftime", keywords,
3803 &format))
3804 return NULL;
Tim Peters37f39822003-01-10 03:49:02 +00003805
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003806 /* Python's strftime does insane things with the year part of the
3807 * timetuple. The year is forced to (the otherwise nonsensical)
Alexander Belopolskyb8bb4662011-01-08 00:13:34 +00003808 * 1900 to work around that.
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003809 */
3810 tuple = Py_BuildValue("iiiiiiiii",
3811 1900, 1, 1, /* year, month, day */
3812 TIME_GET_HOUR(self),
3813 TIME_GET_MINUTE(self),
3814 TIME_GET_SECOND(self),
3815 0, 1, -1); /* weekday, daynum, dst */
3816 if (tuple == NULL)
3817 return NULL;
3818 assert(PyTuple_Size(tuple) == 9);
3819 result = wrap_strftime((PyObject *)self, format, tuple,
3820 Py_None);
3821 Py_DECREF(tuple);
3822 return result;
Tim Peters37f39822003-01-10 03:49:02 +00003823}
Tim Peters2a799bf2002-12-16 20:18:38 +00003824
3825/*
3826 * Miscellaneous methods.
3827 */
3828
Tim Peters37f39822003-01-10 03:49:02 +00003829static PyObject *
Guido van Rossum19960592006-08-24 17:29:38 +00003830time_richcompare(PyObject *self, PyObject *other, int op)
Tim Peters37f39822003-01-10 03:49:02 +00003831{
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003832 PyObject *result = NULL;
3833 PyObject *offset1, *offset2;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003834 int diff;
Tim Peters37f39822003-01-10 03:49:02 +00003835
Brian Curtindfc80e32011-08-10 20:28:54 -05003836 if (! PyTime_Check(other))
3837 Py_RETURN_NOTIMPLEMENTED;
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003838
3839 if (GET_TIME_TZINFO(self) == GET_TIME_TZINFO(other)) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003840 diff = memcmp(((PyDateTime_Time *)self)->data,
3841 ((PyDateTime_Time *)other)->data,
3842 _PyDateTime_TIME_DATASIZE);
3843 return diff_to_bool(diff, op);
3844 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003845 offset1 = time_utcoffset(self, NULL);
3846 if (offset1 == NULL)
3847 return NULL;
3848 offset2 = time_utcoffset(other, NULL);
3849 if (offset2 == NULL)
3850 goto done;
3851 /* If they're both naive, or both aware and have the same offsets,
3852 * we get off cheap. Note that if they're both naive, offset1 ==
3853 * offset2 == Py_None at this point.
3854 */
3855 if ((offset1 == offset2) ||
3856 (PyDelta_Check(offset1) && PyDelta_Check(offset2) &&
3857 delta_cmp(offset1, offset2) == 0)) {
3858 diff = memcmp(((PyDateTime_Time *)self)->data,
3859 ((PyDateTime_Time *)other)->data,
3860 _PyDateTime_TIME_DATASIZE);
3861 result = diff_to_bool(diff, op);
3862 }
3863 /* The hard case: both aware with different UTC offsets */
3864 else if (offset1 != Py_None && offset2 != Py_None) {
3865 int offsecs1, offsecs2;
3866 assert(offset1 != offset2); /* else last "if" handled it */
3867 offsecs1 = TIME_GET_HOUR(self) * 3600 +
3868 TIME_GET_MINUTE(self) * 60 +
3869 TIME_GET_SECOND(self) -
3870 GET_TD_DAYS(offset1) * 86400 -
3871 GET_TD_SECONDS(offset1);
3872 offsecs2 = TIME_GET_HOUR(other) * 3600 +
3873 TIME_GET_MINUTE(other) * 60 +
3874 TIME_GET_SECOND(other) -
3875 GET_TD_DAYS(offset2) * 86400 -
3876 GET_TD_SECONDS(offset2);
3877 diff = offsecs1 - offsecs2;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003878 if (diff == 0)
3879 diff = TIME_GET_MICROSECOND(self) -
3880 TIME_GET_MICROSECOND(other);
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003881 result = diff_to_bool(diff, op);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003882 }
Alexander Belopolsky08313822012-06-15 20:19:47 -04003883 else if (op == Py_EQ) {
3884 result = Py_False;
3885 Py_INCREF(result);
3886 }
3887 else if (op == Py_NE) {
3888 result = Py_True;
3889 Py_INCREF(result);
3890 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003891 else {
3892 PyErr_SetString(PyExc_TypeError,
3893 "can't compare offset-naive and "
3894 "offset-aware times");
3895 }
3896 done:
3897 Py_DECREF(offset1);
3898 Py_XDECREF(offset2);
3899 return result;
Tim Peters37f39822003-01-10 03:49:02 +00003900}
3901
Benjamin Peterson8f67d082010-10-17 20:54:53 +00003902static Py_hash_t
Tim Peters37f39822003-01-10 03:49:02 +00003903time_hash(PyDateTime_Time *self)
3904{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003905 if (self->hashcode == -1) {
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04003906 PyObject *offset, *self0;
Victor Stinner423c16b2017-01-03 23:47:12 +01003907 if (TIME_GET_FOLD(self)) {
3908 self0 = new_time_ex2(TIME_GET_HOUR(self),
3909 TIME_GET_MINUTE(self),
3910 TIME_GET_SECOND(self),
3911 TIME_GET_MICROSECOND(self),
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04003912 HASTZINFO(self) ? self->tzinfo : Py_None,
3913 0, Py_TYPE(self));
3914 if (self0 == NULL)
3915 return -1;
3916 }
3917 else {
3918 self0 = (PyObject *)self;
3919 Py_INCREF(self0);
3920 }
3921 offset = time_utcoffset(self0, NULL);
3922 Py_DECREF(self0);
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003923
3924 if (offset == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003925 return -1;
Tim Peters37f39822003-01-10 03:49:02 +00003926
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003927 /* Reduce this to a hash of another object. */
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003928 if (offset == Py_None)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003929 self->hashcode = generic_hash(
3930 (unsigned char *)self->data, _PyDateTime_TIME_DATASIZE);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003931 else {
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003932 PyObject *temp1, *temp2;
3933 int seconds, microseconds;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003934 assert(HASTZINFO(self));
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003935 seconds = TIME_GET_HOUR(self) * 3600 +
3936 TIME_GET_MINUTE(self) * 60 +
3937 TIME_GET_SECOND(self);
3938 microseconds = TIME_GET_MICROSECOND(self);
3939 temp1 = new_delta(0, seconds, microseconds, 1);
3940 if (temp1 == NULL) {
3941 Py_DECREF(offset);
3942 return -1;
3943 }
3944 temp2 = delta_subtract(temp1, offset);
3945 Py_DECREF(temp1);
3946 if (temp2 == NULL) {
3947 Py_DECREF(offset);
3948 return -1;
3949 }
3950 self->hashcode = PyObject_Hash(temp2);
3951 Py_DECREF(temp2);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003952 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003953 Py_DECREF(offset);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003954 }
3955 return self->hashcode;
Tim Peters37f39822003-01-10 03:49:02 +00003956}
Tim Peters2a799bf2002-12-16 20:18:38 +00003957
Tim Peters12bf3392002-12-24 05:41:27 +00003958static PyObject *
Tim Peters37f39822003-01-10 03:49:02 +00003959time_replace(PyDateTime_Time *self, PyObject *args, PyObject *kw)
Tim Peters12bf3392002-12-24 05:41:27 +00003960{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003961 PyObject *clone;
3962 PyObject *tuple;
3963 int hh = TIME_GET_HOUR(self);
3964 int mm = TIME_GET_MINUTE(self);
3965 int ss = TIME_GET_SECOND(self);
3966 int us = TIME_GET_MICROSECOND(self);
3967 PyObject *tzinfo = HASTZINFO(self) ? self->tzinfo : Py_None;
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04003968 int fold = TIME_GET_FOLD(self);
Tim Peters12bf3392002-12-24 05:41:27 +00003969
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04003970 if (! PyArg_ParseTupleAndKeywords(args, kw, "|iiiiO$i:replace",
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003971 time_kws,
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04003972 &hh, &mm, &ss, &us, &tzinfo, &fold))
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003973 return NULL;
Serhiy Storchaka314d6fc2017-03-31 22:48:16 +03003974 if (fold != 0 && fold != 1) {
3975 PyErr_SetString(PyExc_ValueError,
3976 "fold must be either 0 or 1");
3977 return NULL;
3978 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003979 tuple = Py_BuildValue("iiiiO", hh, mm, ss, us, tzinfo);
3980 if (tuple == NULL)
3981 return NULL;
3982 clone = time_new(Py_TYPE(self), tuple, NULL);
Alexander Belopolsky47649ab2016-08-08 17:05:40 -04003983 if (clone != NULL) {
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04003984 TIME_SET_FOLD(clone, fold);
Alexander Belopolsky47649ab2016-08-08 17:05:40 -04003985 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003986 Py_DECREF(tuple);
3987 return clone;
Tim Peters12bf3392002-12-24 05:41:27 +00003988}
3989
Tim Peters371935f2003-02-01 01:52:50 +00003990/* Pickle support, a simple use of __reduce__. */
Tim Peters2a799bf2002-12-16 20:18:38 +00003991
Tim Peters33e0f382003-01-10 02:05:14 +00003992/* Let basestate be the non-tzinfo data string.
Tim Peters2a799bf2002-12-16 20:18:38 +00003993 * If tzinfo is None, this returns (basestate,), else (basestate, tzinfo).
3994 * So it's a tuple in any (non-error) case.
Tim Petersb57f8f02003-02-01 02:54:15 +00003995 * __getstate__ isn't exposed.
Tim Peters2a799bf2002-12-16 20:18:38 +00003996 */
3997static PyObject *
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04003998time_getstate(PyDateTime_Time *self, int proto)
Tim Peters2a799bf2002-12-16 20:18:38 +00003999{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004000 PyObject *basestate;
4001 PyObject *result = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00004002
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004003 basestate = PyBytes_FromStringAndSize((char *)self->data,
4004 _PyDateTime_TIME_DATASIZE);
4005 if (basestate != NULL) {
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004006 if (proto > 3 && TIME_GET_FOLD(self))
4007 /* Set the first bit of the first byte */
4008 PyBytes_AS_STRING(basestate)[0] |= (1 << 7);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004009 if (! HASTZINFO(self) || self->tzinfo == Py_None)
4010 result = PyTuple_Pack(1, basestate);
4011 else
4012 result = PyTuple_Pack(2, basestate, self->tzinfo);
4013 Py_DECREF(basestate);
4014 }
4015 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00004016}
4017
4018static PyObject *
Serhiy Storchaka546ce652016-11-22 00:29:42 +02004019time_reduce_ex(PyDateTime_Time *self, PyObject *args)
Tim Peters2a799bf2002-12-16 20:18:38 +00004020{
Serhiy Storchaka546ce652016-11-22 00:29:42 +02004021 int proto;
4022 if (!PyArg_ParseTuple(args, "i:__reduce_ex__", &proto))
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004023 return NULL;
4024
4025 return Py_BuildValue("(ON)", Py_TYPE(self), time_getstate(self, proto));
Tim Peters2a799bf2002-12-16 20:18:38 +00004026}
4027
Serhiy Storchaka546ce652016-11-22 00:29:42 +02004028static PyObject *
4029time_reduce(PyDateTime_Time *self, PyObject *arg)
4030{
4031 return Py_BuildValue("(ON)", Py_TYPE(self), time_getstate(self, 2));
4032}
4033
Tim Peters37f39822003-01-10 03:49:02 +00004034static PyMethodDef time_methods[] = {
Guido van Rossum177e41a2003-01-30 22:06:23 +00004035
Alexander Belopolskya2998a62016-03-06 14:58:43 -05004036 {"isoformat", (PyCFunction)time_isoformat, METH_VARARGS | METH_KEYWORDS,
4037 PyDoc_STR("Return string in ISO 8601 format, [HH[:MM[:SS[.mmm[uuu]]]]]"
4038 "[+HH:MM].\n\n"
4039 "timespec specifies what components of the time to include.\n")},
Tim Peters2a799bf2002-12-16 20:18:38 +00004040
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004041 {"strftime", (PyCFunction)time_strftime, METH_VARARGS | METH_KEYWORDS,
4042 PyDoc_STR("format -> strftime() style string.")},
Tim Peters37f39822003-01-10 03:49:02 +00004043
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004044 {"__format__", (PyCFunction)date_format, METH_VARARGS,
4045 PyDoc_STR("Formats self with strftime.")},
Eric Smith1ba31142007-09-11 18:06:02 +00004046
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004047 {"utcoffset", (PyCFunction)time_utcoffset, METH_NOARGS,
4048 PyDoc_STR("Return self.tzinfo.utcoffset(self).")},
Tim Peters2a799bf2002-12-16 20:18:38 +00004049
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004050 {"tzname", (PyCFunction)time_tzname, METH_NOARGS,
4051 PyDoc_STR("Return self.tzinfo.tzname(self).")},
Tim Peters2a799bf2002-12-16 20:18:38 +00004052
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004053 {"dst", (PyCFunction)time_dst, METH_NOARGS,
4054 PyDoc_STR("Return self.tzinfo.dst(self).")},
Tim Peters2a799bf2002-12-16 20:18:38 +00004055
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004056 {"replace", (PyCFunction)time_replace, METH_VARARGS | METH_KEYWORDS,
4057 PyDoc_STR("Return time with new specified fields.")},
Tim Peters12bf3392002-12-24 05:41:27 +00004058
Serhiy Storchaka546ce652016-11-22 00:29:42 +02004059 {"__reduce_ex__", (PyCFunction)time_reduce_ex, METH_VARARGS,
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004060 PyDoc_STR("__reduce_ex__(proto) -> (cls, state)")},
Guido van Rossum177e41a2003-01-30 22:06:23 +00004061
Serhiy Storchaka546ce652016-11-22 00:29:42 +02004062 {"__reduce__", (PyCFunction)time_reduce, METH_NOARGS,
4063 PyDoc_STR("__reduce__() -> (cls, state)")},
4064
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004065 {NULL, NULL}
Tim Peters2a799bf2002-12-16 20:18:38 +00004066};
4067
Serhiy Storchaka2d06e842015-12-25 19:53:18 +02004068static const char time_doc[] =
Raymond Hettinger3a4231d2004-12-19 20:13:24 +00004069PyDoc_STR("time([hour[, minute[, second[, microsecond[, tzinfo]]]]]) --> a time object\n\
4070\n\
4071All arguments are optional. tzinfo may be None, or an instance of\n\
Serhiy Storchaka95949422013-08-27 19:40:23 +03004072a tzinfo subclass. The remaining arguments may be ints.\n");
Tim Peters2a799bf2002-12-16 20:18:38 +00004073
Neal Norwitz227b5332006-03-22 09:28:35 +00004074static PyTypeObject PyDateTime_TimeType = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004075 PyVarObject_HEAD_INIT(NULL, 0)
4076 "datetime.time", /* tp_name */
4077 sizeof(PyDateTime_Time), /* tp_basicsize */
4078 0, /* tp_itemsize */
4079 (destructor)time_dealloc, /* tp_dealloc */
4080 0, /* tp_print */
4081 0, /* tp_getattr */
4082 0, /* tp_setattr */
4083 0, /* tp_reserved */
4084 (reprfunc)time_repr, /* tp_repr */
Benjamin Petersonee6bdc02014-03-20 18:00:35 -05004085 0, /* tp_as_number */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004086 0, /* tp_as_sequence */
4087 0, /* tp_as_mapping */
4088 (hashfunc)time_hash, /* tp_hash */
4089 0, /* tp_call */
4090 (reprfunc)time_str, /* tp_str */
4091 PyObject_GenericGetAttr, /* tp_getattro */
4092 0, /* tp_setattro */
4093 0, /* tp_as_buffer */
4094 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
4095 time_doc, /* tp_doc */
4096 0, /* tp_traverse */
4097 0, /* tp_clear */
4098 time_richcompare, /* tp_richcompare */
4099 0, /* tp_weaklistoffset */
4100 0, /* tp_iter */
4101 0, /* tp_iternext */
4102 time_methods, /* tp_methods */
4103 0, /* tp_members */
4104 time_getset, /* tp_getset */
4105 0, /* tp_base */
4106 0, /* tp_dict */
4107 0, /* tp_descr_get */
4108 0, /* tp_descr_set */
4109 0, /* tp_dictoffset */
4110 0, /* tp_init */
4111 time_alloc, /* tp_alloc */
4112 time_new, /* tp_new */
4113 0, /* tp_free */
Tim Peters2a799bf2002-12-16 20:18:38 +00004114};
4115
4116/*
Tim Petersa9bc1682003-01-11 03:39:11 +00004117 * PyDateTime_DateTime implementation.
Tim Peters2a799bf2002-12-16 20:18:38 +00004118 */
4119
Tim Petersa9bc1682003-01-11 03:39:11 +00004120/* Accessor properties. Properties for day, month, and year are inherited
4121 * from date.
Tim Peters2a799bf2002-12-16 20:18:38 +00004122 */
4123
4124static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004125datetime_hour(PyDateTime_DateTime *self, void *unused)
Tim Peters2a799bf2002-12-16 20:18:38 +00004126{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004127 return PyLong_FromLong(DATE_GET_HOUR(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00004128}
4129
Tim Petersa9bc1682003-01-11 03:39:11 +00004130static PyObject *
4131datetime_minute(PyDateTime_DateTime *self, void *unused)
4132{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004133 return PyLong_FromLong(DATE_GET_MINUTE(self));
Tim Petersa9bc1682003-01-11 03:39:11 +00004134}
4135
4136static PyObject *
4137datetime_second(PyDateTime_DateTime *self, void *unused)
4138{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004139 return PyLong_FromLong(DATE_GET_SECOND(self));
Tim Petersa9bc1682003-01-11 03:39:11 +00004140}
4141
4142static PyObject *
4143datetime_microsecond(PyDateTime_DateTime *self, void *unused)
4144{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004145 return PyLong_FromLong(DATE_GET_MICROSECOND(self));
Tim Petersa9bc1682003-01-11 03:39:11 +00004146}
4147
4148static PyObject *
4149datetime_tzinfo(PyDateTime_DateTime *self, void *unused)
4150{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004151 PyObject *result = HASTZINFO(self) ? self->tzinfo : Py_None;
4152 Py_INCREF(result);
4153 return result;
Tim Petersa9bc1682003-01-11 03:39:11 +00004154}
4155
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004156static PyObject *
4157datetime_fold(PyDateTime_DateTime *self, void *unused)
4158{
4159 return PyLong_FromLong(DATE_GET_FOLD(self));
4160}
4161
Tim Petersa9bc1682003-01-11 03:39:11 +00004162static PyGetSetDef datetime_getset[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004163 {"hour", (getter)datetime_hour},
4164 {"minute", (getter)datetime_minute},
4165 {"second", (getter)datetime_second},
4166 {"microsecond", (getter)datetime_microsecond},
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004167 {"tzinfo", (getter)datetime_tzinfo},
4168 {"fold", (getter)datetime_fold},
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004169 {NULL}
Tim Peters2a799bf2002-12-16 20:18:38 +00004170};
4171
4172/*
4173 * Constructors.
Tim Peters2a799bf2002-12-16 20:18:38 +00004174 */
4175
Martin v. Löwis02cbf4a2006-02-27 17:20:04 +00004176static char *datetime_kws[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004177 "year", "month", "day", "hour", "minute", "second",
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004178 "microsecond", "tzinfo", "fold", NULL
Tim Peters12bf3392002-12-24 05:41:27 +00004179};
4180
Tim Peters2a799bf2002-12-16 20:18:38 +00004181static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004182datetime_new(PyTypeObject *type, PyObject *args, PyObject *kw)
Tim Peters2a799bf2002-12-16 20:18:38 +00004183{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004184 PyObject *self = NULL;
4185 PyObject *state;
4186 int year;
4187 int month;
4188 int day;
4189 int hour = 0;
4190 int minute = 0;
4191 int second = 0;
4192 int usecond = 0;
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004193 int fold = 0;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004194 PyObject *tzinfo = Py_None;
Tim Peters2a799bf2002-12-16 20:18:38 +00004195
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004196 /* Check for invocation from pickle with __getstate__ state */
4197 if (PyTuple_GET_SIZE(args) >= 1 &&
4198 PyTuple_GET_SIZE(args) <= 2 &&
4199 PyBytes_Check(state = PyTuple_GET_ITEM(args, 0)) &&
4200 PyBytes_GET_SIZE(state) == _PyDateTime_DATETIME_DATASIZE &&
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004201 MONTH_IS_SANE(PyBytes_AS_STRING(state)[2] & 0x7F))
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004202 {
4203 PyDateTime_DateTime *me;
4204 char aware;
Tim Peters70533e22003-02-01 04:40:04 +00004205
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004206 if (PyTuple_GET_SIZE(args) == 2) {
4207 tzinfo = PyTuple_GET_ITEM(args, 1);
4208 if (check_tzinfo_subclass(tzinfo) < 0) {
4209 PyErr_SetString(PyExc_TypeError, "bad "
4210 "tzinfo state arg");
4211 return NULL;
4212 }
4213 }
4214 aware = (char)(tzinfo != Py_None);
4215 me = (PyDateTime_DateTime *) (type->tp_alloc(type , aware));
4216 if (me != NULL) {
4217 char *pdata = PyBytes_AS_STRING(state);
Tim Peters70533e22003-02-01 04:40:04 +00004218
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004219 memcpy(me->data, pdata, _PyDateTime_DATETIME_DATASIZE);
4220 me->hashcode = -1;
4221 me->hastzinfo = aware;
4222 if (aware) {
4223 Py_INCREF(tzinfo);
4224 me->tzinfo = tzinfo;
4225 }
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004226 if (pdata[2] & (1 << 7)) {
4227 me->data[2] -= 128;
4228 me->fold = 1;
4229 }
4230 else {
4231 me->fold = 0;
4232 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004233 }
4234 return (PyObject *)me;
4235 }
Guido van Rossum177e41a2003-01-30 22:06:23 +00004236
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004237 if (PyArg_ParseTupleAndKeywords(args, kw, "iii|iiiiO$i", datetime_kws,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004238 &year, &month, &day, &hour, &minute,
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004239 &second, &usecond, &tzinfo, &fold)) {
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004240 self = new_datetime_ex2(year, month, day,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004241 hour, minute, second, usecond,
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004242 tzinfo, fold, type);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004243 }
4244 return self;
Tim Peters2a799bf2002-12-16 20:18:38 +00004245}
4246
Alexander Belopolsky3e7a3cb2016-09-28 17:31:35 -04004247/* TM_FUNC is the shared type of _PyTime_localtime() and
4248 * _PyTime_gmtime(). */
4249typedef int (*TM_FUNC)(time_t timer, struct tm*);
Tim Petersa9bc1682003-01-11 03:39:11 +00004250
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004251/* As of version 2015f max fold in IANA database is
4252 * 23 hours at 1969-09-30 13:00:00 in Kwajalein. */
Benjamin Petersonaf580df2016-09-06 10:46:49 -07004253static long long max_fold_seconds = 24 * 3600;
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004254/* NB: date(1970,1,1).toordinal() == 719163 */
Benjamin Petersonac965ca2016-09-18 18:12:21 -07004255static long long epoch = 719163LL * 24 * 60 * 60;
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004256
Benjamin Petersonaf580df2016-09-06 10:46:49 -07004257static long long
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004258utc_to_seconds(int year, int month, int day,
4259 int hour, int minute, int second)
4260{
Victor Stinnerb67f0962017-02-10 10:34:02 +01004261 long long ordinal;
4262
4263 /* ymd_to_ord() doesn't support year <= 0 */
4264 if (year < MINYEAR || year > MAXYEAR) {
4265 PyErr_Format(PyExc_ValueError, "year %i is out of range", year);
4266 return -1;
4267 }
4268
4269 ordinal = ymd_to_ord(year, month, day);
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004270 return ((ordinal * 24 + hour) * 60 + minute) * 60 + second;
4271}
4272
Benjamin Petersonaf580df2016-09-06 10:46:49 -07004273static long long
4274local(long long u)
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004275{
4276 struct tm local_time;
Alexander Belopolsky8e1d3a22016-07-25 13:54:51 -04004277 time_t t;
4278 u -= epoch;
4279 t = u;
4280 if (t != u) {
4281 PyErr_SetString(PyExc_OverflowError,
4282 "timestamp out of range for platform time_t");
4283 return -1;
4284 }
Alexander Belopolsky3e7a3cb2016-09-28 17:31:35 -04004285 if (_PyTime_localtime(t, &local_time) != 0)
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004286 return -1;
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004287 return utc_to_seconds(local_time.tm_year + 1900,
4288 local_time.tm_mon + 1,
4289 local_time.tm_mday,
4290 local_time.tm_hour,
4291 local_time.tm_min,
4292 local_time.tm_sec);
4293}
4294
Tim Petersa9bc1682003-01-11 03:39:11 +00004295/* Internal helper.
4296 * Build datetime from a time_t and a distinct count of microseconds.
4297 * Pass localtime or gmtime for f, to control the interpretation of timet.
4298 */
4299static PyObject *
4300datetime_from_timet_and_us(PyObject *cls, TM_FUNC f, time_t timet, int us,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004301 PyObject *tzinfo)
Tim Petersa9bc1682003-01-11 03:39:11 +00004302{
Alexander Belopolsky6d88fa52016-09-10 15:58:31 -04004303 struct tm tm;
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004304 int year, month, day, hour, minute, second, fold = 0;
Tim Petersa9bc1682003-01-11 03:39:11 +00004305
Alexander Belopolsky3e7a3cb2016-09-28 17:31:35 -04004306 if (f(timet, &tm) != 0)
4307 return NULL;
Victor Stinner21f58932012-03-14 00:15:40 +01004308
Alexander Belopolsky6d88fa52016-09-10 15:58:31 -04004309 year = tm.tm_year + 1900;
4310 month = tm.tm_mon + 1;
4311 day = tm.tm_mday;
4312 hour = tm.tm_hour;
4313 minute = tm.tm_min;
Victor Stinner21f58932012-03-14 00:15:40 +01004314 /* The platform localtime/gmtime may insert leap seconds,
Alexander Belopolsky6d88fa52016-09-10 15:58:31 -04004315 * indicated by tm.tm_sec > 59. We don't care about them,
Victor Stinner21f58932012-03-14 00:15:40 +01004316 * except to the extent that passing them on to the datetime
4317 * constructor would raise ValueError for a reason that
4318 * made no sense to the user.
4319 */
Alexander Belopolsky6d88fa52016-09-10 15:58:31 -04004320 second = Py_MIN(59, tm.tm_sec);
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004321
Victor Stinnerb67f0962017-02-10 10:34:02 +01004322 /* local timezone requires to compute fold */
Alexander Belopolsky3e7a3cb2016-09-28 17:31:35 -04004323 if (tzinfo == Py_None && f == _PyTime_localtime) {
Benjamin Petersonaf580df2016-09-06 10:46:49 -07004324 long long probe_seconds, result_seconds, transition;
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004325
4326 result_seconds = utc_to_seconds(year, month, day,
4327 hour, minute, second);
4328 /* Probe max_fold_seconds to detect a fold. */
4329 probe_seconds = local(epoch + timet - max_fold_seconds);
4330 if (probe_seconds == -1)
4331 return NULL;
4332 transition = result_seconds - probe_seconds - max_fold_seconds;
4333 if (transition < 0) {
4334 probe_seconds = local(epoch + timet + transition);
4335 if (probe_seconds == -1)
4336 return NULL;
4337 if (probe_seconds == result_seconds)
4338 fold = 1;
4339 }
4340 }
4341 return new_datetime_ex2(year, month, day, hour,
4342 minute, second, us, tzinfo, fold,
4343 (PyTypeObject *)cls);
Tim Petersa9bc1682003-01-11 03:39:11 +00004344}
4345
4346/* Internal helper.
4347 * Build datetime from a Python timestamp. Pass localtime or gmtime for f,
4348 * to control the interpretation of the timestamp. Since a double doesn't
4349 * have enough bits to cover a datetime's full range of precision, it's
4350 * better to call datetime_from_timet_and_us provided you have a way
4351 * to get that much precision (e.g., C time() isn't good enough).
4352 */
4353static PyObject *
Victor Stinner5d272cc2012-03-13 13:35:55 +01004354datetime_from_timestamp(PyObject *cls, TM_FUNC f, PyObject *timestamp,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004355 PyObject *tzinfo)
Tim Petersa9bc1682003-01-11 03:39:11 +00004356{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004357 time_t timet;
Victor Stinner5d272cc2012-03-13 13:35:55 +01004358 long us;
Tim Petersa9bc1682003-01-11 03:39:11 +00004359
Victor Stinnere4a994d2015-03-30 01:10:14 +02004360 if (_PyTime_ObjectToTimeval(timestamp,
Victor Stinner7667f582015-09-09 01:02:23 +02004361 &timet, &us, _PyTime_ROUND_HALF_EVEN) == -1)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004362 return NULL;
Victor Stinner09e5cf22015-03-30 00:09:18 +02004363
Victor Stinner21f58932012-03-14 00:15:40 +01004364 return datetime_from_timet_and_us(cls, f, timet, (int)us, tzinfo);
Tim Petersa9bc1682003-01-11 03:39:11 +00004365}
4366
4367/* Internal helper.
4368 * Build most accurate possible datetime for current time. Pass localtime or
4369 * gmtime for f as appropriate.
4370 */
4371static PyObject *
4372datetime_best_possible(PyObject *cls, TM_FUNC f, PyObject *tzinfo)
4373{
Victor Stinner09e5cf22015-03-30 00:09:18 +02004374 _PyTime_t ts = _PyTime_GetSystemClock();
Victor Stinner1e2b6882015-09-18 13:23:02 +02004375 time_t secs;
4376 int us;
Victor Stinner09e5cf22015-03-30 00:09:18 +02004377
Victor Stinner1e2b6882015-09-18 13:23:02 +02004378 if (_PyTime_AsTimevalTime_t(ts, &secs, &us, _PyTime_ROUND_FLOOR) < 0)
Victor Stinner09e5cf22015-03-30 00:09:18 +02004379 return NULL;
Victor Stinner1e2b6882015-09-18 13:23:02 +02004380 assert(0 <= us && us <= 999999);
Victor Stinner09e5cf22015-03-30 00:09:18 +02004381
Victor Stinner1e2b6882015-09-18 13:23:02 +02004382 return datetime_from_timet_and_us(cls, f, secs, us, tzinfo);
Tim Petersa9bc1682003-01-11 03:39:11 +00004383}
4384
Larry Hastings61272b72014-01-07 12:41:53 -08004385/*[clinic input]
Larry Hastings31826802013-10-19 00:09:25 -07004386
4387@classmethod
Larry Hastingsed4a1c52013-11-18 09:32:13 -08004388datetime.datetime.now
Larry Hastings31826802013-10-19 00:09:25 -07004389
4390 tz: object = None
4391 Timezone object.
4392
4393Returns new datetime object representing current time local to tz.
4394
4395If no tz is specified, uses local timezone.
Larry Hastings61272b72014-01-07 12:41:53 -08004396[clinic start generated code]*/
Larry Hastings31826802013-10-19 00:09:25 -07004397
Larry Hastings31826802013-10-19 00:09:25 -07004398static PyObject *
Larry Hastings5c661892014-01-24 06:17:25 -08004399datetime_datetime_now_impl(PyTypeObject *type, PyObject *tz)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004400/*[clinic end generated code: output=b3386e5345e2b47a input=80d09869c5267d00]*/
Tim Peters2a799bf2002-12-16 20:18:38 +00004401{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004402 PyObject *self;
Tim Peters2a799bf2002-12-16 20:18:38 +00004403
Larry Hastings31826802013-10-19 00:09:25 -07004404 /* Return best possible local time -- this isn't constrained by the
4405 * precision of a timestamp.
4406 */
4407 if (check_tzinfo_subclass(tz) < 0)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004408 return NULL;
Tim Peters10cadce2003-01-23 19:58:02 +00004409
Larry Hastings5c661892014-01-24 06:17:25 -08004410 self = datetime_best_possible((PyObject *)type,
Alexander Belopolsky3e7a3cb2016-09-28 17:31:35 -04004411 tz == Py_None ? _PyTime_localtime :
4412 _PyTime_gmtime,
Larry Hastings31826802013-10-19 00:09:25 -07004413 tz);
4414 if (self != NULL && tz != Py_None) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004415 /* Convert UTC to tzinfo's zone. */
Serhiy Storchaka576f1322016-01-05 21:27:54 +02004416 self = _PyObject_CallMethodId(tz, &PyId_fromutc, "N", self);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004417 }
4418 return self;
Tim Peters2a799bf2002-12-16 20:18:38 +00004419}
4420
Tim Petersa9bc1682003-01-11 03:39:11 +00004421/* Return best possible UTC time -- this isn't constrained by the
4422 * precision of a timestamp.
4423 */
4424static PyObject *
4425datetime_utcnow(PyObject *cls, PyObject *dummy)
4426{
Alexander Belopolsky3e7a3cb2016-09-28 17:31:35 -04004427 return datetime_best_possible(cls, _PyTime_gmtime, Py_None);
Tim Petersa9bc1682003-01-11 03:39:11 +00004428}
4429
Tim Peters2a799bf2002-12-16 20:18:38 +00004430/* Return new local datetime from timestamp (Python timestamp -- a double). */
4431static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004432datetime_fromtimestamp(PyObject *cls, PyObject *args, PyObject *kw)
Tim Peters2a799bf2002-12-16 20:18:38 +00004433{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004434 PyObject *self;
Victor Stinner5d272cc2012-03-13 13:35:55 +01004435 PyObject *timestamp;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004436 PyObject *tzinfo = Py_None;
4437 static char *keywords[] = {"timestamp", "tz", NULL};
Tim Peters2a799bf2002-12-16 20:18:38 +00004438
Victor Stinner5d272cc2012-03-13 13:35:55 +01004439 if (! PyArg_ParseTupleAndKeywords(args, kw, "O|O:fromtimestamp",
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004440 keywords, &timestamp, &tzinfo))
4441 return NULL;
4442 if (check_tzinfo_subclass(tzinfo) < 0)
4443 return NULL;
Tim Peters2a44a8d2003-01-23 20:53:10 +00004444
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004445 self = datetime_from_timestamp(cls,
Alexander Belopolsky3e7a3cb2016-09-28 17:31:35 -04004446 tzinfo == Py_None ? _PyTime_localtime :
4447 _PyTime_gmtime,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004448 timestamp,
4449 tzinfo);
4450 if (self != NULL && tzinfo != Py_None) {
4451 /* Convert UTC to tzinfo's zone. */
Serhiy Storchaka576f1322016-01-05 21:27:54 +02004452 self = _PyObject_CallMethodId(tzinfo, &PyId_fromutc, "N", self);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004453 }
4454 return self;
Tim Peters2a799bf2002-12-16 20:18:38 +00004455}
4456
Tim Petersa9bc1682003-01-11 03:39:11 +00004457/* Return new UTC datetime from timestamp (Python timestamp -- a double). */
4458static PyObject *
4459datetime_utcfromtimestamp(PyObject *cls, PyObject *args)
4460{
Victor Stinner5d272cc2012-03-13 13:35:55 +01004461 PyObject *timestamp;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004462 PyObject *result = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00004463
Victor Stinner5d272cc2012-03-13 13:35:55 +01004464 if (PyArg_ParseTuple(args, "O:utcfromtimestamp", &timestamp))
Alexander Belopolsky3e7a3cb2016-09-28 17:31:35 -04004465 result = datetime_from_timestamp(cls, _PyTime_gmtime, timestamp,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004466 Py_None);
4467 return result;
Tim Petersa9bc1682003-01-11 03:39:11 +00004468}
4469
Alexander Belopolskyca94f552010-06-17 18:30:34 +00004470/* Return new datetime from _strptime.strptime_datetime(). */
Skip Montanaro0af3ade2005-01-13 04:12:31 +00004471static PyObject *
4472datetime_strptime(PyObject *cls, PyObject *args)
4473{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004474 static PyObject *module = NULL;
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02004475 PyObject *string, *format;
Martin v. Löwisbd928fe2011-10-14 10:20:37 +02004476 _Py_IDENTIFIER(_strptime_datetime);
Skip Montanaro0af3ade2005-01-13 04:12:31 +00004477
Martin v. Löwisd63a3b82011-09-28 07:41:54 +02004478 if (!PyArg_ParseTuple(args, "UU:strptime", &string, &format))
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004479 return NULL;
Skip Montanaro0af3ade2005-01-13 04:12:31 +00004480
Alexander Belopolskyca94f552010-06-17 18:30:34 +00004481 if (module == NULL) {
4482 module = PyImport_ImportModuleNoBlock("_strptime");
Alexander Belopolsky311d2a92010-06-28 14:36:55 +00004483 if (module == NULL)
Alexander Belopolskyca94f552010-06-17 18:30:34 +00004484 return NULL;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004485 }
Victor Stinner20401de2016-12-09 15:24:31 +01004486 return _PyObject_CallMethodIdObjArgs(module, &PyId__strptime_datetime,
4487 cls, string, format, NULL);
Skip Montanaro0af3ade2005-01-13 04:12:31 +00004488}
4489
Tim Petersa9bc1682003-01-11 03:39:11 +00004490/* Return new datetime from date/datetime and time arguments. */
4491static PyObject *
4492datetime_combine(PyObject *cls, PyObject *args, PyObject *kw)
4493{
Alexander Belopolsky43746c32016-08-02 17:49:30 -04004494 static char *keywords[] = {"date", "time", "tzinfo", NULL};
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004495 PyObject *date;
4496 PyObject *time;
Alexander Belopolsky43746c32016-08-02 17:49:30 -04004497 PyObject *tzinfo = NULL;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004498 PyObject *result = NULL;
Tim Petersa9bc1682003-01-11 03:39:11 +00004499
Alexander Belopolsky43746c32016-08-02 17:49:30 -04004500 if (PyArg_ParseTupleAndKeywords(args, kw, "O!O!|O:combine", keywords,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004501 &PyDateTime_DateType, &date,
Alexander Belopolsky43746c32016-08-02 17:49:30 -04004502 &PyDateTime_TimeType, &time, &tzinfo)) {
4503 if (tzinfo == NULL) {
4504 if (HASTZINFO(time))
4505 tzinfo = ((PyDateTime_Time *)time)->tzinfo;
4506 else
4507 tzinfo = Py_None;
4508 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004509 result = PyObject_CallFunction(cls, "iiiiiiiO",
Alexander Belopolsky43746c32016-08-02 17:49:30 -04004510 GET_YEAR(date),
4511 GET_MONTH(date),
4512 GET_DAY(date),
4513 TIME_GET_HOUR(time),
4514 TIME_GET_MINUTE(time),
4515 TIME_GET_SECOND(time),
4516 TIME_GET_MICROSECOND(time),
4517 tzinfo);
4518 if (result)
4519 DATE_SET_FOLD(result, TIME_GET_FOLD(time));
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004520 }
4521 return result;
Tim Petersa9bc1682003-01-11 03:39:11 +00004522}
Tim Peters2a799bf2002-12-16 20:18:38 +00004523
4524/*
4525 * Destructor.
4526 */
4527
4528static void
Tim Petersa9bc1682003-01-11 03:39:11 +00004529datetime_dealloc(PyDateTime_DateTime *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00004530{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004531 if (HASTZINFO(self)) {
4532 Py_XDECREF(self->tzinfo);
4533 }
4534 Py_TYPE(self)->tp_free((PyObject *)self);
Tim Peters2a799bf2002-12-16 20:18:38 +00004535}
4536
4537/*
4538 * Indirect access to tzinfo methods.
4539 */
4540
Tim Peters2a799bf2002-12-16 20:18:38 +00004541/* These are all METH_NOARGS, so don't need to check the arglist. */
4542static PyObject *
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004543datetime_utcoffset(PyObject *self, PyObject *unused) {
4544 return call_utcoffset(GET_DT_TZINFO(self), self);
Tim Peters2a799bf2002-12-16 20:18:38 +00004545}
4546
4547static PyObject *
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004548datetime_dst(PyObject *self, PyObject *unused) {
4549 return call_dst(GET_DT_TZINFO(self), self);
Tim Peters855fe882002-12-22 03:43:39 +00004550}
4551
4552static PyObject *
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004553datetime_tzname(PyObject *self, PyObject *unused) {
4554 return call_tzname(GET_DT_TZINFO(self), self);
Tim Peters2a799bf2002-12-16 20:18:38 +00004555}
4556
4557/*
Tim Petersa9bc1682003-01-11 03:39:11 +00004558 * datetime arithmetic.
Tim Peters2a799bf2002-12-16 20:18:38 +00004559 */
4560
Tim Petersa9bc1682003-01-11 03:39:11 +00004561/* factor must be 1 (to add) or -1 (to subtract). The result inherits
4562 * the tzinfo state of date.
Tim Peters2a799bf2002-12-16 20:18:38 +00004563 */
4564static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004565add_datetime_timedelta(PyDateTime_DateTime *date, PyDateTime_Delta *delta,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004566 int factor)
Tim Peters2a799bf2002-12-16 20:18:38 +00004567{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004568 /* Note that the C-level additions can't overflow, because of
4569 * invariant bounds on the member values.
4570 */
4571 int year = GET_YEAR(date);
4572 int month = GET_MONTH(date);
4573 int day = GET_DAY(date) + GET_TD_DAYS(delta) * factor;
4574 int hour = DATE_GET_HOUR(date);
4575 int minute = DATE_GET_MINUTE(date);
4576 int second = DATE_GET_SECOND(date) + GET_TD_SECONDS(delta) * factor;
4577 int microsecond = DATE_GET_MICROSECOND(date) +
4578 GET_TD_MICROSECONDS(delta) * factor;
Tim Peters2a799bf2002-12-16 20:18:38 +00004579
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004580 assert(factor == 1 || factor == -1);
4581 if (normalize_datetime(&year, &month, &day,
Victor Stinnerb67f0962017-02-10 10:34:02 +01004582 &hour, &minute, &second, &microsecond) < 0) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004583 return NULL;
Victor Stinnerb67f0962017-02-10 10:34:02 +01004584 }
4585
4586 return new_datetime(year, month, day,
4587 hour, minute, second, microsecond,
4588 HASTZINFO(date) ? date->tzinfo : Py_None, 0);
Tim Peters2a799bf2002-12-16 20:18:38 +00004589}
4590
4591static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004592datetime_add(PyObject *left, PyObject *right)
Tim Peters2a799bf2002-12-16 20:18:38 +00004593{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004594 if (PyDateTime_Check(left)) {
4595 /* datetime + ??? */
4596 if (PyDelta_Check(right))
4597 /* datetime + delta */
4598 return add_datetime_timedelta(
4599 (PyDateTime_DateTime *)left,
4600 (PyDateTime_Delta *)right,
4601 1);
4602 }
4603 else if (PyDelta_Check(left)) {
4604 /* delta + datetime */
4605 return add_datetime_timedelta((PyDateTime_DateTime *) right,
4606 (PyDateTime_Delta *) left,
4607 1);
4608 }
Brian Curtindfc80e32011-08-10 20:28:54 -05004609 Py_RETURN_NOTIMPLEMENTED;
Tim Peters2a799bf2002-12-16 20:18:38 +00004610}
4611
4612static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004613datetime_subtract(PyObject *left, PyObject *right)
Tim Peters2a799bf2002-12-16 20:18:38 +00004614{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004615 PyObject *result = Py_NotImplemented;
Tim Peters2a799bf2002-12-16 20:18:38 +00004616
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004617 if (PyDateTime_Check(left)) {
4618 /* datetime - ??? */
4619 if (PyDateTime_Check(right)) {
4620 /* datetime - datetime */
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004621 PyObject *offset1, *offset2, *offdiff = NULL;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004622 int delta_d, delta_s, delta_us;
Tim Peters2a799bf2002-12-16 20:18:38 +00004623
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004624 if (GET_DT_TZINFO(left) == GET_DT_TZINFO(right)) {
4625 offset2 = offset1 = Py_None;
4626 Py_INCREF(offset1);
4627 Py_INCREF(offset2);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004628 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004629 else {
4630 offset1 = datetime_utcoffset(left, NULL);
4631 if (offset1 == NULL)
4632 return NULL;
4633 offset2 = datetime_utcoffset(right, NULL);
4634 if (offset2 == NULL) {
4635 Py_DECREF(offset1);
4636 return NULL;
4637 }
4638 if ((offset1 != Py_None) != (offset2 != Py_None)) {
4639 PyErr_SetString(PyExc_TypeError,
4640 "can't subtract offset-naive and "
4641 "offset-aware datetimes");
4642 Py_DECREF(offset1);
4643 Py_DECREF(offset2);
4644 return NULL;
4645 }
4646 }
4647 if ((offset1 != offset2) &&
4648 delta_cmp(offset1, offset2) != 0) {
4649 offdiff = delta_subtract(offset1, offset2);
4650 if (offdiff == NULL) {
4651 Py_DECREF(offset1);
4652 Py_DECREF(offset2);
4653 return NULL;
4654 }
4655 }
4656 Py_DECREF(offset1);
4657 Py_DECREF(offset2);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004658 delta_d = ymd_to_ord(GET_YEAR(left),
4659 GET_MONTH(left),
4660 GET_DAY(left)) -
4661 ymd_to_ord(GET_YEAR(right),
4662 GET_MONTH(right),
4663 GET_DAY(right));
4664 /* These can't overflow, since the values are
4665 * normalized. At most this gives the number of
4666 * seconds in one day.
4667 */
4668 delta_s = (DATE_GET_HOUR(left) -
4669 DATE_GET_HOUR(right)) * 3600 +
4670 (DATE_GET_MINUTE(left) -
4671 DATE_GET_MINUTE(right)) * 60 +
4672 (DATE_GET_SECOND(left) -
4673 DATE_GET_SECOND(right));
4674 delta_us = DATE_GET_MICROSECOND(left) -
4675 DATE_GET_MICROSECOND(right);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004676 result = new_delta(delta_d, delta_s, delta_us, 1);
Victor Stinner70e11ac2013-11-08 00:50:58 +01004677 if (result == NULL)
4678 return NULL;
4679
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004680 if (offdiff != NULL) {
Serhiy Storchakaf01e4082016-04-10 18:12:01 +03004681 Py_SETREF(result, delta_subtract(result, offdiff));
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004682 Py_DECREF(offdiff);
4683 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004684 }
4685 else if (PyDelta_Check(right)) {
4686 /* datetime - delta */
4687 result = add_datetime_timedelta(
4688 (PyDateTime_DateTime *)left,
4689 (PyDateTime_Delta *)right,
4690 -1);
4691 }
4692 }
Tim Peters2a799bf2002-12-16 20:18:38 +00004693
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004694 if (result == Py_NotImplemented)
4695 Py_INCREF(result);
4696 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00004697}
4698
4699/* Various ways to turn a datetime into a string. */
4700
4701static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004702datetime_repr(PyDateTime_DateTime *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00004703{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004704 const char *type_name = Py_TYPE(self)->tp_name;
4705 PyObject *baserepr;
Tim Peters2a799bf2002-12-16 20:18:38 +00004706
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004707 if (DATE_GET_MICROSECOND(self)) {
4708 baserepr = PyUnicode_FromFormat(
4709 "%s(%d, %d, %d, %d, %d, %d, %d)",
4710 type_name,
4711 GET_YEAR(self), GET_MONTH(self), GET_DAY(self),
4712 DATE_GET_HOUR(self), DATE_GET_MINUTE(self),
4713 DATE_GET_SECOND(self),
4714 DATE_GET_MICROSECOND(self));
4715 }
4716 else if (DATE_GET_SECOND(self)) {
4717 baserepr = PyUnicode_FromFormat(
4718 "%s(%d, %d, %d, %d, %d, %d)",
4719 type_name,
4720 GET_YEAR(self), GET_MONTH(self), GET_DAY(self),
4721 DATE_GET_HOUR(self), DATE_GET_MINUTE(self),
4722 DATE_GET_SECOND(self));
4723 }
4724 else {
4725 baserepr = PyUnicode_FromFormat(
4726 "%s(%d, %d, %d, %d, %d)",
4727 type_name,
4728 GET_YEAR(self), GET_MONTH(self), GET_DAY(self),
4729 DATE_GET_HOUR(self), DATE_GET_MINUTE(self));
4730 }
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004731 if (baserepr != NULL && DATE_GET_FOLD(self) != 0)
4732 baserepr = append_keyword_fold(baserepr, DATE_GET_FOLD(self));
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004733 if (baserepr == NULL || ! HASTZINFO(self))
4734 return baserepr;
4735 return append_keyword_tzinfo(baserepr, self->tzinfo);
Tim Peters2a799bf2002-12-16 20:18:38 +00004736}
4737
Tim Petersa9bc1682003-01-11 03:39:11 +00004738static PyObject *
4739datetime_str(PyDateTime_DateTime *self)
4740{
Victor Stinner4c381542016-12-09 00:33:39 +01004741 return _PyObject_CallMethodId((PyObject *)self, &PyId_isoformat, "s", " ");
Tim Petersa9bc1682003-01-11 03:39:11 +00004742}
Tim Peters2a799bf2002-12-16 20:18:38 +00004743
4744static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004745datetime_isoformat(PyDateTime_DateTime *self, PyObject *args, PyObject *kw)
Tim Peters2a799bf2002-12-16 20:18:38 +00004746{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004747 int sep = 'T';
Alexander Belopolskya2998a62016-03-06 14:58:43 -05004748 char *timespec = NULL;
4749 static char *keywords[] = {"sep", "timespec", NULL};
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004750 char buffer[100];
Alexander Belopolskya2998a62016-03-06 14:58:43 -05004751 PyObject *result = NULL;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004752 int us = DATE_GET_MICROSECOND(self);
Alexander Belopolskya2998a62016-03-06 14:58:43 -05004753 static char *specs[][2] = {
4754 {"hours", "%04d-%02d-%02d%c%02d"},
4755 {"minutes", "%04d-%02d-%02d%c%02d:%02d"},
4756 {"seconds", "%04d-%02d-%02d%c%02d:%02d:%02d"},
4757 {"milliseconds", "%04d-%02d-%02d%c%02d:%02d:%02d.%03d"},
4758 {"microseconds", "%04d-%02d-%02d%c%02d:%02d:%02d.%06d"},
4759 };
4760 size_t given_spec;
Tim Peters2a799bf2002-12-16 20:18:38 +00004761
Alexander Belopolskya2998a62016-03-06 14:58:43 -05004762 if (!PyArg_ParseTupleAndKeywords(args, kw, "|Cs:isoformat", keywords, &sep, &timespec))
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004763 return NULL;
Alexander Belopolskya2998a62016-03-06 14:58:43 -05004764
4765 if (timespec == NULL || strcmp(timespec, "auto") == 0) {
4766 if (us == 0) {
4767 /* seconds */
4768 given_spec = 2;
4769 }
4770 else {
4771 /* microseconds */
4772 given_spec = 4;
4773 }
4774 }
4775 else {
4776 for (given_spec = 0; given_spec < Py_ARRAY_LENGTH(specs); given_spec++) {
4777 if (strcmp(timespec, specs[given_spec][0]) == 0) {
4778 if (given_spec == 3) {
4779 us = us / 1000;
4780 }
4781 break;
4782 }
4783 }
4784 }
4785
4786 if (given_spec == Py_ARRAY_LENGTH(specs)) {
4787 PyErr_Format(PyExc_ValueError, "Unknown timespec value");
4788 return NULL;
4789 }
4790 else {
4791 result = PyUnicode_FromFormat(specs[given_spec][1],
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004792 GET_YEAR(self), GET_MONTH(self),
4793 GET_DAY(self), (int)sep,
4794 DATE_GET_HOUR(self), DATE_GET_MINUTE(self),
4795 DATE_GET_SECOND(self), us);
Alexander Belopolskya2998a62016-03-06 14:58:43 -05004796 }
Walter Dörwaldbafa1372007-05-31 17:50:48 +00004797
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004798 if (!result || !HASTZINFO(self))
4799 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00004800
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004801 /* We need to append the UTC offset. */
4802 if (format_utcoffset(buffer, sizeof(buffer), ":", self->tzinfo,
4803 (PyObject *)self) < 0) {
4804 Py_DECREF(result);
4805 return NULL;
4806 }
4807 PyUnicode_AppendAndDel(&result, PyUnicode_FromString(buffer));
4808 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00004809}
4810
Tim Petersa9bc1682003-01-11 03:39:11 +00004811static PyObject *
4812datetime_ctime(PyDateTime_DateTime *self)
4813{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004814 return format_ctime((PyDateTime_Date *)self,
4815 DATE_GET_HOUR(self),
4816 DATE_GET_MINUTE(self),
4817 DATE_GET_SECOND(self));
Tim Petersa9bc1682003-01-11 03:39:11 +00004818}
4819
Tim Peters2a799bf2002-12-16 20:18:38 +00004820/* Miscellaneous methods. */
4821
Tim Petersa9bc1682003-01-11 03:39:11 +00004822static PyObject *
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004823flip_fold(PyObject *dt)
4824{
4825 return new_datetime_ex2(GET_YEAR(dt),
4826 GET_MONTH(dt),
4827 GET_DAY(dt),
4828 DATE_GET_HOUR(dt),
4829 DATE_GET_MINUTE(dt),
4830 DATE_GET_SECOND(dt),
4831 DATE_GET_MICROSECOND(dt),
4832 HASTZINFO(dt) ?
4833 ((PyDateTime_DateTime *)dt)->tzinfo : Py_None,
4834 !DATE_GET_FOLD(dt),
4835 Py_TYPE(dt));
4836}
4837
4838static PyObject *
4839get_flip_fold_offset(PyObject *dt)
4840{
4841 PyObject *result, *flip_dt;
4842
4843 flip_dt = flip_fold(dt);
4844 if (flip_dt == NULL)
4845 return NULL;
4846 result = datetime_utcoffset(flip_dt, NULL);
4847 Py_DECREF(flip_dt);
4848 return result;
4849}
4850
4851/* PEP 495 exception: Whenever one or both of the operands in
4852 * inter-zone comparison is such that its utcoffset() depends
4853 * on the value of its fold fold attribute, the result is False.
4854 *
4855 * Return 1 if exception applies, 0 if not, and -1 on error.
4856 */
4857static int
4858pep495_eq_exception(PyObject *self, PyObject *other,
4859 PyObject *offset_self, PyObject *offset_other)
4860{
4861 int result = 0;
4862 PyObject *flip_offset;
4863
4864 flip_offset = get_flip_fold_offset(self);
4865 if (flip_offset == NULL)
4866 return -1;
4867 if (flip_offset != offset_self &&
4868 delta_cmp(flip_offset, offset_self))
4869 {
4870 result = 1;
4871 goto done;
4872 }
4873 Py_DECREF(flip_offset);
4874
4875 flip_offset = get_flip_fold_offset(other);
4876 if (flip_offset == NULL)
4877 return -1;
4878 if (flip_offset != offset_other &&
4879 delta_cmp(flip_offset, offset_other))
4880 result = 1;
4881 done:
4882 Py_DECREF(flip_offset);
4883 return result;
4884}
4885
4886static PyObject *
Guido van Rossum19960592006-08-24 17:29:38 +00004887datetime_richcompare(PyObject *self, PyObject *other, int op)
Tim Petersa9bc1682003-01-11 03:39:11 +00004888{
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004889 PyObject *result = NULL;
4890 PyObject *offset1, *offset2;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004891 int diff;
Tim Petersa9bc1682003-01-11 03:39:11 +00004892
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004893 if (! PyDateTime_Check(other)) {
4894 if (PyDate_Check(other)) {
4895 /* Prevent invocation of date_richcompare. We want to
4896 return NotImplemented here to give the other object
4897 a chance. But since DateTime is a subclass of
4898 Date, if the other object is a Date, it would
4899 compute an ordering based on the date part alone,
4900 and we don't want that. So force unequal or
4901 uncomparable here in that case. */
4902 if (op == Py_EQ)
4903 Py_RETURN_FALSE;
4904 if (op == Py_NE)
4905 Py_RETURN_TRUE;
4906 return cmperror(self, other);
4907 }
Brian Curtindfc80e32011-08-10 20:28:54 -05004908 Py_RETURN_NOTIMPLEMENTED;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004909 }
Tim Petersa9bc1682003-01-11 03:39:11 +00004910
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004911 if (GET_DT_TZINFO(self) == GET_DT_TZINFO(other)) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004912 diff = memcmp(((PyDateTime_DateTime *)self)->data,
4913 ((PyDateTime_DateTime *)other)->data,
4914 _PyDateTime_DATETIME_DATASIZE);
4915 return diff_to_bool(diff, op);
4916 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004917 offset1 = datetime_utcoffset(self, NULL);
4918 if (offset1 == NULL)
4919 return NULL;
4920 offset2 = datetime_utcoffset(other, NULL);
4921 if (offset2 == NULL)
4922 goto done;
4923 /* If they're both naive, or both aware and have the same offsets,
4924 * we get off cheap. Note that if they're both naive, offset1 ==
4925 * offset2 == Py_None at this point.
4926 */
4927 if ((offset1 == offset2) ||
4928 (PyDelta_Check(offset1) && PyDelta_Check(offset2) &&
4929 delta_cmp(offset1, offset2) == 0)) {
4930 diff = memcmp(((PyDateTime_DateTime *)self)->data,
4931 ((PyDateTime_DateTime *)other)->data,
4932 _PyDateTime_DATETIME_DATASIZE);
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004933 if ((op == Py_EQ || op == Py_NE) && diff == 0) {
4934 int ex = pep495_eq_exception(self, other, offset1, offset2);
4935 if (ex == -1)
4936 goto done;
4937 if (ex)
4938 diff = 1;
4939 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004940 result = diff_to_bool(diff, op);
4941 }
4942 else if (offset1 != Py_None && offset2 != Py_None) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004943 PyDateTime_Delta *delta;
Tim Petersa9bc1682003-01-11 03:39:11 +00004944
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004945 assert(offset1 != offset2); /* else last "if" handled it */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004946 delta = (PyDateTime_Delta *)datetime_subtract((PyObject *)self,
4947 other);
4948 if (delta == NULL)
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004949 goto done;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004950 diff = GET_TD_DAYS(delta);
4951 if (diff == 0)
4952 diff = GET_TD_SECONDS(delta) |
4953 GET_TD_MICROSECONDS(delta);
4954 Py_DECREF(delta);
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004955 if ((op == Py_EQ || op == Py_NE) && diff == 0) {
4956 int ex = pep495_eq_exception(self, other, offset1, offset2);
4957 if (ex == -1)
4958 goto done;
4959 if (ex)
4960 diff = 1;
4961 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004962 result = diff_to_bool(diff, op);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004963 }
Alexander Belopolsky08313822012-06-15 20:19:47 -04004964 else if (op == Py_EQ) {
4965 result = Py_False;
4966 Py_INCREF(result);
4967 }
4968 else if (op == Py_NE) {
4969 result = Py_True;
4970 Py_INCREF(result);
4971 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004972 else {
4973 PyErr_SetString(PyExc_TypeError,
4974 "can't compare offset-naive and "
4975 "offset-aware datetimes");
4976 }
4977 done:
4978 Py_DECREF(offset1);
4979 Py_XDECREF(offset2);
4980 return result;
Tim Petersa9bc1682003-01-11 03:39:11 +00004981}
4982
Benjamin Peterson8f67d082010-10-17 20:54:53 +00004983static Py_hash_t
Tim Petersa9bc1682003-01-11 03:39:11 +00004984datetime_hash(PyDateTime_DateTime *self)
4985{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004986 if (self->hashcode == -1) {
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04004987 PyObject *offset, *self0;
4988 if (DATE_GET_FOLD(self)) {
4989 self0 = new_datetime_ex2(GET_YEAR(self),
4990 GET_MONTH(self),
4991 GET_DAY(self),
4992 DATE_GET_HOUR(self),
4993 DATE_GET_MINUTE(self),
4994 DATE_GET_SECOND(self),
4995 DATE_GET_MICROSECOND(self),
4996 HASTZINFO(self) ? self->tzinfo : Py_None,
4997 0, Py_TYPE(self));
4998 if (self0 == NULL)
4999 return -1;
5000 }
5001 else {
5002 self0 = (PyObject *)self;
5003 Py_INCREF(self0);
5004 }
5005 offset = datetime_utcoffset(self0, NULL);
5006 Py_DECREF(self0);
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005007
5008 if (offset == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005009 return -1;
Tim Petersa9bc1682003-01-11 03:39:11 +00005010
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005011 /* Reduce this to a hash of another object. */
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005012 if (offset == Py_None)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005013 self->hashcode = generic_hash(
5014 (unsigned char *)self->data, _PyDateTime_DATETIME_DATASIZE);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005015 else {
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005016 PyObject *temp1, *temp2;
5017 int days, seconds;
Tim Petersa9bc1682003-01-11 03:39:11 +00005018
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005019 assert(HASTZINFO(self));
5020 days = ymd_to_ord(GET_YEAR(self),
5021 GET_MONTH(self),
5022 GET_DAY(self));
5023 seconds = DATE_GET_HOUR(self) * 3600 +
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005024 DATE_GET_MINUTE(self) * 60 +
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005025 DATE_GET_SECOND(self);
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005026 temp1 = new_delta(days, seconds,
5027 DATE_GET_MICROSECOND(self),
5028 1);
5029 if (temp1 == NULL) {
5030 Py_DECREF(offset);
5031 return -1;
5032 }
5033 temp2 = delta_subtract(temp1, offset);
5034 Py_DECREF(temp1);
5035 if (temp2 == NULL) {
5036 Py_DECREF(offset);
5037 return -1;
5038 }
5039 self->hashcode = PyObject_Hash(temp2);
5040 Py_DECREF(temp2);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005041 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005042 Py_DECREF(offset);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005043 }
5044 return self->hashcode;
Tim Petersa9bc1682003-01-11 03:39:11 +00005045}
Tim Peters2a799bf2002-12-16 20:18:38 +00005046
5047static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00005048datetime_replace(PyDateTime_DateTime *self, PyObject *args, PyObject *kw)
Tim Peters12bf3392002-12-24 05:41:27 +00005049{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005050 PyObject *clone;
5051 PyObject *tuple;
5052 int y = GET_YEAR(self);
5053 int m = GET_MONTH(self);
5054 int d = GET_DAY(self);
5055 int hh = DATE_GET_HOUR(self);
5056 int mm = DATE_GET_MINUTE(self);
5057 int ss = DATE_GET_SECOND(self);
5058 int us = DATE_GET_MICROSECOND(self);
5059 PyObject *tzinfo = HASTZINFO(self) ? self->tzinfo : Py_None;
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005060 int fold = DATE_GET_FOLD(self);
Tim Peters12bf3392002-12-24 05:41:27 +00005061
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005062 if (! PyArg_ParseTupleAndKeywords(args, kw, "|iiiiiiiO$i:replace",
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005063 datetime_kws,
5064 &y, &m, &d, &hh, &mm, &ss, &us,
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005065 &tzinfo, &fold))
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005066 return NULL;
Serhiy Storchaka314d6fc2017-03-31 22:48:16 +03005067 if (fold != 0 && fold != 1) {
5068 PyErr_SetString(PyExc_ValueError,
5069 "fold must be either 0 or 1");
5070 return NULL;
5071 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005072 tuple = Py_BuildValue("iiiiiiiO", y, m, d, hh, mm, ss, us, tzinfo);
5073 if (tuple == NULL)
5074 return NULL;
5075 clone = datetime_new(Py_TYPE(self), tuple, NULL);
Alexander Belopolsky47649ab2016-08-08 17:05:40 -04005076 if (clone != NULL) {
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005077 DATE_SET_FOLD(clone, fold);
Alexander Belopolsky47649ab2016-08-08 17:05:40 -04005078 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005079 Py_DECREF(tuple);
5080 return clone;
Tim Peters12bf3392002-12-24 05:41:27 +00005081}
5082
5083static PyObject *
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005084local_timezone_from_timestamp(time_t timestamp)
Alexander Belopolskyfdc860f2012-06-22 12:23:23 -04005085{
5086 PyObject *result = NULL;
Alexander Belopolskyfdc860f2012-06-22 12:23:23 -04005087 PyObject *delta;
Alexander Belopolsky6d88fa52016-09-10 15:58:31 -04005088 struct tm local_time_tm;
Alexander Belopolskyfdc860f2012-06-22 12:23:23 -04005089 PyObject *nameo = NULL;
5090 const char *zone = NULL;
5091
Alexander Belopolsky3e7a3cb2016-09-28 17:31:35 -04005092 if (_PyTime_localtime(timestamp, &local_time_tm) != 0)
Alexander Belopolsky6d88fa52016-09-10 15:58:31 -04005093 return NULL;
Alexander Belopolskyfdc860f2012-06-22 12:23:23 -04005094#ifdef HAVE_STRUCT_TM_TM_ZONE
Alexander Belopolsky6d88fa52016-09-10 15:58:31 -04005095 zone = local_time_tm.tm_zone;
5096 delta = new_delta(0, local_time_tm.tm_gmtoff, 0, 1);
Alexander Belopolskyfdc860f2012-06-22 12:23:23 -04005097#else /* HAVE_STRUCT_TM_TM_ZONE */
5098 {
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005099 PyObject *local_time, *utc_time;
Alexander Belopolsky6d88fa52016-09-10 15:58:31 -04005100 struct tm utc_time_tm;
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005101 char buf[100];
Alexander Belopolsky6d88fa52016-09-10 15:58:31 -04005102 strftime(buf, sizeof(buf), "%Z", &local_time_tm);
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005103 zone = buf;
Alexander Belopolsky6d88fa52016-09-10 15:58:31 -04005104 local_time = new_datetime(local_time_tm.tm_year + 1900,
5105 local_time_tm.tm_mon + 1,
5106 local_time_tm.tm_mday,
5107 local_time_tm.tm_hour,
5108 local_time_tm.tm_min,
5109 local_time_tm.tm_sec, 0, Py_None, 0);
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005110 if (local_time == NULL) {
5111 return NULL;
5112 }
Alexander Belopolsky3e7a3cb2016-09-28 17:31:35 -04005113 if (_PyTime_gmtime(timestamp, &utc_time_tm) != 0)
Alexander Belopolsky6d88fa52016-09-10 15:58:31 -04005114 return NULL;
Alexander Belopolsky6d88fa52016-09-10 15:58:31 -04005115 utc_time = new_datetime(utc_time_tm.tm_year + 1900,
5116 utc_time_tm.tm_mon + 1,
5117 utc_time_tm.tm_mday,
5118 utc_time_tm.tm_hour,
5119 utc_time_tm.tm_min,
5120 utc_time_tm.tm_sec, 0, Py_None, 0);
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005121 if (utc_time == NULL) {
5122 Py_DECREF(local_time);
5123 return NULL;
5124 }
5125 delta = datetime_subtract(local_time, utc_time);
Alexander Belopolskyfdc860f2012-06-22 12:23:23 -04005126 Py_DECREF(local_time);
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005127 Py_DECREF(utc_time);
Alexander Belopolskyfdc860f2012-06-22 12:23:23 -04005128 }
5129#endif /* HAVE_STRUCT_TM_TM_ZONE */
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005130 if (delta == NULL) {
5131 return NULL;
5132 }
Alexander Belopolskyfdc860f2012-06-22 12:23:23 -04005133 if (zone != NULL) {
5134 nameo = PyUnicode_DecodeLocale(zone, "surrogateescape");
5135 if (nameo == NULL)
5136 goto error;
5137 }
5138 result = new_timezone(delta, nameo);
Christian Heimesb91ffaa2013-06-29 20:52:33 +02005139 Py_XDECREF(nameo);
Alexander Belopolskyfdc860f2012-06-22 12:23:23 -04005140 error:
5141 Py_DECREF(delta);
5142 return result;
5143}
5144
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005145static PyObject *
5146local_timezone(PyDateTime_DateTime *utc_time)
5147{
5148 time_t timestamp;
5149 PyObject *delta;
5150 PyObject *one_second;
5151 PyObject *seconds;
5152
5153 delta = datetime_subtract((PyObject *)utc_time, PyDateTime_Epoch);
5154 if (delta == NULL)
5155 return NULL;
5156 one_second = new_delta(0, 1, 0, 0);
5157 if (one_second == NULL) {
5158 Py_DECREF(delta);
5159 return NULL;
5160 }
5161 seconds = divide_timedelta_timedelta((PyDateTime_Delta *)delta,
5162 (PyDateTime_Delta *)one_second);
5163 Py_DECREF(one_second);
5164 Py_DECREF(delta);
5165 if (seconds == NULL)
5166 return NULL;
5167 timestamp = _PyLong_AsTime_t(seconds);
5168 Py_DECREF(seconds);
5169 if (timestamp == -1 && PyErr_Occurred())
5170 return NULL;
5171 return local_timezone_from_timestamp(timestamp);
5172}
5173
Benjamin Petersonaf580df2016-09-06 10:46:49 -07005174static long long
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005175local_to_seconds(int year, int month, int day,
5176 int hour, int minute, int second, int fold);
5177
5178static PyObject *
5179local_timezone_from_local(PyDateTime_DateTime *local_dt)
5180{
Benjamin Petersonaf580df2016-09-06 10:46:49 -07005181 long long seconds;
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005182 time_t timestamp;
5183 seconds = local_to_seconds(GET_YEAR(local_dt),
5184 GET_MONTH(local_dt),
5185 GET_DAY(local_dt),
5186 DATE_GET_HOUR(local_dt),
5187 DATE_GET_MINUTE(local_dt),
5188 DATE_GET_SECOND(local_dt),
5189 DATE_GET_FOLD(local_dt));
5190 if (seconds == -1)
5191 return NULL;
5192 /* XXX: add bounds check */
5193 timestamp = seconds - epoch;
5194 return local_timezone_from_timestamp(timestamp);
5195}
5196
Alexander Belopolsky878054e2012-06-22 14:11:58 -04005197static PyDateTime_DateTime *
Tim Petersa9bc1682003-01-11 03:39:11 +00005198datetime_astimezone(PyDateTime_DateTime *self, PyObject *args, PyObject *kw)
Tim Peters80475bb2002-12-25 07:40:55 +00005199{
Alexander Belopolsky31227ca2012-06-22 13:23:21 -04005200 PyDateTime_DateTime *result;
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005201 PyObject *offset;
5202 PyObject *temp;
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005203 PyObject *self_tzinfo;
Alexander Belopolskyfdc860f2012-06-22 12:23:23 -04005204 PyObject *tzinfo = Py_None;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005205 static char *keywords[] = {"tz", NULL};
Tim Peters80475bb2002-12-25 07:40:55 +00005206
Alexander Belopolskyfdc860f2012-06-22 12:23:23 -04005207 if (! PyArg_ParseTupleAndKeywords(args, kw, "|O:astimezone", keywords,
Raymond Hettinger5a2146a2014-07-25 14:59:48 -07005208 &tzinfo))
Alexander Belopolskyfdc860f2012-06-22 12:23:23 -04005209 return NULL;
5210
5211 if (check_tzinfo_subclass(tzinfo) == -1)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005212 return NULL;
Tim Peters80475bb2002-12-25 07:40:55 +00005213
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005214 if (!HASTZINFO(self) || self->tzinfo == Py_None) {
5215 self_tzinfo = local_timezone_from_local(self);
5216 if (self_tzinfo == NULL)
5217 return NULL;
5218 } else {
5219 self_tzinfo = self->tzinfo;
5220 Py_INCREF(self_tzinfo);
5221 }
Tim Peters521fc152002-12-31 17:36:56 +00005222
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005223 /* Conversion to self's own time zone is a NOP. */
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005224 if (self_tzinfo == tzinfo) {
5225 Py_DECREF(self_tzinfo);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005226 Py_INCREF(self);
Alexander Belopolsky878054e2012-06-22 14:11:58 -04005227 return self;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005228 }
Tim Peters521fc152002-12-31 17:36:56 +00005229
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005230 /* Convert self to UTC. */
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005231 offset = call_utcoffset(self_tzinfo, (PyObject *)self);
5232 Py_DECREF(self_tzinfo);
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005233 if (offset == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005234 return NULL;
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005235 /* result = self - offset */
Alexander Belopolsky31227ca2012-06-22 13:23:21 -04005236 result = (PyDateTime_DateTime *)add_datetime_timedelta(self,
5237 (PyDateTime_Delta *)offset, -1);
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005238 Py_DECREF(offset);
5239 if (result == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005240 return NULL;
Tim Peters52dcce22003-01-23 16:36:11 +00005241
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005242 /* Make sure result is aware and UTC. */
5243 if (!HASTZINFO(result)) {
5244 temp = (PyObject *)result;
5245 result = (PyDateTime_DateTime *)
5246 new_datetime_ex2(GET_YEAR(result),
5247 GET_MONTH(result),
5248 GET_DAY(result),
5249 DATE_GET_HOUR(result),
5250 DATE_GET_MINUTE(result),
5251 DATE_GET_SECOND(result),
5252 DATE_GET_MICROSECOND(result),
5253 PyDateTime_TimeZone_UTC,
5254 DATE_GET_FOLD(result),
5255 Py_TYPE(result));
5256 Py_DECREF(temp);
5257 if (result == NULL)
5258 return NULL;
5259 }
5260 else {
5261 /* Result is already aware - just replace tzinfo. */
5262 temp = result->tzinfo;
5263 result->tzinfo = PyDateTime_TimeZone_UTC;
5264 Py_INCREF(result->tzinfo);
5265 Py_DECREF(temp);
5266 }
5267
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005268 /* Attach new tzinfo and let fromutc() do the rest. */
Alexander Belopolsky31227ca2012-06-22 13:23:21 -04005269 temp = result->tzinfo;
Alexander Belopolskyfdc860f2012-06-22 12:23:23 -04005270 if (tzinfo == Py_None) {
5271 tzinfo = local_timezone(result);
5272 if (tzinfo == NULL) {
5273 Py_DECREF(result);
5274 return NULL;
5275 }
5276 }
5277 else
5278 Py_INCREF(tzinfo);
Alexander Belopolsky31227ca2012-06-22 13:23:21 -04005279 result->tzinfo = tzinfo;
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005280 Py_DECREF(temp);
Tim Peters52dcce22003-01-23 16:36:11 +00005281
Alexander Belopolsky31227ca2012-06-22 13:23:21 -04005282 temp = (PyObject *)result;
Alexander Belopolsky878054e2012-06-22 14:11:58 -04005283 result = (PyDateTime_DateTime *)
Victor Stinner20401de2016-12-09 15:24:31 +01005284 _PyObject_CallMethodIdObjArgs(tzinfo, &PyId_fromutc, temp, NULL);
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005285 Py_DECREF(temp);
5286
Alexander Belopolsky878054e2012-06-22 14:11:58 -04005287 return result;
Tim Peters80475bb2002-12-25 07:40:55 +00005288}
5289
5290static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00005291datetime_timetuple(PyDateTime_DateTime *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00005292{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005293 int dstflag = -1;
Tim Peters2a799bf2002-12-16 20:18:38 +00005294
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005295 if (HASTZINFO(self) && self->tzinfo != Py_None) {
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005296 PyObject * dst;
Tim Peters2a799bf2002-12-16 20:18:38 +00005297
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005298 dst = call_dst(self->tzinfo, (PyObject *)self);
5299 if (dst == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005300 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00005301
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005302 if (dst != Py_None)
5303 dstflag = delta_bool((PyDateTime_Delta *)dst);
5304 Py_DECREF(dst);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005305 }
5306 return build_struct_time(GET_YEAR(self),
5307 GET_MONTH(self),
5308 GET_DAY(self),
5309 DATE_GET_HOUR(self),
5310 DATE_GET_MINUTE(self),
5311 DATE_GET_SECOND(self),
5312 dstflag);
Tim Peters2a799bf2002-12-16 20:18:38 +00005313}
5314
Benjamin Petersonaf580df2016-09-06 10:46:49 -07005315static long long
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005316local_to_seconds(int year, int month, int day,
5317 int hour, int minute, int second, int fold)
5318{
Benjamin Petersonaf580df2016-09-06 10:46:49 -07005319 long long t, a, b, u1, u2, t1, t2, lt;
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005320 t = utc_to_seconds(year, month, day, hour, minute, second);
5321 /* Our goal is to solve t = local(u) for u. */
5322 lt = local(t);
5323 if (lt == -1)
5324 return -1;
5325 a = lt - t;
5326 u1 = t - a;
5327 t1 = local(u1);
5328 if (t1 == -1)
5329 return -1;
5330 if (t1 == t) {
5331 /* We found one solution, but it may not be the one we need.
5332 * Look for an earlier solution (if `fold` is 0), or a
5333 * later one (if `fold` is 1). */
5334 if (fold)
5335 u2 = u1 + max_fold_seconds;
5336 else
5337 u2 = u1 - max_fold_seconds;
5338 lt = local(u2);
5339 if (lt == -1)
5340 return -1;
5341 b = lt - u2;
5342 if (a == b)
5343 return u1;
5344 }
5345 else {
5346 b = t1 - u1;
5347 assert(a != b);
5348 }
5349 u2 = t - b;
5350 t2 = local(u2);
5351 if (t2 == -1)
5352 return -1;
5353 if (t2 == t)
5354 return u2;
5355 if (t1 == t)
5356 return u1;
5357 /* We have found both offsets a and b, but neither t - a nor t - b is
5358 * a solution. This means t is in the gap. */
5359 return fold?Py_MIN(u1, u2):Py_MAX(u1, u2);
5360}
5361
5362/* date(1970,1,1).toordinal() == 719163 */
5363#define EPOCH_SECONDS (719163LL * 24 * 60 * 60)
5364
Tim Peters2a799bf2002-12-16 20:18:38 +00005365static PyObject *
Alexander Belopolskya4415142012-06-08 12:33:09 -04005366datetime_timestamp(PyDateTime_DateTime *self)
5367{
5368 PyObject *result;
5369
5370 if (HASTZINFO(self) && self->tzinfo != Py_None) {
5371 PyObject *delta;
5372 delta = datetime_subtract((PyObject *)self, PyDateTime_Epoch);
5373 if (delta == NULL)
5374 return NULL;
5375 result = delta_total_seconds(delta);
5376 Py_DECREF(delta);
5377 }
5378 else {
Benjamin Petersonaf580df2016-09-06 10:46:49 -07005379 long long seconds;
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005380 seconds = local_to_seconds(GET_YEAR(self),
5381 GET_MONTH(self),
5382 GET_DAY(self),
5383 DATE_GET_HOUR(self),
5384 DATE_GET_MINUTE(self),
5385 DATE_GET_SECOND(self),
5386 DATE_GET_FOLD(self));
5387 if (seconds == -1)
Alexander Belopolskya4415142012-06-08 12:33:09 -04005388 return NULL;
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005389 result = PyFloat_FromDouble(seconds - EPOCH_SECONDS +
5390 DATE_GET_MICROSECOND(self) / 1e6);
Alexander Belopolskya4415142012-06-08 12:33:09 -04005391 }
5392 return result;
5393}
5394
5395static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00005396datetime_getdate(PyDateTime_DateTime *self)
5397{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005398 return new_date(GET_YEAR(self),
5399 GET_MONTH(self),
5400 GET_DAY(self));
Tim Petersa9bc1682003-01-11 03:39:11 +00005401}
5402
5403static PyObject *
5404datetime_gettime(PyDateTime_DateTime *self)
5405{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005406 return new_time(DATE_GET_HOUR(self),
5407 DATE_GET_MINUTE(self),
5408 DATE_GET_SECOND(self),
5409 DATE_GET_MICROSECOND(self),
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005410 Py_None,
5411 DATE_GET_FOLD(self));
Tim Petersa9bc1682003-01-11 03:39:11 +00005412}
5413
5414static PyObject *
5415datetime_gettimetz(PyDateTime_DateTime *self)
5416{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005417 return new_time(DATE_GET_HOUR(self),
5418 DATE_GET_MINUTE(self),
5419 DATE_GET_SECOND(self),
5420 DATE_GET_MICROSECOND(self),
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005421 GET_DT_TZINFO(self),
5422 DATE_GET_FOLD(self));
Tim Petersa9bc1682003-01-11 03:39:11 +00005423}
5424
5425static PyObject *
5426datetime_utctimetuple(PyDateTime_DateTime *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00005427{
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005428 int y, m, d, hh, mm, ss;
5429 PyObject *tzinfo;
5430 PyDateTime_DateTime *utcself;
Tim Peters2a799bf2002-12-16 20:18:38 +00005431
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005432 tzinfo = GET_DT_TZINFO(self);
5433 if (tzinfo == Py_None) {
5434 utcself = self;
5435 Py_INCREF(utcself);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005436 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005437 else {
5438 PyObject *offset;
5439 offset = call_utcoffset(tzinfo, (PyObject *)self);
5440 if (offset == NULL)
Alexander Belopolsky75f94c22010-06-21 15:21:14 +00005441 return NULL;
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005442 if (offset == Py_None) {
5443 Py_DECREF(offset);
5444 utcself = self;
5445 Py_INCREF(utcself);
5446 }
5447 else {
5448 utcself = (PyDateTime_DateTime *)add_datetime_timedelta(self,
5449 (PyDateTime_Delta *)offset, -1);
5450 Py_DECREF(offset);
5451 if (utcself == NULL)
5452 return NULL;
5453 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005454 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00005455 y = GET_YEAR(utcself);
5456 m = GET_MONTH(utcself);
5457 d = GET_DAY(utcself);
5458 hh = DATE_GET_HOUR(utcself);
5459 mm = DATE_GET_MINUTE(utcself);
5460 ss = DATE_GET_SECOND(utcself);
5461
5462 Py_DECREF(utcself);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005463 return build_struct_time(y, m, d, hh, mm, ss, 0);
Tim Peters2a799bf2002-12-16 20:18:38 +00005464}
5465
Tim Peters371935f2003-02-01 01:52:50 +00005466/* Pickle support, a simple use of __reduce__. */
Tim Peters33e0f382003-01-10 02:05:14 +00005467
Tim Petersa9bc1682003-01-11 03:39:11 +00005468/* Let basestate be the non-tzinfo data string.
Tim Peters2a799bf2002-12-16 20:18:38 +00005469 * If tzinfo is None, this returns (basestate,), else (basestate, tzinfo).
5470 * So it's a tuple in any (non-error) case.
Tim Petersb57f8f02003-02-01 02:54:15 +00005471 * __getstate__ isn't exposed.
Tim Peters2a799bf2002-12-16 20:18:38 +00005472 */
5473static PyObject *
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005474datetime_getstate(PyDateTime_DateTime *self, int proto)
Tim Peters2a799bf2002-12-16 20:18:38 +00005475{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005476 PyObject *basestate;
5477 PyObject *result = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00005478
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005479 basestate = PyBytes_FromStringAndSize((char *)self->data,
5480 _PyDateTime_DATETIME_DATASIZE);
5481 if (basestate != NULL) {
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005482 if (proto > 3 && DATE_GET_FOLD(self))
5483 /* Set the first bit of the third byte */
5484 PyBytes_AS_STRING(basestate)[2] |= (1 << 7);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005485 if (! HASTZINFO(self) || self->tzinfo == Py_None)
5486 result = PyTuple_Pack(1, basestate);
5487 else
5488 result = PyTuple_Pack(2, basestate, self->tzinfo);
5489 Py_DECREF(basestate);
5490 }
5491 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00005492}
5493
5494static PyObject *
Serhiy Storchaka546ce652016-11-22 00:29:42 +02005495datetime_reduce_ex(PyDateTime_DateTime *self, PyObject *args)
Tim Peters2a799bf2002-12-16 20:18:38 +00005496{
Serhiy Storchaka546ce652016-11-22 00:29:42 +02005497 int proto;
5498 if (!PyArg_ParseTuple(args, "i:__reduce_ex__", &proto))
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005499 return NULL;
5500
5501 return Py_BuildValue("(ON)", Py_TYPE(self), datetime_getstate(self, proto));
Tim Peters2a799bf2002-12-16 20:18:38 +00005502}
5503
Serhiy Storchaka546ce652016-11-22 00:29:42 +02005504static PyObject *
5505datetime_reduce(PyDateTime_DateTime *self, PyObject *arg)
5506{
5507 return Py_BuildValue("(ON)", Py_TYPE(self), datetime_getstate(self, 2));
5508}
5509
Tim Petersa9bc1682003-01-11 03:39:11 +00005510static PyMethodDef datetime_methods[] = {
Guido van Rossum177e41a2003-01-30 22:06:23 +00005511
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005512 /* Class methods: */
Tim Peters2a799bf2002-12-16 20:18:38 +00005513
Larry Hastingsed4a1c52013-11-18 09:32:13 -08005514 DATETIME_DATETIME_NOW_METHODDEF
Tim Peters2a799bf2002-12-16 20:18:38 +00005515
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005516 {"utcnow", (PyCFunction)datetime_utcnow,
5517 METH_NOARGS | METH_CLASS,
5518 PyDoc_STR("Return a new datetime representing UTC day and time.")},
Tim Petersa9bc1682003-01-11 03:39:11 +00005519
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005520 {"fromtimestamp", (PyCFunction)datetime_fromtimestamp,
5521 METH_VARARGS | METH_KEYWORDS | METH_CLASS,
5522 PyDoc_STR("timestamp[, tz] -> tz's local time from POSIX timestamp.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00005523
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005524 {"utcfromtimestamp", (PyCFunction)datetime_utcfromtimestamp,
5525 METH_VARARGS | METH_CLASS,
Alexander Belopolskye2e178e2015-03-01 14:52:07 -05005526 PyDoc_STR("Construct a naive UTC datetime from a POSIX timestamp.")},
Tim Petersa9bc1682003-01-11 03:39:11 +00005527
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005528 {"strptime", (PyCFunction)datetime_strptime,
5529 METH_VARARGS | METH_CLASS,
5530 PyDoc_STR("string, format -> new datetime parsed from a string "
5531 "(like time.strptime()).")},
Skip Montanaro0af3ade2005-01-13 04:12:31 +00005532
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005533 {"combine", (PyCFunction)datetime_combine,
5534 METH_VARARGS | METH_KEYWORDS | METH_CLASS,
5535 PyDoc_STR("date, time -> datetime with same date and time fields")},
Tim Petersa9bc1682003-01-11 03:39:11 +00005536
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005537 /* Instance methods: */
Guido van Rossum177e41a2003-01-30 22:06:23 +00005538
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005539 {"date", (PyCFunction)datetime_getdate, METH_NOARGS,
5540 PyDoc_STR("Return date object with same year, month and day.")},
Tim Petersa9bc1682003-01-11 03:39:11 +00005541
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005542 {"time", (PyCFunction)datetime_gettime, METH_NOARGS,
5543 PyDoc_STR("Return time object with same time but with tzinfo=None.")},
Tim Petersa9bc1682003-01-11 03:39:11 +00005544
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005545 {"timetz", (PyCFunction)datetime_gettimetz, METH_NOARGS,
5546 PyDoc_STR("Return time object with same time and tzinfo.")},
Tim Petersa9bc1682003-01-11 03:39:11 +00005547
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005548 {"ctime", (PyCFunction)datetime_ctime, METH_NOARGS,
5549 PyDoc_STR("Return ctime() style string.")},
Tim Petersa9bc1682003-01-11 03:39:11 +00005550
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005551 {"timetuple", (PyCFunction)datetime_timetuple, METH_NOARGS,
5552 PyDoc_STR("Return time tuple, compatible with time.localtime().")},
Tim Peters2a799bf2002-12-16 20:18:38 +00005553
Alexander Belopolskya4415142012-06-08 12:33:09 -04005554 {"timestamp", (PyCFunction)datetime_timestamp, METH_NOARGS,
5555 PyDoc_STR("Return POSIX timestamp as float.")},
5556
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005557 {"utctimetuple", (PyCFunction)datetime_utctimetuple, METH_NOARGS,
5558 PyDoc_STR("Return UTC time tuple, compatible with time.localtime().")},
Tim Peters2a799bf2002-12-16 20:18:38 +00005559
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005560 {"isoformat", (PyCFunction)datetime_isoformat, METH_VARARGS | METH_KEYWORDS,
5561 PyDoc_STR("[sep] -> string in ISO 8601 format, "
Alexander Belopolskya2998a62016-03-06 14:58:43 -05005562 "YYYY-MM-DDT[HH[:MM[:SS[.mmm[uuu]]]]][+HH:MM].\n"
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005563 "sep is used to separate the year from the time, and "
Alexander Belopolskya2998a62016-03-06 14:58:43 -05005564 "defaults to 'T'.\n"
5565 "timespec specifies what components of the time to include"
5566 " (allowed values are 'auto', 'hours', 'minutes', 'seconds',"
5567 " 'milliseconds', and 'microseconds').\n")},
Tim Peters2a799bf2002-12-16 20:18:38 +00005568
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005569 {"utcoffset", (PyCFunction)datetime_utcoffset, METH_NOARGS,
5570 PyDoc_STR("Return self.tzinfo.utcoffset(self).")},
Tim Peters2a799bf2002-12-16 20:18:38 +00005571
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005572 {"tzname", (PyCFunction)datetime_tzname, METH_NOARGS,
5573 PyDoc_STR("Return self.tzinfo.tzname(self).")},
Tim Peters2a799bf2002-12-16 20:18:38 +00005574
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005575 {"dst", (PyCFunction)datetime_dst, METH_NOARGS,
5576 PyDoc_STR("Return self.tzinfo.dst(self).")},
Tim Peters2a799bf2002-12-16 20:18:38 +00005577
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005578 {"replace", (PyCFunction)datetime_replace, METH_VARARGS | METH_KEYWORDS,
5579 PyDoc_STR("Return datetime with new specified fields.")},
Tim Peters12bf3392002-12-24 05:41:27 +00005580
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005581 {"astimezone", (PyCFunction)datetime_astimezone, METH_VARARGS | METH_KEYWORDS,
5582 PyDoc_STR("tz -> convert to local time in new timezone tz\n")},
Tim Peters80475bb2002-12-25 07:40:55 +00005583
Serhiy Storchaka546ce652016-11-22 00:29:42 +02005584 {"__reduce_ex__", (PyCFunction)datetime_reduce_ex, METH_VARARGS,
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005585 PyDoc_STR("__reduce_ex__(proto) -> (cls, state)")},
Guido van Rossum177e41a2003-01-30 22:06:23 +00005586
Serhiy Storchaka546ce652016-11-22 00:29:42 +02005587 {"__reduce__", (PyCFunction)datetime_reduce, METH_NOARGS,
5588 PyDoc_STR("__reduce__() -> (cls, state)")},
5589
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005590 {NULL, NULL}
Tim Peters2a799bf2002-12-16 20:18:38 +00005591};
5592
Serhiy Storchaka2d06e842015-12-25 19:53:18 +02005593static const char datetime_doc[] =
Raymond Hettinger3a4231d2004-12-19 20:13:24 +00005594PyDoc_STR("datetime(year, month, day[, hour[, minute[, second[, microsecond[,tzinfo]]]]])\n\
5595\n\
5596The year, month and day arguments are required. tzinfo may be None, or an\n\
Serhiy Storchaka95949422013-08-27 19:40:23 +03005597instance of a tzinfo subclass. The remaining arguments may be ints.\n");
Tim Peters2a799bf2002-12-16 20:18:38 +00005598
Tim Petersa9bc1682003-01-11 03:39:11 +00005599static PyNumberMethods datetime_as_number = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005600 datetime_add, /* nb_add */
5601 datetime_subtract, /* nb_subtract */
5602 0, /* nb_multiply */
5603 0, /* nb_remainder */
5604 0, /* nb_divmod */
5605 0, /* nb_power */
5606 0, /* nb_negative */
5607 0, /* nb_positive */
5608 0, /* nb_absolute */
5609 0, /* nb_bool */
Tim Peters2a799bf2002-12-16 20:18:38 +00005610};
5611
Neal Norwitz227b5332006-03-22 09:28:35 +00005612static PyTypeObject PyDateTime_DateTimeType = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005613 PyVarObject_HEAD_INIT(NULL, 0)
5614 "datetime.datetime", /* tp_name */
5615 sizeof(PyDateTime_DateTime), /* tp_basicsize */
5616 0, /* tp_itemsize */
5617 (destructor)datetime_dealloc, /* tp_dealloc */
5618 0, /* tp_print */
5619 0, /* tp_getattr */
5620 0, /* tp_setattr */
5621 0, /* tp_reserved */
5622 (reprfunc)datetime_repr, /* tp_repr */
5623 &datetime_as_number, /* tp_as_number */
5624 0, /* tp_as_sequence */
5625 0, /* tp_as_mapping */
5626 (hashfunc)datetime_hash, /* tp_hash */
5627 0, /* tp_call */
5628 (reprfunc)datetime_str, /* tp_str */
5629 PyObject_GenericGetAttr, /* tp_getattro */
5630 0, /* tp_setattro */
5631 0, /* tp_as_buffer */
5632 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
5633 datetime_doc, /* tp_doc */
5634 0, /* tp_traverse */
5635 0, /* tp_clear */
5636 datetime_richcompare, /* tp_richcompare */
5637 0, /* tp_weaklistoffset */
5638 0, /* tp_iter */
5639 0, /* tp_iternext */
5640 datetime_methods, /* tp_methods */
5641 0, /* tp_members */
5642 datetime_getset, /* tp_getset */
5643 &PyDateTime_DateType, /* tp_base */
5644 0, /* tp_dict */
5645 0, /* tp_descr_get */
5646 0, /* tp_descr_set */
5647 0, /* tp_dictoffset */
5648 0, /* tp_init */
5649 datetime_alloc, /* tp_alloc */
5650 datetime_new, /* tp_new */
5651 0, /* tp_free */
Tim Peters2a799bf2002-12-16 20:18:38 +00005652};
5653
5654/* ---------------------------------------------------------------------------
5655 * Module methods and initialization.
5656 */
5657
5658static PyMethodDef module_methods[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005659 {NULL, NULL}
Tim Peters2a799bf2002-12-16 20:18:38 +00005660};
5661
Tim Peters9ddf40b2004-06-20 22:41:32 +00005662/* C API. Clients get at this via PyDateTime_IMPORT, defined in
5663 * datetime.h.
5664 */
5665static PyDateTime_CAPI CAPI = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005666 &PyDateTime_DateType,
5667 &PyDateTime_DateTimeType,
5668 &PyDateTime_TimeType,
5669 &PyDateTime_DeltaType,
5670 &PyDateTime_TZInfoType,
5671 new_date_ex,
5672 new_datetime_ex,
5673 new_time_ex,
5674 new_delta_ex,
5675 datetime_fromtimestamp,
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005676 date_fromtimestamp,
5677 new_datetime_ex2,
5678 new_time_ex2
Tim Peters9ddf40b2004-06-20 22:41:32 +00005679};
5680
5681
Martin v. Löwis1a214512008-06-11 05:26:20 +00005682
5683static struct PyModuleDef datetimemodule = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005684 PyModuleDef_HEAD_INIT,
Alexander Belopolskycf86e362010-07-23 19:25:47 +00005685 "_datetime",
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005686 "Fast implementation of the datetime type.",
5687 -1,
5688 module_methods,
5689 NULL,
5690 NULL,
5691 NULL,
5692 NULL
Martin v. Löwis1a214512008-06-11 05:26:20 +00005693};
5694
Tim Peters2a799bf2002-12-16 20:18:38 +00005695PyMODINIT_FUNC
Alexander Belopolskycf86e362010-07-23 19:25:47 +00005696PyInit__datetime(void)
Tim Peters2a799bf2002-12-16 20:18:38 +00005697{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005698 PyObject *m; /* a module object */
5699 PyObject *d; /* its dict */
5700 PyObject *x;
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00005701 PyObject *delta;
Tim Peters2a799bf2002-12-16 20:18:38 +00005702
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005703 m = PyModule_Create(&datetimemodule);
5704 if (m == NULL)
5705 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00005706
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005707 if (PyType_Ready(&PyDateTime_DateType) < 0)
5708 return NULL;
5709 if (PyType_Ready(&PyDateTime_DateTimeType) < 0)
5710 return NULL;
5711 if (PyType_Ready(&PyDateTime_DeltaType) < 0)
5712 return NULL;
5713 if (PyType_Ready(&PyDateTime_TimeType) < 0)
5714 return NULL;
5715 if (PyType_Ready(&PyDateTime_TZInfoType) < 0)
5716 return NULL;
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00005717 if (PyType_Ready(&PyDateTime_TimeZoneType) < 0)
5718 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00005719
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005720 /* timedelta values */
5721 d = PyDateTime_DeltaType.tp_dict;
Tim Peters2a799bf2002-12-16 20:18:38 +00005722
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005723 x = new_delta(0, 0, 1, 0);
5724 if (x == NULL || PyDict_SetItemString(d, "resolution", x) < 0)
5725 return NULL;
5726 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005727
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005728 x = new_delta(-MAX_DELTA_DAYS, 0, 0, 0);
5729 if (x == NULL || PyDict_SetItemString(d, "min", x) < 0)
5730 return NULL;
5731 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005732
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005733 x = new_delta(MAX_DELTA_DAYS, 24*3600-1, 1000000-1, 0);
5734 if (x == NULL || PyDict_SetItemString(d, "max", x) < 0)
5735 return NULL;
5736 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005737
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005738 /* date values */
5739 d = PyDateTime_DateType.tp_dict;
Tim Peters2a799bf2002-12-16 20:18:38 +00005740
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005741 x = new_date(1, 1, 1);
5742 if (x == NULL || PyDict_SetItemString(d, "min", x) < 0)
5743 return NULL;
5744 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005745
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005746 x = new_date(MAXYEAR, 12, 31);
5747 if (x == NULL || PyDict_SetItemString(d, "max", x) < 0)
5748 return NULL;
5749 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005750
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005751 x = new_delta(1, 0, 0, 0);
5752 if (x == NULL || PyDict_SetItemString(d, "resolution", x) < 0)
5753 return NULL;
5754 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005755
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005756 /* time values */
5757 d = PyDateTime_TimeType.tp_dict;
Tim Peters2a799bf2002-12-16 20:18:38 +00005758
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005759 x = new_time(0, 0, 0, 0, Py_None, 0);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005760 if (x == NULL || PyDict_SetItemString(d, "min", x) < 0)
5761 return NULL;
5762 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005763
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005764 x = new_time(23, 59, 59, 999999, Py_None, 0);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005765 if (x == NULL || PyDict_SetItemString(d, "max", x) < 0)
5766 return NULL;
5767 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005768
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005769 x = new_delta(0, 0, 1, 0);
5770 if (x == NULL || PyDict_SetItemString(d, "resolution", x) < 0)
5771 return NULL;
5772 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005773
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005774 /* datetime values */
5775 d = PyDateTime_DateTimeType.tp_dict;
Tim Peters2a799bf2002-12-16 20:18:38 +00005776
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005777 x = new_datetime(1, 1, 1, 0, 0, 0, 0, Py_None, 0);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005778 if (x == NULL || PyDict_SetItemString(d, "min", x) < 0)
5779 return NULL;
5780 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005781
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005782 x = new_datetime(MAXYEAR, 12, 31, 23, 59, 59, 999999, Py_None, 0);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005783 if (x == NULL || PyDict_SetItemString(d, "max", x) < 0)
5784 return NULL;
5785 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005786
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005787 x = new_delta(0, 0, 1, 0);
5788 if (x == NULL || PyDict_SetItemString(d, "resolution", x) < 0)
5789 return NULL;
5790 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005791
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00005792 /* timezone values */
5793 d = PyDateTime_TimeZoneType.tp_dict;
5794
5795 delta = new_delta(0, 0, 0, 0);
5796 if (delta == NULL)
5797 return NULL;
Alexander Belopolsky1bcbaab2010-10-14 17:03:51 +00005798 x = create_timezone(delta, NULL);
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00005799 Py_DECREF(delta);
5800 if (x == NULL || PyDict_SetItemString(d, "utc", x) < 0)
5801 return NULL;
Alexander Belopolskya11d8c02010-07-06 23:19:45 +00005802 PyDateTime_TimeZone_UTC = x;
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00005803
5804 delta = new_delta(-1, 60, 0, 1); /* -23:59 */
5805 if (delta == NULL)
5806 return NULL;
Alexander Belopolsky1bcbaab2010-10-14 17:03:51 +00005807 x = create_timezone(delta, NULL);
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00005808 Py_DECREF(delta);
5809 if (x == NULL || PyDict_SetItemString(d, "min", x) < 0)
5810 return NULL;
5811 Py_DECREF(x);
5812
5813 delta = new_delta(0, (23 * 60 + 59) * 60, 0, 0); /* +23:59 */
5814 if (delta == NULL)
5815 return NULL;
Alexander Belopolsky1bcbaab2010-10-14 17:03:51 +00005816 x = create_timezone(delta, NULL);
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00005817 Py_DECREF(delta);
5818 if (x == NULL || PyDict_SetItemString(d, "max", x) < 0)
5819 return NULL;
5820 Py_DECREF(x);
5821
Alexander Belopolskya4415142012-06-08 12:33:09 -04005822 /* Epoch */
5823 PyDateTime_Epoch = new_datetime(1970, 1, 1, 0, 0, 0, 0,
Alexander Belopolsky5d0c5982016-07-22 18:47:04 -04005824 PyDateTime_TimeZone_UTC, 0);
Alexander Belopolskya4415142012-06-08 12:33:09 -04005825 if (PyDateTime_Epoch == NULL)
5826 return NULL;
5827
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005828 /* module initialization */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +02005829 PyModule_AddIntMacro(m, MINYEAR);
5830 PyModule_AddIntMacro(m, MAXYEAR);
Tim Peters2a799bf2002-12-16 20:18:38 +00005831
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005832 Py_INCREF(&PyDateTime_DateType);
5833 PyModule_AddObject(m, "date", (PyObject *) &PyDateTime_DateType);
Tim Peters2a799bf2002-12-16 20:18:38 +00005834
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005835 Py_INCREF(&PyDateTime_DateTimeType);
5836 PyModule_AddObject(m, "datetime",
5837 (PyObject *)&PyDateTime_DateTimeType);
Tim Petersa9bc1682003-01-11 03:39:11 +00005838
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005839 Py_INCREF(&PyDateTime_TimeType);
5840 PyModule_AddObject(m, "time", (PyObject *) &PyDateTime_TimeType);
Tim Petersa9bc1682003-01-11 03:39:11 +00005841
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005842 Py_INCREF(&PyDateTime_DeltaType);
5843 PyModule_AddObject(m, "timedelta", (PyObject *) &PyDateTime_DeltaType);
Tim Peters2a799bf2002-12-16 20:18:38 +00005844
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005845 Py_INCREF(&PyDateTime_TZInfoType);
5846 PyModule_AddObject(m, "tzinfo", (PyObject *) &PyDateTime_TZInfoType);
Tim Peters2a799bf2002-12-16 20:18:38 +00005847
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00005848 Py_INCREF(&PyDateTime_TimeZoneType);
5849 PyModule_AddObject(m, "timezone", (PyObject *) &PyDateTime_TimeZoneType);
5850
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005851 x = PyCapsule_New(&CAPI, PyDateTime_CAPSULE_NAME, NULL);
5852 if (x == NULL)
5853 return NULL;
5854 PyModule_AddObject(m, "datetime_CAPI", x);
Tim Peters9ddf40b2004-06-20 22:41:32 +00005855
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005856 /* A 4-year cycle has an extra leap day over what we'd get from
5857 * pasting together 4 single years.
5858 */
Serhiy Storchakafad85aa2015-11-07 15:42:38 +02005859 Py_BUILD_ASSERT(DI4Y == 4 * 365 + 1);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005860 assert(DI4Y == days_before_year(4+1));
Tim Peters2a799bf2002-12-16 20:18:38 +00005861
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005862 /* Similarly, a 400-year cycle has an extra leap day over what we'd
5863 * get from pasting together 4 100-year cycles.
5864 */
Serhiy Storchakafad85aa2015-11-07 15:42:38 +02005865 Py_BUILD_ASSERT(DI400Y == 4 * DI100Y + 1);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005866 assert(DI400Y == days_before_year(400+1));
Tim Peters2a799bf2002-12-16 20:18:38 +00005867
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005868 /* OTOH, a 100-year cycle has one fewer leap day than we'd get from
5869 * pasting together 25 4-year cycles.
5870 */
Serhiy Storchakafad85aa2015-11-07 15:42:38 +02005871 Py_BUILD_ASSERT(DI100Y == 25 * DI4Y - 1);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005872 assert(DI100Y == days_before_year(100+1));
Tim Peters2a799bf2002-12-16 20:18:38 +00005873
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005874 us_per_ms = PyLong_FromLong(1000);
5875 us_per_second = PyLong_FromLong(1000000);
5876 us_per_minute = PyLong_FromLong(60000000);
5877 seconds_per_day = PyLong_FromLong(24 * 3600);
Serhiy Storchakaba85d692017-03-30 09:09:41 +03005878 if (us_per_ms == NULL || us_per_second == NULL ||
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005879 us_per_minute == NULL || seconds_per_day == NULL)
5880 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00005881
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005882 /* The rest are too big for 32-bit ints, but even
5883 * us_per_week fits in 40 bits, so doubles should be exact.
5884 */
5885 us_per_hour = PyLong_FromDouble(3600000000.0);
5886 us_per_day = PyLong_FromDouble(86400000000.0);
5887 us_per_week = PyLong_FromDouble(604800000000.0);
5888 if (us_per_hour == NULL || us_per_day == NULL || us_per_week == NULL)
5889 return NULL;
5890 return m;
Tim Peters2a799bf2002-12-16 20:18:38 +00005891}
Tim Petersf3615152003-01-01 21:51:37 +00005892
5893/* ---------------------------------------------------------------------------
Tim Petersa9bc1682003-01-11 03:39:11 +00005894Some time zone algebra. For a datetime x, let
Tim Petersf3615152003-01-01 21:51:37 +00005895 x.n = x stripped of its timezone -- its naive time.
5896 x.o = x.utcoffset(), and assuming that doesn't raise an exception or
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005897 return None
Tim Petersf3615152003-01-01 21:51:37 +00005898 x.d = x.dst(), and assuming that doesn't raise an exception or
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005899 return None
Tim Petersf3615152003-01-01 21:51:37 +00005900 x.s = x's standard offset, x.o - x.d
5901
5902Now some derived rules, where k is a duration (timedelta).
5903
59041. x.o = x.s + x.d
5905 This follows from the definition of x.s.
5906
Tim Petersc5dc4da2003-01-02 17:55:03 +000059072. If x and y have the same tzinfo member, x.s = y.s.
Tim Petersf3615152003-01-01 21:51:37 +00005908 This is actually a requirement, an assumption we need to make about
5909 sane tzinfo classes.
5910
59113. The naive UTC time corresponding to x is x.n - x.o.
5912 This is again a requirement for a sane tzinfo class.
5913
59144. (x+k).s = x.s
Tim Peters8bb5ad22003-01-24 02:44:45 +00005915 This follows from #2, and that datimetimetz+timedelta preserves tzinfo.
Tim Petersf3615152003-01-01 21:51:37 +00005916
Tim Petersc5dc4da2003-01-02 17:55:03 +000059175. (x+k).n = x.n + k
Tim Petersf3615152003-01-01 21:51:37 +00005918 Again follows from how arithmetic is defined.
5919
Tim Peters8bb5ad22003-01-24 02:44:45 +00005920Now we can explain tz.fromutc(x). Let's assume it's an interesting case
Tim Petersf3615152003-01-01 21:51:37 +00005921(meaning that the various tzinfo methods exist, and don't blow up or return
5922None when called).
5923
Tim Petersa9bc1682003-01-11 03:39:11 +00005924The function wants to return a datetime y with timezone tz, equivalent to x.
Tim Peters8bb5ad22003-01-24 02:44:45 +00005925x is already in UTC.
Tim Petersf3615152003-01-01 21:51:37 +00005926
5927By #3, we want
5928
Tim Peters8bb5ad22003-01-24 02:44:45 +00005929 y.n - y.o = x.n [1]
Tim Petersf3615152003-01-01 21:51:37 +00005930
5931The algorithm starts by attaching tz to x.n, and calling that y. So
5932x.n = y.n at the start. Then it wants to add a duration k to y, so that [1]
5933becomes true; in effect, we want to solve [2] for k:
5934
Tim Peters8bb5ad22003-01-24 02:44:45 +00005935 (y+k).n - (y+k).o = x.n [2]
Tim Petersf3615152003-01-01 21:51:37 +00005936
5937By #1, this is the same as
5938
Tim Peters8bb5ad22003-01-24 02:44:45 +00005939 (y+k).n - ((y+k).s + (y+k).d) = x.n [3]
Tim Petersf3615152003-01-01 21:51:37 +00005940
5941By #5, (y+k).n = y.n + k, which equals x.n + k because x.n=y.n at the start.
5942Substituting that into [3],
5943
Tim Peters8bb5ad22003-01-24 02:44:45 +00005944 x.n + k - (y+k).s - (y+k).d = x.n; the x.n terms cancel, leaving
5945 k - (y+k).s - (y+k).d = 0; rearranging,
5946 k = (y+k).s - (y+k).d; by #4, (y+k).s == y.s, so
5947 k = y.s - (y+k).d
Tim Petersf3615152003-01-01 21:51:37 +00005948
Tim Peters8bb5ad22003-01-24 02:44:45 +00005949On the RHS, (y+k).d can't be computed directly, but y.s can be, and we
5950approximate k by ignoring the (y+k).d term at first. Note that k can't be
5951very large, since all offset-returning methods return a duration of magnitude
5952less than 24 hours. For that reason, if y is firmly in std time, (y+k).d must
5953be 0, so ignoring it has no consequence then.
Tim Petersf3615152003-01-01 21:51:37 +00005954
5955In any case, the new value is
5956
Tim Peters8bb5ad22003-01-24 02:44:45 +00005957 z = y + y.s [4]
Tim Petersf3615152003-01-01 21:51:37 +00005958
Tim Peters8bb5ad22003-01-24 02:44:45 +00005959It's helpful to step back at look at [4] from a higher level: it's simply
5960mapping from UTC to tz's standard time.
Tim Petersc5dc4da2003-01-02 17:55:03 +00005961
5962At this point, if
5963
Tim Peters8bb5ad22003-01-24 02:44:45 +00005964 z.n - z.o = x.n [5]
Tim Petersc5dc4da2003-01-02 17:55:03 +00005965
5966we have an equivalent time, and are almost done. The insecurity here is
Tim Petersf3615152003-01-01 21:51:37 +00005967at the start of daylight time. Picture US Eastern for concreteness. The wall
5968time jumps from 1:59 to 3:00, and wall hours of the form 2:MM don't make good
Tim Peters8bb5ad22003-01-24 02:44:45 +00005969sense then. The docs ask that an Eastern tzinfo class consider such a time to
5970be EDT (because it's "after 2"), which is a redundant spelling of 1:MM EST
5971on the day DST starts. We want to return the 1:MM EST spelling because that's
Tim Petersf3615152003-01-01 21:51:37 +00005972the only spelling that makes sense on the local wall clock.
5973
Tim Petersc5dc4da2003-01-02 17:55:03 +00005974In fact, if [5] holds at this point, we do have the standard-time spelling,
5975but that takes a bit of proof. We first prove a stronger result. What's the
5976difference between the LHS and RHS of [5]? Let
Tim Petersf3615152003-01-01 21:51:37 +00005977
Tim Peters8bb5ad22003-01-24 02:44:45 +00005978 diff = x.n - (z.n - z.o) [6]
Tim Petersf3615152003-01-01 21:51:37 +00005979
Tim Petersc5dc4da2003-01-02 17:55:03 +00005980Now
5981 z.n = by [4]
Tim Peters8bb5ad22003-01-24 02:44:45 +00005982 (y + y.s).n = by #5
5983 y.n + y.s = since y.n = x.n
5984 x.n + y.s = since z and y are have the same tzinfo member,
5985 y.s = z.s by #2
5986 x.n + z.s
Tim Petersf3615152003-01-01 21:51:37 +00005987
Tim Petersc5dc4da2003-01-02 17:55:03 +00005988Plugging that back into [6] gives
Tim Petersf3615152003-01-01 21:51:37 +00005989
Tim Petersc5dc4da2003-01-02 17:55:03 +00005990 diff =
Tim Peters8bb5ad22003-01-24 02:44:45 +00005991 x.n - ((x.n + z.s) - z.o) = expanding
5992 x.n - x.n - z.s + z.o = cancelling
5993 - z.s + z.o = by #2
Tim Petersc5dc4da2003-01-02 17:55:03 +00005994 z.d
Tim Petersf3615152003-01-01 21:51:37 +00005995
Tim Petersc5dc4da2003-01-02 17:55:03 +00005996So diff = z.d.
Tim Petersf3615152003-01-01 21:51:37 +00005997
Tim Petersc5dc4da2003-01-02 17:55:03 +00005998If [5] is true now, diff = 0, so z.d = 0 too, and we have the standard-time
Tim Peters8bb5ad22003-01-24 02:44:45 +00005999spelling we wanted in the endcase described above. We're done. Contrarily,
6000if z.d = 0, then we have a UTC equivalent, and are also done.
Tim Petersf3615152003-01-01 21:51:37 +00006001
Tim Petersc5dc4da2003-01-02 17:55:03 +00006002If [5] is not true now, diff = z.d != 0, and z.d is the offset we need to
6003add to z (in effect, z is in tz's standard time, and we need to shift the
Tim Peters8bb5ad22003-01-24 02:44:45 +00006004local clock into tz's daylight time).
Tim Petersf3615152003-01-01 21:51:37 +00006005
Tim Petersc5dc4da2003-01-02 17:55:03 +00006006Let
Tim Petersf3615152003-01-01 21:51:37 +00006007
Tim Peters4fede1a2003-01-04 00:26:59 +00006008 z' = z + z.d = z + diff [7]
Tim Petersc3bb26a2003-01-02 03:14:59 +00006009
Tim Peters4fede1a2003-01-04 00:26:59 +00006010and we can again ask whether
Tim Petersc3bb26a2003-01-02 03:14:59 +00006011
Tim Peters8bb5ad22003-01-24 02:44:45 +00006012 z'.n - z'.o = x.n [8]
Tim Petersc3bb26a2003-01-02 03:14:59 +00006013
Tim Peters8bb5ad22003-01-24 02:44:45 +00006014If so, we're done. If not, the tzinfo class is insane, according to the
6015assumptions we've made. This also requires a bit of proof. As before, let's
6016compute the difference between the LHS and RHS of [8] (and skipping some of
6017the justifications for the kinds of substitutions we've done several times
6018already):
Tim Peters4fede1a2003-01-04 00:26:59 +00006019
Tim Peters8bb5ad22003-01-24 02:44:45 +00006020 diff' = x.n - (z'.n - z'.o) = replacing z'.n via [7]
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00006021 x.n - (z.n + diff - z'.o) = replacing diff via [6]
6022 x.n - (z.n + x.n - (z.n - z.o) - z'.o) =
6023 x.n - z.n - x.n + z.n - z.o + z'.o = cancel x.n
6024 - z.n + z.n - z.o + z'.o = cancel z.n
6025 - z.o + z'.o = #1 twice
6026 -z.s - z.d + z'.s + z'.d = z and z' have same tzinfo
6027 z'.d - z.d
Tim Peters4fede1a2003-01-04 00:26:59 +00006028
6029So z' is UTC-equivalent to x iff z'.d = z.d at this point. If they are equal,
Tim Peters8bb5ad22003-01-24 02:44:45 +00006030we've found the UTC-equivalent so are done. In fact, we stop with [7] and
6031return z', not bothering to compute z'.d.
Tim Peters4fede1a2003-01-04 00:26:59 +00006032
Tim Peters8bb5ad22003-01-24 02:44:45 +00006033How could z.d and z'd differ? z' = z + z.d [7], so merely moving z' by
6034a dst() offset, and starting *from* a time already in DST (we know z.d != 0),
6035would have to change the result dst() returns: we start in DST, and moving
6036a little further into it takes us out of DST.
Tim Peters4fede1a2003-01-04 00:26:59 +00006037
Tim Peters8bb5ad22003-01-24 02:44:45 +00006038There isn't a sane case where this can happen. The closest it gets is at
6039the end of DST, where there's an hour in UTC with no spelling in a hybrid
6040tzinfo class. In US Eastern, that's 5:MM UTC = 0:MM EST = 1:MM EDT. During
6041that hour, on an Eastern clock 1:MM is taken as being in standard time (6:MM
6042UTC) because the docs insist on that, but 0:MM is taken as being in daylight
6043time (4:MM UTC). There is no local time mapping to 5:MM UTC. The local
6044clock jumps from 1:59 back to 1:00 again, and repeats the 1:MM hour in
6045standard time. Since that's what the local clock *does*, we want to map both
6046UTC hours 5:MM and 6:MM to 1:MM Eastern. The result is ambiguous
Tim Peters4fede1a2003-01-04 00:26:59 +00006047in local time, but so it goes -- it's the way the local clock works.
6048
Tim Peters8bb5ad22003-01-24 02:44:45 +00006049When x = 5:MM UTC is the input to this algorithm, x.o=0, y.o=-5 and y.d=0,
6050so z=0:MM. z.d=60 (minutes) then, so [5] doesn't hold and we keep going.
6051z' = z + z.d = 1:MM then, and z'.d=0, and z'.d - z.d = -60 != 0 so [8]
Tim Peters4fede1a2003-01-04 00:26:59 +00006052(correctly) concludes that z' is not UTC-equivalent to x.
6053
6054Because we know z.d said z was in daylight time (else [5] would have held and
6055we would have stopped then), and we know z.d != z'.d (else [8] would have held
Walter Dörwaldf0dfc7a2003-10-20 14:01:56 +00006056and we would have stopped then), and there are only 2 possible values dst() can
Tim Peters4fede1a2003-01-04 00:26:59 +00006057return in Eastern, it follows that z'.d must be 0 (which it is in the example,
6058but the reasoning doesn't depend on the example -- it depends on there being
6059two possible dst() outcomes, one zero and the other non-zero). Therefore
Tim Peters8bb5ad22003-01-24 02:44:45 +00006060z' must be in standard time, and is the spelling we want in this case.
6061
6062Note again that z' is not UTC-equivalent as far as the hybrid tzinfo class is
6063concerned (because it takes z' as being in standard time rather than the
6064daylight time we intend here), but returning it gives the real-life "local
6065clock repeats an hour" behavior when mapping the "unspellable" UTC hour into
6066tz.
6067
6068When the input is 6:MM, z=1:MM and z.d=0, and we stop at once, again with
6069the 1:MM standard time spelling we want.
6070
6071So how can this break? One of the assumptions must be violated. Two
6072possibilities:
6073
60741) [2] effectively says that y.s is invariant across all y belong to a given
6075 time zone. This isn't true if, for political reasons or continental drift,
6076 a region decides to change its base offset from UTC.
6077
60782) There may be versions of "double daylight" time where the tail end of
6079 the analysis gives up a step too early. I haven't thought about that
6080 enough to say.
6081
6082In any case, it's clear that the default fromutc() is strong enough to handle
6083"almost all" time zones: so long as the standard offset is invariant, it
6084doesn't matter if daylight time transition points change from year to year, or
6085if daylight time is skipped in some years; it doesn't matter how large or
6086small dst() may get within its bounds; and it doesn't even matter if some
6087perverse time zone returns a negative dst()). So a breaking case must be
6088pretty bizarre, and a tzinfo subclass can override fromutc() if it is.
Tim Petersf3615152003-01-01 21:51:37 +00006089--------------------------------------------------------------------------- */