Make sure to set the destination register correctly
[oota-llvm.git] / lib / Target / X86 / X86ISelSimple.cpp
1 //===-- InstSelectSimple.cpp - A simple instruction selector for x86 ------===//
2 //
3 // This file defines a simple peephole instruction selector for the x86 platform
4 //
5 //===----------------------------------------------------------------------===//
6
7 #include "X86.h"
8 #include "X86InstrInfo.h"
9 #include "llvm/Function.h"
10 #include "llvm/iTerminators.h"
11 #include "llvm/Type.h"
12 #include "llvm/Constants.h"
13 #include "llvm/Pass.h"
14 #include "llvm/CodeGen/MachineFunction.h"
15 #include "llvm/CodeGen/MachineInstrBuilder.h"
16 #include "llvm/Support/InstVisitor.h"
17 #include <map>
18
19 namespace {
20   struct ISel : public FunctionPass, InstVisitor<ISel> {
21     TargetMachine &TM;
22     MachineFunction *F;                    // The function we are compiling into
23     MachineBasicBlock *BB;                 // The current MBB we are compiling
24
25     unsigned CurReg;
26     std::map<Value*, unsigned> RegMap;  // Mapping between Val's and SSA Regs
27
28     ISel(TargetMachine &tm)
29       : TM(tm), F(0), BB(0), CurReg(MRegisterInfo::FirstVirtualRegister) {}
30
31     /// runOnFunction - Top level implementation of instruction selection for
32     /// the entire function.
33     ///
34     bool runOnFunction(Function &Fn) {
35       F = &MachineFunction::construct(&Fn, TM);
36       visit(Fn);
37       RegMap.clear();
38       F = 0;
39       return false;  // We never modify the LLVM itself.
40     }
41
42     /// visitBasicBlock - This method is called when we are visiting a new basic
43     /// block.  This simply creates a new MachineBasicBlock to emit code into
44     /// and adds it to the current MachineFunction.  Subsequent visit* for
45     /// instructions will be invoked for all instructions in the basic block.
46     ///
47     void visitBasicBlock(BasicBlock &LLVM_BB) {
48       BB = new MachineBasicBlock(&LLVM_BB);
49       // FIXME: Use the auto-insert form when it's available
50       F->getBasicBlockList().push_back(BB);
51     }
52
53     // Visitation methods for various instructions.  These methods simply emit
54     // fixed X86 code for each instruction.
55     //
56     void visitReturnInst(ReturnInst &RI);
57     void visitAdd(BinaryOperator &B);
58
59     void visitInstruction(Instruction &I) {
60       std::cerr << "Cannot instruction select: " << I;
61       abort();
62     }
63
64     
65     /// copyConstantToRegister - Output the instructions required to put the
66     /// specified constant into the specified register.
67     ///
68     void copyConstantToRegister(Constant *C, unsigned Reg);
69
70     /// getReg - This method turns an LLVM value into a register number.  This
71     /// is guaranteed to produce the same register number for a particular value
72     /// every time it is queried.
73     ///
74     unsigned getReg(Value &V) { return getReg(&V); }  // Allow references
75     unsigned getReg(Value *V) {
76       unsigned &Reg = RegMap[V];
77       if (Reg == 0)
78         Reg = CurReg++;
79
80       // If this operand is a constant, emit the code to copy the constant into
81       // the register here...
82       //
83       if (Constant *C = dyn_cast<Constant>(V))
84         copyConstantToRegister(C, Reg);
85
86       return Reg;
87     }
88   };
89 }
90
91
92 /// copyConstantToRegister - Output the instructions required to put the
93 /// specified constant into the specified register.
94 ///
95 void ISel::copyConstantToRegister(Constant *C, unsigned R) {
96   assert (!isa<ConstantExpr>(C) && "Constant expressions not yet handled!\n");
97
98   switch (C->getType()->getPrimitiveID()) {
99   case Type::SByteTyID:
100     BuildMI(BB, X86::MOVir8, 1, R).addSImm(cast<ConstantSInt>(C)->getValue());
101     break;
102   case Type::UByteTyID:
103     BuildMI(BB, X86::MOVir8, 1, R).addZImm(cast<ConstantUInt>(C)->getValue());
104     break;
105   case Type::ShortTyID:
106     BuildMI(BB, X86::MOVir16, 1, R).addSImm(cast<ConstantSInt>(C)->getValue());
107     break;
108   case Type::UShortTyID:
109     BuildMI(BB, X86::MOVir16, 1, R).addZImm(cast<ConstantUInt>(C)->getValue());
110     break;
111   case Type::IntTyID:
112     BuildMI(BB, X86::MOVir32, 1, R).addSImm(cast<ConstantSInt>(C)->getValue());
113     break;
114   case Type::UIntTyID:
115     BuildMI(BB, X86::MOVir32, 1, R).addZImm(cast<ConstantUInt>(C)->getValue());
116     break;
117   default: assert(0 && "Type not handled yet!");      
118   }
119 }
120
121
122 /// 'ret' instruction - Here we are interested in meeting the x86 ABI.  As such,
123 /// we have the following possibilities:
124 ///
125 ///   ret void: No return value, simply emit a 'ret' instruction
126 ///   ret sbyte, ubyte : Extend value into EAX and return
127 ///   ret short, ushort: Extend value into EAX and return
128 ///   ret int, uint    : Move value into EAX and return
129 ///   ret pointer      : Move value into EAX and return
130 ///   ret long, ulong  : Move value into EAX/EDX (?) and return
131 ///   ret float/double : ?  Top of FP stack?  XMM0?
132 ///
133 void ISel::visitReturnInst(ReturnInst &I) {
134   if (I.getNumOperands() != 0) {  // Not 'ret void'?
135     // Move result into a hard register... then emit a ret
136     visitInstruction(I);  // abort
137   }
138
139   // Emit a simple 'ret' instruction... appending it to the end of the basic
140   // block
141   BuildMI(BB, X86::RET, 0);
142 }
143
144
145 /// 'add' instruction - Simply turn this into an x86 reg,reg add instruction.
146 void ISel::visitAdd(BinaryOperator &B) {
147   unsigned Op0r = getReg(B.getOperand(0)), Op1r = getReg(B.getOperand(1));
148   unsigned DestReg = getReg(B);
149
150   switch (B.getType()->getPrimitiveSize()) {
151   case 1:   // UByte, SByte
152     BuildMI(BB, X86::ADDrr8, 2, DestReg).addReg(Op0r).addReg(Op1r);
153     break;
154   case 2:   // UShort, Short
155     BuildMI(BB, X86::ADDrr16, 2, DestReg).addReg(Op0r).addReg(Op1r);
156     break;
157   case 4:   // UInt, Int
158     BuildMI(BB, X86::ADDrr32, 2, DestReg).addReg(Op0r).addReg(Op1r);
159     break;
160
161   case 8:   // ULong, Long
162   default:
163     visitInstruction(B);  // abort
164   }
165 }
166
167 /// createSimpleX86InstructionSelector - This pass converts an LLVM function
168 /// into a machine code representation is a very simple peep-hole fashion.  The
169 /// generated code sucks but the implementation is nice and simple.
170 ///
171 Pass *createSimpleX86InstructionSelector(TargetMachine &TM) {
172   return new ISel(TM);
173 }