]> granicus.if.org Git - python/commitdiff
bpo-26491 Defer DECREFs until enumobject is in a consistent state (#3747)
authorRaymond Hettinger <rhettinger@users.noreply.github.com>
Mon, 25 Sep 2017 09:15:53 +0000 (02:15 -0700)
committerGitHub <noreply@github.com>
Mon, 25 Sep 2017 09:15:53 +0000 (02:15 -0700)
Objects/enumobject.c

index 3eb1736200c6ddbd9dc3bff8c29280438a2e37eb..154d901e86d1198626aa778689efe886c381e657 100644 (file)
@@ -103,6 +103,8 @@ enum_next_long(enumobject *en, PyObject* next_item)
     PyObject *result = en->en_result;
     PyObject *next_index;
     PyObject *stepped_up;
+    PyObject *old_index;
+    PyObject *old_item;
 
     if (en->en_longindex == NULL) {
         en->en_longindex = PyLong_FromSsize_t(PY_SSIZE_T_MAX);
@@ -118,15 +120,19 @@ enum_next_long(enumobject *en, PyObject* next_item)
 
     if (result->ob_refcnt == 1) {
         Py_INCREF(result);
-        Py_DECREF(PyTuple_GET_ITEM(result, 0));
-        Py_DECREF(PyTuple_GET_ITEM(result, 1));
-    } else {
-        result = PyTuple_New(2);
-        if (result == NULL) {
-            Py_DECREF(next_index);
-            Py_DECREF(next_item);
-            return NULL;
-        }
+        old_index = PyTuple_GET_ITEM(result, 0);
+        old_item = PyTuple_GET_ITEM(result, 1);
+        PyTuple_SET_ITEM(result, 0, next_index);
+        PyTuple_SET_ITEM(result, 1, next_item);
+        Py_DECREF(old_index);
+        Py_DECREF(old_item);
+        return result;
+    }
+    result = PyTuple_New(2);
+    if (result == NULL) {
+        Py_DECREF(next_index);
+        Py_DECREF(next_item);
+        return NULL;
     }
     PyTuple_SET_ITEM(result, 0, next_index);
     PyTuple_SET_ITEM(result, 1, next_item);
@@ -140,6 +146,8 @@ enum_next(enumobject *en)
     PyObject *next_item;
     PyObject *result = en->en_result;
     PyObject *it = en->en_sit;
+    PyObject *old_index;
+    PyObject *old_item;
 
     next_item = (*Py_TYPE(it)->tp_iternext)(it);
     if (next_item == NULL)
@@ -157,15 +165,19 @@ enum_next(enumobject *en)
 
     if (result->ob_refcnt == 1) {
         Py_INCREF(result);
-        Py_DECREF(PyTuple_GET_ITEM(result, 0));
-        Py_DECREF(PyTuple_GET_ITEM(result, 1));
-    } else {
-        result = PyTuple_New(2);
-        if (result == NULL) {
-            Py_DECREF(next_index);
-            Py_DECREF(next_item);
-            return NULL;
-        }
+        old_index = PyTuple_GET_ITEM(result, 0);
+        old_item = PyTuple_GET_ITEM(result, 1);
+        PyTuple_SET_ITEM(result, 0, next_index);
+        PyTuple_SET_ITEM(result, 1, next_item);
+        Py_DECREF(old_index);
+        Py_DECREF(old_item);
+        return result;
+    }
+    result = PyTuple_New(2);
+    if (result == NULL) {
+        Py_DECREF(next_index);
+        Py_DECREF(next_item);
+        return NULL;
     }
     PyTuple_SET_ITEM(result, 0, next_index);
     PyTuple_SET_ITEM(result, 1, next_item);