You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
This repository was archived by the owner on Feb 13, 2025. It is now read-only.
Currently PyFrameObject and PyCFrameObject share the fields f_back and f_execute. The files f_execute is an Stackless specific addition to PyFrameObject.
I propose to remove the field f_execute from PyFrameObject and store the information previously held in f_execute in the field f_executing.
Rationale
The only possible values of PyFrameObject.f_execute are PyEval_EvalFrameEx_slp, slp_eval_frame_value, slp_eval_frame_noval, slp_eval_frame_setup_with, slp_eval_frame_with_cleanup, slp_eval_frame_yield_from and - in case of unpickling invalid frames - corresponding cannot_* functions.
Of these slp_eval_frame_noval, slp_eval_frame_setup_with, slp_eval_frame_with_cleanup and slp_eval_frame_yield_from are trivial wrappers around slp_eval_frame_value with an completely identical body.
* this function is identical to PyEval_EvalFrame_value.
* it serves as a marker whether we are inside of a
* WITH_CLEANUP operation.
* NOTE / XXX: see above.
*/
SLP_DO_NOT_OPTIMIZE_AWAY((char*)5);
r=slp_eval_frame_value(f, throwflag, retval);
returnr;
}
PyEval_EvalFrameEx_slp is also a fairly simple wrapper around slp_eval_frame_value. Differences in behavior between the five execution functions slp_eval_frame* is not caused by their body, but only by an if-block in slp_eval_frame_value:
That is, PyFrameObject.f_execute is already used as a flag and not as a dispatch pointer. We can replace it with the already existing field f_executing. This field is a boolean flag field:
0: frame is not executing
!0: frame is executing
C-Python stores only 0 and 1 in f_executing. Because C-Python makes no difference between various non-zero values of f_executing, it is possible to use values other than 1 to store the information currently encoded by different values of f_execute.
Now, if we drop the field f_execute from PyFrameObject we get the following benefits:
Unmodified PyFrameObject: better compatibility with C-Python. Eventually we can even support the frame evaluation API "eval_frame" defined in PEP 523 (see PyCharm pydevd debug crash #240).
Unmodified PyFrameObject: better maintainability.
We can remove the functions slp_eval_frame_noval, slp_eval_frame_setup_with, slp_eval_frame_with_cleanup, slp_eval_frame_yield_from
Probably it is possible to merge PyEval_EvalFrameEx_slp and slp_eval_frame_value. This would remove duplicated code in ceval.c and greatly improve maintainability.
Today I made a quick test implementation to prove, that the idea works. I'm going to create pull requests for the implementation.
The text was updated successfully, but these errors were encountered:
Stackless now uses an unmodified PyFrameObject structure. The field
PyFrameObject.f_executing now stores the information how to evaluate a
frame.
Additional consequences:
- all frame execution functions now take a "PyCFrameObject *" as first
argument.
- Pickled frames no contain f_executing instead of the name of the
execution function.
Currently
PyFrameObject
andPyCFrameObject
share the fieldsf_back
andf_execute
. The filesf_execute
is an Stackless specific addition toPyFrameObject
.I propose to remove the field
f_execute
fromPyFrameObject
and store the information previously held inf_execute
in the fieldf_executing
.Rationale
The only possible values of
PyFrameObject.f_execute
arePyEval_EvalFrameEx_slp
,slp_eval_frame_value
,slp_eval_frame_noval
,slp_eval_frame_setup_with
,slp_eval_frame_with_cleanup
,slp_eval_frame_yield_from
and - in case of unpickling invalid frames - correspondingcannot_*
functions.Of these
slp_eval_frame_noval
,slp_eval_frame_setup_with
,slp_eval_frame_with_cleanup
andslp_eval_frame_yield_from
are trivial wrappers aroundslp_eval_frame_value
with an completely identical body.stackless/Python/ceval.c
Lines 3840 to 3913 in 74f33db
PyEval_EvalFrameEx_slp
is also a fairly simple wrapper aroundslp_eval_frame_value
. Differences in behavior between the five execution functionsslp_eval_frame*
is not caused by their body, but only by anif
-block inslp_eval_frame_value
:stackless/Python/ceval.c
Lines 1090 to 1116 in 74f33db
That is,
PyFrameObject.f_execute
is already used as a flag and not as a dispatch pointer. We can replace it with the already existing fieldf_executing
. This field is a boolean flag field:C-Python stores only 0 and 1 in
f_executing
. Because C-Python makes no difference between various non-zero values off_executing
, it is possible to use values other than 1 to store the information currently encoded by different values off_execute
.Now, if we drop the field
f_execute
fromPyFrameObject
we get the following benefits:PyFrameObject
: better compatibility with C-Python. Eventually we can even support the frame evaluation API "eval_frame" defined in PEP 523 (see PyCharm pydevd debug crash #240).PyFrameObject
: better maintainability.slp_eval_frame_noval
,slp_eval_frame_setup_with
,slp_eval_frame_with_cleanup
,slp_eval_frame_yield_from
PyEval_EvalFrameEx_slp
andslp_eval_frame_value
. This would remove duplicated code in ceval.c and greatly improve maintainability.Today I made a quick test implementation to prove, that the idea works. I'm going to create pull requests for the implementation.
The text was updated successfully, but these errors were encountered: