]> git.ipfire.org Git - thirdparty/Python/cpython.git/commitdiff
gh-118605: Fix reference leak in FrameLocalsProxy (#118607)
authorTian Gao <gaogaotiantian@hotmail.com>
Sun, 5 May 2024 21:31:35 +0000 (14:31 -0700)
committerGitHub <noreply@github.com>
Sun, 5 May 2024 21:31:35 +0000 (21:31 +0000)
Also add some error checks.

Objects/frameobject.c

index 1cb00e318d9163b79a5ded078145564135fa539e..fdac86961f860c0cd8a58facfb9f0765f938d409 100644 (file)
@@ -232,6 +232,8 @@ framelocalsproxy_merge(PyObject* self, PyObject* other)
         Py_DECREF(value);
     }
 
+    Py_DECREF(iter);
+
     return 0;
 }
 
@@ -242,11 +244,18 @@ framelocalsproxy_keys(PyObject *self, PyObject *__unused)
     PyFrameObject *frame = ((PyFrameLocalsProxyObject*)self)->frame;
     PyCodeObject *co = _PyFrame_GetCode(frame->f_frame);
 
+    if (names == NULL) {
+        return NULL;
+    }
+
     for (int i = 0; i < co->co_nlocalsplus; i++) {
         PyObject *val = framelocalsproxy_getval(frame->f_frame, co, i);
         if (val) {
             PyObject *name = PyTuple_GET_ITEM(co->co_localsplusnames, i);
-            PyList_Append(names, name);
+            if (PyList_Append(names, name) < 0) {
+                Py_DECREF(names);
+                return NULL;
+            }
         }
     }
 
@@ -258,7 +267,10 @@ framelocalsproxy_keys(PyObject *self, PyObject *__unused)
     if (frame->f_extra_locals) {
         assert(PyDict_Check(frame->f_extra_locals));
         while (PyDict_Next(frame->f_extra_locals, &i, &key, &value)) {
-            PyList_Append(names, key);
+            if (PyList_Append(names, key) < 0) {
+                Py_DECREF(names);
+                return NULL;
+            }
         }
     }
 
@@ -306,7 +318,15 @@ framelocalsproxy_visit(PyObject *self, visitproc visit, void *arg)
 static PyObject *
 framelocalsproxy_iter(PyObject *self)
 {
-    return PyObject_GetIter(framelocalsproxy_keys(self, NULL));
+    PyObject* keys = framelocalsproxy_keys(self, NULL);
+    if (keys == NULL) {
+        return NULL;
+    }
+
+    PyObject* iter = PyObject_GetIter(keys);
+    Py_XDECREF(keys);
+
+    return iter;
 }
 
 static PyObject *
@@ -567,6 +587,11 @@ static PyObject*
 framelocalsproxy_reversed(PyObject *self, PyObject *__unused)
 {
     PyObject *result = framelocalsproxy_keys(self, NULL);
+
+    if (result == NULL) {
+        return NULL;
+    }
+
     if (PyList_Reverse(result) < 0) {
         Py_DECREF(result);
         return NULL;