Skip to content
Merged
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
105 changes: 61 additions & 44 deletions llvm/lib/Analysis/ValueTracking.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3786,6 +3786,63 @@ static bool isNonEqualPointersWithRecursiveGEP(const Value *A, const Value *B,
(StartOffset.sle(OffsetB) && StepOffset.isNegative()));
}

static bool isKnownNonEqualFromContext(const Value *V1, const Value *V2,
unsigned Depth, const SimplifyQuery &Q) {
if (!Q.CxtI)
return false;

// Try to infer NonEqual based on information from dominating conditions.
if (Q.DC && Q.DT) {
auto IsKnownNonEqualFromDominatingCondition = [&](const Value *V) {
for (BranchInst *BI : Q.DC->conditionsFor(V)) {
Value *Cond = BI->getCondition();
BasicBlockEdge Edge0(BI->getParent(), BI->getSuccessor(0));
if (Q.DT->dominates(Edge0, Q.CxtI->getParent()) &&
isImpliedCondition(Cond, ICmpInst::ICMP_NE, V1, V2, Q.DL,
/*LHSIsTrue=*/true, Depth)
.value_or(false))
return true;

BasicBlockEdge Edge1(BI->getParent(), BI->getSuccessor(1));
if (Q.DT->dominates(Edge1, Q.CxtI->getParent()) &&
isImpliedCondition(Cond, ICmpInst::ICMP_NE, V1, V2, Q.DL,
/*LHSIsTrue=*/false, Depth)
.value_or(false))
return true;
}

return false;
};

if (IsKnownNonEqualFromDominatingCondition(V1) ||
IsKnownNonEqualFromDominatingCondition(V2))
return true;
}

if (!Q.AC)
return false;

// Try to infer NonEqual based on information from assumptions.
for (auto &AssumeVH : Q.AC->assumptionsFor(V1)) {
if (!AssumeVH)
continue;
CallInst *I = cast<CallInst>(AssumeVH);

assert(I->getFunction() == Q.CxtI->getFunction() &&
"Got assumption for the wrong function!");
assert(I->getIntrinsicID() == Intrinsic::assume &&
"must be an assume intrinsic");

if (isImpliedCondition(I->getArgOperand(0), ICmpInst::ICMP_NE, V1, V2, Q.DL,
/*LHSIsTrue=*/true, Depth)
.value_or(false) &&
isValidAssumeForContext(I, Q.CxtI, Q.DT))
return true;
}

return false;
}

/// Return true if it is known that V1 != V2.
static bool isKnownNonEqual(const Value *V1, const Value *V2,
const APInt &DemandedElts, unsigned Depth,
Expand Down Expand Up @@ -3857,49 +3914,8 @@ static bool isKnownNonEqual(const Value *V1, const Value *V2,
match(V2, m_PtrToIntSameSize(Q.DL, m_Value(B))))
return isKnownNonEqual(A, B, DemandedElts, Depth + 1, Q);

if (!Q.CxtI)
return false;

// Try to infer NonEqual based on information from dominating conditions.
if (Q.DC && Q.DT) {
for (BranchInst *BI : Q.DC->conditionsFor(V1)) {
Value *Cond = BI->getCondition();
BasicBlockEdge Edge0(BI->getParent(), BI->getSuccessor(0));
if (Q.DT->dominates(Edge0, Q.CxtI->getParent()) &&
isImpliedCondition(Cond, ICmpInst::ICMP_NE, V1, V2, Q.DL,
/*LHSIsTrue=*/true, Depth)
.value_or(false))
return true;

BasicBlockEdge Edge1(BI->getParent(), BI->getSuccessor(1));
if (Q.DT->dominates(Edge1, Q.CxtI->getParent()) &&
isImpliedCondition(Cond, ICmpInst::ICMP_NE, V1, V2, Q.DL,
/*LHSIsTrue=*/false, Depth)
.value_or(false))
return true;
}
}

if (!Q.AC)
return false;

// Try to infer NonEqual based on information from assumptions.
for (auto &AssumeVH : Q.AC->assumptionsFor(V1)) {
if (!AssumeVH)
continue;
CallInst *I = cast<CallInst>(AssumeVH);

assert(I->getFunction() == Q.CxtI->getFunction() &&
"Got assumption for the wrong function!");
assert(I->getIntrinsicID() == Intrinsic::assume &&
"must be an assume intrinsic");

if (isImpliedCondition(I->getArgOperand(0), ICmpInst::ICMP_NE, V1, V2, Q.DL,
/*LHSIsTrue=*/true, Depth)
.value_or(false) &&
isValidAssumeForContext(I, Q.CxtI, Q.DT))
return true;
}
if (isKnownNonEqualFromContext(V1, V2, Depth, Q))
return true;

return false;
}
Expand Down Expand Up @@ -10278,7 +10294,8 @@ void llvm::findValuesAffectedByCondition(
bool HasRHSC = match(B, m_ConstantInt());
if (ICmpInst::isEquality(Pred)) {
AddAffected(A);
AddAffected(B);
if (IsAssume)
AddAffected(B);
if (HasRHSC) {
Value *Y;
// (X & C) or (X | C).
Expand Down
Loading