LLVM API Documentation
00001 //===-- SIAnnotateControlFlow.cpp - ------------------===// 00002 // 00003 // The LLVM Compiler Infrastructure 00004 // 00005 // This file is distributed under the University of Illinois Open Source 00006 // License. See LICENSE.TXT for details. 00007 // 00008 //===----------------------------------------------------------------------===// 00009 // 00010 /// \file 00011 /// Annotates the control flow with hardware specific intrinsics. 00012 // 00013 //===----------------------------------------------------------------------===// 00014 00015 #include "AMDGPU.h" 00016 #include "llvm/ADT/DepthFirstIterator.h" 00017 #include "llvm/IR/Constants.h" 00018 #include "llvm/IR/Dominators.h" 00019 #include "llvm/IR/Instructions.h" 00020 #include "llvm/IR/Module.h" 00021 #include "llvm/Pass.h" 00022 #include "llvm/Transforms/Utils/BasicBlockUtils.h" 00023 #include "llvm/Transforms/Utils/SSAUpdater.h" 00024 00025 using namespace llvm; 00026 00027 #define DEBUG_TYPE "si-annotate-control-flow" 00028 00029 namespace { 00030 00031 // Complex types used in this pass 00032 typedef std::pair<BasicBlock *, Value *> StackEntry; 00033 typedef SmallVector<StackEntry, 16> StackVector; 00034 00035 // Intrinsic names the control flow is annotated with 00036 static const char *const IfIntrinsic = "llvm.SI.if"; 00037 static const char *const ElseIntrinsic = "llvm.SI.else"; 00038 static const char *const BreakIntrinsic = "llvm.SI.break"; 00039 static const char *const IfBreakIntrinsic = "llvm.SI.if.break"; 00040 static const char *const ElseBreakIntrinsic = "llvm.SI.else.break"; 00041 static const char *const LoopIntrinsic = "llvm.SI.loop"; 00042 static const char *const EndCfIntrinsic = "llvm.SI.end.cf"; 00043 00044 class SIAnnotateControlFlow : public FunctionPass { 00045 00046 static char ID; 00047 00048 Type *Boolean; 00049 Type *Void; 00050 Type *Int64; 00051 Type *ReturnStruct; 00052 00053 ConstantInt *BoolTrue; 00054 ConstantInt *BoolFalse; 00055 UndefValue *BoolUndef; 00056 Constant *Int64Zero; 00057 00058 Constant *If; 00059 Constant *Else; 00060 Constant *Break; 00061 Constant *IfBreak; 00062 Constant *ElseBreak; 00063 Constant *Loop; 00064 Constant *EndCf; 00065 00066 DominatorTree *DT; 00067 StackVector Stack; 00068 00069 bool isTopOfStack(BasicBlock *BB); 00070 00071 Value *popSaved(); 00072 00073 void push(BasicBlock *BB, Value *Saved); 00074 00075 bool isElse(PHINode *Phi); 00076 00077 void eraseIfUnused(PHINode *Phi); 00078 00079 void openIf(BranchInst *Term); 00080 00081 void insertElse(BranchInst *Term); 00082 00083 Value *handleLoopCondition(Value *Cond, PHINode *Broken); 00084 00085 void handleLoop(BranchInst *Term); 00086 00087 void closeControlFlow(BasicBlock *BB); 00088 00089 public: 00090 SIAnnotateControlFlow(): 00091 FunctionPass(ID) { } 00092 00093 bool doInitialization(Module &M) override; 00094 00095 bool runOnFunction(Function &F) override; 00096 00097 const char *getPassName() const override { 00098 return "SI annotate control flow"; 00099 } 00100 00101 void getAnalysisUsage(AnalysisUsage &AU) const override { 00102 AU.addRequired<DominatorTreeWrapperPass>(); 00103 AU.addPreserved<DominatorTreeWrapperPass>(); 00104 FunctionPass::getAnalysisUsage(AU); 00105 } 00106 00107 }; 00108 00109 } // end anonymous namespace 00110 00111 char SIAnnotateControlFlow::ID = 0; 00112 00113 /// \brief Initialize all the types and constants used in the pass 00114 bool SIAnnotateControlFlow::doInitialization(Module &M) { 00115 LLVMContext &Context = M.getContext(); 00116 00117 Void = Type::getVoidTy(Context); 00118 Boolean = Type::getInt1Ty(Context); 00119 Int64 = Type::getInt64Ty(Context); 00120 ReturnStruct = StructType::get(Boolean, Int64, (Type *)nullptr); 00121 00122 BoolTrue = ConstantInt::getTrue(Context); 00123 BoolFalse = ConstantInt::getFalse(Context); 00124 BoolUndef = UndefValue::get(Boolean); 00125 Int64Zero = ConstantInt::get(Int64, 0); 00126 00127 If = M.getOrInsertFunction( 00128 IfIntrinsic, ReturnStruct, Boolean, (Type *)nullptr); 00129 00130 Else = M.getOrInsertFunction( 00131 ElseIntrinsic, ReturnStruct, Int64, (Type *)nullptr); 00132 00133 Break = M.getOrInsertFunction( 00134 BreakIntrinsic, Int64, Int64, (Type *)nullptr); 00135 00136 IfBreak = M.getOrInsertFunction( 00137 IfBreakIntrinsic, Int64, Boolean, Int64, (Type *)nullptr); 00138 00139 ElseBreak = M.getOrInsertFunction( 00140 ElseBreakIntrinsic, Int64, Int64, Int64, (Type *)nullptr); 00141 00142 Loop = M.getOrInsertFunction( 00143 LoopIntrinsic, Boolean, Int64, (Type *)nullptr); 00144 00145 EndCf = M.getOrInsertFunction( 00146 EndCfIntrinsic, Void, Int64, (Type *)nullptr); 00147 00148 return false; 00149 } 00150 00151 /// \brief Is BB the last block saved on the stack ? 00152 bool SIAnnotateControlFlow::isTopOfStack(BasicBlock *BB) { 00153 return !Stack.empty() && Stack.back().first == BB; 00154 } 00155 00156 /// \brief Pop the last saved value from the control flow stack 00157 Value *SIAnnotateControlFlow::popSaved() { 00158 return Stack.pop_back_val().second; 00159 } 00160 00161 /// \brief Push a BB and saved value to the control flow stack 00162 void SIAnnotateControlFlow::push(BasicBlock *BB, Value *Saved) { 00163 Stack.push_back(std::make_pair(BB, Saved)); 00164 } 00165 00166 /// \brief Can the condition represented by this PHI node treated like 00167 /// an "Else" block? 00168 bool SIAnnotateControlFlow::isElse(PHINode *Phi) { 00169 BasicBlock *IDom = DT->getNode(Phi->getParent())->getIDom()->getBlock(); 00170 for (unsigned i = 0, e = Phi->getNumIncomingValues(); i != e; ++i) { 00171 if (Phi->getIncomingBlock(i) == IDom) { 00172 00173 if (Phi->getIncomingValue(i) != BoolTrue) 00174 return false; 00175 00176 } else { 00177 if (Phi->getIncomingValue(i) != BoolFalse) 00178 return false; 00179 00180 } 00181 } 00182 return true; 00183 } 00184 00185 // \brief Erase "Phi" if it is not used any more 00186 void SIAnnotateControlFlow::eraseIfUnused(PHINode *Phi) { 00187 if (!Phi->hasNUsesOrMore(1)) 00188 Phi->eraseFromParent(); 00189 } 00190 00191 /// \brief Open a new "If" block 00192 void SIAnnotateControlFlow::openIf(BranchInst *Term) { 00193 Value *Ret = CallInst::Create(If, Term->getCondition(), "", Term); 00194 Term->setCondition(ExtractValueInst::Create(Ret, 0, "", Term)); 00195 push(Term->getSuccessor(1), ExtractValueInst::Create(Ret, 1, "", Term)); 00196 } 00197 00198 /// \brief Close the last "If" block and open a new "Else" block 00199 void SIAnnotateControlFlow::insertElse(BranchInst *Term) { 00200 Value *Ret = CallInst::Create(Else, popSaved(), "", Term); 00201 Term->setCondition(ExtractValueInst::Create(Ret, 0, "", Term)); 00202 push(Term->getSuccessor(1), ExtractValueInst::Create(Ret, 1, "", Term)); 00203 } 00204 00205 /// \brief Recursively handle the condition leading to a loop 00206 Value *SIAnnotateControlFlow::handleLoopCondition(Value *Cond, PHINode *Broken) { 00207 if (PHINode *Phi = dyn_cast<PHINode>(Cond)) { 00208 BasicBlock *Parent = Phi->getParent(); 00209 PHINode *NewPhi = PHINode::Create(Int64, 0, "", &Parent->front()); 00210 Value *Ret = NewPhi; 00211 00212 // Handle all non-constant incoming values first 00213 for (unsigned i = 0, e = Phi->getNumIncomingValues(); i != e; ++i) { 00214 Value *Incoming = Phi->getIncomingValue(i); 00215 BasicBlock *From = Phi->getIncomingBlock(i); 00216 if (isa<ConstantInt>(Incoming)) { 00217 NewPhi->addIncoming(Broken, From); 00218 continue; 00219 } 00220 00221 Phi->setIncomingValue(i, BoolFalse); 00222 Value *PhiArg = handleLoopCondition(Incoming, Broken); 00223 NewPhi->addIncoming(PhiArg, From); 00224 } 00225 00226 BasicBlock *IDom = DT->getNode(Parent)->getIDom()->getBlock(); 00227 00228 for (unsigned i = 0, e = Phi->getNumIncomingValues(); i != e; ++i) { 00229 00230 Value *Incoming = Phi->getIncomingValue(i); 00231 if (Incoming != BoolTrue) 00232 continue; 00233 00234 BasicBlock *From = Phi->getIncomingBlock(i); 00235 if (From == IDom) { 00236 CallInst *OldEnd = dyn_cast<CallInst>(Parent->getFirstInsertionPt()); 00237 if (OldEnd && OldEnd->getCalledFunction() == EndCf) { 00238 Value *Args[] = { OldEnd->getArgOperand(0), NewPhi }; 00239 Ret = CallInst::Create(ElseBreak, Args, "", OldEnd); 00240 continue; 00241 } 00242 } 00243 TerminatorInst *Insert = From->getTerminator(); 00244 Value *PhiArg = CallInst::Create(Break, Broken, "", Insert); 00245 NewPhi->setIncomingValue(i, PhiArg); 00246 } 00247 eraseIfUnused(Phi); 00248 return Ret; 00249 00250 } else if (Instruction *Inst = dyn_cast<Instruction>(Cond)) { 00251 BasicBlock *Parent = Inst->getParent(); 00252 TerminatorInst *Insert = Parent->getTerminator(); 00253 Value *Args[] = { Cond, Broken }; 00254 return CallInst::Create(IfBreak, Args, "", Insert); 00255 00256 } else { 00257 llvm_unreachable("Unhandled loop condition!"); 00258 } 00259 return 0; 00260 } 00261 00262 /// \brief Handle a back edge (loop) 00263 void SIAnnotateControlFlow::handleLoop(BranchInst *Term) { 00264 BasicBlock *Target = Term->getSuccessor(1); 00265 PHINode *Broken = PHINode::Create(Int64, 0, "", &Target->front()); 00266 00267 Value *Cond = Term->getCondition(); 00268 Term->setCondition(BoolTrue); 00269 Value *Arg = handleLoopCondition(Cond, Broken); 00270 00271 BasicBlock *BB = Term->getParent(); 00272 for (pred_iterator PI = pred_begin(Target), PE = pred_end(Target); 00273 PI != PE; ++PI) { 00274 00275 Broken->addIncoming(*PI == BB ? Arg : Int64Zero, *PI); 00276 } 00277 00278 Term->setCondition(CallInst::Create(Loop, Arg, "", Term)); 00279 push(Term->getSuccessor(0), Arg); 00280 } 00281 00282 /// \brief Close the last opened control flow 00283 void SIAnnotateControlFlow::closeControlFlow(BasicBlock *BB) { 00284 CallInst::Create(EndCf, popSaved(), "", BB->getFirstInsertionPt()); 00285 } 00286 00287 /// \brief Annotate the control flow with intrinsics so the backend can 00288 /// recognize if/then/else and loops. 00289 bool SIAnnotateControlFlow::runOnFunction(Function &F) { 00290 DT = &getAnalysis<DominatorTreeWrapperPass>().getDomTree(); 00291 00292 for (df_iterator<BasicBlock *> I = df_begin(&F.getEntryBlock()), 00293 E = df_end(&F.getEntryBlock()); I != E; ++I) { 00294 00295 BranchInst *Term = dyn_cast<BranchInst>((*I)->getTerminator()); 00296 00297 if (!Term || Term->isUnconditional()) { 00298 if (isTopOfStack(*I)) 00299 closeControlFlow(*I); 00300 continue; 00301 } 00302 00303 if (I.nodeVisited(Term->getSuccessor(1))) { 00304 if (isTopOfStack(*I)) 00305 closeControlFlow(*I); 00306 handleLoop(Term); 00307 continue; 00308 } 00309 00310 if (isTopOfStack(*I)) { 00311 PHINode *Phi = dyn_cast<PHINode>(Term->getCondition()); 00312 if (Phi && Phi->getParent() == *I && isElse(Phi)) { 00313 insertElse(Term); 00314 eraseIfUnused(Phi); 00315 continue; 00316 } 00317 closeControlFlow(*I); 00318 } 00319 openIf(Term); 00320 } 00321 00322 assert(Stack.empty()); 00323 return true; 00324 } 00325 00326 /// \brief Create the annotation pass 00327 FunctionPass *llvm::createSIAnnotateControlFlowPass() { 00328 return new SIAnnotateControlFlow(); 00329 }