summaryrefslogtreecommitdiffstats
path: root/Modules/datetimemodule.c
diff options
context:
space:
mode:
Diffstat (limited to 'Modules/datetimemodule.c')
-rw-r--r--Modules/datetimemodule.c90
1 files changed, 52 insertions, 38 deletions
diff --git a/Modules/datetimemodule.c b/Modules/datetimemodule.c
index fa9e3a1..c8ef3ae 100644
--- a/Modules/datetimemodule.c
+++ b/Modules/datetimemodule.c
@@ -1224,6 +1224,16 @@ diff_to_bool(int diff, int op)
return result;
}
+/* Raises a "can't compare" TypeError and returns NULL. */
+static PyObject *
+cmperror(PyObject *a, PyObject *b)
+{
+ PyErr_Format(PyExc_TypeError,
+ "can't compare %s to %s",
+ a->ob_type->tp_name, b->ob_type->tp_name);
+ return NULL;
+}
+
/* ---------------------------------------------------------------------------
* Basic object allocation. These allocate Python objects of the right
* size and type, and do the Python object-initialization bit. If there's
@@ -1654,21 +1664,23 @@ delta_subtract(PyObject *left, PyObject *right)
static PyObject *
delta_richcompare(PyDateTime_Delta *self, PyObject *other, int op)
{
- int diff;
+ int diff = 42; /* nonsense */
- if (! PyDelta_CheckExact(other)) {
- PyErr_Format(PyExc_TypeError,
- "can't compare %s to %s instance",
- self->ob_type->tp_name, other->ob_type->tp_name);
- return NULL;
- }
- diff = GET_TD_DAYS(self) - GET_TD_DAYS(other);
- if (diff == 0) {
- diff = GET_TD_SECONDS(self) - GET_TD_SECONDS(other);
- if (diff == 0)
- diff = GET_TD_MICROSECONDS(self) -
- GET_TD_MICROSECONDS(other);
+ if (PyDelta_CheckExact(other)) {
+ diff = GET_TD_DAYS(self) - GET_TD_DAYS(other);
+ if (diff == 0) {
+ diff = GET_TD_SECONDS(self) - GET_TD_SECONDS(other);
+ if (diff == 0)
+ diff = GET_TD_MICROSECONDS(self) -
+ GET_TD_MICROSECONDS(other);
+ }
}
+ else if (op == Py_EQ || op == Py_NE)
+ diff = 1; /* any non-zero value will do */
+
+ else /* stop this from falling back to address comparison */
+ return cmperror((PyObject *)self, other);
+
return diff_to_bool(diff, op);
}
@@ -2443,23 +2455,23 @@ date_isocalendar(PyDateTime_Date *self)
static PyObject *
date_richcompare(PyDateTime_Date *self, PyObject *other, int op)
{
- int diff;
+ int diff = 42; /* nonsense */
- if (! PyDate_Check(other)) {
- if (PyObject_HasAttrString(other, "timetuple")) {
- /* A hook for other kinds of date objects. */
- Py_INCREF(Py_NotImplemented);
- return Py_NotImplemented;
- }
- /* Stop this from falling back to address comparison. */
- PyErr_Format(PyExc_TypeError,
- "can't compare '%s' to '%s'",
- self->ob_type->tp_name,
- other->ob_type->tp_name);
- return NULL;
+ if (PyDate_Check(other))
+ diff = memcmp(self->data, ((PyDateTime_Date *)other)->data,
+ _PyDateTime_DATE_DATASIZE);
+
+ else if (PyObject_HasAttrString(other, "timetuple")) {
+ /* A hook for other kinds of date objects. */
+ Py_INCREF(Py_NotImplemented);
+ return Py_NotImplemented;
}
- diff = memcmp(self->data, ((PyDateTime_Date *)other)->data,
- _PyDateTime_DATE_DATASIZE);
+ else if (op == Py_EQ || op == Py_NE)
+ diff = 1; /* any non-zero value will do */
+
+ else /* stop this from falling back to address comparison */
+ return cmperror((PyObject *)self, other);
+
return diff_to_bool(diff, op);
}
@@ -3173,12 +3185,13 @@ time_richcompare(PyDateTime_Time *self, PyObject *other, int op)
int offset1, offset2;
if (! PyTime_Check(other)) {
+ if (op == Py_EQ || op == Py_NE) {
+ PyObject *result = op == Py_EQ ? Py_False : Py_True;
+ Py_INCREF(result);
+ return result;
+ }
/* Stop this from falling back to address comparison. */
- PyErr_Format(PyExc_TypeError,
- "can't compare '%s' to '%s'",
- self->ob_type->tp_name,
- other->ob_type->tp_name);
- return NULL;
+ return cmperror((PyObject *)self, other);
}
if (classify_two_utcoffsets((PyObject *)self, &offset1, &n1, Py_None,
other, &offset2, &n2, Py_None) < 0)
@@ -4011,12 +4024,13 @@ datetime_richcompare(PyDateTime_DateTime *self, PyObject *other, int op)
Py_INCREF(Py_NotImplemented);
return Py_NotImplemented;
}
+ if (op == Py_EQ || op == Py_NE) {
+ PyObject *result = op == Py_EQ ? Py_False : Py_True;
+ Py_INCREF(result);
+ return result;
+ }
/* Stop this from falling back to address comparison. */
- PyErr_Format(PyExc_TypeError,
- "can't compare '%s' to '%s'",
- self->ob_type->tp_name,
- other->ob_type->tp_name);
- return NULL;
+ return cmperror((PyObject *)self, other);
}
if (classify_two_utcoffsets((PyObject *)self, &offset1, &n1,