File tree Expand file tree Collapse file tree 2 files changed +17
-5
lines changed Expand file tree Collapse file tree 2 files changed +17
-5
lines changed Original file line number Diff line number Diff line change @@ -45,6 +45,19 @@ class C:
45
45
# The reference was released by .clear()
46
46
self .assertIs (None , wr ())
47
47
48
+ def test_clear_does_not_clear_specials (self ):
49
+ class C :
50
+ pass
51
+ c = C ()
52
+ exc = self .outer (c = c )
53
+ del c
54
+ f = exc .__traceback__ .tb_frame
55
+ f .clear ()
56
+ self .assertIsNot (f .f_code , None )
57
+ self .assertIsNot (f .f_locals , None )
58
+ self .assertIsNot (f .f_builtins , None )
59
+ self .assertIsNot (f .f_globals , None )
60
+
48
61
def test_clear_generator (self ):
49
62
endly = False
50
63
def g ():
Original file line number Diff line number Diff line change @@ -612,7 +612,7 @@ frame_dealloc(PyFrameObject *f)
612
612
Py_TRASHCAN_SAFE_BEGIN (f )
613
613
PyCodeObject * co = f -> f_code ;
614
614
615
- /* Kill all local variables */
615
+ /* Kill all local variables including specials. */
616
616
if (f -> f_localsptr ) {
617
617
for (int i = 0 ; i < co -> co_nlocalsplus + FRAME_SPECIALS_SIZE ; i ++ ) {
618
618
Py_CLEAR (f -> f_localsptr [i ]);
@@ -683,11 +683,10 @@ frame_tp_clear(PyFrameObject *f)
683
683
f -> f_state = FRAME_CLEARED ;
684
684
685
685
Py_CLEAR (f -> f_trace );
686
-
686
+ PyCodeObject * co = f -> f_code ;
687
687
/* locals */
688
- PyObject * * localsplus = f -> f_localsptr ;
689
- for (Py_ssize_t i = frame_nslots (f ); -- i >= 0 ; ++ localsplus ) {
690
- Py_CLEAR (* localsplus );
688
+ for (int i = 0 ; i < co -> co_nlocalsplus ; i ++ ) {
689
+ Py_CLEAR (f -> f_localsptr [i ]);
691
690
}
692
691
693
692
/* stack */
You can’t perform that action at this time.
0 commit comments