[LLVMdev] Spilling register and frame indices

Chris Lattner
Tue, 23 May 2006 18:04:36 -0000

On Tue, 23 May 2006, Vladimir Prus wrote:
> right now, LLVM does register spilling by:
>
> 1. Creating stack object
> 2. Passing index of that stack object to MRegisterInfo::storeRegToStackSlot
> 3. At later stage, frame indices are replaced by calling to
> MRegisterInfo::eliminateFrameIndex.
>
> This works for me, but there's slight problem. The target does not have
> "register + contant" addressing mode, so accessing frame index
should be
> done like this:
>
>   some_register = frame_pointer + offset
>         ...... [some_register]
>
> Since frame index eliminations happens after register allocation, I must
> make sure 'some_register' does not participate in normal register
> allocation.

Right.

> That approach sounds suboptimal. By "reserving" one register we
can already
> cause some values to be spilled, that otherwise would be stored in
> register.

Right.

PowerPC has the same problem in certain cases.  For example, vector loads
only support reg+reg addressing, which means you have to load the offset
from the stack pointer into a register before doing the load.

In the case of PPC, we currently just reserve a register for this purpose.
This is suboptimal, but doesn't cause a significant performance issue
normally.

> The lifetimes of those 'some_register' is likely to be very small
(1
> instruction), so "reserving" it everywhere is not good.
>
> Ideal approach would be to add a method to MRegisterInfo to spill specific
> virtual register. The implementation can then create code like:
>
>   virtual_register = frame_pointer + offset
>         [virtual_register]
>
> and then have 'virtual_register' allocated on next iteration of
register
> allocator?

This is one approach.  Another approach is to have to spiller scavange
registers, which is the subject of this enhancement request:
http://llvm.org/PR768

> Also, while RegAllocLocal and RegAllocSimple directly call
> storeRegToStackSlot, I would not found any calls to that method in
> RegAllocLinearScan. Am I missing something?

RegAllocLinearScan just does register assignment, then the code in
VirtRegMap.cpp (poorly named) actually takes the register assignment and
inserts/optimizes the spill code.

Depending on how severe this problem is for your target, I'd suggest just
reserving a register for this for now.  When you get to performance
tuning, and when this bubbles up to the top of the list, I'd suggest
working on PR768.

-Chris

--