[lra] force reg update after spilling to memory [PR120424]
In the added C++ testcase, a stack slot at a negative sp offset is
used to hold a value across a call.
There are a couple of causes that directly lead to this outcome:
- the -fstack-clash-protection and -fnon-call-exception options, that
cause arm_frame_pointer_required to flip from false to true when the
first pseudo gets spilled to memory;
- when the affected pseudo is spilled to memory, we fail to update lra
regno info, because the insns that reference it are already on the
lra_constraint_insn_stack;
There is another potentially-related issue:
- when we notice that the frame pointer can no longer be eliminated to
the stack pointer, we immediately clear can_eliminate, and also
prev_can_eliminate, but update_reg_eliminate relied on the latter to
tell that it needs to propagate a previous_offset to the
newly-selected elimination, or restore the original offsets.
This patch ensures that we update insn register info after spilling a
pseudo to memory, and enables update_reg_eliminate to recognize the
case in which a previously-preferred elimination is disabled
regardless of prev_can_eliminate.
for gcc/ChangeLog
PR rtl-optimization/120424
PR middle-end/118939
* lra-spills.cc (spill_pseudos): Update insn regno info.
* lra-eliminations.cc (update_reg_eliminate): Recognize
disabling of active elimination regardless of
prev_can_eliminate.