[llvm-commits] CVS: llvm/lib/CodeGen/RegAlloc/PhyRegAlloc.cpp
Vikram Adve
vadve at cs.uiuc.edu
Fri Oct 11 11:13:01 PDT 2002
Changes in directory llvm/lib/CodeGen/RegAlloc:
PhyRegAlloc.cpp updated: 1.77 -> 1.78
---
Log message:
Major bug fix: spill code for an instruction in a delay slot was
merrily being inserted before/after the instruction!
---
Diffs of the changes:
Index: llvm/lib/CodeGen/RegAlloc/PhyRegAlloc.cpp
diff -u llvm/lib/CodeGen/RegAlloc/PhyRegAlloc.cpp:1.77 llvm/lib/CodeGen/RegAlloc/PhyRegAlloc.cpp:1.78
--- llvm/lib/CodeGen/RegAlloc/PhyRegAlloc.cpp:1.77 Sat Sep 28 12:02:40 2002
+++ llvm/lib/CodeGen/RegAlloc/PhyRegAlloc.cpp Fri Oct 11 11:12:40 2002
@@ -419,6 +419,32 @@
// Utility functions used below
//-----------------------------
inline void
+InsertBefore(MachineInstr* newMI,
+ MachineCodeForBasicBlock& MIVec,
+ MachineCodeForBasicBlock::iterator& MII)
+{
+ MII = MIVec.insert(MII, newMI);
+ ++MII;
+}
+
+inline void
+InsertAfter(MachineInstr* newMI,
+ MachineCodeForBasicBlock& MIVec,
+ MachineCodeForBasicBlock::iterator& MII)
+{
+ ++MII; // insert before the next instruction
+ MII = MIVec.insert(MII, newMI);
+}
+
+inline void
+SubstituteInPlace(MachineInstr* newMI,
+ MachineCodeForBasicBlock& MIVec,
+ MachineCodeForBasicBlock::iterator MII)
+{
+ *MII = newMI;
+}
+
+inline void
PrependInstructions(vector<MachineInstr *> &IBef,
MachineCodeForBasicBlock& MIVec,
MachineCodeForBasicBlock::iterator& MII,
@@ -434,8 +460,7 @@
if (OrigMI) cerr << "For MInst:\n " << *OrigMI;
cerr << msg << "PREPENDed instr:\n " << **AdIt << "\n";
}
- MII = MIVec.insert(MII, *AdIt);
- ++MII;
+ InsertBefore(*AdIt, MIVec, MII);
}
}
}
@@ -456,8 +481,7 @@
if (OrigMI) cerr << "For MInst:\n " << *OrigMI;
cerr << msg << "APPENDed instr:\n " << **AdIt << "\n";
}
- ++MII; // insert before the next instruction
- MII = MIVec.insert(MII, *AdIt);
+ InsertAfter(*AdIt, MIVec, MII);
}
}
}
@@ -477,7 +501,7 @@
for (Function::const_iterator BBI = Meth->begin(), BBE = Meth->end();
BBI != BBE; ++BBI) {
-
+
// iterate over all the machine instructions in BB
MachineCodeForBasicBlock &MIVec = MachineCodeForBasicBlock::get(BBI);
for (MachineCodeForBasicBlock::iterator MII = MIVec.begin();
@@ -538,13 +562,38 @@
insertCode4SpilledLR(LR, MInst, BBI, OpNum );
}
} // for each operand
-
-
+
// Now add instructions that the register allocator inserts before/after
// this machine instructions (done only for calls/rets/incoming args)
// We do this here, to ensure that spill for an instruction is inserted
// closest as possible to an instruction (see above insertCode4Spill...)
//
+ // First, if the instruction in the delay slot of a branch needs
+ // instructions inserted, move it out of the delay slot and before the
+ // branch because putting code before or after it would be VERY BAD!
+ //
+ unsigned bumpIteratorBy = 0;
+ if (MII != MIVec.begin())
+ if (unsigned predDelaySlots =
+ TM.getInstrInfo().getNumDelaySlots((*(MII-1))->getOpCode()))
+ {
+ assert(predDelaySlots==1 && "Not handling multiple delay slots!");
+ if (TM.getInstrInfo().isBranch((*(MII-1))->getOpCode())
+ && (AddedInstrMap.count(MInst) ||
+ AddedInstrMap[MInst].InstrnsAfter.size() > 0))
+ {
+ // Current instruction is in the delay slot of a branch and it
+ // needs spill code inserted before or after it.
+ // Move it before the preceding branch.
+ InsertBefore(MInst, MIVec, --MII);
+ MachineInstr* nopI =
+ new MachineInstr(TM.getInstrInfo().getNOPOpCode());
+ SubstituteInPlace(nopI, MIVec, MII+1); // replace orig with NOP
+ --MII; // point to MInst in new location
+ bumpIteratorBy = 2; // later skip the branch and the NOP!
+ }
+ }
+
// If there are instructions to be added, *before* this machine
// instruction, add them now.
//
@@ -561,9 +610,18 @@
// added after it must really go after the delayed instruction(s)
// So, we move the InstrAfter of the current instruction to the
// corresponding delayed instruction
-
- unsigned delay;
- if ((delay=TM.getInstrInfo().getNumDelaySlots(MInst->getOpCode())) >0){
+ if (unsigned delay =
+ TM.getInstrInfo().getNumDelaySlots(MInst->getOpCode())) {
+
+ // Delayed instructions are typically branches or calls. Let's make
+ // sure this is not a branch, otherwise "insert-after" is meaningless,
+ // and should never happen for any reason (spill code, register
+ // restores, etc.).
+ assert(! TM.getInstrInfo().isBranch(MInst->getOpCode()) &&
+ ! TM.getInstrInfo().isReturn(MInst->getOpCode()) &&
+ "INTERNAL ERROR: Register allocator should not be inserting "
+ "any code after a branch or return!");
+
move2DelayedInstr(MInst, *(MII+delay) );
}
else {
@@ -572,7 +630,11 @@
AppendInstructions(AddedInstrMap[MInst].InstrnsAfter, MIVec, MII,"");
} // if not delay
}
-
+
+ // If we mucked with the instruction order above, adjust the loop iterator
+ if (bumpIteratorBy)
+ MII = MII + bumpIteratorBy;
+
} // for each machine instruction
}
}
More information about the llvm-commits
mailing list