@@ -162,6 +162,7 @@ class Optimizer:
162162 label_prefix : str
163163 symbol_prefix : str
164164 re_global : re .Pattern [str ]
165+ frame_pointers : bool
165166 # The first block in the linked list:
166167 _root : _Block = dataclasses .field (init = False , default_factory = _Block )
167168 _labels : dict [str , _Block ] = dataclasses .field (init = False , default_factory = dict )
@@ -193,6 +194,7 @@ class Optimizer:
193194 _re_small_const_1 = _RE_NEVER_MATCH
194195 _re_small_const_2 = _RE_NEVER_MATCH
195196 const_reloc = "<Not supported>"
197+ _frame_pointer_modify : typing .ClassVar [re .Pattern [str ]] = _RE_NEVER_MATCH
196198
197199 def __post_init__ (self ) -> None :
198200 # Split the code into a linked list of basic blocks. A basic block is an
@@ -553,6 +555,16 @@ def _small_const_2(self, inst: Instruction) -> tuple[str, Instruction | None]:
553555 def _small_consts_match (self , inst1 : Instruction , inst2 : Instruction ) -> bool :
554556 raise NotImplementedError ()
555557
558+ def _validate (self ) -> None :
559+ for block in self ._blocks ():
560+ if not block .instructions :
561+ continue
562+ for inst in block .instructions :
563+ if self .frame_pointers :
564+ assert (
565+ self ._frame_pointer_modify .match (inst .text ) is None
566+ ), "Frame pointer should not be modified"
567+
556568 def run (self ) -> None :
557569 """Run this optimizer."""
558570 self ._insert_continue_label ()
@@ -565,6 +577,7 @@ def run(self) -> None:
565577 self ._remove_unreachable ()
566578 self ._fixup_external_labels ()
567579 self ._fixup_constants ()
580+ self ._validate ()
568581 self .path .write_text (self ._body ())
569582
570583
@@ -595,6 +608,7 @@ class OptimizerAArch64(Optimizer): # pylint: disable = too-few-public-methods
595608 r"\s*(?P<instruction>ldr)\s+.*(?P<value>_JIT_OP(ARG|ERAND(0|1))_(16|32)).*"
596609 )
597610 const_reloc = "CUSTOM_AARCH64_CONST"
611+ _frame_pointer_modify = re .compile (r"\s*stp\s+x29.*" )
598612
599613 def _get_reg (self , inst : Instruction ) -> str :
600614 _ , rest = inst .text .split (inst .name )
@@ -649,4 +663,5 @@ class OptimizerX86(Optimizer): # pylint: disable = too-few-public-methods
649663 # https://www.felixcloutier.com/x86/jmp
650664 _re_jump = re .compile (r"\s*jmp\s+(?P<target>[\w.]+)" )
651665 # https://www.felixcloutier.com/x86/ret
652- _re_return = re .compile (r"\s*ret\b" )
666+ _re_return = re .compile (r"\s*retq?\b" )
667+ _frame_pointer_modify = re .compile (r"\s*movq?\s+%(\w+),\s+%rbp.*" )
0 commit comments