GH-96092: restore frame height of traceback.walk_stack to that of pyt…#99015
GH-96092: restore frame height of traceback.walk_stack to that of pyt…#99015graingert wants to merge 4 commits intopython:mainfrom
Conversation
7ed1575 to
b5eb38b
Compare
|
Aah I think I see how these incorrect In Line 417 in 908e81f Since cpython/Lib/test/test_traceback.py Line 2324 in c053284 simply instantiates it. Only in _extract_from_extended_frame_gen does the code
if f is None:
f = sys._getframe().f_back.f_backget invoked and by that point we are already inside of the Since this code path was originally
and the lac 8000 k of direct tests for it in the commit adding it seems to suggest so: 6bc2c1e#diff-8a52124ffceebd98f91bf96caa0f341ae109f79e190cd5acc1c56c8968d75252R514 One possible fix is to make |
see python/cpython#96092 and it's not really intended for use outside of StackSummary.extract, see python/cpython#99015 (comment)
|
Here's my recommended fix for this: diff --git a/Lib/test/test_traceback.py b/Lib/test/test_traceback.py
index 149d0234fe..48d5c1a809 100644
--- a/Lib/test/test_traceback.py
+++ b/Lib/test/test_traceback.py
@@ -2241,8 +2241,7 @@ class TestStack(unittest.TestCase):
def test_walk_stack(self):
def deeper():
return list(traceback.walk_stack(None))
- s1 = list(traceback.walk_stack(None))
- s2 = deeper()
+ s1, s2 = list(traceback.walk_stack(None)), deeper()
self.assertEqual(len(s2) - len(s1), 1)
self.assertEqual(s2[1:], s1)
diff --git a/Lib/traceback.py b/Lib/traceback.py
index cf5f355ff0..701ce9e4bb 100644
--- a/Lib/traceback.py
+++ b/Lib/traceback.py
@@ -323,17 +323,21 @@ def line(self):
return self._line.strip()
-def walk_stack(f):
+def walk_stack(frame):
"""Walk a stack yielding the frame and line number for each frame.
This will follow f.f_back from the given frame. If no frame is given, the
current stack is used. Usually used with StackSummary.extract.
"""
- if f is None:
- f = sys._getframe().f_back.f_back.f_back.f_back
- while f is not None:
- yield f, f.f_lineno
- f = f.f_back
+ if frame is None:
+ frame = sys._getframe().f_back
+
+ def walk_stack_generator(f):
+ while f is not None:
+ yield f, f.f_lineno
+ f = f.f_back
+
+ return walk_stack_generator(frame)As mentioned in the comment on the issue, this is a change in behavior we should definitely have a NEWS entry and documentation change. Code in practice is unlikely to break due to it. @graingert, would you like to take this on? |
see python/cpython#96092 and it's not really intended for use outside of StackSummary.extract, see python/cpython#99015 (comment)
see python/cpython#96092 and it's not really intended for use outside of StackSummary.extract, see python/cpython#99015 (comment)
see python/cpython#96092 and it's not really intended for use outside of StackSummary.extract, see python/cpython#99015 (comment)
see python/cpython#96092 and it's not really intended for use outside of StackSummary.extract, see python/cpython#99015 (comment)
see python/cpython#96092 and it's not really intended for use outside of StackSummary.extract, see python/cpython#99015 (comment)
* use sys.executable for python binary * pass the desired frame to traceback.walk_stack for 3.11 see python/cpython#96092 and it's not really intended for use outside of StackSummary.extract, see python/cpython#99015 (comment) * the GC overhead now depends on _PyType_PreHeaderSize faster-cpython/ideas#125 python/cpython@8319114#diff-a3a5c73931235f7f344c072dc755d6508e13923db3f5d581c5e88652075871cbR1684 * GH-6785: asyncio.wait no longer calls ensure_future python/cpython#95601 * test on python 3.11 * exclude macos py 3.10
…hon 3.10