Skip to content

Commit 01bf540

Browse files
committed
Don't count executing generators and coroutines as referrers in gc.get_referrers.
1 parent 760872e commit 01bf540

File tree

3 files changed

+9
-18
lines changed

3 files changed

+9
-18
lines changed

Lib/test/test_asyncio/test_streams.py

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1214,9 +1214,8 @@ async def main():
12141214
# can't use assertRaises because that clears frames
12151215
exc = excs.exceptions[0]
12161216
self.assertIsNotNone(exc)
1217-
self.assertListEqual(gc.get_referrers(exc), [main_coro])
1218-
main_coro = main()
1219-
asyncio.run(main_coro)
1217+
self.assertListEqual(gc.get_referrers(exc), [])
1218+
asyncio.run(main())
12201219

12211220

12221221
if __name__ == '__main__':

Lib/test/test_asyncio/test_taskgroups.py

Lines changed: 5 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -29,15 +29,6 @@ def get_error_types(eg):
2929
return {type(exc) for exc in eg.exceptions}
3030

3131

32-
def no_other_refs():
33-
# due to gh-124392 coroutines now refer to their locals
34-
coro = asyncio.current_task().get_coro()
35-
frame = sys._getframe(1)
36-
while coro.cr_frame != frame:
37-
coro = coro.cr_await
38-
return [coro]
39-
40-
4132
class TestTaskGroup(unittest.IsolatedAsyncioTestCase):
4233

4334
async def test_taskgroup_01(self):
@@ -923,7 +914,7 @@ class _Done(Exception):
923914
exc = e
924915

925916
self.assertIsNotNone(exc)
926-
self.assertListEqual(gc.get_referrers(exc), no_other_refs())
917+
self.assertListEqual(gc.get_referrers(exc), [])
927918

928919

929920
async def test_exception_refcycles_errors(self):
@@ -941,7 +932,7 @@ class _Done(Exception):
941932
exc = excs.exceptions[0]
942933

943934
self.assertIsInstance(exc, _Done)
944-
self.assertListEqual(gc.get_referrers(exc), no_other_refs())
935+
self.assertListEqual(gc.get_referrers(exc), [])
945936

946937

947938
async def test_exception_refcycles_parent_task(self):
@@ -963,7 +954,7 @@ async def coro_fn():
963954
exc = excs.exceptions[0].exceptions[0]
964955

965956
self.assertIsInstance(exc, _Done)
966-
self.assertListEqual(gc.get_referrers(exc), no_other_refs())
957+
self.assertListEqual(gc.get_referrers(exc), [])
967958

968959
async def test_exception_refcycles_propagate_cancellation_error(self):
969960
"""Test that TaskGroup deletes propagate_cancellation_error"""
@@ -978,7 +969,7 @@ async def test_exception_refcycles_propagate_cancellation_error(self):
978969
exc = e.__cause__
979970

980971
self.assertIsInstance(exc, asyncio.CancelledError)
981-
self.assertListEqual(gc.get_referrers(exc), no_other_refs())
972+
self.assertListEqual(gc.get_referrers(exc), [])
982973

983974
async def test_exception_refcycles_base_error(self):
984975
"""Test that TaskGroup deletes self._base_error"""
@@ -995,7 +986,7 @@ class MyKeyboardInterrupt(KeyboardInterrupt):
995986
exc = e
996987

997988
self.assertIsNotNone(exc)
998-
self.assertListEqual(gc.get_referrers(exc), no_other_refs())
989+
self.assertListEqual(gc.get_referrers(exc), [])
999990

1000991

1001992
if __name__ == "__main__":

Objects/genobject.c

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -58,7 +58,7 @@ gen_traverse(PyObject *self, visitproc visit, void *arg)
5858
PyGenObject *gen = _PyGen_CAST(self);
5959
Py_VISIT(gen->gi_name);
6060
Py_VISIT(gen->gi_qualname);
61-
if (gen->gi_frame_state != FRAME_CLEARED) {
61+
if (gen->gi_frame_state < FRAME_EXECUTING) {
6262
_PyInterpreterFrame *frame = &gen->gi_iframe;
6363
assert(frame->frame_obj == NULL ||
6464
frame->frame_obj->f_frame->owner == FRAME_OWNED_BY_GENERATOR);
@@ -375,6 +375,7 @@ gen_close(PyObject *self, PyObject *args)
375375

376376
if (gen->gi_frame_state == FRAME_CREATED) {
377377
gen->gi_frame_state = FRAME_COMPLETED;
378+
_PyFrame_ClearLocals(&gen->gi_iframe);
378379
Py_RETURN_NONE;
379380
}
380381
if (FRAME_STATE_FINISHED(gen->gi_frame_state)) {

0 commit comments

Comments
 (0)