1*9880d681SAndroid Build Coastguard Worker //===-- TargetMachine.cpp - General Target Information ---------------------==//
2*9880d681SAndroid Build Coastguard Worker //
3*9880d681SAndroid Build Coastguard Worker // The LLVM Compiler Infrastructure
4*9880d681SAndroid Build Coastguard Worker //
5*9880d681SAndroid Build Coastguard Worker // This file is distributed under the University of Illinois Open Source
6*9880d681SAndroid Build Coastguard Worker // License. See LICENSE.TXT for details.
7*9880d681SAndroid Build Coastguard Worker //
8*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
9*9880d681SAndroid Build Coastguard Worker //
10*9880d681SAndroid Build Coastguard Worker // This file describes the general parts of a Target machine.
11*9880d681SAndroid Build Coastguard Worker //
12*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
13*9880d681SAndroid Build Coastguard Worker
14*9880d681SAndroid Build Coastguard Worker #include "llvm/Target/TargetMachine.h"
15*9880d681SAndroid Build Coastguard Worker #include "llvm/Analysis/TargetTransformInfo.h"
16*9880d681SAndroid Build Coastguard Worker #include "llvm/CodeGen/MachineFunction.h"
17*9880d681SAndroid Build Coastguard Worker #include "llvm/IR/Function.h"
18*9880d681SAndroid Build Coastguard Worker #include "llvm/IR/GlobalAlias.h"
19*9880d681SAndroid Build Coastguard Worker #include "llvm/IR/GlobalValue.h"
20*9880d681SAndroid Build Coastguard Worker #include "llvm/IR/GlobalVariable.h"
21*9880d681SAndroid Build Coastguard Worker #include "llvm/IR/LegacyPassManager.h"
22*9880d681SAndroid Build Coastguard Worker #include "llvm/IR/Mangler.h"
23*9880d681SAndroid Build Coastguard Worker #include "llvm/MC/MCAsmInfo.h"
24*9880d681SAndroid Build Coastguard Worker #include "llvm/MC/MCContext.h"
25*9880d681SAndroid Build Coastguard Worker #include "llvm/MC/MCInstrInfo.h"
26*9880d681SAndroid Build Coastguard Worker #include "llvm/MC/MCSectionMachO.h"
27*9880d681SAndroid Build Coastguard Worker #include "llvm/MC/MCTargetOptions.h"
28*9880d681SAndroid Build Coastguard Worker #include "llvm/MC/SectionKind.h"
29*9880d681SAndroid Build Coastguard Worker #include "llvm/Target/TargetLowering.h"
30*9880d681SAndroid Build Coastguard Worker #include "llvm/Target/TargetLoweringObjectFile.h"
31*9880d681SAndroid Build Coastguard Worker #include "llvm/Target/TargetSubtargetInfo.h"
32*9880d681SAndroid Build Coastguard Worker using namespace llvm;
33*9880d681SAndroid Build Coastguard Worker
34*9880d681SAndroid Build Coastguard Worker cl::opt<bool> EnableIPRA("enable-ipra", cl::init(false), cl::Hidden,
35*9880d681SAndroid Build Coastguard Worker cl::desc("Enable interprocedural register allocation "
36*9880d681SAndroid Build Coastguard Worker "to reduce load/store at procedure calls."));
37*9880d681SAndroid Build Coastguard Worker
38*9880d681SAndroid Build Coastguard Worker //---------------------------------------------------------------------------
39*9880d681SAndroid Build Coastguard Worker // TargetMachine Class
40*9880d681SAndroid Build Coastguard Worker //
41*9880d681SAndroid Build Coastguard Worker
TargetMachine(const Target & T,StringRef DataLayoutString,const Triple & TT,StringRef CPU,StringRef FS,const TargetOptions & Options)42*9880d681SAndroid Build Coastguard Worker TargetMachine::TargetMachine(const Target &T, StringRef DataLayoutString,
43*9880d681SAndroid Build Coastguard Worker const Triple &TT, StringRef CPU, StringRef FS,
44*9880d681SAndroid Build Coastguard Worker const TargetOptions &Options)
45*9880d681SAndroid Build Coastguard Worker : TheTarget(T), DL(DataLayoutString), TargetTriple(TT), TargetCPU(CPU),
46*9880d681SAndroid Build Coastguard Worker TargetFS(FS), AsmInfo(nullptr), MRI(nullptr), MII(nullptr), STI(nullptr),
47*9880d681SAndroid Build Coastguard Worker RequireStructuredCFG(false), Options(Options) {
48*9880d681SAndroid Build Coastguard Worker if (EnableIPRA.getNumOccurrences())
49*9880d681SAndroid Build Coastguard Worker this->Options.EnableIPRA = EnableIPRA;
50*9880d681SAndroid Build Coastguard Worker }
51*9880d681SAndroid Build Coastguard Worker
~TargetMachine()52*9880d681SAndroid Build Coastguard Worker TargetMachine::~TargetMachine() {
53*9880d681SAndroid Build Coastguard Worker delete AsmInfo;
54*9880d681SAndroid Build Coastguard Worker delete MRI;
55*9880d681SAndroid Build Coastguard Worker delete MII;
56*9880d681SAndroid Build Coastguard Worker delete STI;
57*9880d681SAndroid Build Coastguard Worker }
58*9880d681SAndroid Build Coastguard Worker
isPositionIndependent() const59*9880d681SAndroid Build Coastguard Worker bool TargetMachine::isPositionIndependent() const {
60*9880d681SAndroid Build Coastguard Worker return getRelocationModel() == Reloc::PIC_;
61*9880d681SAndroid Build Coastguard Worker }
62*9880d681SAndroid Build Coastguard Worker
63*9880d681SAndroid Build Coastguard Worker /// \brief Reset the target options based on the function's attributes.
64*9880d681SAndroid Build Coastguard Worker // FIXME: This function needs to go away for a number of reasons:
65*9880d681SAndroid Build Coastguard Worker // a) global state on the TargetMachine is terrible in general,
66*9880d681SAndroid Build Coastguard Worker // b) there's no default state here to keep,
67*9880d681SAndroid Build Coastguard Worker // c) these target options should be passed only on the function
68*9880d681SAndroid Build Coastguard Worker // and not on the TargetMachine (via TargetOptions) at all.
resetTargetOptions(const Function & F) const69*9880d681SAndroid Build Coastguard Worker void TargetMachine::resetTargetOptions(const Function &F) const {
70*9880d681SAndroid Build Coastguard Worker #define RESET_OPTION(X, Y) \
71*9880d681SAndroid Build Coastguard Worker do { \
72*9880d681SAndroid Build Coastguard Worker if (F.hasFnAttribute(Y)) \
73*9880d681SAndroid Build Coastguard Worker Options.X = (F.getFnAttribute(Y).getValueAsString() == "true"); \
74*9880d681SAndroid Build Coastguard Worker } while (0)
75*9880d681SAndroid Build Coastguard Worker
76*9880d681SAndroid Build Coastguard Worker RESET_OPTION(LessPreciseFPMADOption, "less-precise-fpmad");
77*9880d681SAndroid Build Coastguard Worker RESET_OPTION(UnsafeFPMath, "unsafe-fp-math");
78*9880d681SAndroid Build Coastguard Worker RESET_OPTION(NoInfsFPMath, "no-infs-fp-math");
79*9880d681SAndroid Build Coastguard Worker RESET_OPTION(NoNaNsFPMath, "no-nans-fp-math");
80*9880d681SAndroid Build Coastguard Worker }
81*9880d681SAndroid Build Coastguard Worker
82*9880d681SAndroid Build Coastguard Worker /// Returns the code generation relocation model. The choices are static, PIC,
83*9880d681SAndroid Build Coastguard Worker /// and dynamic-no-pic.
getRelocationModel() const84*9880d681SAndroid Build Coastguard Worker Reloc::Model TargetMachine::getRelocationModel() const { return RM; }
85*9880d681SAndroid Build Coastguard Worker
86*9880d681SAndroid Build Coastguard Worker /// Returns the code model. The choices are small, kernel, medium, large, and
87*9880d681SAndroid Build Coastguard Worker /// target default.
getCodeModel() const88*9880d681SAndroid Build Coastguard Worker CodeModel::Model TargetMachine::getCodeModel() const { return CMModel; }
89*9880d681SAndroid Build Coastguard Worker
90*9880d681SAndroid Build Coastguard Worker /// Get the IR-specified TLS model for Var.
getSelectedTLSModel(const GlobalValue * GV)91*9880d681SAndroid Build Coastguard Worker static TLSModel::Model getSelectedTLSModel(const GlobalValue *GV) {
92*9880d681SAndroid Build Coastguard Worker switch (GV->getThreadLocalMode()) {
93*9880d681SAndroid Build Coastguard Worker case GlobalVariable::NotThreadLocal:
94*9880d681SAndroid Build Coastguard Worker llvm_unreachable("getSelectedTLSModel for non-TLS variable");
95*9880d681SAndroid Build Coastguard Worker break;
96*9880d681SAndroid Build Coastguard Worker case GlobalVariable::GeneralDynamicTLSModel:
97*9880d681SAndroid Build Coastguard Worker return TLSModel::GeneralDynamic;
98*9880d681SAndroid Build Coastguard Worker case GlobalVariable::LocalDynamicTLSModel:
99*9880d681SAndroid Build Coastguard Worker return TLSModel::LocalDynamic;
100*9880d681SAndroid Build Coastguard Worker case GlobalVariable::InitialExecTLSModel:
101*9880d681SAndroid Build Coastguard Worker return TLSModel::InitialExec;
102*9880d681SAndroid Build Coastguard Worker case GlobalVariable::LocalExecTLSModel:
103*9880d681SAndroid Build Coastguard Worker return TLSModel::LocalExec;
104*9880d681SAndroid Build Coastguard Worker }
105*9880d681SAndroid Build Coastguard Worker llvm_unreachable("invalid TLS model");
106*9880d681SAndroid Build Coastguard Worker }
107*9880d681SAndroid Build Coastguard Worker
108*9880d681SAndroid Build Coastguard Worker // FIXME: make this a proper option
109*9880d681SAndroid Build Coastguard Worker static bool CanUseCopyRelocWithPIE = false;
110*9880d681SAndroid Build Coastguard Worker
shouldAssumeDSOLocal(const Module & M,const GlobalValue * GV) const111*9880d681SAndroid Build Coastguard Worker bool TargetMachine::shouldAssumeDSOLocal(const Module &M,
112*9880d681SAndroid Build Coastguard Worker const GlobalValue *GV) const {
113*9880d681SAndroid Build Coastguard Worker Reloc::Model RM = getRelocationModel();
114*9880d681SAndroid Build Coastguard Worker const Triple &TT = getTargetTriple();
115*9880d681SAndroid Build Coastguard Worker
116*9880d681SAndroid Build Coastguard Worker // DLLImport explicitly marks the GV as external.
117*9880d681SAndroid Build Coastguard Worker if (GV && GV->hasDLLImportStorageClass())
118*9880d681SAndroid Build Coastguard Worker return false;
119*9880d681SAndroid Build Coastguard Worker
120*9880d681SAndroid Build Coastguard Worker // Every other GV is local on COFF
121*9880d681SAndroid Build Coastguard Worker if (TT.isOSBinFormatCOFF())
122*9880d681SAndroid Build Coastguard Worker return true;
123*9880d681SAndroid Build Coastguard Worker
124*9880d681SAndroid Build Coastguard Worker if (GV && (GV->hasLocalLinkage() || !GV->hasDefaultVisibility()))
125*9880d681SAndroid Build Coastguard Worker return true;
126*9880d681SAndroid Build Coastguard Worker
127*9880d681SAndroid Build Coastguard Worker if (TT.isOSBinFormatMachO()) {
128*9880d681SAndroid Build Coastguard Worker if (RM == Reloc::Static)
129*9880d681SAndroid Build Coastguard Worker return true;
130*9880d681SAndroid Build Coastguard Worker return GV && GV->isStrongDefinitionForLinker();
131*9880d681SAndroid Build Coastguard Worker }
132*9880d681SAndroid Build Coastguard Worker
133*9880d681SAndroid Build Coastguard Worker assert(TT.isOSBinFormatELF());
134*9880d681SAndroid Build Coastguard Worker assert(RM != Reloc::DynamicNoPIC);
135*9880d681SAndroid Build Coastguard Worker
136*9880d681SAndroid Build Coastguard Worker bool IsExecutable =
137*9880d681SAndroid Build Coastguard Worker RM == Reloc::Static || M.getPIELevel() != PIELevel::Default;
138*9880d681SAndroid Build Coastguard Worker if (IsExecutable) {
139*9880d681SAndroid Build Coastguard Worker // If the symbol is defined, it cannot be preempted.
140*9880d681SAndroid Build Coastguard Worker if (GV && !GV->isDeclarationForLinker())
141*9880d681SAndroid Build Coastguard Worker return true;
142*9880d681SAndroid Build Coastguard Worker
143*9880d681SAndroid Build Coastguard Worker bool IsTLS = GV && GV->isThreadLocal();
144*9880d681SAndroid Build Coastguard Worker // Check if we can use copy relocations.
145*9880d681SAndroid Build Coastguard Worker if (!IsTLS && (RM == Reloc::Static || CanUseCopyRelocWithPIE))
146*9880d681SAndroid Build Coastguard Worker return true;
147*9880d681SAndroid Build Coastguard Worker }
148*9880d681SAndroid Build Coastguard Worker
149*9880d681SAndroid Build Coastguard Worker // ELF supports preemption of other symbols.
150*9880d681SAndroid Build Coastguard Worker return false;
151*9880d681SAndroid Build Coastguard Worker }
152*9880d681SAndroid Build Coastguard Worker
getTLSModel(const GlobalValue * GV) const153*9880d681SAndroid Build Coastguard Worker TLSModel::Model TargetMachine::getTLSModel(const GlobalValue *GV) const {
154*9880d681SAndroid Build Coastguard Worker bool IsPIE = GV->getParent()->getPIELevel() != PIELevel::Default;
155*9880d681SAndroid Build Coastguard Worker Reloc::Model RM = getRelocationModel();
156*9880d681SAndroid Build Coastguard Worker bool IsSharedLibrary = RM == Reloc::PIC_ && !IsPIE;
157*9880d681SAndroid Build Coastguard Worker bool IsLocal = shouldAssumeDSOLocal(*GV->getParent(), GV);
158*9880d681SAndroid Build Coastguard Worker
159*9880d681SAndroid Build Coastguard Worker TLSModel::Model Model;
160*9880d681SAndroid Build Coastguard Worker if (IsSharedLibrary) {
161*9880d681SAndroid Build Coastguard Worker if (IsLocal)
162*9880d681SAndroid Build Coastguard Worker Model = TLSModel::LocalDynamic;
163*9880d681SAndroid Build Coastguard Worker else
164*9880d681SAndroid Build Coastguard Worker Model = TLSModel::GeneralDynamic;
165*9880d681SAndroid Build Coastguard Worker } else {
166*9880d681SAndroid Build Coastguard Worker if (IsLocal)
167*9880d681SAndroid Build Coastguard Worker Model = TLSModel::LocalExec;
168*9880d681SAndroid Build Coastguard Worker else
169*9880d681SAndroid Build Coastguard Worker Model = TLSModel::InitialExec;
170*9880d681SAndroid Build Coastguard Worker }
171*9880d681SAndroid Build Coastguard Worker
172*9880d681SAndroid Build Coastguard Worker // If the user specified a more specific model, use that.
173*9880d681SAndroid Build Coastguard Worker TLSModel::Model SelectedModel = getSelectedTLSModel(GV);
174*9880d681SAndroid Build Coastguard Worker if (SelectedModel > Model)
175*9880d681SAndroid Build Coastguard Worker return SelectedModel;
176*9880d681SAndroid Build Coastguard Worker
177*9880d681SAndroid Build Coastguard Worker return Model;
178*9880d681SAndroid Build Coastguard Worker }
179*9880d681SAndroid Build Coastguard Worker
180*9880d681SAndroid Build Coastguard Worker /// Returns the optimization level: None, Less, Default, or Aggressive.
getOptLevel() const181*9880d681SAndroid Build Coastguard Worker CodeGenOpt::Level TargetMachine::getOptLevel() const { return OptLevel; }
182*9880d681SAndroid Build Coastguard Worker
setOptLevel(CodeGenOpt::Level Level)183*9880d681SAndroid Build Coastguard Worker void TargetMachine::setOptLevel(CodeGenOpt::Level Level) { OptLevel = Level; }
184*9880d681SAndroid Build Coastguard Worker
getTargetIRAnalysis()185*9880d681SAndroid Build Coastguard Worker TargetIRAnalysis TargetMachine::getTargetIRAnalysis() {
186*9880d681SAndroid Build Coastguard Worker return TargetIRAnalysis([this](const Function &F) {
187*9880d681SAndroid Build Coastguard Worker return TargetTransformInfo(F.getParent()->getDataLayout());
188*9880d681SAndroid Build Coastguard Worker });
189*9880d681SAndroid Build Coastguard Worker }
190*9880d681SAndroid Build Coastguard Worker
getNameWithPrefix(SmallVectorImpl<char> & Name,const GlobalValue * GV,Mangler & Mang,bool MayAlwaysUsePrivate) const191*9880d681SAndroid Build Coastguard Worker void TargetMachine::getNameWithPrefix(SmallVectorImpl<char> &Name,
192*9880d681SAndroid Build Coastguard Worker const GlobalValue *GV, Mangler &Mang,
193*9880d681SAndroid Build Coastguard Worker bool MayAlwaysUsePrivate) const {
194*9880d681SAndroid Build Coastguard Worker if (MayAlwaysUsePrivate || !GV->hasPrivateLinkage()) {
195*9880d681SAndroid Build Coastguard Worker // Simple case: If GV is not private, it is not important to find out if
196*9880d681SAndroid Build Coastguard Worker // private labels are legal in this case or not.
197*9880d681SAndroid Build Coastguard Worker Mang.getNameWithPrefix(Name, GV, false);
198*9880d681SAndroid Build Coastguard Worker return;
199*9880d681SAndroid Build Coastguard Worker }
200*9880d681SAndroid Build Coastguard Worker const TargetLoweringObjectFile *TLOF = getObjFileLowering();
201*9880d681SAndroid Build Coastguard Worker TLOF->getNameWithPrefix(Name, GV, Mang, *this);
202*9880d681SAndroid Build Coastguard Worker }
203*9880d681SAndroid Build Coastguard Worker
getSymbol(const GlobalValue * GV,Mangler & Mang) const204*9880d681SAndroid Build Coastguard Worker MCSymbol *TargetMachine::getSymbol(const GlobalValue *GV, Mangler &Mang) const {
205*9880d681SAndroid Build Coastguard Worker SmallString<128> NameStr;
206*9880d681SAndroid Build Coastguard Worker getNameWithPrefix(NameStr, GV, Mang);
207*9880d681SAndroid Build Coastguard Worker const TargetLoweringObjectFile *TLOF = getObjFileLowering();
208*9880d681SAndroid Build Coastguard Worker return TLOF->getContext().getOrCreateSymbol(NameStr);
209*9880d681SAndroid Build Coastguard Worker }
210