Skip to content

Commit 934a94f

Browse files
eendebakptclaude
andcommitted
gh-150868: Also use exact-type checks for ints in the fast sum() loops
Per review: use PyLong_CheckExact with the specialized exact-int deallocator in the float and complex fast-sum loops, so int subclasses take the generic path. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
1 parent 506f0db commit 934a94f

2 files changed

Lines changed: 19 additions & 6 deletions

File tree

Lib/test/test_builtin.py

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2241,6 +2241,19 @@ def __del__(self):
22412241
self.assertEqual(sum((F(i) for i in range(5)), 1j), complex(10, 1))
22422242
self.assertEqual(F.count, 5)
22432243

2244+
def test_sum_int_subclass(self):
2245+
# gh-151060: likewise, the float and complex fast-sum loops must not
2246+
# free an int subclass with the exact-int deallocator.
2247+
class I(int):
2248+
count = 0
2249+
def __del__(self):
2250+
I.count += 1
2251+
2252+
self.assertEqual(sum((I(i) for i in range(5)), 1.0), 11.0)
2253+
self.assertEqual(I.count, 5)
2254+
self.assertEqual(sum((I(i) for i in range(5)), 1j), complex(10, 1))
2255+
self.assertEqual(I.count, 10)
2256+
22442257
@requires_IEEE_754
22452258
@skip_if_double_rounding
22462259
@support.cpython_only # Other implementations may choose a different algorithm

Python/bltinmodule.c

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -2981,15 +2981,15 @@ builtin_sum_impl(PyObject *module, PyObject *iterable, PyObject *start)
29812981
_Py_DECREF_SPECIALIZED(item, _PyFloat_ExactDealloc);
29822982
continue;
29832983
}
2984-
if (PyLong_Check(item)) {
2984+
if (PyLong_CheckExact(item)) {
29852985
double value = PyLong_AsDouble(item);
29862986
if (value != -1.0 || !PyErr_Occurred()) {
29872987
re_sum = cs_add(re_sum, value);
2988-
Py_DECREF(item);
2988+
_Py_DECREF_SPECIALIZED(item, _PyLong_ExactDealloc);
29892989
continue;
29902990
}
29912991
else {
2992-
Py_DECREF(item);
2992+
_Py_DECREF_SPECIALIZED(item, _PyLong_ExactDealloc);
29932993
Py_DECREF(iter);
29942994
return NULL;
29952995
}
@@ -3033,15 +3033,15 @@ builtin_sum_impl(PyObject *module, PyObject *iterable, PyObject *start)
30333033
Py_DECREF(item);
30343034
continue;
30353035
}
3036-
if (PyLong_Check(item)) {
3036+
if (PyLong_CheckExact(item)) {
30373037
double value = PyLong_AsDouble(item);
30383038
if (value != -1.0 || !PyErr_Occurred()) {
30393039
re_sum = cs_add(re_sum, value);
3040-
Py_DECREF(item);
3040+
_Py_DECREF_SPECIALIZED(item, _PyLong_ExactDealloc);
30413041
continue;
30423042
}
30433043
else {
3044-
Py_DECREF(item);
3044+
_Py_DECREF_SPECIALIZED(item, _PyLong_ExactDealloc);
30453045
Py_DECREF(iter);
30463046
return NULL;
30473047
}

0 commit comments

Comments
 (0)