diff options
| author | Jakob Stoklund Olesen <stoklund@2pi.dk> | 2011-02-08 18:50:21 +0000 |
|---|---|---|
| committer | Jakob Stoklund Olesen <stoklund@2pi.dk> | 2011-02-08 18:50:21 +0000 |
| commit | 17499351735563fa106044c8336f4114f351556f (patch) | |
| tree | be9785173e05985872fea0c09fca936a40db6aaa /llvm/lib/CodeGen/RegAllocGreedy.cpp | |
| parent | 3d11c8eaf2daaf7b84654371262be5e72ce8c1e7 (diff) | |
| download | bcm5719-llvm-17499351735563fa106044c8336f4114f351556f.tar.gz bcm5719-llvm-17499351735563fa106044c8336f4114f351556f.zip | |
Add SplitEditor::overlapIntv() to create small ranges where both registers are live.
If a live range is used by a terminator instruction, and that live range needs
to leave the block on the stack or in a different register, it can be necessary
to have both sides of the split live at the terminator instruction.
Example:
%vreg2 = COPY %vreg1
JMP %vreg1
Becomes after spilling %vreg2:
SPILL %vreg1
JMP %vreg1
The spill doesn't kill the register as is normally the case.
llvm-svn: 125102
Diffstat (limited to 'llvm/lib/CodeGen/RegAllocGreedy.cpp')
| -rw-r--r-- | llvm/lib/CodeGen/RegAllocGreedy.cpp | 27 |
1 files changed, 25 insertions, 2 deletions
diff --git a/llvm/lib/CodeGen/RegAllocGreedy.cpp b/llvm/lib/CodeGen/RegAllocGreedy.cpp index ff0c790f887..be01bdce44c 100644 --- a/llvm/lib/CodeGen/RegAllocGreedy.cpp +++ b/llvm/lib/CodeGen/RegAllocGreedy.cpp @@ -746,6 +746,7 @@ void RAGreedy::splitAroundRegion(LiveInterval &VirtReg, unsigned PhysReg, assert(Use <= BI.LastUse && "Couldn't find last use"); SlotIndex SegStart = SE.enterIntvBefore(Use); assert(SegStart >= IP.second && "Couldn't avoid interference"); + assert(SegStart < BI.LastSplitPoint && "Impossible split point"); SE.useIntv(SegStart, Stop); continue; } @@ -798,8 +799,30 @@ void RAGreedy::splitAroundRegion(LiveInterval &VirtReg, unsigned PhysReg, if (!RegOut) { // Block is live-through, but exit bundle is on the stack. // Spill immediately after the last use. - DEBUG(dbgs() << ", uses, stack-out.\n"); - SE.useIntv(Start, SE.leaveIntvAfter(BI.LastUse)); + if (BI.LastUse < BI.LastSplitPoint) { + DEBUG(dbgs() << ", uses, stack-out.\n"); + SE.useIntv(Start, SE.leaveIntvAfter(BI.LastUse)); + continue; + } + // The last use is after the last split point, it is probably an + // indirect jump. + DEBUG(dbgs() << ", uses at " << BI.LastUse << " after split point " + << BI.LastSplitPoint << ", stack-out.\n"); + SlotIndex SegEnd; + if (BI.LastSplitPoint == Start) + SegEnd = SE.leaveIntvAtTop(*BI.MBB); + else { + MachineBasicBlock::iterator I = + LIS->getInstructionFromIndex(BI.LastSplitPoint); + do assert(I != BI.MBB->begin() && "Expected instruction"); + while ((--I)->isDebugValue()); + SegEnd = SE.leaveIntvAfter(LIS->getInstructionIndex(I)); + } + SE.useIntv(Start, SegEnd); + // Run a double interval from the split to the last use. + // This makes it possible to spill the complement without affecting the + // indirect branch. + SE.overlapIntv(SegEnd, BI.LastUse); continue; } // Register is live-through. |

