Skip to content

Commit c648d46

Browse files
committed
Assert frame is valid when creating frame object.
1 parent b69e803 commit c648d46

File tree

2 files changed

+22
-16
lines changed

2 files changed

+22
-16
lines changed

Include/internal/pycore_frame.h

Lines changed: 17 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -134,6 +134,21 @@ _PyFrame_SetStackPointer(_PyInterpreterFrame *frame, PyObject **stack_pointer)
134134
frame->stacktop = (int)(stack_pointer - frame->localsplus);
135135
}
136136

137+
/* Determine whether a frame is incomplete.
138+
* A frame is incomplete if it is part way through
139+
* creating cell objects or a generator or coroutine.
140+
*
141+
* Frames on the frame stack are incomplete until the
142+
* first RESUME instruction.
143+
* Frames owned by a generator are always complete.
144+
*/
145+
static inline bool
146+
_PyFrame_IsIncomplete(_PyInterpreterFrame *frame)
147+
{
148+
return frame->owner != FRAME_OWNED_BY_GENERATOR &&
149+
frame->prev_instr < _PyCode_CODE(frame->f_code) + frame->f_code->_co_firsttraceable;
150+
}
151+
137152
/* For use by _PyFrame_GetFrameObject
138153
Do not call directly. */
139154
PyFrameObject *
@@ -145,6 +160,8 @@ _PyFrame_MakeAndSetFrameObject(_PyInterpreterFrame *frame);
145160
static inline PyFrameObject *
146161
_PyFrame_GetFrameObject(_PyInterpreterFrame *frame)
147162
{
163+
164+
assert(!_PyFrame_IsIncomplete(frame));
148165
PyFrameObject *res = frame->frame_obj;
149166
if (res != NULL) {
150167
return res;
@@ -210,16 +227,6 @@ PyGenObject *_PyFrame_GetGenerator(_PyInterpreterFrame *frame)
210227
return (PyGenObject *)(((char *)frame) - offset_in_gen);
211228
}
212229

213-
/* Determine whether a frame is incomplete.
214-
* A frame is incomplete until the first RESUME instruction
215-
* as it may be part way through creating cell objects or a
216-
* generator or coroutine. */
217-
static inline bool
218-
_PyFrame_IsIncomplete(_PyInterpreterFrame *frame)
219-
{
220-
return frame->prev_instr < _PyCode_CODE(frame->f_code) + frame->f_code->_co_firsttraceable;
221-
}
222-
223230
#ifdef __cplusplus
224231
}
225232
#endif

Objects/codeobject.c

Lines changed: 5 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -638,11 +638,10 @@ PyCode_New(int argcount, int kwonlyargcount,
638638
exceptiontable);
639639
}
640640

641-
static const char assert0[4] = {
642-
LOAD_ASSERTION_ERROR,
643-
0,
644-
RAISE_VARARGS,
645-
1
641+
static const char assert0[6] = {
642+
RESUME, 0,
643+
LOAD_ASSERTION_ERROR, 0,
644+
RAISE_VARARGS, 1
646645
};
647646

648647
PyCodeObject *
@@ -666,7 +665,7 @@ PyCode_NewEmpty(const char *filename, const char *funcname, int firstlineno)
666665
if (filename_ob == NULL) {
667666
goto failed;
668667
}
669-
code_ob = PyBytes_FromStringAndSize(assert0, 4);
668+
code_ob = PyBytes_FromStringAndSize(assert0, 6);
670669
if (code_ob == NULL) {
671670
goto failed;
672671
}

0 commit comments

Comments
 (0)