llvm.org GIT mirror llvm / 9da65a8
Match semantics of PointerMayBeCapturedBefore to its name by default As it turns out, the capture tracker named CaptureBefore used by AA, and now available via the PointerMayBeCapturedBefore function, would have been more-aptly named CapturedBeforeOrAt, because it considers captures at the instruction provided. This is not always what one wants, and it is difficult to get the strictly-before behavior given only the current interface. This adds an additional parameter which controls whether or not you want to include captures at the provided instruction. The default is not to include the instruction provided, so that 'Before' matches its name. No functionality change intended. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@213582 91177308-0d34-0410-b5e6-96231b3b80d8 Hal Finkel 5 years ago
3 changed file(s) with 17 addition(s) and 7 deletion(s). Raw diff Collapse all Expand all
3939 /// returning the value (or part of it) from the function counts as capturing
4040 /// it or not. The boolean StoreCaptures specified whether storing the value
4141 /// (or part of it) into memory anywhere automatically counts as capturing it
42 /// or not.
42 /// or not. Captures by the provided instruction are considered if the
43 /// final parameter is true.
4344 bool PointerMayBeCapturedBefore(const Value *V, bool ReturnCaptures,
4445 bool StoreCaptures, const Instruction *I,
45 DominatorTree *DT);
46 DominatorTree *DT, bool IncludeI = false);
4647
4748 /// This callback is used in conjunction with PointerMayBeCaptured. In
4849 /// addition to the interface here, you'll need to provide your own getters
407407 return AliasAnalysis::ModRef;
408408
409409 if (llvm::PointerMayBeCapturedBefore(Object, /* ReturnCaptures */ true,
410 /* StoreCaptures */ true, I, DT))
410 /* StoreCaptures */ true, I, DT,
411 /* include Object */ true))
411412 return AliasAnalysis::ModRef;
412413
413414 unsigned ArgNo = 0;
5656 /// Only support the case where the Value is defined in the same basic block
5757 /// as the given instruction and the use.
5858 struct CapturesBefore : public CaptureTracker {
59 CapturesBefore(bool ReturnCaptures, const Instruction *I, DominatorTree *DT)
59 CapturesBefore(bool ReturnCaptures, const Instruction *I, DominatorTree *DT,
60 bool IncludeI)
6061 : BeforeHere(I), DT(DT), ReturnCaptures(ReturnCaptures),
61 Captured(false) {}
62 IncludeI(IncludeI), Captured(false) {}
6263
6364 void tooManyUses() override { Captured = true; }
6465
6566 bool shouldExplore(const Use *U) override {
6667 Instruction *I = cast(U->getUser());
68 if (BeforeHere == I && !IncludeI)
69 return false;
70
6771 BasicBlock *BB = I->getParent();
6872 // We explore this usage only if the usage can reach "BeforeHere".
6973 // If use is not reachable from entry, there is no need to explore.
8387 return false;
8488
8589 Instruction *I = cast(U->getUser());
90 if (BeforeHere == I && !IncludeI)
91 return false;
92
8693 BasicBlock *BB = I->getParent();
8794 // Same logic as in shouldExplore.
8895 if (BeforeHere != I && !DT->isReachableFromEntry(BB))
98105 DominatorTree *DT;
99106
100107 bool ReturnCaptures;
108 bool IncludeI;
101109
102110 bool Captured;
103111 };
137145 /// or not.
138146 bool llvm::PointerMayBeCapturedBefore(const Value *V, bool ReturnCaptures,
139147 bool StoreCaptures, const Instruction *I,
140 DominatorTree *DT) {
148 DominatorTree *DT, bool IncludeI) {
141149 assert(!isa(V) &&
142150 "It doesn't make sense to ask whether a global is captured.");
143151
147155 // TODO: See comment in PointerMayBeCaptured regarding what could be done
148156 // with StoreCaptures.
149157
150 CapturesBefore CB(ReturnCaptures, I, DT);
158 CapturesBefore CB(ReturnCaptures, I, DT, IncludeI);
151159 PointerMayBeCaptured(V, &CB);
152160 return CB.Captured;
153161 }