gh-117139: Convert the evaluation stack to stack refs (#118450) · python/cpython@22b0de2
@@ -11,6 +11,7 @@ extern "C" {
1111#include <stdbool.h>
1212#include <stddef.h> // offsetof()
1313#include "pycore_code.h" // STATS
14+#include "pycore_stackref.h" // _PyStackRef
14151516/* See Objects/frame_layout.md for an explanation of the frame stack
1617 * including explanation of the PyFrameObject and _PyInterpreterFrame
@@ -67,7 +68,7 @@ typedef struct _PyInterpreterFrame {
6768uint16_t return_offset; /* Only relevant during a function call */
6869char owner;
6970/* Locals and stack */
70-PyObject *localsplus[1];
71+_PyStackRef localsplus[1];
7172} _PyInterpreterFrame;
72737374#define _PyInterpreterFrame_LASTI(IF) \
@@ -78,23 +79,23 @@ static inline PyCodeObject *_PyFrame_GetCode(_PyInterpreterFrame *f) {
7879return (PyCodeObject *)f->f_executable;
7980}
808181-static inline PyObject **_PyFrame_Stackbase(_PyInterpreterFrame *f) {
82-return f->localsplus + _PyFrame_GetCode(f)->co_nlocalsplus;
82+static inline _PyStackRef *_PyFrame_Stackbase(_PyInterpreterFrame *f) {
83+return (f->localsplus + _PyFrame_GetCode(f)->co_nlocalsplus);
8384}
848585-static inline PyObject *_PyFrame_StackPeek(_PyInterpreterFrame *f) {
86+static inline _PyStackRef _PyFrame_StackPeek(_PyInterpreterFrame *f) {
8687assert(f->stacktop > _PyFrame_GetCode(f)->co_nlocalsplus);
87-assert(f->localsplus[f->stacktop-1] != NULL);
88+assert(!PyStackRef_IsNull(f->localsplus[f->stacktop-1]));
8889return f->localsplus[f->stacktop-1];
8990}
909191-static inline PyObject *_PyFrame_StackPop(_PyInterpreterFrame *f) {
92+static inline _PyStackRef _PyFrame_StackPop(_PyInterpreterFrame *f) {
9293assert(f->stacktop > _PyFrame_GetCode(f)->co_nlocalsplus);
9394f->stacktop--;
9495return f->localsplus[f->stacktop];
9596}
969797-static inline void _PyFrame_StackPush(_PyInterpreterFrame *f, PyObject *value) {
98+static inline void _PyFrame_StackPush(_PyInterpreterFrame *f, _PyStackRef value) {
9899f->localsplus[f->stacktop] = value;
99100f->stacktop++;
100101}
@@ -143,14 +144,14 @@ _PyFrame_Initialize(
143144frame->owner = FRAME_OWNED_BY_THREAD;
144145145146for (int i = null_locals_from; i < code->co_nlocalsplus; i++) {
146-frame->localsplus[i] = NULL;
147+frame->localsplus[i] = PyStackRef_NULL;
147148 }
148149}
149150150151/* Gets the pointer to the locals array
151152 * that precedes this frame.
152153 */
153-static inline PyObject**
154+static inline _PyStackRef*
154155_PyFrame_GetLocalsArray(_PyInterpreterFrame *frame)
155156{
156157return frame->localsplus;
@@ -160,16 +161,16 @@ _PyFrame_GetLocalsArray(_PyInterpreterFrame *frame)
160161 Having stacktop <= 0 ensures that invalid
161162 values are not visible to the cycle GC.
162163 We choose -1 rather than 0 to assist debugging. */
163-static inline PyObject**
164+static inline _PyStackRef*
164165_PyFrame_GetStackPointer(_PyInterpreterFrame *frame)
165166{
166-PyObject **sp = frame->localsplus + frame->stacktop;
167+_PyStackRef *sp = frame->localsplus + frame->stacktop;
167168frame->stacktop = -1;
168169return sp;
169170}
170171171172static inline void
172-_PyFrame_SetStackPointer(_PyInterpreterFrame *frame, PyObject **stack_pointer)
173+_PyFrame_SetStackPointer(_PyInterpreterFrame *frame, _PyStackRef *stack_pointer)
173174{
174175frame->stacktop = (int)(stack_pointer - frame->localsplus);
175176}
@@ -309,7 +310,7 @@ _PyFrame_PushTrampolineUnchecked(PyThreadState *tstate, PyCodeObject *code, int
309310310311PyAPI_FUNC(_PyInterpreterFrame *)
311312_PyEvalFramePushAndInit(PyThreadState *tstate, PyFunctionObject *func,
312-PyObject *locals, PyObject* const* args,
313+PyObject *locals, _PyStackRef const* args,
313314size_t argcount, PyObject *kwnames);
314315315316#ifdef __cplusplus