]> git.ipfire.org Git - thirdparty/Python/cpython.git/commitdiff
[3.11] GH-97752: Clear the previous member of newly-created generator/coroutine frame...
authorMiss Islington (bot) <31488909+miss-islington@users.noreply.github.com>
Tue, 4 Oct 2022 04:03:26 +0000 (21:03 -0700)
committerPablo Galindo <pablogsal@gmail.com>
Sat, 22 Oct 2022 19:10:18 +0000 (20:10 +0100)
(cherry picked from commit 93fcc1f4133e177882850177c2c047d46019b812)

Lib/test/test_generators.py
Misc/NEWS.d/next/Core and Builtins/2022-10-03-13-35-48.gh-issue-97752.0xTjJY.rst [new file with mode: 0644]
Python/frame.c

index e5aa7da1e0df13b8a666759cca944bf2082e08f4..353073dbfce00a7c4710caa17ca4100fd900e8e1 100644 (file)
@@ -206,6 +206,25 @@ class GeneratorTest(unittest.TestCase):
         finally:
             gc.set_threshold(*thresholds)
 
+    def test_ag_frame_f_back(self):
+        async def f():
+            yield
+        ag = f()
+        self.assertIsNone(ag.ag_frame.f_back)
+
+    def test_cr_frame_f_back(self):
+        async def f():
+            pass
+        cr = f()
+        self.assertIsNone(cr.cr_frame.f_back)
+        cr.close()  # Suppress RuntimeWarning.
+
+    def test_gi_frame_f_back(self):
+        def f():
+            yield
+        gi = f()
+        self.assertIsNone(gi.gi_frame.f_back)
+
 
 
 class ExceptionTest(unittest.TestCase):
diff --git a/Misc/NEWS.d/next/Core and Builtins/2022-10-03-13-35-48.gh-issue-97752.0xTjJY.rst b/Misc/NEWS.d/next/Core and Builtins/2022-10-03-13-35-48.gh-issue-97752.0xTjJY.rst
new file mode 100644 (file)
index 0000000..c656350
--- /dev/null
@@ -0,0 +1,2 @@
+Fix possible data corruption or crashes when accessing the ``f_back`` member
+of newly-created generator or coroutine frames.
index ef884819e31f8b851efbfcaea7582411ac386e42..9d5cab990c312ae990eeced06e65c14040a2eb0c 100644 (file)
@@ -69,6 +69,9 @@ _PyFrame_Copy(_PyInterpreterFrame *src, _PyInterpreterFrame *dest)
     assert(src->stacktop >= src->f_code->co_nlocalsplus);
     Py_ssize_t size = ((char*)&src->localsplus[src->stacktop]) - (char *)src;
     memcpy(dest, src, size);
+    // Don't leave a dangling pointer to the old frame when creating generators
+    // and coroutines:
+    dest->previous = NULL;
 }