blob: ef2f7b306a04e54b13aaef4c6525a7cb0fcf42f8 [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
Alexander Belopolsky6fc4ade2010-08-05 17:34:27 +000010#include "_time.h"
Tim Peters9ddf40b2004-06-20 22:41:32 +000011
12/* Differentiate between building the core module and building extension
13 * modules.
14 */
Guido van Rossum360e4b82007-05-14 22:51:27 +000015#ifndef Py_BUILD_CORE
Tim Peters9ddf40b2004-06-20 22:41:32 +000016#define Py_BUILD_CORE
Guido van Rossum360e4b82007-05-14 22:51:27 +000017#endif
Tim Peters2a799bf2002-12-16 20:18:38 +000018#include "datetime.h"
Tim Peters9ddf40b2004-06-20 22:41:32 +000019#undef Py_BUILD_CORE
Tim Peters2a799bf2002-12-16 20:18:38 +000020
21/* We require that C int be at least 32 bits, and use int virtually
22 * everywhere. In just a few cases we use a temp long, where a Python
23 * API returns a C long. In such cases, we have to ensure that the
24 * final result fits in a C int (this can be an issue on 64-bit boxes).
25 */
26#if SIZEOF_INT < 4
Alexander Belopolskycf86e362010-07-23 19:25:47 +000027# error "_datetime.c requires that C int have at least 32 bits"
Tim Peters2a799bf2002-12-16 20:18:38 +000028#endif
29
30#define MINYEAR 1
31#define MAXYEAR 9999
Alexander Belopolskyf03a6162010-05-27 21:42:58 +000032#define MAXORDINAL 3652059 /* date(9999,12,31).toordinal() */
Tim Peters2a799bf2002-12-16 20:18:38 +000033
34/* Nine decimal digits is easy to communicate, and leaves enough room
35 * so that two delta days can be added w/o fear of overflowing a signed
36 * 32-bit int, and with plenty of room left over to absorb any possible
37 * carries from adding seconds.
38 */
39#define MAX_DELTA_DAYS 999999999
40
41/* Rename the long macros in datetime.h to more reasonable short names. */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000042#define GET_YEAR PyDateTime_GET_YEAR
43#define GET_MONTH PyDateTime_GET_MONTH
44#define GET_DAY PyDateTime_GET_DAY
45#define DATE_GET_HOUR PyDateTime_DATE_GET_HOUR
46#define DATE_GET_MINUTE PyDateTime_DATE_GET_MINUTE
47#define DATE_GET_SECOND PyDateTime_DATE_GET_SECOND
48#define DATE_GET_MICROSECOND PyDateTime_DATE_GET_MICROSECOND
Tim Peters2a799bf2002-12-16 20:18:38 +000049
50/* Date accessors for date and datetime. */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000051#define SET_YEAR(o, v) (((o)->data[0] = ((v) & 0xff00) >> 8), \
52 ((o)->data[1] = ((v) & 0x00ff)))
53#define SET_MONTH(o, v) (PyDateTime_GET_MONTH(o) = (v))
54#define SET_DAY(o, v) (PyDateTime_GET_DAY(o) = (v))
Tim Peters2a799bf2002-12-16 20:18:38 +000055
56/* Date/Time accessors for datetime. */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000057#define DATE_SET_HOUR(o, v) (PyDateTime_DATE_GET_HOUR(o) = (v))
58#define DATE_SET_MINUTE(o, v) (PyDateTime_DATE_GET_MINUTE(o) = (v))
59#define DATE_SET_SECOND(o, v) (PyDateTime_DATE_GET_SECOND(o) = (v))
60#define DATE_SET_MICROSECOND(o, v) \
61 (((o)->data[7] = ((v) & 0xff0000) >> 16), \
62 ((o)->data[8] = ((v) & 0x00ff00) >> 8), \
63 ((o)->data[9] = ((v) & 0x0000ff)))
Tim Peters2a799bf2002-12-16 20:18:38 +000064
65/* Time accessors for time. */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000066#define TIME_GET_HOUR PyDateTime_TIME_GET_HOUR
67#define TIME_GET_MINUTE PyDateTime_TIME_GET_MINUTE
68#define TIME_GET_SECOND PyDateTime_TIME_GET_SECOND
69#define TIME_GET_MICROSECOND PyDateTime_TIME_GET_MICROSECOND
70#define TIME_SET_HOUR(o, v) (PyDateTime_TIME_GET_HOUR(o) = (v))
71#define TIME_SET_MINUTE(o, v) (PyDateTime_TIME_GET_MINUTE(o) = (v))
72#define TIME_SET_SECOND(o, v) (PyDateTime_TIME_GET_SECOND(o) = (v))
73#define TIME_SET_MICROSECOND(o, v) \
74 (((o)->data[3] = ((v) & 0xff0000) >> 16), \
75 ((o)->data[4] = ((v) & 0x00ff00) >> 8), \
76 ((o)->data[5] = ((v) & 0x0000ff)))
Tim Peters2a799bf2002-12-16 20:18:38 +000077
78/* Delta accessors for timedelta. */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000079#define GET_TD_DAYS(o) (((PyDateTime_Delta *)(o))->days)
80#define GET_TD_SECONDS(o) (((PyDateTime_Delta *)(o))->seconds)
81#define GET_TD_MICROSECONDS(o) (((PyDateTime_Delta *)(o))->microseconds)
Tim Peters2a799bf2002-12-16 20:18:38 +000082
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000083#define SET_TD_DAYS(o, v) ((o)->days = (v))
84#define SET_TD_SECONDS(o, v) ((o)->seconds = (v))
Tim Peters2a799bf2002-12-16 20:18:38 +000085#define SET_TD_MICROSECONDS(o, v) ((o)->microseconds = (v))
86
Tim Petersa032d2e2003-01-11 00:15:54 +000087/* p is a pointer to a time or a datetime object; HASTZINFO(p) returns
88 * p->hastzinfo.
89 */
Alexander Belopolsky73ca4402010-07-07 23:56:38 +000090#define HASTZINFO(p) (((_PyDateTime_BaseTZInfo *)(p))->hastzinfo)
91#define GET_TIME_TZINFO(p) (HASTZINFO(p) ? \
92 ((PyDateTime_Time *)(p))->tzinfo : Py_None)
93#define GET_DT_TZINFO(p) (HASTZINFO(p) ? \
94 ((PyDateTime_DateTime *)(p))->tzinfo : Py_None)
Tim Peters3f606292004-03-21 23:38:41 +000095/* M is a char or int claiming to be a valid month. The macro is equivalent
96 * to the two-sided Python test
Antoine Pitrouf95a1b32010-05-09 15:52:27 +000097 * 1 <= M <= 12
Tim Peters3f606292004-03-21 23:38:41 +000098 */
99#define MONTH_IS_SANE(M) ((unsigned int)(M) - 1 < 12)
100
Tim Peters2a799bf2002-12-16 20:18:38 +0000101/* Forward declarations. */
102static PyTypeObject PyDateTime_DateType;
103static PyTypeObject PyDateTime_DateTimeType;
Tim Peters2a799bf2002-12-16 20:18:38 +0000104static PyTypeObject PyDateTime_DeltaType;
105static PyTypeObject PyDateTime_TimeType;
106static PyTypeObject PyDateTime_TZInfoType;
Alexander Belopolsky4e749a12010-06-14 14:15:50 +0000107static PyTypeObject PyDateTime_TimeZoneType;
Tim Peters2a799bf2002-12-16 20:18:38 +0000108
109/* ---------------------------------------------------------------------------
110 * Math utilities.
111 */
112
113/* k = i+j overflows iff k differs in sign from both inputs,
114 * iff k^i has sign bit set and k^j has sign bit set,
115 * iff (k^i)&(k^j) has sign bit set.
116 */
117#define SIGNED_ADD_OVERFLOWED(RESULT, I, J) \
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000118 ((((RESULT) ^ (I)) & ((RESULT) ^ (J))) < 0)
Tim Peters2a799bf2002-12-16 20:18:38 +0000119
120/* Compute Python divmod(x, y), returning the quotient and storing the
121 * remainder into *r. The quotient is the floor of x/y, and that's
122 * the real point of this. C will probably truncate instead (C99
123 * requires truncation; C89 left it implementation-defined).
124 * Simplification: we *require* that y > 0 here. That's appropriate
125 * for all the uses made of it. This simplifies the code and makes
126 * the overflow case impossible (divmod(LONG_MIN, -1) is the only
127 * overflow case).
128 */
129static int
130divmod(int x, int y, int *r)
131{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000132 int quo;
Tim Peters2a799bf2002-12-16 20:18:38 +0000133
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000134 assert(y > 0);
135 quo = x / y;
136 *r = x - quo * y;
137 if (*r < 0) {
138 --quo;
139 *r += y;
140 }
141 assert(0 <= *r && *r < y);
142 return quo;
Tim Peters2a799bf2002-12-16 20:18:38 +0000143}
144
Tim Peters5d644dd2003-01-02 16:32:54 +0000145/* Round a double to the nearest long. |x| must be small enough to fit
146 * in a C long; this is not checked.
147 */
148static long
149round_to_long(double x)
150{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000151 if (x >= 0.0)
152 x = floor(x + 0.5);
153 else
154 x = ceil(x - 0.5);
155 return (long)x;
Tim Peters5d644dd2003-01-02 16:32:54 +0000156}
157
Alexander Belopolsky1790bc42010-05-31 17:33:47 +0000158/* Nearest integer to m / n for integers m and n. Half-integer results
159 * are rounded to even.
160 */
161static PyObject *
162divide_nearest(PyObject *m, PyObject *n)
163{
164 PyObject *result;
165 PyObject *temp;
166
Mark Dickinsonfa68a612010-06-07 18:47:09 +0000167 temp = _PyLong_DivmodNear(m, n);
Alexander Belopolsky1790bc42010-05-31 17:33:47 +0000168 if (temp == NULL)
169 return NULL;
170 result = PyTuple_GET_ITEM(temp, 0);
171 Py_INCREF(result);
172 Py_DECREF(temp);
173
174 return result;
175}
176
Tim Peters2a799bf2002-12-16 20:18:38 +0000177/* ---------------------------------------------------------------------------
178 * General calendrical helper functions
179 */
180
181/* For each month ordinal in 1..12, the number of days in that month,
182 * and the number of days before that month in the same year. These
183 * are correct for non-leap years only.
184 */
185static int _days_in_month[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000186 0, /* unused; this vector uses 1-based indexing */
187 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31
Tim Peters2a799bf2002-12-16 20:18:38 +0000188};
189
190static int _days_before_month[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000191 0, /* unused; this vector uses 1-based indexing */
192 0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334
Tim Peters2a799bf2002-12-16 20:18:38 +0000193};
194
195/* year -> 1 if leap year, else 0. */
196static int
197is_leap(int year)
198{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000199 /* Cast year to unsigned. The result is the same either way, but
200 * C can generate faster code for unsigned mod than for signed
201 * mod (especially for % 4 -- a good compiler should just grab
202 * the last 2 bits when the LHS is unsigned).
203 */
204 const unsigned int ayear = (unsigned int)year;
205 return ayear % 4 == 0 && (ayear % 100 != 0 || ayear % 400 == 0);
Tim Peters2a799bf2002-12-16 20:18:38 +0000206}
207
208/* year, month -> number of days in that month in that year */
209static int
210days_in_month(int year, int month)
211{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000212 assert(month >= 1);
213 assert(month <= 12);
214 if (month == 2 && is_leap(year))
215 return 29;
216 else
217 return _days_in_month[month];
Tim Peters2a799bf2002-12-16 20:18:38 +0000218}
219
220/* year, month -> number of days in year preceeding first day of month */
221static int
222days_before_month(int year, int month)
223{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000224 int days;
Tim Peters2a799bf2002-12-16 20:18:38 +0000225
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000226 assert(month >= 1);
227 assert(month <= 12);
228 days = _days_before_month[month];
229 if (month > 2 && is_leap(year))
230 ++days;
231 return days;
Tim Peters2a799bf2002-12-16 20:18:38 +0000232}
233
234/* year -> number of days before January 1st of year. Remember that we
235 * start with year 1, so days_before_year(1) == 0.
236 */
237static int
238days_before_year(int year)
239{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000240 int y = year - 1;
241 /* This is incorrect if year <= 0; we really want the floor
242 * here. But so long as MINYEAR is 1, the smallest year this
Alexander Belopolsky59a289d2010-10-13 22:54:34 +0000243 * can see is 1.
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000244 */
Alexander Belopolsky59a289d2010-10-13 22:54:34 +0000245 assert (year >= 1);
246 return y*365 + y/4 - y/100 + y/400;
Tim Peters2a799bf2002-12-16 20:18:38 +0000247}
248
249/* Number of days in 4, 100, and 400 year cycles. That these have
250 * the correct values is asserted in the module init function.
251 */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000252#define DI4Y 1461 /* days_before_year(5); days in 4 years */
253#define DI100Y 36524 /* days_before_year(101); days in 100 years */
254#define DI400Y 146097 /* days_before_year(401); days in 400 years */
Tim Peters2a799bf2002-12-16 20:18:38 +0000255
256/* ordinal -> year, month, day, considering 01-Jan-0001 as day 1. */
257static void
258ord_to_ymd(int ordinal, int *year, int *month, int *day)
259{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000260 int n, n1, n4, n100, n400, leapyear, preceding;
Tim Peters2a799bf2002-12-16 20:18:38 +0000261
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000262 /* ordinal is a 1-based index, starting at 1-Jan-1. The pattern of
263 * leap years repeats exactly every 400 years. The basic strategy is
264 * to find the closest 400-year boundary at or before ordinal, then
265 * work with the offset from that boundary to ordinal. Life is much
266 * clearer if we subtract 1 from ordinal first -- then the values
267 * of ordinal at 400-year boundaries are exactly those divisible
268 * by DI400Y:
269 *
270 * D M Y n n-1
271 * -- --- ---- ---------- ----------------
272 * 31 Dec -400 -DI400Y -DI400Y -1
273 * 1 Jan -399 -DI400Y +1 -DI400Y 400-year boundary
274 * ...
275 * 30 Dec 000 -1 -2
276 * 31 Dec 000 0 -1
277 * 1 Jan 001 1 0 400-year boundary
278 * 2 Jan 001 2 1
279 * 3 Jan 001 3 2
280 * ...
281 * 31 Dec 400 DI400Y DI400Y -1
282 * 1 Jan 401 DI400Y +1 DI400Y 400-year boundary
283 */
284 assert(ordinal >= 1);
285 --ordinal;
286 n400 = ordinal / DI400Y;
287 n = ordinal % DI400Y;
288 *year = n400 * 400 + 1;
Tim Peters2a799bf2002-12-16 20:18:38 +0000289
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000290 /* Now n is the (non-negative) offset, in days, from January 1 of
291 * year, to the desired date. Now compute how many 100-year cycles
292 * precede n.
293 * Note that it's possible for n100 to equal 4! In that case 4 full
294 * 100-year cycles precede the desired day, which implies the
295 * desired day is December 31 at the end of a 400-year cycle.
296 */
297 n100 = n / DI100Y;
298 n = n % DI100Y;
Tim Peters2a799bf2002-12-16 20:18:38 +0000299
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000300 /* Now compute how many 4-year cycles precede it. */
301 n4 = n / DI4Y;
302 n = n % DI4Y;
Tim Peters2a799bf2002-12-16 20:18:38 +0000303
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000304 /* And now how many single years. Again n1 can be 4, and again
305 * meaning that the desired day is December 31 at the end of the
306 * 4-year cycle.
307 */
308 n1 = n / 365;
309 n = n % 365;
Tim Peters2a799bf2002-12-16 20:18:38 +0000310
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000311 *year += n100 * 100 + n4 * 4 + n1;
312 if (n1 == 4 || n100 == 4) {
313 assert(n == 0);
314 *year -= 1;
315 *month = 12;
316 *day = 31;
317 return;
318 }
Tim Peters2a799bf2002-12-16 20:18:38 +0000319
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000320 /* Now the year is correct, and n is the offset from January 1. We
321 * find the month via an estimate that's either exact or one too
322 * large.
323 */
324 leapyear = n1 == 3 && (n4 != 24 || n100 == 3);
325 assert(leapyear == is_leap(*year));
326 *month = (n + 50) >> 5;
327 preceding = (_days_before_month[*month] + (*month > 2 && leapyear));
328 if (preceding > n) {
329 /* estimate is too large */
330 *month -= 1;
331 preceding -= days_in_month(*year, *month);
332 }
333 n -= preceding;
334 assert(0 <= n);
335 assert(n < days_in_month(*year, *month));
Tim Peters2a799bf2002-12-16 20:18:38 +0000336
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000337 *day = n + 1;
Tim Peters2a799bf2002-12-16 20:18:38 +0000338}
339
340/* year, month, day -> ordinal, considering 01-Jan-0001 as day 1. */
341static int
342ymd_to_ord(int year, int month, int day)
343{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000344 return days_before_year(year) + days_before_month(year, month) + day;
Tim Peters2a799bf2002-12-16 20:18:38 +0000345}
346
347/* Day of week, where Monday==0, ..., Sunday==6. 1/1/1 was a Monday. */
348static int
349weekday(int year, int month, int day)
350{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000351 return (ymd_to_ord(year, month, day) + 6) % 7;
Tim Peters2a799bf2002-12-16 20:18:38 +0000352}
353
354/* Ordinal of the Monday starting week 1 of the ISO year. Week 1 is the
355 * first calendar week containing a Thursday.
356 */
357static int
358iso_week1_monday(int year)
359{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000360 int first_day = ymd_to_ord(year, 1, 1); /* ord of 1/1 */
361 /* 0 if 1/1 is a Monday, 1 if a Tue, etc. */
362 int first_weekday = (first_day + 6) % 7;
363 /* ordinal of closest Monday at or before 1/1 */
364 int week1_monday = first_day - first_weekday;
Tim Peters2a799bf2002-12-16 20:18:38 +0000365
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000366 if (first_weekday > 3) /* if 1/1 was Fri, Sat, Sun */
367 week1_monday += 7;
368 return week1_monday;
Tim Peters2a799bf2002-12-16 20:18:38 +0000369}
370
371/* ---------------------------------------------------------------------------
372 * Range checkers.
373 */
374
375/* Check that -MAX_DELTA_DAYS <= days <= MAX_DELTA_DAYS. If so, return 0.
376 * If not, raise OverflowError and return -1.
377 */
378static int
379check_delta_day_range(int days)
380{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000381 if (-MAX_DELTA_DAYS <= days && days <= MAX_DELTA_DAYS)
382 return 0;
383 PyErr_Format(PyExc_OverflowError,
384 "days=%d; must have magnitude <= %d",
385 days, MAX_DELTA_DAYS);
386 return -1;
Tim Peters2a799bf2002-12-16 20:18:38 +0000387}
388
389/* Check that date arguments are in range. Return 0 if they are. If they
390 * aren't, raise ValueError and return -1.
391 */
392static int
393check_date_args(int year, int month, int day)
394{
395
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000396 if (year < MINYEAR || year > MAXYEAR) {
397 PyErr_SetString(PyExc_ValueError,
398 "year is out of range");
399 return -1;
400 }
401 if (month < 1 || month > 12) {
402 PyErr_SetString(PyExc_ValueError,
403 "month must be in 1..12");
404 return -1;
405 }
406 if (day < 1 || day > days_in_month(year, month)) {
407 PyErr_SetString(PyExc_ValueError,
408 "day is out of range for month");
409 return -1;
410 }
411 return 0;
Tim Peters2a799bf2002-12-16 20:18:38 +0000412}
413
414/* Check that time arguments are in range. Return 0 if they are. If they
415 * aren't, raise ValueError and return -1.
416 */
417static int
418check_time_args(int h, int m, int s, int us)
419{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000420 if (h < 0 || h > 23) {
421 PyErr_SetString(PyExc_ValueError,
422 "hour must be in 0..23");
423 return -1;
424 }
425 if (m < 0 || m > 59) {
426 PyErr_SetString(PyExc_ValueError,
427 "minute must be in 0..59");
428 return -1;
429 }
430 if (s < 0 || s > 59) {
431 PyErr_SetString(PyExc_ValueError,
432 "second must be in 0..59");
433 return -1;
434 }
435 if (us < 0 || us > 999999) {
436 PyErr_SetString(PyExc_ValueError,
437 "microsecond must be in 0..999999");
438 return -1;
439 }
440 return 0;
Tim Peters2a799bf2002-12-16 20:18:38 +0000441}
442
443/* ---------------------------------------------------------------------------
444 * Normalization utilities.
445 */
446
447/* One step of a mixed-radix conversion. A "hi" unit is equivalent to
448 * factor "lo" units. factor must be > 0. If *lo is less than 0, or
449 * at least factor, enough of *lo is converted into "hi" units so that
450 * 0 <= *lo < factor. The input values must be such that int overflow
451 * is impossible.
452 */
453static void
454normalize_pair(int *hi, int *lo, int factor)
455{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000456 assert(factor > 0);
457 assert(lo != hi);
458 if (*lo < 0 || *lo >= factor) {
459 const int num_hi = divmod(*lo, factor, lo);
460 const int new_hi = *hi + num_hi;
461 assert(! SIGNED_ADD_OVERFLOWED(new_hi, *hi, num_hi));
462 *hi = new_hi;
463 }
464 assert(0 <= *lo && *lo < factor);
Tim Peters2a799bf2002-12-16 20:18:38 +0000465}
466
467/* Fiddle days (d), seconds (s), and microseconds (us) so that
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000468 * 0 <= *s < 24*3600
469 * 0 <= *us < 1000000
Tim Peters2a799bf2002-12-16 20:18:38 +0000470 * The input values must be such that the internals don't overflow.
471 * The way this routine is used, we don't get close.
472 */
473static void
474normalize_d_s_us(int *d, int *s, int *us)
475{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000476 if (*us < 0 || *us >= 1000000) {
477 normalize_pair(s, us, 1000000);
478 /* |s| can't be bigger than about
479 * |original s| + |original us|/1000000 now.
480 */
Tim Peters2a799bf2002-12-16 20:18:38 +0000481
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000482 }
483 if (*s < 0 || *s >= 24*3600) {
484 normalize_pair(d, s, 24*3600);
485 /* |d| can't be bigger than about
486 * |original d| +
487 * (|original s| + |original us|/1000000) / (24*3600) now.
488 */
489 }
490 assert(0 <= *s && *s < 24*3600);
491 assert(0 <= *us && *us < 1000000);
Tim Peters2a799bf2002-12-16 20:18:38 +0000492}
493
494/* Fiddle years (y), months (m), and days (d) so that
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000495 * 1 <= *m <= 12
496 * 1 <= *d <= days_in_month(*y, *m)
Tim Peters2a799bf2002-12-16 20:18:38 +0000497 * The input values must be such that the internals don't overflow.
498 * The way this routine is used, we don't get close.
499 */
Alexander Belopolskyf03a6162010-05-27 21:42:58 +0000500static int
Tim Peters2a799bf2002-12-16 20:18:38 +0000501normalize_y_m_d(int *y, int *m, int *d)
502{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000503 int dim; /* # of days in month */
Tim Peters2a799bf2002-12-16 20:18:38 +0000504
Alexander Belopolsky59a289d2010-10-13 22:54:34 +0000505 /* In actual use, m is always the month component extracted from a
506 * date/datetime object. Therefore it is always in [1, 12] range.
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000507 */
Alexander Belopolsky59a289d2010-10-13 22:54:34 +0000508
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000509 assert(1 <= *m && *m <= 12);
Tim Peters2a799bf2002-12-16 20:18:38 +0000510
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000511 /* Now only day can be out of bounds (year may also be out of bounds
512 * for a datetime object, but we don't care about that here).
513 * If day is out of bounds, what to do is arguable, but at least the
514 * method here is principled and explainable.
515 */
516 dim = days_in_month(*y, *m);
517 if (*d < 1 || *d > dim) {
518 /* Move day-1 days from the first of the month. First try to
519 * get off cheap if we're only one day out of range
520 * (adjustments for timezone alone can't be worse than that).
521 */
522 if (*d == 0) {
523 --*m;
524 if (*m > 0)
525 *d = days_in_month(*y, *m);
526 else {
527 --*y;
528 *m = 12;
529 *d = 31;
530 }
531 }
532 else if (*d == dim + 1) {
533 /* move forward a day */
534 ++*m;
535 *d = 1;
536 if (*m > 12) {
537 *m = 1;
538 ++*y;
539 }
540 }
541 else {
542 int ordinal = ymd_to_ord(*y, *m, 1) +
543 *d - 1;
Alexander Belopolskyf03a6162010-05-27 21:42:58 +0000544 if (ordinal < 1 || ordinal > MAXORDINAL) {
545 goto error;
546 } else {
547 ord_to_ymd(ordinal, y, m, d);
548 return 0;
549 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000550 }
551 }
552 assert(*m > 0);
553 assert(*d > 0);
Alexander Belopolskyf03a6162010-05-27 21:42:58 +0000554 if (MINYEAR <= *y && *y <= MAXYEAR)
555 return 0;
556 error:
557 PyErr_SetString(PyExc_OverflowError,
558 "date value out of range");
559 return -1;
560
Tim Peters2a799bf2002-12-16 20:18:38 +0000561}
562
563/* Fiddle out-of-bounds months and days so that the result makes some kind
564 * of sense. The parameters are both inputs and outputs. Returns < 0 on
565 * failure, where failure means the adjusted year is out of bounds.
566 */
567static int
568normalize_date(int *year, int *month, int *day)
569{
Alexander Belopolskyf03a6162010-05-27 21:42:58 +0000570 return normalize_y_m_d(year, month, day);
Tim Peters2a799bf2002-12-16 20:18:38 +0000571}
572
573/* Force all the datetime fields into range. The parameters are both
574 * inputs and outputs. Returns < 0 on error.
575 */
576static int
577normalize_datetime(int *year, int *month, int *day,
578 int *hour, int *minute, int *second,
579 int *microsecond)
580{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000581 normalize_pair(second, microsecond, 1000000);
582 normalize_pair(minute, second, 60);
583 normalize_pair(hour, minute, 60);
584 normalize_pair(day, hour, 24);
585 return normalize_date(year, month, day);
Tim Peters2a799bf2002-12-16 20:18:38 +0000586}
587
588/* ---------------------------------------------------------------------------
Tim Petersb0c854d2003-05-17 15:57:00 +0000589 * Basic object allocation: tp_alloc implementations. These allocate
590 * Python objects of the right size and type, and do the Python object-
591 * initialization bit. If there's not enough memory, they return NULL after
592 * setting MemoryError. All data members remain uninitialized trash.
593 *
594 * We abuse the tp_alloc "nitems" argument to communicate whether a tzinfo
Tim Peters03eaf8b2003-05-18 02:24:46 +0000595 * member is needed. This is ugly, imprecise, and possibly insecure.
596 * tp_basicsize for the time and datetime types is set to the size of the
597 * struct that has room for the tzinfo member, so subclasses in Python will
598 * allocate enough space for a tzinfo member whether or not one is actually
599 * needed. That's the "ugly and imprecise" parts. The "possibly insecure"
600 * part is that PyType_GenericAlloc() (which subclasses in Python end up
601 * using) just happens today to effectively ignore the nitems argument
602 * when tp_itemsize is 0, which it is for these type objects. If that
603 * changes, perhaps the callers of tp_alloc slots in this file should
604 * be changed to force a 0 nitems argument unless the type being allocated
605 * is a base type implemented in this file (so that tp_alloc is time_alloc
606 * or datetime_alloc below, which know about the nitems abuse).
Tim Petersb0c854d2003-05-17 15:57:00 +0000607 */
608
609static PyObject *
Martin v. Löwis18e16552006-02-15 17:27:45 +0000610time_alloc(PyTypeObject *type, Py_ssize_t aware)
Tim Petersb0c854d2003-05-17 15:57:00 +0000611{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000612 PyObject *self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000613
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000614 self = (PyObject *)
615 PyObject_MALLOC(aware ?
616 sizeof(PyDateTime_Time) :
617 sizeof(_PyDateTime_BaseTime));
618 if (self == NULL)
619 return (PyObject *)PyErr_NoMemory();
620 PyObject_INIT(self, type);
621 return self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000622}
623
624static PyObject *
Martin v. Löwis18e16552006-02-15 17:27:45 +0000625datetime_alloc(PyTypeObject *type, Py_ssize_t aware)
Tim Petersb0c854d2003-05-17 15:57:00 +0000626{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000627 PyObject *self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000628
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000629 self = (PyObject *)
630 PyObject_MALLOC(aware ?
631 sizeof(PyDateTime_DateTime) :
632 sizeof(_PyDateTime_BaseDateTime));
633 if (self == NULL)
634 return (PyObject *)PyErr_NoMemory();
635 PyObject_INIT(self, type);
636 return self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000637}
638
639/* ---------------------------------------------------------------------------
640 * Helpers for setting object fields. These work on pointers to the
641 * appropriate base class.
642 */
643
644/* For date and datetime. */
645static void
646set_date_fields(PyDateTime_Date *self, int y, int m, int d)
647{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000648 self->hashcode = -1;
649 SET_YEAR(self, y);
650 SET_MONTH(self, m);
651 SET_DAY(self, d);
Tim Petersb0c854d2003-05-17 15:57:00 +0000652}
653
654/* ---------------------------------------------------------------------------
655 * Create various objects, mostly without range checking.
656 */
657
658/* Create a date instance with no range checking. */
659static PyObject *
660new_date_ex(int year, int month, int day, PyTypeObject *type)
661{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000662 PyDateTime_Date *self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000663
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000664 self = (PyDateTime_Date *) (type->tp_alloc(type, 0));
665 if (self != NULL)
666 set_date_fields(self, year, month, day);
667 return (PyObject *) self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000668}
669
670#define new_date(year, month, day) \
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000671 new_date_ex(year, month, day, &PyDateTime_DateType)
Tim Petersb0c854d2003-05-17 15:57:00 +0000672
673/* Create a datetime instance with no range checking. */
674static PyObject *
675new_datetime_ex(int year, int month, int day, int hour, int minute,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000676 int second, int usecond, PyObject *tzinfo, PyTypeObject *type)
Tim Petersb0c854d2003-05-17 15:57:00 +0000677{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000678 PyDateTime_DateTime *self;
679 char aware = tzinfo != Py_None;
Tim Petersb0c854d2003-05-17 15:57:00 +0000680
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000681 self = (PyDateTime_DateTime *) (type->tp_alloc(type, aware));
682 if (self != NULL) {
683 self->hastzinfo = aware;
684 set_date_fields((PyDateTime_Date *)self, year, month, day);
685 DATE_SET_HOUR(self, hour);
686 DATE_SET_MINUTE(self, minute);
687 DATE_SET_SECOND(self, second);
688 DATE_SET_MICROSECOND(self, usecond);
689 if (aware) {
690 Py_INCREF(tzinfo);
691 self->tzinfo = tzinfo;
692 }
693 }
694 return (PyObject *)self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000695}
696
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000697#define new_datetime(y, m, d, hh, mm, ss, us, tzinfo) \
698 new_datetime_ex(y, m, d, hh, mm, ss, us, tzinfo, \
699 &PyDateTime_DateTimeType)
Tim Petersb0c854d2003-05-17 15:57:00 +0000700
701/* Create a time instance with no range checking. */
702static PyObject *
703new_time_ex(int hour, int minute, int second, int usecond,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000704 PyObject *tzinfo, PyTypeObject *type)
Tim Petersb0c854d2003-05-17 15:57:00 +0000705{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000706 PyDateTime_Time *self;
707 char aware = tzinfo != Py_None;
Tim Petersb0c854d2003-05-17 15:57:00 +0000708
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000709 self = (PyDateTime_Time *) (type->tp_alloc(type, aware));
710 if (self != NULL) {
711 self->hastzinfo = aware;
712 self->hashcode = -1;
713 TIME_SET_HOUR(self, hour);
714 TIME_SET_MINUTE(self, minute);
715 TIME_SET_SECOND(self, second);
716 TIME_SET_MICROSECOND(self, usecond);
717 if (aware) {
718 Py_INCREF(tzinfo);
719 self->tzinfo = tzinfo;
720 }
721 }
722 return (PyObject *)self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000723}
724
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000725#define new_time(hh, mm, ss, us, tzinfo) \
726 new_time_ex(hh, mm, ss, us, tzinfo, &PyDateTime_TimeType)
Tim Petersb0c854d2003-05-17 15:57:00 +0000727
728/* Create a timedelta instance. Normalize the members iff normalize is
729 * true. Passing false is a speed optimization, if you know for sure
730 * that seconds and microseconds are already in their proper ranges. In any
731 * case, raises OverflowError and returns NULL if the normalized days is out
732 * of range).
733 */
734static PyObject *
735new_delta_ex(int days, int seconds, int microseconds, int normalize,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000736 PyTypeObject *type)
Tim Petersb0c854d2003-05-17 15:57:00 +0000737{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000738 PyDateTime_Delta *self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000739
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000740 if (normalize)
741 normalize_d_s_us(&days, &seconds, &microseconds);
742 assert(0 <= seconds && seconds < 24*3600);
743 assert(0 <= microseconds && microseconds < 1000000);
Tim Petersb0c854d2003-05-17 15:57:00 +0000744
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000745 if (check_delta_day_range(days) < 0)
746 return NULL;
Tim Petersb0c854d2003-05-17 15:57:00 +0000747
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000748 self = (PyDateTime_Delta *) (type->tp_alloc(type, 0));
749 if (self != NULL) {
750 self->hashcode = -1;
751 SET_TD_DAYS(self, days);
752 SET_TD_SECONDS(self, seconds);
753 SET_TD_MICROSECONDS(self, microseconds);
754 }
755 return (PyObject *) self;
Tim Petersb0c854d2003-05-17 15:57:00 +0000756}
757
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000758#define new_delta(d, s, us, normalize) \
759 new_delta_ex(d, s, us, normalize, &PyDateTime_DeltaType)
Tim Petersb0c854d2003-05-17 15:57:00 +0000760
Alexander Belopolsky4e749a12010-06-14 14:15:50 +0000761
762typedef struct
763{
764 PyObject_HEAD
765 PyObject *offset;
766 PyObject *name;
767} PyDateTime_TimeZone;
768
Alexander Belopolsky1bcbaab2010-10-14 17:03:51 +0000769/* The interned UTC timezone instance */
770static PyObject *PyDateTime_TimeZone_UTC;
Alexander Belopolskya11d8c02010-07-06 23:19:45 +0000771
Alexander Belopolsky4e749a12010-06-14 14:15:50 +0000772/* Create new timezone instance checking offset range. This
773 function does not check the name argument. Caller must assure
774 that offset is a timedelta instance and name is either NULL
775 or a unicode object. */
776static PyObject *
Alexander Belopolsky1bcbaab2010-10-14 17:03:51 +0000777create_timezone(PyObject *offset, PyObject *name)
Alexander Belopolsky4e749a12010-06-14 14:15:50 +0000778{
779 PyDateTime_TimeZone *self;
780 PyTypeObject *type = &PyDateTime_TimeZoneType;
781
782 assert(offset != NULL);
783 assert(PyDelta_Check(offset));
784 assert(name == NULL || PyUnicode_Check(name));
785
Alexander Belopolsky1bcbaab2010-10-14 17:03:51 +0000786 self = (PyDateTime_TimeZone *)(type->tp_alloc(type, 0));
787 if (self == NULL) {
788 return NULL;
789 }
790 Py_INCREF(offset);
791 self->offset = offset;
792 Py_XINCREF(name);
793 self->name = name;
794 return (PyObject *)self;
795}
796
797static int delta_bool(PyDateTime_Delta *self);
798
799static PyObject *
800new_timezone(PyObject *offset, PyObject *name)
801{
802 assert(offset != NULL);
803 assert(PyDelta_Check(offset));
804 assert(name == NULL || PyUnicode_Check(name));
805
806 if (name == NULL && delta_bool((PyDateTime_Delta *)offset) == 0) {
807 Py_INCREF(PyDateTime_TimeZone_UTC);
808 return PyDateTime_TimeZone_UTC;
809 }
Alexander Belopolsky4e749a12010-06-14 14:15:50 +0000810 if (GET_TD_MICROSECONDS(offset) != 0 || GET_TD_SECONDS(offset) % 60 != 0) {
811 PyErr_Format(PyExc_ValueError, "offset must be a timedelta"
812 " representing a whole number of minutes");
813 return NULL;
814 }
815 if ((GET_TD_DAYS(offset) == -1 && GET_TD_SECONDS(offset) == 0) ||
816 GET_TD_DAYS(offset) < -1 || GET_TD_DAYS(offset) >= 1) {
817 PyErr_Format(PyExc_ValueError, "offset must be a timedelta"
818 " strictly between -timedelta(hours=24) and"
819 " timedelta(hours=24).");
820 return NULL;
821 }
822
Alexander Belopolsky1bcbaab2010-10-14 17:03:51 +0000823 return create_timezone(offset, name);
Alexander Belopolsky4e749a12010-06-14 14:15:50 +0000824}
825
Tim Petersb0c854d2003-05-17 15:57:00 +0000826/* ---------------------------------------------------------------------------
Tim Peters2a799bf2002-12-16 20:18:38 +0000827 * tzinfo helpers.
828 */
829
Tim Peters855fe882002-12-22 03:43:39 +0000830/* Ensure that p is None or of a tzinfo subclass. Return 0 if OK; if not
831 * raise TypeError and return -1.
832 */
833static int
834check_tzinfo_subclass(PyObject *p)
835{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000836 if (p == Py_None || PyTZInfo_Check(p))
837 return 0;
838 PyErr_Format(PyExc_TypeError,
839 "tzinfo argument must be None or of a tzinfo subclass, "
840 "not type '%s'",
841 Py_TYPE(p)->tp_name);
842 return -1;
Tim Peters855fe882002-12-22 03:43:39 +0000843}
844
Tim Peters2a799bf2002-12-16 20:18:38 +0000845/* If self has a tzinfo member, return a BORROWED reference to it. Else
846 * return NULL, which is NOT AN ERROR. There are no error returns here,
847 * and the caller must not decref the result.
848 */
849static PyObject *
850get_tzinfo_member(PyObject *self)
851{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000852 PyObject *tzinfo = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +0000853
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000854 if (PyDateTime_Check(self) && HASTZINFO(self))
855 tzinfo = ((PyDateTime_DateTime *)self)->tzinfo;
856 else if (PyTime_Check(self) && HASTZINFO(self))
857 tzinfo = ((PyDateTime_Time *)self)->tzinfo;
Tim Peters2a799bf2002-12-16 20:18:38 +0000858
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000859 return tzinfo;
Tim Peters2a799bf2002-12-16 20:18:38 +0000860}
861
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000862/* Call getattr(tzinfo, name)(tzinfoarg), and check the result. tzinfo must
863 * be an instance of the tzinfo class. If the method returns None, this
864 * returns None. If the method doesn't return None or timedelta, TypeError is
865 * raised and this returns NULL. If it returns a timedelta and the value is
866 * out of range or isn't a whole number of minutes, ValueError is raised and
867 * this returns NULL. Else result is returned.
Tim Peters2a799bf2002-12-16 20:18:38 +0000868 */
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000869static PyObject *
870call_tzinfo_method(PyObject *tzinfo, char *name, PyObject *tzinfoarg)
Tim Peters2a799bf2002-12-16 20:18:38 +0000871{
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000872 PyObject *offset;
Tim Peters2a799bf2002-12-16 20:18:38 +0000873
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000874 assert(tzinfo != NULL);
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000875 assert(PyTZInfo_Check(tzinfo) || tzinfo == Py_None);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000876 assert(tzinfoarg != NULL);
Tim Peters2a799bf2002-12-16 20:18:38 +0000877
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000878 if (tzinfo == Py_None)
879 Py_RETURN_NONE;
880 offset = PyObject_CallMethod(tzinfo, name, "O", tzinfoarg);
881 if (offset == Py_None || offset == NULL)
882 return offset;
883 if (PyDelta_Check(offset)) {
884 if (GET_TD_MICROSECONDS(offset) != 0 || GET_TD_SECONDS(offset) % 60 != 0) {
885 Py_DECREF(offset);
886 PyErr_Format(PyExc_ValueError, "offset must be a timedelta"
887 " representing a whole number of minutes");
888 return NULL;
889 }
890 if ((GET_TD_DAYS(offset) == -1 && GET_TD_SECONDS(offset) == 0) ||
891 GET_TD_DAYS(offset) < -1 || GET_TD_DAYS(offset) >= 1) {
892 Py_DECREF(offset);
893 PyErr_Format(PyExc_ValueError, "offset must be a timedelta"
894 " strictly between -timedelta(hours=24) and"
895 " timedelta(hours=24).");
896 return NULL;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000897 }
898 }
899 else {
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000900 Py_DECREF(offset);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000901 PyErr_Format(PyExc_TypeError,
902 "tzinfo.%s() must return None or "
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000903 "timedelta, not '%.200s'",
904 name, Py_TYPE(offset)->tp_name);
905 return NULL;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000906 }
Tim Peters2a799bf2002-12-16 20:18:38 +0000907
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000908 return offset;
Tim Peters2a799bf2002-12-16 20:18:38 +0000909}
910
911/* Call tzinfo.utcoffset(tzinfoarg), and extract an integer from the
912 * result. tzinfo must be an instance of the tzinfo class. If utcoffset()
913 * returns None, call_utcoffset returns 0 and sets *none to 1. If uctoffset()
Tim Peters397301e2003-01-02 21:28:08 +0000914 * doesn't return None or timedelta, TypeError is raised and this returns -1.
915 * If utcoffset() returns an invalid timedelta (out of range, or not a whole
916 * # of minutes), ValueError is raised and this returns -1. Else *none is
917 * set to 0 and the offset is returned (as int # of minutes east of UTC).
Tim Peters2a799bf2002-12-16 20:18:38 +0000918 */
Tim Peters855fe882002-12-22 03:43:39 +0000919static PyObject *
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000920call_utcoffset(PyObject *tzinfo, PyObject *tzinfoarg)
921{
922 return call_tzinfo_method(tzinfo, "utcoffset", tzinfoarg);
Tim Peters855fe882002-12-22 03:43:39 +0000923}
924
Tim Peters2a799bf2002-12-16 20:18:38 +0000925/* Call tzinfo.dst(tzinfoarg), and extract an integer from the
926 * result. tzinfo must be an instance of the tzinfo class. If dst()
927 * returns None, call_dst returns 0 and sets *none to 1. If dst()
Tim Peters397301e2003-01-02 21:28:08 +0000928 & doesn't return None or timedelta, TypeError is raised and this
Walter Dörwaldf0dfc7a2003-10-20 14:01:56 +0000929 * returns -1. If dst() returns an invalid timedelta for a UTC offset,
Tim Peters397301e2003-01-02 21:28:08 +0000930 * ValueError is raised and this returns -1. Else *none is set to 0 and
931 * the offset is returned (as an int # of minutes east of UTC).
Tim Peters2a799bf2002-12-16 20:18:38 +0000932 */
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000933static PyObject *
934call_dst(PyObject *tzinfo, PyObject *tzinfoarg)
Tim Peters2a799bf2002-12-16 20:18:38 +0000935{
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000936 return call_tzinfo_method(tzinfo, "dst", tzinfoarg);
Tim Peters2a799bf2002-12-16 20:18:38 +0000937}
938
Tim Petersbad8ff02002-12-30 20:52:32 +0000939/* Call tzinfo.tzname(tzinfoarg), and return the result. tzinfo must be
Tim Peters855fe882002-12-22 03:43:39 +0000940 * an instance of the tzinfo class or None. If tzinfo isn't None, and
Tim Petersbad8ff02002-12-30 20:52:32 +0000941 * tzname() doesn't return None or a string, TypeError is raised and this
Guido van Rossume3d1d412007-05-23 21:24:35 +0000942 * returns NULL. If the result is a string, we ensure it is a Unicode
943 * string.
Tim Peters2a799bf2002-12-16 20:18:38 +0000944 */
945static PyObject *
Tim Petersbad8ff02002-12-30 20:52:32 +0000946call_tzname(PyObject *tzinfo, PyObject *tzinfoarg)
Tim Peters2a799bf2002-12-16 20:18:38 +0000947{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000948 PyObject *result;
Tim Peters2a799bf2002-12-16 20:18:38 +0000949
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000950 assert(tzinfo != NULL);
951 assert(check_tzinfo_subclass(tzinfo) >= 0);
952 assert(tzinfoarg != NULL);
Tim Peters2a799bf2002-12-16 20:18:38 +0000953
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000954 if (tzinfo == Py_None)
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000955 Py_RETURN_NONE;
Tim Peters2a799bf2002-12-16 20:18:38 +0000956
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000957 result = PyObject_CallMethod(tzinfo, "tzname", "O", tzinfoarg);
958
959 if (result == NULL || result == Py_None)
960 return result;
961
962 if (!PyUnicode_Check(result)) {
963 PyErr_Format(PyExc_TypeError, "tzinfo.tzname() must "
964 "return None or a string, not '%s'",
965 Py_TYPE(result)->tp_name);
966 Py_DECREF(result);
967 result = NULL;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000968 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +0000969
970 return result;
Tim Peters00237032002-12-27 02:21:51 +0000971}
972
Tim Peters2a799bf2002-12-16 20:18:38 +0000973/* repr is like "someclass(arg1, arg2)". If tzinfo isn't None,
974 * stuff
975 * ", tzinfo=" + repr(tzinfo)
976 * before the closing ")".
977 */
978static PyObject *
979append_keyword_tzinfo(PyObject *repr, PyObject *tzinfo)
980{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000981 PyObject *temp;
Tim Peters2a799bf2002-12-16 20:18:38 +0000982
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000983 assert(PyUnicode_Check(repr));
984 assert(tzinfo);
985 if (tzinfo == Py_None)
986 return repr;
987 /* Get rid of the trailing ')'. */
988 assert(PyUnicode_AS_UNICODE(repr)[PyUnicode_GET_SIZE(repr)-1] == ')');
989 temp = PyUnicode_FromUnicode(PyUnicode_AS_UNICODE(repr),
990 PyUnicode_GET_SIZE(repr) - 1);
991 Py_DECREF(repr);
992 if (temp == NULL)
993 return NULL;
994 repr = PyUnicode_FromFormat("%U, tzinfo=%R)", temp, tzinfo);
995 Py_DECREF(temp);
996 return repr;
Tim Peters2a799bf2002-12-16 20:18:38 +0000997}
998
999/* ---------------------------------------------------------------------------
1000 * String format helpers.
1001 */
1002
1003static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00001004format_ctime(PyDateTime_Date *date, int hours, int minutes, int seconds)
Tim Peters2a799bf2002-12-16 20:18:38 +00001005{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001006 static const char *DayNames[] = {
1007 "Mon", "Tue", "Wed", "Thu", "Fri", "Sat", "Sun"
1008 };
1009 static const char *MonthNames[] = {
1010 "Jan", "Feb", "Mar", "Apr", "May", "Jun",
1011 "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"
1012 };
Tim Peters2a799bf2002-12-16 20:18:38 +00001013
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001014 int wday = weekday(GET_YEAR(date), GET_MONTH(date), GET_DAY(date));
Tim Peters2a799bf2002-12-16 20:18:38 +00001015
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001016 return PyUnicode_FromFormat("%s %s %2d %02d:%02d:%02d %04d",
1017 DayNames[wday], MonthNames[GET_MONTH(date)-1],
1018 GET_DAY(date), hours, minutes, seconds,
1019 GET_YEAR(date));
Tim Peters2a799bf2002-12-16 20:18:38 +00001020}
1021
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001022static PyObject *delta_negative(PyDateTime_Delta *self);
1023
Tim Peters2a799bf2002-12-16 20:18:38 +00001024/* Add an hours & minutes UTC offset string to buf. buf has no more than
1025 * buflen bytes remaining. The UTC offset is gotten by calling
1026 * tzinfo.uctoffset(tzinfoarg). If that returns None, \0 is stored into
1027 * *buf, and that's all. Else the returned value is checked for sanity (an
1028 * integer in range), and if that's OK it's converted to an hours & minutes
1029 * string of the form
1030 * sign HH sep MM
1031 * Returns 0 if everything is OK. If the return value from utcoffset() is
1032 * bogus, an appropriate exception is set and -1 is returned.
1033 */
1034static int
Tim Peters328fff72002-12-20 01:31:27 +00001035format_utcoffset(char *buf, size_t buflen, const char *sep,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001036 PyObject *tzinfo, PyObject *tzinfoarg)
Tim Peters2a799bf2002-12-16 20:18:38 +00001037{
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001038 PyObject *offset;
1039 int hours, minutes, seconds;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001040 char sign;
Tim Peters2a799bf2002-12-16 20:18:38 +00001041
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001042 assert(buflen >= 1);
Amaury Forgeot d'Arc9c74b142008-06-18 00:47:36 +00001043
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001044 offset = call_utcoffset(tzinfo, tzinfoarg);
1045 if (offset == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001046 return -1;
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001047 if (offset == Py_None) {
1048 Py_DECREF(offset);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001049 *buf = '\0';
1050 return 0;
1051 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001052 /* Offset is normalized, so it is negative if days < 0 */
1053 if (GET_TD_DAYS(offset) < 0) {
1054 PyObject *temp = offset;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001055 sign = '-';
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001056 offset = delta_negative((PyDateTime_Delta *)offset);
1057 Py_DECREF(temp);
1058 if (offset == NULL)
1059 return -1;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001060 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001061 else {
1062 sign = '+';
1063 }
1064 /* Offset is not negative here. */
1065 seconds = GET_TD_SECONDS(offset);
1066 Py_DECREF(offset);
1067 minutes = divmod(seconds, 60, &seconds);
1068 hours = divmod(minutes, 60, &minutes);
1069 assert(seconds == 0);
1070 /* XXX ignore sub-minute data, curently not allowed. */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001071 PyOS_snprintf(buf, buflen, "%c%02d%s%02d", sign, hours, sep, minutes);
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001072
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001073 return 0;
Tim Peters2a799bf2002-12-16 20:18:38 +00001074}
1075
Guido van Rossumd8595fe2007-05-23 21:36:49 +00001076static PyObject *
1077make_Zreplacement(PyObject *object, PyObject *tzinfoarg)
1078{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001079 PyObject *temp;
1080 PyObject *tzinfo = get_tzinfo_member(object);
1081 PyObject *Zreplacement = PyUnicode_FromStringAndSize(NULL, 0);
1082 if (Zreplacement == NULL)
1083 return NULL;
1084 if (tzinfo == Py_None || tzinfo == NULL)
1085 return Zreplacement;
Neal Norwitzaea70e02007-08-12 04:32:26 +00001086
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001087 assert(tzinfoarg != NULL);
1088 temp = call_tzname(tzinfo, tzinfoarg);
1089 if (temp == NULL)
1090 goto Error;
1091 if (temp == Py_None) {
1092 Py_DECREF(temp);
1093 return Zreplacement;
1094 }
Neal Norwitzaea70e02007-08-12 04:32:26 +00001095
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001096 assert(PyUnicode_Check(temp));
1097 /* Since the tzname is getting stuffed into the
1098 * format, we have to double any % signs so that
1099 * strftime doesn't treat them as format codes.
1100 */
1101 Py_DECREF(Zreplacement);
1102 Zreplacement = PyObject_CallMethod(temp, "replace", "ss", "%", "%%");
1103 Py_DECREF(temp);
1104 if (Zreplacement == NULL)
1105 return NULL;
1106 if (!PyUnicode_Check(Zreplacement)) {
1107 PyErr_SetString(PyExc_TypeError,
1108 "tzname.replace() did not return a string");
1109 goto Error;
1110 }
1111 return Zreplacement;
Guido van Rossumd8595fe2007-05-23 21:36:49 +00001112
1113 Error:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001114 Py_DECREF(Zreplacement);
1115 return NULL;
Guido van Rossumd8595fe2007-05-23 21:36:49 +00001116}
1117
Christian Heimesdd15f6c2008-03-16 00:07:10 +00001118static PyObject *
1119make_freplacement(PyObject *object)
1120{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001121 char freplacement[64];
1122 if (PyTime_Check(object))
1123 sprintf(freplacement, "%06d", TIME_GET_MICROSECOND(object));
1124 else if (PyDateTime_Check(object))
1125 sprintf(freplacement, "%06d", DATE_GET_MICROSECOND(object));
1126 else
1127 sprintf(freplacement, "%06d", 0);
Christian Heimesdd15f6c2008-03-16 00:07:10 +00001128
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001129 return PyBytes_FromStringAndSize(freplacement, strlen(freplacement));
Christian Heimesdd15f6c2008-03-16 00:07:10 +00001130}
1131
Tim Peters2a799bf2002-12-16 20:18:38 +00001132/* I sure don't want to reproduce the strftime code from the time module,
1133 * so this imports the module and calls it. All the hair is due to
Christian Heimesdd15f6c2008-03-16 00:07:10 +00001134 * giving special meanings to the %z, %Z and %f format codes via a
1135 * preprocessing step on the format string.
Tim Petersbad8ff02002-12-30 20:52:32 +00001136 * tzinfoarg is the argument to pass to the object's tzinfo method, if
1137 * needed.
Tim Peters2a799bf2002-12-16 20:18:38 +00001138 */
1139static PyObject *
Tim Petersbad8ff02002-12-30 20:52:32 +00001140wrap_strftime(PyObject *object, PyObject *format, PyObject *timetuple,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001141 PyObject *tzinfoarg)
Tim Peters2a799bf2002-12-16 20:18:38 +00001142{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001143 PyObject *result = NULL; /* guilty until proved innocent */
Tim Peters2a799bf2002-12-16 20:18:38 +00001144
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001145 PyObject *zreplacement = NULL; /* py string, replacement for %z */
1146 PyObject *Zreplacement = NULL; /* py string, replacement for %Z */
1147 PyObject *freplacement = NULL; /* py string, replacement for %f */
Tim Peters2a799bf2002-12-16 20:18:38 +00001148
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001149 const char *pin; /* pointer to next char in input format */
1150 Py_ssize_t flen; /* length of input format */
1151 char ch; /* next char in input format */
Tim Peters2a799bf2002-12-16 20:18:38 +00001152
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001153 PyObject *newfmt = NULL; /* py string, the output format */
1154 char *pnew; /* pointer to available byte in output format */
1155 size_t totalnew; /* number bytes total in output format buffer,
1156 exclusive of trailing \0 */
1157 size_t usednew; /* number bytes used so far in output format buffer */
Tim Peters2a799bf2002-12-16 20:18:38 +00001158
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001159 const char *ptoappend; /* ptr to string to append to output buffer */
1160 Py_ssize_t ntoappend; /* # of bytes to append to output buffer */
Tim Peters2a799bf2002-12-16 20:18:38 +00001161
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001162 assert(object && format && timetuple);
1163 assert(PyUnicode_Check(format));
1164 /* Convert the input format to a C string and size */
1165 pin = _PyUnicode_AsStringAndSize(format, &flen);
1166 if (!pin)
1167 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001168
Alexander Belopolskyb8bb4662011-01-08 00:13:34 +00001169 /* Give up if the year is before 1000.
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001170 * Python strftime() plays games with the year, and different
1171 * games depending on whether envar PYTHON2K is set. This makes
Alexander Belopolskyb8bb4662011-01-08 00:13:34 +00001172 * years before 1000 a nightmare, even if the platform strftime
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001173 * supports them (and not all do).
1174 * We could get a lot farther here by avoiding Python's strftime
1175 * wrapper and calling the C strftime() directly, but that isn't
1176 * an option in the Python implementation of this module.
1177 */
1178 {
1179 long year;
1180 PyObject *pyyear = PySequence_GetItem(timetuple, 0);
1181 if (pyyear == NULL) return NULL;
1182 assert(PyLong_Check(pyyear));
1183 year = PyLong_AsLong(pyyear);
1184 Py_DECREF(pyyear);
Alexander Belopolskyb8bb4662011-01-08 00:13:34 +00001185 if (year < 1000) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001186 PyErr_Format(PyExc_ValueError, "year=%ld is before "
Alexander Belopolskyb8bb4662011-01-08 00:13:34 +00001187 "1000; the datetime strftime() "
1188 "methods require year >= 1000",
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001189 year);
1190 return NULL;
1191 }
1192 }
Tim Petersd6844152002-12-22 20:58:42 +00001193
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001194 /* Scan the input format, looking for %z/%Z/%f escapes, building
1195 * a new format. Since computing the replacements for those codes
1196 * is expensive, don't unless they're actually used.
1197 */
1198 if (flen > INT_MAX - 1) {
1199 PyErr_NoMemory();
1200 goto Done;
1201 }
Amaury Forgeot d'Arc9c74b142008-06-18 00:47:36 +00001202
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001203 totalnew = flen + 1; /* realistic if no %z/%Z */
1204 newfmt = PyBytes_FromStringAndSize(NULL, totalnew);
1205 if (newfmt == NULL) goto Done;
1206 pnew = PyBytes_AsString(newfmt);
1207 usednew = 0;
Tim Peters2a799bf2002-12-16 20:18:38 +00001208
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001209 while ((ch = *pin++) != '\0') {
1210 if (ch != '%') {
1211 ptoappend = pin - 1;
1212 ntoappend = 1;
1213 }
1214 else if ((ch = *pin++) == '\0') {
1215 /* There's a lone trailing %; doesn't make sense. */
1216 PyErr_SetString(PyExc_ValueError, "strftime format "
1217 "ends with raw %");
1218 goto Done;
1219 }
1220 /* A % has been seen and ch is the character after it. */
1221 else if (ch == 'z') {
1222 if (zreplacement == NULL) {
1223 /* format utcoffset */
1224 char buf[100];
1225 PyObject *tzinfo = get_tzinfo_member(object);
1226 zreplacement = PyBytes_FromStringAndSize("", 0);
1227 if (zreplacement == NULL) goto Done;
1228 if (tzinfo != Py_None && tzinfo != NULL) {
1229 assert(tzinfoarg != NULL);
1230 if (format_utcoffset(buf,
1231 sizeof(buf),
1232 "",
1233 tzinfo,
1234 tzinfoarg) < 0)
1235 goto Done;
1236 Py_DECREF(zreplacement);
1237 zreplacement =
1238 PyBytes_FromStringAndSize(buf,
1239 strlen(buf));
1240 if (zreplacement == NULL)
1241 goto Done;
1242 }
1243 }
1244 assert(zreplacement != NULL);
1245 ptoappend = PyBytes_AS_STRING(zreplacement);
1246 ntoappend = PyBytes_GET_SIZE(zreplacement);
1247 }
1248 else if (ch == 'Z') {
1249 /* format tzname */
1250 if (Zreplacement == NULL) {
1251 Zreplacement = make_Zreplacement(object,
1252 tzinfoarg);
1253 if (Zreplacement == NULL)
1254 goto Done;
1255 }
1256 assert(Zreplacement != NULL);
1257 assert(PyUnicode_Check(Zreplacement));
1258 ptoappend = _PyUnicode_AsStringAndSize(Zreplacement,
1259 &ntoappend);
Alexander Belopolskye239d232010-12-08 23:31:48 +00001260 if (ptoappend == NULL)
1261 goto Done;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001262 }
1263 else if (ch == 'f') {
1264 /* format microseconds */
1265 if (freplacement == NULL) {
1266 freplacement = make_freplacement(object);
1267 if (freplacement == NULL)
1268 goto Done;
1269 }
1270 assert(freplacement != NULL);
1271 assert(PyBytes_Check(freplacement));
1272 ptoappend = PyBytes_AS_STRING(freplacement);
1273 ntoappend = PyBytes_GET_SIZE(freplacement);
1274 }
1275 else {
1276 /* percent followed by neither z nor Z */
1277 ptoappend = pin - 2;
1278 ntoappend = 2;
1279 }
Tim Peters2a799bf2002-12-16 20:18:38 +00001280
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001281 /* Append the ntoappend chars starting at ptoappend to
1282 * the new format.
1283 */
1284 if (ntoappend == 0)
1285 continue;
1286 assert(ptoappend != NULL);
1287 assert(ntoappend > 0);
1288 while (usednew + ntoappend > totalnew) {
1289 size_t bigger = totalnew << 1;
1290 if ((bigger >> 1) != totalnew) { /* overflow */
1291 PyErr_NoMemory();
1292 goto Done;
1293 }
1294 if (_PyBytes_Resize(&newfmt, bigger) < 0)
1295 goto Done;
1296 totalnew = bigger;
1297 pnew = PyBytes_AsString(newfmt) + usednew;
1298 }
1299 memcpy(pnew, ptoappend, ntoappend);
1300 pnew += ntoappend;
1301 usednew += ntoappend;
1302 assert(usednew <= totalnew);
1303 } /* end while() */
Tim Peters2a799bf2002-12-16 20:18:38 +00001304
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001305 if (_PyBytes_Resize(&newfmt, usednew) < 0)
1306 goto Done;
1307 {
1308 PyObject *format;
1309 PyObject *time = PyImport_ImportModuleNoBlock("time");
1310 if (time == NULL)
1311 goto Done;
1312 format = PyUnicode_FromString(PyBytes_AS_STRING(newfmt));
1313 if (format != NULL) {
1314 result = PyObject_CallMethod(time, "strftime", "OO",
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001315 format, timetuple, NULL);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001316 Py_DECREF(format);
1317 }
1318 Py_DECREF(time);
1319 }
Tim Peters2a799bf2002-12-16 20:18:38 +00001320 Done:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001321 Py_XDECREF(freplacement);
1322 Py_XDECREF(zreplacement);
1323 Py_XDECREF(Zreplacement);
1324 Py_XDECREF(newfmt);
1325 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001326}
1327
Tim Peters2a799bf2002-12-16 20:18:38 +00001328/* ---------------------------------------------------------------------------
1329 * Wrap functions from the time module. These aren't directly available
1330 * from C. Perhaps they should be.
1331 */
1332
1333/* Call time.time() and return its result (a Python float). */
1334static PyObject *
Guido van Rossumbd43e912002-12-16 20:34:55 +00001335time_time(void)
Tim Peters2a799bf2002-12-16 20:18:38 +00001336{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001337 PyObject *result = NULL;
1338 PyObject *time = PyImport_ImportModuleNoBlock("time");
Tim Peters2a799bf2002-12-16 20:18:38 +00001339
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001340 if (time != NULL) {
1341 result = PyObject_CallMethod(time, "time", "()");
1342 Py_DECREF(time);
1343 }
1344 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001345}
1346
1347/* Build a time.struct_time. The weekday and day number are automatically
1348 * computed from the y,m,d args.
1349 */
1350static PyObject *
1351build_struct_time(int y, int m, int d, int hh, int mm, int ss, int dstflag)
1352{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001353 PyObject *time;
1354 PyObject *result = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001355
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001356 time = PyImport_ImportModuleNoBlock("time");
1357 if (time != NULL) {
1358 result = PyObject_CallMethod(time, "struct_time",
1359 "((iiiiiiiii))",
1360 y, m, d,
1361 hh, mm, ss,
1362 weekday(y, m, d),
1363 days_before_month(y, m) + d,
1364 dstflag);
1365 Py_DECREF(time);
1366 }
1367 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001368}
1369
1370/* ---------------------------------------------------------------------------
1371 * Miscellaneous helpers.
1372 */
1373
Mark Dickinsone94c6792009-02-02 20:36:42 +00001374/* For various reasons, we need to use tp_richcompare instead of tp_reserved.
Tim Peters2a799bf2002-12-16 20:18:38 +00001375 * The comparisons here all most naturally compute a cmp()-like result.
1376 * This little helper turns that into a bool result for rich comparisons.
1377 */
1378static PyObject *
1379diff_to_bool(int diff, int op)
1380{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001381 PyObject *result;
1382 int istrue;
Tim Peters2a799bf2002-12-16 20:18:38 +00001383
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001384 switch (op) {
1385 case Py_EQ: istrue = diff == 0; break;
1386 case Py_NE: istrue = diff != 0; break;
1387 case Py_LE: istrue = diff <= 0; break;
1388 case Py_GE: istrue = diff >= 0; break;
1389 case Py_LT: istrue = diff < 0; break;
1390 case Py_GT: istrue = diff > 0; break;
1391 default:
1392 assert(! "op unknown");
1393 istrue = 0; /* To shut up compiler */
1394 }
1395 result = istrue ? Py_True : Py_False;
1396 Py_INCREF(result);
1397 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001398}
1399
Tim Peters07534a62003-02-07 22:50:28 +00001400/* Raises a "can't compare" TypeError and returns NULL. */
1401static PyObject *
1402cmperror(PyObject *a, PyObject *b)
1403{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001404 PyErr_Format(PyExc_TypeError,
1405 "can't compare %s to %s",
1406 Py_TYPE(a)->tp_name, Py_TYPE(b)->tp_name);
1407 return NULL;
Tim Peters07534a62003-02-07 22:50:28 +00001408}
1409
Tim Peters2a799bf2002-12-16 20:18:38 +00001410/* ---------------------------------------------------------------------------
Tim Peters2a799bf2002-12-16 20:18:38 +00001411 * Cached Python objects; these are set by the module init function.
1412 */
1413
1414/* Conversion factors. */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001415static PyObject *us_per_us = NULL; /* 1 */
1416static PyObject *us_per_ms = NULL; /* 1000 */
1417static PyObject *us_per_second = NULL; /* 1000000 */
1418static PyObject *us_per_minute = NULL; /* 1e6 * 60 as Python int */
1419static PyObject *us_per_hour = NULL; /* 1e6 * 3600 as Python long */
1420static PyObject *us_per_day = NULL; /* 1e6 * 3600 * 24 as Python long */
1421static PyObject *us_per_week = NULL; /* 1e6*3600*24*7 as Python long */
Tim Peters2a799bf2002-12-16 20:18:38 +00001422static PyObject *seconds_per_day = NULL; /* 3600*24 as Python int */
1423
Tim Peters2a799bf2002-12-16 20:18:38 +00001424/* ---------------------------------------------------------------------------
1425 * Class implementations.
1426 */
1427
1428/*
1429 * PyDateTime_Delta implementation.
1430 */
1431
1432/* Convert a timedelta to a number of us,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001433 * (24*3600*self.days + self.seconds)*1000000 + self.microseconds
Tim Peters2a799bf2002-12-16 20:18:38 +00001434 * as a Python int or long.
1435 * Doing mixed-radix arithmetic by hand instead is excruciating in C,
1436 * due to ubiquitous overflow possibilities.
1437 */
1438static PyObject *
1439delta_to_microseconds(PyDateTime_Delta *self)
1440{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001441 PyObject *x1 = NULL;
1442 PyObject *x2 = NULL;
1443 PyObject *x3 = NULL;
1444 PyObject *result = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001445
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001446 x1 = PyLong_FromLong(GET_TD_DAYS(self));
1447 if (x1 == NULL)
1448 goto Done;
1449 x2 = PyNumber_Multiply(x1, seconds_per_day); /* days in seconds */
1450 if (x2 == NULL)
1451 goto Done;
1452 Py_DECREF(x1);
1453 x1 = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001454
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001455 /* x2 has days in seconds */
1456 x1 = PyLong_FromLong(GET_TD_SECONDS(self)); /* seconds */
1457 if (x1 == NULL)
1458 goto Done;
1459 x3 = PyNumber_Add(x1, x2); /* days and seconds in seconds */
1460 if (x3 == NULL)
1461 goto Done;
1462 Py_DECREF(x1);
1463 Py_DECREF(x2);
1464 x1 = x2 = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001465
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001466 /* x3 has days+seconds in seconds */
1467 x1 = PyNumber_Multiply(x3, us_per_second); /* us */
1468 if (x1 == NULL)
1469 goto Done;
1470 Py_DECREF(x3);
1471 x3 = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001472
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001473 /* x1 has days+seconds in us */
1474 x2 = PyLong_FromLong(GET_TD_MICROSECONDS(self));
1475 if (x2 == NULL)
1476 goto Done;
1477 result = PyNumber_Add(x1, x2);
Tim Peters2a799bf2002-12-16 20:18:38 +00001478
1479Done:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001480 Py_XDECREF(x1);
1481 Py_XDECREF(x2);
1482 Py_XDECREF(x3);
1483 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001484}
1485
1486/* Convert a number of us (as a Python int or long) to a timedelta.
1487 */
1488static PyObject *
Tim Petersb0c854d2003-05-17 15:57:00 +00001489microseconds_to_delta_ex(PyObject *pyus, PyTypeObject *type)
Tim Peters2a799bf2002-12-16 20:18:38 +00001490{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001491 int us;
1492 int s;
1493 int d;
1494 long temp;
Tim Peters2a799bf2002-12-16 20:18:38 +00001495
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001496 PyObject *tuple = NULL;
1497 PyObject *num = NULL;
1498 PyObject *result = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001499
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001500 tuple = PyNumber_Divmod(pyus, us_per_second);
1501 if (tuple == NULL)
1502 goto Done;
Tim Peters2a799bf2002-12-16 20:18:38 +00001503
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001504 num = PyTuple_GetItem(tuple, 1); /* us */
1505 if (num == NULL)
1506 goto Done;
1507 temp = PyLong_AsLong(num);
1508 num = NULL;
1509 if (temp == -1 && PyErr_Occurred())
1510 goto Done;
1511 assert(0 <= temp && temp < 1000000);
1512 us = (int)temp;
1513 if (us < 0) {
1514 /* The divisor was positive, so this must be an error. */
1515 assert(PyErr_Occurred());
1516 goto Done;
1517 }
Tim Peters2a799bf2002-12-16 20:18:38 +00001518
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001519 num = PyTuple_GetItem(tuple, 0); /* leftover seconds */
1520 if (num == NULL)
1521 goto Done;
1522 Py_INCREF(num);
1523 Py_DECREF(tuple);
Tim Peters2a799bf2002-12-16 20:18:38 +00001524
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001525 tuple = PyNumber_Divmod(num, seconds_per_day);
1526 if (tuple == NULL)
1527 goto Done;
1528 Py_DECREF(num);
Tim Peters2a799bf2002-12-16 20:18:38 +00001529
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001530 num = PyTuple_GetItem(tuple, 1); /* seconds */
1531 if (num == NULL)
1532 goto Done;
1533 temp = PyLong_AsLong(num);
1534 num = NULL;
1535 if (temp == -1 && PyErr_Occurred())
1536 goto Done;
1537 assert(0 <= temp && temp < 24*3600);
1538 s = (int)temp;
Tim Peters0b0f41c2002-12-19 01:44:38 +00001539
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001540 if (s < 0) {
1541 /* The divisor was positive, so this must be an error. */
1542 assert(PyErr_Occurred());
1543 goto Done;
1544 }
Tim Peters2a799bf2002-12-16 20:18:38 +00001545
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001546 num = PyTuple_GetItem(tuple, 0); /* leftover days */
1547 if (num == NULL)
1548 goto Done;
1549 Py_INCREF(num);
1550 temp = PyLong_AsLong(num);
1551 if (temp == -1 && PyErr_Occurred())
1552 goto Done;
1553 d = (int)temp;
1554 if ((long)d != temp) {
1555 PyErr_SetString(PyExc_OverflowError, "normalized days too "
1556 "large to fit in a C int");
1557 goto Done;
1558 }
1559 result = new_delta_ex(d, s, us, 0, type);
Tim Peters2a799bf2002-12-16 20:18:38 +00001560
1561Done:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001562 Py_XDECREF(tuple);
1563 Py_XDECREF(num);
1564 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001565}
1566
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001567#define microseconds_to_delta(pymicros) \
1568 microseconds_to_delta_ex(pymicros, &PyDateTime_DeltaType)
Tim Petersb0c854d2003-05-17 15:57:00 +00001569
Tim Peters2a799bf2002-12-16 20:18:38 +00001570static PyObject *
1571multiply_int_timedelta(PyObject *intobj, PyDateTime_Delta *delta)
1572{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001573 PyObject *pyus_in;
1574 PyObject *pyus_out;
1575 PyObject *result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001576
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001577 pyus_in = delta_to_microseconds(delta);
1578 if (pyus_in == NULL)
1579 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001580
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001581 pyus_out = PyNumber_Multiply(pyus_in, intobj);
1582 Py_DECREF(pyus_in);
1583 if (pyus_out == NULL)
1584 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001585
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001586 result = microseconds_to_delta(pyus_out);
1587 Py_DECREF(pyus_out);
1588 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001589}
1590
1591static PyObject *
Alexander Belopolsky1790bc42010-05-31 17:33:47 +00001592multiply_float_timedelta(PyObject *floatobj, PyDateTime_Delta *delta)
1593{
1594 PyObject *result = NULL;
1595 PyObject *pyus_in = NULL, *temp, *pyus_out;
1596 PyObject *ratio = NULL;
1597
1598 pyus_in = delta_to_microseconds(delta);
1599 if (pyus_in == NULL)
1600 return NULL;
1601 ratio = PyObject_CallMethod(floatobj, "as_integer_ratio", NULL);
1602 if (ratio == NULL)
1603 goto error;
1604 temp = PyNumber_Multiply(pyus_in, PyTuple_GET_ITEM(ratio, 0));
1605 Py_DECREF(pyus_in);
1606 pyus_in = NULL;
1607 if (temp == NULL)
1608 goto error;
1609 pyus_out = divide_nearest(temp, PyTuple_GET_ITEM(ratio, 1));
1610 Py_DECREF(temp);
1611 if (pyus_out == NULL)
1612 goto error;
1613 result = microseconds_to_delta(pyus_out);
1614 Py_DECREF(pyus_out);
1615 error:
1616 Py_XDECREF(pyus_in);
1617 Py_XDECREF(ratio);
1618
1619 return result;
1620}
1621
1622static PyObject *
Tim Peters2a799bf2002-12-16 20:18:38 +00001623divide_timedelta_int(PyDateTime_Delta *delta, PyObject *intobj)
1624{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001625 PyObject *pyus_in;
1626 PyObject *pyus_out;
1627 PyObject *result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001628
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001629 pyus_in = delta_to_microseconds(delta);
1630 if (pyus_in == NULL)
1631 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001632
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001633 pyus_out = PyNumber_FloorDivide(pyus_in, intobj);
1634 Py_DECREF(pyus_in);
1635 if (pyus_out == NULL)
1636 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00001637
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001638 result = microseconds_to_delta(pyus_out);
1639 Py_DECREF(pyus_out);
1640 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001641}
1642
1643static PyObject *
Mark Dickinson7c186e22010-04-20 22:32:49 +00001644divide_timedelta_timedelta(PyDateTime_Delta *left, PyDateTime_Delta *right)
1645{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001646 PyObject *pyus_left;
1647 PyObject *pyus_right;
1648 PyObject *result;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001649
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001650 pyus_left = delta_to_microseconds(left);
1651 if (pyus_left == NULL)
1652 return NULL;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001653
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001654 pyus_right = delta_to_microseconds(right);
1655 if (pyus_right == NULL) {
1656 Py_DECREF(pyus_left);
1657 return NULL;
1658 }
Mark Dickinson7c186e22010-04-20 22:32:49 +00001659
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001660 result = PyNumber_FloorDivide(pyus_left, pyus_right);
1661 Py_DECREF(pyus_left);
1662 Py_DECREF(pyus_right);
1663 return result;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001664}
1665
1666static PyObject *
1667truedivide_timedelta_timedelta(PyDateTime_Delta *left, PyDateTime_Delta *right)
1668{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001669 PyObject *pyus_left;
1670 PyObject *pyus_right;
1671 PyObject *result;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001672
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001673 pyus_left = delta_to_microseconds(left);
1674 if (pyus_left == NULL)
1675 return NULL;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001676
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001677 pyus_right = delta_to_microseconds(right);
1678 if (pyus_right == NULL) {
1679 Py_DECREF(pyus_left);
1680 return NULL;
1681 }
Mark Dickinson7c186e22010-04-20 22:32:49 +00001682
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001683 result = PyNumber_TrueDivide(pyus_left, pyus_right);
1684 Py_DECREF(pyus_left);
1685 Py_DECREF(pyus_right);
1686 return result;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001687}
1688
1689static PyObject *
Alexander Belopolsky1790bc42010-05-31 17:33:47 +00001690truedivide_timedelta_float(PyDateTime_Delta *delta, PyObject *f)
1691{
1692 PyObject *result = NULL;
1693 PyObject *pyus_in = NULL, *temp, *pyus_out;
1694 PyObject *ratio = NULL;
1695
1696 pyus_in = delta_to_microseconds(delta);
1697 if (pyus_in == NULL)
1698 return NULL;
1699 ratio = PyObject_CallMethod(f, "as_integer_ratio", NULL);
1700 if (ratio == NULL)
1701 goto error;
1702 temp = PyNumber_Multiply(pyus_in, PyTuple_GET_ITEM(ratio, 1));
1703 Py_DECREF(pyus_in);
1704 pyus_in = NULL;
1705 if (temp == NULL)
1706 goto error;
1707 pyus_out = divide_nearest(temp, PyTuple_GET_ITEM(ratio, 0));
1708 Py_DECREF(temp);
1709 if (pyus_out == NULL)
1710 goto error;
1711 result = microseconds_to_delta(pyus_out);
1712 Py_DECREF(pyus_out);
1713 error:
1714 Py_XDECREF(pyus_in);
1715 Py_XDECREF(ratio);
1716
1717 return result;
1718}
1719
1720static PyObject *
1721truedivide_timedelta_int(PyDateTime_Delta *delta, PyObject *i)
1722{
1723 PyObject *result;
1724 PyObject *pyus_in, *pyus_out;
1725 pyus_in = delta_to_microseconds(delta);
1726 if (pyus_in == NULL)
1727 return NULL;
1728 pyus_out = divide_nearest(pyus_in, i);
1729 Py_DECREF(pyus_in);
1730 if (pyus_out == NULL)
1731 return NULL;
1732 result = microseconds_to_delta(pyus_out);
1733 Py_DECREF(pyus_out);
1734
1735 return result;
1736}
1737
1738static PyObject *
Tim Peters2a799bf2002-12-16 20:18:38 +00001739delta_add(PyObject *left, PyObject *right)
1740{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001741 PyObject *result = Py_NotImplemented;
Tim Peters2a799bf2002-12-16 20:18:38 +00001742
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001743 if (PyDelta_Check(left) && PyDelta_Check(right)) {
1744 /* delta + delta */
1745 /* The C-level additions can't overflow because of the
1746 * invariant bounds.
1747 */
1748 int days = GET_TD_DAYS(left) + GET_TD_DAYS(right);
1749 int seconds = GET_TD_SECONDS(left) + GET_TD_SECONDS(right);
1750 int microseconds = GET_TD_MICROSECONDS(left) +
1751 GET_TD_MICROSECONDS(right);
1752 result = new_delta(days, seconds, microseconds, 1);
1753 }
Tim Peters2a799bf2002-12-16 20:18:38 +00001754
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001755 if (result == Py_NotImplemented)
1756 Py_INCREF(result);
1757 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001758}
1759
1760static PyObject *
1761delta_negative(PyDateTime_Delta *self)
1762{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001763 return new_delta(-GET_TD_DAYS(self),
1764 -GET_TD_SECONDS(self),
1765 -GET_TD_MICROSECONDS(self),
1766 1);
Tim Peters2a799bf2002-12-16 20:18:38 +00001767}
1768
1769static PyObject *
1770delta_positive(PyDateTime_Delta *self)
1771{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001772 /* Could optimize this (by returning self) if this isn't a
1773 * subclass -- but who uses unary + ? Approximately nobody.
1774 */
1775 return new_delta(GET_TD_DAYS(self),
1776 GET_TD_SECONDS(self),
1777 GET_TD_MICROSECONDS(self),
1778 0);
Tim Peters2a799bf2002-12-16 20:18:38 +00001779}
1780
1781static PyObject *
1782delta_abs(PyDateTime_Delta *self)
1783{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001784 PyObject *result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001785
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001786 assert(GET_TD_MICROSECONDS(self) >= 0);
1787 assert(GET_TD_SECONDS(self) >= 0);
Tim Peters2a799bf2002-12-16 20:18:38 +00001788
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001789 if (GET_TD_DAYS(self) < 0)
1790 result = delta_negative(self);
1791 else
1792 result = delta_positive(self);
Tim Peters2a799bf2002-12-16 20:18:38 +00001793
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001794 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001795}
1796
1797static PyObject *
1798delta_subtract(PyObject *left, PyObject *right)
1799{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001800 PyObject *result = Py_NotImplemented;
Tim Peters2a799bf2002-12-16 20:18:38 +00001801
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001802 if (PyDelta_Check(left) && PyDelta_Check(right)) {
1803 /* delta - delta */
Alexander Belopolskyb6f5ec72011-04-05 20:07:38 -04001804 /* The C-level additions can't overflow because of the
1805 * invariant bounds.
1806 */
1807 int days = GET_TD_DAYS(left) - GET_TD_DAYS(right);
1808 int seconds = GET_TD_SECONDS(left) - GET_TD_SECONDS(right);
1809 int microseconds = GET_TD_MICROSECONDS(left) -
1810 GET_TD_MICROSECONDS(right);
1811 result = new_delta(days, seconds, microseconds, 1);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001812 }
Tim Peters2a799bf2002-12-16 20:18:38 +00001813
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001814 if (result == Py_NotImplemented)
1815 Py_INCREF(result);
1816 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001817}
1818
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001819static int
1820delta_cmp(PyObject *self, PyObject *other)
1821{
1822 int diff = GET_TD_DAYS(self) - GET_TD_DAYS(other);
1823 if (diff == 0) {
1824 diff = GET_TD_SECONDS(self) - GET_TD_SECONDS(other);
1825 if (diff == 0)
1826 diff = GET_TD_MICROSECONDS(self) -
1827 GET_TD_MICROSECONDS(other);
1828 }
1829 return diff;
1830}
1831
Tim Peters2a799bf2002-12-16 20:18:38 +00001832static PyObject *
Guido van Rossum19960592006-08-24 17:29:38 +00001833delta_richcompare(PyObject *self, PyObject *other, int op)
Tim Peters2a799bf2002-12-16 20:18:38 +00001834{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001835 if (PyDelta_Check(other)) {
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00001836 int diff = delta_cmp(self, other);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001837 return diff_to_bool(diff, op);
1838 }
1839 else {
1840 Py_INCREF(Py_NotImplemented);
1841 return Py_NotImplemented;
1842 }
Tim Peters2a799bf2002-12-16 20:18:38 +00001843}
1844
1845static PyObject *delta_getstate(PyDateTime_Delta *self);
1846
Benjamin Peterson8f67d082010-10-17 20:54:53 +00001847static Py_hash_t
Tim Peters2a799bf2002-12-16 20:18:38 +00001848delta_hash(PyDateTime_Delta *self)
1849{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001850 if (self->hashcode == -1) {
1851 PyObject *temp = delta_getstate(self);
1852 if (temp != NULL) {
1853 self->hashcode = PyObject_Hash(temp);
1854 Py_DECREF(temp);
1855 }
1856 }
1857 return self->hashcode;
Tim Peters2a799bf2002-12-16 20:18:38 +00001858}
1859
1860static PyObject *
1861delta_multiply(PyObject *left, PyObject *right)
1862{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001863 PyObject *result = Py_NotImplemented;
Tim Peters2a799bf2002-12-16 20:18:38 +00001864
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001865 if (PyDelta_Check(left)) {
1866 /* delta * ??? */
1867 if (PyLong_Check(right))
1868 result = multiply_int_timedelta(right,
1869 (PyDateTime_Delta *) left);
Alexander Belopolsky1790bc42010-05-31 17:33:47 +00001870 else if (PyFloat_Check(right))
1871 result = multiply_float_timedelta(right,
1872 (PyDateTime_Delta *) left);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001873 }
1874 else if (PyLong_Check(left))
1875 result = multiply_int_timedelta(left,
Alexander Belopolsky1790bc42010-05-31 17:33:47 +00001876 (PyDateTime_Delta *) right);
1877 else if (PyFloat_Check(left))
1878 result = multiply_float_timedelta(left,
1879 (PyDateTime_Delta *) right);
Tim Peters2a799bf2002-12-16 20:18:38 +00001880
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001881 if (result == Py_NotImplemented)
1882 Py_INCREF(result);
1883 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001884}
1885
1886static PyObject *
1887delta_divide(PyObject *left, PyObject *right)
1888{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001889 PyObject *result = Py_NotImplemented;
Tim Peters2a799bf2002-12-16 20:18:38 +00001890
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001891 if (PyDelta_Check(left)) {
1892 /* delta * ??? */
1893 if (PyLong_Check(right))
1894 result = divide_timedelta_int(
1895 (PyDateTime_Delta *)left,
1896 right);
1897 else if (PyDelta_Check(right))
1898 result = divide_timedelta_timedelta(
1899 (PyDateTime_Delta *)left,
1900 (PyDateTime_Delta *)right);
1901 }
Tim Peters2a799bf2002-12-16 20:18:38 +00001902
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001903 if (result == Py_NotImplemented)
1904 Py_INCREF(result);
1905 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00001906}
1907
Mark Dickinson7c186e22010-04-20 22:32:49 +00001908static PyObject *
1909delta_truedivide(PyObject *left, PyObject *right)
1910{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001911 PyObject *result = Py_NotImplemented;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001912
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001913 if (PyDelta_Check(left)) {
1914 if (PyDelta_Check(right))
1915 result = truedivide_timedelta_timedelta(
1916 (PyDateTime_Delta *)left,
1917 (PyDateTime_Delta *)right);
Alexander Belopolsky1790bc42010-05-31 17:33:47 +00001918 else if (PyFloat_Check(right))
1919 result = truedivide_timedelta_float(
1920 (PyDateTime_Delta *)left, right);
1921 else if (PyLong_Check(right))
1922 result = truedivide_timedelta_int(
1923 (PyDateTime_Delta *)left, right);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001924 }
Mark Dickinson7c186e22010-04-20 22:32:49 +00001925
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001926 if (result == Py_NotImplemented)
1927 Py_INCREF(result);
1928 return result;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001929}
1930
1931static PyObject *
1932delta_remainder(PyObject *left, PyObject *right)
1933{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001934 PyObject *pyus_left;
1935 PyObject *pyus_right;
1936 PyObject *pyus_remainder;
1937 PyObject *remainder;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001938
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001939 if (!PyDelta_Check(left) || !PyDelta_Check(right)) {
1940 Py_INCREF(Py_NotImplemented);
1941 return Py_NotImplemented;
1942 }
Mark Dickinson7c186e22010-04-20 22:32:49 +00001943
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001944 pyus_left = delta_to_microseconds((PyDateTime_Delta *)left);
1945 if (pyus_left == NULL)
1946 return NULL;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001947
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001948 pyus_right = delta_to_microseconds((PyDateTime_Delta *)right);
1949 if (pyus_right == NULL) {
1950 Py_DECREF(pyus_left);
1951 return NULL;
1952 }
Mark Dickinson7c186e22010-04-20 22:32:49 +00001953
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001954 pyus_remainder = PyNumber_Remainder(pyus_left, pyus_right);
1955 Py_DECREF(pyus_left);
1956 Py_DECREF(pyus_right);
1957 if (pyus_remainder == NULL)
1958 return NULL;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001959
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001960 remainder = microseconds_to_delta(pyus_remainder);
1961 Py_DECREF(pyus_remainder);
1962 if (remainder == NULL)
1963 return NULL;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001964
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001965 return remainder;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001966}
1967
1968static PyObject *
1969delta_divmod(PyObject *left, PyObject *right)
1970{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001971 PyObject *pyus_left;
1972 PyObject *pyus_right;
1973 PyObject *divmod;
1974 PyObject *delta;
1975 PyObject *result;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001976
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001977 if (!PyDelta_Check(left) || !PyDelta_Check(right)) {
1978 Py_INCREF(Py_NotImplemented);
1979 return Py_NotImplemented;
1980 }
Mark Dickinson7c186e22010-04-20 22:32:49 +00001981
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001982 pyus_left = delta_to_microseconds((PyDateTime_Delta *)left);
1983 if (pyus_left == NULL)
1984 return NULL;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001985
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001986 pyus_right = delta_to_microseconds((PyDateTime_Delta *)right);
1987 if (pyus_right == NULL) {
1988 Py_DECREF(pyus_left);
1989 return NULL;
1990 }
Mark Dickinson7c186e22010-04-20 22:32:49 +00001991
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001992 divmod = PyNumber_Divmod(pyus_left, pyus_right);
1993 Py_DECREF(pyus_left);
1994 Py_DECREF(pyus_right);
1995 if (divmod == NULL)
1996 return NULL;
Mark Dickinson7c186e22010-04-20 22:32:49 +00001997
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001998 assert(PyTuple_Size(divmod) == 2);
1999 delta = microseconds_to_delta(PyTuple_GET_ITEM(divmod, 1));
2000 if (delta == NULL) {
2001 Py_DECREF(divmod);
2002 return NULL;
2003 }
2004 result = PyTuple_Pack(2, PyTuple_GET_ITEM(divmod, 0), delta);
2005 Py_DECREF(delta);
2006 Py_DECREF(divmod);
2007 return result;
Mark Dickinson7c186e22010-04-20 22:32:49 +00002008}
2009
Tim Peters2a799bf2002-12-16 20:18:38 +00002010/* Fold in the value of the tag ("seconds", "weeks", etc) component of a
2011 * timedelta constructor. sofar is the # of microseconds accounted for
2012 * so far, and there are factor microseconds per current unit, the number
2013 * of which is given by num. num * factor is added to sofar in a
2014 * numerically careful way, and that's the result. Any fractional
2015 * microseconds left over (this can happen if num is a float type) are
2016 * added into *leftover.
2017 * Note that there are many ways this can give an error (NULL) return.
2018 */
2019static PyObject *
2020accum(const char* tag, PyObject *sofar, PyObject *num, PyObject *factor,
2021 double *leftover)
2022{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002023 PyObject *prod;
2024 PyObject *sum;
Tim Peters2a799bf2002-12-16 20:18:38 +00002025
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002026 assert(num != NULL);
Tim Peters2a799bf2002-12-16 20:18:38 +00002027
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002028 if (PyLong_Check(num)) {
2029 prod = PyNumber_Multiply(num, factor);
2030 if (prod == NULL)
2031 return NULL;
2032 sum = PyNumber_Add(sofar, prod);
2033 Py_DECREF(prod);
2034 return sum;
2035 }
Tim Peters2a799bf2002-12-16 20:18:38 +00002036
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002037 if (PyFloat_Check(num)) {
2038 double dnum;
2039 double fracpart;
2040 double intpart;
2041 PyObject *x;
2042 PyObject *y;
Tim Peters2a799bf2002-12-16 20:18:38 +00002043
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002044 /* The Plan: decompose num into an integer part and a
2045 * fractional part, num = intpart + fracpart.
2046 * Then num * factor ==
2047 * intpart * factor + fracpart * factor
2048 * and the LHS can be computed exactly in long arithmetic.
2049 * The RHS is again broken into an int part and frac part.
2050 * and the frac part is added into *leftover.
2051 */
2052 dnum = PyFloat_AsDouble(num);
2053 if (dnum == -1.0 && PyErr_Occurred())
2054 return NULL;
2055 fracpart = modf(dnum, &intpart);
2056 x = PyLong_FromDouble(intpart);
2057 if (x == NULL)
2058 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002059
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002060 prod = PyNumber_Multiply(x, factor);
2061 Py_DECREF(x);
2062 if (prod == NULL)
2063 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002064
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002065 sum = PyNumber_Add(sofar, prod);
2066 Py_DECREF(prod);
2067 if (sum == NULL)
2068 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002069
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002070 if (fracpart == 0.0)
2071 return sum;
2072 /* So far we've lost no information. Dealing with the
2073 * fractional part requires float arithmetic, and may
2074 * lose a little info.
2075 */
2076 assert(PyLong_Check(factor));
2077 dnum = PyLong_AsDouble(factor);
Tim Peters2a799bf2002-12-16 20:18:38 +00002078
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002079 dnum *= fracpart;
2080 fracpart = modf(dnum, &intpart);
2081 x = PyLong_FromDouble(intpart);
2082 if (x == NULL) {
2083 Py_DECREF(sum);
2084 return NULL;
2085 }
Tim Peters2a799bf2002-12-16 20:18:38 +00002086
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002087 y = PyNumber_Add(sum, x);
2088 Py_DECREF(sum);
2089 Py_DECREF(x);
2090 *leftover += fracpart;
2091 return y;
2092 }
Tim Peters2a799bf2002-12-16 20:18:38 +00002093
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002094 PyErr_Format(PyExc_TypeError,
2095 "unsupported type for timedelta %s component: %s",
2096 tag, Py_TYPE(num)->tp_name);
2097 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002098}
2099
2100static PyObject *
2101delta_new(PyTypeObject *type, PyObject *args, PyObject *kw)
2102{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002103 PyObject *self = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002104
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002105 /* Argument objects. */
2106 PyObject *day = NULL;
2107 PyObject *second = NULL;
2108 PyObject *us = NULL;
2109 PyObject *ms = NULL;
2110 PyObject *minute = NULL;
2111 PyObject *hour = NULL;
2112 PyObject *week = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002113
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002114 PyObject *x = NULL; /* running sum of microseconds */
2115 PyObject *y = NULL; /* temp sum of microseconds */
2116 double leftover_us = 0.0;
Tim Peters2a799bf2002-12-16 20:18:38 +00002117
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002118 static char *keywords[] = {
2119 "days", "seconds", "microseconds", "milliseconds",
2120 "minutes", "hours", "weeks", NULL
2121 };
Tim Peters2a799bf2002-12-16 20:18:38 +00002122
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002123 if (PyArg_ParseTupleAndKeywords(args, kw, "|OOOOOOO:__new__",
2124 keywords,
2125 &day, &second, &us,
2126 &ms, &minute, &hour, &week) == 0)
2127 goto Done;
Tim Peters2a799bf2002-12-16 20:18:38 +00002128
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002129 x = PyLong_FromLong(0);
2130 if (x == NULL)
2131 goto Done;
Tim Peters2a799bf2002-12-16 20:18:38 +00002132
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002133#define CLEANUP \
2134 Py_DECREF(x); \
2135 x = y; \
2136 if (x == NULL) \
2137 goto Done
Tim Peters2a799bf2002-12-16 20:18:38 +00002138
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002139 if (us) {
2140 y = accum("microseconds", x, us, us_per_us, &leftover_us);
2141 CLEANUP;
2142 }
2143 if (ms) {
2144 y = accum("milliseconds", x, ms, us_per_ms, &leftover_us);
2145 CLEANUP;
2146 }
2147 if (second) {
2148 y = accum("seconds", x, second, us_per_second, &leftover_us);
2149 CLEANUP;
2150 }
2151 if (minute) {
2152 y = accum("minutes", x, minute, us_per_minute, &leftover_us);
2153 CLEANUP;
2154 }
2155 if (hour) {
2156 y = accum("hours", x, hour, us_per_hour, &leftover_us);
2157 CLEANUP;
2158 }
2159 if (day) {
2160 y = accum("days", x, day, us_per_day, &leftover_us);
2161 CLEANUP;
2162 }
2163 if (week) {
2164 y = accum("weeks", x, week, us_per_week, &leftover_us);
2165 CLEANUP;
2166 }
2167 if (leftover_us) {
2168 /* Round to nearest whole # of us, and add into x. */
2169 PyObject *temp = PyLong_FromLong(round_to_long(leftover_us));
2170 if (temp == NULL) {
2171 Py_DECREF(x);
2172 goto Done;
2173 }
2174 y = PyNumber_Add(x, temp);
2175 Py_DECREF(temp);
2176 CLEANUP;
2177 }
Tim Peters2a799bf2002-12-16 20:18:38 +00002178
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002179 self = microseconds_to_delta_ex(x, type);
2180 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00002181Done:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002182 return self;
Tim Peters2a799bf2002-12-16 20:18:38 +00002183
2184#undef CLEANUP
2185}
2186
2187static int
Jack Diederich4dafcc42006-11-28 19:15:13 +00002188delta_bool(PyDateTime_Delta *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00002189{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002190 return (GET_TD_DAYS(self) != 0
2191 || GET_TD_SECONDS(self) != 0
2192 || GET_TD_MICROSECONDS(self) != 0);
Tim Peters2a799bf2002-12-16 20:18:38 +00002193}
2194
2195static PyObject *
2196delta_repr(PyDateTime_Delta *self)
2197{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002198 if (GET_TD_MICROSECONDS(self) != 0)
2199 return PyUnicode_FromFormat("%s(%d, %d, %d)",
2200 Py_TYPE(self)->tp_name,
2201 GET_TD_DAYS(self),
2202 GET_TD_SECONDS(self),
2203 GET_TD_MICROSECONDS(self));
2204 if (GET_TD_SECONDS(self) != 0)
2205 return PyUnicode_FromFormat("%s(%d, %d)",
2206 Py_TYPE(self)->tp_name,
2207 GET_TD_DAYS(self),
2208 GET_TD_SECONDS(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002209
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002210 return PyUnicode_FromFormat("%s(%d)",
2211 Py_TYPE(self)->tp_name,
2212 GET_TD_DAYS(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002213}
2214
2215static PyObject *
2216delta_str(PyDateTime_Delta *self)
2217{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002218 int us = GET_TD_MICROSECONDS(self);
2219 int seconds = GET_TD_SECONDS(self);
2220 int minutes = divmod(seconds, 60, &seconds);
2221 int hours = divmod(minutes, 60, &minutes);
2222 int days = GET_TD_DAYS(self);
Tim Peters2a799bf2002-12-16 20:18:38 +00002223
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002224 if (days) {
2225 if (us)
2226 return PyUnicode_FromFormat("%d day%s, %d:%02d:%02d.%06d",
2227 days, (days == 1 || days == -1) ? "" : "s",
2228 hours, minutes, seconds, us);
2229 else
2230 return PyUnicode_FromFormat("%d day%s, %d:%02d:%02d",
2231 days, (days == 1 || days == -1) ? "" : "s",
2232 hours, minutes, seconds);
2233 } else {
2234 if (us)
2235 return PyUnicode_FromFormat("%d:%02d:%02d.%06d",
2236 hours, minutes, seconds, us);
2237 else
2238 return PyUnicode_FromFormat("%d:%02d:%02d",
2239 hours, minutes, seconds);
2240 }
Tim Peters2a799bf2002-12-16 20:18:38 +00002241
Tim Peters2a799bf2002-12-16 20:18:38 +00002242}
2243
Tim Peters371935f2003-02-01 01:52:50 +00002244/* Pickle support, a simple use of __reduce__. */
2245
Tim Petersb57f8f02003-02-01 02:54:15 +00002246/* __getstate__ isn't exposed */
Tim Peters2a799bf2002-12-16 20:18:38 +00002247static PyObject *
2248delta_getstate(PyDateTime_Delta *self)
2249{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002250 return Py_BuildValue("iii", GET_TD_DAYS(self),
2251 GET_TD_SECONDS(self),
2252 GET_TD_MICROSECONDS(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002253}
2254
Tim Peters2a799bf2002-12-16 20:18:38 +00002255static PyObject *
Antoine Pitroube6859d2009-11-25 23:02:32 +00002256delta_total_seconds(PyObject *self)
2257{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002258 PyObject *total_seconds;
2259 PyObject *total_microseconds;
2260 PyObject *one_million;
Mark Dickinson0381e3f2010-05-08 14:35:02 +00002261
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002262 total_microseconds = delta_to_microseconds((PyDateTime_Delta *)self);
2263 if (total_microseconds == NULL)
2264 return NULL;
Mark Dickinson0381e3f2010-05-08 14:35:02 +00002265
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002266 one_million = PyLong_FromLong(1000000L);
2267 if (one_million == NULL) {
2268 Py_DECREF(total_microseconds);
2269 return NULL;
2270 }
Mark Dickinson0381e3f2010-05-08 14:35:02 +00002271
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002272 total_seconds = PyNumber_TrueDivide(total_microseconds, one_million);
Mark Dickinson0381e3f2010-05-08 14:35:02 +00002273
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002274 Py_DECREF(total_microseconds);
2275 Py_DECREF(one_million);
2276 return total_seconds;
Antoine Pitroube6859d2009-11-25 23:02:32 +00002277}
2278
2279static PyObject *
Tim Peters2a799bf2002-12-16 20:18:38 +00002280delta_reduce(PyDateTime_Delta* self)
2281{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002282 return Py_BuildValue("ON", Py_TYPE(self), delta_getstate(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002283}
2284
2285#define OFFSET(field) offsetof(PyDateTime_Delta, field)
2286
2287static PyMemberDef delta_members[] = {
Guido van Rossum177e41a2003-01-30 22:06:23 +00002288
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002289 {"days", T_INT, OFFSET(days), READONLY,
2290 PyDoc_STR("Number of days.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002291
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002292 {"seconds", T_INT, OFFSET(seconds), READONLY,
2293 PyDoc_STR("Number of seconds (>= 0 and less than 1 day).")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002294
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002295 {"microseconds", T_INT, OFFSET(microseconds), READONLY,
2296 PyDoc_STR("Number of microseconds (>= 0 and less than 1 second).")},
2297 {NULL}
Tim Peters2a799bf2002-12-16 20:18:38 +00002298};
2299
2300static PyMethodDef delta_methods[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002301 {"total_seconds", (PyCFunction)delta_total_seconds, METH_NOARGS,
2302 PyDoc_STR("Total seconds in the duration.")},
Antoine Pitroube6859d2009-11-25 23:02:32 +00002303
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002304 {"__reduce__", (PyCFunction)delta_reduce, METH_NOARGS,
2305 PyDoc_STR("__reduce__() -> (cls, state)")},
Guido van Rossum177e41a2003-01-30 22:06:23 +00002306
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002307 {NULL, NULL},
Tim Peters2a799bf2002-12-16 20:18:38 +00002308};
2309
2310static char delta_doc[] =
2311PyDoc_STR("Difference between two datetime values.");
2312
2313static PyNumberMethods delta_as_number = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002314 delta_add, /* nb_add */
2315 delta_subtract, /* nb_subtract */
2316 delta_multiply, /* nb_multiply */
2317 delta_remainder, /* nb_remainder */
2318 delta_divmod, /* nb_divmod */
2319 0, /* nb_power */
2320 (unaryfunc)delta_negative, /* nb_negative */
2321 (unaryfunc)delta_positive, /* nb_positive */
2322 (unaryfunc)delta_abs, /* nb_absolute */
2323 (inquiry)delta_bool, /* nb_bool */
2324 0, /*nb_invert*/
2325 0, /*nb_lshift*/
2326 0, /*nb_rshift*/
2327 0, /*nb_and*/
2328 0, /*nb_xor*/
2329 0, /*nb_or*/
2330 0, /*nb_int*/
2331 0, /*nb_reserved*/
2332 0, /*nb_float*/
2333 0, /*nb_inplace_add*/
2334 0, /*nb_inplace_subtract*/
2335 0, /*nb_inplace_multiply*/
2336 0, /*nb_inplace_remainder*/
2337 0, /*nb_inplace_power*/
2338 0, /*nb_inplace_lshift*/
2339 0, /*nb_inplace_rshift*/
2340 0, /*nb_inplace_and*/
2341 0, /*nb_inplace_xor*/
2342 0, /*nb_inplace_or*/
2343 delta_divide, /* nb_floor_divide */
2344 delta_truedivide, /* nb_true_divide */
2345 0, /* nb_inplace_floor_divide */
2346 0, /* nb_inplace_true_divide */
Tim Peters2a799bf2002-12-16 20:18:38 +00002347};
2348
2349static PyTypeObject PyDateTime_DeltaType = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002350 PyVarObject_HEAD_INIT(NULL, 0)
2351 "datetime.timedelta", /* tp_name */
2352 sizeof(PyDateTime_Delta), /* tp_basicsize */
2353 0, /* tp_itemsize */
2354 0, /* tp_dealloc */
2355 0, /* tp_print */
2356 0, /* tp_getattr */
2357 0, /* tp_setattr */
2358 0, /* tp_reserved */
2359 (reprfunc)delta_repr, /* tp_repr */
2360 &delta_as_number, /* tp_as_number */
2361 0, /* tp_as_sequence */
2362 0, /* tp_as_mapping */
2363 (hashfunc)delta_hash, /* tp_hash */
2364 0, /* tp_call */
2365 (reprfunc)delta_str, /* tp_str */
2366 PyObject_GenericGetAttr, /* tp_getattro */
2367 0, /* tp_setattro */
2368 0, /* tp_as_buffer */
2369 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
2370 delta_doc, /* tp_doc */
2371 0, /* tp_traverse */
2372 0, /* tp_clear */
2373 delta_richcompare, /* tp_richcompare */
2374 0, /* tp_weaklistoffset */
2375 0, /* tp_iter */
2376 0, /* tp_iternext */
2377 delta_methods, /* tp_methods */
2378 delta_members, /* tp_members */
2379 0, /* tp_getset */
2380 0, /* tp_base */
2381 0, /* tp_dict */
2382 0, /* tp_descr_get */
2383 0, /* tp_descr_set */
2384 0, /* tp_dictoffset */
2385 0, /* tp_init */
2386 0, /* tp_alloc */
2387 delta_new, /* tp_new */
2388 0, /* tp_free */
Tim Peters2a799bf2002-12-16 20:18:38 +00002389};
2390
2391/*
2392 * PyDateTime_Date implementation.
2393 */
2394
2395/* Accessor properties. */
2396
2397static PyObject *
2398date_year(PyDateTime_Date *self, void *unused)
2399{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002400 return PyLong_FromLong(GET_YEAR(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002401}
2402
2403static PyObject *
2404date_month(PyDateTime_Date *self, void *unused)
2405{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002406 return PyLong_FromLong(GET_MONTH(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002407}
2408
2409static PyObject *
2410date_day(PyDateTime_Date *self, void *unused)
2411{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002412 return PyLong_FromLong(GET_DAY(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002413}
2414
2415static PyGetSetDef date_getset[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002416 {"year", (getter)date_year},
2417 {"month", (getter)date_month},
2418 {"day", (getter)date_day},
2419 {NULL}
Tim Peters2a799bf2002-12-16 20:18:38 +00002420};
2421
2422/* Constructors. */
2423
Martin v. Löwis02cbf4a2006-02-27 17:20:04 +00002424static char *date_kws[] = {"year", "month", "day", NULL};
Tim Peters12bf3392002-12-24 05:41:27 +00002425
Tim Peters2a799bf2002-12-16 20:18:38 +00002426static PyObject *
2427date_new(PyTypeObject *type, PyObject *args, PyObject *kw)
2428{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002429 PyObject *self = NULL;
2430 PyObject *state;
2431 int year;
2432 int month;
2433 int day;
Tim Peters2a799bf2002-12-16 20:18:38 +00002434
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002435 /* Check for invocation from pickle with __getstate__ state */
2436 if (PyTuple_GET_SIZE(args) == 1 &&
2437 PyBytes_Check(state = PyTuple_GET_ITEM(args, 0)) &&
2438 PyBytes_GET_SIZE(state) == _PyDateTime_DATE_DATASIZE &&
2439 MONTH_IS_SANE(PyBytes_AS_STRING(state)[2]))
2440 {
2441 PyDateTime_Date *me;
Tim Peters70533e22003-02-01 04:40:04 +00002442
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002443 me = (PyDateTime_Date *) (type->tp_alloc(type, 0));
2444 if (me != NULL) {
2445 char *pdata = PyBytes_AS_STRING(state);
2446 memcpy(me->data, pdata, _PyDateTime_DATE_DATASIZE);
2447 me->hashcode = -1;
2448 }
2449 return (PyObject *)me;
2450 }
Guido van Rossum177e41a2003-01-30 22:06:23 +00002451
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002452 if (PyArg_ParseTupleAndKeywords(args, kw, "iii", date_kws,
2453 &year, &month, &day)) {
2454 if (check_date_args(year, month, day) < 0)
2455 return NULL;
2456 self = new_date_ex(year, month, day, type);
2457 }
2458 return self;
Tim Peters2a799bf2002-12-16 20:18:38 +00002459}
2460
2461/* Return new date from localtime(t). */
2462static PyObject *
Tim Peters1b6f7a92004-06-20 02:50:16 +00002463date_local_from_time_t(PyObject *cls, double ts)
Tim Peters2a799bf2002-12-16 20:18:38 +00002464{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002465 struct tm *tm;
2466 time_t t;
2467 PyObject *result = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002468
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002469 t = _PyTime_DoubleToTimet(ts);
2470 if (t == (time_t)-1 && PyErr_Occurred())
2471 return NULL;
2472 tm = localtime(&t);
2473 if (tm)
2474 result = PyObject_CallFunction(cls, "iii",
2475 tm->tm_year + 1900,
2476 tm->tm_mon + 1,
2477 tm->tm_mday);
2478 else
2479 PyErr_SetString(PyExc_ValueError,
2480 "timestamp out of range for "
2481 "platform localtime() function");
2482 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00002483}
2484
2485/* Return new date from current time.
2486 * We say this is equivalent to fromtimestamp(time.time()), and the
2487 * only way to be sure of that is to *call* time.time(). That's not
2488 * generally the same as calling C's time.
2489 */
2490static PyObject *
2491date_today(PyObject *cls, PyObject *dummy)
2492{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002493 PyObject *time;
2494 PyObject *result;
Tim Peters2a799bf2002-12-16 20:18:38 +00002495
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002496 time = time_time();
2497 if (time == NULL)
2498 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002499
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002500 /* Note well: today() is a class method, so this may not call
2501 * date.fromtimestamp. For example, it may call
2502 * datetime.fromtimestamp. That's why we need all the accuracy
2503 * time.time() delivers; if someone were gonzo about optimization,
2504 * date.today() could get away with plain C time().
2505 */
2506 result = PyObject_CallMethod(cls, "fromtimestamp", "O", time);
2507 Py_DECREF(time);
2508 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00002509}
2510
2511/* Return new date from given timestamp (Python timestamp -- a double). */
2512static PyObject *
2513date_fromtimestamp(PyObject *cls, PyObject *args)
2514{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002515 double timestamp;
2516 PyObject *result = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002517
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002518 if (PyArg_ParseTuple(args, "d:fromtimestamp", &timestamp))
2519 result = date_local_from_time_t(cls, timestamp);
2520 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00002521}
2522
2523/* Return new date from proleptic Gregorian ordinal. Raises ValueError if
2524 * the ordinal is out of range.
2525 */
2526static PyObject *
2527date_fromordinal(PyObject *cls, PyObject *args)
2528{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002529 PyObject *result = NULL;
2530 int ordinal;
Tim Peters2a799bf2002-12-16 20:18:38 +00002531
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002532 if (PyArg_ParseTuple(args, "i:fromordinal", &ordinal)) {
2533 int year;
2534 int month;
2535 int day;
Tim Peters2a799bf2002-12-16 20:18:38 +00002536
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002537 if (ordinal < 1)
2538 PyErr_SetString(PyExc_ValueError, "ordinal must be "
2539 ">= 1");
2540 else {
2541 ord_to_ymd(ordinal, &year, &month, &day);
2542 result = PyObject_CallFunction(cls, "iii",
2543 year, month, day);
2544 }
2545 }
2546 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00002547}
2548
2549/*
2550 * Date arithmetic.
2551 */
2552
2553/* date + timedelta -> date. If arg negate is true, subtract the timedelta
2554 * instead.
2555 */
2556static PyObject *
2557add_date_timedelta(PyDateTime_Date *date, PyDateTime_Delta *delta, int negate)
2558{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002559 PyObject *result = NULL;
2560 int year = GET_YEAR(date);
2561 int month = GET_MONTH(date);
2562 int deltadays = GET_TD_DAYS(delta);
2563 /* C-level overflow is impossible because |deltadays| < 1e9. */
2564 int day = GET_DAY(date) + (negate ? -deltadays : deltadays);
Tim Peters2a799bf2002-12-16 20:18:38 +00002565
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002566 if (normalize_date(&year, &month, &day) >= 0)
2567 result = new_date(year, month, day);
2568 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00002569}
2570
2571static PyObject *
2572date_add(PyObject *left, PyObject *right)
2573{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002574 if (PyDateTime_Check(left) || PyDateTime_Check(right)) {
2575 Py_INCREF(Py_NotImplemented);
2576 return Py_NotImplemented;
2577 }
2578 if (PyDate_Check(left)) {
2579 /* date + ??? */
2580 if (PyDelta_Check(right))
2581 /* date + delta */
2582 return add_date_timedelta((PyDateTime_Date *) left,
2583 (PyDateTime_Delta *) right,
2584 0);
2585 }
2586 else {
2587 /* ??? + date
2588 * 'right' must be one of us, or we wouldn't have been called
2589 */
2590 if (PyDelta_Check(left))
2591 /* delta + date */
2592 return add_date_timedelta((PyDateTime_Date *) right,
2593 (PyDateTime_Delta *) left,
2594 0);
2595 }
2596 Py_INCREF(Py_NotImplemented);
2597 return Py_NotImplemented;
Tim Peters2a799bf2002-12-16 20:18:38 +00002598}
2599
2600static PyObject *
2601date_subtract(PyObject *left, PyObject *right)
2602{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002603 if (PyDateTime_Check(left) || PyDateTime_Check(right)) {
2604 Py_INCREF(Py_NotImplemented);
2605 return Py_NotImplemented;
2606 }
2607 if (PyDate_Check(left)) {
2608 if (PyDate_Check(right)) {
2609 /* date - date */
2610 int left_ord = ymd_to_ord(GET_YEAR(left),
2611 GET_MONTH(left),
2612 GET_DAY(left));
2613 int right_ord = ymd_to_ord(GET_YEAR(right),
2614 GET_MONTH(right),
2615 GET_DAY(right));
2616 return new_delta(left_ord - right_ord, 0, 0, 0);
2617 }
2618 if (PyDelta_Check(right)) {
2619 /* date - delta */
2620 return add_date_timedelta((PyDateTime_Date *) left,
2621 (PyDateTime_Delta *) right,
2622 1);
2623 }
2624 }
2625 Py_INCREF(Py_NotImplemented);
2626 return Py_NotImplemented;
Tim Peters2a799bf2002-12-16 20:18:38 +00002627}
2628
2629
2630/* Various ways to turn a date into a string. */
2631
2632static PyObject *
2633date_repr(PyDateTime_Date *self)
2634{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002635 return PyUnicode_FromFormat("%s(%d, %d, %d)",
2636 Py_TYPE(self)->tp_name,
2637 GET_YEAR(self), GET_MONTH(self), GET_DAY(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002638}
2639
2640static PyObject *
2641date_isoformat(PyDateTime_Date *self)
2642{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002643 return PyUnicode_FromFormat("%04d-%02d-%02d",
2644 GET_YEAR(self), GET_MONTH(self), GET_DAY(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002645}
2646
Tim Peterse2df5ff2003-05-02 18:39:55 +00002647/* str() calls the appropriate isoformat() method. */
Tim Peters2a799bf2002-12-16 20:18:38 +00002648static PyObject *
2649date_str(PyDateTime_Date *self)
2650{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002651 return PyObject_CallMethod((PyObject *)self, "isoformat", "()");
Tim Peters2a799bf2002-12-16 20:18:38 +00002652}
2653
2654
2655static PyObject *
2656date_ctime(PyDateTime_Date *self)
2657{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002658 return format_ctime(self, 0, 0, 0);
Tim Peters2a799bf2002-12-16 20:18:38 +00002659}
2660
2661static PyObject *
2662date_strftime(PyDateTime_Date *self, PyObject *args, PyObject *kw)
2663{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002664 /* This method can be inherited, and needs to call the
2665 * timetuple() method appropriate to self's class.
2666 */
2667 PyObject *result;
2668 PyObject *tuple;
2669 PyObject *format;
2670 static char *keywords[] = {"format", NULL};
Tim Peters2a799bf2002-12-16 20:18:38 +00002671
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002672 if (! PyArg_ParseTupleAndKeywords(args, kw, "U:strftime", keywords,
2673 &format))
2674 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002675
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002676 tuple = PyObject_CallMethod((PyObject *)self, "timetuple", "()");
2677 if (tuple == NULL)
2678 return NULL;
2679 result = wrap_strftime((PyObject *)self, format, tuple,
2680 (PyObject *)self);
2681 Py_DECREF(tuple);
2682 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00002683}
2684
Eric Smith1ba31142007-09-11 18:06:02 +00002685static PyObject *
2686date_format(PyDateTime_Date *self, PyObject *args)
2687{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002688 PyObject *format;
Eric Smith1ba31142007-09-11 18:06:02 +00002689
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002690 if (!PyArg_ParseTuple(args, "U:__format__", &format))
2691 return NULL;
Eric Smith1ba31142007-09-11 18:06:02 +00002692
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002693 /* if the format is zero length, return str(self) */
2694 if (PyUnicode_GetSize(format) == 0)
2695 return PyObject_Str((PyObject *)self);
Eric Smith1ba31142007-09-11 18:06:02 +00002696
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002697 return PyObject_CallMethod((PyObject *)self, "strftime", "O", format);
Eric Smith1ba31142007-09-11 18:06:02 +00002698}
2699
Tim Peters2a799bf2002-12-16 20:18:38 +00002700/* ISO methods. */
2701
2702static PyObject *
2703date_isoweekday(PyDateTime_Date *self)
2704{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002705 int dow = weekday(GET_YEAR(self), GET_MONTH(self), GET_DAY(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002706
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002707 return PyLong_FromLong(dow + 1);
Tim Peters2a799bf2002-12-16 20:18:38 +00002708}
2709
2710static PyObject *
2711date_isocalendar(PyDateTime_Date *self)
2712{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002713 int year = GET_YEAR(self);
2714 int week1_monday = iso_week1_monday(year);
2715 int today = ymd_to_ord(year, GET_MONTH(self), GET_DAY(self));
2716 int week;
2717 int day;
Tim Peters2a799bf2002-12-16 20:18:38 +00002718
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002719 week = divmod(today - week1_monday, 7, &day);
2720 if (week < 0) {
2721 --year;
2722 week1_monday = iso_week1_monday(year);
2723 week = divmod(today - week1_monday, 7, &day);
2724 }
2725 else if (week >= 52 && today >= iso_week1_monday(year + 1)) {
2726 ++year;
2727 week = 0;
2728 }
2729 return Py_BuildValue("iii", year, week + 1, day + 1);
Tim Peters2a799bf2002-12-16 20:18:38 +00002730}
2731
2732/* Miscellaneous methods. */
2733
Tim Peters2a799bf2002-12-16 20:18:38 +00002734static PyObject *
Guido van Rossum19960592006-08-24 17:29:38 +00002735date_richcompare(PyObject *self, PyObject *other, int op)
Tim Peters2a799bf2002-12-16 20:18:38 +00002736{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002737 if (PyDate_Check(other)) {
2738 int diff = memcmp(((PyDateTime_Date *)self)->data,
2739 ((PyDateTime_Date *)other)->data,
2740 _PyDateTime_DATE_DATASIZE);
2741 return diff_to_bool(diff, op);
2742 }
2743 else {
2744 Py_INCREF(Py_NotImplemented);
2745 return Py_NotImplemented;
2746 }
Tim Peters2a799bf2002-12-16 20:18:38 +00002747}
2748
2749static PyObject *
2750date_timetuple(PyDateTime_Date *self)
2751{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002752 return build_struct_time(GET_YEAR(self),
2753 GET_MONTH(self),
2754 GET_DAY(self),
2755 0, 0, 0, -1);
Tim Peters2a799bf2002-12-16 20:18:38 +00002756}
2757
Tim Peters12bf3392002-12-24 05:41:27 +00002758static PyObject *
2759date_replace(PyDateTime_Date *self, PyObject *args, PyObject *kw)
2760{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002761 PyObject *clone;
2762 PyObject *tuple;
2763 int year = GET_YEAR(self);
2764 int month = GET_MONTH(self);
2765 int day = GET_DAY(self);
Tim Peters12bf3392002-12-24 05:41:27 +00002766
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002767 if (! PyArg_ParseTupleAndKeywords(args, kw, "|iii:replace", date_kws,
2768 &year, &month, &day))
2769 return NULL;
2770 tuple = Py_BuildValue("iii", year, month, day);
2771 if (tuple == NULL)
2772 return NULL;
2773 clone = date_new(Py_TYPE(self), tuple, NULL);
2774 Py_DECREF(tuple);
2775 return clone;
Tim Peters12bf3392002-12-24 05:41:27 +00002776}
2777
Guido van Rossumfd53fd62007-08-24 04:05:13 +00002778/*
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002779 Borrowed from stringobject.c, originally it was string_hash()
Guido van Rossumfd53fd62007-08-24 04:05:13 +00002780*/
Benjamin Peterson8f67d082010-10-17 20:54:53 +00002781static Py_hash_t
Guido van Rossumfd53fd62007-08-24 04:05:13 +00002782generic_hash(unsigned char *data, int len)
2783{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002784 register unsigned char *p;
Benjamin Peterson8f67d082010-10-17 20:54:53 +00002785 register Py_hash_t x;
Guido van Rossumfd53fd62007-08-24 04:05:13 +00002786
Benjamin Petersone249dca2012-02-21 11:09:13 -05002787 assert(_Py_HashSecret_Initialized);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002788 p = (unsigned char *) data;
Georg Brandl09a7c722012-02-20 21:31:46 +01002789 x = _Py_HashSecret.prefix;
2790 x ^= *p << 7;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002791 while (--len >= 0)
2792 x = (1000003*x) ^ *p++;
2793 x ^= len;
Georg Brandl09a7c722012-02-20 21:31:46 +01002794 x ^= _Py_HashSecret.suffix;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002795 if (x == -1)
2796 x = -2;
Guido van Rossumfd53fd62007-08-24 04:05:13 +00002797
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002798 return x;
Guido van Rossumfd53fd62007-08-24 04:05:13 +00002799}
2800
2801
2802static PyObject *date_getstate(PyDateTime_Date *self);
Tim Peters2a799bf2002-12-16 20:18:38 +00002803
Benjamin Peterson8f67d082010-10-17 20:54:53 +00002804static Py_hash_t
Tim Peters2a799bf2002-12-16 20:18:38 +00002805date_hash(PyDateTime_Date *self)
2806{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002807 if (self->hashcode == -1)
2808 self->hashcode = generic_hash(
2809 (unsigned char *)self->data, _PyDateTime_DATE_DATASIZE);
Guido van Rossum254348e2007-11-21 19:29:53 +00002810
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002811 return self->hashcode;
Tim Peters2a799bf2002-12-16 20:18:38 +00002812}
2813
2814static PyObject *
2815date_toordinal(PyDateTime_Date *self)
2816{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002817 return PyLong_FromLong(ymd_to_ord(GET_YEAR(self), GET_MONTH(self),
2818 GET_DAY(self)));
Tim Peters2a799bf2002-12-16 20:18:38 +00002819}
2820
2821static PyObject *
2822date_weekday(PyDateTime_Date *self)
2823{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002824 int dow = weekday(GET_YEAR(self), GET_MONTH(self), GET_DAY(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002825
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002826 return PyLong_FromLong(dow);
Tim Peters2a799bf2002-12-16 20:18:38 +00002827}
2828
Tim Peters371935f2003-02-01 01:52:50 +00002829/* Pickle support, a simple use of __reduce__. */
Tim Peters2a799bf2002-12-16 20:18:38 +00002830
Tim Petersb57f8f02003-02-01 02:54:15 +00002831/* __getstate__ isn't exposed */
Tim Peters2a799bf2002-12-16 20:18:38 +00002832static PyObject *
Guido van Rossumfd53fd62007-08-24 04:05:13 +00002833date_getstate(PyDateTime_Date *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00002834{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002835 PyObject* field;
2836 field = PyBytes_FromStringAndSize((char*)self->data,
2837 _PyDateTime_DATE_DATASIZE);
2838 return Py_BuildValue("(N)", field);
Tim Peters2a799bf2002-12-16 20:18:38 +00002839}
2840
2841static PyObject *
Guido van Rossum177e41a2003-01-30 22:06:23 +00002842date_reduce(PyDateTime_Date *self, PyObject *arg)
Tim Peters2a799bf2002-12-16 20:18:38 +00002843{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002844 return Py_BuildValue("(ON)", Py_TYPE(self), date_getstate(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00002845}
2846
2847static PyMethodDef date_methods[] = {
Guido van Rossum177e41a2003-01-30 22:06:23 +00002848
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002849 /* Class methods: */
Guido van Rossum177e41a2003-01-30 22:06:23 +00002850
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002851 {"fromtimestamp", (PyCFunction)date_fromtimestamp, METH_VARARGS |
2852 METH_CLASS,
2853 PyDoc_STR("timestamp -> local date from a POSIX timestamp (like "
2854 "time.time()).")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002855
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002856 {"fromordinal", (PyCFunction)date_fromordinal, METH_VARARGS |
2857 METH_CLASS,
2858 PyDoc_STR("int -> date corresponding to a proleptic Gregorian "
2859 "ordinal.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002860
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002861 {"today", (PyCFunction)date_today, METH_NOARGS | METH_CLASS,
2862 PyDoc_STR("Current date or datetime: same as "
2863 "self.__class__.fromtimestamp(time.time()).")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002864
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002865 /* Instance methods: */
Tim Peters2a799bf2002-12-16 20:18:38 +00002866
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002867 {"ctime", (PyCFunction)date_ctime, METH_NOARGS,
2868 PyDoc_STR("Return ctime() style string.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002869
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002870 {"strftime", (PyCFunction)date_strftime, METH_VARARGS | METH_KEYWORDS,
2871 PyDoc_STR("format -> strftime() style string.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002872
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002873 {"__format__", (PyCFunction)date_format, METH_VARARGS,
2874 PyDoc_STR("Formats self with strftime.")},
Eric Smith1ba31142007-09-11 18:06:02 +00002875
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002876 {"timetuple", (PyCFunction)date_timetuple, METH_NOARGS,
2877 PyDoc_STR("Return time tuple, compatible with time.localtime().")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002878
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002879 {"isocalendar", (PyCFunction)date_isocalendar, METH_NOARGS,
2880 PyDoc_STR("Return a 3-tuple containing ISO year, week number, and "
2881 "weekday.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002882
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002883 {"isoformat", (PyCFunction)date_isoformat, METH_NOARGS,
2884 PyDoc_STR("Return string in ISO 8601 format, YYYY-MM-DD.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002885
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002886 {"isoweekday", (PyCFunction)date_isoweekday, METH_NOARGS,
2887 PyDoc_STR("Return the day of the week represented by the date.\n"
2888 "Monday == 1 ... Sunday == 7")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002889
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002890 {"toordinal", (PyCFunction)date_toordinal, METH_NOARGS,
2891 PyDoc_STR("Return proleptic Gregorian ordinal. January 1 of year "
2892 "1 is day 1.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002893
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002894 {"weekday", (PyCFunction)date_weekday, METH_NOARGS,
2895 PyDoc_STR("Return the day of the week represented by the date.\n"
2896 "Monday == 0 ... Sunday == 6")},
Tim Peters2a799bf2002-12-16 20:18:38 +00002897
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002898 {"replace", (PyCFunction)date_replace, METH_VARARGS | METH_KEYWORDS,
2899 PyDoc_STR("Return date with new specified fields.")},
Tim Peters12bf3392002-12-24 05:41:27 +00002900
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002901 {"__reduce__", (PyCFunction)date_reduce, METH_NOARGS,
2902 PyDoc_STR("__reduce__() -> (cls, state)")},
Guido van Rossum177e41a2003-01-30 22:06:23 +00002903
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002904 {NULL, NULL}
Tim Peters2a799bf2002-12-16 20:18:38 +00002905};
2906
2907static char date_doc[] =
Raymond Hettinger3a4231d2004-12-19 20:13:24 +00002908PyDoc_STR("date(year, month, day) --> date object");
Tim Peters2a799bf2002-12-16 20:18:38 +00002909
2910static PyNumberMethods date_as_number = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002911 date_add, /* nb_add */
2912 date_subtract, /* nb_subtract */
2913 0, /* nb_multiply */
2914 0, /* nb_remainder */
2915 0, /* nb_divmod */
2916 0, /* nb_power */
2917 0, /* nb_negative */
2918 0, /* nb_positive */
2919 0, /* nb_absolute */
2920 0, /* nb_bool */
Tim Peters2a799bf2002-12-16 20:18:38 +00002921};
2922
2923static PyTypeObject PyDateTime_DateType = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002924 PyVarObject_HEAD_INIT(NULL, 0)
2925 "datetime.date", /* tp_name */
2926 sizeof(PyDateTime_Date), /* tp_basicsize */
2927 0, /* tp_itemsize */
2928 0, /* tp_dealloc */
2929 0, /* tp_print */
2930 0, /* tp_getattr */
2931 0, /* tp_setattr */
2932 0, /* tp_reserved */
2933 (reprfunc)date_repr, /* tp_repr */
2934 &date_as_number, /* tp_as_number */
2935 0, /* tp_as_sequence */
2936 0, /* tp_as_mapping */
2937 (hashfunc)date_hash, /* tp_hash */
2938 0, /* tp_call */
2939 (reprfunc)date_str, /* tp_str */
2940 PyObject_GenericGetAttr, /* tp_getattro */
2941 0, /* tp_setattro */
2942 0, /* tp_as_buffer */
2943 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
2944 date_doc, /* tp_doc */
2945 0, /* tp_traverse */
2946 0, /* tp_clear */
2947 date_richcompare, /* tp_richcompare */
2948 0, /* tp_weaklistoffset */
2949 0, /* tp_iter */
2950 0, /* tp_iternext */
2951 date_methods, /* tp_methods */
2952 0, /* tp_members */
2953 date_getset, /* tp_getset */
2954 0, /* tp_base */
2955 0, /* tp_dict */
2956 0, /* tp_descr_get */
2957 0, /* tp_descr_set */
2958 0, /* tp_dictoffset */
2959 0, /* tp_init */
2960 0, /* tp_alloc */
2961 date_new, /* tp_new */
2962 0, /* tp_free */
Tim Peters2a799bf2002-12-16 20:18:38 +00002963};
2964
2965/*
Tim Peters2a799bf2002-12-16 20:18:38 +00002966 * PyDateTime_TZInfo implementation.
2967 */
2968
2969/* This is a pure abstract base class, so doesn't do anything beyond
2970 * raising NotImplemented exceptions. Real tzinfo classes need
2971 * to derive from this. This is mostly for clarity, and for efficiency in
Tim Petersa9bc1682003-01-11 03:39:11 +00002972 * datetime and time constructors (their tzinfo arguments need to
Tim Peters2a799bf2002-12-16 20:18:38 +00002973 * be subclasses of this tzinfo class, which is easy and quick to check).
2974 *
2975 * Note: For reasons having to do with pickling of subclasses, we have
2976 * to allow tzinfo objects to be instantiated. This wasn't an issue
2977 * in the Python implementation (__init__() could raise NotImplementedError
2978 * there without ill effect), but doing so in the C implementation hit a
2979 * brick wall.
2980 */
2981
2982static PyObject *
2983tzinfo_nogo(const char* methodname)
2984{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002985 PyErr_Format(PyExc_NotImplementedError,
2986 "a tzinfo subclass must implement %s()",
2987 methodname);
2988 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00002989}
2990
2991/* Methods. A subclass must implement these. */
2992
Tim Peters52dcce22003-01-23 16:36:11 +00002993static PyObject *
Tim Peters2a799bf2002-12-16 20:18:38 +00002994tzinfo_tzname(PyDateTime_TZInfo *self, PyObject *dt)
2995{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00002996 return tzinfo_nogo("tzname");
Tim Peters2a799bf2002-12-16 20:18:38 +00002997}
2998
Tim Peters52dcce22003-01-23 16:36:11 +00002999static PyObject *
Tim Peters2a799bf2002-12-16 20:18:38 +00003000tzinfo_utcoffset(PyDateTime_TZInfo *self, PyObject *dt)
3001{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003002 return tzinfo_nogo("utcoffset");
Tim Peters2a799bf2002-12-16 20:18:38 +00003003}
3004
Tim Peters52dcce22003-01-23 16:36:11 +00003005static PyObject *
Tim Peters2a799bf2002-12-16 20:18:38 +00003006tzinfo_dst(PyDateTime_TZInfo *self, PyObject *dt)
3007{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003008 return tzinfo_nogo("dst");
Tim Peters2a799bf2002-12-16 20:18:38 +00003009}
3010
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003011
3012static PyObject *add_datetime_timedelta(PyDateTime_DateTime *date,
3013 PyDateTime_Delta *delta,
3014 int factor);
3015static PyObject *datetime_utcoffset(PyObject *self, PyObject *);
3016static PyObject *datetime_dst(PyObject *self, PyObject *);
3017
Tim Peters52dcce22003-01-23 16:36:11 +00003018static PyObject *
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003019tzinfo_fromutc(PyDateTime_TZInfo *self, PyObject *dt)
Tim Peters52dcce22003-01-23 16:36:11 +00003020{
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003021 PyObject *result = NULL;
3022 PyObject *off = NULL, *dst = NULL;
3023 PyDateTime_Delta *delta = NULL;
Tim Peters52dcce22003-01-23 16:36:11 +00003024
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003025 if (!PyDateTime_Check(dt)) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003026 PyErr_SetString(PyExc_TypeError,
3027 "fromutc: argument must be a datetime");
3028 return NULL;
3029 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003030 if (GET_DT_TZINFO(dt) != (PyObject *)self) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003031 PyErr_SetString(PyExc_ValueError, "fromutc: dt.tzinfo "
3032 "is not self");
3033 return NULL;
3034 }
Tim Peters52dcce22003-01-23 16:36:11 +00003035
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003036 off = datetime_utcoffset(dt, NULL);
3037 if (off == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003038 return NULL;
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003039 if (off == Py_None) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003040 PyErr_SetString(PyExc_ValueError, "fromutc: non-None "
3041 "utcoffset() result required");
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003042 goto Fail;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003043 }
Tim Peters52dcce22003-01-23 16:36:11 +00003044
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003045 dst = datetime_dst(dt, NULL);
3046 if (dst == NULL)
3047 goto Fail;
3048 if (dst == Py_None) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003049 PyErr_SetString(PyExc_ValueError, "fromutc: non-None "
3050 "dst() result required");
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003051 goto Fail;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003052 }
Tim Peters52dcce22003-01-23 16:36:11 +00003053
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003054 delta = (PyDateTime_Delta *)delta_subtract(off, dst);
3055 if (delta == NULL)
3056 goto Fail;
3057 result = add_datetime_timedelta((PyDateTime_DateTime *)dt, delta, 1);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003058 if (result == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003059 goto Fail;
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003060
3061 Py_DECREF(dst);
3062 dst = call_dst(GET_DT_TZINFO(dt), result);
3063 if (dst == NULL)
3064 goto Fail;
3065 if (dst == Py_None)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003066 goto Inconsistent;
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003067 if (delta_bool(delta) != 0) {
3068 PyObject *temp = result;
3069 result = add_datetime_timedelta((PyDateTime_DateTime *)result,
3070 (PyDateTime_Delta *)dst, 1);
3071 Py_DECREF(temp);
3072 if (result == NULL)
3073 goto Fail;
3074 }
3075 Py_DECREF(delta);
3076 Py_DECREF(dst);
3077 Py_DECREF(off);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003078 return result;
Tim Peters52dcce22003-01-23 16:36:11 +00003079
3080Inconsistent:
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003081 PyErr_SetString(PyExc_ValueError, "fromutc: tz.dst() gave"
3082 "inconsistent results; cannot convert");
Tim Peters52dcce22003-01-23 16:36:11 +00003083
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003084 /* fall thru to failure */
Tim Peters52dcce22003-01-23 16:36:11 +00003085Fail:
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003086 Py_XDECREF(off);
3087 Py_XDECREF(dst);
3088 Py_XDECREF(delta);
3089 Py_XDECREF(result);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003090 return NULL;
Tim Peters52dcce22003-01-23 16:36:11 +00003091}
3092
Tim Peters2a799bf2002-12-16 20:18:38 +00003093/*
3094 * Pickle support. This is solely so that tzinfo subclasses can use
Guido van Rossum177e41a2003-01-30 22:06:23 +00003095 * pickling -- tzinfo itself is supposed to be uninstantiable.
Tim Peters2a799bf2002-12-16 20:18:38 +00003096 */
3097
Guido van Rossum177e41a2003-01-30 22:06:23 +00003098static PyObject *
3099tzinfo_reduce(PyObject *self)
3100{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003101 PyObject *args, *state, *tmp;
3102 PyObject *getinitargs, *getstate;
Tim Peters2a799bf2002-12-16 20:18:38 +00003103
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003104 tmp = PyTuple_New(0);
3105 if (tmp == NULL)
3106 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00003107
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003108 getinitargs = PyObject_GetAttrString(self, "__getinitargs__");
3109 if (getinitargs != NULL) {
3110 args = PyObject_CallObject(getinitargs, tmp);
3111 Py_DECREF(getinitargs);
3112 if (args == NULL) {
3113 Py_DECREF(tmp);
3114 return NULL;
3115 }
3116 }
3117 else {
3118 PyErr_Clear();
3119 args = tmp;
3120 Py_INCREF(args);
3121 }
Guido van Rossum177e41a2003-01-30 22:06:23 +00003122
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003123 getstate = PyObject_GetAttrString(self, "__getstate__");
3124 if (getstate != NULL) {
3125 state = PyObject_CallObject(getstate, tmp);
3126 Py_DECREF(getstate);
3127 if (state == NULL) {
3128 Py_DECREF(args);
3129 Py_DECREF(tmp);
3130 return NULL;
3131 }
3132 }
3133 else {
3134 PyObject **dictptr;
3135 PyErr_Clear();
3136 state = Py_None;
3137 dictptr = _PyObject_GetDictPtr(self);
3138 if (dictptr && *dictptr && PyDict_Size(*dictptr))
3139 state = *dictptr;
3140 Py_INCREF(state);
3141 }
Guido van Rossum177e41a2003-01-30 22:06:23 +00003142
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003143 Py_DECREF(tmp);
Guido van Rossum177e41a2003-01-30 22:06:23 +00003144
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003145 if (state == Py_None) {
3146 Py_DECREF(state);
3147 return Py_BuildValue("(ON)", Py_TYPE(self), args);
3148 }
3149 else
3150 return Py_BuildValue("(ONN)", Py_TYPE(self), args, state);
Guido van Rossum177e41a2003-01-30 22:06:23 +00003151}
Tim Peters2a799bf2002-12-16 20:18:38 +00003152
3153static PyMethodDef tzinfo_methods[] = {
Guido van Rossum177e41a2003-01-30 22:06:23 +00003154
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003155 {"tzname", (PyCFunction)tzinfo_tzname, METH_O,
3156 PyDoc_STR("datetime -> string name of time zone.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00003157
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003158 {"utcoffset", (PyCFunction)tzinfo_utcoffset, METH_O,
Sean Reifscheiderdeda8cb2010-06-04 01:51:38 +00003159 PyDoc_STR("datetime -> timedelta showing offset from UTC, negative "
3160 "values indicating West of UTC")},
Tim Peters2a799bf2002-12-16 20:18:38 +00003161
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003162 {"dst", (PyCFunction)tzinfo_dst, METH_O,
3163 PyDoc_STR("datetime -> DST offset in minutes east of UTC.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00003164
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003165 {"fromutc", (PyCFunction)tzinfo_fromutc, METH_O,
Alexander Belopolsky2f194b92010-07-03 03:35:27 +00003166 PyDoc_STR("datetime in UTC -> datetime in local time.")},
Tim Peters52dcce22003-01-23 16:36:11 +00003167
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003168 {"__reduce__", (PyCFunction)tzinfo_reduce, METH_NOARGS,
3169 PyDoc_STR("-> (cls, state)")},
Guido van Rossum177e41a2003-01-30 22:06:23 +00003170
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003171 {NULL, NULL}
Tim Peters2a799bf2002-12-16 20:18:38 +00003172};
3173
3174static char tzinfo_doc[] =
3175PyDoc_STR("Abstract base class for time zone info objects.");
3176
Neal Norwitz227b5332006-03-22 09:28:35 +00003177static PyTypeObject PyDateTime_TZInfoType = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003178 PyVarObject_HEAD_INIT(NULL, 0)
3179 "datetime.tzinfo", /* tp_name */
3180 sizeof(PyDateTime_TZInfo), /* tp_basicsize */
3181 0, /* tp_itemsize */
3182 0, /* tp_dealloc */
3183 0, /* tp_print */
3184 0, /* tp_getattr */
3185 0, /* tp_setattr */
3186 0, /* tp_reserved */
3187 0, /* tp_repr */
3188 0, /* tp_as_number */
3189 0, /* tp_as_sequence */
3190 0, /* tp_as_mapping */
3191 0, /* tp_hash */
3192 0, /* tp_call */
3193 0, /* tp_str */
3194 PyObject_GenericGetAttr, /* tp_getattro */
3195 0, /* tp_setattro */
3196 0, /* tp_as_buffer */
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003197 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003198 tzinfo_doc, /* tp_doc */
3199 0, /* tp_traverse */
3200 0, /* tp_clear */
3201 0, /* tp_richcompare */
3202 0, /* tp_weaklistoffset */
3203 0, /* tp_iter */
3204 0, /* tp_iternext */
3205 tzinfo_methods, /* tp_methods */
3206 0, /* tp_members */
3207 0, /* tp_getset */
3208 0, /* tp_base */
3209 0, /* tp_dict */
3210 0, /* tp_descr_get */
3211 0, /* tp_descr_set */
3212 0, /* tp_dictoffset */
3213 0, /* tp_init */
3214 0, /* tp_alloc */
3215 PyType_GenericNew, /* tp_new */
3216 0, /* tp_free */
Tim Peters2a799bf2002-12-16 20:18:38 +00003217};
3218
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003219static char *timezone_kws[] = {"offset", "name", NULL};
3220
3221static PyObject *
3222timezone_new(PyTypeObject *type, PyObject *args, PyObject *kw)
3223{
3224 PyObject *offset;
3225 PyObject *name = NULL;
3226 if (PyArg_ParseTupleAndKeywords(args, kw, "O!|O!:timezone", timezone_kws,
3227 &PyDateTime_DeltaType, &offset,
3228 &PyUnicode_Type, &name))
3229 return new_timezone(offset, name);
3230
3231 return NULL;
3232}
3233
3234static void
3235timezone_dealloc(PyDateTime_TimeZone *self)
3236{
3237 Py_CLEAR(self->offset);
3238 Py_CLEAR(self->name);
3239 Py_TYPE(self)->tp_free((PyObject *)self);
3240}
3241
3242static PyObject *
3243timezone_richcompare(PyDateTime_TimeZone *self,
3244 PyDateTime_TimeZone *other, int op)
3245{
Alexander Belopolsky57caede2012-09-20 17:23:46 -04003246 if (op != Py_EQ && op != Py_NE) {
3247 Py_INCREF(Py_NotImplemented);
3248 return Py_NotImplemented;
3249 }
Alexander Belopolsky3ec15362012-09-20 16:39:33 -04003250 if (Py_TYPE(other) != &PyDateTime_TimeZoneType) {
3251 if (op == Py_EQ)
3252 Py_RETURN_FALSE;
3253 else
3254 Py_RETURN_TRUE;
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003255 }
3256 return delta_richcompare(self->offset, other->offset, op);
3257}
3258
Benjamin Peterson8f67d082010-10-17 20:54:53 +00003259static Py_hash_t
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003260timezone_hash(PyDateTime_TimeZone *self)
3261{
3262 return delta_hash((PyDateTime_Delta *)self->offset);
3263}
3264
3265/* Check argument type passed to tzname, utcoffset, or dst methods.
3266 Returns 0 for good argument. Returns -1 and sets exception info
3267 otherwise.
3268 */
3269static int
3270_timezone_check_argument(PyObject *dt, const char *meth)
3271{
3272 if (dt == Py_None || PyDateTime_Check(dt))
3273 return 0;
3274 PyErr_Format(PyExc_TypeError, "%s(dt) argument must be a datetime instance"
3275 " or None, not %.200s", meth, Py_TYPE(dt)->tp_name);
3276 return -1;
3277}
3278
3279static PyObject *
Alexander Belopolskya11d8c02010-07-06 23:19:45 +00003280timezone_repr(PyDateTime_TimeZone *self)
3281{
3282 /* Note that although timezone is not subclassable, it is convenient
3283 to use Py_TYPE(self)->tp_name here. */
3284 const char *type_name = Py_TYPE(self)->tp_name;
3285
3286 if (((PyObject *)self) == PyDateTime_TimeZone_UTC)
3287 return PyUnicode_FromFormat("%s.utc", type_name);
3288
3289 if (self->name == NULL)
3290 return PyUnicode_FromFormat("%s(%R)", type_name, self->offset);
3291
3292 return PyUnicode_FromFormat("%s(%R, %R)", type_name, self->offset,
3293 self->name);
3294}
3295
3296
3297static PyObject *
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003298timezone_str(PyDateTime_TimeZone *self)
3299{
3300 char buf[10];
3301 int hours, minutes, seconds;
3302 PyObject *offset;
3303 char sign;
3304
3305 if (self->name != NULL) {
3306 Py_INCREF(self->name);
3307 return self->name;
3308 }
3309 /* Offset is normalized, so it is negative if days < 0 */
3310 if (GET_TD_DAYS(self->offset) < 0) {
3311 sign = '-';
3312 offset = delta_negative((PyDateTime_Delta *)self->offset);
3313 if (offset == NULL)
3314 return NULL;
3315 }
3316 else {
3317 sign = '+';
3318 offset = self->offset;
3319 Py_INCREF(offset);
3320 }
3321 /* Offset is not negative here. */
3322 seconds = GET_TD_SECONDS(offset);
3323 Py_DECREF(offset);
3324 minutes = divmod(seconds, 60, &seconds);
3325 hours = divmod(minutes, 60, &minutes);
3326 assert(seconds == 0);
3327 /* XXX ignore sub-minute data, curently not allowed. */
3328 PyOS_snprintf(buf, sizeof(buf), "UTC%c%02d:%02d", sign, hours, minutes);
3329
3330 return PyUnicode_FromString(buf);
3331}
3332
3333static PyObject *
3334timezone_tzname(PyDateTime_TimeZone *self, PyObject *dt)
3335{
3336 if (_timezone_check_argument(dt, "tzname") == -1)
3337 return NULL;
3338
3339 return timezone_str(self);
3340}
3341
3342static PyObject *
3343timezone_utcoffset(PyDateTime_TimeZone *self, PyObject *dt)
3344{
3345 if (_timezone_check_argument(dt, "utcoffset") == -1)
3346 return NULL;
3347
3348 Py_INCREF(self->offset);
3349 return self->offset;
3350}
3351
3352static PyObject *
3353timezone_dst(PyObject *self, PyObject *dt)
3354{
3355 if (_timezone_check_argument(dt, "dst") == -1)
3356 return NULL;
3357
3358 Py_RETURN_NONE;
3359}
3360
3361static PyObject *
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003362timezone_fromutc(PyDateTime_TimeZone *self, PyDateTime_DateTime *dt)
3363{
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003364 if (!PyDateTime_Check(dt)) {
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003365 PyErr_SetString(PyExc_TypeError,
3366 "fromutc: argument must be a datetime");
3367 return NULL;
3368 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003369 if (!HASTZINFO(dt) || dt->tzinfo != (PyObject *)self) {
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003370 PyErr_SetString(PyExc_ValueError, "fromutc: dt.tzinfo "
3371 "is not self");
3372 return NULL;
3373 }
3374
3375 return add_datetime_timedelta(dt, (PyDateTime_Delta *)self->offset, 1);
3376}
3377
Alexander Belopolsky1b7046b2010-06-23 21:40:15 +00003378static PyObject *
3379timezone_getinitargs(PyDateTime_TimeZone *self)
3380{
3381 if (self->name == NULL)
3382 return Py_BuildValue("(O)", self->offset);
3383 return Py_BuildValue("(OO)", self->offset, self->name);
3384}
3385
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003386static PyMethodDef timezone_methods[] = {
3387 {"tzname", (PyCFunction)timezone_tzname, METH_O,
3388 PyDoc_STR("If name is specified when timezone is created, returns the name."
Alexander Belopolskyb39a0c22010-06-15 19:24:52 +00003389 " Otherwise returns offset as 'UTC(+|-)HH:MM'.")},
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003390
3391 {"utcoffset", (PyCFunction)timezone_utcoffset, METH_O,
Alexander Belopolskyb39a0c22010-06-15 19:24:52 +00003392 PyDoc_STR("Return fixed offset.")},
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003393
3394 {"dst", (PyCFunction)timezone_dst, METH_O,
Alexander Belopolskyb39a0c22010-06-15 19:24:52 +00003395 PyDoc_STR("Return None.")},
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003396
3397 {"fromutc", (PyCFunction)timezone_fromutc, METH_O,
3398 PyDoc_STR("datetime in UTC -> datetime in local time.")},
3399
Alexander Belopolsky1b7046b2010-06-23 21:40:15 +00003400 {"__getinitargs__", (PyCFunction)timezone_getinitargs, METH_NOARGS,
3401 PyDoc_STR("pickle support")},
3402
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003403 {NULL, NULL}
3404};
3405
3406static char timezone_doc[] =
3407PyDoc_STR("Fixed offset from UTC implementation of tzinfo.");
3408
3409static PyTypeObject PyDateTime_TimeZoneType = {
3410 PyVarObject_HEAD_INIT(NULL, 0)
3411 "datetime.timezone", /* tp_name */
3412 sizeof(PyDateTime_TimeZone), /* tp_basicsize */
3413 0, /* tp_itemsize */
3414 (destructor)timezone_dealloc, /* tp_dealloc */
3415 0, /* tp_print */
3416 0, /* tp_getattr */
3417 0, /* tp_setattr */
3418 0, /* tp_reserved */
Alexander Belopolskya11d8c02010-07-06 23:19:45 +00003419 (reprfunc)timezone_repr, /* tp_repr */
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00003420 0, /* tp_as_number */
3421 0, /* tp_as_sequence */
3422 0, /* tp_as_mapping */
3423 (hashfunc)timezone_hash, /* tp_hash */
3424 0, /* tp_call */
3425 (reprfunc)timezone_str, /* tp_str */
3426 0, /* tp_getattro */
3427 0, /* tp_setattro */
3428 0, /* tp_as_buffer */
3429 Py_TPFLAGS_DEFAULT, /* tp_flags */
3430 timezone_doc, /* tp_doc */
3431 0, /* tp_traverse */
3432 0, /* tp_clear */
3433 (richcmpfunc)timezone_richcompare,/* tp_richcompare */
3434 0, /* tp_weaklistoffset */
3435 0, /* tp_iter */
3436 0, /* tp_iternext */
3437 timezone_methods, /* tp_methods */
3438 0, /* tp_members */
3439 0, /* tp_getset */
3440 &PyDateTime_TZInfoType, /* tp_base */
3441 0, /* tp_dict */
3442 0, /* tp_descr_get */
3443 0, /* tp_descr_set */
3444 0, /* tp_dictoffset */
3445 0, /* tp_init */
3446 0, /* tp_alloc */
3447 timezone_new, /* tp_new */
3448};
3449
Tim Peters2a799bf2002-12-16 20:18:38 +00003450/*
Tim Peters37f39822003-01-10 03:49:02 +00003451 * PyDateTime_Time implementation.
Tim Peters2a799bf2002-12-16 20:18:38 +00003452 */
3453
Tim Peters37f39822003-01-10 03:49:02 +00003454/* Accessor properties.
Tim Peters2a799bf2002-12-16 20:18:38 +00003455 */
3456
3457static PyObject *
Tim Peters37f39822003-01-10 03:49:02 +00003458time_hour(PyDateTime_Time *self, void *unused)
Tim Peters2a799bf2002-12-16 20:18:38 +00003459{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003460 return PyLong_FromLong(TIME_GET_HOUR(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00003461}
3462
Tim Peters37f39822003-01-10 03:49:02 +00003463static PyObject *
3464time_minute(PyDateTime_Time *self, void *unused)
3465{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003466 return PyLong_FromLong(TIME_GET_MINUTE(self));
Tim Peters37f39822003-01-10 03:49:02 +00003467}
3468
3469/* The name time_second conflicted with some platform header file. */
3470static PyObject *
3471py_time_second(PyDateTime_Time *self, void *unused)
3472{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003473 return PyLong_FromLong(TIME_GET_SECOND(self));
Tim Peters37f39822003-01-10 03:49:02 +00003474}
3475
3476static PyObject *
3477time_microsecond(PyDateTime_Time *self, void *unused)
3478{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003479 return PyLong_FromLong(TIME_GET_MICROSECOND(self));
Tim Peters37f39822003-01-10 03:49:02 +00003480}
3481
3482static PyObject *
3483time_tzinfo(PyDateTime_Time *self, void *unused)
3484{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003485 PyObject *result = HASTZINFO(self) ? self->tzinfo : Py_None;
3486 Py_INCREF(result);
3487 return result;
Tim Peters37f39822003-01-10 03:49:02 +00003488}
3489
3490static PyGetSetDef time_getset[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003491 {"hour", (getter)time_hour},
3492 {"minute", (getter)time_minute},
3493 {"second", (getter)py_time_second},
3494 {"microsecond", (getter)time_microsecond},
3495 {"tzinfo", (getter)time_tzinfo},
3496 {NULL}
Tim Peters2a799bf2002-12-16 20:18:38 +00003497};
3498
3499/*
3500 * Constructors.
3501 */
3502
Martin v. Löwis02cbf4a2006-02-27 17:20:04 +00003503static char *time_kws[] = {"hour", "minute", "second", "microsecond",
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003504 "tzinfo", NULL};
Tim Peters12bf3392002-12-24 05:41:27 +00003505
Tim Peters2a799bf2002-12-16 20:18:38 +00003506static PyObject *
Tim Peters37f39822003-01-10 03:49:02 +00003507time_new(PyTypeObject *type, PyObject *args, PyObject *kw)
Tim Peters2a799bf2002-12-16 20:18:38 +00003508{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003509 PyObject *self = NULL;
3510 PyObject *state;
3511 int hour = 0;
3512 int minute = 0;
3513 int second = 0;
3514 int usecond = 0;
3515 PyObject *tzinfo = Py_None;
Tim Peters2a799bf2002-12-16 20:18:38 +00003516
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003517 /* Check for invocation from pickle with __getstate__ state */
3518 if (PyTuple_GET_SIZE(args) >= 1 &&
3519 PyTuple_GET_SIZE(args) <= 2 &&
3520 PyBytes_Check(state = PyTuple_GET_ITEM(args, 0)) &&
3521 PyBytes_GET_SIZE(state) == _PyDateTime_TIME_DATASIZE &&
3522 ((unsigned char) (PyBytes_AS_STRING(state)[0])) < 24)
3523 {
3524 PyDateTime_Time *me;
3525 char aware;
Tim Peters70533e22003-02-01 04:40:04 +00003526
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003527 if (PyTuple_GET_SIZE(args) == 2) {
3528 tzinfo = PyTuple_GET_ITEM(args, 1);
3529 if (check_tzinfo_subclass(tzinfo) < 0) {
3530 PyErr_SetString(PyExc_TypeError, "bad "
3531 "tzinfo state arg");
3532 return NULL;
3533 }
3534 }
3535 aware = (char)(tzinfo != Py_None);
3536 me = (PyDateTime_Time *) (type->tp_alloc(type, aware));
3537 if (me != NULL) {
3538 char *pdata = PyBytes_AS_STRING(state);
Tim Peters70533e22003-02-01 04:40:04 +00003539
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003540 memcpy(me->data, pdata, _PyDateTime_TIME_DATASIZE);
3541 me->hashcode = -1;
3542 me->hastzinfo = aware;
3543 if (aware) {
3544 Py_INCREF(tzinfo);
3545 me->tzinfo = tzinfo;
3546 }
3547 }
3548 return (PyObject *)me;
3549 }
Guido van Rossum177e41a2003-01-30 22:06:23 +00003550
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003551 if (PyArg_ParseTupleAndKeywords(args, kw, "|iiiiO", time_kws,
3552 &hour, &minute, &second, &usecond,
3553 &tzinfo)) {
3554 if (check_time_args(hour, minute, second, usecond) < 0)
3555 return NULL;
3556 if (check_tzinfo_subclass(tzinfo) < 0)
3557 return NULL;
3558 self = new_time_ex(hour, minute, second, usecond, tzinfo,
3559 type);
3560 }
3561 return self;
Tim Peters2a799bf2002-12-16 20:18:38 +00003562}
3563
3564/*
3565 * Destructor.
3566 */
3567
3568static void
Tim Peters37f39822003-01-10 03:49:02 +00003569time_dealloc(PyDateTime_Time *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00003570{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003571 if (HASTZINFO(self)) {
3572 Py_XDECREF(self->tzinfo);
3573 }
3574 Py_TYPE(self)->tp_free((PyObject *)self);
Tim Peters2a799bf2002-12-16 20:18:38 +00003575}
3576
3577/*
Tim Peters855fe882002-12-22 03:43:39 +00003578 * Indirect access to tzinfo methods.
Tim Peters2a799bf2002-12-16 20:18:38 +00003579 */
3580
Tim Peters2a799bf2002-12-16 20:18:38 +00003581/* These are all METH_NOARGS, so don't need to check the arglist. */
3582static PyObject *
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003583time_utcoffset(PyObject *self, PyObject *unused) {
3584 return call_utcoffset(GET_TIME_TZINFO(self), Py_None);
Tim Peters2a799bf2002-12-16 20:18:38 +00003585}
3586
3587static PyObject *
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003588time_dst(PyObject *self, PyObject *unused) {
3589 return call_dst(GET_TIME_TZINFO(self), Py_None);
Tim Peters855fe882002-12-22 03:43:39 +00003590}
3591
3592static PyObject *
Tim Peters37f39822003-01-10 03:49:02 +00003593time_tzname(PyDateTime_Time *self, PyObject *unused) {
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003594 return call_tzname(GET_TIME_TZINFO(self), Py_None);
Tim Peters2a799bf2002-12-16 20:18:38 +00003595}
3596
3597/*
Tim Peters37f39822003-01-10 03:49:02 +00003598 * Various ways to turn a time into a string.
Tim Peters2a799bf2002-12-16 20:18:38 +00003599 */
3600
3601static PyObject *
Tim Peters37f39822003-01-10 03:49:02 +00003602time_repr(PyDateTime_Time *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00003603{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003604 const char *type_name = Py_TYPE(self)->tp_name;
3605 int h = TIME_GET_HOUR(self);
3606 int m = TIME_GET_MINUTE(self);
3607 int s = TIME_GET_SECOND(self);
3608 int us = TIME_GET_MICROSECOND(self);
3609 PyObject *result = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00003610
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003611 if (us)
3612 result = PyUnicode_FromFormat("%s(%d, %d, %d, %d)",
3613 type_name, h, m, s, us);
3614 else if (s)
3615 result = PyUnicode_FromFormat("%s(%d, %d, %d)",
3616 type_name, h, m, s);
3617 else
3618 result = PyUnicode_FromFormat("%s(%d, %d)", type_name, h, m);
3619 if (result != NULL && HASTZINFO(self))
3620 result = append_keyword_tzinfo(result, self->tzinfo);
3621 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00003622}
3623
Tim Peters37f39822003-01-10 03:49:02 +00003624static PyObject *
3625time_str(PyDateTime_Time *self)
3626{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003627 return PyObject_CallMethod((PyObject *)self, "isoformat", "()");
Tim Peters37f39822003-01-10 03:49:02 +00003628}
Tim Peters2a799bf2002-12-16 20:18:38 +00003629
3630static PyObject *
Thomas Wouterscf297e42007-02-23 15:07:44 +00003631time_isoformat(PyDateTime_Time *self, PyObject *unused)
Tim Peters2a799bf2002-12-16 20:18:38 +00003632{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003633 char buf[100];
3634 PyObject *result;
3635 int us = TIME_GET_MICROSECOND(self);;
Tim Peters2a799bf2002-12-16 20:18:38 +00003636
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003637 if (us)
3638 result = PyUnicode_FromFormat("%02d:%02d:%02d.%06d",
3639 TIME_GET_HOUR(self),
3640 TIME_GET_MINUTE(self),
3641 TIME_GET_SECOND(self),
3642 us);
3643 else
3644 result = PyUnicode_FromFormat("%02d:%02d:%02d",
3645 TIME_GET_HOUR(self),
3646 TIME_GET_MINUTE(self),
3647 TIME_GET_SECOND(self));
Tim Peters37f39822003-01-10 03:49:02 +00003648
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003649 if (result == NULL || !HASTZINFO(self) || self->tzinfo == Py_None)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003650 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00003651
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003652 /* We need to append the UTC offset. */
3653 if (format_utcoffset(buf, sizeof(buf), ":", self->tzinfo,
3654 Py_None) < 0) {
3655 Py_DECREF(result);
3656 return NULL;
3657 }
3658 PyUnicode_AppendAndDel(&result, PyUnicode_FromString(buf));
3659 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00003660}
3661
Tim Peters37f39822003-01-10 03:49:02 +00003662static PyObject *
3663time_strftime(PyDateTime_Time *self, PyObject *args, PyObject *kw)
3664{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003665 PyObject *result;
3666 PyObject *tuple;
3667 PyObject *format;
3668 static char *keywords[] = {"format", NULL};
Tim Peters37f39822003-01-10 03:49:02 +00003669
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003670 if (! PyArg_ParseTupleAndKeywords(args, kw, "U:strftime", keywords,
3671 &format))
3672 return NULL;
Tim Peters37f39822003-01-10 03:49:02 +00003673
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003674 /* Python's strftime does insane things with the year part of the
3675 * timetuple. The year is forced to (the otherwise nonsensical)
Alexander Belopolskyb8bb4662011-01-08 00:13:34 +00003676 * 1900 to work around that.
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003677 */
3678 tuple = Py_BuildValue("iiiiiiiii",
3679 1900, 1, 1, /* year, month, day */
3680 TIME_GET_HOUR(self),
3681 TIME_GET_MINUTE(self),
3682 TIME_GET_SECOND(self),
3683 0, 1, -1); /* weekday, daynum, dst */
3684 if (tuple == NULL)
3685 return NULL;
3686 assert(PyTuple_Size(tuple) == 9);
3687 result = wrap_strftime((PyObject *)self, format, tuple,
3688 Py_None);
3689 Py_DECREF(tuple);
3690 return result;
Tim Peters37f39822003-01-10 03:49:02 +00003691}
Tim Peters2a799bf2002-12-16 20:18:38 +00003692
3693/*
3694 * Miscellaneous methods.
3695 */
3696
Tim Peters37f39822003-01-10 03:49:02 +00003697static PyObject *
Guido van Rossum19960592006-08-24 17:29:38 +00003698time_richcompare(PyObject *self, PyObject *other, int op)
Tim Peters37f39822003-01-10 03:49:02 +00003699{
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003700 PyObject *result = NULL;
3701 PyObject *offset1, *offset2;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003702 int diff;
Tim Peters37f39822003-01-10 03:49:02 +00003703
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003704 if (! PyTime_Check(other)) {
3705 Py_INCREF(Py_NotImplemented);
3706 return Py_NotImplemented;
3707 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003708
3709 if (GET_TIME_TZINFO(self) == GET_TIME_TZINFO(other)) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003710 diff = memcmp(((PyDateTime_Time *)self)->data,
3711 ((PyDateTime_Time *)other)->data,
3712 _PyDateTime_TIME_DATASIZE);
3713 return diff_to_bool(diff, op);
3714 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003715 offset1 = time_utcoffset(self, NULL);
3716 if (offset1 == NULL)
3717 return NULL;
3718 offset2 = time_utcoffset(other, NULL);
3719 if (offset2 == NULL)
3720 goto done;
3721 /* If they're both naive, or both aware and have the same offsets,
3722 * we get off cheap. Note that if they're both naive, offset1 ==
3723 * offset2 == Py_None at this point.
3724 */
3725 if ((offset1 == offset2) ||
3726 (PyDelta_Check(offset1) && PyDelta_Check(offset2) &&
3727 delta_cmp(offset1, offset2) == 0)) {
3728 diff = memcmp(((PyDateTime_Time *)self)->data,
3729 ((PyDateTime_Time *)other)->data,
3730 _PyDateTime_TIME_DATASIZE);
3731 result = diff_to_bool(diff, op);
3732 }
3733 /* The hard case: both aware with different UTC offsets */
3734 else if (offset1 != Py_None && offset2 != Py_None) {
3735 int offsecs1, offsecs2;
3736 assert(offset1 != offset2); /* else last "if" handled it */
3737 offsecs1 = TIME_GET_HOUR(self) * 3600 +
3738 TIME_GET_MINUTE(self) * 60 +
3739 TIME_GET_SECOND(self) -
3740 GET_TD_DAYS(offset1) * 86400 -
3741 GET_TD_SECONDS(offset1);
3742 offsecs2 = TIME_GET_HOUR(other) * 3600 +
3743 TIME_GET_MINUTE(other) * 60 +
3744 TIME_GET_SECOND(other) -
3745 GET_TD_DAYS(offset2) * 86400 -
3746 GET_TD_SECONDS(offset2);
3747 diff = offsecs1 - offsecs2;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003748 if (diff == 0)
3749 diff = TIME_GET_MICROSECOND(self) -
3750 TIME_GET_MICROSECOND(other);
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003751 result = diff_to_bool(diff, op);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003752 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003753 else {
3754 PyErr_SetString(PyExc_TypeError,
3755 "can't compare offset-naive and "
3756 "offset-aware times");
3757 }
3758 done:
3759 Py_DECREF(offset1);
3760 Py_XDECREF(offset2);
3761 return result;
Tim Peters37f39822003-01-10 03:49:02 +00003762}
3763
Benjamin Peterson8f67d082010-10-17 20:54:53 +00003764static Py_hash_t
Tim Peters37f39822003-01-10 03:49:02 +00003765time_hash(PyDateTime_Time *self)
3766{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003767 if (self->hashcode == -1) {
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003768 PyObject *offset;
Tim Peters37f39822003-01-10 03:49:02 +00003769
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003770 offset = time_utcoffset((PyObject *)self, NULL);
3771
3772 if (offset == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003773 return -1;
Tim Peters37f39822003-01-10 03:49:02 +00003774
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003775 /* Reduce this to a hash of another object. */
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003776 if (offset == Py_None)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003777 self->hashcode = generic_hash(
3778 (unsigned char *)self->data, _PyDateTime_TIME_DATASIZE);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003779 else {
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003780 PyObject *temp1, *temp2;
3781 int seconds, microseconds;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003782 assert(HASTZINFO(self));
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003783 seconds = TIME_GET_HOUR(self) * 3600 +
3784 TIME_GET_MINUTE(self) * 60 +
3785 TIME_GET_SECOND(self);
3786 microseconds = TIME_GET_MICROSECOND(self);
3787 temp1 = new_delta(0, seconds, microseconds, 1);
3788 if (temp1 == NULL) {
3789 Py_DECREF(offset);
3790 return -1;
3791 }
3792 temp2 = delta_subtract(temp1, offset);
3793 Py_DECREF(temp1);
3794 if (temp2 == NULL) {
3795 Py_DECREF(offset);
3796 return -1;
3797 }
3798 self->hashcode = PyObject_Hash(temp2);
3799 Py_DECREF(temp2);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003800 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003801 Py_DECREF(offset);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003802 }
3803 return self->hashcode;
Tim Peters37f39822003-01-10 03:49:02 +00003804}
Tim Peters2a799bf2002-12-16 20:18:38 +00003805
Tim Peters12bf3392002-12-24 05:41:27 +00003806static PyObject *
Tim Peters37f39822003-01-10 03:49:02 +00003807time_replace(PyDateTime_Time *self, PyObject *args, PyObject *kw)
Tim Peters12bf3392002-12-24 05:41:27 +00003808{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003809 PyObject *clone;
3810 PyObject *tuple;
3811 int hh = TIME_GET_HOUR(self);
3812 int mm = TIME_GET_MINUTE(self);
3813 int ss = TIME_GET_SECOND(self);
3814 int us = TIME_GET_MICROSECOND(self);
3815 PyObject *tzinfo = HASTZINFO(self) ? self->tzinfo : Py_None;
Tim Peters12bf3392002-12-24 05:41:27 +00003816
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003817 if (! PyArg_ParseTupleAndKeywords(args, kw, "|iiiiO:replace",
3818 time_kws,
3819 &hh, &mm, &ss, &us, &tzinfo))
3820 return NULL;
3821 tuple = Py_BuildValue("iiiiO", hh, mm, ss, us, tzinfo);
3822 if (tuple == NULL)
3823 return NULL;
3824 clone = time_new(Py_TYPE(self), tuple, NULL);
3825 Py_DECREF(tuple);
3826 return clone;
Tim Peters12bf3392002-12-24 05:41:27 +00003827}
3828
Tim Peters2a799bf2002-12-16 20:18:38 +00003829static int
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003830time_bool(PyObject *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00003831{
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003832 PyObject *offset, *tzinfo;
3833 int offsecs = 0;
Tim Peters2a799bf2002-12-16 20:18:38 +00003834
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003835 if (TIME_GET_SECOND(self) || TIME_GET_MICROSECOND(self)) {
3836 /* Since utcoffset is in whole minutes, nothing can
3837 * alter the conclusion that this is nonzero.
3838 */
3839 return 1;
3840 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003841 tzinfo = GET_TIME_TZINFO(self);
3842 if (tzinfo != Py_None) {
3843 offset = call_utcoffset(tzinfo, Py_None);
3844 if (offset == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003845 return -1;
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003846 offsecs = GET_TD_DAYS(offset)*86400 + GET_TD_SECONDS(offset);
3847 Py_DECREF(offset);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003848 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00003849 return (TIME_GET_MINUTE(self)*60 - offsecs + TIME_GET_HOUR(self)*3600) != 0;
Tim Peters2a799bf2002-12-16 20:18:38 +00003850}
3851
Tim Peters371935f2003-02-01 01:52:50 +00003852/* Pickle support, a simple use of __reduce__. */
Tim Peters2a799bf2002-12-16 20:18:38 +00003853
Tim Peters33e0f382003-01-10 02:05:14 +00003854/* Let basestate be the non-tzinfo data string.
Tim Peters2a799bf2002-12-16 20:18:38 +00003855 * If tzinfo is None, this returns (basestate,), else (basestate, tzinfo).
3856 * So it's a tuple in any (non-error) case.
Tim Petersb57f8f02003-02-01 02:54:15 +00003857 * __getstate__ isn't exposed.
Tim Peters2a799bf2002-12-16 20:18:38 +00003858 */
3859static PyObject *
Tim Peters37f39822003-01-10 03:49:02 +00003860time_getstate(PyDateTime_Time *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00003861{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003862 PyObject *basestate;
3863 PyObject *result = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00003864
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003865 basestate = PyBytes_FromStringAndSize((char *)self->data,
3866 _PyDateTime_TIME_DATASIZE);
3867 if (basestate != NULL) {
3868 if (! HASTZINFO(self) || self->tzinfo == Py_None)
3869 result = PyTuple_Pack(1, basestate);
3870 else
3871 result = PyTuple_Pack(2, basestate, self->tzinfo);
3872 Py_DECREF(basestate);
3873 }
3874 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00003875}
3876
3877static PyObject *
Guido van Rossum177e41a2003-01-30 22:06:23 +00003878time_reduce(PyDateTime_Time *self, PyObject *arg)
Tim Peters2a799bf2002-12-16 20:18:38 +00003879{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003880 return Py_BuildValue("(ON)", Py_TYPE(self), time_getstate(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00003881}
3882
Tim Peters37f39822003-01-10 03:49:02 +00003883static PyMethodDef time_methods[] = {
Guido van Rossum177e41a2003-01-30 22:06:23 +00003884
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003885 {"isoformat", (PyCFunction)time_isoformat, METH_NOARGS,
3886 PyDoc_STR("Return string in ISO 8601 format, HH:MM:SS[.mmmmmm]"
3887 "[+HH:MM].")},
Tim Peters2a799bf2002-12-16 20:18:38 +00003888
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003889 {"strftime", (PyCFunction)time_strftime, METH_VARARGS | METH_KEYWORDS,
3890 PyDoc_STR("format -> strftime() style string.")},
Tim Peters37f39822003-01-10 03:49:02 +00003891
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003892 {"__format__", (PyCFunction)date_format, METH_VARARGS,
3893 PyDoc_STR("Formats self with strftime.")},
Eric Smith1ba31142007-09-11 18:06:02 +00003894
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003895 {"utcoffset", (PyCFunction)time_utcoffset, METH_NOARGS,
3896 PyDoc_STR("Return self.tzinfo.utcoffset(self).")},
Tim Peters2a799bf2002-12-16 20:18:38 +00003897
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003898 {"tzname", (PyCFunction)time_tzname, METH_NOARGS,
3899 PyDoc_STR("Return self.tzinfo.tzname(self).")},
Tim Peters2a799bf2002-12-16 20:18:38 +00003900
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003901 {"dst", (PyCFunction)time_dst, METH_NOARGS,
3902 PyDoc_STR("Return self.tzinfo.dst(self).")},
Tim Peters2a799bf2002-12-16 20:18:38 +00003903
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003904 {"replace", (PyCFunction)time_replace, METH_VARARGS | METH_KEYWORDS,
3905 PyDoc_STR("Return time with new specified fields.")},
Tim Peters12bf3392002-12-24 05:41:27 +00003906
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003907 {"__reduce__", (PyCFunction)time_reduce, METH_NOARGS,
3908 PyDoc_STR("__reduce__() -> (cls, state)")},
Guido van Rossum177e41a2003-01-30 22:06:23 +00003909
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003910 {NULL, NULL}
Tim Peters2a799bf2002-12-16 20:18:38 +00003911};
3912
Tim Peters37f39822003-01-10 03:49:02 +00003913static char time_doc[] =
Raymond Hettinger3a4231d2004-12-19 20:13:24 +00003914PyDoc_STR("time([hour[, minute[, second[, microsecond[, tzinfo]]]]]) --> a time object\n\
3915\n\
3916All arguments are optional. tzinfo may be None, or an instance of\n\
3917a tzinfo subclass. The remaining arguments may be ints or longs.\n");
Tim Peters2a799bf2002-12-16 20:18:38 +00003918
Tim Peters37f39822003-01-10 03:49:02 +00003919static PyNumberMethods time_as_number = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003920 0, /* nb_add */
3921 0, /* nb_subtract */
3922 0, /* nb_multiply */
3923 0, /* nb_remainder */
3924 0, /* nb_divmod */
3925 0, /* nb_power */
3926 0, /* nb_negative */
3927 0, /* nb_positive */
3928 0, /* nb_absolute */
3929 (inquiry)time_bool, /* nb_bool */
Tim Peters2a799bf2002-12-16 20:18:38 +00003930};
3931
Neal Norwitz227b5332006-03-22 09:28:35 +00003932static PyTypeObject PyDateTime_TimeType = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003933 PyVarObject_HEAD_INIT(NULL, 0)
3934 "datetime.time", /* tp_name */
3935 sizeof(PyDateTime_Time), /* tp_basicsize */
3936 0, /* tp_itemsize */
3937 (destructor)time_dealloc, /* tp_dealloc */
3938 0, /* tp_print */
3939 0, /* tp_getattr */
3940 0, /* tp_setattr */
3941 0, /* tp_reserved */
3942 (reprfunc)time_repr, /* tp_repr */
3943 &time_as_number, /* tp_as_number */
3944 0, /* tp_as_sequence */
3945 0, /* tp_as_mapping */
3946 (hashfunc)time_hash, /* tp_hash */
3947 0, /* tp_call */
3948 (reprfunc)time_str, /* tp_str */
3949 PyObject_GenericGetAttr, /* tp_getattro */
3950 0, /* tp_setattro */
3951 0, /* tp_as_buffer */
3952 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
3953 time_doc, /* tp_doc */
3954 0, /* tp_traverse */
3955 0, /* tp_clear */
3956 time_richcompare, /* tp_richcompare */
3957 0, /* tp_weaklistoffset */
3958 0, /* tp_iter */
3959 0, /* tp_iternext */
3960 time_methods, /* tp_methods */
3961 0, /* tp_members */
3962 time_getset, /* tp_getset */
3963 0, /* tp_base */
3964 0, /* tp_dict */
3965 0, /* tp_descr_get */
3966 0, /* tp_descr_set */
3967 0, /* tp_dictoffset */
3968 0, /* tp_init */
3969 time_alloc, /* tp_alloc */
3970 time_new, /* tp_new */
3971 0, /* tp_free */
Tim Peters2a799bf2002-12-16 20:18:38 +00003972};
3973
3974/*
Tim Petersa9bc1682003-01-11 03:39:11 +00003975 * PyDateTime_DateTime implementation.
Tim Peters2a799bf2002-12-16 20:18:38 +00003976 */
3977
Tim Petersa9bc1682003-01-11 03:39:11 +00003978/* Accessor properties. Properties for day, month, and year are inherited
3979 * from date.
Tim Peters2a799bf2002-12-16 20:18:38 +00003980 */
3981
3982static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00003983datetime_hour(PyDateTime_DateTime *self, void *unused)
Tim Peters2a799bf2002-12-16 20:18:38 +00003984{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003985 return PyLong_FromLong(DATE_GET_HOUR(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00003986}
3987
Tim Petersa9bc1682003-01-11 03:39:11 +00003988static PyObject *
3989datetime_minute(PyDateTime_DateTime *self, void *unused)
3990{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003991 return PyLong_FromLong(DATE_GET_MINUTE(self));
Tim Petersa9bc1682003-01-11 03:39:11 +00003992}
3993
3994static PyObject *
3995datetime_second(PyDateTime_DateTime *self, void *unused)
3996{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00003997 return PyLong_FromLong(DATE_GET_SECOND(self));
Tim Petersa9bc1682003-01-11 03:39:11 +00003998}
3999
4000static PyObject *
4001datetime_microsecond(PyDateTime_DateTime *self, void *unused)
4002{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004003 return PyLong_FromLong(DATE_GET_MICROSECOND(self));
Tim Petersa9bc1682003-01-11 03:39:11 +00004004}
4005
4006static PyObject *
4007datetime_tzinfo(PyDateTime_DateTime *self, void *unused)
4008{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004009 PyObject *result = HASTZINFO(self) ? self->tzinfo : Py_None;
4010 Py_INCREF(result);
4011 return result;
Tim Petersa9bc1682003-01-11 03:39:11 +00004012}
4013
4014static PyGetSetDef datetime_getset[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004015 {"hour", (getter)datetime_hour},
4016 {"minute", (getter)datetime_minute},
4017 {"second", (getter)datetime_second},
4018 {"microsecond", (getter)datetime_microsecond},
4019 {"tzinfo", (getter)datetime_tzinfo},
4020 {NULL}
Tim Peters2a799bf2002-12-16 20:18:38 +00004021};
4022
4023/*
4024 * Constructors.
Tim Peters2a799bf2002-12-16 20:18:38 +00004025 */
4026
Martin v. Löwis02cbf4a2006-02-27 17:20:04 +00004027static char *datetime_kws[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004028 "year", "month", "day", "hour", "minute", "second",
4029 "microsecond", "tzinfo", NULL
Tim Peters12bf3392002-12-24 05:41:27 +00004030};
4031
Tim Peters2a799bf2002-12-16 20:18:38 +00004032static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004033datetime_new(PyTypeObject *type, PyObject *args, PyObject *kw)
Tim Peters2a799bf2002-12-16 20:18:38 +00004034{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004035 PyObject *self = NULL;
4036 PyObject *state;
4037 int year;
4038 int month;
4039 int day;
4040 int hour = 0;
4041 int minute = 0;
4042 int second = 0;
4043 int usecond = 0;
4044 PyObject *tzinfo = Py_None;
Tim Peters2a799bf2002-12-16 20:18:38 +00004045
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004046 /* Check for invocation from pickle with __getstate__ state */
4047 if (PyTuple_GET_SIZE(args) >= 1 &&
4048 PyTuple_GET_SIZE(args) <= 2 &&
4049 PyBytes_Check(state = PyTuple_GET_ITEM(args, 0)) &&
4050 PyBytes_GET_SIZE(state) == _PyDateTime_DATETIME_DATASIZE &&
4051 MONTH_IS_SANE(PyBytes_AS_STRING(state)[2]))
4052 {
4053 PyDateTime_DateTime *me;
4054 char aware;
Tim Peters70533e22003-02-01 04:40:04 +00004055
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004056 if (PyTuple_GET_SIZE(args) == 2) {
4057 tzinfo = PyTuple_GET_ITEM(args, 1);
4058 if (check_tzinfo_subclass(tzinfo) < 0) {
4059 PyErr_SetString(PyExc_TypeError, "bad "
4060 "tzinfo state arg");
4061 return NULL;
4062 }
4063 }
4064 aware = (char)(tzinfo != Py_None);
4065 me = (PyDateTime_DateTime *) (type->tp_alloc(type , aware));
4066 if (me != NULL) {
4067 char *pdata = PyBytes_AS_STRING(state);
Tim Peters70533e22003-02-01 04:40:04 +00004068
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004069 memcpy(me->data, pdata, _PyDateTime_DATETIME_DATASIZE);
4070 me->hashcode = -1;
4071 me->hastzinfo = aware;
4072 if (aware) {
4073 Py_INCREF(tzinfo);
4074 me->tzinfo = tzinfo;
4075 }
4076 }
4077 return (PyObject *)me;
4078 }
Guido van Rossum177e41a2003-01-30 22:06:23 +00004079
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004080 if (PyArg_ParseTupleAndKeywords(args, kw, "iii|iiiiO", datetime_kws,
4081 &year, &month, &day, &hour, &minute,
4082 &second, &usecond, &tzinfo)) {
4083 if (check_date_args(year, month, day) < 0)
4084 return NULL;
4085 if (check_time_args(hour, minute, second, usecond) < 0)
4086 return NULL;
4087 if (check_tzinfo_subclass(tzinfo) < 0)
4088 return NULL;
4089 self = new_datetime_ex(year, month, day,
4090 hour, minute, second, usecond,
4091 tzinfo, type);
4092 }
4093 return self;
Tim Peters2a799bf2002-12-16 20:18:38 +00004094}
4095
Tim Petersa9bc1682003-01-11 03:39:11 +00004096/* TM_FUNC is the shared type of localtime() and gmtime(). */
4097typedef struct tm *(*TM_FUNC)(const time_t *timer);
4098
4099/* Internal helper.
4100 * Build datetime from a time_t and a distinct count of microseconds.
4101 * Pass localtime or gmtime for f, to control the interpretation of timet.
4102 */
4103static PyObject *
4104datetime_from_timet_and_us(PyObject *cls, TM_FUNC f, time_t timet, int us,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004105 PyObject *tzinfo)
Tim Petersa9bc1682003-01-11 03:39:11 +00004106{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004107 struct tm *tm;
4108 PyObject *result = NULL;
Tim Petersa9bc1682003-01-11 03:39:11 +00004109
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004110 tm = f(&timet);
4111 if (tm) {
4112 /* The platform localtime/gmtime may insert leap seconds,
4113 * indicated by tm->tm_sec > 59. We don't care about them,
4114 * except to the extent that passing them on to the datetime
4115 * constructor would raise ValueError for a reason that
4116 * made no sense to the user.
4117 */
4118 if (tm->tm_sec > 59)
4119 tm->tm_sec = 59;
4120 result = PyObject_CallFunction(cls, "iiiiiiiO",
4121 tm->tm_year + 1900,
4122 tm->tm_mon + 1,
4123 tm->tm_mday,
4124 tm->tm_hour,
4125 tm->tm_min,
4126 tm->tm_sec,
4127 us,
4128 tzinfo);
4129 }
4130 else
4131 PyErr_SetString(PyExc_ValueError,
4132 "timestamp out of range for "
4133 "platform localtime()/gmtime() function");
4134 return result;
Tim Petersa9bc1682003-01-11 03:39:11 +00004135}
4136
4137/* Internal helper.
4138 * Build datetime from a Python timestamp. Pass localtime or gmtime for f,
4139 * to control the interpretation of the timestamp. Since a double doesn't
4140 * have enough bits to cover a datetime's full range of precision, it's
4141 * better to call datetime_from_timet_and_us provided you have a way
4142 * to get that much precision (e.g., C time() isn't good enough).
4143 */
4144static PyObject *
4145datetime_from_timestamp(PyObject *cls, TM_FUNC f, double timestamp,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004146 PyObject *tzinfo)
Tim Petersa9bc1682003-01-11 03:39:11 +00004147{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004148 time_t timet;
4149 double fraction;
4150 int us;
Tim Petersa9bc1682003-01-11 03:39:11 +00004151
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004152 timet = _PyTime_DoubleToTimet(timestamp);
4153 if (timet == (time_t)-1 && PyErr_Occurred())
4154 return NULL;
4155 fraction = timestamp - (double)timet;
4156 us = (int)round_to_long(fraction * 1e6);
4157 if (us < 0) {
4158 /* Truncation towards zero is not what we wanted
4159 for negative numbers (Python's mod semantics) */
4160 timet -= 1;
4161 us += 1000000;
4162 }
4163 /* If timestamp is less than one microsecond smaller than a
4164 * full second, round up. Otherwise, ValueErrors are raised
4165 * for some floats. */
4166 if (us == 1000000) {
4167 timet += 1;
4168 us = 0;
4169 }
4170 return datetime_from_timet_and_us(cls, f, timet, us, tzinfo);
Tim Petersa9bc1682003-01-11 03:39:11 +00004171}
4172
4173/* Internal helper.
4174 * Build most accurate possible datetime for current time. Pass localtime or
4175 * gmtime for f as appropriate.
4176 */
4177static PyObject *
4178datetime_best_possible(PyObject *cls, TM_FUNC f, PyObject *tzinfo)
4179{
Alexander Belopolsky6fc4ade2010-08-05 17:34:27 +00004180 _PyTime_timeval t;
4181 _PyTime_gettimeofday(&t);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004182 return datetime_from_timet_and_us(cls, f, t.tv_sec, (int)t.tv_usec,
4183 tzinfo);
Tim Petersa9bc1682003-01-11 03:39:11 +00004184}
4185
Tim Peters2a799bf2002-12-16 20:18:38 +00004186/* Return best possible local time -- this isn't constrained by the
4187 * precision of a timestamp.
4188 */
4189static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004190datetime_now(PyObject *cls, PyObject *args, PyObject *kw)
Tim Peters2a799bf2002-12-16 20:18:38 +00004191{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004192 PyObject *self;
4193 PyObject *tzinfo = Py_None;
4194 static char *keywords[] = {"tz", NULL};
Tim Peters2a799bf2002-12-16 20:18:38 +00004195
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004196 if (! PyArg_ParseTupleAndKeywords(args, kw, "|O:now", keywords,
4197 &tzinfo))
4198 return NULL;
4199 if (check_tzinfo_subclass(tzinfo) < 0)
4200 return NULL;
Tim Peters10cadce2003-01-23 19:58:02 +00004201
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004202 self = datetime_best_possible(cls,
4203 tzinfo == Py_None ? localtime : gmtime,
4204 tzinfo);
4205 if (self != NULL && tzinfo != Py_None) {
4206 /* Convert UTC to tzinfo's zone. */
4207 PyObject *temp = self;
4208 self = PyObject_CallMethod(tzinfo, "fromutc", "O", self);
4209 Py_DECREF(temp);
4210 }
4211 return self;
Tim Peters2a799bf2002-12-16 20:18:38 +00004212}
4213
Tim Petersa9bc1682003-01-11 03:39:11 +00004214/* Return best possible UTC time -- this isn't constrained by the
4215 * precision of a timestamp.
4216 */
4217static PyObject *
4218datetime_utcnow(PyObject *cls, PyObject *dummy)
4219{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004220 return datetime_best_possible(cls, gmtime, Py_None);
Tim Petersa9bc1682003-01-11 03:39:11 +00004221}
4222
Tim Peters2a799bf2002-12-16 20:18:38 +00004223/* Return new local datetime from timestamp (Python timestamp -- a double). */
4224static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004225datetime_fromtimestamp(PyObject *cls, PyObject *args, PyObject *kw)
Tim Peters2a799bf2002-12-16 20:18:38 +00004226{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004227 PyObject *self;
4228 double timestamp;
4229 PyObject *tzinfo = Py_None;
4230 static char *keywords[] = {"timestamp", "tz", NULL};
Tim Peters2a799bf2002-12-16 20:18:38 +00004231
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004232 if (! PyArg_ParseTupleAndKeywords(args, kw, "d|O:fromtimestamp",
4233 keywords, &timestamp, &tzinfo))
4234 return NULL;
4235 if (check_tzinfo_subclass(tzinfo) < 0)
4236 return NULL;
Tim Peters2a44a8d2003-01-23 20:53:10 +00004237
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004238 self = datetime_from_timestamp(cls,
4239 tzinfo == Py_None ? localtime : gmtime,
4240 timestamp,
4241 tzinfo);
4242 if (self != NULL && tzinfo != Py_None) {
4243 /* Convert UTC to tzinfo's zone. */
4244 PyObject *temp = self;
4245 self = PyObject_CallMethod(tzinfo, "fromutc", "O", self);
4246 Py_DECREF(temp);
4247 }
4248 return self;
Tim Peters2a799bf2002-12-16 20:18:38 +00004249}
4250
Tim Petersa9bc1682003-01-11 03:39:11 +00004251/* Return new UTC datetime from timestamp (Python timestamp -- a double). */
4252static PyObject *
4253datetime_utcfromtimestamp(PyObject *cls, PyObject *args)
4254{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004255 double timestamp;
4256 PyObject *result = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00004257
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004258 if (PyArg_ParseTuple(args, "d:utcfromtimestamp", &timestamp))
4259 result = datetime_from_timestamp(cls, gmtime, timestamp,
4260 Py_None);
4261 return result;
Tim Petersa9bc1682003-01-11 03:39:11 +00004262}
4263
Alexander Belopolskyca94f552010-06-17 18:30:34 +00004264/* Return new datetime from _strptime.strptime_datetime(). */
Skip Montanaro0af3ade2005-01-13 04:12:31 +00004265static PyObject *
4266datetime_strptime(PyObject *cls, PyObject *args)
4267{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004268 static PyObject *module = NULL;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004269 const Py_UNICODE *string, *format;
Skip Montanaro0af3ade2005-01-13 04:12:31 +00004270
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004271 if (!PyArg_ParseTuple(args, "uu:strptime", &string, &format))
4272 return NULL;
Skip Montanaro0af3ade2005-01-13 04:12:31 +00004273
Alexander Belopolskyca94f552010-06-17 18:30:34 +00004274 if (module == NULL) {
4275 module = PyImport_ImportModuleNoBlock("_strptime");
Alexander Belopolsky311d2a92010-06-28 14:36:55 +00004276 if (module == NULL)
Alexander Belopolskyca94f552010-06-17 18:30:34 +00004277 return NULL;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004278 }
Alexander Belopolskyf5682182010-06-18 18:44:37 +00004279 return PyObject_CallMethod(module, "_strptime_datetime", "Ouu",
4280 cls, string, format);
Skip Montanaro0af3ade2005-01-13 04:12:31 +00004281}
4282
Tim Petersa9bc1682003-01-11 03:39:11 +00004283/* Return new datetime from date/datetime and time arguments. */
4284static PyObject *
4285datetime_combine(PyObject *cls, PyObject *args, PyObject *kw)
4286{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004287 static char *keywords[] = {"date", "time", NULL};
4288 PyObject *date;
4289 PyObject *time;
4290 PyObject *result = NULL;
Tim Petersa9bc1682003-01-11 03:39:11 +00004291
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004292 if (PyArg_ParseTupleAndKeywords(args, kw, "O!O!:combine", keywords,
4293 &PyDateTime_DateType, &date,
4294 &PyDateTime_TimeType, &time)) {
4295 PyObject *tzinfo = Py_None;
Tim Petersa9bc1682003-01-11 03:39:11 +00004296
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004297 if (HASTZINFO(time))
4298 tzinfo = ((PyDateTime_Time *)time)->tzinfo;
4299 result = PyObject_CallFunction(cls, "iiiiiiiO",
4300 GET_YEAR(date),
4301 GET_MONTH(date),
4302 GET_DAY(date),
4303 TIME_GET_HOUR(time),
4304 TIME_GET_MINUTE(time),
4305 TIME_GET_SECOND(time),
4306 TIME_GET_MICROSECOND(time),
4307 tzinfo);
4308 }
4309 return result;
Tim Petersa9bc1682003-01-11 03:39:11 +00004310}
Tim Peters2a799bf2002-12-16 20:18:38 +00004311
4312/*
4313 * Destructor.
4314 */
4315
4316static void
Tim Petersa9bc1682003-01-11 03:39:11 +00004317datetime_dealloc(PyDateTime_DateTime *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00004318{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004319 if (HASTZINFO(self)) {
4320 Py_XDECREF(self->tzinfo);
4321 }
4322 Py_TYPE(self)->tp_free((PyObject *)self);
Tim Peters2a799bf2002-12-16 20:18:38 +00004323}
4324
4325/*
4326 * Indirect access to tzinfo methods.
4327 */
4328
Tim Peters2a799bf2002-12-16 20:18:38 +00004329/* These are all METH_NOARGS, so don't need to check the arglist. */
4330static PyObject *
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004331datetime_utcoffset(PyObject *self, PyObject *unused) {
4332 return call_utcoffset(GET_DT_TZINFO(self), self);
Tim Peters2a799bf2002-12-16 20:18:38 +00004333}
4334
4335static PyObject *
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004336datetime_dst(PyObject *self, PyObject *unused) {
4337 return call_dst(GET_DT_TZINFO(self), self);
Tim Peters855fe882002-12-22 03:43:39 +00004338}
4339
4340static PyObject *
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004341datetime_tzname(PyObject *self, PyObject *unused) {
4342 return call_tzname(GET_DT_TZINFO(self), self);
Tim Peters2a799bf2002-12-16 20:18:38 +00004343}
4344
4345/*
Tim Petersa9bc1682003-01-11 03:39:11 +00004346 * datetime arithmetic.
Tim Peters2a799bf2002-12-16 20:18:38 +00004347 */
4348
Tim Petersa9bc1682003-01-11 03:39:11 +00004349/* factor must be 1 (to add) or -1 (to subtract). The result inherits
4350 * the tzinfo state of date.
Tim Peters2a799bf2002-12-16 20:18:38 +00004351 */
4352static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004353add_datetime_timedelta(PyDateTime_DateTime *date, PyDateTime_Delta *delta,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004354 int factor)
Tim Peters2a799bf2002-12-16 20:18:38 +00004355{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004356 /* Note that the C-level additions can't overflow, because of
4357 * invariant bounds on the member values.
4358 */
4359 int year = GET_YEAR(date);
4360 int month = GET_MONTH(date);
4361 int day = GET_DAY(date) + GET_TD_DAYS(delta) * factor;
4362 int hour = DATE_GET_HOUR(date);
4363 int minute = DATE_GET_MINUTE(date);
4364 int second = DATE_GET_SECOND(date) + GET_TD_SECONDS(delta) * factor;
4365 int microsecond = DATE_GET_MICROSECOND(date) +
4366 GET_TD_MICROSECONDS(delta) * factor;
Tim Peters2a799bf2002-12-16 20:18:38 +00004367
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004368 assert(factor == 1 || factor == -1);
4369 if (normalize_datetime(&year, &month, &day,
4370 &hour, &minute, &second, &microsecond) < 0)
4371 return NULL;
4372 else
4373 return new_datetime(year, month, day,
4374 hour, minute, second, microsecond,
4375 HASTZINFO(date) ? date->tzinfo : Py_None);
Tim Peters2a799bf2002-12-16 20:18:38 +00004376}
4377
4378static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004379datetime_add(PyObject *left, PyObject *right)
Tim Peters2a799bf2002-12-16 20:18:38 +00004380{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004381 if (PyDateTime_Check(left)) {
4382 /* datetime + ??? */
4383 if (PyDelta_Check(right))
4384 /* datetime + delta */
4385 return add_datetime_timedelta(
4386 (PyDateTime_DateTime *)left,
4387 (PyDateTime_Delta *)right,
4388 1);
4389 }
4390 else if (PyDelta_Check(left)) {
4391 /* delta + datetime */
4392 return add_datetime_timedelta((PyDateTime_DateTime *) right,
4393 (PyDateTime_Delta *) left,
4394 1);
4395 }
4396 Py_INCREF(Py_NotImplemented);
4397 return Py_NotImplemented;
Tim Peters2a799bf2002-12-16 20:18:38 +00004398}
4399
4400static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004401datetime_subtract(PyObject *left, PyObject *right)
Tim Peters2a799bf2002-12-16 20:18:38 +00004402{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004403 PyObject *result = Py_NotImplemented;
Tim Peters2a799bf2002-12-16 20:18:38 +00004404
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004405 if (PyDateTime_Check(left)) {
4406 /* datetime - ??? */
4407 if (PyDateTime_Check(right)) {
4408 /* datetime - datetime */
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004409 PyObject *offset1, *offset2, *offdiff = NULL;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004410 int delta_d, delta_s, delta_us;
Tim Peters2a799bf2002-12-16 20:18:38 +00004411
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004412 if (GET_DT_TZINFO(left) == GET_DT_TZINFO(right)) {
4413 offset2 = offset1 = Py_None;
4414 Py_INCREF(offset1);
4415 Py_INCREF(offset2);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004416 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004417 else {
4418 offset1 = datetime_utcoffset(left, NULL);
4419 if (offset1 == NULL)
4420 return NULL;
4421 offset2 = datetime_utcoffset(right, NULL);
4422 if (offset2 == NULL) {
4423 Py_DECREF(offset1);
4424 return NULL;
4425 }
4426 if ((offset1 != Py_None) != (offset2 != Py_None)) {
4427 PyErr_SetString(PyExc_TypeError,
4428 "can't subtract offset-naive and "
4429 "offset-aware datetimes");
4430 Py_DECREF(offset1);
4431 Py_DECREF(offset2);
4432 return NULL;
4433 }
4434 }
4435 if ((offset1 != offset2) &&
4436 delta_cmp(offset1, offset2) != 0) {
4437 offdiff = delta_subtract(offset1, offset2);
4438 if (offdiff == NULL) {
4439 Py_DECREF(offset1);
4440 Py_DECREF(offset2);
4441 return NULL;
4442 }
4443 }
4444 Py_DECREF(offset1);
4445 Py_DECREF(offset2);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004446 delta_d = ymd_to_ord(GET_YEAR(left),
4447 GET_MONTH(left),
4448 GET_DAY(left)) -
4449 ymd_to_ord(GET_YEAR(right),
4450 GET_MONTH(right),
4451 GET_DAY(right));
4452 /* These can't overflow, since the values are
4453 * normalized. At most this gives the number of
4454 * seconds in one day.
4455 */
4456 delta_s = (DATE_GET_HOUR(left) -
4457 DATE_GET_HOUR(right)) * 3600 +
4458 (DATE_GET_MINUTE(left) -
4459 DATE_GET_MINUTE(right)) * 60 +
4460 (DATE_GET_SECOND(left) -
4461 DATE_GET_SECOND(right));
4462 delta_us = DATE_GET_MICROSECOND(left) -
4463 DATE_GET_MICROSECOND(right);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004464 result = new_delta(delta_d, delta_s, delta_us, 1);
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004465 if (offdiff != NULL) {
4466 PyObject *temp = result;
4467 result = delta_subtract(result, offdiff);
4468 Py_DECREF(temp);
4469 Py_DECREF(offdiff);
4470 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004471 }
4472 else if (PyDelta_Check(right)) {
4473 /* datetime - delta */
4474 result = add_datetime_timedelta(
4475 (PyDateTime_DateTime *)left,
4476 (PyDateTime_Delta *)right,
4477 -1);
4478 }
4479 }
Tim Peters2a799bf2002-12-16 20:18:38 +00004480
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004481 if (result == Py_NotImplemented)
4482 Py_INCREF(result);
4483 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00004484}
4485
4486/* Various ways to turn a datetime into a string. */
4487
4488static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004489datetime_repr(PyDateTime_DateTime *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00004490{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004491 const char *type_name = Py_TYPE(self)->tp_name;
4492 PyObject *baserepr;
Tim Peters2a799bf2002-12-16 20:18:38 +00004493
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004494 if (DATE_GET_MICROSECOND(self)) {
4495 baserepr = PyUnicode_FromFormat(
4496 "%s(%d, %d, %d, %d, %d, %d, %d)",
4497 type_name,
4498 GET_YEAR(self), GET_MONTH(self), GET_DAY(self),
4499 DATE_GET_HOUR(self), DATE_GET_MINUTE(self),
4500 DATE_GET_SECOND(self),
4501 DATE_GET_MICROSECOND(self));
4502 }
4503 else if (DATE_GET_SECOND(self)) {
4504 baserepr = PyUnicode_FromFormat(
4505 "%s(%d, %d, %d, %d, %d, %d)",
4506 type_name,
4507 GET_YEAR(self), GET_MONTH(self), GET_DAY(self),
4508 DATE_GET_HOUR(self), DATE_GET_MINUTE(self),
4509 DATE_GET_SECOND(self));
4510 }
4511 else {
4512 baserepr = PyUnicode_FromFormat(
4513 "%s(%d, %d, %d, %d, %d)",
4514 type_name,
4515 GET_YEAR(self), GET_MONTH(self), GET_DAY(self),
4516 DATE_GET_HOUR(self), DATE_GET_MINUTE(self));
4517 }
4518 if (baserepr == NULL || ! HASTZINFO(self))
4519 return baserepr;
4520 return append_keyword_tzinfo(baserepr, self->tzinfo);
Tim Peters2a799bf2002-12-16 20:18:38 +00004521}
4522
Tim Petersa9bc1682003-01-11 03:39:11 +00004523static PyObject *
4524datetime_str(PyDateTime_DateTime *self)
4525{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004526 return PyObject_CallMethod((PyObject *)self, "isoformat", "(s)", " ");
Tim Petersa9bc1682003-01-11 03:39:11 +00004527}
Tim Peters2a799bf2002-12-16 20:18:38 +00004528
4529static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004530datetime_isoformat(PyDateTime_DateTime *self, PyObject *args, PyObject *kw)
Tim Peters2a799bf2002-12-16 20:18:38 +00004531{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004532 int sep = 'T';
4533 static char *keywords[] = {"sep", NULL};
4534 char buffer[100];
4535 PyObject *result;
4536 int us = DATE_GET_MICROSECOND(self);
Tim Peters2a799bf2002-12-16 20:18:38 +00004537
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004538 if (!PyArg_ParseTupleAndKeywords(args, kw, "|C:isoformat", keywords, &sep))
4539 return NULL;
4540 if (us)
4541 result = PyUnicode_FromFormat("%04d-%02d-%02d%c%02d:%02d:%02d.%06d",
4542 GET_YEAR(self), GET_MONTH(self),
4543 GET_DAY(self), (int)sep,
4544 DATE_GET_HOUR(self), DATE_GET_MINUTE(self),
4545 DATE_GET_SECOND(self), us);
4546 else
4547 result = PyUnicode_FromFormat("%04d-%02d-%02d%c%02d:%02d:%02d",
4548 GET_YEAR(self), GET_MONTH(self),
4549 GET_DAY(self), (int)sep,
4550 DATE_GET_HOUR(self), DATE_GET_MINUTE(self),
4551 DATE_GET_SECOND(self));
Walter Dörwaldbafa1372007-05-31 17:50:48 +00004552
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004553 if (!result || !HASTZINFO(self))
4554 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00004555
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004556 /* We need to append the UTC offset. */
4557 if (format_utcoffset(buffer, sizeof(buffer), ":", self->tzinfo,
4558 (PyObject *)self) < 0) {
4559 Py_DECREF(result);
4560 return NULL;
4561 }
4562 PyUnicode_AppendAndDel(&result, PyUnicode_FromString(buffer));
4563 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00004564}
4565
Tim Petersa9bc1682003-01-11 03:39:11 +00004566static PyObject *
4567datetime_ctime(PyDateTime_DateTime *self)
4568{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004569 return format_ctime((PyDateTime_Date *)self,
4570 DATE_GET_HOUR(self),
4571 DATE_GET_MINUTE(self),
4572 DATE_GET_SECOND(self));
Tim Petersa9bc1682003-01-11 03:39:11 +00004573}
4574
Tim Peters2a799bf2002-12-16 20:18:38 +00004575/* Miscellaneous methods. */
4576
Tim Petersa9bc1682003-01-11 03:39:11 +00004577static PyObject *
Guido van Rossum19960592006-08-24 17:29:38 +00004578datetime_richcompare(PyObject *self, PyObject *other, int op)
Tim Petersa9bc1682003-01-11 03:39:11 +00004579{
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004580 PyObject *result = NULL;
4581 PyObject *offset1, *offset2;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004582 int diff;
Tim Petersa9bc1682003-01-11 03:39:11 +00004583
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004584 if (! PyDateTime_Check(other)) {
4585 if (PyDate_Check(other)) {
4586 /* Prevent invocation of date_richcompare. We want to
4587 return NotImplemented here to give the other object
4588 a chance. But since DateTime is a subclass of
4589 Date, if the other object is a Date, it would
4590 compute an ordering based on the date part alone,
4591 and we don't want that. So force unequal or
4592 uncomparable here in that case. */
4593 if (op == Py_EQ)
4594 Py_RETURN_FALSE;
4595 if (op == Py_NE)
4596 Py_RETURN_TRUE;
4597 return cmperror(self, other);
4598 }
4599 Py_INCREF(Py_NotImplemented);
4600 return Py_NotImplemented;
4601 }
Tim Petersa9bc1682003-01-11 03:39:11 +00004602
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004603 if (GET_DT_TZINFO(self) == GET_DT_TZINFO(other)) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004604 diff = memcmp(((PyDateTime_DateTime *)self)->data,
4605 ((PyDateTime_DateTime *)other)->data,
4606 _PyDateTime_DATETIME_DATASIZE);
4607 return diff_to_bool(diff, op);
4608 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004609 offset1 = datetime_utcoffset(self, NULL);
4610 if (offset1 == NULL)
4611 return NULL;
4612 offset2 = datetime_utcoffset(other, NULL);
4613 if (offset2 == NULL)
4614 goto done;
4615 /* If they're both naive, or both aware and have the same offsets,
4616 * we get off cheap. Note that if they're both naive, offset1 ==
4617 * offset2 == Py_None at this point.
4618 */
4619 if ((offset1 == offset2) ||
4620 (PyDelta_Check(offset1) && PyDelta_Check(offset2) &&
4621 delta_cmp(offset1, offset2) == 0)) {
4622 diff = memcmp(((PyDateTime_DateTime *)self)->data,
4623 ((PyDateTime_DateTime *)other)->data,
4624 _PyDateTime_DATETIME_DATASIZE);
4625 result = diff_to_bool(diff, op);
4626 }
4627 else if (offset1 != Py_None && offset2 != Py_None) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004628 PyDateTime_Delta *delta;
Tim Petersa9bc1682003-01-11 03:39:11 +00004629
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004630 assert(offset1 != offset2); /* else last "if" handled it */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004631 delta = (PyDateTime_Delta *)datetime_subtract((PyObject *)self,
4632 other);
4633 if (delta == NULL)
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004634 goto done;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004635 diff = GET_TD_DAYS(delta);
4636 if (diff == 0)
4637 diff = GET_TD_SECONDS(delta) |
4638 GET_TD_MICROSECONDS(delta);
4639 Py_DECREF(delta);
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004640 result = diff_to_bool(diff, op);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004641 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004642 else {
4643 PyErr_SetString(PyExc_TypeError,
4644 "can't compare offset-naive and "
4645 "offset-aware datetimes");
4646 }
4647 done:
4648 Py_DECREF(offset1);
4649 Py_XDECREF(offset2);
4650 return result;
Tim Petersa9bc1682003-01-11 03:39:11 +00004651}
4652
Benjamin Peterson8f67d082010-10-17 20:54:53 +00004653static Py_hash_t
Tim Petersa9bc1682003-01-11 03:39:11 +00004654datetime_hash(PyDateTime_DateTime *self)
4655{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004656 if (self->hashcode == -1) {
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004657 PyObject *offset;
Tim Petersa9bc1682003-01-11 03:39:11 +00004658
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004659 offset = datetime_utcoffset((PyObject *)self, NULL);
4660
4661 if (offset == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004662 return -1;
Tim Petersa9bc1682003-01-11 03:39:11 +00004663
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004664 /* Reduce this to a hash of another object. */
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004665 if (offset == Py_None)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004666 self->hashcode = generic_hash(
4667 (unsigned char *)self->data, _PyDateTime_DATETIME_DATASIZE);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004668 else {
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004669 PyObject *temp1, *temp2;
4670 int days, seconds;
Tim Petersa9bc1682003-01-11 03:39:11 +00004671
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004672 assert(HASTZINFO(self));
4673 days = ymd_to_ord(GET_YEAR(self),
4674 GET_MONTH(self),
4675 GET_DAY(self));
4676 seconds = DATE_GET_HOUR(self) * 3600 +
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004677 DATE_GET_MINUTE(self) * 60 +
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004678 DATE_GET_SECOND(self);
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004679 temp1 = new_delta(days, seconds,
4680 DATE_GET_MICROSECOND(self),
4681 1);
4682 if (temp1 == NULL) {
4683 Py_DECREF(offset);
4684 return -1;
4685 }
4686 temp2 = delta_subtract(temp1, offset);
4687 Py_DECREF(temp1);
4688 if (temp2 == NULL) {
4689 Py_DECREF(offset);
4690 return -1;
4691 }
4692 self->hashcode = PyObject_Hash(temp2);
4693 Py_DECREF(temp2);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004694 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004695 Py_DECREF(offset);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004696 }
4697 return self->hashcode;
Tim Petersa9bc1682003-01-11 03:39:11 +00004698}
Tim Peters2a799bf2002-12-16 20:18:38 +00004699
4700static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004701datetime_replace(PyDateTime_DateTime *self, PyObject *args, PyObject *kw)
Tim Peters12bf3392002-12-24 05:41:27 +00004702{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004703 PyObject *clone;
4704 PyObject *tuple;
4705 int y = GET_YEAR(self);
4706 int m = GET_MONTH(self);
4707 int d = GET_DAY(self);
4708 int hh = DATE_GET_HOUR(self);
4709 int mm = DATE_GET_MINUTE(self);
4710 int ss = DATE_GET_SECOND(self);
4711 int us = DATE_GET_MICROSECOND(self);
4712 PyObject *tzinfo = HASTZINFO(self) ? self->tzinfo : Py_None;
Tim Peters12bf3392002-12-24 05:41:27 +00004713
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004714 if (! PyArg_ParseTupleAndKeywords(args, kw, "|iiiiiiiO:replace",
4715 datetime_kws,
4716 &y, &m, &d, &hh, &mm, &ss, &us,
4717 &tzinfo))
4718 return NULL;
4719 tuple = Py_BuildValue("iiiiiiiO", y, m, d, hh, mm, ss, us, tzinfo);
4720 if (tuple == NULL)
4721 return NULL;
4722 clone = datetime_new(Py_TYPE(self), tuple, NULL);
4723 Py_DECREF(tuple);
4724 return clone;
Tim Peters12bf3392002-12-24 05:41:27 +00004725}
4726
4727static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004728datetime_astimezone(PyDateTime_DateTime *self, PyObject *args, PyObject *kw)
Tim Peters80475bb2002-12-25 07:40:55 +00004729{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004730 PyObject *result;
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004731 PyObject *offset;
4732 PyObject *temp;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004733 PyObject *tzinfo;
4734 static char *keywords[] = {"tz", NULL};
Tim Peters80475bb2002-12-25 07:40:55 +00004735
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004736 if (! PyArg_ParseTupleAndKeywords(args, kw, "O!:astimezone", keywords,
4737 &PyDateTime_TZInfoType, &tzinfo))
4738 return NULL;
Tim Peters80475bb2002-12-25 07:40:55 +00004739
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004740 if (!HASTZINFO(self) || self->tzinfo == Py_None)
4741 goto NeedAware;
Tim Peters521fc152002-12-31 17:36:56 +00004742
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004743 /* Conversion to self's own time zone is a NOP. */
4744 if (self->tzinfo == tzinfo) {
4745 Py_INCREF(self);
4746 return (PyObject *)self;
4747 }
Tim Peters521fc152002-12-31 17:36:56 +00004748
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004749 /* Convert self to UTC. */
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004750 offset = datetime_utcoffset((PyObject *)self, NULL);
4751 if (offset == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004752 return NULL;
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004753 if (offset == Py_None) {
4754 Py_DECREF(offset);
4755 NeedAware:
4756 PyErr_SetString(PyExc_ValueError, "astimezone() cannot be applied to "
4757 "a naive datetime");
4758 return NULL;
4759 }
Tim Petersf3615152003-01-01 21:51:37 +00004760
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004761 /* result = self - offset */
4762 result = add_datetime_timedelta(self,
4763 (PyDateTime_Delta *)offset, -1);
4764 Py_DECREF(offset);
4765 if (result == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004766 return NULL;
Tim Peters52dcce22003-01-23 16:36:11 +00004767
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004768 /* Attach new tzinfo and let fromutc() do the rest. */
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004769 temp = ((PyDateTime_DateTime *)result)->tzinfo;
4770 ((PyDateTime_DateTime *)result)->tzinfo = tzinfo;
4771 Py_INCREF(tzinfo);
4772 Py_DECREF(temp);
Tim Peters52dcce22003-01-23 16:36:11 +00004773
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004774 temp = result;
4775 result = PyObject_CallMethod(tzinfo, "fromutc", "O", temp);
4776 Py_DECREF(temp);
4777
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004778 return result;
Tim Peters80475bb2002-12-25 07:40:55 +00004779}
4780
4781static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004782datetime_timetuple(PyDateTime_DateTime *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00004783{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004784 int dstflag = -1;
Tim Peters2a799bf2002-12-16 20:18:38 +00004785
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004786 if (HASTZINFO(self) && self->tzinfo != Py_None) {
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004787 PyObject * dst;
Tim Peters2a799bf2002-12-16 20:18:38 +00004788
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004789 dst = call_dst(self->tzinfo, (PyObject *)self);
4790 if (dst == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004791 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00004792
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004793 if (dst != Py_None)
4794 dstflag = delta_bool((PyDateTime_Delta *)dst);
4795 Py_DECREF(dst);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004796 }
4797 return build_struct_time(GET_YEAR(self),
4798 GET_MONTH(self),
4799 GET_DAY(self),
4800 DATE_GET_HOUR(self),
4801 DATE_GET_MINUTE(self),
4802 DATE_GET_SECOND(self),
4803 dstflag);
Tim Peters2a799bf2002-12-16 20:18:38 +00004804}
4805
4806static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004807datetime_getdate(PyDateTime_DateTime *self)
4808{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004809 return new_date(GET_YEAR(self),
4810 GET_MONTH(self),
4811 GET_DAY(self));
Tim Petersa9bc1682003-01-11 03:39:11 +00004812}
4813
4814static PyObject *
4815datetime_gettime(PyDateTime_DateTime *self)
4816{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004817 return new_time(DATE_GET_HOUR(self),
4818 DATE_GET_MINUTE(self),
4819 DATE_GET_SECOND(self),
4820 DATE_GET_MICROSECOND(self),
4821 Py_None);
Tim Petersa9bc1682003-01-11 03:39:11 +00004822}
4823
4824static PyObject *
4825datetime_gettimetz(PyDateTime_DateTime *self)
4826{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004827 return new_time(DATE_GET_HOUR(self),
4828 DATE_GET_MINUTE(self),
4829 DATE_GET_SECOND(self),
4830 DATE_GET_MICROSECOND(self),
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004831 GET_DT_TZINFO(self));
Tim Petersa9bc1682003-01-11 03:39:11 +00004832}
4833
4834static PyObject *
4835datetime_utctimetuple(PyDateTime_DateTime *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00004836{
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004837 int y, m, d, hh, mm, ss;
4838 PyObject *tzinfo;
4839 PyDateTime_DateTime *utcself;
Tim Peters2a799bf2002-12-16 20:18:38 +00004840
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004841 tzinfo = GET_DT_TZINFO(self);
4842 if (tzinfo == Py_None) {
4843 utcself = self;
4844 Py_INCREF(utcself);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004845 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004846 else {
4847 PyObject *offset;
4848 offset = call_utcoffset(tzinfo, (PyObject *)self);
4849 if (offset == NULL)
Alexander Belopolsky75f94c22010-06-21 15:21:14 +00004850 return NULL;
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004851 if (offset == Py_None) {
4852 Py_DECREF(offset);
4853 utcself = self;
4854 Py_INCREF(utcself);
4855 }
4856 else {
4857 utcself = (PyDateTime_DateTime *)add_datetime_timedelta(self,
4858 (PyDateTime_Delta *)offset, -1);
4859 Py_DECREF(offset);
4860 if (utcself == NULL)
4861 return NULL;
4862 }
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004863 }
Alexander Belopolsky73ca4402010-07-07 23:56:38 +00004864 y = GET_YEAR(utcself);
4865 m = GET_MONTH(utcself);
4866 d = GET_DAY(utcself);
4867 hh = DATE_GET_HOUR(utcself);
4868 mm = DATE_GET_MINUTE(utcself);
4869 ss = DATE_GET_SECOND(utcself);
4870
4871 Py_DECREF(utcself);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004872 return build_struct_time(y, m, d, hh, mm, ss, 0);
Tim Peters2a799bf2002-12-16 20:18:38 +00004873}
4874
Tim Peters371935f2003-02-01 01:52:50 +00004875/* Pickle support, a simple use of __reduce__. */
Tim Peters33e0f382003-01-10 02:05:14 +00004876
Tim Petersa9bc1682003-01-11 03:39:11 +00004877/* Let basestate be the non-tzinfo data string.
Tim Peters2a799bf2002-12-16 20:18:38 +00004878 * If tzinfo is None, this returns (basestate,), else (basestate, tzinfo).
4879 * So it's a tuple in any (non-error) case.
Tim Petersb57f8f02003-02-01 02:54:15 +00004880 * __getstate__ isn't exposed.
Tim Peters2a799bf2002-12-16 20:18:38 +00004881 */
4882static PyObject *
Tim Petersa9bc1682003-01-11 03:39:11 +00004883datetime_getstate(PyDateTime_DateTime *self)
Tim Peters2a799bf2002-12-16 20:18:38 +00004884{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004885 PyObject *basestate;
4886 PyObject *result = NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00004887
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004888 basestate = PyBytes_FromStringAndSize((char *)self->data,
4889 _PyDateTime_DATETIME_DATASIZE);
4890 if (basestate != NULL) {
4891 if (! HASTZINFO(self) || self->tzinfo == Py_None)
4892 result = PyTuple_Pack(1, basestate);
4893 else
4894 result = PyTuple_Pack(2, basestate, self->tzinfo);
4895 Py_DECREF(basestate);
4896 }
4897 return result;
Tim Peters2a799bf2002-12-16 20:18:38 +00004898}
4899
4900static PyObject *
Guido van Rossum177e41a2003-01-30 22:06:23 +00004901datetime_reduce(PyDateTime_DateTime *self, PyObject *arg)
Tim Peters2a799bf2002-12-16 20:18:38 +00004902{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004903 return Py_BuildValue("(ON)", Py_TYPE(self), datetime_getstate(self));
Tim Peters2a799bf2002-12-16 20:18:38 +00004904}
4905
Tim Petersa9bc1682003-01-11 03:39:11 +00004906static PyMethodDef datetime_methods[] = {
Guido van Rossum177e41a2003-01-30 22:06:23 +00004907
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004908 /* Class methods: */
Tim Peters2a799bf2002-12-16 20:18:38 +00004909
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004910 {"now", (PyCFunction)datetime_now,
4911 METH_VARARGS | METH_KEYWORDS | METH_CLASS,
4912 PyDoc_STR("[tz] -> new datetime with tz's local day and time.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00004913
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004914 {"utcnow", (PyCFunction)datetime_utcnow,
4915 METH_NOARGS | METH_CLASS,
4916 PyDoc_STR("Return a new datetime representing UTC day and time.")},
Tim Petersa9bc1682003-01-11 03:39:11 +00004917
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004918 {"fromtimestamp", (PyCFunction)datetime_fromtimestamp,
4919 METH_VARARGS | METH_KEYWORDS | METH_CLASS,
4920 PyDoc_STR("timestamp[, tz] -> tz's local time from POSIX timestamp.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00004921
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004922 {"utcfromtimestamp", (PyCFunction)datetime_utcfromtimestamp,
4923 METH_VARARGS | METH_CLASS,
4924 PyDoc_STR("timestamp -> UTC datetime from a POSIX timestamp "
4925 "(like time.time()).")},
Tim Petersa9bc1682003-01-11 03:39:11 +00004926
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004927 {"strptime", (PyCFunction)datetime_strptime,
4928 METH_VARARGS | METH_CLASS,
4929 PyDoc_STR("string, format -> new datetime parsed from a string "
4930 "(like time.strptime()).")},
Skip Montanaro0af3ade2005-01-13 04:12:31 +00004931
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004932 {"combine", (PyCFunction)datetime_combine,
4933 METH_VARARGS | METH_KEYWORDS | METH_CLASS,
4934 PyDoc_STR("date, time -> datetime with same date and time fields")},
Tim Petersa9bc1682003-01-11 03:39:11 +00004935
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004936 /* Instance methods: */
Guido van Rossum177e41a2003-01-30 22:06:23 +00004937
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004938 {"date", (PyCFunction)datetime_getdate, METH_NOARGS,
4939 PyDoc_STR("Return date object with same year, month and day.")},
Tim Petersa9bc1682003-01-11 03:39:11 +00004940
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004941 {"time", (PyCFunction)datetime_gettime, METH_NOARGS,
4942 PyDoc_STR("Return time object with same time but with tzinfo=None.")},
Tim Petersa9bc1682003-01-11 03:39:11 +00004943
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004944 {"timetz", (PyCFunction)datetime_gettimetz, METH_NOARGS,
4945 PyDoc_STR("Return time object with same time and tzinfo.")},
Tim Petersa9bc1682003-01-11 03:39:11 +00004946
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004947 {"ctime", (PyCFunction)datetime_ctime, METH_NOARGS,
4948 PyDoc_STR("Return ctime() style string.")},
Tim Petersa9bc1682003-01-11 03:39:11 +00004949
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004950 {"timetuple", (PyCFunction)datetime_timetuple, METH_NOARGS,
4951 PyDoc_STR("Return time tuple, compatible with time.localtime().")},
Tim Peters2a799bf2002-12-16 20:18:38 +00004952
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004953 {"utctimetuple", (PyCFunction)datetime_utctimetuple, METH_NOARGS,
4954 PyDoc_STR("Return UTC time tuple, compatible with time.localtime().")},
Tim Peters2a799bf2002-12-16 20:18:38 +00004955
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004956 {"isoformat", (PyCFunction)datetime_isoformat, METH_VARARGS | METH_KEYWORDS,
4957 PyDoc_STR("[sep] -> string in ISO 8601 format, "
4958 "YYYY-MM-DDTHH:MM:SS[.mmmmmm][+HH:MM].\n\n"
4959 "sep is used to separate the year from the time, and "
4960 "defaults to 'T'.")},
Tim Peters2a799bf2002-12-16 20:18:38 +00004961
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004962 {"utcoffset", (PyCFunction)datetime_utcoffset, METH_NOARGS,
4963 PyDoc_STR("Return self.tzinfo.utcoffset(self).")},
Tim Peters2a799bf2002-12-16 20:18:38 +00004964
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004965 {"tzname", (PyCFunction)datetime_tzname, METH_NOARGS,
4966 PyDoc_STR("Return self.tzinfo.tzname(self).")},
Tim Peters2a799bf2002-12-16 20:18:38 +00004967
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004968 {"dst", (PyCFunction)datetime_dst, METH_NOARGS,
4969 PyDoc_STR("Return self.tzinfo.dst(self).")},
Tim Peters2a799bf2002-12-16 20:18:38 +00004970
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004971 {"replace", (PyCFunction)datetime_replace, METH_VARARGS | METH_KEYWORDS,
4972 PyDoc_STR("Return datetime with new specified fields.")},
Tim Peters12bf3392002-12-24 05:41:27 +00004973
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004974 {"astimezone", (PyCFunction)datetime_astimezone, METH_VARARGS | METH_KEYWORDS,
4975 PyDoc_STR("tz -> convert to local time in new timezone tz\n")},
Tim Peters80475bb2002-12-25 07:40:55 +00004976
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004977 {"__reduce__", (PyCFunction)datetime_reduce, METH_NOARGS,
4978 PyDoc_STR("__reduce__() -> (cls, state)")},
Guido van Rossum177e41a2003-01-30 22:06:23 +00004979
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004980 {NULL, NULL}
Tim Peters2a799bf2002-12-16 20:18:38 +00004981};
4982
Tim Petersa9bc1682003-01-11 03:39:11 +00004983static char datetime_doc[] =
Raymond Hettinger3a4231d2004-12-19 20:13:24 +00004984PyDoc_STR("datetime(year, month, day[, hour[, minute[, second[, microsecond[,tzinfo]]]]])\n\
4985\n\
4986The year, month and day arguments are required. tzinfo may be None, or an\n\
4987instance of a tzinfo subclass. The remaining arguments may be ints or longs.\n");
Tim Peters2a799bf2002-12-16 20:18:38 +00004988
Tim Petersa9bc1682003-01-11 03:39:11 +00004989static PyNumberMethods datetime_as_number = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00004990 datetime_add, /* nb_add */
4991 datetime_subtract, /* nb_subtract */
4992 0, /* nb_multiply */
4993 0, /* nb_remainder */
4994 0, /* nb_divmod */
4995 0, /* nb_power */
4996 0, /* nb_negative */
4997 0, /* nb_positive */
4998 0, /* nb_absolute */
4999 0, /* nb_bool */
Tim Peters2a799bf2002-12-16 20:18:38 +00005000};
5001
Neal Norwitz227b5332006-03-22 09:28:35 +00005002static PyTypeObject PyDateTime_DateTimeType = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005003 PyVarObject_HEAD_INIT(NULL, 0)
5004 "datetime.datetime", /* tp_name */
5005 sizeof(PyDateTime_DateTime), /* tp_basicsize */
5006 0, /* tp_itemsize */
5007 (destructor)datetime_dealloc, /* tp_dealloc */
5008 0, /* tp_print */
5009 0, /* tp_getattr */
5010 0, /* tp_setattr */
5011 0, /* tp_reserved */
5012 (reprfunc)datetime_repr, /* tp_repr */
5013 &datetime_as_number, /* tp_as_number */
5014 0, /* tp_as_sequence */
5015 0, /* tp_as_mapping */
5016 (hashfunc)datetime_hash, /* tp_hash */
5017 0, /* tp_call */
5018 (reprfunc)datetime_str, /* tp_str */
5019 PyObject_GenericGetAttr, /* tp_getattro */
5020 0, /* tp_setattro */
5021 0, /* tp_as_buffer */
5022 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
5023 datetime_doc, /* tp_doc */
5024 0, /* tp_traverse */
5025 0, /* tp_clear */
5026 datetime_richcompare, /* tp_richcompare */
5027 0, /* tp_weaklistoffset */
5028 0, /* tp_iter */
5029 0, /* tp_iternext */
5030 datetime_methods, /* tp_methods */
5031 0, /* tp_members */
5032 datetime_getset, /* tp_getset */
5033 &PyDateTime_DateType, /* tp_base */
5034 0, /* tp_dict */
5035 0, /* tp_descr_get */
5036 0, /* tp_descr_set */
5037 0, /* tp_dictoffset */
5038 0, /* tp_init */
5039 datetime_alloc, /* tp_alloc */
5040 datetime_new, /* tp_new */
5041 0, /* tp_free */
Tim Peters2a799bf2002-12-16 20:18:38 +00005042};
5043
5044/* ---------------------------------------------------------------------------
5045 * Module methods and initialization.
5046 */
5047
5048static PyMethodDef module_methods[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005049 {NULL, NULL}
Tim Peters2a799bf2002-12-16 20:18:38 +00005050};
5051
Tim Peters9ddf40b2004-06-20 22:41:32 +00005052/* C API. Clients get at this via PyDateTime_IMPORT, defined in
5053 * datetime.h.
5054 */
5055static PyDateTime_CAPI CAPI = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005056 &PyDateTime_DateType,
5057 &PyDateTime_DateTimeType,
5058 &PyDateTime_TimeType,
5059 &PyDateTime_DeltaType,
5060 &PyDateTime_TZInfoType,
5061 new_date_ex,
5062 new_datetime_ex,
5063 new_time_ex,
5064 new_delta_ex,
5065 datetime_fromtimestamp,
5066 date_fromtimestamp
Tim Peters9ddf40b2004-06-20 22:41:32 +00005067};
5068
5069
Martin v. Löwis1a214512008-06-11 05:26:20 +00005070
5071static struct PyModuleDef datetimemodule = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005072 PyModuleDef_HEAD_INIT,
Alexander Belopolskycf86e362010-07-23 19:25:47 +00005073 "_datetime",
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005074 "Fast implementation of the datetime type.",
5075 -1,
5076 module_methods,
5077 NULL,
5078 NULL,
5079 NULL,
5080 NULL
Martin v. Löwis1a214512008-06-11 05:26:20 +00005081};
5082
Tim Peters2a799bf2002-12-16 20:18:38 +00005083PyMODINIT_FUNC
Alexander Belopolskycf86e362010-07-23 19:25:47 +00005084PyInit__datetime(void)
Tim Peters2a799bf2002-12-16 20:18:38 +00005085{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005086 PyObject *m; /* a module object */
5087 PyObject *d; /* its dict */
5088 PyObject *x;
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00005089 PyObject *delta;
Tim Peters2a799bf2002-12-16 20:18:38 +00005090
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005091 m = PyModule_Create(&datetimemodule);
5092 if (m == NULL)
5093 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00005094
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005095 if (PyType_Ready(&PyDateTime_DateType) < 0)
5096 return NULL;
5097 if (PyType_Ready(&PyDateTime_DateTimeType) < 0)
5098 return NULL;
5099 if (PyType_Ready(&PyDateTime_DeltaType) < 0)
5100 return NULL;
5101 if (PyType_Ready(&PyDateTime_TimeType) < 0)
5102 return NULL;
5103 if (PyType_Ready(&PyDateTime_TZInfoType) < 0)
5104 return NULL;
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00005105 if (PyType_Ready(&PyDateTime_TimeZoneType) < 0)
5106 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00005107
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005108 /* timedelta values */
5109 d = PyDateTime_DeltaType.tp_dict;
Tim Peters2a799bf2002-12-16 20:18:38 +00005110
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005111 x = new_delta(0, 0, 1, 0);
5112 if (x == NULL || PyDict_SetItemString(d, "resolution", x) < 0)
5113 return NULL;
5114 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005115
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005116 x = new_delta(-MAX_DELTA_DAYS, 0, 0, 0);
5117 if (x == NULL || PyDict_SetItemString(d, "min", x) < 0)
5118 return NULL;
5119 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005120
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005121 x = new_delta(MAX_DELTA_DAYS, 24*3600-1, 1000000-1, 0);
5122 if (x == NULL || PyDict_SetItemString(d, "max", x) < 0)
5123 return NULL;
5124 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005125
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005126 /* date values */
5127 d = PyDateTime_DateType.tp_dict;
Tim Peters2a799bf2002-12-16 20:18:38 +00005128
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005129 x = new_date(1, 1, 1);
5130 if (x == NULL || PyDict_SetItemString(d, "min", x) < 0)
5131 return NULL;
5132 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005133
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005134 x = new_date(MAXYEAR, 12, 31);
5135 if (x == NULL || PyDict_SetItemString(d, "max", x) < 0)
5136 return NULL;
5137 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005138
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005139 x = new_delta(1, 0, 0, 0);
5140 if (x == NULL || PyDict_SetItemString(d, "resolution", x) < 0)
5141 return NULL;
5142 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005143
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005144 /* time values */
5145 d = PyDateTime_TimeType.tp_dict;
Tim Peters2a799bf2002-12-16 20:18:38 +00005146
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005147 x = new_time(0, 0, 0, 0, Py_None);
5148 if (x == NULL || PyDict_SetItemString(d, "min", x) < 0)
5149 return NULL;
5150 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005151
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005152 x = new_time(23, 59, 59, 999999, Py_None);
5153 if (x == NULL || PyDict_SetItemString(d, "max", x) < 0)
5154 return NULL;
5155 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005156
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005157 x = new_delta(0, 0, 1, 0);
5158 if (x == NULL || PyDict_SetItemString(d, "resolution", x) < 0)
5159 return NULL;
5160 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005161
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005162 /* datetime values */
5163 d = PyDateTime_DateTimeType.tp_dict;
Tim Peters2a799bf2002-12-16 20:18:38 +00005164
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005165 x = new_datetime(1, 1, 1, 0, 0, 0, 0, Py_None);
5166 if (x == NULL || PyDict_SetItemString(d, "min", x) < 0)
5167 return NULL;
5168 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005169
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005170 x = new_datetime(MAXYEAR, 12, 31, 23, 59, 59, 999999, Py_None);
5171 if (x == NULL || PyDict_SetItemString(d, "max", x) < 0)
5172 return NULL;
5173 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005174
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005175 x = new_delta(0, 0, 1, 0);
5176 if (x == NULL || PyDict_SetItemString(d, "resolution", x) < 0)
5177 return NULL;
5178 Py_DECREF(x);
Tim Peters2a799bf2002-12-16 20:18:38 +00005179
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00005180 /* timezone values */
5181 d = PyDateTime_TimeZoneType.tp_dict;
5182
5183 delta = new_delta(0, 0, 0, 0);
5184 if (delta == NULL)
5185 return NULL;
Alexander Belopolsky1bcbaab2010-10-14 17:03:51 +00005186 x = create_timezone(delta, NULL);
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00005187 Py_DECREF(delta);
5188 if (x == NULL || PyDict_SetItemString(d, "utc", x) < 0)
5189 return NULL;
Alexander Belopolskya11d8c02010-07-06 23:19:45 +00005190 PyDateTime_TimeZone_UTC = x;
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00005191
5192 delta = new_delta(-1, 60, 0, 1); /* -23:59 */
5193 if (delta == NULL)
5194 return NULL;
Alexander Belopolsky1bcbaab2010-10-14 17:03:51 +00005195 x = create_timezone(delta, NULL);
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00005196 Py_DECREF(delta);
5197 if (x == NULL || PyDict_SetItemString(d, "min", x) < 0)
5198 return NULL;
5199 Py_DECREF(x);
5200
5201 delta = new_delta(0, (23 * 60 + 59) * 60, 0, 0); /* +23:59 */
5202 if (delta == NULL)
5203 return NULL;
Alexander Belopolsky1bcbaab2010-10-14 17:03:51 +00005204 x = create_timezone(delta, NULL);
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00005205 Py_DECREF(delta);
5206 if (x == NULL || PyDict_SetItemString(d, "max", x) < 0)
5207 return NULL;
5208 Py_DECREF(x);
5209
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005210 /* module initialization */
5211 PyModule_AddIntConstant(m, "MINYEAR", MINYEAR);
5212 PyModule_AddIntConstant(m, "MAXYEAR", MAXYEAR);
Tim Peters2a799bf2002-12-16 20:18:38 +00005213
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005214 Py_INCREF(&PyDateTime_DateType);
5215 PyModule_AddObject(m, "date", (PyObject *) &PyDateTime_DateType);
Tim Peters2a799bf2002-12-16 20:18:38 +00005216
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005217 Py_INCREF(&PyDateTime_DateTimeType);
5218 PyModule_AddObject(m, "datetime",
5219 (PyObject *)&PyDateTime_DateTimeType);
Tim Petersa9bc1682003-01-11 03:39:11 +00005220
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005221 Py_INCREF(&PyDateTime_TimeType);
5222 PyModule_AddObject(m, "time", (PyObject *) &PyDateTime_TimeType);
Tim Petersa9bc1682003-01-11 03:39:11 +00005223
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005224 Py_INCREF(&PyDateTime_DeltaType);
5225 PyModule_AddObject(m, "timedelta", (PyObject *) &PyDateTime_DeltaType);
Tim Peters2a799bf2002-12-16 20:18:38 +00005226
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005227 Py_INCREF(&PyDateTime_TZInfoType);
5228 PyModule_AddObject(m, "tzinfo", (PyObject *) &PyDateTime_TZInfoType);
Tim Peters2a799bf2002-12-16 20:18:38 +00005229
Alexander Belopolsky4e749a12010-06-14 14:15:50 +00005230 Py_INCREF(&PyDateTime_TimeZoneType);
5231 PyModule_AddObject(m, "timezone", (PyObject *) &PyDateTime_TimeZoneType);
5232
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005233 x = PyCapsule_New(&CAPI, PyDateTime_CAPSULE_NAME, NULL);
5234 if (x == NULL)
5235 return NULL;
5236 PyModule_AddObject(m, "datetime_CAPI", x);
Tim Peters9ddf40b2004-06-20 22:41:32 +00005237
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005238 /* A 4-year cycle has an extra leap day over what we'd get from
5239 * pasting together 4 single years.
5240 */
5241 assert(DI4Y == 4 * 365 + 1);
5242 assert(DI4Y == days_before_year(4+1));
Tim Peters2a799bf2002-12-16 20:18:38 +00005243
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005244 /* Similarly, a 400-year cycle has an extra leap day over what we'd
5245 * get from pasting together 4 100-year cycles.
5246 */
5247 assert(DI400Y == 4 * DI100Y + 1);
5248 assert(DI400Y == days_before_year(400+1));
Tim Peters2a799bf2002-12-16 20:18:38 +00005249
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005250 /* OTOH, a 100-year cycle has one fewer leap day than we'd get from
5251 * pasting together 25 4-year cycles.
5252 */
5253 assert(DI100Y == 25 * DI4Y - 1);
5254 assert(DI100Y == days_before_year(100+1));
Tim Peters2a799bf2002-12-16 20:18:38 +00005255
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005256 us_per_us = PyLong_FromLong(1);
5257 us_per_ms = PyLong_FromLong(1000);
5258 us_per_second = PyLong_FromLong(1000000);
5259 us_per_minute = PyLong_FromLong(60000000);
5260 seconds_per_day = PyLong_FromLong(24 * 3600);
5261 if (us_per_us == NULL || us_per_ms == NULL || us_per_second == NULL ||
5262 us_per_minute == NULL || seconds_per_day == NULL)
5263 return NULL;
Tim Peters2a799bf2002-12-16 20:18:38 +00005264
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005265 /* The rest are too big for 32-bit ints, but even
5266 * us_per_week fits in 40 bits, so doubles should be exact.
5267 */
5268 us_per_hour = PyLong_FromDouble(3600000000.0);
5269 us_per_day = PyLong_FromDouble(86400000000.0);
5270 us_per_week = PyLong_FromDouble(604800000000.0);
5271 if (us_per_hour == NULL || us_per_day == NULL || us_per_week == NULL)
5272 return NULL;
5273 return m;
Tim Peters2a799bf2002-12-16 20:18:38 +00005274}
Tim Petersf3615152003-01-01 21:51:37 +00005275
5276/* ---------------------------------------------------------------------------
Tim Petersa9bc1682003-01-11 03:39:11 +00005277Some time zone algebra. For a datetime x, let
Tim Petersf3615152003-01-01 21:51:37 +00005278 x.n = x stripped of its timezone -- its naive time.
5279 x.o = x.utcoffset(), and assuming that doesn't raise an exception or
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005280 return None
Tim Petersf3615152003-01-01 21:51:37 +00005281 x.d = x.dst(), and assuming that doesn't raise an exception or
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005282 return None
Tim Petersf3615152003-01-01 21:51:37 +00005283 x.s = x's standard offset, x.o - x.d
5284
5285Now some derived rules, where k is a duration (timedelta).
5286
52871. x.o = x.s + x.d
5288 This follows from the definition of x.s.
5289
Tim Petersc5dc4da2003-01-02 17:55:03 +000052902. If x and y have the same tzinfo member, x.s = y.s.
Tim Petersf3615152003-01-01 21:51:37 +00005291 This is actually a requirement, an assumption we need to make about
5292 sane tzinfo classes.
5293
52943. The naive UTC time corresponding to x is x.n - x.o.
5295 This is again a requirement for a sane tzinfo class.
5296
52974. (x+k).s = x.s
Tim Peters8bb5ad22003-01-24 02:44:45 +00005298 This follows from #2, and that datimetimetz+timedelta preserves tzinfo.
Tim Petersf3615152003-01-01 21:51:37 +00005299
Tim Petersc5dc4da2003-01-02 17:55:03 +000053005. (x+k).n = x.n + k
Tim Petersf3615152003-01-01 21:51:37 +00005301 Again follows from how arithmetic is defined.
5302
Tim Peters8bb5ad22003-01-24 02:44:45 +00005303Now we can explain tz.fromutc(x). Let's assume it's an interesting case
Tim Petersf3615152003-01-01 21:51:37 +00005304(meaning that the various tzinfo methods exist, and don't blow up or return
5305None when called).
5306
Tim Petersa9bc1682003-01-11 03:39:11 +00005307The function wants to return a datetime y with timezone tz, equivalent to x.
Tim Peters8bb5ad22003-01-24 02:44:45 +00005308x is already in UTC.
Tim Petersf3615152003-01-01 21:51:37 +00005309
5310By #3, we want
5311
Tim Peters8bb5ad22003-01-24 02:44:45 +00005312 y.n - y.o = x.n [1]
Tim Petersf3615152003-01-01 21:51:37 +00005313
5314The algorithm starts by attaching tz to x.n, and calling that y. So
5315x.n = y.n at the start. Then it wants to add a duration k to y, so that [1]
5316becomes true; in effect, we want to solve [2] for k:
5317
Tim Peters8bb5ad22003-01-24 02:44:45 +00005318 (y+k).n - (y+k).o = x.n [2]
Tim Petersf3615152003-01-01 21:51:37 +00005319
5320By #1, this is the same as
5321
Tim Peters8bb5ad22003-01-24 02:44:45 +00005322 (y+k).n - ((y+k).s + (y+k).d) = x.n [3]
Tim Petersf3615152003-01-01 21:51:37 +00005323
5324By #5, (y+k).n = y.n + k, which equals x.n + k because x.n=y.n at the start.
5325Substituting that into [3],
5326
Tim Peters8bb5ad22003-01-24 02:44:45 +00005327 x.n + k - (y+k).s - (y+k).d = x.n; the x.n terms cancel, leaving
5328 k - (y+k).s - (y+k).d = 0; rearranging,
5329 k = (y+k).s - (y+k).d; by #4, (y+k).s == y.s, so
5330 k = y.s - (y+k).d
Tim Petersf3615152003-01-01 21:51:37 +00005331
Tim Peters8bb5ad22003-01-24 02:44:45 +00005332On the RHS, (y+k).d can't be computed directly, but y.s can be, and we
5333approximate k by ignoring the (y+k).d term at first. Note that k can't be
5334very large, since all offset-returning methods return a duration of magnitude
5335less than 24 hours. For that reason, if y is firmly in std time, (y+k).d must
5336be 0, so ignoring it has no consequence then.
Tim Petersf3615152003-01-01 21:51:37 +00005337
5338In any case, the new value is
5339
Tim Peters8bb5ad22003-01-24 02:44:45 +00005340 z = y + y.s [4]
Tim Petersf3615152003-01-01 21:51:37 +00005341
Tim Peters8bb5ad22003-01-24 02:44:45 +00005342It's helpful to step back at look at [4] from a higher level: it's simply
5343mapping from UTC to tz's standard time.
Tim Petersc5dc4da2003-01-02 17:55:03 +00005344
5345At this point, if
5346
Tim Peters8bb5ad22003-01-24 02:44:45 +00005347 z.n - z.o = x.n [5]
Tim Petersc5dc4da2003-01-02 17:55:03 +00005348
5349we have an equivalent time, and are almost done. The insecurity here is
Tim Petersf3615152003-01-01 21:51:37 +00005350at the start of daylight time. Picture US Eastern for concreteness. The wall
5351time 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 +00005352sense then. The docs ask that an Eastern tzinfo class consider such a time to
5353be EDT (because it's "after 2"), which is a redundant spelling of 1:MM EST
5354on the day DST starts. We want to return the 1:MM EST spelling because that's
Tim Petersf3615152003-01-01 21:51:37 +00005355the only spelling that makes sense on the local wall clock.
5356
Tim Petersc5dc4da2003-01-02 17:55:03 +00005357In fact, if [5] holds at this point, we do have the standard-time spelling,
5358but that takes a bit of proof. We first prove a stronger result. What's the
5359difference between the LHS and RHS of [5]? Let
Tim Petersf3615152003-01-01 21:51:37 +00005360
Tim Peters8bb5ad22003-01-24 02:44:45 +00005361 diff = x.n - (z.n - z.o) [6]
Tim Petersf3615152003-01-01 21:51:37 +00005362
Tim Petersc5dc4da2003-01-02 17:55:03 +00005363Now
5364 z.n = by [4]
Tim Peters8bb5ad22003-01-24 02:44:45 +00005365 (y + y.s).n = by #5
5366 y.n + y.s = since y.n = x.n
5367 x.n + y.s = since z and y are have the same tzinfo member,
5368 y.s = z.s by #2
5369 x.n + z.s
Tim Petersf3615152003-01-01 21:51:37 +00005370
Tim Petersc5dc4da2003-01-02 17:55:03 +00005371Plugging that back into [6] gives
Tim Petersf3615152003-01-01 21:51:37 +00005372
Tim Petersc5dc4da2003-01-02 17:55:03 +00005373 diff =
Tim Peters8bb5ad22003-01-24 02:44:45 +00005374 x.n - ((x.n + z.s) - z.o) = expanding
5375 x.n - x.n - z.s + z.o = cancelling
5376 - z.s + z.o = by #2
Tim Petersc5dc4da2003-01-02 17:55:03 +00005377 z.d
Tim Petersf3615152003-01-01 21:51:37 +00005378
Tim Petersc5dc4da2003-01-02 17:55:03 +00005379So diff = z.d.
Tim Petersf3615152003-01-01 21:51:37 +00005380
Tim Petersc5dc4da2003-01-02 17:55:03 +00005381If [5] is true now, diff = 0, so z.d = 0 too, and we have the standard-time
Tim Peters8bb5ad22003-01-24 02:44:45 +00005382spelling we wanted in the endcase described above. We're done. Contrarily,
5383if z.d = 0, then we have a UTC equivalent, and are also done.
Tim Petersf3615152003-01-01 21:51:37 +00005384
Tim Petersc5dc4da2003-01-02 17:55:03 +00005385If [5] is not true now, diff = z.d != 0, and z.d is the offset we need to
5386add to z (in effect, z is in tz's standard time, and we need to shift the
Tim Peters8bb5ad22003-01-24 02:44:45 +00005387local clock into tz's daylight time).
Tim Petersf3615152003-01-01 21:51:37 +00005388
Tim Petersc5dc4da2003-01-02 17:55:03 +00005389Let
Tim Petersf3615152003-01-01 21:51:37 +00005390
Tim Peters4fede1a2003-01-04 00:26:59 +00005391 z' = z + z.d = z + diff [7]
Tim Petersc3bb26a2003-01-02 03:14:59 +00005392
Tim Peters4fede1a2003-01-04 00:26:59 +00005393and we can again ask whether
Tim Petersc3bb26a2003-01-02 03:14:59 +00005394
Tim Peters8bb5ad22003-01-24 02:44:45 +00005395 z'.n - z'.o = x.n [8]
Tim Petersc3bb26a2003-01-02 03:14:59 +00005396
Tim Peters8bb5ad22003-01-24 02:44:45 +00005397If so, we're done. If not, the tzinfo class is insane, according to the
5398assumptions we've made. This also requires a bit of proof. As before, let's
5399compute the difference between the LHS and RHS of [8] (and skipping some of
5400the justifications for the kinds of substitutions we've done several times
5401already):
Tim Peters4fede1a2003-01-04 00:26:59 +00005402
Tim Peters8bb5ad22003-01-24 02:44:45 +00005403 diff' = x.n - (z'.n - z'.o) = replacing z'.n via [7]
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00005404 x.n - (z.n + diff - z'.o) = replacing diff via [6]
5405 x.n - (z.n + x.n - (z.n - z.o) - z'.o) =
5406 x.n - z.n - x.n + z.n - z.o + z'.o = cancel x.n
5407 - z.n + z.n - z.o + z'.o = cancel z.n
5408 - z.o + z'.o = #1 twice
5409 -z.s - z.d + z'.s + z'.d = z and z' have same tzinfo
5410 z'.d - z.d
Tim Peters4fede1a2003-01-04 00:26:59 +00005411
5412So 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 +00005413we've found the UTC-equivalent so are done. In fact, we stop with [7] and
5414return z', not bothering to compute z'.d.
Tim Peters4fede1a2003-01-04 00:26:59 +00005415
Tim Peters8bb5ad22003-01-24 02:44:45 +00005416How could z.d and z'd differ? z' = z + z.d [7], so merely moving z' by
5417a dst() offset, and starting *from* a time already in DST (we know z.d != 0),
5418would have to change the result dst() returns: we start in DST, and moving
5419a little further into it takes us out of DST.
Tim Peters4fede1a2003-01-04 00:26:59 +00005420
Tim Peters8bb5ad22003-01-24 02:44:45 +00005421There isn't a sane case where this can happen. The closest it gets is at
5422the end of DST, where there's an hour in UTC with no spelling in a hybrid
5423tzinfo class. In US Eastern, that's 5:MM UTC = 0:MM EST = 1:MM EDT. During
5424that hour, on an Eastern clock 1:MM is taken as being in standard time (6:MM
5425UTC) because the docs insist on that, but 0:MM is taken as being in daylight
5426time (4:MM UTC). There is no local time mapping to 5:MM UTC. The local
5427clock jumps from 1:59 back to 1:00 again, and repeats the 1:MM hour in
5428standard time. Since that's what the local clock *does*, we want to map both
5429UTC hours 5:MM and 6:MM to 1:MM Eastern. The result is ambiguous
Tim Peters4fede1a2003-01-04 00:26:59 +00005430in local time, but so it goes -- it's the way the local clock works.
5431
Tim Peters8bb5ad22003-01-24 02:44:45 +00005432When x = 5:MM UTC is the input to this algorithm, x.o=0, y.o=-5 and y.d=0,
5433so z=0:MM. z.d=60 (minutes) then, so [5] doesn't hold and we keep going.
5434z' = 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 +00005435(correctly) concludes that z' is not UTC-equivalent to x.
5436
5437Because we know z.d said z was in daylight time (else [5] would have held and
5438we would have stopped then), and we know z.d != z'.d (else [8] would have held
Walter Dörwaldf0dfc7a2003-10-20 14:01:56 +00005439and we would have stopped then), and there are only 2 possible values dst() can
Tim Peters4fede1a2003-01-04 00:26:59 +00005440return in Eastern, it follows that z'.d must be 0 (which it is in the example,
5441but the reasoning doesn't depend on the example -- it depends on there being
5442two possible dst() outcomes, one zero and the other non-zero). Therefore
Tim Peters8bb5ad22003-01-24 02:44:45 +00005443z' must be in standard time, and is the spelling we want in this case.
5444
5445Note again that z' is not UTC-equivalent as far as the hybrid tzinfo class is
5446concerned (because it takes z' as being in standard time rather than the
5447daylight time we intend here), but returning it gives the real-life "local
5448clock repeats an hour" behavior when mapping the "unspellable" UTC hour into
5449tz.
5450
5451When the input is 6:MM, z=1:MM and z.d=0, and we stop at once, again with
5452the 1:MM standard time spelling we want.
5453
5454So how can this break? One of the assumptions must be violated. Two
5455possibilities:
5456
54571) [2] effectively says that y.s is invariant across all y belong to a given
5458 time zone. This isn't true if, for political reasons or continental drift,
5459 a region decides to change its base offset from UTC.
5460
54612) There may be versions of "double daylight" time where the tail end of
5462 the analysis gives up a step too early. I haven't thought about that
5463 enough to say.
5464
5465In any case, it's clear that the default fromutc() is strong enough to handle
5466"almost all" time zones: so long as the standard offset is invariant, it
5467doesn't matter if daylight time transition points change from year to year, or
5468if daylight time is skipped in some years; it doesn't matter how large or
5469small dst() may get within its bounds; and it doesn't even matter if some
5470perverse time zone returns a negative dst()). So a breaking case must be
5471pretty bizarre, and a tzinfo subclass can override fromutc() if it is.
Tim Petersf3615152003-01-01 21:51:37 +00005472--------------------------------------------------------------------------- */