1f903da7335433ae243cf7ff59662be1a03ee9a14Tom Stellard//===-- AMDGPUTargetMachine.cpp - TargetMachine for hw codegen targets-----===// 2a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard// 3a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard// The LLVM Compiler Infrastructure 4a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard// 5a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard// This file is distributed under the University of Illinois Open Source 6a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard// License. See LICENSE.TXT for details. 7a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard// 8a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard//===----------------------------------------------------------------------===// 9a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard// 10f903da7335433ae243cf7ff59662be1a03ee9a14Tom Stellard// The AMDGPU target machine contains all of the hardware specific information 11f903da7335433ae243cf7ff59662be1a03ee9a14Tom Stellard// needed to emit code for R600 and SI GPUs. 12a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard// 13a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard//===----------------------------------------------------------------------===// 14a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard 15a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard#include "AMDGPUTargetMachine.h" 16a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard#include "AMDGPU.h" 17a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard#include "R600ISelLowering.h" 18a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard#include "R600InstrInfo.h" 19a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard#include "SIISelLowering.h" 20a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard#include "SIInstrInfo.h" 21a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard#include "llvm/Analysis/Passes.h" 22a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard#include "llvm/Analysis/Verifier.h" 23a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard#include "llvm/CodeGen/MachineFunctionAnalysis.h" 24a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard#include "llvm/CodeGen/MachineModuleInfo.h" 25a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard#include "llvm/CodeGen/Passes.h" 26a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard#include "llvm/MC/MCAsmInfo.h" 27a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard#include "llvm/PassManager.h" 28a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard#include "llvm/Support/TargetRegistry.h" 29a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard#include "llvm/Support/raw_os_ostream.h" 30a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard#include "llvm/Transforms/IPO.h" 31a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard#include "llvm/Transforms/Scalar.h" 32565a4e2a8625c79bde0eacf674a4f633151eeb0eVincent Lejeune#include <llvm/CodeGen/Passes.h> 33a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard 34a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellardusing namespace llvm; 35a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard 3649fb99bd131a4ed89e6f55cf360f67618acafec4Tom Stellardextern "C" void LLVMInitializeAMDGPUTarget() { 3749fb99bd131a4ed89e6f55cf360f67618acafec4Tom Stellard // Register the target 3849fb99bd131a4ed89e6f55cf360f67618acafec4Tom Stellard RegisterTargetMachine<AMDGPUTargetMachine> X(TheAMDGPUTarget); 3949fb99bd131a4ed89e6f55cf360f67618acafec4Tom Stellard} 4049fb99bd131a4ed89e6f55cf360f67618acafec4Tom Stellard 41a75c6163e605f35b14f26930dd9227e4f337ec9eTom StellardAMDGPUTargetMachine::AMDGPUTargetMachine(const Target &T, StringRef TT, 42a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard StringRef CPU, StringRef FS, 43a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard TargetOptions Options, 44a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard Reloc::Model RM, CodeModel::Model CM, 45a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard CodeGenOpt::Level OptLevel 46a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard) 47a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard: 4849fb99bd131a4ed89e6f55cf360f67618acafec4Tom Stellard LLVMTargetMachine(T, TT, CPU, FS, Options, RM, CM, OptLevel), 49a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard Subtarget(TT, CPU, FS), 5049fb99bd131a4ed89e6f55cf360f67618acafec4Tom Stellard DataLayout(Subtarget.getDataLayout()), 5149fb99bd131a4ed89e6f55cf360f67618acafec4Tom Stellard FrameLowering(TargetFrameLowering::StackGrowsUp, 5249fb99bd131a4ed89e6f55cf360f67618acafec4Tom Stellard Subtarget.device()->getStackAlignment(), 0), 5349fb99bd131a4ed89e6f55cf360f67618acafec4Tom Stellard IntrinsicInfo(this), 54cd287301ec598d2811f3f85c03d23bae01be2359Tom Stellard InstrItins(&Subtarget.getInstrItineraryData()), 55a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard mDump(false) 56a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard 57a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard{ 58bcfc97dbf40c256ed59c2424e0c55b845f0f2569Tom Stellard // TLInfo uses InstrInfo so it must be initialized after. 592f921101c0826dc52a2c69f85c3da0f7f6e8212aTom Stellard if (Subtarget.device()->getGeneration() <= AMDGPUDeviceInfo::HD6XXX) { 60a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard InstrInfo = new R600InstrInfo(*this); 61a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard TLInfo = new R600TargetLowering(*this); 62a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard } else { 63a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard InstrInfo = new SIInstrInfo(*this); 64a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard TLInfo = new SITargetLowering(*this); 65a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard } 66a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard} 67a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard 68a75c6163e605f35b14f26930dd9227e4f337ec9eTom StellardAMDGPUTargetMachine::~AMDGPUTargetMachine() 69a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard{ 70a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard} 71a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard 72a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellardnamespace { 73a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellardclass AMDGPUPassConfig : public TargetPassConfig { 74a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellardpublic: 75a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard AMDGPUPassConfig(AMDGPUTargetMachine *TM, PassManagerBase &PM) 76a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard : TargetPassConfig(TM, PM) {} 77a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard 78a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard AMDGPUTargetMachine &getAMDGPUTargetMachine() const { 79a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard return getTM<AMDGPUTargetMachine>(); 80a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard } 81a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard 82a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard virtual bool addPreISel(); 83a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard virtual bool addInstSelector(); 84a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard virtual bool addPreRegAlloc(); 85a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard virtual bool addPostRegAlloc(); 86a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard virtual bool addPreSched2(); 87a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard virtual bool addPreEmitPass(); 88a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard}; 89a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard} // End of anonymous namespace 90a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard 91a75c6163e605f35b14f26930dd9227e4f337ec9eTom StellardTargetPassConfig *AMDGPUTargetMachine::createPassConfig(PassManagerBase &PM) { 92a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard return new AMDGPUPassConfig(this, PM); 93a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard} 94a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard 95a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellardbool 96a75c6163e605f35b14f26930dd9227e4f337ec9eTom StellardAMDGPUPassConfig::addPreISel() 97a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard{ 98b72ab79d73b29ec087d90cf2c698adbab4db5defTom Stellard const AMDGPUSubtarget &ST = TM->getSubtarget<AMDGPUSubtarget>(); 992f921101c0826dc52a2c69f85c3da0f7f6e8212aTom Stellard if (ST.device()->getGeneration() <= AMDGPUDeviceInfo::HD6XXX) { 100d742d812d82ef61de1f41a18c8251db9b001bdd1Tom Stellard PM->add(createR600KernelParametersPass( 101a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard getAMDGPUTargetMachine().getTargetData())); 102a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard } 103a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard return false; 104a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard} 105a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard 106a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellardbool AMDGPUPassConfig::addInstSelector() { 1072f921101c0826dc52a2c69f85c3da0f7f6e8212aTom Stellard PM->add(createAMDGPUPeepholeOpt(*TM)); 1082f921101c0826dc52a2c69f85c3da0f7f6e8212aTom Stellard PM->add(createAMDGPUISelDag(getAMDGPUTargetMachine())); 109a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard return false; 110a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard} 111a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard 112a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellardbool AMDGPUPassConfig::addPreRegAlloc() { 113b72ab79d73b29ec087d90cf2c698adbab4db5defTom Stellard const AMDGPUSubtarget &ST = TM->getSubtarget<AMDGPUSubtarget>(); 114a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard 1152f921101c0826dc52a2c69f85c3da0f7f6e8212aTom Stellard if (ST.device()->getGeneration() > AMDGPUDeviceInfo::HD6XXX) { 116d742d812d82ef61de1f41a18c8251db9b001bdd1Tom Stellard PM->add(createSIAssignInterpRegsPass(*TM)); 117a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard } 118d742d812d82ef61de1f41a18c8251db9b001bdd1Tom Stellard PM->add(createAMDGPUConvertToISAPass(*TM)); 119a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard return false; 120a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard} 121a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard 122a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellardbool AMDGPUPassConfig::addPostRegAlloc() { 123a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard return false; 124a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard} 125a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard 126a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellardbool AMDGPUPassConfig::addPreSched2() { 127565a4e2a8625c79bde0eacf674a4f633151eeb0eVincent Lejeune 128565a4e2a8625c79bde0eacf674a4f633151eeb0eVincent Lejeune addPass(IfConverterID); 129a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard return false; 130a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard} 131a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard 132a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellardbool AMDGPUPassConfig::addPreEmitPass() { 1332f921101c0826dc52a2c69f85c3da0f7f6e8212aTom Stellard PM->add(createAMDGPUCFGPreparationPass(*TM)); 1342f921101c0826dc52a2c69f85c3da0f7f6e8212aTom Stellard PM->add(createAMDGPUCFGStructurizerPass(*TM)); 135a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard 13682a5d0c64142990236b40567561b6e99b7158216Tom Stellard const AMDGPUSubtarget &ST = TM->getSubtarget<AMDGPUSubtarget>(); 13782a5d0c64142990236b40567561b6e99b7158216Tom Stellard if (ST.device()->getGeneration() <= AMDGPUDeviceInfo::HD6XXX) { 13882a5d0c64142990236b40567561b6e99b7158216Tom Stellard PM->add(createR600ExpandSpecialInstrsPass(*TM)); 13982a5d0c64142990236b40567561b6e99b7158216Tom Stellard addPass(FinalizeMachineBundlesID); 14082a5d0c64142990236b40567561b6e99b7158216Tom Stellard } 14182a5d0c64142990236b40567561b6e99b7158216Tom Stellard 142a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard return false; 143a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard} 144a75c6163e605f35b14f26930dd9227e4f337ec9eTom Stellard 145