Go to the documentation of this file.
41 #define DEBUG_TYPE "tlshoist"
45 cl::desc(
"hoist the TLS loads in PIC model to eliminate redundant "
46 "TLS address calculation."));
61 StringRef getPassName()
const override {
return "TLS Variable Hoist"; }
78 "TLS Variable Hoist",
false,
false)
85 return new TLSVariableHoistLegacyPass();
93 LLVM_DEBUG(
dbgs() <<
"********** Begin TLS Variable Hoist **********\n");
97 Impl.runImpl(Fn, getAnalysis<DominatorTreeWrapperPass>().getDomTree(),
98 getAnalysis<LoopInfoWrapperPass>().getLoopInfo());
101 LLVM_DEBUG(
dbgs() <<
"********** Function after TLS Variable Hoist: "
105 LLVM_DEBUG(
dbgs() <<
"********** End TLS Variable Hoist **********\n");
110 void TLSVariableHoistPass::collectTLSCandidate(
Instruction *Inst) {
117 auto *GV = dyn_cast<GlobalVariable>(Inst->
getOperand(Idx));
118 if (!GV || !GV->isThreadLocal())
122 TLSCandMap[GV].addUser(Inst, Idx);
126 void TLSVariableHoistPass::collectTLSCandidates(
Function &Fn) {
142 if (!DT->isReachableFromEntry(&
BB))
146 collectTLSCandidate(&Inst);
151 if (Cand.
Users.size() != 1)
163 assert(L &&
"Unexcepted Loop status!");
178 Dom = DT->findNearestCommonDominator(Dom, PredBB);
180 assert(Dom &&
"Not find dominator BB!");
190 if (DT->dominates(
I1, I2))
192 if (DT->dominates(I2,
I1))
197 DT->findNearestCommonDominator(
I1->getParent(), I2->
getParent());
200 assert(Dom &&
"Common dominator not found!");
216 if (
Loop *L = LI->getLoopFor(
BB)) {
217 Pos = getNearestLoopDomInst(
BB, L);
218 assert(Pos &&
"Not find insert position out of loop!");
220 Pos = getDomInst(LastPos, Pos);
224 assert(LastPos &&
"Unexpected insert position!");
241 bool TLSVariableHoistPass::tryReplaceTLSCandidate(
Function &Fn,
251 auto *
CastInst = genBitCastInst(Fn, GV);
260 bool TLSVariableHoistPass::tryReplaceTLSCandidates(
Function &Fn) {
261 if (TLSCandMap.empty())
264 bool Replaced =
false;
265 for (
auto &GV2Cand : TLSCandMap) {
267 Replaced |= tryReplaceTLSCandidate(Fn, GV);
284 assert(this->LI && this->DT &&
"Unexcepted requirement!");
287 collectTLSCandidates(Fn);
289 bool MadeChange = tryReplaceTLSCandidates(Fn);
A set of analyses that are preserved following a run of a transformation pass.
This is an optimization pass for GlobalISel generic memory operations.
We currently emits eax Perhaps this is what we really should generate is Is imull three or four cycles eax eax The current instruction priority is based on pattern complexity The former is more complex because it folds a load so the latter will not be emitted Perhaps we should use AddedComplexity to give LEA32r a higher priority We should always try to match LEA first since the LEA matching code does some estimate to determine whether the match is profitable if we care more about code then imull is better It s two bytes shorter than movl leal On a Pentium M
SmallVector< TLSUser, 8 > Users
InstListType::iterator iterator
Instruction iterators...
PassT::Result & getResult(IRUnitT &IR, ExtraArgTs... ExtraArgs)
Get the result of an analysis pass for a given IR unit.
bool hasOptNone() const
Do not optimize this function (-O0).
static cl::opt< bool > TLSLoadHoist("tls-load-hoist", cl::init(false), cl::Hidden, cl::desc("hoist the TLS loads in PIC model to eliminate redundant " "TLS address calculation."))
Represents a single loop in the control flow graph.
static bool oneUseOutsideLoop(tlshoist::TLSCandidate &Cand, LoopInfo *LI)
TLS Variable Hoist
When an instruction is found to use only loop invariant operands that are safe to hoist,...
This class represents a no-op cast from one type to another.
const BasicBlock & getEntryBlock() const
Concrete subclass of DominatorTreeBase that is used to compute a normal dominator tree.
The instances of the Type class are immutable: once they are created, they are never changed.
The legacy pass manager's analysis pass to compute loop information.
void initializeTLSVariableHoistLegacyPassPass(PassRegistry &)
PreservedAnalyses run(Function &F, FunctionAnalysisManager &AM)
LLVM Basic Block Representation.
raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
LoopT * getParentLoop() const
Return the parent loop if it exists or nullptr for top level loops.
static PassRegistry * getPassRegistry()
getPassRegistry - Access the global registry object, which is automatically initialized at applicatio...
static GCRegistry::Add< CoreCLRGC > E("coreclr", "CoreCLR-compatible GC")
Represent the analysis usage information of a pass.
static bool runImpl(const TargetLibraryInfo &TLI, Function &F)
bool hasFnAttr(Attribute::AttrKind Kind) const
Return true if the attribute exists for the function.
Legacy analysis pass which computes a DominatorTree.
auto predecessors(MachineBasicBlock *BB)
unsigned ID
LLVM IR allows to use arbitrary numbers as calling convention identifiers.
#define INITIALIZE_PASS_END(passName, arg, name, cfg, analysis)
AttributeList getAttributes() const
Return the attribute list for this Function.
Module * getParent()
Get the module that this global value is contained inside of...
INITIALIZE_PASS_DEPENDENCY(DominatorTreeWrapperPass)
LoopT * getLoopFor(const BlockT *BB) const
Return the inner most loop that BB lives in.
initializer< Ty > init(const Ty &Val)
BlockT * getLoopPreheader() const
If there is a preheader for this loop, return it.
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
A Module instance is used to store all the information related to an LLVM module.
void setOperand(unsigned i, Value *Val)
bool any_of(R &&range, UnaryPredicate P)
Provide wrappers to std::any_of which take ranges instead of having to pass begin/end explicitly.
void setPreservesCFG()
This function should be called by the pass, iff they do not:
StringRef - Represent a constant reference to a string, i.e.
Represents analyses that only rely on functions' control flow.
self_iterator getIterator()
Keeps track of a TLS variable candidate and its users.
This is the base class for all instructions that perform data casts.
StringRef getName() const
Return a constant reference to the value's name.
FunctionPass * createTLSVariableHoistPass()
static bool runOnFunction(Function &F, bool PostInlining)
INITIALIZE_PASS_BEGIN(TLSVariableHoistLegacyPass, "tlshoist", "TLS Variable Hoist", false, false) INITIALIZE_PASS_END(TLSVariableHoistLegacyPass
static PreservedAnalyses all()
Construct a special preserved set that preserves all passes.
BlockT * getHeader() const
bool runImpl(Function &F, DominatorTree &DT, LoopInfo &LI)
Optimize expensive TLS variables in the given function.
Analysis pass which computes a DominatorTree.
const InstListType & getInstList() const
Return the underlying instruction list container.
void preserveSet()
Mark an analysis set as preserved.
unsigned getNumOperands() const
const BasicBlock * getParent() const
const Instruction * getTerminator() const LLVM_READONLY
Returns the terminator instruction if the block is well formed or null if the block is not well forme...
PointerType * getType() const
Global values are always pointers.
A container for analyses that lazily runs them and caches their results.
FunctionPass class - This class is used to implement most global optimizations.
Common register allocation spilling lr str ldr sxth r3 ldr mla r4 can lr mov lr str ldr sxth r3 mla r4 and then merge mul and lr str ldr sxth r3 mla r4 It also increase the likelihood the store may become dead bb27 Successors according to LLVM BB
AnalysisUsage & addRequired()
Value * getOperand(unsigned i) const
Analysis pass that exposes the LoopInfo for a function.