blob: 89f699b368f8090f744fe9e51de6255b343a7b1a [file] [log] [blame]
Chris Lattnered5171e2002-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 Sasanka89fb46b2001-09-18 22:52:44 +00008#include "SparcInternals.h"
Chris Lattner699683c2002-02-04 05:59:25 +00009#include "SparcRegClassInfo.h"
10#include "llvm/Target/Sparc.h"
Chris Lattnered5171e2002-02-03 07:52:04 +000011#include "llvm/CodeGen/MachineCodeForMethod.h"
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +000012#include "llvm/CodeGen/PhyRegAlloc.h"
Chris Lattner699683c2002-02-04 05:59:25 +000013#include "llvm/CodeGen/MachineInstr.h"
Chris Lattner699683c2002-02-04 05:59:25 +000014#include "llvm/Analysis/LiveVar/MethodLiveVarInfo.h"
15#include "llvm/iTerminators.h"
16#include "llvm/iOther.h"
Ruchira Sasankad00982a2002-01-07 19:20:28 +000017#include "llvm/DerivedTypes.h"
Chris Lattner697954c2002-01-20 22:54:45 +000018#include <iostream>
19using std::cerr;
Chris Lattner20b1ea02001-09-14 03:47:57 +000020
Chris Lattner699683c2002-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. Advef1c15ee2002-03-18 03:12:16 +000035// getZeroRegNum - returns the register that contains always zero.
36// this is the unified register number
Chris Lattner699683c2002-02-04 05:59:25 +000037//
Vikram S. Advef1c15ee2002-03-18 03:12:16 +000038int UltraSparcRegInfo::getZeroRegNum() const {
39 return this->getUnifiedRegNum(UltraSparcRegInfo::IntRegClassID,
40 SparcIntRegOrder::g0);
41}
Chris Lattner699683c2002-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. Advef1c15ee2002-03-18 03:12:16 +000047 return this->getUnifiedRegNum(UltraSparcRegInfo::IntRegClassID,
48 SparcIntRegOrder::o7);
Chris Lattner699683c2002-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. Advef1c15ee2002-03-18 03:12:16 +000056 return this->getUnifiedRegNum(UltraSparcRegInfo::IntRegClassID,
57 SparcIntRegOrder::i7);
Chris Lattner699683c2002-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. Advef1c15ee2002-03-18 03:12:16 +000079// Get unified reg number for frame pointer
Chris Lattner699683c2002-02-04 05:59:25 +000080unsigned UltraSparcRegInfo::getFramePointer() const {
Vikram S. Advef1c15ee2002-03-18 03:12:16 +000081 return this->getUnifiedRegNum(UltraSparcRegInfo::IntRegClassID,
82 SparcIntRegOrder::i6);
Chris Lattner699683c2002-02-04 05:59:25 +000083}
84
Vikram S. Advef1c15ee2002-03-18 03:12:16 +000085// Get unified reg number for stack pointer
Chris Lattner699683c2002-02-04 05:59:25 +000086unsigned UltraSparcRegInfo::getStackPointer() const {
Vikram S. Advef1c15ee2002-03-18 03:12:16 +000087 return this->getUnifiedRegNum(UltraSparcRegInfo::IntRegClassID,
88 SparcIntRegOrder::o6);
Chris Lattner699683c2002-02-04 05:59:25 +000089}
90
91
92
Ruchira Sasankad00982a2002-01-07 19:20:28 +000093//---------------------------------------------------------------------------
Ruchira Sasankad00982a2002-01-07 19:20:28 +000094// Finds the return value of a sparc specific call instruction
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +000095//---------------------------------------------------------------------------
Vikram S. Advea44c6c02002-03-31 19:04:50 +000096
Ruchira Sasankab3b6f532001-10-21 16:43:41 +000097const Value *
Ruchira Sasankad00982a2002-01-07 19:20:28 +000098UltraSparcRegInfo::getCallInstRetVal(const MachineInstr *CallMI) const {
Ruchira Sasankab3b6f532001-10-21 16:43:41 +000099 unsigned OpCode = CallMI->getOpCode();
Chris Lattner697954c2002-01-20 22:54:45 +0000100 unsigned NumOfImpRefs = CallMI->getNumImplicitRefs();
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000101
Chris Lattner697954c2002-01-20 22:54:45 +0000102 if (OpCode == CALL) {
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000103
104 // The one before the last implicit operand is the return value of
105 // a CALL instr
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000106 //
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000107 if( NumOfImpRefs > 1 )
Chris Lattner699683c2002-02-04 05:59:25 +0000108 if (CallMI->implicitRefIsDefined(NumOfImpRefs-2))
109 return CallMI->getImplicitRef(NumOfImpRefs-2);
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000110
Chris Lattner697954c2002-01-20 22:54:45 +0000111 } else if (OpCode == JMPLCALL) {
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000112
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000113 // The last implicit operand is the return value of a JMPL
114 //
Chris Lattner697954c2002-01-20 22:54:45 +0000115 if(NumOfImpRefs > 0)
116 if (CallMI->implicitRefIsDefined(NumOfImpRefs-1))
117 return CallMI->getImplicitRef(NumOfImpRefs-1);
Chris Lattner699683c2002-02-04 05:59:25 +0000118 } else
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000119 assert(0 && "OpCode must be CALL/JMPL for a call instr");
120
121 return NULL;
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000122}
123
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000124
Vikram S. Advea44c6c02002-03-31 19:04:50 +0000125const Value *
126UltraSparcRegInfo::getCallInstIndirectAddrVal(const MachineInstr *CallMI) const
127{
128 return (CallMI->getOpCode() == JMPLCALL)?
129 CallMI->getOperand(0).getVRegValue() : NULL;
130}
131
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000132
133//---------------------------------------------------------------------------
134// Finds the return address of a call sparc specific call instruction
135//---------------------------------------------------------------------------
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000136const Value *
Chris Lattner699683c2002-02-04 05:59:25 +0000137UltraSparcRegInfo::getCallInstRetAddr(const MachineInstr *CallMI) const {
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000138 unsigned OpCode = CallMI->getOpCode();
139
Chris Lattner699683c2002-02-04 05:59:25 +0000140 if (OpCode == CALL) {
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000141 unsigned NumOfImpRefs = CallMI->getNumImplicitRefs();
142
143 assert( NumOfImpRefs && "CALL instr must have at least on ImpRef");
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000144
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000145 // The last implicit operand is the return address of a CALL instr
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000146 //
Chris Lattner699683c2002-02-04 05:59:25 +0000147 return CallMI->getImplicitRef(NumOfImpRefs-1);
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000148
Chris Lattner699683c2002-02-04 05:59:25 +0000149 } else if(OpCode == JMPLCALL) {
150 MachineOperand &MO = (MachineOperand &)CallMI->getOperand(2);
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000151 return MO.getVRegValue();
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000152 }
Chris Lattner699683c2002-02-04 05:59:25 +0000153
154 assert(0 && "OpCode must be CALL/JMPL for a call instr");
155 return 0;
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000156}
157
Chris Lattner699683c2002-02-04 05:59:25 +0000158// The following 3 methods are used to find the RegType (see enum above)
159// of a LiveRange, Value and using the unified RegClassID
160//
161int UltraSparcRegInfo::getRegType(const LiveRange *LR) const {
Chris Lattner699683c2002-02-04 05:59:25 +0000162 switch (LR->getRegClass()->getID()) {
163 case IntRegClassID: return IntRegType;
Chris Lattner37730942002-02-05 03:52:29 +0000164 case FloatRegClassID: {
165 const Type *Typ = LR->getType();
166 if (Typ == Type::FloatTy)
Chris Lattner699683c2002-02-04 05:59:25 +0000167 return FPSingleRegType;
Chris Lattner37730942002-02-05 03:52:29 +0000168 else if (Typ == Type::DoubleTy)
Chris Lattner699683c2002-02-04 05:59:25 +0000169 return FPDoubleRegType;
170 assert(0 && "Unknown type in FloatRegClass");
Chris Lattner37730942002-02-05 03:52:29 +0000171 }
Chris Lattner699683c2002-02-04 05:59:25 +0000172 case IntCCRegClassID: return IntCCRegType;
173 case FloatCCRegClassID: return FloatCCRegType;
174 default: assert( 0 && "Unknown reg class ID");
175 return 0;
176 }
177}
178
179int UltraSparcRegInfo::getRegType(const Value *Val) const {
180 unsigned Typ;
181
182 switch (getRegClassIDOfValue(Val)) {
183 case IntRegClassID: return IntRegType;
184 case FloatRegClassID:
185 Typ = Val->getType()->getPrimitiveID();
186 if (Typ == Type::FloatTyID)
187 return FPSingleRegType;
188 else if (Typ == Type::DoubleTyID)
189 return FPDoubleRegType;
190 assert(0 && "Unknown type in FloatRegClass");
191
192 case IntCCRegClassID: return IntCCRegType;
193 case FloatCCRegClassID: return FloatCCRegType ;
194 default: assert(0 && "Unknown reg class ID");
195 return 0;
196 }
197}
198
199int UltraSparcRegInfo::getRegType(int reg) const {
200 if (reg < 32)
201 return IntRegType;
202 else if (reg < (32 + 32))
203 return FPSingleRegType;
204 else if (reg < (64 + 32))
205 return FPDoubleRegType;
206 else if (reg < (64+32+4))
207 return FloatCCRegType;
208 else if (reg < (64+32+4+2))
209 return IntCCRegType;
210 else
211 assert(0 && "Invalid register number in getRegType");
Chris Lattner49b8a9c2002-02-24 23:02:40 +0000212 return 0;
Chris Lattner699683c2002-02-04 05:59:25 +0000213}
214
215
216
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000217
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000218
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000219//---------------------------------------------------------------------------
Vikram S. Adve53fec862001-10-22 13:41:12 +0000220// Finds the # of actual arguments of the call instruction
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000221//---------------------------------------------------------------------------
Chris Lattner699683c2002-02-04 05:59:25 +0000222unsigned
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000223UltraSparcRegInfo::getCallInstNumArgs(const MachineInstr *CallMI) const {
224
225 unsigned OpCode = CallMI->getOpCode();
Chris Lattner699683c2002-02-04 05:59:25 +0000226 unsigned NumOfImpRefs = CallMI->getNumImplicitRefs();
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000227
Chris Lattner699683c2002-02-04 05:59:25 +0000228 if (OpCode == CALL) {
229 switch (NumOfImpRefs) {
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000230 case 0: assert(0 && "A CALL inst must have at least one ImpRef (RetAddr)");
Chris Lattner699683c2002-02-04 05:59:25 +0000231 case 1: return 0;
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000232 default: // two or more implicit refs
Chris Lattner699683c2002-02-04 05:59:25 +0000233 if (CallMI->implicitRefIsDefined(NumOfImpRefs-2))
234 return NumOfImpRefs - 2;
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000235 else
Chris Lattner699683c2002-02-04 05:59:25 +0000236 return NumOfImpRefs - 1;
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000237 }
Chris Lattner699683c2002-02-04 05:59:25 +0000238 } else if (OpCode == JMPLCALL) {
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000239
240 // The last implicit operand is the return value of a JMPL instr
241 if( NumOfImpRefs > 0 ) {
Chris Lattner699683c2002-02-04 05:59:25 +0000242 if (CallMI->implicitRefIsDefined(NumOfImpRefs-1))
243 return NumOfImpRefs - 1;
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000244 else
Chris Lattner699683c2002-02-04 05:59:25 +0000245 return NumOfImpRefs;
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000246 }
247 else
Chris Lattner699683c2002-02-04 05:59:25 +0000248 return NumOfImpRefs;
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000249 }
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000250
Chris Lattner699683c2002-02-04 05:59:25 +0000251 assert(0 && "OpCode must be CALL/JMPL for a call instr");
252 return 0;
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000253}
254
255
Vikram S. Adve53fec862001-10-22 13:41:12 +0000256
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000257//---------------------------------------------------------------------------
258// Finds whether a call is an indirect call
259//---------------------------------------------------------------------------
260bool UltraSparcRegInfo::isVarArgCall(const MachineInstr *CallMI) const {
261
262 assert ( (UltraSparcInfo->getInstrInfo()).isCall(CallMI->getOpCode()) );
263
264 const MachineOperand & calleeOp = CallMI->getOperand(0);
265 Value *calleeVal = calleeOp.getVRegValue();
266
Chris Lattner2aac6bf2002-04-04 22:19:18 +0000267 PointerType *PT = cast<PointerType>(calleeVal->getType());
268 return cast<FunctionType>(PT->getElementType())->isVarArg();
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000269}
270
271
272
273
274//---------------------------------------------------------------------------
275// Suggests a register for the ret address in the RET machine instruction.
276// We always suggest %i7 by convention.
277//---------------------------------------------------------------------------
Chris Lattner699683c2002-02-04 05:59:25 +0000278void UltraSparcRegInfo::suggestReg4RetAddr(const MachineInstr *RetMI,
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000279 LiveRangeInfo& LRI) const {
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000280
Vikram S. Adve53fec862001-10-22 13:41:12 +0000281 assert( (RetMI->getNumOperands() >= 2)
282 && "JMPL/RETURN must have 3 and 2 operands respectively");
283
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000284 MachineOperand & MO = ( MachineOperand &) RetMI->getOperand(0);
285
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000286 // return address is always mapped to i7
287 //
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000288 MO.setRegForValue( getUnifiedRegNum( IntRegClassID, SparcIntRegOrder::i7) );
Vikram S. Adve53fec862001-10-22 13:41:12 +0000289
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000290 // Possible Optimization:
Ruchira Sasankac4d4b762001-10-16 01:23:19 +0000291 // Instead of setting the color, we can suggest one. In that case,
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000292 // we have to test later whether it received the suggested color.
293 // In that case, a LR has to be created at the start of method.
294 // It has to be done as follows (remove the setRegVal above):
Ruchira Sasanka91442282001-09-30 23:16:47 +0000295
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000296 // const Value *RetAddrVal = MO.getVRegValue();
297 // assert( RetAddrVal && "LR for ret address must be created at start");
298 // LiveRange * RetAddrLR = LRI.getLiveRangeForValue( RetAddrVal);
299 // RetAddrLR->setSuggestedColor(getUnifiedRegNum( IntRegClassID,
300 // SparcIntRegOrdr::i7) );
Ruchira Sasanka91442282001-09-30 23:16:47 +0000301}
302
303
304//---------------------------------------------------------------------------
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000305// Suggests a register for the ret address in the JMPL/CALL machine instr.
306// Sparc ABI dictates that %o7 be used for this purpose.
Ruchira Sasanka91442282001-09-30 23:16:47 +0000307//---------------------------------------------------------------------------
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000308void UltraSparcRegInfo::suggestReg4CallAddr(const MachineInstr * CallMI,
309 LiveRangeInfo& LRI,
Chris Lattner697954c2002-01-20 22:54:45 +0000310 std::vector<RegClass *> RCList) const {
Ruchira Sasanka91442282001-09-30 23:16:47 +0000311
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000312
313 const Value *RetAddrVal = getCallInstRetAddr( CallMI );
314
315 // RetAddrVal cannot be NULL (asserted in getCallInstRetAddr)
316 // create a new LR for the return address and color it
317
318 LiveRange * RetAddrLR = new LiveRange();
Chris Lattnerd1b60fb2002-02-04 16:37:09 +0000319 RetAddrLR->insert( RetAddrVal );
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000320 unsigned RegClassID = getRegClassIDOfValue( RetAddrVal );
321 RetAddrLR->setRegClass( RCList[RegClassID] );
322 RetAddrLR->setColor(getUnifiedRegNum(IntRegClassID,SparcIntRegOrder::o7));
323 LRI.addLRToMap( RetAddrVal, RetAddrLR);
324
Ruchira Sasanka91442282001-09-30 23:16:47 +0000325}
326
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000327
328
Ruchira Sasanka91442282001-09-30 23:16:47 +0000329
330//---------------------------------------------------------------------------
331// This method will suggest colors to incoming args to a method.
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000332// According to the Sparc ABI, the first 6 incoming args are in
333// %i0 - %i5 (if they are integer) OR in %f0 - %f31 (if they are float).
Ruchira Sasanka91442282001-09-30 23:16:47 +0000334// If the arg is passed on stack due to the lack of regs, NOTHING will be
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000335// done - it will be colored (or spilled) as a normal live range.
Ruchira Sasanka91442282001-09-30 23:16:47 +0000336//---------------------------------------------------------------------------
Chris Lattnerb7653df2002-04-08 22:03:57 +0000337void UltraSparcRegInfo::suggestRegs4MethodArgs(const Function *Meth,
Ruchira Sasanka91442282001-09-30 23:16:47 +0000338 LiveRangeInfo& LRI) const
Chris Lattner20b1ea02001-09-14 03:47:57 +0000339{
340
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000341 // get the argument list
Chris Lattnerb7653df2002-04-08 22:03:57 +0000342 const Function::ArgumentListType& ArgList = Meth->getArgumentList();
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000343 // get an iterator to arg list
Chris Lattnerb7653df2002-04-08 22:03:57 +0000344 Function::ArgumentListType::const_iterator ArgIt = ArgList.begin();
Chris Lattner20b1ea02001-09-14 03:47:57 +0000345
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000346 // for each argument
Ruchira Sasanka91442282001-09-30 23:16:47 +0000347 for( unsigned argNo=0; ArgIt != ArgList.end() ; ++ArgIt, ++argNo) {
Chris Lattner20b1ea02001-09-14 03:47:57 +0000348
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000349 // get the LR of arg
350 LiveRange *const LR = LRI.getLiveRangeForValue((const Value *) *ArgIt);
Ruchira Sasanka91442282001-09-30 23:16:47 +0000351 assert( LR && "No live range found for method arg");
352
353 unsigned RegType = getRegType( LR );
354
Chris Lattner20b1ea02001-09-14 03:47:57 +0000355
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000356 // if the arg is in int class - allocate a reg for an int arg
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000357 //
Ruchira Sasanka91442282001-09-30 23:16:47 +0000358 if( RegType == IntRegType ) {
Chris Lattner20b1ea02001-09-14 03:47:57 +0000359
Ruchira Sasanka91442282001-09-30 23:16:47 +0000360 if( argNo < NumOfIntArgRegs) {
361 LR->setSuggestedColor( SparcIntRegOrder::i0 + argNo );
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000362 }
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000363 else {
Ruchira Sasanka91442282001-09-30 23:16:47 +0000364 // Do NOTHING as this will be colored as a normal value.
Chris Lattner1e23ed72001-10-15 18:15:27 +0000365 if (DEBUG_RA) cerr << " Int Regr not suggested for method arg\n";
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000366 }
Ruchira Sasanka91442282001-09-30 23:16:47 +0000367
Chris Lattner20b1ea02001-09-14 03:47:57 +0000368 }
Ruchira Sasanka91442282001-09-30 23:16:47 +0000369 else if( RegType==FPSingleRegType && (argNo*2+1) < NumOfFloatArgRegs)
370 LR->setSuggestedColor( SparcFloatRegOrder::f0 + (argNo * 2 + 1) );
371
372
373 else if( RegType == FPDoubleRegType && (argNo*2) < NumOfFloatArgRegs)
374 LR->setSuggestedColor( SparcFloatRegOrder::f0 + (argNo * 2) );
375
Chris Lattner20b1ea02001-09-14 03:47:57 +0000376 }
Chris Lattner20b1ea02001-09-14 03:47:57 +0000377}
378
Ruchira Sasanka91442282001-09-30 23:16:47 +0000379
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000380
381//---------------------------------------------------------------------------
382// This method is called after graph coloring to move incoming args to
383// the correct hardware registers if they did not receive the correct
384// (suggested) color through graph coloring.
385//---------------------------------------------------------------------------
Chris Lattnerb7653df2002-04-08 22:03:57 +0000386void UltraSparcRegInfo::colorMethodArgs(const Function *Meth,
Chris Lattner699683c2002-02-04 05:59:25 +0000387 LiveRangeInfo &LRI,
388 AddedInstrns *FirstAI) const {
Ruchira Sasanka91442282001-09-30 23:16:47 +0000389
390 // get the argument list
Chris Lattnerb7653df2002-04-08 22:03:57 +0000391 const Function::ArgumentListType& ArgList = Meth->getArgumentList();
Ruchira Sasanka91442282001-09-30 23:16:47 +0000392 // get an iterator to arg list
Chris Lattnerb7653df2002-04-08 22:03:57 +0000393 Function::ArgumentListType::const_iterator ArgIt = ArgList.begin();
Ruchira Sasanka91442282001-09-30 23:16:47 +0000394 MachineInstr *AdMI;
395
396
397 // for each argument
398 for( unsigned argNo=0; ArgIt != ArgList.end() ; ++ArgIt, ++argNo) {
399
400 // get the LR of arg
Chris Lattnerb7653df2002-04-08 22:03:57 +0000401 LiveRange *LR = LRI.getLiveRangeForValue(*ArgIt);
Ruchira Sasanka91442282001-09-30 23:16:47 +0000402 assert( LR && "No live range found for method arg");
403
404
Ruchira Sasanka91442282001-09-30 23:16:47 +0000405 unsigned RegType = getRegType( LR );
406 unsigned RegClassID = (LR->getRegClass())->getID();
407
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000408 // Find whether this argument is coming in a register (if not, on stack)
409 // Also find the correct register that the argument must go (UniArgReg)
410 //
Ruchira Sasanka91442282001-09-30 23:16:47 +0000411 bool isArgInReg = false;
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000412 unsigned UniArgReg = InvalidRegNum; // reg that LR MUST be colored with
Ruchira Sasanka91442282001-09-30 23:16:47 +0000413
414 if( (RegType== IntRegType && argNo < NumOfIntArgRegs)) {
415 isArgInReg = true;
Ruchira Sasankac74a7202001-10-24 15:56:58 +0000416 UniArgReg = getUnifiedRegNum( RegClassID, SparcIntRegOrder::i0 + argNo );
Ruchira Sasanka91442282001-09-30 23:16:47 +0000417 }
418 else if(RegType == FPSingleRegType && argNo < NumOfFloatArgRegs) {
419 isArgInReg = true;
420 UniArgReg = getUnifiedRegNum( RegClassID,
421 SparcFloatRegOrder::f0 + argNo*2 + 1 ) ;
422 }
423 else if(RegType == FPDoubleRegType && argNo < NumOfFloatArgRegs) {
424 isArgInReg = true;
425 UniArgReg = getUnifiedRegNum(RegClassID, SparcFloatRegOrder::f0+argNo*2);
426 }
427
428
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000429 if( LR->hasColor() ) { // if this arg received a register
Ruchira Sasanka91442282001-09-30 23:16:47 +0000430
Ruchira Sasankac74a7202001-10-24 15:56:58 +0000431 unsigned UniLRReg = getUnifiedRegNum( RegClassID, LR->getColor() );
432
433 // if LR received the correct color, nothing to do
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000434 //
Ruchira Sasankac74a7202001-10-24 15:56:58 +0000435 if( UniLRReg == UniArgReg )
436 continue;
437
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000438 // We are here because the LR did not receive the suggested
439 // but LR received another register.
440 // Now we have to copy the %i reg (or stack pos of arg)
441 // to the register the LR was colored with.
Ruchira Sasankac74a7202001-10-24 15:56:58 +0000442
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000443 // if the arg is coming in UniArgReg register, it MUST go into
Ruchira Sasankac74a7202001-10-24 15:56:58 +0000444 // the UniLRReg register
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000445 //
Ruchira Sasanka91442282001-09-30 23:16:47 +0000446 if( isArgInReg )
Ruchira Sasankac74a7202001-10-24 15:56:58 +0000447 AdMI = cpReg2RegMI( UniArgReg, UniLRReg, RegType );
Ruchira Sasanka91442282001-09-30 23:16:47 +0000448
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000449 else {
Ruchira Sasanka91442282001-09-30 23:16:47 +0000450
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000451 // Now the arg is coming on stack. Since the LR recieved a register,
452 // we just have to load the arg on stack into that register
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000453 //
Vikram S. Adve1c0fba62001-11-08 04:56:41 +0000454 const MachineFrameInfo& frameInfo = target.getFrameInfo();
455 assert(frameInfo.argsOnStackHaveFixedSize());
456
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000457 bool growUp; // find the offset of arg in stack frame
Vikram S. Adve1c0fba62001-11-08 04:56:41 +0000458 int firstArg =
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000459 frameInfo.getFirstIncomingArgOffset(MachineCodeForMethod::get(Meth),
460 growUp);
Vikram S. Adve1c0fba62001-11-08 04:56:41 +0000461 int offsetFromFP =
462 growUp? firstArg + argNo * frameInfo.getSizeOfEachArgOnStack()
463 : firstArg - argNo * frameInfo.getSizeOfEachArgOnStack();
464
465 AdMI = cpMem2RegMI(getFramePointer(), offsetFromFP,
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000466 UniLRReg, RegType );
467 }
468
469 FirstAI->InstrnsBefore.push_back( AdMI );
470
471 } // if LR received a color
472
473 else {
474
475 // Now, the LR did not receive a color. But it has a stack offset for
476 // spilling.
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000477 // So, if the arg is coming in UniArgReg register, we can just move
478 // that on to the stack pos of LR
479
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000480 if( isArgInReg ) {
Chris Lattner697954c2002-01-20 22:54:45 +0000481 cpReg2MemMI(UniArgReg, getFramePointer(),
482 LR->getSpillOffFromFP(), RegType );
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000483
484 FirstAI->InstrnsBefore.push_back( AdMI );
485 }
486
487 else {
488
489 // Now the arg is coming on stack. Since the LR did NOT
490 // recieved a register as well, it is allocated a stack position. We
491 // can simply change the stack poistion of the LR. We can do this,
492 // since this method is called before any other method that makes
493 // uses of the stack pos of the LR (e.g., updateMachineInstr)
494
Vikram S. Adve1c0fba62001-11-08 04:56:41 +0000495 const MachineFrameInfo& frameInfo = target.getFrameInfo();
496 assert(frameInfo.argsOnStackHaveFixedSize());
497
498 bool growUp;
499 int firstArg = frameInfo.getFirstIncomingArgOffset(MachineCodeForMethod::get(Meth), growUp);
500 int offsetFromFP =
501 growUp? firstArg + argNo * frameInfo.getSizeOfEachArgOnStack()
502 : firstArg - argNo * frameInfo.getSizeOfEachArgOnStack();
503
504 LR->modifySpillOffFromFP( offsetFromFP );
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000505 }
Ruchira Sasanka91442282001-09-30 23:16:47 +0000506
507 }
508
Ruchira Sasanka91442282001-09-30 23:16:47 +0000509 } // for each incoming argument
510
511}
512
Chris Lattner20b1ea02001-09-14 03:47:57 +0000513
514
Ruchira Sasanka91442282001-09-30 23:16:47 +0000515//---------------------------------------------------------------------------
516// This method is called before graph coloring to suggest colors to the
517// outgoing call args and the return value of the call.
518//---------------------------------------------------------------------------
Chris Lattner699683c2002-02-04 05:59:25 +0000519void UltraSparcRegInfo::suggestRegs4CallArgs(const MachineInstr *CallMI,
Ruchira Sasanka91442282001-09-30 23:16:47 +0000520 LiveRangeInfo& LRI,
Chris Lattner697954c2002-01-20 22:54:45 +0000521 std::vector<RegClass *> RCList) const {
Chris Lattner20b1ea02001-09-14 03:47:57 +0000522
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000523 assert ( (UltraSparcInfo->getInstrInfo()).isCall(CallMI->getOpCode()) );
Chris Lattner20b1ea02001-09-14 03:47:57 +0000524
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000525 suggestReg4CallAddr(CallMI, LRI, RCList);
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000526
Chris Lattner20b1ea02001-09-14 03:47:57 +0000527
Ruchira Sasanka91442282001-09-30 23:16:47 +0000528 // First color the return value of the call instruction. The return value
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000529 // will be in %o0 if the value is an integer type, or in %f0 if the
530 // value is a float type.
531
Ruchira Sasanka91442282001-09-30 23:16:47 +0000532 // the return value cannot have a LR in machine instruction since it is
533 // only defined by the call instruction
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000534
Ruchira Sasanka91442282001-09-30 23:16:47 +0000535 // if type is not void, create a new live range and set its
536 // register class and add to LRI
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000537
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000538
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000539 const Value *RetVal = getCallInstRetVal( CallMI );
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000540
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000541
Chris Lattner699683c2002-02-04 05:59:25 +0000542 if (RetVal) {
543 assert ((!LRI.getLiveRangeForValue(RetVal)) &&
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000544 "LR for ret Value of call already definded!");
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000545
Chris Lattner699683c2002-02-04 05:59:25 +0000546 // create a new LR for the return value
547 LiveRange *RetValLR = new LiveRange();
Chris Lattnerd1b60fb2002-02-04 16:37:09 +0000548 RetValLR->insert(RetVal);
Chris Lattner699683c2002-02-04 05:59:25 +0000549 unsigned RegClassID = getRegClassIDOfValue(RetVal);
550 RetValLR->setRegClass(RCList[RegClassID]);
551 LRI.addLRToMap(RetVal, RetValLR);
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000552
553 // now suggest a register depending on the register class of ret arg
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000554
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000555 if( RegClassID == IntRegClassID )
556 RetValLR->setSuggestedColor(SparcIntRegOrder::o0);
557 else if (RegClassID == FloatRegClassID )
558 RetValLR->setSuggestedColor(SparcFloatRegOrder::f0 );
559 else assert( 0 && "Unknown reg class for return value of call\n");
Chris Lattner20b1ea02001-09-14 03:47:57 +0000560 }
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000561
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000562
Ruchira Sasanka91442282001-09-30 23:16:47 +0000563 // Now suggest colors for arguments (operands) of the call instruction.
564 // Colors are suggested only if the arg number is smaller than the
565 // the number of registers allocated for argument passing.
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000566 // Now, go thru call args - implicit operands of the call MI
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000567
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000568 unsigned NumOfCallArgs = getCallInstNumArgs( CallMI );
Ruchira Sasanka91442282001-09-30 23:16:47 +0000569
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000570 for(unsigned argNo=0, i=0; i < NumOfCallArgs; ++i, ++argNo ) {
571
572 const Value *CallArg = CallMI->getImplicitRef(i);
Ruchira Sasanka91442282001-09-30 23:16:47 +0000573
574 // get the LR of call operand (parameter)
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000575 LiveRange *const LR = LRI.getLiveRangeForValue(CallArg);
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000576
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000577 // not possible to have a null LR since all args (even consts)
578 // must be defined before
Chris Lattner0665a5f2002-02-05 01:43:49 +0000579 if (!LR) {
580 cerr << " ERROR: In call instr, no LR for arg: " << RAV(CallArg) << "\n";
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000581 assert(0 && "NO LR for call arg");
Ruchira Sasanka91442282001-09-30 23:16:47 +0000582 }
583
584 unsigned RegType = getRegType( LR );
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000585
Ruchira Sasanka91442282001-09-30 23:16:47 +0000586 // if the arg is in int class - allocate a reg for an int arg
587 if( RegType == IntRegType ) {
588
589 if( argNo < NumOfIntArgRegs)
590 LR->setSuggestedColor( SparcIntRegOrder::o0 + argNo );
591
592 else if (DEBUG_RA)
593 // Do NOTHING as this will be colored as a normal value.
Chris Lattner697954c2002-01-20 22:54:45 +0000594 cerr << " Regr not suggested for int call arg\n";
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000595
Ruchira Sasanka91442282001-09-30 23:16:47 +0000596 }
597 else if( RegType == FPSingleRegType && (argNo*2 +1)< NumOfFloatArgRegs)
598 LR->setSuggestedColor( SparcFloatRegOrder::f0 + (argNo * 2 + 1) );
599
600
601 else if( RegType == FPDoubleRegType && (argNo*2) < NumOfFloatArgRegs)
602 LR->setSuggestedColor( SparcFloatRegOrder::f0 + (argNo * 2) );
603
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000604
Ruchira Sasanka91442282001-09-30 23:16:47 +0000605 } // for all call arguments
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000606
Chris Lattner20b1ea02001-09-14 03:47:57 +0000607}
608
609
Ruchira Sasanka91442282001-09-30 23:16:47 +0000610//---------------------------------------------------------------------------
611// After graph coloring, we have call this method to see whehter the return
612// value and the call args received the correct colors. If not, we have
613// to instert copy instructions.
614//---------------------------------------------------------------------------
Chris Lattner20b1ea02001-09-14 03:47:57 +0000615
Chris Lattner699683c2002-02-04 05:59:25 +0000616void UltraSparcRegInfo::colorCallArgs(const MachineInstr *CallMI,
617 LiveRangeInfo &LRI,
618 AddedInstrns *CallAI,
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000619 PhyRegAlloc &PRA,
620 const BasicBlock *BB) const {
Chris Lattner20b1ea02001-09-14 03:47:57 +0000621
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000622 assert ( (UltraSparcInfo->getInstrInfo()).isCall(CallMI->getOpCode()) );
623
Vikram S. Adve1c0fba62001-11-08 04:56:41 +0000624 // Reset the optional args area in the stack frame
625 // since that is reused for each call
626 //
627 PRA.mcInfo.resetOptionalArgs(target);
628
Ruchira Sasanka91442282001-09-30 23:16:47 +0000629 // First color the return value of the call.
630 // If there is a LR for the return value, it means this
631 // method returns a value
632
633 MachineInstr *AdMI;
Chris Lattner20b1ea02001-09-14 03:47:57 +0000634
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000635 const Value *RetVal = getCallInstRetVal( CallMI );
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000636
Chris Lattner0665a5f2002-02-05 01:43:49 +0000637 if (RetVal) {
638 LiveRange *RetValLR = LRI.getLiveRangeForValue( RetVal );
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000639
Chris Lattner0665a5f2002-02-05 01:43:49 +0000640 if (!RetValLR) {
641 cerr << "\nNo LR for:" << RAV(RetVal) << "\n";
642 assert(0 && "ERR:No LR for non-void return value");
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000643 }
Ruchira Sasankac74a7202001-10-24 15:56:58 +0000644
645 unsigned RegClassID = (RetValLR->getRegClass())->getID();
646 bool recvCorrectColor = false;
647
648 unsigned CorrectCol; // correct color for ret value
649 if(RegClassID == IntRegClassID)
650 CorrectCol = SparcIntRegOrder::o0;
651 else if(RegClassID == FloatRegClassID)
652 CorrectCol = SparcFloatRegOrder::f0;
Chris Lattner8e5c0b42001-11-07 14:01:59 +0000653 else {
Ruchira Sasankac74a7202001-10-24 15:56:58 +0000654 assert( 0 && "Unknown RegClass");
Chris Lattner8e5c0b42001-11-07 14:01:59 +0000655 return;
656 }
Ruchira Sasankac74a7202001-10-24 15:56:58 +0000657
658 // if the LR received the correct color, NOTHING to do
659
660 if( RetValLR->hasColor() )
661 if( RetValLR->getColor() == CorrectCol )
662 recvCorrectColor = true;
663
664
665 // if we didn't receive the correct color for some reason,
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000666 // put copy instruction
667
Ruchira Sasankac74a7202001-10-24 15:56:58 +0000668 if( !recvCorrectColor ) {
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000669
670 unsigned RegType = getRegType( RetValLR );
671
672 // the reg that LR must be colored with
673 unsigned UniRetReg = getUnifiedRegNum( RegClassID, CorrectCol);
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000674
675 if( RetValLR->hasColor() ) {
676
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000677 unsigned
678 UniRetLRReg=getUnifiedRegNum(RegClassID,RetValLR->getColor());
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000679
Ruchira Sasankac74a7202001-10-24 15:56:58 +0000680 // the return value is coming in UniRetReg but has to go into
681 // the UniRetLRReg
682
683 AdMI = cpReg2RegMI( UniRetReg, UniRetLRReg, RegType );
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000684
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000685 } // if LR has color
686 else {
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000687
688 // if the LR did NOT receive a color, we have to move the return
689 // value coming in UniRetReg to the stack pos of spilled LR
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000690
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000691 AdMI = cpReg2MemMI(UniRetReg, getFramePointer(),
692 RetValLR->getSpillOffFromFP(), RegType );
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000693 }
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000694
695 CallAI->InstrnsAfter.push_back( AdMI );
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000696
697 } // the LR didn't receive the suggested color
698
699 } // if there a return value
Ruchira Sasanka91442282001-09-30 23:16:47 +0000700
701
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000702 //-------------------------------------------
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000703 // Now color all args of the call instruction
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000704 //-------------------------------------------
Ruchira Sasanka91442282001-09-30 23:16:47 +0000705
Chris Lattner697954c2002-01-20 22:54:45 +0000706 std::vector<MachineInstr *> AddedInstrnsBefore;
Ruchira Sasanka868cf822001-11-09 23:49:14 +0000707
Ruchira Sasankab3b6f532001-10-21 16:43:41 +0000708 unsigned NumOfCallArgs = getCallInstNumArgs( CallMI );
Ruchira Sasanka91442282001-09-30 23:16:47 +0000709
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000710 bool VarArgCall = isVarArgCall( CallMI );
711
712 if(VarArgCall) cerr << "\nVar arg call found!!\n";
713
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000714 for(unsigned argNo=0, i=0; i < NumOfCallArgs; ++i, ++argNo ) {
715
716 const Value *CallArg = CallMI->getImplicitRef(i);
717
Ruchira Sasanka91442282001-09-30 23:16:47 +0000718 // get the LR of call operand (parameter)
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000719 LiveRange *const LR = LRI.getLiveRangeForValue(CallArg);
Ruchira Sasanka91442282001-09-30 23:16:47 +0000720
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000721 unsigned RegType = getRegType( CallArg );
722 unsigned RegClassID = getRegClassIDOfValue( CallArg);
Ruchira Sasanka91442282001-09-30 23:16:47 +0000723
724 // find whether this argument is coming in a register (if not, on stack)
725
726 bool isArgInReg = false;
Ruchira Sasankac74a7202001-10-24 15:56:58 +0000727 unsigned UniArgReg = InvalidRegNum; // reg that LR must be colored with
Ruchira Sasanka91442282001-09-30 23:16:47 +0000728
729 if( (RegType== IntRegType && argNo < NumOfIntArgRegs)) {
730 isArgInReg = true;
731 UniArgReg = getUnifiedRegNum(RegClassID, SparcIntRegOrder::o0 + argNo );
732 }
733 else if(RegType == FPSingleRegType && argNo < NumOfFloatArgRegs) {
734 isArgInReg = true;
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000735
736 if( !VarArgCall )
737 UniArgReg = getUnifiedRegNum(RegClassID,
738 SparcFloatRegOrder::f0 + (argNo*2 + 1) );
739 else {
740 // a variable argument call - must pass float arg in %o's
741 if( argNo < NumOfIntArgRegs)
742 UniArgReg=getUnifiedRegNum(IntRegClassID,SparcIntRegOrder::o0+argNo);
743 else
744 isArgInReg = false;
745 }
746
Ruchira Sasanka91442282001-09-30 23:16:47 +0000747 }
748 else if(RegType == FPDoubleRegType && argNo < NumOfFloatArgRegs) {
749 isArgInReg = true;
Chris Lattner20b1ea02001-09-14 03:47:57 +0000750
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000751 if( !VarArgCall )
752 UniArgReg =getUnifiedRegNum(RegClassID,SparcFloatRegOrder::f0+argNo*2);
753 else {
754 // a variable argument call - must pass float arg in %o's
755 if( argNo < NumOfIntArgRegs)
756 UniArgReg=getUnifiedRegNum(IntRegClassID,SparcIntRegOrder::o0+argNo);
757 else
758 isArgInReg = false;
759 }
760 }
Chris Lattner20b1ea02001-09-14 03:47:57 +0000761
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000762 // not possible to have a null LR since all args (even consts)
763 // must be defined before
Chris Lattner0665a5f2002-02-05 01:43:49 +0000764 if (!LR) {
765 cerr << " ERROR: In call instr, no LR for arg: " << RAV(CallArg) << "\n";
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000766 assert(0 && "NO LR for call arg");
Ruchira Sasanka91442282001-09-30 23:16:47 +0000767 }
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000768
Ruchira Sasanka91442282001-09-30 23:16:47 +0000769
Chris Lattner699683c2002-02-04 05:59:25 +0000770 if (LR->hasColor()) {
Ruchira Sasankac74a7202001-10-24 15:56:58 +0000771 unsigned UniLRReg = getUnifiedRegNum( RegClassID, LR->getColor() );
772
773 // if LR received the correct color, nothing to do
774 if( UniLRReg == UniArgReg )
775 continue;
776
Ruchira Sasanka91442282001-09-30 23:16:47 +0000777 // We are here because though the LR is allocated a register, it
778 // was not allocated the suggested register. So, we have to copy %ix reg
779 // (or stack pos of arg) to the register it was colored with
780
Ruchira Sasankac74a7202001-10-24 15:56:58 +0000781 // the LR is colored with UniLRReg but has to go into UniArgReg
782 // to pass it as an argument
Ruchira Sasanka91442282001-09-30 23:16:47 +0000783
Ruchira Sasanka9d478662001-11-12 20:54:19 +0000784 if( isArgInReg ) {
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000785
786 if( VarArgCall && RegClassID == FloatRegClassID ) {
787
788
789 // for a variable argument call, the float reg must go in a %o reg.
790 // We have to move a float reg to an int reg via memory.
791 // The store instruction will be directly added to
792 // CallAI->InstrnsBefore since it does not need reordering
793 //
794 int TmpOff = PRA.mcInfo.pushTempValue(target,
795 getSpilledRegSize(RegType));
796
797 AdMI = cpReg2MemMI(UniLRReg, getFramePointer(), TmpOff, RegType );
798 CallAI->InstrnsBefore.push_back( AdMI );
799
800 AdMI = cpMem2RegMI(getFramePointer(), TmpOff, UniArgReg, IntRegType);
801 AddedInstrnsBefore.push_back( AdMI );
802 }
803
804 else {
805 AdMI = cpReg2RegMI(UniLRReg, UniArgReg, RegType );
806 AddedInstrnsBefore.push_back( AdMI );
807 }
808
Chris Lattner699683c2002-02-04 05:59:25 +0000809 } else {
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000810 // Now, we have to pass the arg on stack. Since LR received a register
811 // we just have to move that register to the stack position where
812 // the argument must be passed
Ruchira Sasanka91442282001-09-30 23:16:47 +0000813
Vikram S. Adve1c0fba62001-11-08 04:56:41 +0000814 int argOffset = PRA.mcInfo.allocateOptionalArg(target, LR->getType());
Ruchira Sasanka91442282001-09-30 23:16:47 +0000815
Ruchira Sasankac56e5c12001-11-11 22:37:51 +0000816 AdMI = cpReg2MemMI(UniLRReg, getStackPointer(), argOffset, RegType );
Ruchira Sasanka9d478662001-11-12 20:54:19 +0000817
818 // Now add the instruction. We can directly add to
819 // CallAI->InstrnsBefore since we are just saving a reg on stack
820 //
821 CallAI->InstrnsBefore.push_back( AdMI );
822
823 //cerr << "\nCaution: Passing a reg on stack";
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000824 }
825
Ruchira Sasanka9d478662001-11-12 20:54:19 +0000826
Chris Lattner699683c2002-02-04 05:59:25 +0000827 } else { // LR is not colored (i.e., spilled)
Ruchira Sasanka91442282001-09-30 23:16:47 +0000828
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000829 if( isArgInReg ) {
830
831 // Now the LR did NOT recieve a register but has a stack poistion.
832 // Since, the outgoing arg goes in a register we just have to insert
833 // a load instruction to load the LR to outgoing register
834
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000835 if( VarArgCall && RegClassID == FloatRegClassID )
836 AdMI = cpMem2RegMI(getFramePointer(), LR->getSpillOffFromFP(),
837 UniArgReg, IntRegType );
838 else
839 AdMI = cpMem2RegMI(getFramePointer(), LR->getSpillOffFromFP(),
840 UniArgReg, RegType );
Vikram S. Adve1c0fba62001-11-08 04:56:41 +0000841
Ruchira Sasanka91014f62001-11-12 20:31:47 +0000842 cerr << "\nCaution: Loading a spilled val to a reg as a call arg";
Ruchira Sasanka868cf822001-11-09 23:49:14 +0000843 AddedInstrnsBefore.push_back( AdMI ); // Now add the instruction
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000844 }
Vikram S. Adve1c0fba62001-11-08 04:56:41 +0000845
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000846 else {
847 // Now, we have to pass the arg on stack. Since LR also did NOT
848 // receive a register we have to move an argument in memory to
849 // outgoing parameter on stack.
850
851 // Optoimize: Optimize when reverse pointers in MahineInstr are
852 // introduced.
853 // call PRA.getUnusedRegAtMI(....) to get an unused reg. Only if this
854 // fails, then use the following code. Currently, we cannot call the
855 // above method since we cannot find LVSetBefore without the BB
856
Ruchira Sasanka295264d2001-11-15 20:25:07 +0000857 int TReg = PRA.getUniRegNotUsedByThisInst( LR->getRegClass(), CallMI );
Ruchira Sasanka868cf822001-11-09 23:49:14 +0000858
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000859 int TmpOff = PRA.mcInfo.pushTempValue(target,
860 getSpilledRegSize(getRegType(LR)) );
861
Vikram S. Adve1c0fba62001-11-08 04:56:41 +0000862
863 int argOffset = PRA.mcInfo.allocateOptionalArg(target, LR->getType());
864
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000865 MachineInstr *Ad1, *Ad2, *Ad3, *Ad4;
Vikram S. Adve1c0fba62001-11-08 04:56:41 +0000866
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000867 // Sequence:
868 // (1) Save TReg on stack
869 // (2) Load LR value into TReg from stack pos of LR
870 // (3) Store Treg on outgoing Arg pos on stack
871 // (4) Load the old value of TReg from stack to TReg (restore it)
872
873 Ad1 = cpReg2MemMI(TReg, getFramePointer(), TmpOff, RegType );
874 Ad2 = cpMem2RegMI(getFramePointer(), LR->getSpillOffFromFP(),
875 TReg, RegType );
Ruchira Sasankac56e5c12001-11-11 22:37:51 +0000876 Ad3 = cpReg2MemMI(TReg, getStackPointer(), argOffset, RegType );
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000877 Ad4 = cpMem2RegMI(getFramePointer(), TmpOff, TReg, RegType );
Ruchira Sasanka868cf822001-11-09 23:49:14 +0000878
879 // We directly add to CallAI->InstrnsBefore instead of adding to
880 // AddedInstrnsBefore since these instructions must not be
881 // reordered.
Vikram S. Adve1c0fba62001-11-08 04:56:41 +0000882
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000883 CallAI->InstrnsBefore.push_back( Ad1 );
884 CallAI->InstrnsBefore.push_back( Ad2 );
885 CallAI->InstrnsBefore.push_back( Ad3 );
886 CallAI->InstrnsBefore.push_back( Ad4 );
Ruchira Sasanka868cf822001-11-09 23:49:14 +0000887
Ruchira Sasanka91014f62001-11-12 20:31:47 +0000888 cerr << "\nCaution: Call arg moved from stack2stack for: " << *CallMI ;
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000889 }
Ruchira Sasanka91442282001-09-30 23:16:47 +0000890 }
Ruchira Sasanka91442282001-09-30 23:16:47 +0000891 } // for each parameter in call instruction
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000892
Ruchira Sasanka868cf822001-11-09 23:49:14 +0000893
894 // if we added any instruction before the call instruction, verify
895 // that they are in the proper order and if not, reorder them
896
Chris Lattner699683c2002-02-04 05:59:25 +0000897 if (!AddedInstrnsBefore.empty()) {
Ruchira Sasanka868cf822001-11-09 23:49:14 +0000898
Chris Lattner699683c2002-02-04 05:59:25 +0000899 if (DEBUG_RA) {
Ruchira Sasanka868cf822001-11-09 23:49:14 +0000900 cerr << "\nCalling reorder with instrns: \n";
901 for(unsigned i=0; i < AddedInstrnsBefore.size(); i++)
902 cerr << *(AddedInstrnsBefore[i]);
903 }
904
Chris Lattner697954c2002-01-20 22:54:45 +0000905 std::vector<MachineInstr *> TmpVec;
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +0000906 OrderAddedInstrns(AddedInstrnsBefore, TmpVec, PRA);
Ruchira Sasanka868cf822001-11-09 23:49:14 +0000907
Chris Lattner699683c2002-02-04 05:59:25 +0000908 if (DEBUG_RA) {
Ruchira Sasanka868cf822001-11-09 23:49:14 +0000909 cerr << "\nAfter reordering instrns: \n";
Chris Lattner699683c2002-02-04 05:59:25 +0000910 for(unsigned i = 0; i < TmpVec.size(); i++)
911 cerr << *TmpVec[i];
Ruchira Sasanka868cf822001-11-09 23:49:14 +0000912 }
913
914 // copy the results back from TmpVec to InstrnsBefore
915 for(unsigned i=0; i < TmpVec.size(); i++)
916 CallAI->InstrnsBefore.push_back( TmpVec[i] );
917 }
918
919
Ruchira Sasankad00982a2002-01-07 19:20:28 +0000920 // now insert caller saving code for this call instruction
921 //
922 insertCallerSavingCode(CallMI, BB, PRA);
923
Vikram S. Adve1c0fba62001-11-08 04:56:41 +0000924 // Reset optional args area again to be safe
Vikram S. Adve1c0fba62001-11-08 04:56:41 +0000925 PRA.mcInfo.resetOptionalArgs(target);
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000926}
927
Ruchira Sasanka91442282001-09-30 23:16:47 +0000928//---------------------------------------------------------------------------
929// This method is called for an LLVM return instruction to identify which
930// values will be returned from this method and to suggest colors.
931//---------------------------------------------------------------------------
Chris Lattner699683c2002-02-04 05:59:25 +0000932void UltraSparcRegInfo::suggestReg4RetValue(const MachineInstr *RetMI,
933 LiveRangeInfo &LRI) const {
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000934
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000935 assert( (UltraSparcInfo->getInstrInfo()).isReturn( RetMI->getOpCode() ) );
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000936
Ruchira Sasanka88dedc12001-10-23 21:40:39 +0000937 suggestReg4RetAddr(RetMI, LRI);
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000938
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000939 // if there is an implicit ref, that has to be the ret value
940 if( RetMI->getNumImplicitRefs() > 0 ) {
Ruchira Sasanka91442282001-09-30 23:16:47 +0000941
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000942 // The first implicit operand is the return value of a return instr
943 const Value *RetVal = RetMI->getImplicitRef(0);
Ruchira Sasanka91442282001-09-30 23:16:47 +0000944
Ruchira Sasanka91442282001-09-30 23:16:47 +0000945 LiveRange *const LR = LRI.getLiveRangeForValue( RetVal );
Ruchira Sasanka91442282001-09-30 23:16:47 +0000946
Chris Lattner0665a5f2002-02-05 01:43:49 +0000947 if (!LR) {
948 cerr << "\nNo LR for:" << RAV(RetVal) << "\n";
949 assert(0 && "No LR for return value of non-void method");
950 }
Ruchira Sasanka91442282001-09-30 23:16:47 +0000951
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000952 unsigned RegClassID = (LR->getRegClass())->getID();
Ruchira Sasanka91442282001-09-30 23:16:47 +0000953
Chris Lattner699683c2002-02-04 05:59:25 +0000954 if (RegClassID == IntRegClassID)
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000955 LR->setSuggestedColor(SparcIntRegOrder::i0);
Chris Lattner699683c2002-02-04 05:59:25 +0000956 else if (RegClassID == FloatRegClassID)
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000957 LR->setSuggestedColor(SparcFloatRegOrder::f0);
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +0000958 }
Ruchira Sasanka91442282001-09-30 23:16:47 +0000959}
960
Ruchira Sasanka91442282001-09-30 23:16:47 +0000961
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000962
963//---------------------------------------------------------------------------
964// Colors the return value of a method to %i0 or %f0, if possible. If it is
965// not possilbe to directly color the LR, insert a copy instruction to move
966// the LR to %i0 or %f0. When the LR is spilled, instead of the copy, we
967// have to put a load instruction.
Ruchira Sasanka91442282001-09-30 23:16:47 +0000968//---------------------------------------------------------------------------
Chris Lattner699683c2002-02-04 05:59:25 +0000969void UltraSparcRegInfo::colorRetValue(const MachineInstr *RetMI,
970 LiveRangeInfo &LRI,
971 AddedInstrns *RetAI) const {
Ruchira Sasanka91442282001-09-30 23:16:47 +0000972
Chris Lattner699683c2002-02-04 05:59:25 +0000973 assert((UltraSparcInfo->getInstrInfo()).isReturn( RetMI->getOpCode()));
Ruchira Sasanka91442282001-09-30 23:16:47 +0000974
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000975 // if there is an implicit ref, that has to be the ret value
Chris Lattner699683c2002-02-04 05:59:25 +0000976 if(RetMI->getNumImplicitRefs() > 0) {
Ruchira Sasanka91442282001-09-30 23:16:47 +0000977
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000978 // The first implicit operand is the return value of a return instr
979 const Value *RetVal = RetMI->getImplicitRef(0);
Ruchira Sasanka91442282001-09-30 23:16:47 +0000980
Chris Lattner699683c2002-02-04 05:59:25 +0000981 LiveRange *LR = LRI.getLiveRangeForValue(RetVal);
Ruchira Sasanka91442282001-09-30 23:16:47 +0000982
Chris Lattner0665a5f2002-02-05 01:43:49 +0000983 if (!LR) {
984 cerr << "\nNo LR for:" << RAV(RetVal) << "\n";
985 // assert( LR && "No LR for return value of non-void method");
986 return;
Ruchira Sasanka20c82b12001-10-28 18:15:12 +0000987 }
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +0000988
Ruchira Sasanka91442282001-09-30 23:16:47 +0000989 unsigned RegClassID = getRegClassIDOfValue(RetVal);
990 unsigned RegType = getRegType( RetVal );
Ruchira Sasanka88dedc12001-10-23 21:40:39 +0000991
Ruchira Sasanka88dedc12001-10-23 21:40:39 +0000992 unsigned CorrectCol;
Ruchira Sasanka91442282001-09-30 23:16:47 +0000993 if(RegClassID == IntRegClassID)
Ruchira Sasanka88dedc12001-10-23 21:40:39 +0000994 CorrectCol = SparcIntRegOrder::i0;
Ruchira Sasanka91442282001-09-30 23:16:47 +0000995 else if(RegClassID == FloatRegClassID)
Ruchira Sasanka88dedc12001-10-23 21:40:39 +0000996 CorrectCol = SparcFloatRegOrder::f0;
Chris Lattner8e5c0b42001-11-07 14:01:59 +0000997 else {
Chris Lattner699683c2002-02-04 05:59:25 +0000998 assert (0 && "Unknown RegClass");
Chris Lattner8e5c0b42001-11-07 14:01:59 +0000999 return;
1000 }
Ruchira Sasanka91442282001-09-30 23:16:47 +00001001
Ruchira Sasankac74a7202001-10-24 15:56:58 +00001002 // if the LR received the correct color, NOTHING to do
Ruchira Sasanka91442282001-09-30 23:16:47 +00001003
Chris Lattner699683c2002-02-04 05:59:25 +00001004 if (LR->hasColor() && LR->getColor() == CorrectCol)
1005 return;
Ruchira Sasanka88dedc12001-10-23 21:40:39 +00001006
Chris Lattner699683c2002-02-04 05:59:25 +00001007 unsigned UniRetReg = getUnifiedRegNum(RegClassID, CorrectCol);
Ruchira Sasanka91442282001-09-30 23:16:47 +00001008
Chris Lattner699683c2002-02-04 05:59:25 +00001009 if (LR->hasColor()) {
Ruchira Sasanka91442282001-09-30 23:16:47 +00001010
Ruchira Sasanka88dedc12001-10-23 21:40:39 +00001011 // We are here because the LR was allocted a regiter
1012 // It may be the suggested register or not
Ruchira Sasanka91442282001-09-30 23:16:47 +00001013
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +00001014 // copy the LR of retun value to i0 or f0
Ruchira Sasanka91442282001-09-30 23:16:47 +00001015
Ruchira Sasankacc3ccac2001-10-15 16:25:28 +00001016 unsigned UniLRReg =getUnifiedRegNum( RegClassID, LR->getColor());
Ruchira Sasanka91442282001-09-30 23:16:47 +00001017
Ruchira Sasankac74a7202001-10-24 15:56:58 +00001018 // the LR received UniLRReg but must be colored with UniRetReg
1019 // to pass as the return value
Chris Lattner697954c2002-01-20 22:54:45 +00001020 RetAI->InstrnsBefore.push_back(cpReg2RegMI(UniLRReg, UniRetReg, RegType));
Ruchira Sasanka91442282001-09-30 23:16:47 +00001021 }
Ruchira Sasanka20c82b12001-10-28 18:15:12 +00001022 else { // if the LR is spilled
Chris Lattner697954c2002-01-20 22:54:45 +00001023 MachineInstr *AdMI = cpMem2RegMI(getFramePointer(),
1024 LR->getSpillOffFromFP(),
1025 UniRetReg, RegType);
1026 RetAI->InstrnsBefore.push_back(AdMI);
1027 cerr << "\nCopied the return value from stack\n";
Ruchira Sasanka20c82b12001-10-28 18:15:12 +00001028 }
1029
Ruchira Sasanka91442282001-09-30 23:16:47 +00001030 } // if there is a return value
1031
1032}
1033
1034
1035//---------------------------------------------------------------------------
1036// Copy from a register to register. Register number must be the unified
1037// register number
1038//---------------------------------------------------------------------------
1039
Chris Lattner699683c2002-02-04 05:59:25 +00001040MachineInstr * UltraSparcRegInfo::cpReg2RegMI(unsigned SrcReg, unsigned DestReg,
1041 int RegType) const {
Ruchira Sasanka91442282001-09-30 23:16:47 +00001042
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001043 assert( ((int)SrcReg != InvalidRegNum) && ((int)DestReg != InvalidRegNum) &&
Ruchira Sasanka91442282001-09-30 23:16:47 +00001044 "Invalid Register");
1045
1046 MachineInstr * MI = NULL;
1047
1048 switch( RegType ) {
1049
1050 case IntRegType:
Ruchira Sasanka735d6e32001-10-18 22:38:52 +00001051 case IntCCRegType:
1052 case FloatCCRegType:
Ruchira Sasanka91442282001-09-30 23:16:47 +00001053 MI = new MachineInstr(ADD, 3);
Vikram S. Advef1c15ee2002-03-18 03:12:16 +00001054 MI->SetMachineOperandReg(0, SrcReg, false);
1055 MI->SetMachineOperandReg(1, this->getZeroRegNum(), false);
1056 MI->SetMachineOperandReg(2, DestReg, true);
Ruchira Sasanka91442282001-09-30 23:16:47 +00001057 break;
1058
1059 case FPSingleRegType:
1060 MI = new MachineInstr(FMOVS, 2);
Vikram S. Advef1c15ee2002-03-18 03:12:16 +00001061 MI->SetMachineOperandReg(0, SrcReg, false);
1062 MI->SetMachineOperandReg(1, DestReg, true);
Ruchira Sasanka91442282001-09-30 23:16:47 +00001063 break;
1064
1065 case FPDoubleRegType:
1066 MI = new MachineInstr(FMOVD, 2);
Vikram S. Advef1c15ee2002-03-18 03:12:16 +00001067 MI->SetMachineOperandReg(0, SrcReg, false);
1068 MI->SetMachineOperandReg(1, DestReg, true);
Ruchira Sasanka91442282001-09-30 23:16:47 +00001069 break;
1070
1071 default:
1072 assert(0 && "Unknow RegType");
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +00001073 }
1074
1075 return MI;
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +00001076}
Chris Lattner20b1ea02001-09-14 03:47:57 +00001077
1078
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001079//---------------------------------------------------------------------------
Ruchira Sasanka7dcd6122001-10-24 22:05:34 +00001080// Copy from a register to memory (i.e., Store). Register number must
1081// be the unified register number
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001082//---------------------------------------------------------------------------
1083
1084
Chris Lattner699683c2002-02-04 05:59:25 +00001085MachineInstr * UltraSparcRegInfo::cpReg2MemMI(unsigned SrcReg,
1086 unsigned DestPtrReg,
1087 int Offset, int RegType) const {
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001088 MachineInstr * MI = NULL;
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001089 switch( RegType ) {
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001090 case IntRegType:
Ruchira Sasanka735d6e32001-10-18 22:38:52 +00001091 case FloatCCRegType:
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001092 MI = new MachineInstr(STX, 3);
Vikram S. Advef1c15ee2002-03-18 03:12:16 +00001093 MI->SetMachineOperandReg(0, SrcReg, false);
1094 MI->SetMachineOperandReg(1, DestPtrReg, false);
1095 MI->SetMachineOperandConst(2, MachineOperand:: MO_SignExtendedImmed,
1096 (int64_t) Offset);
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001097 break;
1098
1099 case FPSingleRegType:
1100 MI = new MachineInstr(ST, 3);
Vikram S. Advef1c15ee2002-03-18 03:12:16 +00001101 MI->SetMachineOperandReg(0, SrcReg, false);
1102 MI->SetMachineOperandReg(1, DestPtrReg, false);
1103 MI->SetMachineOperandConst(2, MachineOperand:: MO_SignExtendedImmed,
1104 (int64_t) Offset);
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001105 break;
1106
1107 case FPDoubleRegType:
1108 MI = new MachineInstr(STD, 3);
Vikram S. Advef1c15ee2002-03-18 03:12:16 +00001109 MI->SetMachineOperandReg(0, SrcReg, false);
1110 MI->SetMachineOperandReg(1, DestPtrReg, false);
1111 MI->SetMachineOperandConst(2, MachineOperand:: MO_SignExtendedImmed,
1112 (int64_t) Offset);
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001113 break;
1114
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001115 case IntCCRegType:
1116 assert( 0 && "Cannot directly store %ccr to memory");
1117
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001118 default:
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001119 assert(0 && "Unknow RegType in cpReg2MemMI");
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001120 }
1121
1122 return MI;
1123}
1124
1125
1126//---------------------------------------------------------------------------
Ruchira Sasanka7dcd6122001-10-24 22:05:34 +00001127// Copy from memory to a reg (i.e., Load) Register number must be the unified
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001128// register number
1129//---------------------------------------------------------------------------
1130
1131
Chris Lattner699683c2002-02-04 05:59:25 +00001132MachineInstr * UltraSparcRegInfo::cpMem2RegMI(unsigned SrcPtrReg,
1133 int Offset,
1134 unsigned DestReg,
1135 int RegType) const {
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001136 MachineInstr * MI = NULL;
Chris Lattner699683c2002-02-04 05:59:25 +00001137 switch (RegType) {
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001138 case IntRegType:
Ruchira Sasanka735d6e32001-10-18 22:38:52 +00001139 case FloatCCRegType:
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001140 MI = new MachineInstr(LDX, 3);
Vikram S. Advef1c15ee2002-03-18 03:12:16 +00001141 MI->SetMachineOperandReg(0, SrcPtrReg, false);
1142 MI->SetMachineOperandConst(1, MachineOperand:: MO_SignExtendedImmed,
1143 (int64_t) Offset);
1144 MI->SetMachineOperandReg(2, DestReg, true);
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001145 break;
1146
1147 case FPSingleRegType:
1148 MI = new MachineInstr(LD, 3);
Vikram S. Advef1c15ee2002-03-18 03:12:16 +00001149 MI->SetMachineOperandReg(0, SrcPtrReg, false);
1150 MI->SetMachineOperandConst(1, MachineOperand:: MO_SignExtendedImmed,
1151 (int64_t) Offset);
1152 MI->SetMachineOperandReg(2, DestReg, true);
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001153
1154 break;
1155
1156 case FPDoubleRegType:
1157 MI = new MachineInstr(LDD, 3);
Vikram S. Advef1c15ee2002-03-18 03:12:16 +00001158 MI->SetMachineOperandReg(0, SrcPtrReg, false);
1159 MI->SetMachineOperandConst(1, MachineOperand:: MO_SignExtendedImmed,
1160 (int64_t) Offset);
1161 MI->SetMachineOperandReg(2, DestReg, true);
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001162 break;
1163
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001164 case IntCCRegType:
1165 assert( 0 && "Cannot directly load into %ccr from memory");
1166
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001167 default:
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001168 assert(0 && "Unknown RegType in cpMem2RegMI");
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001169 }
1170
1171 return MI;
1172}
1173
1174
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001175
1176
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001177
Ruchira Sasanka67a463a2001-11-12 14:45:33 +00001178//---------------------------------------------------------------------------
1179// Generate a copy instruction to copy a value to another. Temporarily
1180// used by PhiElimination code.
1181//---------------------------------------------------------------------------
1182
1183
Chris Lattner699683c2002-02-04 05:59:25 +00001184MachineInstr *UltraSparcRegInfo::cpValue2Value(Value *Src, Value *Dest) const {
Ruchira Sasanka67a463a2001-11-12 14:45:33 +00001185 int RegType = getRegType( Src );
1186
1187 assert( (RegType==getRegType(Src)) && "Src & Dest are diff types");
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001188
Ruchira Sasankaef1b0cb2001-11-03 17:13:27 +00001189 MachineInstr * MI = NULL;
1190
Ruchira Sasanka67a463a2001-11-12 14:45:33 +00001191 switch( RegType ) {
Ruchira Sasanka67a463a2001-11-12 14:45:33 +00001192 case IntRegType:
Ruchira Sasanka67a463a2001-11-12 14:45:33 +00001193 MI = new MachineInstr(ADD, 3);
Vikram S. Advef1c15ee2002-03-18 03:12:16 +00001194 MI->SetMachineOperandVal(0, MachineOperand:: MO_VirtualRegister, Src, false);
1195 MI->SetMachineOperandReg(1, this->getZeroRegNum(), false);
1196 MI->SetMachineOperandVal(2, MachineOperand:: MO_VirtualRegister, Dest, true);
Ruchira Sasanka67a463a2001-11-12 14:45:33 +00001197 break;
1198
1199 case FPSingleRegType:
1200 MI = new MachineInstr(FMOVS, 2);
Vikram S. Advef1c15ee2002-03-18 03:12:16 +00001201 MI->SetMachineOperandVal(0, MachineOperand:: MO_VirtualRegister, Src, false);
1202 MI->SetMachineOperandVal(1, MachineOperand:: MO_VirtualRegister, Dest, true);
Ruchira Sasanka67a463a2001-11-12 14:45:33 +00001203 break;
1204
1205
1206 case FPDoubleRegType:
1207 MI = new MachineInstr(FMOVD, 2);
Vikram S. Advef1c15ee2002-03-18 03:12:16 +00001208 MI->SetMachineOperandVal(0, MachineOperand:: MO_VirtualRegister, Src, false);
1209 MI->SetMachineOperandVal(1, MachineOperand:: MO_VirtualRegister, Dest, true);
Ruchira Sasanka67a463a2001-11-12 14:45:33 +00001210 break;
1211
1212 default:
1213 assert(0 && "Unknow RegType in CpValu2Value");
1214 }
Ruchira Sasankaef1b0cb2001-11-03 17:13:27 +00001215
1216 return MI;
Ruchira Sasankaef1b0cb2001-11-03 17:13:27 +00001217}
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001218
1219
1220
Ruchira Sasanka67a463a2001-11-12 14:45:33 +00001221
1222
1223
Ruchira Sasanka20c82b12001-10-28 18:15:12 +00001224//----------------------------------------------------------------------------
1225// This method inserts caller saving/restoring instructons before/after
Ruchira Sasankabf915522002-01-07 21:03:42 +00001226// a call machine instruction. The caller saving/restoring instructions are
1227// inserted like:
1228//
1229// ** caller saving instructions
1230// other instructions inserted for the call by ColorCallArg
1231// CALL instruction
1232// other instructions inserted for the call ColorCallArg
1233// ** caller restoring instructions
1234//
Ruchira Sasanka20c82b12001-10-28 18:15:12 +00001235//----------------------------------------------------------------------------
Ruchira Sasankac4d4b762001-10-16 01:23:19 +00001236
Ruchira Sasanka91442282001-09-30 23:16:47 +00001237
Ruchira Sasanka20c82b12001-10-28 18:15:12 +00001238void UltraSparcRegInfo::insertCallerSavingCode(const MachineInstr *MInst,
1239 const BasicBlock *BB,
1240 PhyRegAlloc &PRA) const {
Ruchira Sasanka91442282001-09-30 23:16:47 +00001241
Ruchira Sasankabf915522002-01-07 21:03:42 +00001242 // has set to record which registers were saved/restored
1243 //
Chris Lattner697954c2002-01-20 22:54:45 +00001244 std::hash_set<unsigned> PushedRegSet;
Ruchira Sasankabf915522002-01-07 21:03:42 +00001245
Ruchira Sasanka20c82b12001-10-28 18:15:12 +00001246 // Now find the LR of the return value of the call
1247 // The last *implicit operand* is the return value of a call
1248 // Insert it to to he PushedRegSet since we must not save that register
1249 // and restore it after the call.
1250 // We do this because, we look at the LV set *after* the instruction
1251 // to determine, which LRs must be saved across calls. The return value
1252 // of the call is live in this set - but we must not save/restore it.
Ruchira Sasanka91442282001-09-30 23:16:47 +00001253
1254
Ruchira Sasanka20c82b12001-10-28 18:15:12 +00001255 const Value *RetVal = getCallInstRetVal( MInst );
Ruchira Sasanka91442282001-09-30 23:16:47 +00001256
Chris Lattner699683c2002-02-04 05:59:25 +00001257 if (RetVal) {
Ruchira Sasanka20c82b12001-10-28 18:15:12 +00001258 LiveRange *RetValLR = PRA.LRI.getLiveRangeForValue( RetVal );
Chris Lattner699683c2002-02-04 05:59:25 +00001259 assert(RetValLR && "No LR for RetValue of call");
Ruchira Sasanka91442282001-09-30 23:16:47 +00001260
Chris Lattner699683c2002-02-04 05:59:25 +00001261 if (RetValLR->hasColor())
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001262 PushedRegSet.insert(
1263 getUnifiedRegNum((RetValLR->getRegClass())->getID(),
Ruchira Sasanka20c82b12001-10-28 18:15:12 +00001264 RetValLR->getColor() ) );
Ruchira Sasanka91442282001-09-30 23:16:47 +00001265 }
1266
1267
Chris Lattner748697d2002-02-05 04:20:12 +00001268 const ValueSet &LVSetAft = PRA.LVI->getLiveVarSetAfterMInst(MInst, BB);
1269 ValueSet::const_iterator LIt = LVSetAft.begin();
Ruchira Sasanka91442282001-09-30 23:16:47 +00001270
Ruchira Sasanka20c82b12001-10-28 18:15:12 +00001271 // for each live var in live variable set after machine inst
Chris Lattner748697d2002-02-05 04:20:12 +00001272 for( ; LIt != LVSetAft.end(); ++LIt) {
Ruchira Sasanka20c82b12001-10-28 18:15:12 +00001273
1274 // get the live range corresponding to live var
1275 LiveRange *const LR = PRA.LRI.getLiveRangeForValue(*LIt );
1276
1277 // LR can be null if it is a const since a const
1278 // doesn't have a dominating def - see Assumptions above
1279 if( LR ) {
1280
1281 if( LR->hasColor() ) {
1282
1283 unsigned RCID = (LR->getRegClass())->getID();
1284 unsigned Color = LR->getColor();
1285
1286 if ( isRegVolatile(RCID, Color) ) {
1287
1288 // if the value is in both LV sets (i.e., live before and after
1289 // the call machine instruction)
1290
1291 unsigned Reg = getUnifiedRegNum(RCID, Color);
1292
1293 if( PushedRegSet.find(Reg) == PushedRegSet.end() ) {
1294
1295 // if we haven't already pushed that register
1296
1297 unsigned RegType = getRegType( LR );
1298
1299 // Now get two instructions - to push on stack and pop from stack
1300 // and add them to InstrnsBefore and InstrnsAfter of the
1301 // call instruction
1302
Ruchira Sasankad00982a2002-01-07 19:20:28 +00001303
1304 int StackOff = PRA.mcInfo.pushTempValue(target,
1305 getSpilledRegSize(RegType));
1306
Vikram S. Adve1c0fba62001-11-08 04:56:41 +00001307
Vikram S. Advef1c15ee2002-03-18 03:12:16 +00001308 MachineInstr *AdIBefCC=NULL, *AdIAftCC=NULL, *AdICpCC;
1309 MachineInstr *AdIBef=NULL, *AdIAft=NULL;
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001310
1311 //---- Insert code for pushing the reg on stack ----------
1312
1313 if( RegType == IntCCRegType ) {
1314
1315 // Handle IntCCRegType specially since we cannot directly
1316 // push %ccr on to the stack
1317
Chris Lattner748697d2002-02-05 04:20:12 +00001318 const ValueSet &LVSetBef =
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001319 PRA.LVI->getLiveVarSetBeforeMInst(MInst, BB);
1320
1321 // get a free INTEGER register
1322 int FreeIntReg =
Vikram S. Advef1c15ee2002-03-18 03:12:16 +00001323 PRA.getUsableUniRegAtMI(PRA.getRegClassByID(IntRegClassID) /*LR->getRegClass()*/,
1324 IntRegType, MInst, &LVSetBef, AdIBefCC, AdIAftCC);
1325
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001326 // insert the instructions in reverse order since we are
1327 // adding them to the front of InstrnsBefore
1328
1329 if(AdIAftCC)
Chris Lattner0b0ffa02002-04-09 05:13:04 +00001330 PRA.AddedInstrMap[MInst].InstrnsBefore.push_front(AdIAftCC);
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001331
1332 AdICpCC = cpCCR2IntMI(FreeIntReg);
Chris Lattner0b0ffa02002-04-09 05:13:04 +00001333 PRA.AddedInstrMap[MInst].InstrnsBefore.push_front(AdICpCC);
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001334
1335 if(AdIBefCC)
Chris Lattner0b0ffa02002-04-09 05:13:04 +00001336 PRA.AddedInstrMap[MInst].InstrnsBefore.push_front(AdIBefCC);
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001337
Ruchira Sasankaaa12a782001-11-10 00:26:55 +00001338 if(DEBUG_RA) {
1339 cerr << "\n!! Inserted caller saving (push) inst for %ccr:";
1340 if(AdIBefCC) cerr << "\t" << *(AdIBefCC);
1341 cerr << "\t" << *AdICpCC;
1342 if(AdIAftCC) cerr << "\t" << *(AdIAftCC);
1343 }
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001344
1345 } else {
1346 // for any other register type, just add the push inst
Ruchira Sasanka6beb0132001-11-11 21:49:37 +00001347 AdIBef = cpReg2MemMI(Reg, getFramePointer(), StackOff, RegType );
Chris Lattner0b0ffa02002-04-09 05:13:04 +00001348 PRA.AddedInstrMap[MInst].InstrnsBefore.push_front(AdIBef);
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001349 }
1350
1351
1352 //---- Insert code for popping the reg from the stack ----------
1353
Chris Lattner748697d2002-02-05 04:20:12 +00001354 if (RegType == IntCCRegType) {
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001355
1356 // Handle IntCCRegType specially since we cannot directly
1357 // pop %ccr on from the stack
1358
1359 // get a free INT register
1360 int FreeIntReg =
Vikram S. Advef1c15ee2002-03-18 03:12:16 +00001361 PRA.getUsableUniRegAtMI(PRA.getRegClassByID(IntRegClassID) /* LR->getRegClass()*/,
1362 IntRegType, MInst, &LVSetAft, AdIBefCC, AdIAftCC);
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001363
1364 if(AdIBefCC)
Chris Lattner0b0ffa02002-04-09 05:13:04 +00001365 PRA.AddedInstrMap[MInst].InstrnsAfter.push_back(AdIBefCC);
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001366
1367 AdICpCC = cpInt2CCRMI(FreeIntReg);
Chris Lattner0b0ffa02002-04-09 05:13:04 +00001368 PRA.AddedInstrMap[MInst].InstrnsAfter.push_back(AdICpCC);
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001369
1370 if(AdIAftCC)
Chris Lattner0b0ffa02002-04-09 05:13:04 +00001371 PRA.AddedInstrMap[MInst].InstrnsAfter.push_back(AdIAftCC);
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001372
Ruchira Sasankaaa12a782001-11-10 00:26:55 +00001373 if(DEBUG_RA) {
1374
1375 cerr << "\n!! Inserted caller saving (pop) inst for %ccr:";
1376 if(AdIBefCC) cerr << "\t" << *(AdIBefCC);
1377 cerr << "\t" << *AdICpCC;
1378 if(AdIAftCC) cerr << "\t" << *(AdIAftCC);
1379 }
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001380
1381 } else {
1382 // for any other register type, just add the pop inst
Ruchira Sasanka6beb0132001-11-11 21:49:37 +00001383 AdIAft = cpMem2RegMI(getFramePointer(), StackOff, Reg, RegType );
Chris Lattner0b0ffa02002-04-09 05:13:04 +00001384 PRA.AddedInstrMap[MInst].InstrnsAfter.push_back(AdIAft);
Ruchira Sasanka20c82b12001-10-28 18:15:12 +00001385 }
Ruchira Sasanka20c82b12001-10-28 18:15:12 +00001386
Chris Lattner748697d2002-02-05 04:20:12 +00001387 PushedRegSet.insert(Reg);
Ruchira Sasanka20c82b12001-10-28 18:15:12 +00001388
Ruchira Sasankaaa12a782001-11-10 00:26:55 +00001389 if(DEBUG_RA) {
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001390 cerr << "\nFor call inst:" << *MInst;
Ruchira Sasankaaa12a782001-11-10 00:26:55 +00001391 cerr << " -inserted caller saving instrs:\n\t ";
Vikram S. Advef1c15ee2002-03-18 03:12:16 +00001392 if( RegType == IntCCRegType ) {
1393 if(AdIBefCC) cerr << *AdIBefCC << "\t";
1394 if(AdIAftCC) cerr << *AdIAftCC;
1395 }
1396 else {
1397 if(AdIBef) cerr << *AdIBef << "\t";
1398 if(AdIAft) cerr << *AdIAft;
1399 }
Ruchira Sasanka20c82b12001-10-28 18:15:12 +00001400 }
1401 } // if not already pushed
1402
1403 } // if LR has a volatile color
1404
1405 } // if LR has color
1406
1407 } // if there is a LR for Var
Ruchira Sasanka91442282001-09-30 23:16:47 +00001408
Ruchira Sasanka20c82b12001-10-28 18:15:12 +00001409 } // for each value in the LV set after instruction
1410
Ruchira Sasanka91442282001-09-30 23:16:47 +00001411}
1412
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001413//---------------------------------------------------------------------------
1414// Copies %ccr into an integer register. IntReg is the UNIFIED register
1415// number.
1416//---------------------------------------------------------------------------
Ruchira Sasanka91442282001-09-30 23:16:47 +00001417
Chris Lattner699683c2002-02-04 05:59:25 +00001418MachineInstr * UltraSparcRegInfo::cpCCR2IntMI(unsigned IntReg) const {
1419 MachineInstr * MI = new MachineInstr(RDCCR, 2);
Vikram S. Advef1c15ee2002-03-18 03:12:16 +00001420 MI->SetMachineOperandReg(0, this->getUnifiedRegNum(UltraSparcRegInfo::IntCCRegClassID,
1421 SparcIntCCRegOrder::ccr),
1422 false, true);
1423 MI->SetMachineOperandReg(1, IntReg, true);
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001424 return MI;
1425}
Ruchira Sasanka91442282001-09-30 23:16:47 +00001426
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001427//---------------------------------------------------------------------------
1428// Copies an integer register into %ccr. IntReg is the UNIFIED register
1429// number.
1430//---------------------------------------------------------------------------
1431
Chris Lattner699683c2002-02-04 05:59:25 +00001432MachineInstr *UltraSparcRegInfo::cpInt2CCRMI(unsigned IntReg) const {
1433 MachineInstr *MI = new MachineInstr(WRCCR, 3);
Vikram S. Advef1c15ee2002-03-18 03:12:16 +00001434 MI->SetMachineOperandReg(0, IntReg, false);
1435 MI->SetMachineOperandReg(1, this->getZeroRegNum(), false);
1436 MI->SetMachineOperandReg(2, this->getUnifiedRegNum(UltraSparcRegInfo::IntCCRegClassID, SparcIntCCRegOrder::ccr),
1437 true, true);
Ruchira Sasanka3839e6e2001-11-03 19:59:59 +00001438 return MI;
1439}
Ruchira Sasanka91442282001-09-30 23:16:47 +00001440
1441
Ruchira Sasanka20c82b12001-10-28 18:15:12 +00001442
1443
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +00001444//---------------------------------------------------------------------------
1445// Print the register assigned to a LR
1446//---------------------------------------------------------------------------
1447
Chris Lattner699683c2002-02-04 05:59:25 +00001448void UltraSparcRegInfo::printReg(const LiveRange *LR) {
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +00001449 unsigned RegClassID = (LR->getRegClass())->getID();
Chris Lattner1e23ed72001-10-15 18:15:27 +00001450 cerr << " *Node " << (LR->getUserIGNode())->getIndex();
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +00001451
Chris Lattner699683c2002-02-04 05:59:25 +00001452 if (!LR->hasColor()) {
Chris Lattner697954c2002-01-20 22:54:45 +00001453 cerr << " - could not find a color\n";
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +00001454 return;
1455 }
1456
1457 // if a color is found
1458
Chris Lattner1e23ed72001-10-15 18:15:27 +00001459 cerr << " colored with color "<< LR->getColor();
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +00001460
Chris Lattner699683c2002-02-04 05:59:25 +00001461 if (RegClassID == IntRegClassID) {
Chris Lattner697954c2002-01-20 22:54:45 +00001462 cerr<< " [" << SparcIntRegOrder::getRegName(LR->getColor()) << "]\n";
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +00001463
Chris Lattner699683c2002-02-04 05:59:25 +00001464 } else if (RegClassID == FloatRegClassID) {
Chris Lattner1e23ed72001-10-15 18:15:27 +00001465 cerr << "[" << SparcFloatRegOrder::getRegName(LR->getColor());
Chris Lattner37730942002-02-05 03:52:29 +00001466 if( LR->getType() == Type::DoubleTy)
Chris Lattner1e23ed72001-10-15 18:15:27 +00001467 cerr << "+" << SparcFloatRegOrder::getRegName(LR->getColor()+1);
Chris Lattner697954c2002-01-20 22:54:45 +00001468 cerr << "]\n";
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +00001469 }
Ruchira Sasanka89fb46b2001-09-18 22:52:44 +00001470}
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001471
1472//---------------------------------------------------------------------------
1473// This method examines instructions inserted by RegAlloc code before a
1474// machine instruction to detect invalid orders that destroy values before
1475// they are used. If it detects such conditions, it reorders the instructions.
1476//
1477// The unordered instructions come in the UnordVec. These instructions are
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001478// instructions inserted by RegAlloc. All such instruction MUST have
1479// their USES BEFORE THE DEFS after reordering.
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001480
1481// The UnordVec & OrdVec must be DISTINCT. The OrdVec must be empty when
1482// this method is called.
1483
1484// This method uses two vectors for efficiency in accessing
1485
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001486// Since instructions are inserted in RegAlloc, this assumes that the
1487// first operand is the source reg and the last operand is the dest reg.
1488
1489// All the uses are before THE def to a register
1490
1491
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001492//---------------------------------------------------------------------------
Chris Lattner697954c2002-01-20 22:54:45 +00001493void UltraSparcRegInfo::OrderAddedInstrns(std::vector<MachineInstr *> &UnordVec,
1494 std::vector<MachineInstr *> &OrdVec,
1495 PhyRegAlloc &PRA) const{
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001496
1497 /*
1498 Problem: We can have instructions inserted by RegAlloc like
1499 1. add %ox %g0 %oy
1500 2. add %oy %g0 %oz, where z!=x or z==x
1501
1502 This is wrong since %oy used by 2 is overwritten by 1
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001503
1504 Solution:
1505 We re-order the instructions so that the uses are before the defs
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001506
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001507 Algorithm:
1508
1509 do
1510 for each instruction 'DefInst' in the UnOrdVec
1511 for each instruction 'UseInst' that follows the DefInst
1512 if the reg defined by DefInst is used by UseInst
1513 mark DefInst as not movable in this iteration
1514 If DefInst is not marked as not-movable, move DefInst to OrdVec
1515 while all instructions in DefInst are moved to OrdVec
1516
1517 For moving, we call the move2OrdVec(). It checks whether there is a def
1518 in it for the uses in the instruction to be added to OrdVec. If there
1519 are no preceding defs, it just appends the instruction. If there is a
1520 preceding def, it puts two instructions to save the reg on stack before
1521 the load and puts a restore at use.
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001522
1523 */
1524
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001525 bool CouldMoveAll;
1526 bool DebugPrint = false;
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001527
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001528 do {
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001529 CouldMoveAll = true;
Chris Lattner697954c2002-01-20 22:54:45 +00001530 std::vector<MachineInstr *>::iterator DefIt = UnordVec.begin();
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001531
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001532 for( ; DefIt != UnordVec.end(); ++DefIt ) {
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001533
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001534 // for each instruction in the UnordVec do ...
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001535
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001536 MachineInstr *DefInst = *DefIt;
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001537
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001538 if( DefInst == NULL) continue;
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001539
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001540 //cerr << "\nInst in UnordVec = " << *DefInst;
1541
1542 // last operand is the def (unless for a store which has no def reg)
1543 MachineOperand& DefOp = DefInst->getOperand(DefInst->getNumOperands()-1);
1544
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001545 if( DefOp.opIsDef() &&
1546 DefOp.getOperandType() == MachineOperand::MO_MachineRegister) {
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001547
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001548 // If the operand in DefInst is a def ...
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001549
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001550 bool DefEqUse = false;
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001551
Chris Lattner697954c2002-01-20 22:54:45 +00001552 std::vector<MachineInstr *>::iterator UseIt = DefIt;
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001553 UseIt++;
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001554
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001555 for( ; UseIt != UnordVec.end(); ++UseIt ) {
1556
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001557 MachineInstr *UseInst = *UseIt;
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001558 if( UseInst == NULL) continue;
1559
1560 // for each inst (UseInst) that is below the DefInst do ...
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001561 MachineOperand& UseOp = UseInst->getOperand(0);
1562
1563 if( ! UseOp.opIsDef() &&
1564 UseOp.getOperandType() == MachineOperand::MO_MachineRegister) {
1565
1566 // if use is a register ...
1567
1568 if( DefOp.getMachineRegNum() == UseOp.getMachineRegNum() ) {
1569
1570 // if Def and this use are the same, it means that this use
1571 // is destroyed by a def before it is used
1572
1573 // cerr << "\nCouldn't move " << *DefInst;
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001574
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001575 DefEqUse = true;
1576 CouldMoveAll = false;
1577 DebugPrint = true;
1578 break;
1579 } // if two registers are equal
1580
1581 } // if use is a register
1582
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001583 }// for all use instructions
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001584
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001585 if( ! DefEqUse ) {
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001586
1587 // after examining all the instructions that follow the DefInst
1588 // if there are no dependencies, we can move it to the OrdVec
1589
1590 // cerr << "Moved to Ord: " << *DefInst;
1591
1592 moveInst2OrdVec(OrdVec, DefInst, PRA);
1593
1594 //OrdVec.push_back(DefInst);
1595
1596 // mark the pos of DefInst with NULL to indicate that it is
1597 // empty
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001598 *DefIt = NULL;
1599 }
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001600
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001601 } // if Def is a machine register
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001602
1603 } // for all instructions in the UnordVec
1604
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001605
Chris Lattner699683c2002-02-04 05:59:25 +00001606 } while(!CouldMoveAll);
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001607
Chris Lattner699683c2002-02-04 05:59:25 +00001608 if (DebugPrint) {
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001609 cerr << "\nAdded instructions were reordered to:\n";
1610 for(unsigned int i=0; i < OrdVec.size(); i++)
1611 cerr << *(OrdVec[i]);
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001612 }
Ruchira Sasanka868cf822001-11-09 23:49:14 +00001613}
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001614
1615
1616
1617
1618
Chris Lattner697954c2002-01-20 22:54:45 +00001619void UltraSparcRegInfo::moveInst2OrdVec(std::vector<MachineInstr *> &OrdVec,
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001620 MachineInstr *UnordInst,
Chris Lattner699683c2002-02-04 05:59:25 +00001621 PhyRegAlloc &PRA) const {
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001622 MachineOperand& UseOp = UnordInst->getOperand(0);
1623
1624 if( ! UseOp.opIsDef() &&
1625 UseOp.getOperandType() == MachineOperand::MO_MachineRegister) {
1626
1627 // for the use of UnordInst, see whether there is a defining instr
1628 // before in the OrdVec
1629 bool DefEqUse = false;
1630
Chris Lattner697954c2002-01-20 22:54:45 +00001631 std::vector<MachineInstr *>::iterator OrdIt = OrdVec.begin();
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001632
1633 for( ; OrdIt != OrdVec.end(); ++OrdIt ) {
1634
1635 MachineInstr *OrdInst = *OrdIt ;
1636
1637 MachineOperand& DefOp =
1638 OrdInst->getOperand(OrdInst->getNumOperands()-1);
1639
1640 if( DefOp.opIsDef() &&
1641 DefOp.getOperandType() == MachineOperand::MO_MachineRegister) {
1642
1643 //cerr << "\nDefining Ord Inst: " << *OrdInst;
1644
1645 if( DefOp.getMachineRegNum() == UseOp.getMachineRegNum() ) {
1646
1647 // we are here because there is a preceding def in the OrdVec
1648 // for the use in this intr we are going to insert. This
1649 // happened because the original code was like:
1650 // 1. add %ox %g0 %oy
1651 // 2. add %oy %g0 %ox
1652 // In Round1, we added 2 to OrdVec but 1 remained in UnordVec
1653 // Now we are processing %ox of 1.
1654 // We have to
1655
1656 const int UReg = DefOp.getMachineRegNum();
1657 const int RegType = getRegType(UReg);
1658 MachineInstr *AdIBef, *AdIAft;
1659
Ruchira Sasankad00982a2002-01-07 19:20:28 +00001660 const int StackOff = PRA.mcInfo.pushTempValue(target,
1661 getSpilledRegSize(RegType));
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001662
1663 // Save the UReg (%ox) on stack before it's destroyed
Ruchira Sasanka6beb0132001-11-11 21:49:37 +00001664 AdIBef=cpReg2MemMI(UReg, getFramePointer(), StackOff, RegType);
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001665 OrdIt = OrdVec.insert( OrdIt, AdIBef);
1666 OrdIt++; // points to current instr we processed
1667
1668 // Load directly into DReg (%oy)
1669 MachineOperand& DOp=
1670 (UnordInst->getOperand(UnordInst->getNumOperands()-1));
1671 assert(DOp.opIsDef() && "Last operand is not the def");
1672 const int DReg = DOp.getMachineRegNum();
1673
Ruchira Sasanka6beb0132001-11-11 21:49:37 +00001674 AdIAft=cpMem2RegMI(getFramePointer(), StackOff, DReg, RegType);
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001675 OrdVec.push_back(AdIAft);
1676
1677 cerr << "\nFixed CIRCULAR references by reordering";
1678
1679 if( DEBUG_RA ) {
1680 cerr << "\nBefore CIRCULAR Reordering:\n";
1681 cerr << *UnordInst;
1682 cerr << *OrdInst;
1683
1684 cerr << "\nAfter CIRCULAR Reordering - All Inst so far:\n";
1685 for(unsigned i=0; i < OrdVec.size(); i++)
1686 cerr << *(OrdVec[i]);
1687 }
1688
1689 // Do not copy the UseInst to OrdVec
1690 DefEqUse = true;
1691 break;
1692
1693 }// if two registers are equal
1694
1695 } // if Def is a register
1696
1697 } // for each instr in OrdVec
1698
Chris Lattner699683c2002-02-04 05:59:25 +00001699 if(!DefEqUse) {
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001700
1701 // We didn't find a def in the OrdVec, so just append this inst
1702 OrdVec.push_back( UnordInst );
1703 //cerr << "Reordered Inst (Moved Dn): " << *UnordInst;
1704 }
1705
1706 }// if the operand in UnordInst is a use
Ruchira Sasankaae4bcd72001-11-10 21:20:43 +00001707}