@@ -1546,6 +1546,29 @@ delta_to_microseconds(PyDateTime_Delta *self)
1546
1546
return result ;
1547
1547
}
1548
1548
1549
+ static PyObject *
1550
+ checked_divmod (PyObject * a , PyObject * b )
1551
+ {
1552
+ PyObject * result = PyNumber_Divmod (a , b );
1553
+ if (result != NULL ) {
1554
+ if (!PyTuple_Check (result )) {
1555
+ PyErr_Format (PyExc_TypeError ,
1556
+ "divmod() returned non-tuple (type %.200s)" ,
1557
+ result -> ob_type -> tp_name );
1558
+ Py_DECREF (result );
1559
+ return NULL ;
1560
+ }
1561
+ if (PyTuple_GET_SIZE (result ) != 2 ) {
1562
+ PyErr_Format (PyExc_TypeError ,
1563
+ "divmod() returned a tuple of size %zd" ,
1564
+ PyTuple_GET_SIZE (result ));
1565
+ Py_DECREF (result );
1566
+ return NULL ;
1567
+ }
1568
+ }
1569
+ return result ;
1570
+ }
1571
+
1549
1572
/* Convert a number of us (as a Python int or long) to a timedelta.
1550
1573
*/
1551
1574
static PyObject *
@@ -1554,70 +1577,49 @@ microseconds_to_delta_ex(PyObject *pyus, PyTypeObject *type)
1554
1577
int us ;
1555
1578
int s ;
1556
1579
int d ;
1557
- long temp ;
1558
1580
1559
1581
PyObject * tuple = NULL ;
1560
1582
PyObject * num = NULL ;
1561
1583
PyObject * result = NULL ;
1562
1584
1563
- assert (_PyAnyInt_CheckExact (pyus ));
1564
- tuple = PyNumber_Divmod (pyus , us_per_second );
1565
- if (tuple == NULL )
1585
+ tuple = checked_divmod (pyus , us_per_second );
1586
+ if (tuple == NULL ) {
1566
1587
goto Done ;
1588
+ }
1567
1589
1568
- num = PyTuple_GetItem (tuple , 1 ); /* us */
1569
- if (num == NULL )
1570
- goto Done ;
1571
- temp = PyLong_AsLong (num );
1590
+ num = PyTuple_GET_ITEM (tuple , 1 ); /* us */
1591
+ us = _PyLong_AsInt (num );
1572
1592
num = NULL ;
1573
- if (temp == -1 && PyErr_Occurred ())
1574
- goto Done ;
1575
- assert (0 <= temp && temp < 1000000 );
1576
- us = (int )temp ;
1577
- if (us < 0 ) {
1578
- /* The divisor was positive, so this must be an error. */
1579
- assert (PyErr_Occurred ());
1593
+ if (us == -1 && PyErr_Occurred ()) {
1580
1594
goto Done ;
1581
1595
}
1596
+ if (!(0 <= us && us < 1000000 )) {
1597
+ goto BadDivmod ;
1598
+ }
1582
1599
1583
- num = PyTuple_GetItem (tuple , 0 ); /* leftover seconds */
1584
- if (num == NULL )
1585
- goto Done ;
1600
+ num = PyTuple_GET_ITEM (tuple , 0 ); /* leftover seconds */
1586
1601
Py_INCREF (num );
1587
1602
Py_DECREF (tuple );
1588
1603
1589
- tuple = PyNumber_Divmod (num , seconds_per_day );
1604
+ tuple = checked_divmod (num , seconds_per_day );
1590
1605
if (tuple == NULL )
1591
1606
goto Done ;
1592
1607
Py_DECREF (num );
1593
1608
1594
- num = PyTuple_GetItem (tuple , 1 ); /* seconds */
1595
- if (num == NULL )
1596
- goto Done ;
1597
- temp = PyLong_AsLong (num );
1609
+ num = PyTuple_GET_ITEM (tuple , 1 ); /* seconds */
1610
+ s = _PyLong_AsInt (num );
1598
1611
num = NULL ;
1599
- if (temp == -1 && PyErr_Occurred ())
1600
- goto Done ;
1601
- assert (0 <= temp && temp < 24 * 3600 );
1602
- s = (int )temp ;
1603
-
1604
- if (s < 0 ) {
1605
- /* The divisor was positive, so this must be an error. */
1606
- assert (PyErr_Occurred ());
1612
+ if (s == -1 && PyErr_Occurred ()) {
1607
1613
goto Done ;
1608
1614
}
1615
+ if (!(0 <= s && s < 24 * 3600 )) {
1616
+ goto BadDivmod ;
1617
+ }
1609
1618
1610
- num = PyTuple_GetItem (tuple , 0 ); /* leftover days */
1611
- if (num == NULL )
1612
- goto Done ;
1619
+ num = PyTuple_GET_ITEM (tuple , 0 ); /* leftover days */
1613
1620
Py_INCREF (num );
1614
- temp = PyLong_AsLong (num );
1615
- if (temp == -1 && PyErr_Occurred ())
1616
- goto Done ;
1617
- d = (int )temp ;
1618
- if ((long )d != temp ) {
1619
- PyErr_SetString (PyExc_OverflowError , "normalized days too "
1620
- "large to fit in a C int" );
1621
+ d = _PyLong_AsInt (num );
1622
+ if (d == -1 && PyErr_Occurred ()) {
1621
1623
goto Done ;
1622
1624
}
1623
1625
result = new_delta_ex (d , s , us , 0 , type );
@@ -1626,6 +1628,11 @@ microseconds_to_delta_ex(PyObject *pyus, PyTypeObject *type)
1626
1628
Py_XDECREF (tuple );
1627
1629
Py_XDECREF (num );
1628
1630
return result ;
1631
+
1632
+ BadDivmod :
1633
+ PyErr_SetString (PyExc_TypeError ,
1634
+ "divmod() returned a value out of range" );
1635
+ goto Done ;
1629
1636
}
1630
1637
1631
1638
#define microseconds_to_delta (pymicros ) \
@@ -1642,7 +1649,7 @@ multiply_int_timedelta(PyObject *intobj, PyDateTime_Delta *delta)
1642
1649
if (pyus_in == NULL )
1643
1650
return NULL ;
1644
1651
1645
- pyus_out = PyNumber_Multiply (pyus_in , intobj );
1652
+ pyus_out = PyNumber_Multiply (intobj , pyus_in );
1646
1653
Py_DECREF (pyus_in );
1647
1654
if (pyus_out == NULL )
1648
1655
return NULL ;
@@ -1853,13 +1860,11 @@ accum(const char* tag, PyObject *sofar, PyObject *num, PyObject *factor,
1853
1860
assert (num != NULL );
1854
1861
1855
1862
if (_PyAnyInt_Check (num )) {
1856
- prod = PyNumber_Multiply (factor , num );
1863
+ prod = PyNumber_Multiply (num , factor );
1857
1864
if (prod == NULL )
1858
1865
return NULL ;
1859
- assert (_PyAnyInt_CheckExact (prod ));
1860
1866
sum = PyNumbe
81CD
r_Add (sofar , prod );
1861
1867
Py_DECREF (prod );
1862
- assert (sum == NULL || _PyAnyInt_CheckExact (sum ));
1863
1868
return sum ;
1864
1869
}
1865
1870
@@ -1920,7 +1925,6 @@ accum(const char* tag, PyObject *sofar, PyObject *num, PyObject *factor,
1920
1925
Py_DECREF (sum );
1921
1926
Py_DECREF (x );
1922
1927
* leftover += fracpart ;
1923
- assert (y == NULL || _PyAnyInt_CheckExact (y ));
1924
1928
return y ;
1925
1929
}
1926
1930
0 commit comments