blob: 95bd87f9505012fbff2f23728cd5987a8f5f043d [file] [log] [blame]
Chris Lattner029af0b2002-02-03 07:52:04 +00001//===-- SparcRegInfo.cpp - Sparc Target Register Information --------------===//
2//
3// This file contains implementation of Sparc specific helper methods
4// used for register allocation.
5//
6//===----------------------------------------------------------------------===//
7
Ruchira Sasankadfc6c882001-09-18 22:52:44 +00008#include "SparcInternals.h"
Chris Lattner5216cc52002-02-04 05:59:25 +00009#include "SparcRegClassInfo.h"
Misha Brukman7ae7f842002-10-28 00:28:31 +000010#include "llvm/CodeGen/MachineFunction.h"
Chris Lattnerd47aac92002-12-28 20:21:29 +000011#include "llvm/CodeGen/MachineFunctionInfo.h"
Ruchira Sasankadfc6c882001-09-18 22:52:44 +000012#include "llvm/CodeGen/PhyRegAlloc.h"
Vikram S. Advee9327f02002-05-19 15:25:51 +000013#include "llvm/CodeGen/InstrSelection.h"
Chris Lattner1ebaa902003-01-15 17:47:49 +000014#include "llvm/CodeGen/MachineInstrBuilder.h"
Anand Shuklae6c3ee62003-06-01 02:48:23 +000015#include "llvm/CodeGen/MachineCodeForInstruction.h"
Vikram S. Advee9327f02002-05-19 15:25:51 +000016#include "llvm/CodeGen/MachineInstrAnnot.h"
Chris Lattner24c1d5e2003-01-14 23:05:08 +000017#include "llvm/CodeGen/FunctionLiveVarInfo.h" // FIXME: Remove
Chris Lattner90fc6652003-01-15 19:50:44 +000018#include "../../CodeGen/RegAlloc/RegAllocCommon.h" // FIXME!
Chris Lattner5216cc52002-02-04 05:59:25 +000019#include "llvm/iTerminators.h"
20#include "llvm/iOther.h"
Chris Lattner06be1802002-04-09 19:08:28 +000021#include "llvm/Function.h"
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +000022#include "llvm/DerivedTypes.h"
Chris Lattnerb0ddffa2001-09-14 03:47:57 +000023
Chris Lattner24c1d5e2003-01-14 23:05:08 +000024enum {
25 BadRegClass = ~0
26};
27
Chris Lattner5216cc52002-02-04 05:59:25 +000028UltraSparcRegInfo::UltraSparcRegInfo(const UltraSparc &tgt)
Vikram S. Advea83804a2003-05-31 07:32:01 +000029 : TargetRegInfo(tgt), NumOfIntArgRegs(6), NumOfFloatArgRegs(32)
30{
Chris Lattner5216cc52002-02-04 05:59:25 +000031 MachineRegClassArr.push_back(new SparcIntRegClass(IntRegClassID));
32 MachineRegClassArr.push_back(new SparcFloatRegClass(FloatRegClassID));
33 MachineRegClassArr.push_back(new SparcIntCCRegClass(IntCCRegClassID));
34 MachineRegClassArr.push_back(new SparcFloatCCRegClass(FloatCCRegClassID));
Vikram S. Adve8adb9942003-05-27 00:02:22 +000035 MachineRegClassArr.push_back(new SparcSpecialRegClass(SpecialRegClassID));
Vikram S. Adveaee67012002-07-08 23:23:12 +000036
Chris Lattner56e91662002-08-12 21:25:05 +000037 assert(SparcFloatRegClass::StartOfNonVolatileRegs == 32 &&
Chris Lattner5216cc52002-02-04 05:59:25 +000038 "32 Float regs are used for float arg passing");
39}
40
41
Vikram S. Advedb1435f2002-03-18 03:12:16 +000042// getZeroRegNum - returns the register that contains always zero.
43// this is the unified register number
Chris Lattner5216cc52002-02-04 05:59:25 +000044//
Vikram S. Advedb1435f2002-03-18 03:12:16 +000045int UltraSparcRegInfo::getZeroRegNum() const {
Chris Lattner56e91662002-08-12 21:25:05 +000046 return getUnifiedRegNum(UltraSparcRegInfo::IntRegClassID,
47 SparcIntRegClass::g0);
Vikram S. Advedb1435f2002-03-18 03:12:16 +000048}
Chris Lattner5216cc52002-02-04 05:59:25 +000049
50// getCallAddressReg - returns the reg used for pushing the address when a
51// method is called. This can be used for other purposes between calls
52//
53unsigned UltraSparcRegInfo::getCallAddressReg() const {
Chris Lattner56e91662002-08-12 21:25:05 +000054 return getUnifiedRegNum(UltraSparcRegInfo::IntRegClassID,
55 SparcIntRegClass::o7);
Chris Lattner5216cc52002-02-04 05:59:25 +000056}
57
58// Returns the register containing the return address.
59// It should be made sure that this register contains the return
60// value when a return instruction is reached.
61//
62unsigned UltraSparcRegInfo::getReturnAddressReg() const {
Chris Lattner56e91662002-08-12 21:25:05 +000063 return getUnifiedRegNum(UltraSparcRegInfo::IntRegClassID,
64 SparcIntRegClass::i7);
65}
66
67// Register get name implementations...
68
69// Int register names in same order as enum in class SparcIntRegClass
70static const char * const IntRegNames[] = {
71 "o0", "o1", "o2", "o3", "o4", "o5", "o7",
72 "l0", "l1", "l2", "l3", "l4", "l5", "l6", "l7",
73 "i0", "i1", "i2", "i3", "i4", "i5",
74 "i6", "i7",
75 "g0", "g1", "g2", "g3", "g4", "g5", "g6", "g7",
76 "o6"
77};
78
Vikram S. Adve8adb9942003-05-27 00:02:22 +000079const char * const SparcIntRegClass::getRegName(unsigned reg) const {
Chris Lattner56e91662002-08-12 21:25:05 +000080 assert(reg < NumOfAllRegs);
81 return IntRegNames[reg];
82}
83
84static const char * const FloatRegNames[] = {
85 "f0", "f1", "f2", "f3", "f4", "f5", "f6", "f7", "f8", "f9",
86 "f10", "f11", "f12", "f13", "f14", "f15", "f16", "f17", "f18", "f19",
87 "f20", "f21", "f22", "f23", "f24", "f25", "f26", "f27", "f28", "f29",
88 "f30", "f31", "f32", "f33", "f34", "f35", "f36", "f37", "f38", "f39",
89 "f40", "f41", "f42", "f43", "f44", "f45", "f46", "f47", "f48", "f49",
90 "f50", "f51", "f52", "f53", "f54", "f55", "f56", "f57", "f58", "f59",
91 "f60", "f61", "f62", "f63"
92};
93
Vikram S. Adve8adb9942003-05-27 00:02:22 +000094const char * const SparcFloatRegClass::getRegName(unsigned reg) const {
Chris Lattner56e91662002-08-12 21:25:05 +000095 assert (reg < NumOfAllRegs);
96 return FloatRegNames[reg];
97}
98
99
100static const char * const IntCCRegNames[] = {
101 "xcc", "ccr"
102};
103
Vikram S. Adve8adb9942003-05-27 00:02:22 +0000104const char * const SparcIntCCRegClass::getRegName(unsigned reg) const {
Chris Lattner56e91662002-08-12 21:25:05 +0000105 assert(reg < 2);
106 return IntCCRegNames[reg];
107}
108
109static const char * const FloatCCRegNames[] = {
110 "fcc0", "fcc1", "fcc2", "fcc3"
111};
112
Vikram S. Adve8adb9942003-05-27 00:02:22 +0000113const char * const SparcFloatCCRegClass::getRegName(unsigned reg) const {
114 assert (reg < 5);
Chris Lattner56e91662002-08-12 21:25:05 +0000115 return FloatCCRegNames[reg];
Chris Lattner5216cc52002-02-04 05:59:25 +0000116}
117
Vikram S. Adve8adb9942003-05-27 00:02:22 +0000118static const char * const SpecialRegNames[] = {
119 "fsr"
120};
121
122const char * const SparcSpecialRegClass::getRegName(unsigned reg) const {
123 assert (reg < 1);
124 return SpecialRegNames[reg];
Chris Lattner5216cc52002-02-04 05:59:25 +0000125}
126
Vikram S. Advedb1435f2002-03-18 03:12:16 +0000127// Get unified reg number for frame pointer
Chris Lattner5216cc52002-02-04 05:59:25 +0000128unsigned UltraSparcRegInfo::getFramePointer() const {
Chris Lattner56e91662002-08-12 21:25:05 +0000129 return getUnifiedRegNum(UltraSparcRegInfo::IntRegClassID,
130 SparcIntRegClass::i6);
Chris Lattner5216cc52002-02-04 05:59:25 +0000131}
132
Vikram S. Advedb1435f2002-03-18 03:12:16 +0000133// Get unified reg number for stack pointer
Chris Lattner5216cc52002-02-04 05:59:25 +0000134unsigned UltraSparcRegInfo::getStackPointer() const {
Chris Lattner56e91662002-08-12 21:25:05 +0000135 return getUnifiedRegNum(UltraSparcRegInfo::IntRegClassID,
136 SparcIntRegClass::o6);
Chris Lattner5216cc52002-02-04 05:59:25 +0000137}
138
139
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000140//---------------------------------------------------------------------------
141// Finds whether a call is an indirect call
142//---------------------------------------------------------------------------
143
144inline bool
145isVarArgsFunction(const Type *funcType) {
146 return cast<FunctionType>(cast<PointerType>(funcType)
147 ->getElementType())->isVarArg();
148}
149
150inline bool
151isVarArgsCall(const MachineInstr *CallMI) {
152 Value* callee = CallMI->getOperand(0).getVRegValue();
153 // const Type* funcType = isa<Function>(callee)? callee->getType()
154 // : cast<PointerType>(callee->getType())->getElementType();
155 const Type* funcType = callee->getType();
156 return isVarArgsFunction(funcType);
157}
158
159
Vikram S. Advea83804a2003-05-31 07:32:01 +0000160// Get the register number for the specified argument #argNo,
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000161//
162// Return value:
Vikram S. Advea83804a2003-05-31 07:32:01 +0000163// getInvalidRegNum(), if there is no int register available for the arg.
164// regNum, otherwise (this is NOT the unified reg. num).
165// regClassId is set to the register class ID.
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000166//
Vikram S. Advea83804a2003-05-31 07:32:01 +0000167int
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000168UltraSparcRegInfo::regNumForIntArg(bool inCallee, bool isVarArgsCall,
Vikram S. Advea83804a2003-05-31 07:32:01 +0000169 unsigned argNo, unsigned& regClassId) const
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000170{
Vikram S. Advee9327f02002-05-19 15:25:51 +0000171 regClassId = IntRegClassID;
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000172 if (argNo >= NumOfIntArgRegs)
Vikram S. Advea83804a2003-05-31 07:32:01 +0000173 return getInvalidRegNum();
Vikram S. Advee9327f02002-05-19 15:25:51 +0000174 else
Chris Lattner56e91662002-08-12 21:25:05 +0000175 return argNo + (inCallee? SparcIntRegClass::i0 : SparcIntRegClass::o0);
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000176}
177
Vikram S. Advea83804a2003-05-31 07:32:01 +0000178// Get the register number for the specified FP argument #argNo,
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000179// Use INT regs for FP args if this is a varargs call.
180//
181// Return value:
Vikram S. Advea83804a2003-05-31 07:32:01 +0000182// getInvalidRegNum(), if there is no int register available for the arg.
183// regNum, otherwise (this is NOT the unified reg. num).
184// regClassId is set to the register class ID.
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000185//
Vikram S. Advea83804a2003-05-31 07:32:01 +0000186int
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000187UltraSparcRegInfo::regNumForFPArg(unsigned regType,
188 bool inCallee, bool isVarArgsCall,
Vikram S. Advea83804a2003-05-31 07:32:01 +0000189 unsigned argNo, unsigned& regClassId) const
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000190{
Vikram S. Advee9327f02002-05-19 15:25:51 +0000191 if (isVarArgsCall)
Vikram S. Advea83804a2003-05-31 07:32:01 +0000192 return regNumForIntArg(inCallee, isVarArgsCall, argNo, regClassId);
Vikram S. Advee9327f02002-05-19 15:25:51 +0000193 else
194 {
195 regClassId = FloatRegClassID;
196 if (regType == FPSingleRegType)
197 return (argNo*2+1 >= NumOfFloatArgRegs)?
Vikram S. Advea83804a2003-05-31 07:32:01 +0000198 getInvalidRegNum() : SparcFloatRegClass::f0 + (argNo * 2 + 1);
Vikram S. Advee9327f02002-05-19 15:25:51 +0000199 else if (regType == FPDoubleRegType)
200 return (argNo*2 >= NumOfFloatArgRegs)?
Vikram S. Advea83804a2003-05-31 07:32:01 +0000201 getInvalidRegNum() : SparcFloatRegClass::f0 + (argNo * 2);
Vikram S. Advee9327f02002-05-19 15:25:51 +0000202 else
203 assert(0 && "Illegal FP register type");
Chris Lattner3091e112002-07-25 06:08:32 +0000204 return 0;
Vikram S. Advee9327f02002-05-19 15:25:51 +0000205 }
Vikram S. Adve02662bd2002-03-31 19:04:50 +0000206}
207
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000208
209//---------------------------------------------------------------------------
210// Finds the return address of a call sparc specific call instruction
211//---------------------------------------------------------------------------
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000212
Vikram S. Adveaee67012002-07-08 23:23:12 +0000213// The following 4 methods are used to find the RegType (SparcInternals.h)
Vikram S. Advee9327f02002-05-19 15:25:51 +0000214// of a LiveRange, a Value, and for a given register unified reg number.
Chris Lattner5216cc52002-02-04 05:59:25 +0000215//
Vikram S. Adve8adb9942003-05-27 00:02:22 +0000216int UltraSparcRegInfo::getRegTypeForClassAndType(unsigned regClassID,
217 const Type* type) const
218{
Vikram S. Advee9327f02002-05-19 15:25:51 +0000219 switch (regClassID) {
Vikram S. Adve8adb9942003-05-27 00:02:22 +0000220 case IntRegClassID: return IntRegType;
221 case FloatRegClassID:
222 if (type == Type::FloatTy) return FPSingleRegType;
223 else if (type == Type::DoubleTy) return FPDoubleRegType;
224 assert(0 && "Unknown type in FloatRegClass"); return 0;
225 case IntCCRegClassID: return IntCCRegType;
226 case FloatCCRegClassID: return FloatCCRegType;
227 case SpecialRegClassID: return SpecialRegType;
Vikram S. Advee9327f02002-05-19 15:25:51 +0000228 default: assert( 0 && "Unknown reg class ID"); return 0;
Chris Lattner5216cc52002-02-04 05:59:25 +0000229 }
230}
231
Vikram S. Adve8adb9942003-05-27 00:02:22 +0000232int UltraSparcRegInfo::getRegType(const Type* type) const
233{
234 return getRegTypeForClassAndType(getRegClassIDOfType(type), type);
Vikram S. Advee9327f02002-05-19 15:25:51 +0000235}
236
Vikram S. Adve8adb9942003-05-27 00:02:22 +0000237int UltraSparcRegInfo::getRegType(const LiveRange *LR) const
238{
239 return getRegTypeForClassAndType(LR->getRegClassID(), LR->getType());
240}
Chris Lattner5216cc52002-02-04 05:59:25 +0000241
Vikram S. Adve8adb9942003-05-27 00:02:22 +0000242int UltraSparcRegInfo::getRegType(int unifiedRegNum) const
243{
Vikram S. Adveaee67012002-07-08 23:23:12 +0000244 if (unifiedRegNum < 32)
Chris Lattner5216cc52002-02-04 05:59:25 +0000245 return IntRegType;
Vikram S. Adveaee67012002-07-08 23:23:12 +0000246 else if (unifiedRegNum < (32 + 32))
Chris Lattner5216cc52002-02-04 05:59:25 +0000247 return FPSingleRegType;
Vikram S. Adveaee67012002-07-08 23:23:12 +0000248 else if (unifiedRegNum < (64 + 32))
Chris Lattner5216cc52002-02-04 05:59:25 +0000249 return FPDoubleRegType;
Vikram S. Adveaee67012002-07-08 23:23:12 +0000250 else if (unifiedRegNum < (64+32+4))
Chris Lattner5216cc52002-02-04 05:59:25 +0000251 return FloatCCRegType;
Vikram S. Adveaee67012002-07-08 23:23:12 +0000252 else if (unifiedRegNum < (64+32+4+2))
Chris Lattner5216cc52002-02-04 05:59:25 +0000253 return IntCCRegType;
254 else
Vikram S. Adveaee67012002-07-08 23:23:12 +0000255 assert(0 && "Invalid unified register number in getRegType");
Chris Lattner5536c9c2002-02-24 23:02:40 +0000256 return 0;
Chris Lattner5216cc52002-02-04 05:59:25 +0000257}
258
259
Vikram S. Adveaee67012002-07-08 23:23:12 +0000260// To find the register class used for a specified Type
261//
262unsigned UltraSparcRegInfo::getRegClassIDOfType(const Type *type,
Chris Lattner3091e112002-07-25 06:08:32 +0000263 bool isCCReg) const {
Vikram S. Adveaee67012002-07-08 23:23:12 +0000264 Type::PrimitiveID ty = type->getPrimitiveID();
265 unsigned res;
266
267 // FIXME: Comparing types like this isn't very safe...
268 if ((ty && ty <= Type::LongTyID) || (ty == Type::LabelTyID) ||
269 (ty == Type::FunctionTyID) || (ty == Type::PointerTyID) )
270 res = IntRegClassID; // sparc int reg (ty=0: void)
271 else if (ty <= Type::DoubleTyID)
272 res = FloatRegClassID; // sparc float reg class
273 else {
274 //std::cerr << "TypeID: " << ty << "\n";
275 assert(0 && "Cannot resolve register class for type");
276 return 0;
277 }
278
Chris Lattnerf9fd5912003-01-15 21:14:32 +0000279 if (isCCReg)
280 return res + 2; // corresponding condition code register
Vikram S. Adveaee67012002-07-08 23:23:12 +0000281 else
282 return res;
283}
284
Vikram S. Adveaee67012002-07-08 23:23:12 +0000285unsigned UltraSparcRegInfo::getRegClassIDOfRegType(int regType) const {
286 switch(regType) {
287 case IntRegType: return IntRegClassID;
288 case FPSingleRegType:
289 case FPDoubleRegType: return FloatRegClassID;
290 case IntCCRegType: return IntCCRegClassID;
291 case FloatCCRegType: return FloatCCRegClassID;
292 default:
293 assert(0 && "Invalid register type in getRegClassIDOfRegType");
294 return 0;
295 }
296}
297
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000298//---------------------------------------------------------------------------
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000299// Suggests a register for the ret address in the RET machine instruction.
300// We always suggest %i7 by convention.
301//---------------------------------------------------------------------------
Vikram S. Adveaee67012002-07-08 23:23:12 +0000302void UltraSparcRegInfo::suggestReg4RetAddr(MachineInstr *RetMI,
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000303 LiveRangeInfo& LRI) const {
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000304
Vikram S. Adveaee67012002-07-08 23:23:12 +0000305 assert(target.getInstrInfo().isReturn(RetMI->getOpCode()));
Vikram S. Adve84982772001-10-22 13:41:12 +0000306
Vikram S. Adveaee67012002-07-08 23:23:12 +0000307 // return address is always mapped to i7 so set it immediately
308 RetMI->SetRegForOperand(0, getUnifiedRegNum(IntRegClassID,
Chris Lattner56e91662002-08-12 21:25:05 +0000309 SparcIntRegClass::i7));
Vikram S. Adve84982772001-10-22 13:41:12 +0000310
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000311 // Possible Optimization:
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +0000312 // Instead of setting the color, we can suggest one. In that case,
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000313 // we have to test later whether it received the suggested color.
314 // In that case, a LR has to be created at the start of method.
315 // It has to be done as follows (remove the setRegVal above):
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000316
Vikram S. Adveaee67012002-07-08 23:23:12 +0000317 // MachineOperand & MO = RetMI->getOperand(0);
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000318 // const Value *RetAddrVal = MO.getVRegValue();
319 // assert( RetAddrVal && "LR for ret address must be created at start");
320 // LiveRange * RetAddrLR = LRI.getLiveRangeForValue( RetAddrVal);
321 // RetAddrLR->setSuggestedColor(getUnifiedRegNum( IntRegClassID,
Vikram S. Adveaee67012002-07-08 23:23:12 +0000322 // SparcIntRegOrdr::i7) );
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000323}
324
325
326//---------------------------------------------------------------------------
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000327// Suggests a register for the ret address in the JMPL/CALL machine instr.
328// Sparc ABI dictates that %o7 be used for this purpose.
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000329//---------------------------------------------------------------------------
Vikram S. Adve6d1036d2002-09-28 16:59:05 +0000330void
331UltraSparcRegInfo::suggestReg4CallAddr(MachineInstr * CallMI,
332 LiveRangeInfo& LRI) const
333{
Vikram S. Advee9327f02002-05-19 15:25:51 +0000334 CallArgsDescriptor* argDesc = CallArgsDescriptor::get(CallMI);
335 const Value *RetAddrVal = argDesc->getReturnAddrReg();
Vikram S. Adve6d1036d2002-09-28 16:59:05 +0000336 assert(RetAddrVal && "INTERNAL ERROR: Return address value is required");
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000337
Vikram S. Adve6d1036d2002-09-28 16:59:05 +0000338 // A LR must already exist for the return address.
339 LiveRange *RetAddrLR = LRI.getLiveRangeForValue(RetAddrVal);
340 assert(RetAddrLR && "INTERNAL ERROR: No LR for return address of call!");
341
Chris Lattnerf9fd5912003-01-15 21:14:32 +0000342 unsigned RegClassID = RetAddrLR->getRegClassID();
Vikram S. Adve6d1036d2002-09-28 16:59:05 +0000343 RetAddrLR->setColor(getUnifiedRegNum(IntRegClassID, SparcIntRegClass::o7));
344}
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000345
346
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000347
348//---------------------------------------------------------------------------
349// This method will suggest colors to incoming args to a method.
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000350// According to the Sparc ABI, the first 6 incoming args are in
351// %i0 - %i5 (if they are integer) OR in %f0 - %f31 (if they are float).
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000352// If the arg is passed on stack due to the lack of regs, NOTHING will be
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000353// done - it will be colored (or spilled) as a normal live range.
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000354//---------------------------------------------------------------------------
Chris Lattnerf739fa82002-04-08 22:03:57 +0000355void UltraSparcRegInfo::suggestRegs4MethodArgs(const Function *Meth,
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000356 LiveRangeInfo& LRI) const
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000357{
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000358 // check if this is a varArgs function. needed for choosing regs.
359 bool isVarArgs = isVarArgsFunction(Meth->getType());
360
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000361 // for each argument. count INT and FP arguments separately.
Chris Lattner7076ff22002-06-25 16:13:21 +0000362 unsigned argNo=0, intArgNo=0, fpArgNo=0;
363 for(Function::const_aiterator I = Meth->abegin(), E = Meth->aend();
364 I != E; ++I, ++argNo) {
365 // get the LR of arg
366 LiveRange *LR = LRI.getLiveRangeForValue(I);
367 assert(LR && "No live range found for method arg");
368
369 unsigned regType = getRegType(LR);
Chris Lattner24c1d5e2003-01-14 23:05:08 +0000370 unsigned regClassIDOfArgReg = BadRegClass; // reg class of chosen reg (unused)
Chris Lattner7076ff22002-06-25 16:13:21 +0000371
372 int regNum = (regType == IntRegType)
373 ? regNumForIntArg(/*inCallee*/ true, isVarArgs,
Vikram S. Advea83804a2003-05-31 07:32:01 +0000374 argNo, regClassIDOfArgReg)
Chris Lattner7076ff22002-06-25 16:13:21 +0000375 : regNumForFPArg(regType, /*inCallee*/ true, isVarArgs,
Vikram S. Advea83804a2003-05-31 07:32:01 +0000376 argNo, regClassIDOfArgReg);
Chris Lattner7076ff22002-06-25 16:13:21 +0000377
Vikram S. Advea83804a2003-05-31 07:32:01 +0000378 if(regNum != getInvalidRegNum())
Chris Lattner7076ff22002-06-25 16:13:21 +0000379 LR->setSuggestedColor(regNum);
380 }
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000381}
382
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000383
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000384//---------------------------------------------------------------------------
385// This method is called after graph coloring to move incoming args to
386// the correct hardware registers if they did not receive the correct
387// (suggested) color through graph coloring.
388//---------------------------------------------------------------------------
Chris Lattnerf739fa82002-04-08 22:03:57 +0000389void UltraSparcRegInfo::colorMethodArgs(const Function *Meth,
Chris Lattner5216cc52002-02-04 05:59:25 +0000390 LiveRangeInfo &LRI,
391 AddedInstrns *FirstAI) const {
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000392
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000393 // check if this is a varArgs function. needed for choosing regs.
394 bool isVarArgs = isVarArgsFunction(Meth->getType());
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000395 MachineInstr *AdMI;
396
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000397 // for each argument
Chris Lattner7076ff22002-06-25 16:13:21 +0000398 // for each argument. count INT and FP arguments separately.
399 unsigned argNo=0, intArgNo=0, fpArgNo=0;
400 for(Function::const_aiterator I = Meth->abegin(), E = Meth->aend();
401 I != E; ++I, ++argNo) {
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000402 // get the LR of arg
Chris Lattner7076ff22002-06-25 16:13:21 +0000403 LiveRange *LR = LRI.getLiveRangeForValue(I);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000404 assert( LR && "No live range found for method arg");
405
Chris Lattnerf9fd5912003-01-15 21:14:32 +0000406 unsigned regType = getRegType(LR);
407 unsigned RegClassID = LR->getRegClassID();
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000408
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000409 // Find whether this argument is coming in a register (if not, on stack)
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000410 // Also find the correct register the argument must use (UniArgReg)
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000411 //
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000412 bool isArgInReg = false;
Vikram S. Advea83804a2003-05-31 07:32:01 +0000413 unsigned UniArgReg = getInvalidRegNum(); // reg that LR MUST be colored with
Chris Lattner24c1d5e2003-01-14 23:05:08 +0000414 unsigned regClassIDOfArgReg = BadRegClass; // reg class of chosen reg
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000415
416 int regNum = (regType == IntRegType)
Vikram S. Advee9327f02002-05-19 15:25:51 +0000417 ? regNumForIntArg(/*inCallee*/ true, isVarArgs,
Vikram S. Advea83804a2003-05-31 07:32:01 +0000418 argNo, regClassIDOfArgReg)
Vikram S. Advee9327f02002-05-19 15:25:51 +0000419 : regNumForFPArg(regType, /*inCallee*/ true, isVarArgs,
Vikram S. Advea83804a2003-05-31 07:32:01 +0000420 argNo, regClassIDOfArgReg);
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000421
Vikram S. Advea83804a2003-05-31 07:32:01 +0000422 if(regNum != getInvalidRegNum()) {
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000423 isArgInReg = true;
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000424 UniArgReg = getUnifiedRegNum( regClassIDOfArgReg, regNum);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000425 }
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000426
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000427 if( LR->hasColor() ) { // if this arg received a register
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000428
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000429 unsigned UniLRReg = getUnifiedRegNum( RegClassID, LR->getColor() );
430
431 // if LR received the correct color, nothing to do
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000432 //
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000433 if( UniLRReg == UniArgReg )
434 continue;
435
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000436 // We are here because the LR did not receive the suggested
437 // but LR received another register.
438 // Now we have to copy the %i reg (or stack pos of arg)
439 // to the register the LR was colored with.
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000440
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000441 // if the arg is coming in UniArgReg register, it MUST go into
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000442 // the UniLRReg register
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000443 //
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000444 if( isArgInReg ) {
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000445 if( regClassIDOfArgReg != RegClassID ) {
Vikram S. Advee9327f02002-05-19 15:25:51 +0000446 assert(0 && "This could should work but it is not tested yet");
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000447
448 // It is a variable argument call: the float reg must go in a %o reg.
449 // We have to move an int reg to a float reg via memory.
450 //
451 assert(isVarArgs &&
452 RegClassID == FloatRegClassID &&
453 regClassIDOfArgReg == IntRegClassID &&
454 "This should only be an Int register for an FP argument");
455
Chris Lattnerd47aac92002-12-28 20:21:29 +0000456 int TmpOff = MachineFunction::get(Meth).getInfo()->pushTempValue(
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000457 getSpilledRegSize(regType));
Vikram S. Adveaee67012002-07-08 23:23:12 +0000458 cpReg2MemMI(FirstAI->InstrnsBefore,
459 UniArgReg, getFramePointer(), TmpOff, IntRegType);
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000460
Vikram S. Adveaee67012002-07-08 23:23:12 +0000461 cpMem2RegMI(FirstAI->InstrnsBefore,
462 getFramePointer(), TmpOff, UniLRReg, regType);
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000463 }
464 else {
Vikram S. Adveaee67012002-07-08 23:23:12 +0000465 cpReg2RegMI(FirstAI->InstrnsBefore, UniArgReg, UniLRReg, regType);
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000466 }
467 }
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000468 else {
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000469
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000470 // Now the arg is coming on stack. Since the LR recieved a register,
471 // we just have to load the arg on stack into that register
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000472 //
Chris Lattnerd47aac92002-12-28 20:21:29 +0000473 const TargetFrameInfo& frameInfo = target.getFrameInfo();
Vikram S. Adve7a1524f2001-11-08 04:56:41 +0000474 int offsetFromFP =
Misha Brukman7ae7f842002-10-28 00:28:31 +0000475 frameInfo.getIncomingArgOffset(MachineFunction::get(Meth),
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000476 argNo);
Vikram S. Advea83804a2003-05-31 07:32:01 +0000477
478 // float arguments on stack are right justified so adjust the offset!
479 // int arguments are also right justified but they are always loaded as
480 // a full double-word so the offset does not need to be adjusted.
481 if (regType == FPSingleRegType) {
482 unsigned argSize = target.getTargetData().getTypeSize(LR->getType());
483 unsigned slotSize = frameInfo.getSizeOfEachArgOnStack();
484 assert(argSize <= slotSize && "Insufficient slot size!");
485 offsetFromFP += slotSize - argSize;
486 }
487
Vikram S. Adveaee67012002-07-08 23:23:12 +0000488 cpMem2RegMI(FirstAI->InstrnsBefore,
489 getFramePointer(), offsetFromFP, UniLRReg, regType);
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000490 }
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000491
492 } // if LR received a color
493
494 else {
495
496 // Now, the LR did not receive a color. But it has a stack offset for
497 // spilling.
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000498 // So, if the arg is coming in UniArgReg register, we can just move
499 // that on to the stack pos of LR
500
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000501 if( isArgInReg ) {
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000502
503 if( regClassIDOfArgReg != RegClassID ) {
504 assert(0 &&
505 "FP arguments to a varargs function should be explicitly "
506 "copied to/from int registers by instruction selection!");
507
508 // It must be a float arg for a variable argument call, which
509 // must come in a %o reg. Move the int reg to the stack.
510 //
511 assert(isVarArgs && regClassIDOfArgReg == IntRegClassID &&
512 "This should only be an Int register for an FP argument");
513
Vikram S. Adveaee67012002-07-08 23:23:12 +0000514 cpReg2MemMI(FirstAI->InstrnsBefore, UniArgReg,
515 getFramePointer(), LR->getSpillOffFromFP(), IntRegType);
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000516 }
517 else {
Vikram S. Adveaee67012002-07-08 23:23:12 +0000518 cpReg2MemMI(FirstAI->InstrnsBefore, UniArgReg,
519 getFramePointer(), LR->getSpillOffFromFP(), regType);
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000520 }
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000521 }
522
523 else {
524
525 // Now the arg is coming on stack. Since the LR did NOT
526 // recieved a register as well, it is allocated a stack position. We
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000527 // can simply change the stack position of the LR. We can do this,
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000528 // since this method is called before any other method that makes
529 // uses of the stack pos of the LR (e.g., updateMachineInstr)
Vikram S. Advea83804a2003-05-31 07:32:01 +0000530 //
Chris Lattnerd47aac92002-12-28 20:21:29 +0000531 const TargetFrameInfo& frameInfo = target.getFrameInfo();
Vikram S. Adve7a1524f2001-11-08 04:56:41 +0000532 int offsetFromFP =
Misha Brukman7ae7f842002-10-28 00:28:31 +0000533 frameInfo.getIncomingArgOffset(MachineFunction::get(Meth),
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000534 argNo);
Vikram S. Advea83804a2003-05-31 07:32:01 +0000535
536 // FP arguments on stack are right justified so adjust offset!
537 // int arguments are also right justified but they are always loaded as
538 // a full double-word so the offset does not need to be adjusted.
539 if (regType == FPSingleRegType) {
540 unsigned argSize = target.getTargetData().getTypeSize(LR->getType());
541 unsigned slotSize = frameInfo.getSizeOfEachArgOnStack();
542 assert(argSize <= slotSize && "Insufficient slot size!");
543 offsetFromFP += slotSize - argSize;
544 }
Vikram S. Adve7a1524f2001-11-08 04:56:41 +0000545
546 LR->modifySpillOffFromFP( offsetFromFP );
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000547 }
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000548
549 }
550
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000551 } // for each incoming argument
552
553}
554
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000555
556
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000557//---------------------------------------------------------------------------
558// This method is called before graph coloring to suggest colors to the
559// outgoing call args and the return value of the call.
560//---------------------------------------------------------------------------
Vikram S. Adveaee67012002-07-08 23:23:12 +0000561void UltraSparcRegInfo::suggestRegs4CallArgs(MachineInstr *CallMI,
Vikram S. Adve6d1036d2002-09-28 16:59:05 +0000562 LiveRangeInfo& LRI) const {
Vikram S. Adve879eac92002-10-13 00:05:30 +0000563 assert ( (target.getInstrInfo()).isCall(CallMI->getOpCode()) );
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000564
Vikram S. Advee9327f02002-05-19 15:25:51 +0000565 CallArgsDescriptor* argDesc = CallArgsDescriptor::get(CallMI);
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000566
Vikram S. Adve6d1036d2002-09-28 16:59:05 +0000567 suggestReg4CallAddr(CallMI, LRI);
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000568
Vikram S. Adve6d1036d2002-09-28 16:59:05 +0000569 // First color the return value of the call instruction, if any.
570 // The return value will be in %o0 if the value is an integer type,
571 // or in %f0 if the value is a float type.
572 //
573 if (const Value *RetVal = argDesc->getReturnValue()) {
574 LiveRange *RetValLR = LRI.getLiveRangeForValue(RetVal);
575 assert(RetValLR && "No LR for return Value of call!");
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000576
Chris Lattnerf9fd5912003-01-15 21:14:32 +0000577 unsigned RegClassID = RetValLR->getRegClassID();
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000578
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000579 // now suggest a register depending on the register class of ret arg
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000580 if( RegClassID == IntRegClassID )
Chris Lattner56e91662002-08-12 21:25:05 +0000581 RetValLR->setSuggestedColor(SparcIntRegClass::o0);
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000582 else if (RegClassID == FloatRegClassID )
Chris Lattner56e91662002-08-12 21:25:05 +0000583 RetValLR->setSuggestedColor(SparcFloatRegClass::f0 );
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000584 else assert( 0 && "Unknown reg class for return value of call\n");
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000585 }
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000586
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000587 // Now suggest colors for arguments (operands) of the call instruction.
588 // Colors are suggested only if the arg number is smaller than the
589 // the number of registers allocated for argument passing.
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000590 // Now, go thru call args - implicit operands of the call MI
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000591
Vikram S. Advee9327f02002-05-19 15:25:51 +0000592 unsigned NumOfCallArgs = argDesc->getNumArgs();
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000593
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000594 for(unsigned argNo=0, i=0, intArgNo=0, fpArgNo=0;
595 i < NumOfCallArgs; ++i, ++argNo) {
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000596
Vikram S. Advee9327f02002-05-19 15:25:51 +0000597 const Value *CallArg = argDesc->getArgInfo(i).getArgVal();
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000598
599 // get the LR of call operand (parameter)
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000600 LiveRange *const LR = LRI.getLiveRangeForValue(CallArg);
Vikram S. Advea83804a2003-05-31 07:32:01 +0000601 if (!LR)
602 continue; // no live ranges for constants and labels
Vikram S. Adve6d1036d2002-09-28 16:59:05 +0000603
Chris Lattnerf9fd5912003-01-15 21:14:32 +0000604 unsigned regType = getRegType(LR);
Vikram S. Advea83804a2003-05-31 07:32:01 +0000605 unsigned regClassIDOfArgReg = BadRegClass; // chosen reg class (unused)
Vikram S. Adve6d1036d2002-09-28 16:59:05 +0000606
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000607 // Choose a register for this arg depending on whether it is
Vikram S. Advee9327f02002-05-19 15:25:51 +0000608 // an INT or FP value. Here we ignore whether or not it is a
609 // varargs calls, because FP arguments will be explicitly copied
610 // to an integer Value and handled under (argCopy != NULL) below.
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000611 int regNum = (regType == IntRegType)
Vikram S. Advee9327f02002-05-19 15:25:51 +0000612 ? regNumForIntArg(/*inCallee*/ false, /*isVarArgs*/ false,
Vikram S. Advea83804a2003-05-31 07:32:01 +0000613 argNo, regClassIDOfArgReg)
Vikram S. Advee9327f02002-05-19 15:25:51 +0000614 : regNumForFPArg(regType, /*inCallee*/ false, /*isVarArgs*/ false,
Vikram S. Advea83804a2003-05-31 07:32:01 +0000615 argNo, regClassIDOfArgReg);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000616
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000617 // If a register could be allocated, use it.
618 // If not, do NOTHING as this will be colored as a normal value.
Vikram S. Advea83804a2003-05-31 07:32:01 +0000619 if(regNum != getInvalidRegNum())
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000620 LR->setSuggestedColor(regNum);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000621
Vikram S. Advea83804a2003-05-31 07:32:01 +0000622#ifdef CANNOT_PRECOPY_CALLARGS
Vikram S. Advee9327f02002-05-19 15:25:51 +0000623 // Repeat for the second copy of the argument, which would be
624 // an FP argument being passed to a function with no prototype
625 const Value *argCopy = argDesc->getArgInfo(i).getArgCopy();
626 if (argCopy != NULL)
627 {
Chris Lattnerb0b412e2002-09-03 01:08:28 +0000628 assert(regType != IntRegType && argCopy->getType()->isInteger()
Vikram S. Advee9327f02002-05-19 15:25:51 +0000629 && "Must be passing copy of FP argument in int register");
630 int copyRegNum = regNumForIntArg(/*inCallee*/false, /*isVarArgs*/false,
Vikram S. Advea83804a2003-05-31 07:32:01 +0000631 argNo, regClassIDOfArgReg);
632 assert(copyRegNum != getInvalidRegNum());
Vikram S. Advee9327f02002-05-19 15:25:51 +0000633 LiveRange *const copyLR = LRI.getLiveRangeForValue(argCopy);
634 copyLR->setSuggestedColor(copyRegNum);
635 }
Vikram S. Advea83804a2003-05-31 07:32:01 +0000636#endif
Vikram S. Advee9327f02002-05-19 15:25:51 +0000637
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000638 } // for all call arguments
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000639
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000640}
641
642
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000643//---------------------------------------------------------------------------
Vikram S. Advee9327f02002-05-19 15:25:51 +0000644// Helper method for UltraSparcRegInfo::colorCallArgs().
645//---------------------------------------------------------------------------
646
647void
Vikram S. Adveaee67012002-07-08 23:23:12 +0000648UltraSparcRegInfo::InitializeOutgoingArg(MachineInstr* CallMI,
Vikram S. Advee9327f02002-05-19 15:25:51 +0000649 AddedInstrns *CallAI,
650 PhyRegAlloc &PRA, LiveRange* LR,
651 unsigned regType, unsigned RegClassID,
Chris Lattnerd47aac92002-12-28 20:21:29 +0000652 int UniArgRegOrNone, unsigned argNo,
Misha Brukman352f7ac2003-05-21 17:59:06 +0000653 std::vector<MachineInstr*> &AddedInstrnsBefore)
Vikram S. Advee9327f02002-05-19 15:25:51 +0000654 const
655{
Vikram S. Advea83804a2003-05-31 07:32:01 +0000656 assert(0 && "Should never get here because we are now using precopying!");
657
Vikram S. Advee9327f02002-05-19 15:25:51 +0000658 MachineInstr *AdMI;
659 bool isArgInReg = false;
Chris Lattner24c1d5e2003-01-14 23:05:08 +0000660 unsigned UniArgReg = BadRegClass; // unused unless initialized below
Vikram S. Advea83804a2003-05-31 07:32:01 +0000661 if (UniArgRegOrNone != getInvalidRegNum())
Vikram S. Advee9327f02002-05-19 15:25:51 +0000662 {
663 isArgInReg = true;
664 UniArgReg = (unsigned) UniArgRegOrNone;
665 }
666
667 if (LR->hasColor()) {
668 unsigned UniLRReg = getUnifiedRegNum(RegClassID, LR->getColor());
669
670 // if LR received the correct color, nothing to do
671 if( isArgInReg && UniArgReg == UniLRReg )
672 return;
673
674 // The LR is allocated to a register UniLRReg and must be copied
675 // to UniArgReg or to the stack slot.
676 //
677 if( isArgInReg ) {
678 // Copy UniLRReg to UniArgReg
Vikram S. Adveaee67012002-07-08 23:23:12 +0000679 cpReg2RegMI(AddedInstrnsBefore, UniLRReg, UniArgReg, regType);
Vikram S. Advee9327f02002-05-19 15:25:51 +0000680 }
681 else {
682 // Copy UniLRReg to the stack to pass the arg on stack.
Chris Lattnerd47aac92002-12-28 20:21:29 +0000683 const TargetFrameInfo& frameInfo = target.getFrameInfo();
Chris Lattnere3aa50d2002-10-28 19:32:07 +0000684 int argOffset = frameInfo.getOutgoingArgOffset(PRA.MF, argNo);
Vikram S. Adveaee67012002-07-08 23:23:12 +0000685 cpReg2MemMI(CallAI->InstrnsBefore,
686 UniLRReg, getStackPointer(), argOffset, regType);
Vikram S. Advee9327f02002-05-19 15:25:51 +0000687 }
688
689 } else { // LR is not colored (i.e., spilled)
690
691 if( isArgInReg ) {
692 // Insert a load instruction to load the LR to UniArgReg
Vikram S. Adveaee67012002-07-08 23:23:12 +0000693 cpMem2RegMI(AddedInstrnsBefore, getFramePointer(),
694 LR->getSpillOffFromFP(), UniArgReg, regType);
Vikram S. Advee9327f02002-05-19 15:25:51 +0000695 // Now add the instruction
696 }
697
698 else {
699 // Now, we have to pass the arg on stack. Since LR also did NOT
700 // receive a register we have to move an argument in memory to
701 // outgoing parameter on stack.
702 // Use TReg to load and store the value.
703 // Use TmpOff to save TReg, since that may have a live value.
704 //
Chris Lattnerf9fd5912003-01-15 21:14:32 +0000705 int TReg = PRA.getUniRegNotUsedByThisInst(LR->getRegClass(), CallMI);
Chris Lattnerd47aac92002-12-28 20:21:29 +0000706 int TmpOff = PRA.MF.getInfo()->
707 pushTempValue(getSpilledRegSize(getRegType(LR)));
708 const TargetFrameInfo& frameInfo = target.getFrameInfo();
Chris Lattnere3aa50d2002-10-28 19:32:07 +0000709 int argOffset = frameInfo.getOutgoingArgOffset(PRA.MF, argNo);
Vikram S. Advee9327f02002-05-19 15:25:51 +0000710
711 MachineInstr *Ad1, *Ad2, *Ad3, *Ad4;
712
713 // Sequence:
714 // (1) Save TReg on stack
715 // (2) Load LR value into TReg from stack pos of LR
716 // (3) Store Treg on outgoing Arg pos on stack
717 // (4) Load the old value of TReg from stack to TReg (restore it)
718 //
719 // OPTIMIZE THIS:
720 // When reverse pointers in MahineInstr are introduced:
721 // Call PRA.getUnusedRegAtMI(....) to get an unused reg. Step 1 is
722 // needed only if this fails. Currently, we cannot call the
723 // above method since we cannot find LVSetBefore without the BB
724 //
725 // NOTE: We directly add to CallAI->InstrnsBefore instead of adding to
726 // AddedInstrnsBefore since these instructions must not be reordered.
Vikram S. Adveaee67012002-07-08 23:23:12 +0000727 cpReg2MemMI(CallAI->InstrnsBefore,
728 TReg, getFramePointer(), TmpOff, regType);
729 cpMem2RegMI(CallAI->InstrnsBefore,
730 getFramePointer(), LR->getSpillOffFromFP(), TReg, regType);
731 cpReg2MemMI(CallAI->InstrnsBefore,
732 TReg, getStackPointer(), argOffset, regType);
733 cpMem2RegMI(CallAI->InstrnsBefore,
734 getFramePointer(), TmpOff, TReg, regType);
Vikram S. Advee9327f02002-05-19 15:25:51 +0000735 }
736 }
737}
738
739//---------------------------------------------------------------------------
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000740// After graph coloring, we have call this method to see whehter the return
741// value and the call args received the correct colors. If not, we have
742// to instert copy instructions.
743//---------------------------------------------------------------------------
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000744
Vikram S. Adveaee67012002-07-08 23:23:12 +0000745void UltraSparcRegInfo::colorCallArgs(MachineInstr *CallMI,
Chris Lattner5216cc52002-02-04 05:59:25 +0000746 LiveRangeInfo &LRI,
747 AddedInstrns *CallAI,
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000748 PhyRegAlloc &PRA,
749 const BasicBlock *BB) const {
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000750
Vikram S. Adve879eac92002-10-13 00:05:30 +0000751 assert ( (target.getInstrInfo()).isCall(CallMI->getOpCode()) );
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000752
Vikram S. Advee9327f02002-05-19 15:25:51 +0000753 CallArgsDescriptor* argDesc = CallArgsDescriptor::get(CallMI);
754
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000755 // First color the return value of the call.
756 // If there is a LR for the return value, it means this
757 // method returns a value
758
759 MachineInstr *AdMI;
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000760
Vikram S. Advee9327f02002-05-19 15:25:51 +0000761 const Value *RetVal = argDesc->getReturnValue();
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000762
Chris Lattner30e8fb62002-02-05 01:43:49 +0000763 if (RetVal) {
764 LiveRange *RetValLR = LRI.getLiveRangeForValue( RetVal );
Vikram S. Advea83804a2003-05-31 07:32:01 +0000765 assert(RetValLR && "ERROR: No LR for non-void return value");
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000766
Vikram S. Advea83804a2003-05-31 07:32:01 +0000767 // Mark the return value register as used by this instruction
Chris Lattnerf9fd5912003-01-15 21:14:32 +0000768 unsigned RegClassID = RetValLR->getRegClassID();
Vikram S. Advea83804a2003-05-31 07:32:01 +0000769 unsigned CorrectCol = (RegClassID == IntRegClassID
770 ? (unsigned) SparcIntRegClass::o0
771 : (unsigned) SparcFloatRegClass::f0);
Vikram S. Adve4aee77c702002-07-10 21:36:00 +0000772
Vikram S. Advea83804a2003-05-31 07:32:01 +0000773 CallMI->insertUsedReg(getUnifiedRegNum(RegClassID, CorrectCol));
Vikram S. Adve4aee77c702002-07-10 21:36:00 +0000774
Vikram S. Advea83804a2003-05-31 07:32:01 +0000775#ifdef CANNOT_PRECOPY_CALLARGS
776 // unified number for CorrectCol
777 unsigned UniRetReg = getUnifiedRegNum(RegClassID, CorrectCol);
778 recvCorrectColor;
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000779
780 // if the LR received the correct color, NOTHING to do
Vikram S. Advea83804a2003-05-31 07:32:01 +0000781 bool recvCorrectColor = (RetValLR->hasColor()
782 ? RetValLR->getColor() == CorrectCol : false);
Vikram S. Adve4aee77c702002-07-10 21:36:00 +0000783
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000784 // if we didn't receive the correct color for some reason,
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000785 // put copy instruction
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000786 if( !recvCorrectColor ) {
Vikram S. Adve4aee77c702002-07-10 21:36:00 +0000787
Chris Lattnerf9fd5912003-01-15 21:14:32 +0000788 unsigned regType = getRegType(RetValLR);
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000789
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000790 if( RetValLR->hasColor() ) {
791
Vikram S. Adve4aee77c702002-07-10 21:36:00 +0000792 unsigned UniRetLRReg=getUnifiedRegNum(RegClassID,RetValLR->getColor());
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000793
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000794 // the return value is coming in UniRetReg but has to go into
795 // the UniRetLRReg
796
Vikram S. Adveaee67012002-07-08 23:23:12 +0000797 cpReg2RegMI(CallAI->InstrnsAfter, UniRetReg, UniRetLRReg, regType);
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000798
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000799 } // if LR has color
800 else {
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000801
802 // if the LR did NOT receive a color, we have to move the return
803 // value coming in UniRetReg to the stack pos of spilled LR
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000804
Vikram S. Adveaee67012002-07-08 23:23:12 +0000805 cpReg2MemMI(CallAI->InstrnsAfter, UniRetReg,
806 getFramePointer(),RetValLR->getSpillOffFromFP(), regType);
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000807 }
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000808 } // the LR didn't receive the suggested color
Vikram S. Advea83804a2003-05-31 07:32:01 +0000809#endif
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000810
811 } // if there a return value
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000812
813
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000814 //-------------------------------------------
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000815 // Now color all args of the call instruction
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000816 //-------------------------------------------
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000817
Misha Brukman352f7ac2003-05-21 17:59:06 +0000818 std::vector<MachineInstr*> AddedInstrnsBefore;
Vikram S. Advee9327f02002-05-19 15:25:51 +0000819
820 unsigned NumOfCallArgs = argDesc->getNumArgs();
821
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000822 for(unsigned argNo=0, i=0, intArgNo=0, fpArgNo=0;
823 i < NumOfCallArgs; ++i, ++argNo) {
Vikram S. Advea83804a2003-05-31 07:32:01 +0000824
Vikram S. Advee9327f02002-05-19 15:25:51 +0000825 const Value *CallArg = argDesc->getArgInfo(i).getArgVal();
Chris Lattnerf9fd5912003-01-15 21:14:32 +0000826 unsigned regType = getRegType(CallArg->getType());
Vikram S. Advea83804a2003-05-31 07:32:01 +0000827
Vikram S. Advee9327f02002-05-19 15:25:51 +0000828 // Find whether this argument is coming in a register (if not, on stack)
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000829 // Also find the correct register the argument must use (UniArgReg)
830 //
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000831 bool isArgInReg = false;
Vikram S. Advea83804a2003-05-31 07:32:01 +0000832 int UniArgReg = getInvalidRegNum(); // reg that LR MUST be colored with
Chris Lattner24c1d5e2003-01-14 23:05:08 +0000833 unsigned regClassIDOfArgReg = BadRegClass; // reg class of chosen reg
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000834
Vikram S. Advee9327f02002-05-19 15:25:51 +0000835 // Find the register that must be used for this arg, depending on
836 // whether it is an INT or FP value. Here we ignore whether or not it
837 // is a varargs calls, because FP arguments will be explicitly copied
838 // to an integer Value and handled under (argCopy != NULL) below.
Vikram S. Advea83804a2003-05-31 07:32:01 +0000839 //
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000840 int regNum = (regType == IntRegType)
Vikram S. Advee9327f02002-05-19 15:25:51 +0000841 ? regNumForIntArg(/*inCallee*/ false, /*isVarArgs*/ false,
Vikram S. Advea83804a2003-05-31 07:32:01 +0000842 argNo, regClassIDOfArgReg)
Vikram S. Advee9327f02002-05-19 15:25:51 +0000843 : regNumForFPArg(regType, /*inCallee*/ false, /*isVarArgs*/ false,
Vikram S. Advea83804a2003-05-31 07:32:01 +0000844 argNo, regClassIDOfArgReg);
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000845
Vikram S. Advea83804a2003-05-31 07:32:01 +0000846 if (regNum != getInvalidRegNum()) {
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000847 isArgInReg = true;
Vikram S. Advea83804a2003-05-31 07:32:01 +0000848 UniArgReg = getUnifiedRegNum(regClassIDOfArgReg, regNum);
849 CallMI->insertUsedReg(UniArgReg); // mark the reg as used
850 }
851
852#ifdef CANNOT_PRECOPY_CALLARGS
853
854 // Get the LR of call operand (parameter). There must be one because
855 // all args (even constants) must be defined before.
856 LiveRange *const LR = LRI.getLiveRangeForValue(CallArg);
857 assert(LR && "NO LR for call arg");
858
859 unsigned RegClassID = getRegClassIDOfType(CallArg->getType());
860
861 if (regNum != getInvalidRegNum()) {
Vikram S. Advee9327f02002-05-19 15:25:51 +0000862 assert(regClassIDOfArgReg == RegClassID &&
863 "Moving values between reg classes must happen during selection");
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000864 }
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000865
Vikram S. Advee9327f02002-05-19 15:25:51 +0000866 InitializeOutgoingArg(CallMI, CallAI, PRA, LR, regType, RegClassID,
867 UniArgReg, argNo, AddedInstrnsBefore);
Vikram S. Advea83804a2003-05-31 07:32:01 +0000868#endif
Vikram S. Advee9327f02002-05-19 15:25:51 +0000869
870 // Repeat for the second copy of the argument, which would be
871 // an FP argument being passed to a function with no prototype.
Vikram S. Adve4aee77c702002-07-10 21:36:00 +0000872 // It may either be passed as a copy in an integer register
873 // (in argCopy), or on the stack (useStackSlot).
Vikram S. Advea83804a2003-05-31 07:32:01 +0000874 int argCopyReg = argDesc->getArgInfo(i).getArgCopy();
875 if (argCopyReg != TargetRegInfo::getInvalidRegNum())
Vikram S. Advee9327f02002-05-19 15:25:51 +0000876 {
Vikram S. Advea83804a2003-05-31 07:32:01 +0000877 CallMI->insertUsedReg(argCopyReg); // mark the reg as used
878
879#ifdef CANNOT_PRECOPY_CALLARGS
Chris Lattnerb0b412e2002-09-03 01:08:28 +0000880 assert(regType != IntRegType && argCopy->getType()->isInteger()
Vikram S. Advee9327f02002-05-19 15:25:51 +0000881 && "Must be passing copy of FP argument in int register");
Vikram S. Advea6d94c92002-04-25 04:42:21 +0000882
Chris Lattnerf9fd5912003-01-15 21:14:32 +0000883 unsigned copyRegClassID = getRegClassIDOfType(argCopy->getType());
884 unsigned copyRegType = getRegType(argCopy->getType());
Vikram S. Advee9327f02002-05-19 15:25:51 +0000885
886 int copyRegNum = regNumForIntArg(/*inCallee*/false, /*isVarArgs*/false,
Vikram S. Advea83804a2003-05-31 07:32:01 +0000887 argNo, regClassIDOfArgReg);
888 assert(copyRegNum != getInvalidRegNum());
Vikram S. Advee9327f02002-05-19 15:25:51 +0000889 assert(regClassIDOfArgReg == copyRegClassID &&
890 "Moving values between reg classes must happen during selection");
891
892 InitializeOutgoingArg(CallMI, CallAI, PRA,
893 LRI.getLiveRangeForValue(argCopy), copyRegType,
894 copyRegClassID, copyRegNum, argNo,
895 AddedInstrnsBefore);
Vikram S. Advea83804a2003-05-31 07:32:01 +0000896#endif
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000897 }
Vikram S. Adve4aee77c702002-07-10 21:36:00 +0000898
Vikram S. Advea83804a2003-05-31 07:32:01 +0000899#ifdef CANNOT_PRECOPY_CALLARGS
900 if (regNum != getInvalidRegNum() &&
Vikram S. Adve4aee77c702002-07-10 21:36:00 +0000901 argDesc->getArgInfo(i).usesStackSlot())
902 {
903 // Pass the argument via the stack in addition to regNum
904 assert(regType != IntRegType && "Passing an integer arg. twice?");
905 assert(!argCopy && "Passing FP arg in FP reg, INT reg, and stack?");
906 InitializeOutgoingArg(CallMI, CallAI, PRA, LR, regType, RegClassID,
Vikram S. Advea83804a2003-05-31 07:32:01 +0000907 getInvalidRegNum(), argNo, AddedInstrnsBefore);
Vikram S. Adve4aee77c702002-07-10 21:36:00 +0000908 }
Vikram S. Advea83804a2003-05-31 07:32:01 +0000909#endif
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000910 } // for each parameter in call instruction
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000911
Vikram S. Advee9327f02002-05-19 15:25:51 +0000912 // If we added any instruction before the call instruction, verify
Ruchira Sasankad0d294a2001-11-09 23:49:14 +0000913 // that they are in the proper order and if not, reorder them
Vikram S. Advee9327f02002-05-19 15:25:51 +0000914 //
Misha Brukman352f7ac2003-05-21 17:59:06 +0000915 std::vector<MachineInstr*> ReorderedVec;
Chris Lattner5216cc52002-02-04 05:59:25 +0000916 if (!AddedInstrnsBefore.empty()) {
Ruchira Sasankad0d294a2001-11-09 23:49:14 +0000917
Chris Lattner5216cc52002-02-04 05:59:25 +0000918 if (DEBUG_RA) {
Misha Brukman352f7ac2003-05-21 17:59:06 +0000919 std::cerr << "\nCalling reorder with instrns: \n";
Ruchira Sasankad0d294a2001-11-09 23:49:14 +0000920 for(unsigned i=0; i < AddedInstrnsBefore.size(); i++)
Misha Brukman352f7ac2003-05-21 17:59:06 +0000921 std::cerr << *(AddedInstrnsBefore[i]);
Ruchira Sasankad0d294a2001-11-09 23:49:14 +0000922 }
923
Vikram S. Adve4aee77c702002-07-10 21:36:00 +0000924 OrderAddedInstrns(AddedInstrnsBefore, ReorderedVec, PRA);
925 assert(ReorderedVec.size() >= AddedInstrnsBefore.size()
926 && "Dropped some instructions when reordering!");
927
Chris Lattner5216cc52002-02-04 05:59:25 +0000928 if (DEBUG_RA) {
Misha Brukman352f7ac2003-05-21 17:59:06 +0000929 std::cerr << "\nAfter reordering instrns: \n";
Vikram S. Adve4aee77c702002-07-10 21:36:00 +0000930 for(unsigned i = 0; i < ReorderedVec.size(); i++)
Misha Brukman352f7ac2003-05-21 17:59:06 +0000931 std::cerr << *ReorderedVec[i];
Ruchira Sasankad0d294a2001-11-09 23:49:14 +0000932 }
Ruchira Sasankad0d294a2001-11-09 23:49:14 +0000933 }
Vikram S. Advee9327f02002-05-19 15:25:51 +0000934
Vikram S. Adve4aee77c702002-07-10 21:36:00 +0000935 // Now insert caller saving code for this call instruction
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000936 //
Vikram S. Adve4aee77c702002-07-10 21:36:00 +0000937 insertCallerSavingCode(CallAI->InstrnsBefore, CallAI->InstrnsAfter,
938 CallMI, BB, PRA);
939
940 // Then insert the final reordered code for the call arguments.
941 //
942 for(unsigned i=0; i < ReorderedVec.size(); i++)
943 CallAI->InstrnsBefore.push_back( ReorderedVec[i] );
Anand Shuklae6c3ee62003-06-01 02:48:23 +0000944
Vikram S. Adveb5f8ada2003-07-02 01:13:57 +0000945#ifndef NDEBUG
946 // Temporary sanity checking code to detect whether the same machine
947 // instruction is ever inserted twice before/after a call.
948 // I suspect this is happening but am not sure. --Vikram, 7/1/03.
949 //
950 std::set<const MachineInstr*> instrsSeen;
951 for (int i = 0, N = CallAI->InstrnsBefore.size(); i < N; ++i) {
952 assert(instrsSeen.find(CallAI->InstrnsBefore[i]) == instrsSeen.end() &&
953 "Duplicate machine instruction in InstrnsBefore!");
954 instrsSeen.insert(CallAI->InstrnsBefore[i]);
955 }
956 for (int i = 0, N = CallAI->InstrnsAfter.size(); i < N; ++i) {
957 assert(instrsSeen.find(CallAI->InstrnsAfter[i]) == instrsSeen.end() &&
958 "Duplicate machine instruction in InstrnsBefore/After!");
959 instrsSeen.insert(CallAI->InstrnsAfter[i]);
960 }
961#endif
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000962}
963
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000964//---------------------------------------------------------------------------
Anand Shuklae6c3ee62003-06-01 02:48:23 +0000965// this method is called for an LLVM return instruction to identify which
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000966// values will be returned from this method and to suggest colors.
967//---------------------------------------------------------------------------
Vikram S. Adveaee67012002-07-08 23:23:12 +0000968void UltraSparcRegInfo::suggestReg4RetValue(MachineInstr *RetMI,
Chris Lattner5216cc52002-02-04 05:59:25 +0000969 LiveRangeInfo &LRI) const {
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000970
Vikram S. Adve879eac92002-10-13 00:05:30 +0000971 assert( (target.getInstrInfo()).isReturn( RetMI->getOpCode() ) );
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000972
Vikram S. Adveaee67012002-07-08 23:23:12 +0000973 suggestReg4RetAddr(RetMI, LRI);
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000974
Vikram S. Advea83804a2003-05-31 07:32:01 +0000975 // To find the return value (if any), we can get the LLVM return instr.
976 // from the return address register, which is the first operand
977 Value* tmpI = RetMI->getOperand(0).getVRegValue();
978 ReturnInst* retI=cast<ReturnInst>(cast<TmpInstruction>(tmpI)->getOperand(0));
979 if (const Value *RetVal = retI->getReturnValue())
980 if (LiveRange *const LR = LRI.getLiveRangeForValue(RetVal))
981 LR->setSuggestedColor(LR->getRegClassID() == IntRegClassID
982 ? (unsigned) SparcIntRegClass::i0
983 : (unsigned) SparcFloatRegClass::f0);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000984}
985
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000986
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000987
988//---------------------------------------------------------------------------
989// Colors the return value of a method to %i0 or %f0, if possible. If it is
990// not possilbe to directly color the LR, insert a copy instruction to move
991// the LR to %i0 or %f0. When the LR is spilled, instead of the copy, we
992// have to put a load instruction.
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000993//---------------------------------------------------------------------------
Vikram S. Adveaee67012002-07-08 23:23:12 +0000994void UltraSparcRegInfo::colorRetValue(MachineInstr *RetMI,
Chris Lattner5216cc52002-02-04 05:59:25 +0000995 LiveRangeInfo &LRI,
996 AddedInstrns *RetAI) const {
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000997
Vikram S. Adve879eac92002-10-13 00:05:30 +0000998 assert((target.getInstrInfo()).isReturn( RetMI->getOpCode()));
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000999
Vikram S. Advea83804a2003-05-31 07:32:01 +00001000 // To find the return value (if any), we can get the LLVM return instr.
1001 // from the return address register, which is the first operand
1002 Value* tmpI = RetMI->getOperand(0).getVRegValue();
1003 ReturnInst* retI=cast<ReturnInst>(cast<TmpInstruction>(tmpI)->getOperand(0));
1004 if (const Value *RetVal = retI->getReturnValue()) {
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +00001005
Chris Lattnerf9fd5912003-01-15 21:14:32 +00001006 unsigned RegClassID = getRegClassIDOfType(RetVal->getType());
1007 unsigned regType = getRegType(RetVal->getType());
Vikram S. Advea83804a2003-05-31 07:32:01 +00001008 unsigned CorrectCol = (RegClassID == IntRegClassID
1009 ? (unsigned) SparcIntRegClass::i0
1010 : (unsigned) SparcFloatRegClass::f0);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001011
Vikram S. Adve4aee77c702002-07-10 21:36:00 +00001012 // convert to unified number
Chris Lattner56e91662002-08-12 21:25:05 +00001013 unsigned UniRetReg = getUnifiedRegNum(RegClassID, CorrectCol);
Vikram S. Adve4aee77c702002-07-10 21:36:00 +00001014
Vikram S. Adveaee67012002-07-08 23:23:12 +00001015 // Mark the register as used by this instruction
Chris Lattnerce64edd2002-10-22 23:16:21 +00001016 RetMI->insertUsedReg(UniRetReg);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001017
Vikram S. Advea83804a2003-05-31 07:32:01 +00001018#ifdef CANNOT_PRECOPY_CALLARGS
1019 LiveRange *LR = LRI.getLiveRangeForValue(RetVal);
1020 assert(LR && "No LR for return value of non-void method?");
1021
1022 if (LR->hasColor()) {
1023 // if the LR received the correct color, NOTHING to do
1024 if (LR->getColor() == CorrectCol)
1025 return;
1026
1027 // We are here because the LR was allocated a register
Ruchira Sasanka6a7f0202001-10-23 21:40:39 +00001028 // It may be the suggested register or not
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001029
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +00001030 // copy the LR of retun value to i0 or f0
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001031
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +00001032 unsigned UniLRReg =getUnifiedRegNum( RegClassID, LR->getColor());
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001033
Ruchira Sasanka36bcd792001-10-24 15:56:58 +00001034 // the LR received UniLRReg but must be colored with UniRetReg
1035 // to pass as the return value
Vikram S. Adveaee67012002-07-08 23:23:12 +00001036 cpReg2RegMI(RetAI->InstrnsBefore, UniLRReg, UniRetReg, regType);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001037 }
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001038 else { // if the LR is spilled
Vikram S. Adveaee67012002-07-08 23:23:12 +00001039 cpMem2RegMI(RetAI->InstrnsBefore, getFramePointer(),
1040 LR->getSpillOffFromFP(), UniRetReg, regType);
Misha Brukman352f7ac2003-05-21 17:59:06 +00001041 //std::cerr << "\nCopied the return value from stack\n";
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001042 }
Vikram S. Advea83804a2003-05-31 07:32:01 +00001043#endif
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001044
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001045 } // if there is a return value
1046
1047}
1048
Vikram S. Adveaee67012002-07-08 23:23:12 +00001049//---------------------------------------------------------------------------
1050// Check if a specified register type needs a scratch register to be
1051// copied to/from memory. If it does, the reg. type that must be used
1052// for scratch registers is returned in scratchRegType.
1053//
1054// Only the int CC register needs such a scratch register.
1055// The FP CC registers can (and must) be copied directly to/from memory.
1056//---------------------------------------------------------------------------
1057
1058bool
1059UltraSparcRegInfo::regTypeNeedsScratchReg(int RegType,
1060 int& scratchRegType) const
1061{
1062 if (RegType == IntCCRegType)
1063 {
1064 scratchRegType = IntRegType;
1065 return true;
1066 }
1067 return false;
1068}
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001069
1070//---------------------------------------------------------------------------
1071// Copy from a register to register. Register number must be the unified
Vikram S. Adveaee67012002-07-08 23:23:12 +00001072// register number.
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001073//---------------------------------------------------------------------------
1074
Vikram S. Advee9327f02002-05-19 15:25:51 +00001075void
Misha Brukman352f7ac2003-05-21 17:59:06 +00001076UltraSparcRegInfo::cpReg2RegMI(std::vector<MachineInstr*>& mvec,
Vikram S. Adveaee67012002-07-08 23:23:12 +00001077 unsigned SrcReg,
Vikram S. Advee9327f02002-05-19 15:25:51 +00001078 unsigned DestReg,
Vikram S. Adveaee67012002-07-08 23:23:12 +00001079 int RegType) const {
Misha Brukman2969ec52003-06-06 09:52:23 +00001080 assert( ((int)SrcReg != getInvalidRegNum()) &&
1081 ((int)DestReg != getInvalidRegNum()) &&
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001082 "Invalid Register");
1083
1084 MachineInstr * MI = NULL;
Vikram S. Advee9327f02002-05-19 15:25:51 +00001085
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001086 switch( RegType ) {
1087
Ruchira Sasanka5f629312001-10-18 22:38:52 +00001088 case IntCCRegType:
Misha Brukman56f4fa12003-05-20 20:32:24 +00001089 if (getRegType(DestReg) == IntRegType) {
1090 // copy intCC reg to int reg
1091 // Use SrcReg+1 to get the name "%ccr" instead of "%xcc" for RDCCR
1092 MI = BuildMI(V9::RDCCR, 2).addMReg(SrcReg+1).addMReg(DestReg,MOTy::Def);
1093 } else {
1094 // copy int reg to intCC reg
1095 // Use DestReg+1 to get the name "%ccr" instead of "%xcc" for WRCCR
1096 assert(getRegType(SrcReg) == IntRegType
1097 && "Can only copy CC reg to/from integer reg");
Chris Lattnercb9ef2b2003-06-16 12:03:00 +00001098 MI = BuildMI(V9::WRCCRr, 3).addMReg(SrcReg)
Misha Brukman2969ec52003-06-06 09:52:23 +00001099 .addMReg(SparcIntRegClass::g0).addMReg(DestReg+1, MOTy::Def);
Misha Brukman56f4fa12003-05-20 20:32:24 +00001100 }
Vikram S. Adveaee67012002-07-08 23:23:12 +00001101 break;
1102
Ruchira Sasanka5f629312001-10-18 22:38:52 +00001103 case FloatCCRegType:
Vikram S. Adveaee67012002-07-08 23:23:12 +00001104 assert(0 && "Cannot copy FPCC register to any other register");
Vikram S. Advee9327f02002-05-19 15:25:51 +00001105 break;
1106
1107 case IntRegType:
Misha Brukmanaf96d392003-05-27 22:40:34 +00001108 MI = BuildMI(V9::ADDr, 3).addMReg(SrcReg).addMReg(getZeroRegNum())
Misha Brukman56f4fa12003-05-20 20:32:24 +00001109 .addMReg(DestReg, MOTy::Def);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001110 break;
Vikram S. Advee9327f02002-05-19 15:25:51 +00001111
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001112 case FPSingleRegType:
Misha Brukman56f4fa12003-05-20 20:32:24 +00001113 MI = BuildMI(V9::FMOVS, 2).addMReg(SrcReg).addMReg(DestReg, MOTy::Def);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001114 break;
1115
1116 case FPDoubleRegType:
Misha Brukman56f4fa12003-05-20 20:32:24 +00001117 MI = BuildMI(V9::FMOVD, 2).addMReg(SrcReg).addMReg(DestReg, MOTy::Def);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001118 break;
1119
1120 default:
Vikram S. Advee9327f02002-05-19 15:25:51 +00001121 assert(0 && "Unknown RegType");
Vikram S. Adveaee67012002-07-08 23:23:12 +00001122 break;
Ruchira Sasankadfc6c882001-09-18 22:52:44 +00001123 }
Vikram S. Advee9327f02002-05-19 15:25:51 +00001124
1125 if (MI)
1126 mvec.push_back(MI);
Ruchira Sasankadfc6c882001-09-18 22:52:44 +00001127}
Chris Lattnerb0ddffa2001-09-14 03:47:57 +00001128
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001129//---------------------------------------------------------------------------
Ruchira Sasanka0863c162001-10-24 22:05:34 +00001130// Copy from a register to memory (i.e., Store). Register number must
1131// be the unified register number
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001132//---------------------------------------------------------------------------
1133
1134
Vikram S. Advee9327f02002-05-19 15:25:51 +00001135void
Misha Brukman352f7ac2003-05-21 17:59:06 +00001136UltraSparcRegInfo::cpReg2MemMI(std::vector<MachineInstr*>& mvec,
Vikram S. Adveaee67012002-07-08 23:23:12 +00001137 unsigned SrcReg,
Vikram S. Advee9327f02002-05-19 15:25:51 +00001138 unsigned DestPtrReg,
1139 int Offset, int RegType,
Chris Lattner3091e112002-07-25 06:08:32 +00001140 int scratchReg) const {
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001141 MachineInstr * MI = NULL;
Chris Lattner1ebaa902003-01-15 17:47:49 +00001142 switch (RegType) {
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001143 case IntRegType:
Misha Brukmanaf96d392003-05-27 22:40:34 +00001144 assert(target.getInstrInfo().constantFitsInImmedField(V9::STXi, Offset));
1145 MI = BuildMI(V9::STXi,3).addMReg(SrcReg).addMReg(DestPtrReg)
1146 .addSImm(Offset);
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001147 break;
1148
1149 case FPSingleRegType:
Misha Brukmanaf96d392003-05-27 22:40:34 +00001150 assert(target.getInstrInfo().constantFitsInImmedField(V9::STFi, Offset));
1151 MI = BuildMI(V9::STFi, 3).addMReg(SrcReg).addMReg(DestPtrReg)
1152 .addSImm(Offset);
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001153 break;
1154
1155 case FPDoubleRegType:
Misha Brukmanaf96d392003-05-27 22:40:34 +00001156 assert(target.getInstrInfo().constantFitsInImmedField(V9::STDFi, Offset));
1157 MI = BuildMI(V9::STDFi,3).addMReg(SrcReg).addMReg(DestPtrReg)
1158 .addSImm(Offset);
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001159 break;
1160
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001161 case IntCCRegType:
Vikram S. Adveaee67012002-07-08 23:23:12 +00001162 assert(scratchReg >= 0 && "Need scratch reg to store %ccr to memory");
Chris Lattner56e91662002-08-12 21:25:05 +00001163 assert(getRegType(scratchReg) ==IntRegType && "Invalid scratch reg");
Vikram S. Adveaee67012002-07-08 23:23:12 +00001164
1165 // Use SrcReg+1 to get the name "%ccr" instead of "%xcc" for RDCCR
Misha Brukman56f4fa12003-05-20 20:32:24 +00001166 MI = BuildMI(V9::RDCCR, 2).addMReg(SrcReg+1).addMReg(scratchReg, MOTy::Def);
Vikram S. Adveaee67012002-07-08 23:23:12 +00001167 mvec.push_back(MI);
1168
Chris Lattner56e91662002-08-12 21:25:05 +00001169 cpReg2MemMI(mvec, scratchReg, DestPtrReg, Offset, IntRegType);
Chris Lattner1ebaa902003-01-15 17:47:49 +00001170 return;
Vikram S. Adveaee67012002-07-08 23:23:12 +00001171
Vikram S. Adve8adb9942003-05-27 00:02:22 +00001172 case FloatCCRegType: {
Misha Brukmanaf96d392003-05-27 22:40:34 +00001173 assert(target.getInstrInfo().constantFitsInImmedField(V9::STXFSRi, Offset));
Vikram S. Adve8adb9942003-05-27 00:02:22 +00001174 unsigned fsrRegNum = getUnifiedRegNum(UltraSparcRegInfo::SpecialRegClassID,
1175 SparcSpecialRegClass::fsr);
Misha Brukmanaf96d392003-05-27 22:40:34 +00001176 MI = BuildMI(V9::STXFSRi, 3)
Vikram S. Adve8adb9942003-05-27 00:02:22 +00001177 .addMReg(fsrRegNum).addMReg(DestPtrReg).addSImm(Offset);
Vikram S. Adveaee67012002-07-08 23:23:12 +00001178 break;
Vikram S. Adve8adb9942003-05-27 00:02:22 +00001179 }
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001180 default:
Vikram S. Advee9327f02002-05-19 15:25:51 +00001181 assert(0 && "Unknown RegType in cpReg2MemMI");
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001182 }
Chris Lattner1ebaa902003-01-15 17:47:49 +00001183 mvec.push_back(MI);
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001184}
1185
1186
1187//---------------------------------------------------------------------------
Ruchira Sasanka0863c162001-10-24 22:05:34 +00001188// Copy from memory to a reg (i.e., Load) Register number must be the unified
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001189// register number
1190//---------------------------------------------------------------------------
1191
1192
Vikram S. Advee9327f02002-05-19 15:25:51 +00001193void
Misha Brukman352f7ac2003-05-21 17:59:06 +00001194UltraSparcRegInfo::cpMem2RegMI(std::vector<MachineInstr*>& mvec,
Vikram S. Adveaee67012002-07-08 23:23:12 +00001195 unsigned SrcPtrReg,
Vikram S. Advee9327f02002-05-19 15:25:51 +00001196 int Offset,
1197 unsigned DestReg,
1198 int RegType,
Chris Lattner3091e112002-07-25 06:08:32 +00001199 int scratchReg) const {
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001200 MachineInstr * MI = NULL;
Chris Lattner5216cc52002-02-04 05:59:25 +00001201 switch (RegType) {
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001202 case IntRegType:
Misha Brukmanaf96d392003-05-27 22:40:34 +00001203 assert(target.getInstrInfo().constantFitsInImmedField(V9::LDXi, Offset));
1204 MI = BuildMI(V9::LDXi, 3).addMReg(SrcPtrReg).addSImm(Offset)
Misha Brukman56f4fa12003-05-20 20:32:24 +00001205 .addMReg(DestReg, MOTy::Def);
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001206 break;
1207
1208 case FPSingleRegType:
Misha Brukmanaf96d392003-05-27 22:40:34 +00001209 assert(target.getInstrInfo().constantFitsInImmedField(V9::LDFi, Offset));
1210 MI = BuildMI(V9::LDFi, 3).addMReg(SrcPtrReg).addSImm(Offset)
Misha Brukman56f4fa12003-05-20 20:32:24 +00001211 .addMReg(DestReg, MOTy::Def);
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001212 break;
1213
1214 case FPDoubleRegType:
Misha Brukmanaf96d392003-05-27 22:40:34 +00001215 assert(target.getInstrInfo().constantFitsInImmedField(V9::LDDFi, Offset));
1216 MI = BuildMI(V9::LDDFi, 3).addMReg(SrcPtrReg).addSImm(Offset)
1217 .addMReg(DestReg, MOTy::Def);
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001218 break;
1219
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001220 case IntCCRegType:
Vikram S. Adveaee67012002-07-08 23:23:12 +00001221 assert(scratchReg >= 0 && "Need scratch reg to load %ccr from memory");
Chris Lattner56e91662002-08-12 21:25:05 +00001222 assert(getRegType(scratchReg) ==IntRegType && "Invalid scratch reg");
1223 cpMem2RegMI(mvec, SrcPtrReg, Offset, scratchReg, IntRegType);
Vikram S. Adveaee67012002-07-08 23:23:12 +00001224
1225 // Use DestReg+1 to get the name "%ccr" instead of "%xcc" for WRCCR
Chris Lattnercb9ef2b2003-06-16 12:03:00 +00001226 MI = BuildMI(V9::WRCCRr, 3).addMReg(scratchReg)
Misha Brukman2969ec52003-06-06 09:52:23 +00001227 .addMReg(SparcIntRegClass::g0).addMReg(DestReg+1,MOTy::Def);
Vikram S. Adveaee67012002-07-08 23:23:12 +00001228 break;
1229
Vikram S. Adve8adb9942003-05-27 00:02:22 +00001230 case FloatCCRegType: {
Misha Brukmanaf96d392003-05-27 22:40:34 +00001231 assert(target.getInstrInfo().constantFitsInImmedField(V9::LDXFSRi, Offset));
Vikram S. Adve8adb9942003-05-27 00:02:22 +00001232 unsigned fsrRegNum = getUnifiedRegNum(UltraSparcRegInfo::SpecialRegClassID,
1233 SparcSpecialRegClass::fsr);
Misha Brukmanaf96d392003-05-27 22:40:34 +00001234 MI = BuildMI(V9::LDXFSRi, 3).addMReg(SrcPtrReg).addSImm(Offset)
Vikram S. Adve8adb9942003-05-27 00:02:22 +00001235 .addMReg(fsrRegNum, MOTy::UseAndDef);
Vikram S. Adveaee67012002-07-08 23:23:12 +00001236 break;
Vikram S. Adve8adb9942003-05-27 00:02:22 +00001237 }
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001238 default:
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001239 assert(0 && "Unknown RegType in cpMem2RegMI");
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001240 }
Chris Lattner1ebaa902003-01-15 17:47:49 +00001241 mvec.push_back(MI);
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001242}
1243
1244
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001245//---------------------------------------------------------------------------
1246// Generate a copy instruction to copy a value to another. Temporarily
1247// used by PhiElimination code.
1248//---------------------------------------------------------------------------
1249
1250
Vikram S. Advee9327f02002-05-19 15:25:51 +00001251void
Chris Lattner1ebaa902003-01-15 17:47:49 +00001252UltraSparcRegInfo::cpValue2Value(Value *Src, Value *Dest,
Misha Brukman352f7ac2003-05-21 17:59:06 +00001253 std::vector<MachineInstr*>& mvec) const {
Chris Lattnerf9fd5912003-01-15 21:14:32 +00001254 int RegType = getRegType(Src->getType());
Ruchira Sasankab7a39722001-11-03 17:13:27 +00001255 MachineInstr * MI = NULL;
1256
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001257 switch( RegType ) {
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001258 case IntRegType:
Misha Brukmanaf96d392003-05-27 22:40:34 +00001259 MI = BuildMI(V9::ADDr, 3).addReg(Src).addMReg(getZeroRegNum())
Misha Brukman56f4fa12003-05-20 20:32:24 +00001260 .addRegDef(Dest);
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001261 break;
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001262 case FPSingleRegType:
Misha Brukman56f4fa12003-05-20 20:32:24 +00001263 MI = BuildMI(V9::FMOVS, 2).addReg(Src).addRegDef(Dest);
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001264 break;
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001265 case FPDoubleRegType:
Misha Brukman56f4fa12003-05-20 20:32:24 +00001266 MI = BuildMI(V9::FMOVD, 2).addReg(Src).addRegDef(Dest);
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001267 break;
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001268 default:
1269 assert(0 && "Unknow RegType in CpValu2Value");
1270 }
Ruchira Sasankab7a39722001-11-03 17:13:27 +00001271
Chris Lattner9bebf832002-10-28 20:10:56 +00001272 mvec.push_back(MI);
Ruchira Sasankab7a39722001-11-03 17:13:27 +00001273}
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001274
1275
1276
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001277
1278
1279
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001280//----------------------------------------------------------------------------
1281// This method inserts caller saving/restoring instructons before/after
Ruchira Sasankaf4c2ddd2002-01-07 21:03:42 +00001282// a call machine instruction. The caller saving/restoring instructions are
1283// inserted like:
1284//
1285// ** caller saving instructions
1286// other instructions inserted for the call by ColorCallArg
1287// CALL instruction
1288// other instructions inserted for the call ColorCallArg
1289// ** caller restoring instructions
1290//
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001291//----------------------------------------------------------------------------
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001292
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001293
Vikram S. Adve4aee77c702002-07-10 21:36:00 +00001294void
Misha Brukman352f7ac2003-05-21 17:59:06 +00001295UltraSparcRegInfo::insertCallerSavingCode
1296(std::vector<MachineInstr*> &instrnsBefore,
1297 std::vector<MachineInstr*> &instrnsAfter,
1298 MachineInstr *CallMI,
1299 const BasicBlock *BB,
1300 PhyRegAlloc &PRA) const
Vikram S. Adve4aee77c702002-07-10 21:36:00 +00001301{
Vikram S. Adve879eac92002-10-13 00:05:30 +00001302 assert ( (target.getInstrInfo()).isCall(CallMI->getOpCode()) );
Vikram S. Advee9327f02002-05-19 15:25:51 +00001303
Ruchira Sasankaf4c2ddd2002-01-07 21:03:42 +00001304 // has set to record which registers were saved/restored
1305 //
Chris Lattnere98dd5f2002-07-24 21:21:32 +00001306 hash_set<unsigned> PushedRegSet;
Ruchira Sasankaf4c2ddd2002-01-07 21:03:42 +00001307
Vikram S. Advee9327f02002-05-19 15:25:51 +00001308 CallArgsDescriptor* argDesc = CallArgsDescriptor::get(CallMI);
1309
Vikram S. Advea83804a2003-05-31 07:32:01 +00001310 // Now check if the call has a return value (using argDesc) and if so,
1311 // find the LR of the TmpInstruction representing the return value register.
1312 // (using the last or second-last *implicit operand* of the call MI).
1313 // Insert it to to the PushedRegSet since we must not save that register
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001314 // and restore it after the call.
1315 // We do this because, we look at the LV set *after* the instruction
1316 // to determine, which LRs must be saved across calls. The return value
1317 // of the call is live in this set - but we must not save/restore it.
Vikram S. Advea83804a2003-05-31 07:32:01 +00001318 //
1319 if (const Value *origRetVal = argDesc->getReturnValue()) {
1320 unsigned retValRefNum = (CallMI->getNumImplicitRefs() -
1321 (argDesc->getIndirectFuncPtr()? 1 : 2));
1322 const TmpInstruction* tmpRetVal =
1323 cast<TmpInstruction>(CallMI->getImplicitRef(retValRefNum));
1324 assert(tmpRetVal->getOperand(0) == origRetVal &&
1325 tmpRetVal->getType() == origRetVal->getType() &&
1326 "Wrong implicit ref?");
1327 LiveRange *RetValLR = PRA.LRI.getLiveRangeForValue( tmpRetVal );
Chris Lattner5216cc52002-02-04 05:59:25 +00001328 assert(RetValLR && "No LR for RetValue of call");
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001329
Chris Lattner5216cc52002-02-04 05:59:25 +00001330 if (RetValLR->hasColor())
Chris Lattnerf9fd5912003-01-15 21:14:32 +00001331 PushedRegSet.insert(getUnifiedRegNum(RetValLR->getRegClassID(),
1332 RetValLR->getColor()));
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001333 }
1334
Vikram S. Advee9327f02002-05-19 15:25:51 +00001335 const ValueSet &LVSetAft = PRA.LVI->getLiveVarSetAfterMInst(CallMI, BB);
Chris Lattner7e5ee422002-02-05 04:20:12 +00001336 ValueSet::const_iterator LIt = LVSetAft.begin();
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001337
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001338 // for each live var in live variable set after machine inst
Chris Lattner7e5ee422002-02-05 04:20:12 +00001339 for( ; LIt != LVSetAft.end(); ++LIt) {
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001340
1341 // get the live range corresponding to live var
1342 LiveRange *const LR = PRA.LRI.getLiveRangeForValue(*LIt );
1343
1344 // LR can be null if it is a const since a const
1345 // doesn't have a dominating def - see Assumptions above
1346 if( LR ) {
1347
1348 if( LR->hasColor() ) {
1349
Chris Lattnerf9fd5912003-01-15 21:14:32 +00001350 unsigned RCID = LR->getRegClassID();
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001351 unsigned Color = LR->getColor();
1352
1353 if ( isRegVolatile(RCID, Color) ) {
1354
1355 // if the value is in both LV sets (i.e., live before and after
1356 // the call machine instruction)
Vikram S. Adveaee67012002-07-08 23:23:12 +00001357
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001358 unsigned Reg = getUnifiedRegNum(RCID, Color);
1359
1360 if( PushedRegSet.find(Reg) == PushedRegSet.end() ) {
1361
1362 // if we haven't already pushed that register
1363
Chris Lattnerf9fd5912003-01-15 21:14:32 +00001364 unsigned RegType = getRegType(LR);
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001365
1366 // Now get two instructions - to push on stack and pop from stack
1367 // and add them to InstrnsBefore and InstrnsAfter of the
1368 // call instruction
Vikram S. Adveaee67012002-07-08 23:23:12 +00001369 //
Vikram S. Advea83804a2003-05-31 07:32:01 +00001370 int StackOff =
1371 PRA.MF.getInfo()->pushTempValue(getSpilledRegSize(RegType));
Vikram S. Adve7a1524f2001-11-08 04:56:41 +00001372
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001373 //---- Insert code for pushing the reg on stack ----------
Vikram S. Adveaee67012002-07-08 23:23:12 +00001374
Vikram S. Adveb5f8ada2003-07-02 01:13:57 +00001375 std::vector<MachineInstr*> AdIBef, AdIAft;
1376
Vikram S. Adveaee67012002-07-08 23:23:12 +00001377 // We may need a scratch register to copy the saved value
1378 // to/from memory. This may itself have to insert code to
1379 // free up a scratch register. Any such code should go before
Vikram S. Advea83804a2003-05-31 07:32:01 +00001380 // the save code. The scratch register, if any, is by default
1381 // temporary and not "used" by the instruction unless the
1382 // copy code itself decides to keep the value in the scratch reg.
Vikram S. Adveaee67012002-07-08 23:23:12 +00001383 int scratchRegType = -1;
1384 int scratchReg = -1;
Chris Lattner56e91662002-08-12 21:25:05 +00001385 if (regTypeNeedsScratchReg(RegType, scratchRegType))
Vikram S. Adveaee67012002-07-08 23:23:12 +00001386 { // Find a register not live in the LVSet before CallMI
1387 const ValueSet &LVSetBef =
1388 PRA.LVI->getLiveVarSetBeforeMInst(CallMI, BB);
1389 scratchReg = PRA.getUsableUniRegAtMI(scratchRegType, &LVSetBef,
1390 CallMI, AdIBef, AdIAft);
Chris Lattner56e91662002-08-12 21:25:05 +00001391 assert(scratchReg != getInvalidRegNum());
Vikram S. Adveaee67012002-07-08 23:23:12 +00001392 }
1393
1394 if (AdIBef.size() > 0)
1395 instrnsBefore.insert(instrnsBefore.end(),
1396 AdIBef.begin(), AdIBef.end());
1397
1398 cpReg2MemMI(instrnsBefore, Reg,getFramePointer(),StackOff,RegType,
1399 scratchReg);
1400
Vikram S. Adve4aee77c702002-07-10 21:36:00 +00001401 if (AdIAft.size() > 0)
Vikram S. Adveaee67012002-07-08 23:23:12 +00001402 instrnsBefore.insert(instrnsBefore.end(),
1403 AdIAft.begin(), AdIAft.end());
1404
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001405 //---- Insert code for popping the reg from the stack ----------
1406
Vikram S. Adveb5f8ada2003-07-02 01:13:57 +00001407 AdIBef.clear();
1408 AdIAft.clear();
1409
Vikram S. Adveaee67012002-07-08 23:23:12 +00001410 // We may need a scratch register to copy the saved value
1411 // from memory. This may itself have to insert code to
1412 // free up a scratch register. Any such code should go
Vikram S. Advea83804a2003-05-31 07:32:01 +00001413 // after the save code. As above, scratch is not marked "used".
Vikram S. Adveaee67012002-07-08 23:23:12 +00001414 //
1415 scratchRegType = -1;
1416 scratchReg = -1;
Chris Lattner56e91662002-08-12 21:25:05 +00001417 if (regTypeNeedsScratchReg(RegType, scratchRegType))
Vikram S. Adveaee67012002-07-08 23:23:12 +00001418 { // Find a register not live in the LVSet after CallMI
1419 scratchReg = PRA.getUsableUniRegAtMI(scratchRegType, &LVSetAft,
1420 CallMI, AdIBef, AdIAft);
Chris Lattner56e91662002-08-12 21:25:05 +00001421 assert(scratchReg != getInvalidRegNum());
Vikram S. Adveaee67012002-07-08 23:23:12 +00001422 }
1423
1424 if (AdIBef.size() > 0)
1425 instrnsAfter.insert(instrnsAfter.end(),
1426 AdIBef.begin(), AdIBef.end());
1427
1428 cpMem2RegMI(instrnsAfter, getFramePointer(), StackOff,Reg,RegType,
1429 scratchReg);
1430
1431 if (AdIAft.size() > 0)
1432 instrnsAfter.insert(instrnsAfter.end(),
1433 AdIAft.begin(), AdIAft.end());
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001434
Chris Lattner7e5ee422002-02-05 04:20:12 +00001435 PushedRegSet.insert(Reg);
Vikram S. Adveaee67012002-07-08 23:23:12 +00001436
Ruchira Sasanka1812fc42001-11-10 00:26:55 +00001437 if(DEBUG_RA) {
Misha Brukman352f7ac2003-05-21 17:59:06 +00001438 std::cerr << "\nFor call inst:" << *CallMI;
1439 std::cerr << " -inserted caller saving instrs: Before:\n\t ";
Vikram S. Adveaee67012002-07-08 23:23:12 +00001440 for_each(instrnsBefore.begin(), instrnsBefore.end(),
Anand Shukla7e882db2002-07-09 19:16:59 +00001441 std::mem_fun(&MachineInstr::dump));
Misha Brukman352f7ac2003-05-21 17:59:06 +00001442 std::cerr << " -and After:\n\t ";
Vikram S. Adveaee67012002-07-08 23:23:12 +00001443 for_each(instrnsAfter.begin(), instrnsAfter.end(),
Anand Shukla7e882db2002-07-09 19:16:59 +00001444 std::mem_fun(&MachineInstr::dump));
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001445 }
1446 } // if not already pushed
1447
1448 } // if LR has a volatile color
1449
1450 } // if LR has color
1451
1452 } // if there is a LR for Var
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001453
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001454 } // for each value in the LV set after instruction
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001455}
1456
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001457
Ruchira Sasankadfc6c882001-09-18 22:52:44 +00001458//---------------------------------------------------------------------------
1459// Print the register assigned to a LR
1460//---------------------------------------------------------------------------
1461
Vikram S. Adve8adb9942003-05-27 00:02:22 +00001462void UltraSparcRegInfo::printReg(const LiveRange *LR) const {
Chris Lattnerf9fd5912003-01-15 21:14:32 +00001463 unsigned RegClassID = LR->getRegClassID();
Misha Brukman352f7ac2003-05-21 17:59:06 +00001464 std::cerr << " *Node " << (LR->getUserIGNode())->getIndex();
Ruchira Sasankadfc6c882001-09-18 22:52:44 +00001465
Chris Lattner5216cc52002-02-04 05:59:25 +00001466 if (!LR->hasColor()) {
Misha Brukman352f7ac2003-05-21 17:59:06 +00001467 std::cerr << " - could not find a color\n";
Ruchira Sasankadfc6c882001-09-18 22:52:44 +00001468 return;
1469 }
1470
1471 // if a color is found
1472
Misha Brukman352f7ac2003-05-21 17:59:06 +00001473 std::cerr << " colored with color "<< LR->getColor();
Ruchira Sasankadfc6c882001-09-18 22:52:44 +00001474
Vikram S. Adve8adb9942003-05-27 00:02:22 +00001475 unsigned uRegName = getUnifiedRegNum(RegClassID, LR->getColor());
1476
1477 std::cerr << "[";
1478 std::cerr<< getUnifiedRegName(uRegName);
1479 if (RegClassID == FloatRegClassID && LR->getType() == Type::DoubleTy)
1480 std::cerr << "+" << getUnifiedRegName(uRegName+1);
1481 std::cerr << "]\n";
Ruchira Sasankadfc6c882001-09-18 22:52:44 +00001482}
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001483
1484//---------------------------------------------------------------------------
1485// This method examines instructions inserted by RegAlloc code before a
1486// machine instruction to detect invalid orders that destroy values before
1487// they are used. If it detects such conditions, it reorders the instructions.
1488//
1489// The unordered instructions come in the UnordVec. These instructions are
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001490// instructions inserted by RegAlloc. All such instruction MUST have
1491// their USES BEFORE THE DEFS after reordering.
Vikram S. Advee9327f02002-05-19 15:25:51 +00001492//
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001493// The UnordVec & OrdVec must be DISTINCT. The OrdVec must be empty when
1494// this method is called.
Vikram S. Advee9327f02002-05-19 15:25:51 +00001495//
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001496// This method uses two vectors for efficiency in accessing
Vikram S. Advee9327f02002-05-19 15:25:51 +00001497//
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001498// Since instructions are inserted in RegAlloc, this assumes that the
1499// first operand is the source reg and the last operand is the dest reg.
Vikram S. Adveaee67012002-07-08 23:23:12 +00001500// It also does not consider operands that are both use and def.
Vikram S. Advee9327f02002-05-19 15:25:51 +00001501//
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001502// All the uses are before THE def to a register
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001503//---------------------------------------------------------------------------
Vikram S. Advee9327f02002-05-19 15:25:51 +00001504
1505void UltraSparcRegInfo::OrderAddedInstrns(std::vector<MachineInstr*> &UnordVec,
1506 std::vector<MachineInstr*> &OrdVec,
Chris Lattner7f74a562002-01-20 22:54:45 +00001507 PhyRegAlloc &PRA) const{
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001508
1509 /*
1510 Problem: We can have instructions inserted by RegAlloc like
1511 1. add %ox %g0 %oy
1512 2. add %oy %g0 %oz, where z!=x or z==x
1513
1514 This is wrong since %oy used by 2 is overwritten by 1
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001515
1516 Solution:
1517 We re-order the instructions so that the uses are before the defs
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001518
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001519 Algorithm:
1520
1521 do
1522 for each instruction 'DefInst' in the UnOrdVec
1523 for each instruction 'UseInst' that follows the DefInst
1524 if the reg defined by DefInst is used by UseInst
1525 mark DefInst as not movable in this iteration
1526 If DefInst is not marked as not-movable, move DefInst to OrdVec
1527 while all instructions in DefInst are moved to OrdVec
1528
1529 For moving, we call the move2OrdVec(). It checks whether there is a def
1530 in it for the uses in the instruction to be added to OrdVec. If there
1531 are no preceding defs, it just appends the instruction. If there is a
1532 preceding def, it puts two instructions to save the reg on stack before
1533 the load and puts a restore at use.
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001534
1535 */
1536
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001537 bool CouldMoveAll;
1538 bool DebugPrint = false;
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001539
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001540 do {
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001541 CouldMoveAll = true;
Misha Brukman352f7ac2003-05-21 17:59:06 +00001542 std::vector<MachineInstr*>::iterator DefIt = UnordVec.begin();
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001543
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001544 for( ; DefIt != UnordVec.end(); ++DefIt ) {
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001545
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001546 // for each instruction in the UnordVec do ...
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001547
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001548 MachineInstr *DefInst = *DefIt;
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001549
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001550 if( DefInst == NULL) continue;
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001551
Misha Brukman352f7ac2003-05-21 17:59:06 +00001552 //std::cerr << "\nInst in UnordVec = " << *DefInst;
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001553
1554 // last operand is the def (unless for a store which has no def reg)
1555 MachineOperand& DefOp = DefInst->getOperand(DefInst->getNumOperands()-1);
1556
Vikram S. Adve8adb9942003-05-27 00:02:22 +00001557 if ((DefOp.opIsDefOnly() || DefOp.opIsDefAndUse()) &&
Chris Lattner6a30b022002-10-28 04:45:29 +00001558 DefOp.getType() == MachineOperand::MO_MachineRegister) {
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001559
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001560 // If the operand in DefInst is a def ...
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001561 bool DefEqUse = false;
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001562
Misha Brukman352f7ac2003-05-21 17:59:06 +00001563 std::vector<MachineInstr*>::iterator UseIt = DefIt;
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001564 UseIt++;
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001565
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001566 for( ; UseIt != UnordVec.end(); ++UseIt ) {
1567
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001568 MachineInstr *UseInst = *UseIt;
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001569 if( UseInst == NULL) continue;
1570
1571 // for each inst (UseInst) that is below the DefInst do ...
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001572 MachineOperand& UseOp = UseInst->getOperand(0);
1573
Vikram S. Adve8adb9942003-05-27 00:02:22 +00001574 if (!UseOp.opIsDefOnly() &&
Chris Lattner6a30b022002-10-28 04:45:29 +00001575 UseOp.getType() == MachineOperand::MO_MachineRegister) {
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001576
1577 // if use is a register ...
1578
1579 if( DefOp.getMachineRegNum() == UseOp.getMachineRegNum() ) {
1580
1581 // if Def and this use are the same, it means that this use
1582 // is destroyed by a def before it is used
1583
Misha Brukman352f7ac2003-05-21 17:59:06 +00001584 // std::cerr << "\nCouldn't move " << *DefInst;
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001585
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001586 DefEqUse = true;
1587 CouldMoveAll = false;
1588 DebugPrint = true;
1589 break;
1590 } // if two registers are equal
1591
1592 } // if use is a register
1593
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001594 }// for all use instructions
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001595
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001596 if( ! DefEqUse ) {
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001597
1598 // after examining all the instructions that follow the DefInst
1599 // if there are no dependencies, we can move it to the OrdVec
1600
Misha Brukman352f7ac2003-05-21 17:59:06 +00001601 // std::cerr << "Moved to Ord: " << *DefInst;
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001602
1603 moveInst2OrdVec(OrdVec, DefInst, PRA);
1604
1605 //OrdVec.push_back(DefInst);
1606
1607 // mark the pos of DefInst with NULL to indicate that it is
1608 // empty
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001609 *DefIt = NULL;
1610 }
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001611
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001612 } // if Def is a machine register
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001613
1614 } // for all instructions in the UnordVec
1615
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001616
Chris Lattner5216cc52002-02-04 05:59:25 +00001617 } while(!CouldMoveAll);
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001618
Chris Lattner070cf772002-06-04 03:09:57 +00001619 if (DebugPrint && DEBUG_RA) {
Misha Brukman352f7ac2003-05-21 17:59:06 +00001620 std::cerr << "\nAdded instructions were reordered to:\n";
Chris Lattnerd47aac92002-12-28 20:21:29 +00001621 for(unsigned i=0; i < OrdVec.size(); i++)
Misha Brukman352f7ac2003-05-21 17:59:06 +00001622 std::cerr << *OrdVec[i];
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001623 }
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001624}
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001625
1626
1627
1628
1629
Misha Brukman352f7ac2003-05-21 17:59:06 +00001630void UltraSparcRegInfo::moveInst2OrdVec(std::vector<MachineInstr*> &OrdVec,
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001631 MachineInstr *UnordInst,
Chris Lattner5216cc52002-02-04 05:59:25 +00001632 PhyRegAlloc &PRA) const {
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001633 MachineOperand& UseOp = UnordInst->getOperand(0);
1634
Vikram S. Adve8adb9942003-05-27 00:02:22 +00001635 if (!UseOp.opIsDefOnly() &&
Chris Lattner6a30b022002-10-28 04:45:29 +00001636 UseOp.getType() == MachineOperand::MO_MachineRegister) {
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001637
1638 // for the use of UnordInst, see whether there is a defining instr
1639 // before in the OrdVec
1640 bool DefEqUse = false;
1641
Misha Brukman352f7ac2003-05-21 17:59:06 +00001642 std::vector<MachineInstr*>::iterator OrdIt = OrdVec.begin();
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001643
1644 for( ; OrdIt != OrdVec.end(); ++OrdIt ) {
1645
1646 MachineInstr *OrdInst = *OrdIt ;
1647
1648 MachineOperand& DefOp =
1649 OrdInst->getOperand(OrdInst->getNumOperands()-1);
1650
Vikram S. Adve8adb9942003-05-27 00:02:22 +00001651 if( (DefOp.opIsDefOnly() || DefOp.opIsDefAndUse()) &&
Chris Lattner6a30b022002-10-28 04:45:29 +00001652 DefOp.getType() == MachineOperand::MO_MachineRegister) {
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001653
Misha Brukman352f7ac2003-05-21 17:59:06 +00001654 //std::cerr << "\nDefining Ord Inst: " << *OrdInst;
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001655
1656 if( DefOp.getMachineRegNum() == UseOp.getMachineRegNum() ) {
1657
1658 // we are here because there is a preceding def in the OrdVec
1659 // for the use in this intr we are going to insert. This
1660 // happened because the original code was like:
1661 // 1. add %ox %g0 %oy
1662 // 2. add %oy %g0 %ox
1663 // In Round1, we added 2 to OrdVec but 1 remained in UnordVec
1664 // Now we are processing %ox of 1.
1665 // We have to
1666
Chris Lattnere3aa50d2002-10-28 19:32:07 +00001667 int UReg = DefOp.getMachineRegNum();
1668 int RegType = getRegType(UReg);
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001669 MachineInstr *AdIBef, *AdIAft;
1670
Chris Lattnerd47aac92002-12-28 20:21:29 +00001671 int StackOff =
1672 PRA.MF.getInfo()->pushTempValue(getSpilledRegSize(RegType));
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001673
1674 // Save the UReg (%ox) on stack before it's destroyed
Misha Brukman352f7ac2003-05-21 17:59:06 +00001675 std::vector<MachineInstr*> mvec;
Vikram S. Adveaee67012002-07-08 23:23:12 +00001676 cpReg2MemMI(mvec, UReg, getFramePointer(), StackOff, RegType);
Misha Brukman352f7ac2003-05-21 17:59:06 +00001677 for (std::vector<MachineInstr*>::iterator MI=mvec.begin();
Chris Lattnerd47aac92002-12-28 20:21:29 +00001678 MI != mvec.end(); ++MI)
1679 OrdIt = 1+OrdVec.insert(OrdIt, *MI);
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001680
1681 // Load directly into DReg (%oy)
1682 MachineOperand& DOp=
1683 (UnordInst->getOperand(UnordInst->getNumOperands()-1));
Vikram S. Adve8adb9942003-05-27 00:02:22 +00001684 assert((DOp.opIsDefOnly() || DefOp.opIsDefAndUse()) &&
1685 "Last operand is not the def");
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001686 const int DReg = DOp.getMachineRegNum();
1687
Vikram S. Adveaee67012002-07-08 23:23:12 +00001688 cpMem2RegMI(OrdVec, getFramePointer(), StackOff, DReg, RegType);
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001689
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001690 if( DEBUG_RA ) {
Misha Brukman352f7ac2003-05-21 17:59:06 +00001691 std::cerr << "\nFixed CIRCULAR references by reordering:";
1692 std::cerr << "\nBefore CIRCULAR Reordering:\n";
1693 std::cerr << *UnordInst;
1694 std::cerr << *OrdInst;
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001695
Misha Brukman352f7ac2003-05-21 17:59:06 +00001696 std::cerr << "\nAfter CIRCULAR Reordering - All Inst so far:\n";
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001697 for(unsigned i=0; i < OrdVec.size(); i++)
Misha Brukman352f7ac2003-05-21 17:59:06 +00001698 std::cerr << *(OrdVec[i]);
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001699 }
1700
1701 // Do not copy the UseInst to OrdVec
1702 DefEqUse = true;
1703 break;
1704
1705 }// if two registers are equal
1706
1707 } // if Def is a register
1708
1709 } // for each instr in OrdVec
1710
Chris Lattner5216cc52002-02-04 05:59:25 +00001711 if(!DefEqUse) {
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001712
1713 // We didn't find a def in the OrdVec, so just append this inst
1714 OrdVec.push_back( UnordInst );
Misha Brukman352f7ac2003-05-21 17:59:06 +00001715 //std::cerr << "Reordered Inst (Moved Dn): " << *UnordInst;
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001716 }
1717
1718 }// if the operand in UnordInst is a use
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001719}