GH-128682: Account for escapes in DECREF_INPUTS (GH-129953)

* Handle escapes in DECREF_INPUTS

* Mark a few more functions as escaping

* Replace DECREF_INPUTS with PyStackRef_CLOSE where possible
This commit is contained in:
Mark Shannon 2025-02-12 17:44:59 +00:00 committed by GitHub
parent 3e222e3a15
commit 72f56654d0
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
18 changed files with 2228 additions and 921 deletions

View file

@ -15,6 +15,8 @@ class CWriter:
self.line_directives = line_directives
self.last_token = None
self.newline = True
self.pending_spill = False
self.pending_reload = False
def set_position(self, tkn: Token) -> None:
if self.last_token is not None:
@ -33,6 +35,7 @@ class CWriter:
self.newline = False
def emit_at(self, txt: str, where: Token) -> None:
self.maybe_write_spill()
self.set_position(where)
self.out.write(txt)
@ -109,6 +112,7 @@ class CWriter:
self.last_token = None
def emit(self, txt: str | Token) -> None:
self.maybe_write_spill()
if isinstance(txt, Token):
self.emit_token(txt)
elif isinstance(txt, str):
@ -122,6 +126,28 @@ class CWriter:
self.newline = True
self.last_token = None
def emit_spill(self) -> None:
if self.pending_reload:
self.pending_reload = False
return
assert not self.pending_spill
self.pending_spill = True
def maybe_write_spill(self) -> None:
if self.pending_spill:
self.pending_spill = False
self.emit_str("_PyFrame_SetStackPointer(frame, stack_pointer);\n")
elif self.pending_reload:
self.pending_reload = False
self.emit_str("stack_pointer = _PyFrame_GetStackPointer(frame);\n")
def emit_reload(self) -> None:
if self.pending_spill:
self.pending_spill = False
return
assert not self.pending_reload
self.pending_reload = True
@contextlib.contextmanager
def header_guard(self, name: str) -> Iterator[None]:
self.out.write(