Revert "include/llvm: Add R600 Intrinsics v6"
[oota-llvm.git] / lib / Target / AMDGPU / AMDGPUTargetMachine.cpp
1 //===-- AMDGPUTargetMachine.cpp - TargetMachine for hw codegen targets-----===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 // The AMDGPU target machine contains all of the hardware specific information
11 // needed to emit code for R600 and SI GPUs.
12 //
13 //===----------------------------------------------------------------------===//
14
15 #include "AMDGPUTargetMachine.h"
16 #include "AMDGPU.h"
17 #include "R600ISelLowering.h"
18 #include "R600InstrInfo.h"
19 #include "SIISelLowering.h"
20 #include "SIInstrInfo.h"
21 #include "llvm/Analysis/Passes.h"
22 #include "llvm/Analysis/Verifier.h"
23 #include "llvm/CodeGen/MachineFunctionAnalysis.h"
24 #include "llvm/CodeGen/MachineModuleInfo.h"
25 #include "llvm/CodeGen/Passes.h"
26 #include "llvm/MC/MCAsmInfo.h"
27 #include "llvm/PassManager.h"
28 #include "llvm/Support/TargetRegistry.h"
29 #include "llvm/Support/raw_os_ostream.h"
30 #include "llvm/Transforms/IPO.h"
31 #include "llvm/Transforms/Scalar.h"
32
33 using namespace llvm;
34
35 extern "C" void LLVMInitializeAMDGPUTarget() {
36   // Register the target
37   RegisterTargetMachine<AMDGPUTargetMachine> X(TheAMDGPUTarget);
38 }
39
40 AMDGPUTargetMachine::AMDGPUTargetMachine(const Target &T, StringRef TT,
41     StringRef CPU, StringRef FS,
42   TargetOptions Options,
43   Reloc::Model RM, CodeModel::Model CM,
44   CodeGenOpt::Level OptLevel
45 )
46 :
47   LLVMTargetMachine(T, TT, CPU, FS, Options, RM, CM, OptLevel),
48   Subtarget(TT, CPU, FS),
49   DataLayout(Subtarget.getDataLayout()),
50   FrameLowering(TargetFrameLowering::StackGrowsUp,
51       Subtarget.device()->getStackAlignment(), 0),
52   IntrinsicInfo(this),
53   InstrItins(&Subtarget.getInstrItineraryData()),
54   mDump(false)
55
56 {
57   // TLInfo uses InstrInfo so it must be initialized after.
58   if (Subtarget.device()->getGeneration() <= AMDILDeviceInfo::HD6XXX) {
59     InstrInfo = new R600InstrInfo(*this);
60     TLInfo = new R600TargetLowering(*this);
61   } else {
62     InstrInfo = new SIInstrInfo(*this);
63     TLInfo = new SITargetLowering(*this);
64   }
65 }
66
67 AMDGPUTargetMachine::~AMDGPUTargetMachine()
68 {
69 }
70
71 bool AMDGPUTargetMachine::addPassesToEmitFile(PassManagerBase &PM,
72                                               formatted_raw_ostream &Out,
73                                               CodeGenFileType FileType,
74                                               bool DisableVerify,
75                                               AnalysisID StartAfter,
76                                               AnalysisID StopAfter) {
77   // XXX: Hack here addPassesToEmitFile will fail, but this is Ok since we are
78   // only using it to access addPassesToGenerateCode()
79   bool fail = LLVMTargetMachine::addPassesToEmitFile(PM, Out, FileType,
80                                                      DisableVerify);
81   assert(fail);
82
83   const AMDILSubtarget &STM = getSubtarget<AMDILSubtarget>();
84   std::string gpu = STM.getDeviceName();
85   if (gpu == "SI") {
86     PM.add(createSICodeEmitterPass(Out));
87   } else if (Subtarget.device()->getGeneration() <= AMDILDeviceInfo::HD6XXX) {
88     PM.add(createR600CodeEmitterPass(Out));
89   } else {
90     abort();
91     return true;
92   }
93   PM.add(createGCInfoDeleter());
94
95   return false;
96 }
97
98 namespace {
99 class AMDGPUPassConfig : public TargetPassConfig {
100 public:
101   AMDGPUPassConfig(AMDGPUTargetMachine *TM, PassManagerBase &PM)
102     : TargetPassConfig(TM, PM) {}
103
104   AMDGPUTargetMachine &getAMDGPUTargetMachine() const {
105     return getTM<AMDGPUTargetMachine>();
106   }
107
108   virtual bool addPreISel();
109   virtual bool addInstSelector();
110   virtual bool addPreRegAlloc();
111   virtual bool addPostRegAlloc();
112   virtual bool addPreSched2();
113   virtual bool addPreEmitPass();
114 };
115 } // End of anonymous namespace
116
117 TargetPassConfig *AMDGPUTargetMachine::createPassConfig(PassManagerBase &PM) {
118   return new AMDGPUPassConfig(this, PM);
119 }
120
121 bool
122 AMDGPUPassConfig::addPreISel()
123 {
124   const AMDILSubtarget &ST = TM->getSubtarget<AMDILSubtarget>();
125   if (ST.device()->getGeneration() <= AMDILDeviceInfo::HD6XXX) {
126     addPass(createR600KernelParametersPass(
127                      getAMDGPUTargetMachine().getTargetData()));
128   }
129   return false;
130 }
131
132 bool AMDGPUPassConfig::addInstSelector() {
133   addPass(createAMDILPeepholeOpt(*TM));
134   addPass(createAMDILISelDag(getAMDGPUTargetMachine()));
135   return false;
136 }
137
138 bool AMDGPUPassConfig::addPreRegAlloc() {
139   const AMDILSubtarget &ST = TM->getSubtarget<AMDILSubtarget>();
140
141   if (ST.device()->getGeneration() > AMDILDeviceInfo::HD6XXX) {
142     addPass(createSIAssignInterpRegsPass(*TM));
143   }
144   addPass(createAMDGPUConvertToISAPass(*TM));
145   return false;
146 }
147
148 bool AMDGPUPassConfig::addPostRegAlloc() {
149   return false;
150 }
151
152 bool AMDGPUPassConfig::addPreSched2() {
153   return false;
154 }
155
156 bool AMDGPUPassConfig::addPreEmitPass() {
157   addPass(createAMDILCFGPreparationPass(*TM));
158   addPass(createAMDILCFGStructurizerPass(*TM));
159
160   return false;
161 }
162