aboutsummaryrefslogtreecommitdiff
path: root/contrib/llvm-project/llvm/lib/Analysis/CaptureTracking.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'contrib/llvm-project/llvm/lib/Analysis/CaptureTracking.cpp')
-rw-r--r--contrib/llvm-project/llvm/lib/Analysis/CaptureTracking.cpp60
1 files changed, 21 insertions, 39 deletions
diff --git a/contrib/llvm-project/llvm/lib/Analysis/CaptureTracking.cpp b/contrib/llvm-project/llvm/lib/Analysis/CaptureTracking.cpp
index 00e096af3110..7f8f7b26f8fe 100644
--- a/contrib/llvm-project/llvm/lib/Analysis/CaptureTracking.cpp
+++ b/contrib/llvm-project/llvm/lib/Analysis/CaptureTracking.cpp
@@ -16,7 +16,6 @@
//===----------------------------------------------------------------------===//
#include "llvm/Analysis/CaptureTracking.h"
-#include "llvm/ADT/SmallPtrSet.h"
#include "llvm/ADT/SmallSet.h"
#include "llvm/ADT/SmallVector.h"
#include "llvm/ADT/Statistic.h"
@@ -74,10 +73,8 @@ bool CaptureTracker::isDereferenceableOrNull(Value *O, const DataLayout &DL) {
namespace {
struct SimpleCaptureTracker : public CaptureTracker {
- explicit SimpleCaptureTracker(
-
- const SmallPtrSetImpl<const Value *> &EphValues, bool ReturnCaptures)
- : EphValues(EphValues), ReturnCaptures(ReturnCaptures) {}
+ explicit SimpleCaptureTracker(bool ReturnCaptures)
+ : ReturnCaptures(ReturnCaptures) {}
void tooManyUses() override {
LLVM_DEBUG(dbgs() << "Captured due to too many uses\n");
@@ -88,17 +85,12 @@ namespace {
if (isa<ReturnInst>(U->getUser()) && !ReturnCaptures)
return false;
- if (EphValues.contains(U->getUser()))
- return false;
-
LLVM_DEBUG(dbgs() << "Captured by: " << *U->getUser() << "\n");
Captured = true;
return true;
}
- const SmallPtrSetImpl<const Value *> &EphValues;
-
bool ReturnCaptures;
bool Captured = false;
@@ -166,9 +158,8 @@ namespace {
// escape are not in a cycle.
struct EarliestCaptures : public CaptureTracker {
- EarliestCaptures(bool ReturnCaptures, Function &F, const DominatorTree &DT,
- const SmallPtrSetImpl<const Value *> &EphValues)
- : EphValues(EphValues), DT(DT), ReturnCaptures(ReturnCaptures), F(F) {}
+ EarliestCaptures(bool ReturnCaptures, Function &F, const DominatorTree &DT)
+ : DT(DT), ReturnCaptures(ReturnCaptures), F(F) {}
void tooManyUses() override {
Captured = true;
@@ -180,9 +171,6 @@ namespace {
if (isa<ReturnInst>(I) && !ReturnCaptures)
return false;
- if (EphValues.contains(I))
- return false;
-
if (!EarliestCapture)
EarliestCapture = I;
else
@@ -194,8 +182,6 @@ namespace {
return false;
}
- const SmallPtrSetImpl<const Value *> &EphValues;
-
Instruction *EarliestCapture = nullptr;
const DominatorTree &DT;
@@ -217,17 +203,6 @@ namespace {
/// counts as capturing it or not.
bool llvm::PointerMayBeCaptured(const Value *V, bool ReturnCaptures,
bool StoreCaptures, unsigned MaxUsesToExplore) {
- SmallPtrSet<const Value *, 1> Empty;
- return PointerMayBeCaptured(V, ReturnCaptures, StoreCaptures, Empty,
- MaxUsesToExplore);
-}
-
-/// Variant of the above function which accepts a set of Values that are
-/// ephemeral and cannot cause pointers to escape.
-bool llvm::PointerMayBeCaptured(const Value *V, bool ReturnCaptures,
- bool StoreCaptures,
- const SmallPtrSetImpl<const Value *> &EphValues,
- unsigned MaxUsesToExplore) {
assert(!isa<GlobalValue>(V) &&
"It doesn't make sense to ask whether a global is captured.");
@@ -239,7 +214,7 @@ bool llvm::PointerMayBeCaptured(const Value *V, bool ReturnCaptures,
LLVM_DEBUG(dbgs() << "Captured?: " << *V << " = ");
- SimpleCaptureTracker SCT(EphValues, ReturnCaptures);
+ SimpleCaptureTracker SCT(ReturnCaptures);
PointerMayBeCaptured(V, &SCT, MaxUsesToExplore);
if (SCT.Captured)
++NumCaptured;
@@ -283,16 +258,14 @@ bool llvm::PointerMayBeCapturedBefore(const Value *V, bool ReturnCaptures,
return CB.Captured;
}
-Instruction *
-llvm::FindEarliestCapture(const Value *V, Function &F, bool ReturnCaptures,
- bool StoreCaptures, const DominatorTree &DT,
-
- const SmallPtrSetImpl<const Value *> &EphValues,
- unsigned MaxUsesToExplore) {
+Instruction *llvm::FindEarliestCapture(const Value *V, Function &F,
+ bool ReturnCaptures, bool StoreCaptures,
+ const DominatorTree &DT,
+ unsigned MaxUsesToExplore) {
assert(!isa<GlobalValue>(V) &&
"It doesn't make sense to ask whether a global is captured.");
- EarliestCaptures CB(ReturnCaptures, F, DT, EphValues);
+ EarliestCaptures CB(ReturnCaptures, F, DT);
PointerMayBeCaptured(V, &CB, MaxUsesToExplore);
if (CB.Captured)
++NumCapturedBefore;
@@ -304,7 +277,11 @@ llvm::FindEarliestCapture(const Value *V, Function &F, bool ReturnCaptures,
UseCaptureKind llvm::DetermineUseCaptureKind(
const Use &U,
function_ref<bool(Value *, const DataLayout &)> IsDereferenceableOrNull) {
- Instruction *I = cast<Instruction>(U.getUser());
+ Instruction *I = dyn_cast<Instruction>(U.getUser());
+
+ // TODO: Investigate non-instruction uses.
+ if (!I)
+ return UseCaptureKind::MAY_CAPTURE;
switch (I->getOpcode()) {
case Instruction::Call:
@@ -384,8 +361,13 @@ UseCaptureKind llvm::DetermineUseCaptureKind(
return UseCaptureKind::MAY_CAPTURE;
return UseCaptureKind::NO_CAPTURE;
}
- case Instruction::BitCast:
case Instruction::GetElementPtr:
+ // AA does not support pointers of vectors, so GEP vector splats need to
+ // be considered as captures.
+ if (I->getType()->isVectorTy())
+ return UseCaptureKind::MAY_CAPTURE;
+ return UseCaptureKind::PASSTHROUGH;
+ case Instruction::BitCast:
case Instruction::PHI:
case Instruction::Select:
case Instruction::AddrSpaceCast: