34dd83b49e0b85ce236918723d0c246dfa920c17
[oota-llvm.git] / lib / Target / SparcV9 / InstrSelection / InstrSelectionSupport.cpp
1 // $Id$ -*-c++-*-
2 //***************************************************************************
3 // File:
4 //      InstrSelectionSupport.h
5 // 
6 // Purpose:
7 //      Target-independent instruction selection code.
8 //      See SparcInstrSelection.cpp for usage.
9 //      
10 // History:
11 //      10/10/01         -  Vikram Adve  -  Created
12 //**************************************************************************/
13
14 #include "llvm/CodeGen/InstrSelectionSupport.h"
15 #include "llvm/CodeGen/InstrSelection.h"
16 #include "llvm/CodeGen/MachineInstr.h"
17 #include "llvm/Target/TargetMachine.h"
18 #include "llvm/Target/MachineRegInfo.h"
19 #include "llvm/ConstantVals.h"
20 #include "llvm/Method.h"
21 #include "llvm/BasicBlock.h"
22 #include "llvm/Instruction.h"
23 #include "llvm/Type.h"
24 #include "llvm/iMemory.h"
25 using std::vector;
26
27 //*************************** Local Functions ******************************/
28
29
30 static TmpInstruction*
31 InsertCodeToLoadConstant(Value* opValue,
32                          Instruction* vmInstr,
33                          vector<MachineInstr*>& loadConstVec,
34                          TargetMachine& target)
35 {
36   vector<TmpInstruction*> tempVec;
37   
38   // Create a tmp virtual register to hold the constant.
39   TmpInstruction* tmpReg =
40     new TmpInstruction(TMP_INSTRUCTION_OPCODE, opValue, NULL);
41   vmInstr->getMachineInstrVec().addTempValue(tmpReg);
42   
43   target.getInstrInfo().CreateCodeToLoadConst(opValue, tmpReg,
44                                               loadConstVec, tempVec);
45   
46   // Register the new tmp values created for this m/c instruction sequence
47   for (unsigned i=0; i < tempVec.size(); i++)
48     vmInstr->getMachineInstrVec().addTempValue(tempVec[i]);
49   
50   // Record the mapping from the tmp VM instruction to machine instruction.
51   // Do this for all machine instructions that were not mapped to any
52   // other temp values created by 
53   // tmpReg->addMachineInstruction(loadConstVec.back());
54   
55   return tmpReg;
56 }
57
58
59 //---------------------------------------------------------------------------
60 // Function GetConstantValueAsSignedInt
61 // 
62 // Convenience function to get the value of an integer constant, for an
63 // appropriate integer or non-integer type that can be held in an integer.
64 // The type of the argument must be the following:
65 //      Signed or unsigned integer
66 //      Boolean
67 //      Pointer
68 // 
69 // isValidConstant is set to true if a valid constant was found.
70 //---------------------------------------------------------------------------
71
72 int64_t
73 GetConstantValueAsSignedInt(const Value *V,
74                             bool &isValidConstant)
75 {
76   if (!isa<Constant>(V))
77     {
78       isValidConstant = false;
79       return 0;
80     }
81   
82   isValidConstant = true;
83   
84   if (V->getType() == Type::BoolTy)
85     return (int64_t) cast<ConstantBool>(V)->getValue();
86   
87   if (V->getType()->isIntegral())
88     {
89       if (V->getType()->isSigned())
90         return cast<ConstantSInt>(V)->getValue();
91       
92       assert(V->getType()->isUnsigned());
93       uint64_t Val = cast<ConstantUInt>(V)->getValue();
94       if (Val < INT64_MAX)     // then safe to cast to signed
95         return (int64_t)Val;
96     }
97
98   isValidConstant = false;
99   return 0;
100 }
101
102
103 //---------------------------------------------------------------------------
104 // Function: FoldGetElemChain
105 // 
106 // Purpose:
107 //   Fold a chain of GetElementPtr instructions into an equivalent
108 //   (Pointer, IndexVector) pair.  Returns the pointer Value, and
109 //   stores the resulting IndexVector in argument chainIdxVec.
110 //---------------------------------------------------------------------------
111
112 Value*
113 FoldGetElemChain(const InstructionNode* getElemInstrNode,
114                  vector<Value*>& chainIdxVec)
115 {
116   MemAccessInst* getElemInst = (MemAccessInst*)
117     getElemInstrNode->getInstruction();
118   
119   // Initialize return values from the incoming instruction
120   Value* ptrVal = getElemInst->getPointerOperand();
121   chainIdxVec = getElemInst->copyIndices();
122   
123   // Now chase the chain of getElementInstr instructions, if any
124   InstrTreeNode* ptrChild = getElemInstrNode->leftChild();
125   while (ptrChild->getOpLabel() == Instruction::GetElementPtr ||
126          ptrChild->getOpLabel() == GetElemPtrIdx)
127     {
128       // Child is a GetElemPtr instruction
129       getElemInst = (MemAccessInst*)
130         ((InstructionNode*) ptrChild)->getInstruction();
131       const vector<Value*>& idxVec = getElemInst->copyIndices();
132       
133       // Get the pointer value out of ptrChild and *prepend* its index vector
134       ptrVal = getElemInst->getPointerOperand();
135       chainIdxVec.insert(chainIdxVec.begin(), idxVec.begin(), idxVec.end());
136       
137       ptrChild = ptrChild->leftChild();
138     }
139   
140   return ptrVal;
141 }
142
143
144 //------------------------------------------------------------------------ 
145 // Function Set2OperandsFromInstr
146 // Function Set3OperandsFromInstr
147 // 
148 // For the common case of 2- and 3-operand arithmetic/logical instructions,
149 // set the m/c instr. operands directly from the VM instruction's operands.
150 // Check whether the first or second operand is 0 and can use a dedicated "0"
151 // register.
152 // Check whether the second operand should use an immediate field or register.
153 // (First and third operands are never immediates for such instructions.)
154 // 
155 // Arguments:
156 // canDiscardResult: Specifies that the result operand can be discarded
157 //                   by using the dedicated "0"
158 // 
159 // op1position, op2position and resultPosition: Specify in which position
160 //                   in the machine instruction the 3 operands (arg1, arg2
161 //                   and result) should go.
162 // 
163 // RETURN VALUE: unsigned int flags, where
164 //      flags & 0x01    => operand 1 is constant and needs a register
165 //      flags & 0x02    => operand 2 is constant and needs a register
166 //------------------------------------------------------------------------ 
167
168 void
169 Set2OperandsFromInstr(MachineInstr* minstr,
170                       InstructionNode* vmInstrNode,
171                       const TargetMachine& target,
172                       bool canDiscardResult,
173                       int op1Position,
174                       int resultPosition)
175 {
176   Set3OperandsFromInstr(minstr, vmInstrNode, target,
177                         canDiscardResult, op1Position,
178                         /*op2Position*/ -1, resultPosition);
179 }
180
181
182 void
183 Set3OperandsFromInstr(MachineInstr* minstr,
184                       InstructionNode* vmInstrNode,
185                       const TargetMachine& target,
186                       bool canDiscardResult,
187                       int op1Position,
188                       int op2Position,
189                       int resultPosition)
190 {
191   assert(op1Position >= 0);
192   assert(resultPosition >= 0);
193   
194   // operand 1
195   minstr->SetMachineOperand(op1Position, MachineOperand::MO_VirtualRegister,
196                             vmInstrNode->leftChild()->getValue());   
197   
198   // operand 2 (if any)
199   if (op2Position >= 0)
200     minstr->SetMachineOperand(op2Position, MachineOperand::MO_VirtualRegister,
201                               vmInstrNode->rightChild()->getValue());   
202   
203   // result operand: if it can be discarded, use a dead register if one exists
204   if (canDiscardResult && target.getRegInfo().getZeroRegNum() >= 0)
205     minstr->SetMachineOperand(resultPosition,
206                               target.getRegInfo().getZeroRegNum());
207   else
208     minstr->SetMachineOperand(resultPosition,
209                               MachineOperand::MO_VirtualRegister, vmInstrNode->getValue());
210 }
211
212
213 MachineOperand::MachineOperandType
214 ChooseRegOrImmed(Value* val,
215                  MachineOpCode opCode,
216                  const TargetMachine& target,
217                  bool canUseImmed,
218                  unsigned int& getMachineRegNum,
219                  int64_t& getImmedValue)
220 {
221   MachineOperand::MachineOperandType opType =
222     MachineOperand::MO_VirtualRegister;
223   getMachineRegNum = 0;
224   getImmedValue = 0;
225   
226   // Check for the common case first: argument is not constant
227   // 
228   Constant *CPV = dyn_cast<Constant>(val);
229   if (!CPV) return opType;
230
231   if (ConstantBool *CPB = dyn_cast<ConstantBool>(CPV))
232     {
233       if (!CPB->getValue() && target.getRegInfo().getZeroRegNum() >= 0)
234         {
235           getMachineRegNum = target.getRegInfo().getZeroRegNum();
236           return MachineOperand::MO_MachineRegister;
237         }
238
239       getImmedValue = 1;
240       return MachineOperand::MO_SignExtendedImmed;
241     }
242   
243   // Otherwise it needs to be an integer or a NULL pointer
244   if (! CPV->getType()->isIntegral() &&
245       ! (CPV->getType()->isPointerType() &&
246          CPV->isNullValue()))
247     return opType;
248   
249   // Now get the constant value and check if it fits in the IMMED field.
250   // Take advantage of the fact that the max unsigned value will rarely
251   // fit into any IMMED field and ignore that case (i.e., cast smaller
252   // unsigned constants to signed).
253   // 
254   int64_t intValue;
255   if (CPV->getType()->isPointerType())
256     {
257       intValue = 0;
258     }
259   else if (CPV->getType()->isSigned())
260     {
261       intValue = cast<ConstantSInt>(CPV)->getValue();
262     }
263   else
264     {
265       uint64_t V = cast<ConstantUInt>(CPV)->getValue();
266       if (V >= INT64_MAX) return opType;
267       intValue = (int64_t)V;
268     }
269
270   if (intValue == 0 && target.getRegInfo().getZeroRegNum() >= 0)
271     {
272       opType = MachineOperand::MO_MachineRegister;
273       getMachineRegNum = target.getRegInfo().getZeroRegNum();
274     }
275   else if (canUseImmed &&
276            target.getInstrInfo().constantFitsInImmedField(opCode, intValue))
277     {
278       opType = MachineOperand::MO_SignExtendedImmed;
279       getImmedValue = intValue;
280     }
281   
282   return opType;
283 }
284
285
286 //---------------------------------------------------------------------------
287 // Function: FixConstantOperandsForInstr
288 // 
289 // Purpose:
290 // Special handling for constant operands of a machine instruction
291 // -- if the constant is 0, use the hardwired 0 register, if any;
292 // -- if the constant fits in the IMMEDIATE field, use that field;
293 // -- else create instructions to put the constant into a register, either
294 //    directly or by loading explicitly from the constant pool.
295 // 
296 // In the first 2 cases, the operand of `minstr' is modified in place.
297 // Returns a vector of machine instructions generated for operands that
298 // fall under case 3; these must be inserted before `minstr'.
299 //---------------------------------------------------------------------------
300
301 vector<MachineInstr*>
302 FixConstantOperandsForInstr(Instruction* vmInstr,
303                             MachineInstr* minstr,
304                             TargetMachine& target)
305 {
306   vector<MachineInstr*> loadConstVec;
307   
308   const MachineInstrDescriptor& instrDesc =
309     target.getInstrInfo().getDescriptor(minstr->getOpCode());
310   
311   Method* method = vmInstr->getParent()->getParent();
312   
313   for (unsigned op=0; op < minstr->getNumOperands(); op++)
314     {
315       const MachineOperand& mop = minstr->getOperand(op);
316           
317       // skip the result position (for efficiency below) and any other
318       // positions already marked as not a virtual register
319       if (instrDesc.resultPos == (int) op || 
320           mop.getOperandType() != MachineOperand::MO_VirtualRegister ||
321           mop.getVRegValue() == NULL)
322         {
323           continue;
324         }
325           
326       Value* opValue = mop.getVRegValue();
327       bool constantThatMustBeLoaded = false;
328       
329       if (Constant *OpConst = dyn_cast<Constant>(opValue)) {
330           unsigned int machineRegNum;
331           int64_t immedValue;
332           MachineOperand::MachineOperandType opType =
333             ChooseRegOrImmed(opValue, minstr->getOpCode(), target,
334                              (target.getInstrInfo().getImmmedConstantPos(minstr->getOpCode()) == (int) op),
335                              machineRegNum, immedValue);
336           
337           if (opType == MachineOperand::MO_MachineRegister)
338             minstr->SetMachineOperand(op, machineRegNum);
339           else if (opType == MachineOperand::MO_VirtualRegister)
340             constantThatMustBeLoaded = true; // load is generated below
341           else
342             minstr->SetMachineOperand(op, opType, immedValue);
343
344           if (constantThatMustBeLoaded)
345             { // register the value so it is emitted in the assembly
346               MachineCodeForMethod::get(method).addToConstantPool(OpConst);
347             }
348         }
349       
350       if (constantThatMustBeLoaded || isa<GlobalValue>(opValue))
351         { // opValue is a constant that must be explicitly loaded into a reg.
352           TmpInstruction* tmpReg = InsertCodeToLoadConstant(opValue, vmInstr,
353                                                         loadConstVec, target);
354           minstr->SetMachineOperand(op, MachineOperand::MO_VirtualRegister,
355                                         tmpReg);
356         }
357     }
358   
359   // 
360   // Also, check for implicit operands used (not those defined) by the
361   // machine instruction.  These include:
362   // -- arguments to a Call
363   // -- return value of a Return
364   // Any such operand that is a constant value needs to be fixed also.
365   // The current instructions with implicit refs (viz., Call and Return)
366   // have no immediate fields, so the constant always needs to be loaded
367   // into a register.
368   // 
369   for (unsigned i=0, N=minstr->getNumImplicitRefs(); i < N; ++i)
370     if (isa<Constant>(minstr->getImplicitRef(i)) ||
371         isa<GlobalValue>(minstr->getImplicitRef(i)))
372       {
373         Value* oldVal = minstr->getImplicitRef(i);
374         TmpInstruction* tmpReg =
375           InsertCodeToLoadConstant(oldVal, vmInstr, loadConstVec, target);
376         minstr->setImplicitRef(i, tmpReg);
377         
378         if (Constant *C = dyn_cast<Constant>(oldVal))
379           { // register the value so it is emitted in the assembly
380             MachineCodeForMethod::get(method).addToConstantPool(C);
381           }
382       }
383   
384   return loadConstVec;
385 }
386
387