blob: 9a3c7bd0b5f3be910b3b69c0133327859feb3c44 [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"
10#include "llvm/Target/Sparc.h"
Chris Lattner029af0b2002-02-03 07:52:04 +000011#include "llvm/CodeGen/MachineCodeForMethod.h"
Ruchira Sasankadfc6c882001-09-18 22:52:44 +000012#include "llvm/CodeGen/PhyRegAlloc.h"
Chris Lattner5216cc52002-02-04 05:59:25 +000013#include "llvm/CodeGen/MachineInstr.h"
Chris Lattner5216cc52002-02-04 05:59:25 +000014#include "llvm/Analysis/LiveVar/MethodLiveVarInfo.h"
15#include "llvm/iTerminators.h"
16#include "llvm/iOther.h"
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +000017#include "llvm/DerivedTypes.h"
Chris Lattner7f74a562002-01-20 22:54:45 +000018#include <iostream>
19using std::cerr;
Chris Lattnerb0ddffa2001-09-14 03:47:57 +000020
Chris Lattner5216cc52002-02-04 05:59:25 +000021UltraSparcRegInfo::UltraSparcRegInfo(const UltraSparc &tgt)
22 : MachineRegInfo(tgt), UltraSparcInfo(&tgt), NumOfIntArgRegs(6),
23 NumOfFloatArgRegs(32), InvalidRegNum(1000) {
24
25 MachineRegClassArr.push_back(new SparcIntRegClass(IntRegClassID));
26 MachineRegClassArr.push_back(new SparcFloatRegClass(FloatRegClassID));
27 MachineRegClassArr.push_back(new SparcIntCCRegClass(IntCCRegClassID));
28 MachineRegClassArr.push_back(new SparcFloatCCRegClass(FloatCCRegClassID));
29
30 assert(SparcFloatRegOrder::StartOfNonVolatileRegs == 32 &&
31 "32 Float regs are used for float arg passing");
32}
33
34
Vikram S. Advedb1435f2002-03-18 03:12:16 +000035// getZeroRegNum - returns the register that contains always zero.
36// this is the unified register number
Chris Lattner5216cc52002-02-04 05:59:25 +000037//
Vikram S. Advedb1435f2002-03-18 03:12:16 +000038int UltraSparcRegInfo::getZeroRegNum() const {
39 return this->getUnifiedRegNum(UltraSparcRegInfo::IntRegClassID,
40 SparcIntRegOrder::g0);
41}
Chris Lattner5216cc52002-02-04 05:59:25 +000042
43// getCallAddressReg - returns the reg used for pushing the address when a
44// method is called. This can be used for other purposes between calls
45//
46unsigned UltraSparcRegInfo::getCallAddressReg() const {
Vikram S. Advedb1435f2002-03-18 03:12:16 +000047 return this->getUnifiedRegNum(UltraSparcRegInfo::IntRegClassID,
48 SparcIntRegOrder::o7);
Chris Lattner5216cc52002-02-04 05:59:25 +000049}
50
51// Returns the register containing the return address.
52// It should be made sure that this register contains the return
53// value when a return instruction is reached.
54//
55unsigned UltraSparcRegInfo::getReturnAddressReg() const {
Vikram S. Advedb1435f2002-03-18 03:12:16 +000056 return this->getUnifiedRegNum(UltraSparcRegInfo::IntRegClassID,
57 SparcIntRegOrder::i7);
Chris Lattner5216cc52002-02-04 05:59:25 +000058}
59
60// given the unified register number, this gives the name
61// for generating assembly code or debugging.
62//
63const std::string UltraSparcRegInfo::getUnifiedRegName(int reg) const {
64 if( reg < 32 )
65 return SparcIntRegOrder::getRegName(reg);
66 else if ( reg < (64 + 32) )
67 return SparcFloatRegOrder::getRegName( reg - 32);
68 else if( reg < (64+32+4) )
69 return SparcFloatCCRegOrder::getRegName( reg -32 - 64);
70 else if( reg < (64+32+4+2) ) // two names: %xcc and %ccr
71 return SparcIntCCRegOrder::getRegName( reg -32 - 64 - 4);
72 else if (reg== InvalidRegNum) //****** TODO: Remove */
73 return "<*NoReg*>";
74 else
75 assert(0 && "Invalid register number");
76 return "";
77}
78
Vikram S. Advedb1435f2002-03-18 03:12:16 +000079// Get unified reg number for frame pointer
Chris Lattner5216cc52002-02-04 05:59:25 +000080unsigned UltraSparcRegInfo::getFramePointer() const {
Vikram S. Advedb1435f2002-03-18 03:12:16 +000081 return this->getUnifiedRegNum(UltraSparcRegInfo::IntRegClassID,
82 SparcIntRegOrder::i6);
Chris Lattner5216cc52002-02-04 05:59:25 +000083}
84
Vikram S. Advedb1435f2002-03-18 03:12:16 +000085// Get unified reg number for stack pointer
Chris Lattner5216cc52002-02-04 05:59:25 +000086unsigned UltraSparcRegInfo::getStackPointer() const {
Vikram S. Advedb1435f2002-03-18 03:12:16 +000087 return this->getUnifiedRegNum(UltraSparcRegInfo::IntRegClassID,
88 SparcIntRegOrder::o6);
Chris Lattner5216cc52002-02-04 05:59:25 +000089}
90
91
92
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +000093//---------------------------------------------------------------------------
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +000094// Finds the return value of a sparc specific call instruction
Ruchira Sasankadfc6c882001-09-18 22:52:44 +000095//---------------------------------------------------------------------------
Ruchira Sasanka24729a32001-10-21 16:43:41 +000096const Value *
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +000097UltraSparcRegInfo::getCallInstRetVal(const MachineInstr *CallMI) const {
Ruchira Sasanka24729a32001-10-21 16:43:41 +000098 unsigned OpCode = CallMI->getOpCode();
Chris Lattner7f74a562002-01-20 22:54:45 +000099 unsigned NumOfImpRefs = CallMI->getNumImplicitRefs();
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000100
Chris Lattner7f74a562002-01-20 22:54:45 +0000101 if (OpCode == CALL) {
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000102
103 // The one before the last implicit operand is the return value of
104 // a CALL instr
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000105 //
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000106 if( NumOfImpRefs > 1 )
Chris Lattner5216cc52002-02-04 05:59:25 +0000107 if (CallMI->implicitRefIsDefined(NumOfImpRefs-2))
108 return CallMI->getImplicitRef(NumOfImpRefs-2);
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000109
Chris Lattner7f74a562002-01-20 22:54:45 +0000110 } else if (OpCode == JMPLCALL) {
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000111
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000112 // The last implicit operand is the return value of a JMPL
113 //
Chris Lattner7f74a562002-01-20 22:54:45 +0000114 if(NumOfImpRefs > 0)
115 if (CallMI->implicitRefIsDefined(NumOfImpRefs-1))
116 return CallMI->getImplicitRef(NumOfImpRefs-1);
Chris Lattner5216cc52002-02-04 05:59:25 +0000117 } else
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000118 assert(0 && "OpCode must be CALL/JMPL for a call instr");
119
120 return NULL;
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000121}
122
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000123
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000124
125//---------------------------------------------------------------------------
126// Finds the return address of a call sparc specific call instruction
127//---------------------------------------------------------------------------
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000128const Value *
Chris Lattner5216cc52002-02-04 05:59:25 +0000129UltraSparcRegInfo::getCallInstRetAddr(const MachineInstr *CallMI) const {
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000130 unsigned OpCode = CallMI->getOpCode();
131
Chris Lattner5216cc52002-02-04 05:59:25 +0000132 if (OpCode == CALL) {
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000133 unsigned NumOfImpRefs = CallMI->getNumImplicitRefs();
134
135 assert( NumOfImpRefs && "CALL instr must have at least on ImpRef");
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000136
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000137 // The last implicit operand is the return address of a CALL instr
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000138 //
Chris Lattner5216cc52002-02-04 05:59:25 +0000139 return CallMI->getImplicitRef(NumOfImpRefs-1);
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000140
Chris Lattner5216cc52002-02-04 05:59:25 +0000141 } else if(OpCode == JMPLCALL) {
142 MachineOperand &MO = (MachineOperand &)CallMI->getOperand(2);
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000143 return MO.getVRegValue();
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000144 }
Chris Lattner5216cc52002-02-04 05:59:25 +0000145
146 assert(0 && "OpCode must be CALL/JMPL for a call instr");
147 return 0;
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000148}
149
Chris Lattner5216cc52002-02-04 05:59:25 +0000150// The following 3 methods are used to find the RegType (see enum above)
151// of a LiveRange, Value and using the unified RegClassID
152//
153int UltraSparcRegInfo::getRegType(const LiveRange *LR) const {
Chris Lattner5216cc52002-02-04 05:59:25 +0000154 switch (LR->getRegClass()->getID()) {
155 case IntRegClassID: return IntRegType;
Chris Lattnerd30f9892002-02-05 03:52:29 +0000156 case FloatRegClassID: {
157 const Type *Typ = LR->getType();
158 if (Typ == Type::FloatTy)
Chris Lattner5216cc52002-02-04 05:59:25 +0000159 return FPSingleRegType;
Chris Lattnerd30f9892002-02-05 03:52:29 +0000160 else if (Typ == Type::DoubleTy)
Chris Lattner5216cc52002-02-04 05:59:25 +0000161 return FPDoubleRegType;
162 assert(0 && "Unknown type in FloatRegClass");
Chris Lattnerd30f9892002-02-05 03:52:29 +0000163 }
Chris Lattner5216cc52002-02-04 05:59:25 +0000164 case IntCCRegClassID: return IntCCRegType;
165 case FloatCCRegClassID: return FloatCCRegType;
166 default: assert( 0 && "Unknown reg class ID");
167 return 0;
168 }
169}
170
171int UltraSparcRegInfo::getRegType(const Value *Val) const {
172 unsigned Typ;
173
174 switch (getRegClassIDOfValue(Val)) {
175 case IntRegClassID: return IntRegType;
176 case FloatRegClassID:
177 Typ = Val->getType()->getPrimitiveID();
178 if (Typ == Type::FloatTyID)
179 return FPSingleRegType;
180 else if (Typ == Type::DoubleTyID)
181 return FPDoubleRegType;
182 assert(0 && "Unknown type in FloatRegClass");
183
184 case IntCCRegClassID: return IntCCRegType;
185 case FloatCCRegClassID: return FloatCCRegType ;
186 default: assert(0 && "Unknown reg class ID");
187 return 0;
188 }
189}
190
191int UltraSparcRegInfo::getRegType(int reg) const {
192 if (reg < 32)
193 return IntRegType;
194 else if (reg < (32 + 32))
195 return FPSingleRegType;
196 else if (reg < (64 + 32))
197 return FPDoubleRegType;
198 else if (reg < (64+32+4))
199 return FloatCCRegType;
200 else if (reg < (64+32+4+2))
201 return IntCCRegType;
202 else
203 assert(0 && "Invalid register number in getRegType");
Chris Lattner5536c9c2002-02-24 23:02:40 +0000204 return 0;
Chris Lattner5216cc52002-02-04 05:59:25 +0000205}
206
207
208
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000209
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000210
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000211//---------------------------------------------------------------------------
Vikram S. Adve84982772001-10-22 13:41:12 +0000212// Finds the # of actual arguments of the call instruction
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000213//---------------------------------------------------------------------------
Chris Lattner5216cc52002-02-04 05:59:25 +0000214unsigned
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000215UltraSparcRegInfo::getCallInstNumArgs(const MachineInstr *CallMI) const {
216
217 unsigned OpCode = CallMI->getOpCode();
Chris Lattner5216cc52002-02-04 05:59:25 +0000218 unsigned NumOfImpRefs = CallMI->getNumImplicitRefs();
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000219
Chris Lattner5216cc52002-02-04 05:59:25 +0000220 if (OpCode == CALL) {
221 switch (NumOfImpRefs) {
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000222 case 0: assert(0 && "A CALL inst must have at least one ImpRef (RetAddr)");
Chris Lattner5216cc52002-02-04 05:59:25 +0000223 case 1: return 0;
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000224 default: // two or more implicit refs
Chris Lattner5216cc52002-02-04 05:59:25 +0000225 if (CallMI->implicitRefIsDefined(NumOfImpRefs-2))
226 return NumOfImpRefs - 2;
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000227 else
Chris Lattner5216cc52002-02-04 05:59:25 +0000228 return NumOfImpRefs - 1;
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000229 }
Chris Lattner5216cc52002-02-04 05:59:25 +0000230 } else if (OpCode == JMPLCALL) {
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000231
232 // The last implicit operand is the return value of a JMPL instr
233 if( NumOfImpRefs > 0 ) {
Chris Lattner5216cc52002-02-04 05:59:25 +0000234 if (CallMI->implicitRefIsDefined(NumOfImpRefs-1))
235 return NumOfImpRefs - 1;
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000236 else
Chris Lattner5216cc52002-02-04 05:59:25 +0000237 return NumOfImpRefs;
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000238 }
239 else
Chris Lattner5216cc52002-02-04 05:59:25 +0000240 return NumOfImpRefs;
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000241 }
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000242
Chris Lattner5216cc52002-02-04 05:59:25 +0000243 assert(0 && "OpCode must be CALL/JMPL for a call instr");
244 return 0;
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000245}
246
247
Vikram S. Adve84982772001-10-22 13:41:12 +0000248
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000249//---------------------------------------------------------------------------
250// Finds whether a call is an indirect call
251//---------------------------------------------------------------------------
252bool UltraSparcRegInfo::isVarArgCall(const MachineInstr *CallMI) const {
253
254 assert ( (UltraSparcInfo->getInstrInfo()).isCall(CallMI->getOpCode()) );
255
256 const MachineOperand & calleeOp = CallMI->getOperand(0);
257 Value *calleeVal = calleeOp.getVRegValue();
258
259 PointerType *PT = cast<PointerType> (calleeVal->getType());
260 MethodType *MT = cast<MethodType>(PT->getElementType());
261
262 return MT->isVarArg();
263}
264
265
266
267
268//---------------------------------------------------------------------------
269// Suggests a register for the ret address in the RET machine instruction.
270// We always suggest %i7 by convention.
271//---------------------------------------------------------------------------
Chris Lattner5216cc52002-02-04 05:59:25 +0000272void UltraSparcRegInfo::suggestReg4RetAddr(const MachineInstr *RetMI,
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000273 LiveRangeInfo& LRI) const {
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000274
Vikram S. Adve84982772001-10-22 13:41:12 +0000275 assert( (RetMI->getNumOperands() >= 2)
276 && "JMPL/RETURN must have 3 and 2 operands respectively");
277
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000278 MachineOperand & MO = ( MachineOperand &) RetMI->getOperand(0);
279
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000280 // return address is always mapped to i7
281 //
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000282 MO.setRegForValue( getUnifiedRegNum( IntRegClassID, SparcIntRegOrder::i7) );
Vikram S. Adve84982772001-10-22 13:41:12 +0000283
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000284 // Possible Optimization:
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +0000285 // Instead of setting the color, we can suggest one. In that case,
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000286 // we have to test later whether it received the suggested color.
287 // In that case, a LR has to be created at the start of method.
288 // It has to be done as follows (remove the setRegVal above):
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000289
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000290 // const Value *RetAddrVal = MO.getVRegValue();
291 // assert( RetAddrVal && "LR for ret address must be created at start");
292 // LiveRange * RetAddrLR = LRI.getLiveRangeForValue( RetAddrVal);
293 // RetAddrLR->setSuggestedColor(getUnifiedRegNum( IntRegClassID,
294 // SparcIntRegOrdr::i7) );
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000295}
296
297
298//---------------------------------------------------------------------------
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000299// Suggests a register for the ret address in the JMPL/CALL machine instr.
300// Sparc ABI dictates that %o7 be used for this purpose.
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000301//---------------------------------------------------------------------------
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000302void UltraSparcRegInfo::suggestReg4CallAddr(const MachineInstr * CallMI,
303 LiveRangeInfo& LRI,
Chris Lattner7f74a562002-01-20 22:54:45 +0000304 std::vector<RegClass *> RCList) const {
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000305
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000306
307 const Value *RetAddrVal = getCallInstRetAddr( CallMI );
308
309 // RetAddrVal cannot be NULL (asserted in getCallInstRetAddr)
310 // create a new LR for the return address and color it
311
312 LiveRange * RetAddrLR = new LiveRange();
Chris Lattnere6b511d2002-02-04 16:37:09 +0000313 RetAddrLR->insert( RetAddrVal );
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000314 unsigned RegClassID = getRegClassIDOfValue( RetAddrVal );
315 RetAddrLR->setRegClass( RCList[RegClassID] );
316 RetAddrLR->setColor(getUnifiedRegNum(IntRegClassID,SparcIntRegOrder::o7));
317 LRI.addLRToMap( RetAddrVal, RetAddrLR);
318
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000319}
320
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000321
322
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000323
324//---------------------------------------------------------------------------
325// This method will suggest colors to incoming args to a method.
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000326// According to the Sparc ABI, the first 6 incoming args are in
327// %i0 - %i5 (if they are integer) OR in %f0 - %f31 (if they are float).
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000328// If the arg is passed on stack due to the lack of regs, NOTHING will be
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000329// done - it will be colored (or spilled) as a normal live range.
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000330//---------------------------------------------------------------------------
Chris Lattner5216cc52002-02-04 05:59:25 +0000331void UltraSparcRegInfo::suggestRegs4MethodArgs(const Method *Meth,
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000332 LiveRangeInfo& LRI) const
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000333{
334
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000335 // get the argument list
336 const Method::ArgumentListType& ArgList = Meth->getArgumentList();
337 // get an iterator to arg list
338 Method::ArgumentListType::const_iterator ArgIt = ArgList.begin();
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000339
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000340 // for each argument
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000341 for( unsigned argNo=0; ArgIt != ArgList.end() ; ++ArgIt, ++argNo) {
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000342
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000343 // get the LR of arg
344 LiveRange *const LR = LRI.getLiveRangeForValue((const Value *) *ArgIt);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000345 assert( LR && "No live range found for method arg");
346
347 unsigned RegType = getRegType( LR );
348
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000349
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000350 // if the arg is in int class - allocate a reg for an int arg
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000351 //
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000352 if( RegType == IntRegType ) {
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000353
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000354 if( argNo < NumOfIntArgRegs) {
355 LR->setSuggestedColor( SparcIntRegOrder::i0 + argNo );
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000356 }
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000357 else {
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000358 // Do NOTHING as this will be colored as a normal value.
Chris Lattnerf3f1e452001-10-15 18:15:27 +0000359 if (DEBUG_RA) cerr << " Int Regr not suggested for method arg\n";
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000360 }
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000361
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000362 }
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000363 else if( RegType==FPSingleRegType && (argNo*2+1) < NumOfFloatArgRegs)
364 LR->setSuggestedColor( SparcFloatRegOrder::f0 + (argNo * 2 + 1) );
365
366
367 else if( RegType == FPDoubleRegType && (argNo*2) < NumOfFloatArgRegs)
368 LR->setSuggestedColor( SparcFloatRegOrder::f0 + (argNo * 2) );
369
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000370 }
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000371}
372
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000373
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000374
375//---------------------------------------------------------------------------
376// This method is called after graph coloring to move incoming args to
377// the correct hardware registers if they did not receive the correct
378// (suggested) color through graph coloring.
379//---------------------------------------------------------------------------
Chris Lattner5216cc52002-02-04 05:59:25 +0000380void UltraSparcRegInfo::colorMethodArgs(const Method *Meth,
381 LiveRangeInfo &LRI,
382 AddedInstrns *FirstAI) const {
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000383
384 // get the argument list
385 const Method::ArgumentListType& ArgList = Meth->getArgumentList();
386 // get an iterator to arg list
387 Method::ArgumentListType::const_iterator ArgIt = ArgList.begin();
388
389 MachineInstr *AdMI;
390
391
392 // for each argument
393 for( unsigned argNo=0; ArgIt != ArgList.end() ; ++ArgIt, ++argNo) {
394
395 // get the LR of arg
396 LiveRange *const LR = LRI.getLiveRangeForValue((const Value *) *ArgIt);
397 assert( LR && "No live range found for method arg");
398
399
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000400 unsigned RegType = getRegType( LR );
401 unsigned RegClassID = (LR->getRegClass())->getID();
402
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000403 // Find whether this argument is coming in a register (if not, on stack)
404 // Also find the correct register that the argument must go (UniArgReg)
405 //
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000406 bool isArgInReg = false;
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000407 unsigned UniArgReg = InvalidRegNum; // reg that LR MUST be colored with
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000408
409 if( (RegType== IntRegType && argNo < NumOfIntArgRegs)) {
410 isArgInReg = true;
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000411 UniArgReg = getUnifiedRegNum( RegClassID, SparcIntRegOrder::i0 + argNo );
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000412 }
413 else if(RegType == FPSingleRegType && argNo < NumOfFloatArgRegs) {
414 isArgInReg = true;
415 UniArgReg = getUnifiedRegNum( RegClassID,
416 SparcFloatRegOrder::f0 + argNo*2 + 1 ) ;
417 }
418 else if(RegType == FPDoubleRegType && argNo < NumOfFloatArgRegs) {
419 isArgInReg = true;
420 UniArgReg = getUnifiedRegNum(RegClassID, SparcFloatRegOrder::f0+argNo*2);
421 }
422
423
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000424 if( LR->hasColor() ) { // if this arg received a register
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000425
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000426 unsigned UniLRReg = getUnifiedRegNum( RegClassID, LR->getColor() );
427
428 // if LR received the correct color, nothing to do
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000429 //
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000430 if( UniLRReg == UniArgReg )
431 continue;
432
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000433 // We are here because the LR did not receive the suggested
434 // but LR received another register.
435 // Now we have to copy the %i reg (or stack pos of arg)
436 // to the register the LR was colored with.
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000437
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000438 // if the arg is coming in UniArgReg register, it MUST go into
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000439 // the UniLRReg register
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000440 //
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000441 if( isArgInReg )
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000442 AdMI = cpReg2RegMI( UniArgReg, UniLRReg, RegType );
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000443
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000444 else {
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000445
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000446 // Now the arg is coming on stack. Since the LR recieved a register,
447 // we just have to load the arg on stack into that register
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000448 //
Vikram S. Adve7a1524f2001-11-08 04:56:41 +0000449 const MachineFrameInfo& frameInfo = target.getFrameInfo();
450 assert(frameInfo.argsOnStackHaveFixedSize());
451
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000452 bool growUp; // find the offset of arg in stack frame
Vikram S. Adve7a1524f2001-11-08 04:56:41 +0000453 int firstArg =
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000454 frameInfo.getFirstIncomingArgOffset(MachineCodeForMethod::get(Meth),
455 growUp);
Vikram S. Adve7a1524f2001-11-08 04:56:41 +0000456 int offsetFromFP =
457 growUp? firstArg + argNo * frameInfo.getSizeOfEachArgOnStack()
458 : firstArg - argNo * frameInfo.getSizeOfEachArgOnStack();
459
460 AdMI = cpMem2RegMI(getFramePointer(), offsetFromFP,
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000461 UniLRReg, RegType );
462 }
463
464 FirstAI->InstrnsBefore.push_back( AdMI );
465
466 } // if LR received a color
467
468 else {
469
470 // Now, the LR did not receive a color. But it has a stack offset for
471 // spilling.
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000472 // So, if the arg is coming in UniArgReg register, we can just move
473 // that on to the stack pos of LR
474
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000475 if( isArgInReg ) {
Chris Lattner7f74a562002-01-20 22:54:45 +0000476 cpReg2MemMI(UniArgReg, getFramePointer(),
477 LR->getSpillOffFromFP(), RegType );
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000478
479 FirstAI->InstrnsBefore.push_back( AdMI );
480 }
481
482 else {
483
484 // Now the arg is coming on stack. Since the LR did NOT
485 // recieved a register as well, it is allocated a stack position. We
486 // can simply change the stack poistion of the LR. We can do this,
487 // since this method is called before any other method that makes
488 // uses of the stack pos of the LR (e.g., updateMachineInstr)
489
Vikram S. Adve7a1524f2001-11-08 04:56:41 +0000490 const MachineFrameInfo& frameInfo = target.getFrameInfo();
491 assert(frameInfo.argsOnStackHaveFixedSize());
492
493 bool growUp;
494 int firstArg = frameInfo.getFirstIncomingArgOffset(MachineCodeForMethod::get(Meth), growUp);
495 int offsetFromFP =
496 growUp? firstArg + argNo * frameInfo.getSizeOfEachArgOnStack()
497 : firstArg - argNo * frameInfo.getSizeOfEachArgOnStack();
498
499 LR->modifySpillOffFromFP( offsetFromFP );
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000500 }
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000501
502 }
503
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000504 } // for each incoming argument
505
506}
507
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000508
509
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000510//---------------------------------------------------------------------------
511// This method is called before graph coloring to suggest colors to the
512// outgoing call args and the return value of the call.
513//---------------------------------------------------------------------------
Chris Lattner5216cc52002-02-04 05:59:25 +0000514void UltraSparcRegInfo::suggestRegs4CallArgs(const MachineInstr *CallMI,
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000515 LiveRangeInfo& LRI,
Chris Lattner7f74a562002-01-20 22:54:45 +0000516 std::vector<RegClass *> RCList) const {
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000517
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000518 assert ( (UltraSparcInfo->getInstrInfo()).isCall(CallMI->getOpCode()) );
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000519
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000520 suggestReg4CallAddr(CallMI, LRI, RCList);
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000521
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000522
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000523 // First color the return value of the call instruction. The return value
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000524 // will be in %o0 if the value is an integer type, or in %f0 if the
525 // value is a float type.
526
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000527 // the return value cannot have a LR in machine instruction since it is
528 // only defined by the call instruction
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000529
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000530 // if type is not void, create a new live range and set its
531 // register class and add to LRI
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000532
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000533
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000534 const Value *RetVal = getCallInstRetVal( CallMI );
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000535
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000536
Chris Lattner5216cc52002-02-04 05:59:25 +0000537 if (RetVal) {
538 assert ((!LRI.getLiveRangeForValue(RetVal)) &&
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000539 "LR for ret Value of call already definded!");
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000540
Chris Lattner5216cc52002-02-04 05:59:25 +0000541 // create a new LR for the return value
542 LiveRange *RetValLR = new LiveRange();
Chris Lattnere6b511d2002-02-04 16:37:09 +0000543 RetValLR->insert(RetVal);
Chris Lattner5216cc52002-02-04 05:59:25 +0000544 unsigned RegClassID = getRegClassIDOfValue(RetVal);
545 RetValLR->setRegClass(RCList[RegClassID]);
546 LRI.addLRToMap(RetVal, RetValLR);
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000547
548 // now suggest a register depending on the register class of ret arg
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000549
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000550 if( RegClassID == IntRegClassID )
551 RetValLR->setSuggestedColor(SparcIntRegOrder::o0);
552 else if (RegClassID == FloatRegClassID )
553 RetValLR->setSuggestedColor(SparcFloatRegOrder::f0 );
554 else assert( 0 && "Unknown reg class for return value of call\n");
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000555 }
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000556
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000557
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000558 // Now suggest colors for arguments (operands) of the call instruction.
559 // Colors are suggested only if the arg number is smaller than the
560 // the number of registers allocated for argument passing.
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000561 // Now, go thru call args - implicit operands of the call MI
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000562
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000563 unsigned NumOfCallArgs = getCallInstNumArgs( CallMI );
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000564
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000565 for(unsigned argNo=0, i=0; i < NumOfCallArgs; ++i, ++argNo ) {
566
567 const Value *CallArg = CallMI->getImplicitRef(i);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000568
569 // get the LR of call operand (parameter)
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000570 LiveRange *const LR = LRI.getLiveRangeForValue(CallArg);
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000571
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000572 // not possible to have a null LR since all args (even consts)
573 // must be defined before
Chris Lattner30e8fb62002-02-05 01:43:49 +0000574 if (!LR) {
575 cerr << " ERROR: In call instr, no LR for arg: " << RAV(CallArg) << "\n";
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000576 assert(0 && "NO LR for call arg");
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000577 }
578
579 unsigned RegType = getRegType( LR );
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000580
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000581 // if the arg is in int class - allocate a reg for an int arg
582 if( RegType == IntRegType ) {
583
584 if( argNo < NumOfIntArgRegs)
585 LR->setSuggestedColor( SparcIntRegOrder::o0 + argNo );
586
587 else if (DEBUG_RA)
588 // Do NOTHING as this will be colored as a normal value.
Chris Lattner7f74a562002-01-20 22:54:45 +0000589 cerr << " Regr not suggested for int call arg\n";
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000590
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000591 }
592 else if( RegType == FPSingleRegType && (argNo*2 +1)< NumOfFloatArgRegs)
593 LR->setSuggestedColor( SparcFloatRegOrder::f0 + (argNo * 2 + 1) );
594
595
596 else if( RegType == FPDoubleRegType && (argNo*2) < NumOfFloatArgRegs)
597 LR->setSuggestedColor( SparcFloatRegOrder::f0 + (argNo * 2) );
598
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000599
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000600 } // for all call arguments
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000601
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000602}
603
604
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000605//---------------------------------------------------------------------------
606// After graph coloring, we have call this method to see whehter the return
607// value and the call args received the correct colors. If not, we have
608// to instert copy instructions.
609//---------------------------------------------------------------------------
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000610
Chris Lattner5216cc52002-02-04 05:59:25 +0000611void UltraSparcRegInfo::colorCallArgs(const MachineInstr *CallMI,
612 LiveRangeInfo &LRI,
613 AddedInstrns *CallAI,
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000614 PhyRegAlloc &PRA,
615 const BasicBlock *BB) const {
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000616
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000617 assert ( (UltraSparcInfo->getInstrInfo()).isCall(CallMI->getOpCode()) );
618
Vikram S. Adve7a1524f2001-11-08 04:56:41 +0000619 // Reset the optional args area in the stack frame
620 // since that is reused for each call
621 //
622 PRA.mcInfo.resetOptionalArgs(target);
623
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000624 // First color the return value of the call.
625 // If there is a LR for the return value, it means this
626 // method returns a value
627
628 MachineInstr *AdMI;
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000629
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000630 const Value *RetVal = getCallInstRetVal( CallMI );
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000631
Chris Lattner30e8fb62002-02-05 01:43:49 +0000632 if (RetVal) {
633 LiveRange *RetValLR = LRI.getLiveRangeForValue( RetVal );
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000634
Chris Lattner30e8fb62002-02-05 01:43:49 +0000635 if (!RetValLR) {
636 cerr << "\nNo LR for:" << RAV(RetVal) << "\n";
637 assert(0 && "ERR:No LR for non-void return value");
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000638 }
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000639
640 unsigned RegClassID = (RetValLR->getRegClass())->getID();
641 bool recvCorrectColor = false;
642
643 unsigned CorrectCol; // correct color for ret value
644 if(RegClassID == IntRegClassID)
645 CorrectCol = SparcIntRegOrder::o0;
646 else if(RegClassID == FloatRegClassID)
647 CorrectCol = SparcFloatRegOrder::f0;
Chris Lattnere147d062001-11-07 14:01:59 +0000648 else {
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000649 assert( 0 && "Unknown RegClass");
Chris Lattnere147d062001-11-07 14:01:59 +0000650 return;
651 }
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000652
653 // if the LR received the correct color, NOTHING to do
654
655 if( RetValLR->hasColor() )
656 if( RetValLR->getColor() == CorrectCol )
657 recvCorrectColor = true;
658
659
660 // if we didn't receive the correct color for some reason,
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000661 // put copy instruction
662
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000663 if( !recvCorrectColor ) {
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000664
665 unsigned RegType = getRegType( RetValLR );
666
667 // the reg that LR must be colored with
668 unsigned UniRetReg = getUnifiedRegNum( RegClassID, CorrectCol);
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000669
670 if( RetValLR->hasColor() ) {
671
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000672 unsigned
673 UniRetLRReg=getUnifiedRegNum(RegClassID,RetValLR->getColor());
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000674
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000675 // the return value is coming in UniRetReg but has to go into
676 // the UniRetLRReg
677
678 AdMI = cpReg2RegMI( UniRetReg, UniRetLRReg, RegType );
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000679
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000680 } // if LR has color
681 else {
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000682
683 // if the LR did NOT receive a color, we have to move the return
684 // value coming in UniRetReg to the stack pos of spilled LR
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000685
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000686 AdMI = cpReg2MemMI(UniRetReg, getFramePointer(),
687 RetValLR->getSpillOffFromFP(), RegType );
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000688 }
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000689
690 CallAI->InstrnsAfter.push_back( AdMI );
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000691
692 } // the LR didn't receive the suggested color
693
694 } // if there a return value
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000695
696
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000697 //-------------------------------------------
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000698 // Now color all args of the call instruction
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000699 //-------------------------------------------
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000700
Chris Lattner7f74a562002-01-20 22:54:45 +0000701 std::vector<MachineInstr *> AddedInstrnsBefore;
Ruchira Sasankad0d294a2001-11-09 23:49:14 +0000702
Ruchira Sasanka24729a32001-10-21 16:43:41 +0000703 unsigned NumOfCallArgs = getCallInstNumArgs( CallMI );
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000704
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000705 bool VarArgCall = isVarArgCall( CallMI );
706
707 if(VarArgCall) cerr << "\nVar arg call found!!\n";
708
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000709 for(unsigned argNo=0, i=0; i < NumOfCallArgs; ++i, ++argNo ) {
710
711 const Value *CallArg = CallMI->getImplicitRef(i);
712
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000713 // get the LR of call operand (parameter)
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000714 LiveRange *const LR = LRI.getLiveRangeForValue(CallArg);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000715
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000716 unsigned RegType = getRegType( CallArg );
717 unsigned RegClassID = getRegClassIDOfValue( CallArg);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000718
719 // find whether this argument is coming in a register (if not, on stack)
720
721 bool isArgInReg = false;
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000722 unsigned UniArgReg = InvalidRegNum; // reg that LR must be colored with
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000723
724 if( (RegType== IntRegType && argNo < NumOfIntArgRegs)) {
725 isArgInReg = true;
726 UniArgReg = getUnifiedRegNum(RegClassID, SparcIntRegOrder::o0 + argNo );
727 }
728 else if(RegType == FPSingleRegType && argNo < NumOfFloatArgRegs) {
729 isArgInReg = true;
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000730
731 if( !VarArgCall )
732 UniArgReg = getUnifiedRegNum(RegClassID,
733 SparcFloatRegOrder::f0 + (argNo*2 + 1) );
734 else {
735 // a variable argument call - must pass float arg in %o's
736 if( argNo < NumOfIntArgRegs)
737 UniArgReg=getUnifiedRegNum(IntRegClassID,SparcIntRegOrder::o0+argNo);
738 else
739 isArgInReg = false;
740 }
741
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000742 }
743 else if(RegType == FPDoubleRegType && argNo < NumOfFloatArgRegs) {
744 isArgInReg = true;
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000745
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000746 if( !VarArgCall )
747 UniArgReg =getUnifiedRegNum(RegClassID,SparcFloatRegOrder::f0+argNo*2);
748 else {
749 // a variable argument call - must pass float arg in %o's
750 if( argNo < NumOfIntArgRegs)
751 UniArgReg=getUnifiedRegNum(IntRegClassID,SparcIntRegOrder::o0+argNo);
752 else
753 isArgInReg = false;
754 }
755 }
Chris Lattnerb0ddffa2001-09-14 03:47:57 +0000756
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000757 // not possible to have a null LR since all args (even consts)
758 // must be defined before
Chris Lattner30e8fb62002-02-05 01:43:49 +0000759 if (!LR) {
760 cerr << " ERROR: In call instr, no LR for arg: " << RAV(CallArg) << "\n";
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000761 assert(0 && "NO LR for call arg");
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000762 }
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000763
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000764
Chris Lattner5216cc52002-02-04 05:59:25 +0000765 if (LR->hasColor()) {
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000766 unsigned UniLRReg = getUnifiedRegNum( RegClassID, LR->getColor() );
767
768 // if LR received the correct color, nothing to do
769 if( UniLRReg == UniArgReg )
770 continue;
771
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000772 // We are here because though the LR is allocated a register, it
773 // was not allocated the suggested register. So, we have to copy %ix reg
774 // (or stack pos of arg) to the register it was colored with
775
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000776 // the LR is colored with UniLRReg but has to go into UniArgReg
777 // to pass it as an argument
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000778
Ruchira Sasanka20e105f2001-11-12 20:54:19 +0000779 if( isArgInReg ) {
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000780
781 if( VarArgCall && RegClassID == FloatRegClassID ) {
782
783
784 // for a variable argument call, the float reg must go in a %o reg.
785 // We have to move a float reg to an int reg via memory.
786 // The store instruction will be directly added to
787 // CallAI->InstrnsBefore since it does not need reordering
788 //
789 int TmpOff = PRA.mcInfo.pushTempValue(target,
790 getSpilledRegSize(RegType));
791
792 AdMI = cpReg2MemMI(UniLRReg, getFramePointer(), TmpOff, RegType );
793 CallAI->InstrnsBefore.push_back( AdMI );
794
795 AdMI = cpMem2RegMI(getFramePointer(), TmpOff, UniArgReg, IntRegType);
796 AddedInstrnsBefore.push_back( AdMI );
797 }
798
799 else {
800 AdMI = cpReg2RegMI(UniLRReg, UniArgReg, RegType );
801 AddedInstrnsBefore.push_back( AdMI );
802 }
803
Chris Lattner5216cc52002-02-04 05:59:25 +0000804 } else {
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000805 // Now, we have to pass the arg on stack. Since LR received a register
806 // we just have to move that register to the stack position where
807 // the argument must be passed
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000808
Vikram S. Adve7a1524f2001-11-08 04:56:41 +0000809 int argOffset = PRA.mcInfo.allocateOptionalArg(target, LR->getType());
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000810
Ruchira Sasanka80fc4342001-11-11 22:37:51 +0000811 AdMI = cpReg2MemMI(UniLRReg, getStackPointer(), argOffset, RegType );
Ruchira Sasanka20e105f2001-11-12 20:54:19 +0000812
813 // Now add the instruction. We can directly add to
814 // CallAI->InstrnsBefore since we are just saving a reg on stack
815 //
816 CallAI->InstrnsBefore.push_back( AdMI );
817
818 //cerr << "\nCaution: Passing a reg on stack";
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000819 }
820
Ruchira Sasanka20e105f2001-11-12 20:54:19 +0000821
Chris Lattner5216cc52002-02-04 05:59:25 +0000822 } else { // LR is not colored (i.e., spilled)
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000823
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000824 if( isArgInReg ) {
825
826 // Now the LR did NOT recieve a register but has a stack poistion.
827 // Since, the outgoing arg goes in a register we just have to insert
828 // a load instruction to load the LR to outgoing register
829
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000830 if( VarArgCall && RegClassID == FloatRegClassID )
831 AdMI = cpMem2RegMI(getFramePointer(), LR->getSpillOffFromFP(),
832 UniArgReg, IntRegType );
833 else
834 AdMI = cpMem2RegMI(getFramePointer(), LR->getSpillOffFromFP(),
835 UniArgReg, RegType );
Vikram S. Adve7a1524f2001-11-08 04:56:41 +0000836
Ruchira Sasanka24e29432001-11-12 20:31:47 +0000837 cerr << "\nCaution: Loading a spilled val to a reg as a call arg";
Ruchira Sasankad0d294a2001-11-09 23:49:14 +0000838 AddedInstrnsBefore.push_back( AdMI ); // Now add the instruction
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000839 }
Vikram S. Adve7a1524f2001-11-08 04:56:41 +0000840
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000841 else {
842 // Now, we have to pass the arg on stack. Since LR also did NOT
843 // receive a register we have to move an argument in memory to
844 // outgoing parameter on stack.
845
846 // Optoimize: Optimize when reverse pointers in MahineInstr are
847 // introduced.
848 // call PRA.getUnusedRegAtMI(....) to get an unused reg. Only if this
849 // fails, then use the following code. Currently, we cannot call the
850 // above method since we cannot find LVSetBefore without the BB
851
Ruchira Sasankac97ccc52001-11-15 20:25:07 +0000852 int TReg = PRA.getUniRegNotUsedByThisInst( LR->getRegClass(), CallMI );
Ruchira Sasankad0d294a2001-11-09 23:49:14 +0000853
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000854 int TmpOff = PRA.mcInfo.pushTempValue(target,
855 getSpilledRegSize(getRegType(LR)) );
856
Vikram S. Adve7a1524f2001-11-08 04:56:41 +0000857
858 int argOffset = PRA.mcInfo.allocateOptionalArg(target, LR->getType());
859
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000860 MachineInstr *Ad1, *Ad2, *Ad3, *Ad4;
Vikram S. Adve7a1524f2001-11-08 04:56:41 +0000861
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000862 // Sequence:
863 // (1) Save TReg on stack
864 // (2) Load LR value into TReg from stack pos of LR
865 // (3) Store Treg on outgoing Arg pos on stack
866 // (4) Load the old value of TReg from stack to TReg (restore it)
867
868 Ad1 = cpReg2MemMI(TReg, getFramePointer(), TmpOff, RegType );
869 Ad2 = cpMem2RegMI(getFramePointer(), LR->getSpillOffFromFP(),
870 TReg, RegType );
Ruchira Sasanka80fc4342001-11-11 22:37:51 +0000871 Ad3 = cpReg2MemMI(TReg, getStackPointer(), argOffset, RegType );
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000872 Ad4 = cpMem2RegMI(getFramePointer(), TmpOff, TReg, RegType );
Ruchira Sasankad0d294a2001-11-09 23:49:14 +0000873
874 // We directly add to CallAI->InstrnsBefore instead of adding to
875 // AddedInstrnsBefore since these instructions must not be
876 // reordered.
Vikram S. Adve7a1524f2001-11-08 04:56:41 +0000877
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000878 CallAI->InstrnsBefore.push_back( Ad1 );
879 CallAI->InstrnsBefore.push_back( Ad2 );
880 CallAI->InstrnsBefore.push_back( Ad3 );
881 CallAI->InstrnsBefore.push_back( Ad4 );
Ruchira Sasankad0d294a2001-11-09 23:49:14 +0000882
Ruchira Sasanka24e29432001-11-12 20:31:47 +0000883 cerr << "\nCaution: Call arg moved from stack2stack for: " << *CallMI ;
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000884 }
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000885 }
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000886 } // for each parameter in call instruction
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000887
Ruchira Sasankad0d294a2001-11-09 23:49:14 +0000888
889 // if we added any instruction before the call instruction, verify
890 // that they are in the proper order and if not, reorder them
891
Chris Lattner5216cc52002-02-04 05:59:25 +0000892 if (!AddedInstrnsBefore.empty()) {
Ruchira Sasankad0d294a2001-11-09 23:49:14 +0000893
Chris Lattner5216cc52002-02-04 05:59:25 +0000894 if (DEBUG_RA) {
Ruchira Sasankad0d294a2001-11-09 23:49:14 +0000895 cerr << "\nCalling reorder with instrns: \n";
896 for(unsigned i=0; i < AddedInstrnsBefore.size(); i++)
897 cerr << *(AddedInstrnsBefore[i]);
898 }
899
Chris Lattner7f74a562002-01-20 22:54:45 +0000900 std::vector<MachineInstr *> TmpVec;
Ruchira Sasanka0c085982001-11-10 21:20:43 +0000901 OrderAddedInstrns(AddedInstrnsBefore, TmpVec, PRA);
Ruchira Sasankad0d294a2001-11-09 23:49:14 +0000902
Chris Lattner5216cc52002-02-04 05:59:25 +0000903 if (DEBUG_RA) {
Ruchira Sasankad0d294a2001-11-09 23:49:14 +0000904 cerr << "\nAfter reordering instrns: \n";
Chris Lattner5216cc52002-02-04 05:59:25 +0000905 for(unsigned i = 0; i < TmpVec.size(); i++)
906 cerr << *TmpVec[i];
Ruchira Sasankad0d294a2001-11-09 23:49:14 +0000907 }
908
909 // copy the results back from TmpVec to InstrnsBefore
910 for(unsigned i=0; i < TmpVec.size(); i++)
911 CallAI->InstrnsBefore.push_back( TmpVec[i] );
912 }
913
914
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +0000915 // now insert caller saving code for this call instruction
916 //
917 insertCallerSavingCode(CallMI, BB, PRA);
918
Vikram S. Adve7a1524f2001-11-08 04:56:41 +0000919 // Reset optional args area again to be safe
Vikram S. Adve7a1524f2001-11-08 04:56:41 +0000920 PRA.mcInfo.resetOptionalArgs(target);
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000921}
922
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000923//---------------------------------------------------------------------------
924// This method is called for an LLVM return instruction to identify which
925// values will be returned from this method and to suggest colors.
926//---------------------------------------------------------------------------
Chris Lattner5216cc52002-02-04 05:59:25 +0000927void UltraSparcRegInfo::suggestReg4RetValue(const MachineInstr *RetMI,
928 LiveRangeInfo &LRI) const {
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000929
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000930 assert( (UltraSparcInfo->getInstrInfo()).isReturn( RetMI->getOpCode() ) );
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000931
Ruchira Sasanka6a7f0202001-10-23 21:40:39 +0000932 suggestReg4RetAddr(RetMI, LRI);
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000933
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000934 // if there is an implicit ref, that has to be the ret value
935 if( RetMI->getNumImplicitRefs() > 0 ) {
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000936
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000937 // The first implicit operand is the return value of a return instr
938 const Value *RetVal = RetMI->getImplicitRef(0);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000939
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000940 LiveRange *const LR = LRI.getLiveRangeForValue( RetVal );
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000941
Chris Lattner30e8fb62002-02-05 01:43:49 +0000942 if (!LR) {
943 cerr << "\nNo LR for:" << RAV(RetVal) << "\n";
944 assert(0 && "No LR for return value of non-void method");
945 }
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000946
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000947 unsigned RegClassID = (LR->getRegClass())->getID();
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000948
Chris Lattner5216cc52002-02-04 05:59:25 +0000949 if (RegClassID == IntRegClassID)
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000950 LR->setSuggestedColor(SparcIntRegOrder::i0);
Chris Lattner5216cc52002-02-04 05:59:25 +0000951 else if (RegClassID == FloatRegClassID)
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000952 LR->setSuggestedColor(SparcFloatRegOrder::f0);
Ruchira Sasankadfc6c882001-09-18 22:52:44 +0000953 }
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000954}
955
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000956
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000957
958//---------------------------------------------------------------------------
959// Colors the return value of a method to %i0 or %f0, if possible. If it is
960// not possilbe to directly color the LR, insert a copy instruction to move
961// the LR to %i0 or %f0. When the LR is spilled, instead of the copy, we
962// have to put a load instruction.
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000963//---------------------------------------------------------------------------
Chris Lattner5216cc52002-02-04 05:59:25 +0000964void UltraSparcRegInfo::colorRetValue(const MachineInstr *RetMI,
965 LiveRangeInfo &LRI,
966 AddedInstrns *RetAI) const {
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000967
Chris Lattner5216cc52002-02-04 05:59:25 +0000968 assert((UltraSparcInfo->getInstrInfo()).isReturn( RetMI->getOpCode()));
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000969
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000970 // if there is an implicit ref, that has to be the ret value
Chris Lattner5216cc52002-02-04 05:59:25 +0000971 if(RetMI->getNumImplicitRefs() > 0) {
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000972
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000973 // The first implicit operand is the return value of a return instr
974 const Value *RetVal = RetMI->getImplicitRef(0);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000975
Chris Lattner5216cc52002-02-04 05:59:25 +0000976 LiveRange *LR = LRI.getLiveRangeForValue(RetVal);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000977
Chris Lattner30e8fb62002-02-05 01:43:49 +0000978 if (!LR) {
979 cerr << "\nNo LR for:" << RAV(RetVal) << "\n";
980 // assert( LR && "No LR for return value of non-void method");
981 return;
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +0000982 }
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +0000983
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000984 unsigned RegClassID = getRegClassIDOfValue(RetVal);
985 unsigned RegType = getRegType( RetVal );
Ruchira Sasanka6a7f0202001-10-23 21:40:39 +0000986
Ruchira Sasanka6a7f0202001-10-23 21:40:39 +0000987 unsigned CorrectCol;
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000988 if(RegClassID == IntRegClassID)
Ruchira Sasanka6a7f0202001-10-23 21:40:39 +0000989 CorrectCol = SparcIntRegOrder::i0;
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000990 else if(RegClassID == FloatRegClassID)
Ruchira Sasanka6a7f0202001-10-23 21:40:39 +0000991 CorrectCol = SparcFloatRegOrder::f0;
Chris Lattnere147d062001-11-07 14:01:59 +0000992 else {
Chris Lattner5216cc52002-02-04 05:59:25 +0000993 assert (0 && "Unknown RegClass");
Chris Lattnere147d062001-11-07 14:01:59 +0000994 return;
995 }
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000996
Ruchira Sasanka36bcd792001-10-24 15:56:58 +0000997 // if the LR received the correct color, NOTHING to do
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +0000998
Chris Lattner5216cc52002-02-04 05:59:25 +0000999 if (LR->hasColor() && LR->getColor() == CorrectCol)
1000 return;
Ruchira Sasanka6a7f0202001-10-23 21:40:39 +00001001
Chris Lattner5216cc52002-02-04 05:59:25 +00001002 unsigned UniRetReg = getUnifiedRegNum(RegClassID, CorrectCol);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001003
Chris Lattner5216cc52002-02-04 05:59:25 +00001004 if (LR->hasColor()) {
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001005
Ruchira Sasanka6a7f0202001-10-23 21:40:39 +00001006 // We are here because the LR was allocted a regiter
1007 // It may be the suggested register or not
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001008
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +00001009 // copy the LR of retun value to i0 or f0
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001010
Ruchira Sasanka086bf0f2001-10-15 16:25:28 +00001011 unsigned UniLRReg =getUnifiedRegNum( RegClassID, LR->getColor());
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001012
Ruchira Sasanka36bcd792001-10-24 15:56:58 +00001013 // the LR received UniLRReg but must be colored with UniRetReg
1014 // to pass as the return value
Chris Lattner7f74a562002-01-20 22:54:45 +00001015 RetAI->InstrnsBefore.push_back(cpReg2RegMI(UniLRReg, UniRetReg, RegType));
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001016 }
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001017 else { // if the LR is spilled
Chris Lattner7f74a562002-01-20 22:54:45 +00001018 MachineInstr *AdMI = cpMem2RegMI(getFramePointer(),
1019 LR->getSpillOffFromFP(),
1020 UniRetReg, RegType);
1021 RetAI->InstrnsBefore.push_back(AdMI);
1022 cerr << "\nCopied the return value from stack\n";
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001023 }
1024
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001025 } // if there is a return value
1026
1027}
1028
1029
1030//---------------------------------------------------------------------------
1031// Copy from a register to register. Register number must be the unified
1032// register number
1033//---------------------------------------------------------------------------
1034
Chris Lattner5216cc52002-02-04 05:59:25 +00001035MachineInstr * UltraSparcRegInfo::cpReg2RegMI(unsigned SrcReg, unsigned DestReg,
1036 int RegType) const {
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001037
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001038 assert( ((int)SrcReg != InvalidRegNum) && ((int)DestReg != InvalidRegNum) &&
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001039 "Invalid Register");
1040
1041 MachineInstr * MI = NULL;
1042
1043 switch( RegType ) {
1044
1045 case IntRegType:
Ruchira Sasanka5f629312001-10-18 22:38:52 +00001046 case IntCCRegType:
1047 case FloatCCRegType:
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001048 MI = new MachineInstr(ADD, 3);
Vikram S. Advedb1435f2002-03-18 03:12:16 +00001049 MI->SetMachineOperandReg(0, SrcReg, false);
1050 MI->SetMachineOperandReg(1, this->getZeroRegNum(), false);
1051 MI->SetMachineOperandReg(2, DestReg, true);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001052 break;
1053
1054 case FPSingleRegType:
1055 MI = new MachineInstr(FMOVS, 2);
Vikram S. Advedb1435f2002-03-18 03:12:16 +00001056 MI->SetMachineOperandReg(0, SrcReg, false);
1057 MI->SetMachineOperandReg(1, DestReg, true);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001058 break;
1059
1060 case FPDoubleRegType:
1061 MI = new MachineInstr(FMOVD, 2);
Vikram S. Advedb1435f2002-03-18 03:12:16 +00001062 MI->SetMachineOperandReg(0, SrcReg, false);
1063 MI->SetMachineOperandReg(1, DestReg, true);
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001064 break;
1065
1066 default:
1067 assert(0 && "Unknow RegType");
Ruchira Sasankadfc6c882001-09-18 22:52:44 +00001068 }
1069
1070 return MI;
Ruchira Sasankadfc6c882001-09-18 22:52:44 +00001071}
Chris Lattnerb0ddffa2001-09-14 03:47:57 +00001072
1073
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001074//---------------------------------------------------------------------------
Ruchira Sasanka0863c162001-10-24 22:05:34 +00001075// Copy from a register to memory (i.e., Store). Register number must
1076// be the unified register number
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001077//---------------------------------------------------------------------------
1078
1079
Chris Lattner5216cc52002-02-04 05:59:25 +00001080MachineInstr * UltraSparcRegInfo::cpReg2MemMI(unsigned SrcReg,
1081 unsigned DestPtrReg,
1082 int Offset, int RegType) const {
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001083 MachineInstr * MI = NULL;
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001084 switch( RegType ) {
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001085 case IntRegType:
Ruchira Sasanka5f629312001-10-18 22:38:52 +00001086 case FloatCCRegType:
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001087 MI = new MachineInstr(STX, 3);
Vikram S. Advedb1435f2002-03-18 03:12:16 +00001088 MI->SetMachineOperandReg(0, SrcReg, false);
1089 MI->SetMachineOperandReg(1, DestPtrReg, false);
1090 MI->SetMachineOperandConst(2, MachineOperand:: MO_SignExtendedImmed,
1091 (int64_t) Offset);
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001092 break;
1093
1094 case FPSingleRegType:
1095 MI = new MachineInstr(ST, 3);
Vikram S. Advedb1435f2002-03-18 03:12:16 +00001096 MI->SetMachineOperandReg(0, SrcReg, false);
1097 MI->SetMachineOperandReg(1, DestPtrReg, false);
1098 MI->SetMachineOperandConst(2, MachineOperand:: MO_SignExtendedImmed,
1099 (int64_t) Offset);
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001100 break;
1101
1102 case FPDoubleRegType:
1103 MI = new MachineInstr(STD, 3);
Vikram S. Advedb1435f2002-03-18 03:12:16 +00001104 MI->SetMachineOperandReg(0, SrcReg, false);
1105 MI->SetMachineOperandReg(1, DestPtrReg, false);
1106 MI->SetMachineOperandConst(2, MachineOperand:: MO_SignExtendedImmed,
1107 (int64_t) Offset);
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001108 break;
1109
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001110 case IntCCRegType:
1111 assert( 0 && "Cannot directly store %ccr to memory");
1112
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001113 default:
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001114 assert(0 && "Unknow RegType in cpReg2MemMI");
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001115 }
1116
1117 return MI;
1118}
1119
1120
1121//---------------------------------------------------------------------------
Ruchira Sasanka0863c162001-10-24 22:05:34 +00001122// Copy from memory to a reg (i.e., Load) Register number must be the unified
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001123// register number
1124//---------------------------------------------------------------------------
1125
1126
Chris Lattner5216cc52002-02-04 05:59:25 +00001127MachineInstr * UltraSparcRegInfo::cpMem2RegMI(unsigned SrcPtrReg,
1128 int Offset,
1129 unsigned DestReg,
1130 int RegType) const {
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001131 MachineInstr * MI = NULL;
Chris Lattner5216cc52002-02-04 05:59:25 +00001132 switch (RegType) {
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001133 case IntRegType:
Ruchira Sasanka5f629312001-10-18 22:38:52 +00001134 case FloatCCRegType:
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001135 MI = new MachineInstr(LDX, 3);
Vikram S. Advedb1435f2002-03-18 03:12:16 +00001136 MI->SetMachineOperandReg(0, SrcPtrReg, false);
1137 MI->SetMachineOperandConst(1, MachineOperand:: MO_SignExtendedImmed,
1138 (int64_t) Offset);
1139 MI->SetMachineOperandReg(2, DestReg, true);
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001140 break;
1141
1142 case FPSingleRegType:
1143 MI = new MachineInstr(LD, 3);
Vikram S. Advedb1435f2002-03-18 03:12:16 +00001144 MI->SetMachineOperandReg(0, SrcPtrReg, false);
1145 MI->SetMachineOperandConst(1, MachineOperand:: MO_SignExtendedImmed,
1146 (int64_t) Offset);
1147 MI->SetMachineOperandReg(2, DestReg, true);
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001148
1149 break;
1150
1151 case FPDoubleRegType:
1152 MI = new MachineInstr(LDD, 3);
Vikram S. Advedb1435f2002-03-18 03:12:16 +00001153 MI->SetMachineOperandReg(0, SrcPtrReg, false);
1154 MI->SetMachineOperandConst(1, MachineOperand:: MO_SignExtendedImmed,
1155 (int64_t) Offset);
1156 MI->SetMachineOperandReg(2, DestReg, true);
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001157 break;
1158
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001159 case IntCCRegType:
1160 assert( 0 && "Cannot directly load into %ccr from memory");
1161
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001162 default:
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001163 assert(0 && "Unknown RegType in cpMem2RegMI");
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001164 }
1165
1166 return MI;
1167}
1168
1169
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001170
1171
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001172
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001173//---------------------------------------------------------------------------
1174// Generate a copy instruction to copy a value to another. Temporarily
1175// used by PhiElimination code.
1176//---------------------------------------------------------------------------
1177
1178
Chris Lattner5216cc52002-02-04 05:59:25 +00001179MachineInstr *UltraSparcRegInfo::cpValue2Value(Value *Src, Value *Dest) const {
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001180 int RegType = getRegType( Src );
1181
1182 assert( (RegType==getRegType(Src)) && "Src & Dest are diff types");
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001183
Ruchira Sasankab7a39722001-11-03 17:13:27 +00001184 MachineInstr * MI = NULL;
1185
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001186 switch( RegType ) {
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001187 case IntRegType:
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001188 MI = new MachineInstr(ADD, 3);
Vikram S. Advedb1435f2002-03-18 03:12:16 +00001189 MI->SetMachineOperandVal(0, MachineOperand:: MO_VirtualRegister, Src, false);
1190 MI->SetMachineOperandReg(1, this->getZeroRegNum(), false);
1191 MI->SetMachineOperandVal(2, MachineOperand:: MO_VirtualRegister, Dest, true);
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001192 break;
1193
1194 case FPSingleRegType:
1195 MI = new MachineInstr(FMOVS, 2);
Vikram S. Advedb1435f2002-03-18 03:12:16 +00001196 MI->SetMachineOperandVal(0, MachineOperand:: MO_VirtualRegister, Src, false);
1197 MI->SetMachineOperandVal(1, MachineOperand:: MO_VirtualRegister, Dest, true);
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001198 break;
1199
1200
1201 case FPDoubleRegType:
1202 MI = new MachineInstr(FMOVD, 2);
Vikram S. Advedb1435f2002-03-18 03:12:16 +00001203 MI->SetMachineOperandVal(0, MachineOperand:: MO_VirtualRegister, Src, false);
1204 MI->SetMachineOperandVal(1, MachineOperand:: MO_VirtualRegister, Dest, true);
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001205 break;
1206
1207 default:
1208 assert(0 && "Unknow RegType in CpValu2Value");
1209 }
Ruchira Sasankab7a39722001-11-03 17:13:27 +00001210
1211 return MI;
Ruchira Sasankab7a39722001-11-03 17:13:27 +00001212}
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001213
1214
1215
Ruchira Sasankafcdc2ff2001-11-12 14:45:33 +00001216
1217
1218
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001219//----------------------------------------------------------------------------
1220// This method inserts caller saving/restoring instructons before/after
Ruchira Sasankaf4c2ddd2002-01-07 21:03:42 +00001221// a call machine instruction. The caller saving/restoring instructions are
1222// inserted like:
1223//
1224// ** caller saving instructions
1225// other instructions inserted for the call by ColorCallArg
1226// CALL instruction
1227// other instructions inserted for the call ColorCallArg
1228// ** caller restoring instructions
1229//
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001230//----------------------------------------------------------------------------
Ruchira Sasanka5b8971f2001-10-16 01:23:19 +00001231
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001232
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001233void UltraSparcRegInfo::insertCallerSavingCode(const MachineInstr *MInst,
1234 const BasicBlock *BB,
1235 PhyRegAlloc &PRA) const {
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001236
Ruchira Sasankaf4c2ddd2002-01-07 21:03:42 +00001237 // has set to record which registers were saved/restored
1238 //
Chris Lattner7f74a562002-01-20 22:54:45 +00001239 std::hash_set<unsigned> PushedRegSet;
Ruchira Sasankaf4c2ddd2002-01-07 21:03:42 +00001240
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001241 // Now find the LR of the return value of the call
1242 // The last *implicit operand* is the return value of a call
1243 // Insert it to to he PushedRegSet since we must not save that register
1244 // and restore it after the call.
1245 // We do this because, we look at the LV set *after* the instruction
1246 // to determine, which LRs must be saved across calls. The return value
1247 // of the call is live in this set - but we must not save/restore it.
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001248
1249
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001250 const Value *RetVal = getCallInstRetVal( MInst );
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001251
Chris Lattner5216cc52002-02-04 05:59:25 +00001252 if (RetVal) {
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001253 LiveRange *RetValLR = PRA.LRI.getLiveRangeForValue( RetVal );
Chris Lattner5216cc52002-02-04 05:59:25 +00001254 assert(RetValLR && "No LR for RetValue of call");
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001255
Chris Lattner5216cc52002-02-04 05:59:25 +00001256 if (RetValLR->hasColor())
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001257 PushedRegSet.insert(
1258 getUnifiedRegNum((RetValLR->getRegClass())->getID(),
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001259 RetValLR->getColor() ) );
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001260 }
1261
1262
Chris Lattner7e5ee422002-02-05 04:20:12 +00001263 const ValueSet &LVSetAft = PRA.LVI->getLiveVarSetAfterMInst(MInst, BB);
1264 ValueSet::const_iterator LIt = LVSetAft.begin();
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001265
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001266 // for each live var in live variable set after machine inst
Chris Lattner7e5ee422002-02-05 04:20:12 +00001267 for( ; LIt != LVSetAft.end(); ++LIt) {
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001268
1269 // get the live range corresponding to live var
1270 LiveRange *const LR = PRA.LRI.getLiveRangeForValue(*LIt );
1271
1272 // LR can be null if it is a const since a const
1273 // doesn't have a dominating def - see Assumptions above
1274 if( LR ) {
1275
1276 if( LR->hasColor() ) {
1277
1278 unsigned RCID = (LR->getRegClass())->getID();
1279 unsigned Color = LR->getColor();
1280
1281 if ( isRegVolatile(RCID, Color) ) {
1282
1283 // if the value is in both LV sets (i.e., live before and after
1284 // the call machine instruction)
1285
1286 unsigned Reg = getUnifiedRegNum(RCID, Color);
1287
1288 if( PushedRegSet.find(Reg) == PushedRegSet.end() ) {
1289
1290 // if we haven't already pushed that register
1291
1292 unsigned RegType = getRegType( LR );
1293
1294 // Now get two instructions - to push on stack and pop from stack
1295 // and add them to InstrnsBefore and InstrnsAfter of the
1296 // call instruction
1297
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +00001298
1299 int StackOff = PRA.mcInfo.pushTempValue(target,
1300 getSpilledRegSize(RegType));
1301
Vikram S. Adve7a1524f2001-11-08 04:56:41 +00001302
Vikram S. Advedb1435f2002-03-18 03:12:16 +00001303 MachineInstr *AdIBefCC=NULL, *AdIAftCC=NULL, *AdICpCC;
1304 MachineInstr *AdIBef=NULL, *AdIAft=NULL;
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001305
1306 //---- Insert code for pushing the reg on stack ----------
1307
1308 if( RegType == IntCCRegType ) {
1309
1310 // Handle IntCCRegType specially since we cannot directly
1311 // push %ccr on to the stack
1312
Chris Lattner7e5ee422002-02-05 04:20:12 +00001313 const ValueSet &LVSetBef =
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001314 PRA.LVI->getLiveVarSetBeforeMInst(MInst, BB);
1315
1316 // get a free INTEGER register
1317 int FreeIntReg =
Vikram S. Advedb1435f2002-03-18 03:12:16 +00001318 PRA.getUsableUniRegAtMI(PRA.getRegClassByID(IntRegClassID) /*LR->getRegClass()*/,
1319 IntRegType, MInst, &LVSetBef, AdIBefCC, AdIAftCC);
1320
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001321 // insert the instructions in reverse order since we are
1322 // adding them to the front of InstrnsBefore
1323
1324 if(AdIAftCC)
Chris Lattner7e5ee422002-02-05 04:20:12 +00001325 PRA.AddedInstrMap[MInst]->InstrnsBefore.push_front(AdIAftCC);
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001326
1327 AdICpCC = cpCCR2IntMI(FreeIntReg);
Chris Lattner7e5ee422002-02-05 04:20:12 +00001328 PRA.AddedInstrMap[MInst]->InstrnsBefore.push_front(AdICpCC);
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001329
1330 if(AdIBefCC)
Chris Lattner7e5ee422002-02-05 04:20:12 +00001331 PRA.AddedInstrMap[MInst]->InstrnsBefore.push_front(AdIBefCC);
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001332
Ruchira Sasanka1812fc42001-11-10 00:26:55 +00001333 if(DEBUG_RA) {
1334 cerr << "\n!! Inserted caller saving (push) inst for %ccr:";
1335 if(AdIBefCC) cerr << "\t" << *(AdIBefCC);
1336 cerr << "\t" << *AdICpCC;
1337 if(AdIAftCC) cerr << "\t" << *(AdIAftCC);
1338 }
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001339
1340 } else {
1341 // for any other register type, just add the push inst
Ruchira Sasanka2d5c48f2001-11-11 21:49:37 +00001342 AdIBef = cpReg2MemMI(Reg, getFramePointer(), StackOff, RegType );
Chris Lattner7e5ee422002-02-05 04:20:12 +00001343 PRA.AddedInstrMap[MInst]->InstrnsBefore.push_front(AdIBef);
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001344 }
1345
1346
1347 //---- Insert code for popping the reg from the stack ----------
1348
Chris Lattner7e5ee422002-02-05 04:20:12 +00001349 if (RegType == IntCCRegType) {
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001350
1351 // Handle IntCCRegType specially since we cannot directly
1352 // pop %ccr on from the stack
1353
1354 // get a free INT register
1355 int FreeIntReg =
Vikram S. Advedb1435f2002-03-18 03:12:16 +00001356 PRA.getUsableUniRegAtMI(PRA.getRegClassByID(IntRegClassID) /* LR->getRegClass()*/,
1357 IntRegType, MInst, &LVSetAft, AdIBefCC, AdIAftCC);
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001358
1359 if(AdIBefCC)
Chris Lattner7e5ee422002-02-05 04:20:12 +00001360 PRA.AddedInstrMap[MInst]->InstrnsAfter.push_back(AdIBefCC);
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001361
1362 AdICpCC = cpInt2CCRMI(FreeIntReg);
Chris Lattner7e5ee422002-02-05 04:20:12 +00001363 PRA.AddedInstrMap[MInst]->InstrnsAfter.push_back(AdICpCC);
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001364
1365 if(AdIAftCC)
Chris Lattner7e5ee422002-02-05 04:20:12 +00001366 PRA.AddedInstrMap[MInst]->InstrnsAfter.push_back(AdIAftCC);
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001367
Ruchira Sasanka1812fc42001-11-10 00:26:55 +00001368 if(DEBUG_RA) {
1369
1370 cerr << "\n!! Inserted caller saving (pop) inst for %ccr:";
1371 if(AdIBefCC) cerr << "\t" << *(AdIBefCC);
1372 cerr << "\t" << *AdICpCC;
1373 if(AdIAftCC) cerr << "\t" << *(AdIAftCC);
1374 }
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001375
1376 } else {
1377 // for any other register type, just add the pop inst
Ruchira Sasanka2d5c48f2001-11-11 21:49:37 +00001378 AdIAft = cpMem2RegMI(getFramePointer(), StackOff, Reg, RegType );
Chris Lattner7e5ee422002-02-05 04:20:12 +00001379 PRA.AddedInstrMap[MInst]->InstrnsAfter.push_back(AdIAft);
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001380 }
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001381
Chris Lattner7e5ee422002-02-05 04:20:12 +00001382 PushedRegSet.insert(Reg);
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001383
Ruchira Sasanka1812fc42001-11-10 00:26:55 +00001384 if(DEBUG_RA) {
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001385 cerr << "\nFor call inst:" << *MInst;
Ruchira Sasanka1812fc42001-11-10 00:26:55 +00001386 cerr << " -inserted caller saving instrs:\n\t ";
Vikram S. Advedb1435f2002-03-18 03:12:16 +00001387 if( RegType == IntCCRegType ) {
1388 if(AdIBefCC) cerr << *AdIBefCC << "\t";
1389 if(AdIAftCC) cerr << *AdIAftCC;
1390 }
1391 else {
1392 if(AdIBef) cerr << *AdIBef << "\t";
1393 if(AdIAft) cerr << *AdIAft;
1394 }
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001395 }
1396 } // if not already pushed
1397
1398 } // if LR has a volatile color
1399
1400 } // if LR has color
1401
1402 } // if there is a LR for Var
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001403
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001404 } // for each value in the LV set after instruction
1405
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001406}
1407
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001408//---------------------------------------------------------------------------
1409// Copies %ccr into an integer register. IntReg is the UNIFIED register
1410// number.
1411//---------------------------------------------------------------------------
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001412
Chris Lattner5216cc52002-02-04 05:59:25 +00001413MachineInstr * UltraSparcRegInfo::cpCCR2IntMI(unsigned IntReg) const {
1414 MachineInstr * MI = new MachineInstr(RDCCR, 2);
Vikram S. Advedb1435f2002-03-18 03:12:16 +00001415 MI->SetMachineOperandReg(0, this->getUnifiedRegNum(UltraSparcRegInfo::IntCCRegClassID,
1416 SparcIntCCRegOrder::ccr),
1417 false, true);
1418 MI->SetMachineOperandReg(1, IntReg, true);
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001419 return MI;
1420}
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001421
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001422//---------------------------------------------------------------------------
1423// Copies an integer register into %ccr. IntReg is the UNIFIED register
1424// number.
1425//---------------------------------------------------------------------------
1426
Chris Lattner5216cc52002-02-04 05:59:25 +00001427MachineInstr *UltraSparcRegInfo::cpInt2CCRMI(unsigned IntReg) const {
1428 MachineInstr *MI = new MachineInstr(WRCCR, 3);
Vikram S. Advedb1435f2002-03-18 03:12:16 +00001429 MI->SetMachineOperandReg(0, IntReg, false);
1430 MI->SetMachineOperandReg(1, this->getZeroRegNum(), false);
1431 MI->SetMachineOperandReg(2, this->getUnifiedRegNum(UltraSparcRegInfo::IntCCRegClassID, SparcIntCCRegOrder::ccr),
1432 true, true);
Ruchira Sasanka9d8950d2001-11-03 19:59:59 +00001433 return MI;
1434}
Ruchira Sasanka5867c7a2001-09-30 23:16:47 +00001435
1436
Ruchira Sasanka9c38dbc2001-10-28 18:15:12 +00001437
1438
Ruchira Sasankadfc6c882001-09-18 22:52:44 +00001439//---------------------------------------------------------------------------
1440// Print the register assigned to a LR
1441//---------------------------------------------------------------------------
1442
Chris Lattner5216cc52002-02-04 05:59:25 +00001443void UltraSparcRegInfo::printReg(const LiveRange *LR) {
Ruchira Sasankadfc6c882001-09-18 22:52:44 +00001444 unsigned RegClassID = (LR->getRegClass())->getID();
Chris Lattnerf3f1e452001-10-15 18:15:27 +00001445 cerr << " *Node " << (LR->getUserIGNode())->getIndex();
Ruchira Sasankadfc6c882001-09-18 22:52:44 +00001446
Chris Lattner5216cc52002-02-04 05:59:25 +00001447 if (!LR->hasColor()) {
Chris Lattner7f74a562002-01-20 22:54:45 +00001448 cerr << " - could not find a color\n";
Ruchira Sasankadfc6c882001-09-18 22:52:44 +00001449 return;
1450 }
1451
1452 // if a color is found
1453
Chris Lattnerf3f1e452001-10-15 18:15:27 +00001454 cerr << " colored with color "<< LR->getColor();
Ruchira Sasankadfc6c882001-09-18 22:52:44 +00001455
Chris Lattner5216cc52002-02-04 05:59:25 +00001456 if (RegClassID == IntRegClassID) {
Chris Lattner7f74a562002-01-20 22:54:45 +00001457 cerr<< " [" << SparcIntRegOrder::getRegName(LR->getColor()) << "]\n";
Ruchira Sasankadfc6c882001-09-18 22:52:44 +00001458
Chris Lattner5216cc52002-02-04 05:59:25 +00001459 } else if (RegClassID == FloatRegClassID) {
Chris Lattnerf3f1e452001-10-15 18:15:27 +00001460 cerr << "[" << SparcFloatRegOrder::getRegName(LR->getColor());
Chris Lattnerd30f9892002-02-05 03:52:29 +00001461 if( LR->getType() == Type::DoubleTy)
Chris Lattnerf3f1e452001-10-15 18:15:27 +00001462 cerr << "+" << SparcFloatRegOrder::getRegName(LR->getColor()+1);
Chris Lattner7f74a562002-01-20 22:54:45 +00001463 cerr << "]\n";
Ruchira Sasankadfc6c882001-09-18 22:52:44 +00001464 }
Ruchira Sasankadfc6c882001-09-18 22:52:44 +00001465}
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001466
1467//---------------------------------------------------------------------------
1468// This method examines instructions inserted by RegAlloc code before a
1469// machine instruction to detect invalid orders that destroy values before
1470// they are used. If it detects such conditions, it reorders the instructions.
1471//
1472// The unordered instructions come in the UnordVec. These instructions are
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001473// instructions inserted by RegAlloc. All such instruction MUST have
1474// their USES BEFORE THE DEFS after reordering.
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001475
1476// The UnordVec & OrdVec must be DISTINCT. The OrdVec must be empty when
1477// this method is called.
1478
1479// This method uses two vectors for efficiency in accessing
1480
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001481// Since instructions are inserted in RegAlloc, this assumes that the
1482// first operand is the source reg and the last operand is the dest reg.
1483
1484// All the uses are before THE def to a register
1485
1486
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001487//---------------------------------------------------------------------------
Chris Lattner7f74a562002-01-20 22:54:45 +00001488void UltraSparcRegInfo::OrderAddedInstrns(std::vector<MachineInstr *> &UnordVec,
1489 std::vector<MachineInstr *> &OrdVec,
1490 PhyRegAlloc &PRA) const{
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001491
1492 /*
1493 Problem: We can have instructions inserted by RegAlloc like
1494 1. add %ox %g0 %oy
1495 2. add %oy %g0 %oz, where z!=x or z==x
1496
1497 This is wrong since %oy used by 2 is overwritten by 1
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001498
1499 Solution:
1500 We re-order the instructions so that the uses are before the defs
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001501
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001502 Algorithm:
1503
1504 do
1505 for each instruction 'DefInst' in the UnOrdVec
1506 for each instruction 'UseInst' that follows the DefInst
1507 if the reg defined by DefInst is used by UseInst
1508 mark DefInst as not movable in this iteration
1509 If DefInst is not marked as not-movable, move DefInst to OrdVec
1510 while all instructions in DefInst are moved to OrdVec
1511
1512 For moving, we call the move2OrdVec(). It checks whether there is a def
1513 in it for the uses in the instruction to be added to OrdVec. If there
1514 are no preceding defs, it just appends the instruction. If there is a
1515 preceding def, it puts two instructions to save the reg on stack before
1516 the load and puts a restore at use.
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001517
1518 */
1519
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001520 bool CouldMoveAll;
1521 bool DebugPrint = false;
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001522
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001523 do {
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001524 CouldMoveAll = true;
Chris Lattner7f74a562002-01-20 22:54:45 +00001525 std::vector<MachineInstr *>::iterator DefIt = UnordVec.begin();
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001526
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001527 for( ; DefIt != UnordVec.end(); ++DefIt ) {
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001528
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001529 // for each instruction in the UnordVec do ...
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001530
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001531 MachineInstr *DefInst = *DefIt;
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001532
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001533 if( DefInst == NULL) continue;
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001534
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001535 //cerr << "\nInst in UnordVec = " << *DefInst;
1536
1537 // last operand is the def (unless for a store which has no def reg)
1538 MachineOperand& DefOp = DefInst->getOperand(DefInst->getNumOperands()-1);
1539
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001540 if( DefOp.opIsDef() &&
1541 DefOp.getOperandType() == MachineOperand::MO_MachineRegister) {
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001542
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001543 // If the operand in DefInst is a def ...
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001544
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001545 bool DefEqUse = false;
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001546
Chris Lattner7f74a562002-01-20 22:54:45 +00001547 std::vector<MachineInstr *>::iterator UseIt = DefIt;
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001548 UseIt++;
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001549
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001550 for( ; UseIt != UnordVec.end(); ++UseIt ) {
1551
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001552 MachineInstr *UseInst = *UseIt;
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001553 if( UseInst == NULL) continue;
1554
1555 // for each inst (UseInst) that is below the DefInst do ...
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001556 MachineOperand& UseOp = UseInst->getOperand(0);
1557
1558 if( ! UseOp.opIsDef() &&
1559 UseOp.getOperandType() == MachineOperand::MO_MachineRegister) {
1560
1561 // if use is a register ...
1562
1563 if( DefOp.getMachineRegNum() == UseOp.getMachineRegNum() ) {
1564
1565 // if Def and this use are the same, it means that this use
1566 // is destroyed by a def before it is used
1567
1568 // cerr << "\nCouldn't move " << *DefInst;
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001569
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001570 DefEqUse = true;
1571 CouldMoveAll = false;
1572 DebugPrint = true;
1573 break;
1574 } // if two registers are equal
1575
1576 } // if use is a register
1577
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001578 }// for all use instructions
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001579
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001580 if( ! DefEqUse ) {
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001581
1582 // after examining all the instructions that follow the DefInst
1583 // if there are no dependencies, we can move it to the OrdVec
1584
1585 // cerr << "Moved to Ord: " << *DefInst;
1586
1587 moveInst2OrdVec(OrdVec, DefInst, PRA);
1588
1589 //OrdVec.push_back(DefInst);
1590
1591 // mark the pos of DefInst with NULL to indicate that it is
1592 // empty
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001593 *DefIt = NULL;
1594 }
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001595
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001596 } // if Def is a machine register
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001597
1598 } // for all instructions in the UnordVec
1599
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001600
Chris Lattner5216cc52002-02-04 05:59:25 +00001601 } while(!CouldMoveAll);
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001602
Chris Lattner5216cc52002-02-04 05:59:25 +00001603 if (DebugPrint) {
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001604 cerr << "\nAdded instructions were reordered to:\n";
1605 for(unsigned int i=0; i < OrdVec.size(); i++)
1606 cerr << *(OrdVec[i]);
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001607 }
Ruchira Sasankad0d294a2001-11-09 23:49:14 +00001608}
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001609
1610
1611
1612
1613
Chris Lattner7f74a562002-01-20 22:54:45 +00001614void UltraSparcRegInfo::moveInst2OrdVec(std::vector<MachineInstr *> &OrdVec,
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001615 MachineInstr *UnordInst,
Chris Lattner5216cc52002-02-04 05:59:25 +00001616 PhyRegAlloc &PRA) const {
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001617 MachineOperand& UseOp = UnordInst->getOperand(0);
1618
1619 if( ! UseOp.opIsDef() &&
1620 UseOp.getOperandType() == MachineOperand::MO_MachineRegister) {
1621
1622 // for the use of UnordInst, see whether there is a defining instr
1623 // before in the OrdVec
1624 bool DefEqUse = false;
1625
Chris Lattner7f74a562002-01-20 22:54:45 +00001626 std::vector<MachineInstr *>::iterator OrdIt = OrdVec.begin();
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001627
1628 for( ; OrdIt != OrdVec.end(); ++OrdIt ) {
1629
1630 MachineInstr *OrdInst = *OrdIt ;
1631
1632 MachineOperand& DefOp =
1633 OrdInst->getOperand(OrdInst->getNumOperands()-1);
1634
1635 if( DefOp.opIsDef() &&
1636 DefOp.getOperandType() == MachineOperand::MO_MachineRegister) {
1637
1638 //cerr << "\nDefining Ord Inst: " << *OrdInst;
1639
1640 if( DefOp.getMachineRegNum() == UseOp.getMachineRegNum() ) {
1641
1642 // we are here because there is a preceding def in the OrdVec
1643 // for the use in this intr we are going to insert. This
1644 // happened because the original code was like:
1645 // 1. add %ox %g0 %oy
1646 // 2. add %oy %g0 %ox
1647 // In Round1, we added 2 to OrdVec but 1 remained in UnordVec
1648 // Now we are processing %ox of 1.
1649 // We have to
1650
1651 const int UReg = DefOp.getMachineRegNum();
1652 const int RegType = getRegType(UReg);
1653 MachineInstr *AdIBef, *AdIAft;
1654
Ruchira Sasanka4cfbfd52002-01-07 19:20:28 +00001655 const int StackOff = PRA.mcInfo.pushTempValue(target,
1656 getSpilledRegSize(RegType));
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001657
1658 // Save the UReg (%ox) on stack before it's destroyed
Ruchira Sasanka2d5c48f2001-11-11 21:49:37 +00001659 AdIBef=cpReg2MemMI(UReg, getFramePointer(), StackOff, RegType);
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001660 OrdIt = OrdVec.insert( OrdIt, AdIBef);
1661 OrdIt++; // points to current instr we processed
1662
1663 // Load directly into DReg (%oy)
1664 MachineOperand& DOp=
1665 (UnordInst->getOperand(UnordInst->getNumOperands()-1));
1666 assert(DOp.opIsDef() && "Last operand is not the def");
1667 const int DReg = DOp.getMachineRegNum();
1668
Ruchira Sasanka2d5c48f2001-11-11 21:49:37 +00001669 AdIAft=cpMem2RegMI(getFramePointer(), StackOff, DReg, RegType);
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001670 OrdVec.push_back(AdIAft);
1671
1672 cerr << "\nFixed CIRCULAR references by reordering";
1673
1674 if( DEBUG_RA ) {
1675 cerr << "\nBefore CIRCULAR Reordering:\n";
1676 cerr << *UnordInst;
1677 cerr << *OrdInst;
1678
1679 cerr << "\nAfter CIRCULAR Reordering - All Inst so far:\n";
1680 for(unsigned i=0; i < OrdVec.size(); i++)
1681 cerr << *(OrdVec[i]);
1682 }
1683
1684 // Do not copy the UseInst to OrdVec
1685 DefEqUse = true;
1686 break;
1687
1688 }// if two registers are equal
1689
1690 } // if Def is a register
1691
1692 } // for each instr in OrdVec
1693
Chris Lattner5216cc52002-02-04 05:59:25 +00001694 if(!DefEqUse) {
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001695
1696 // We didn't find a def in the OrdVec, so just append this inst
1697 OrdVec.push_back( UnordInst );
1698 //cerr << "Reordered Inst (Moved Dn): " << *UnordInst;
1699 }
1700
1701 }// if the operand in UnordInst is a use
Ruchira Sasanka0c085982001-11-10 21:20:43 +00001702}