Skip to content

Commit

Permalink
[ValueTracking] Reduce duplication in haveNoCommonBitsSet() (NFC)
Browse files Browse the repository at this point in the history
Extract a function and call it with both operand orders, so that
we don't have to explicitly commute every single pattern.
  • Loading branch information
nikic committed Dec 1, 2023
1 parent 977af42 commit da86d4a
Showing 1 changed file with 24 additions and 26 deletions.
50 changes: 24 additions & 26 deletions llvm/lib/Analysis/ValueTracking.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -186,47 +186,30 @@ KnownBits llvm::computeKnownBits(const Value *V, const APInt &DemandedElts,
SimplifyQuery(DL, DT, AC, safeCxtI(V, CxtI), UseInstrInfo));
}

bool llvm::haveNoCommonBitsSet(const WithCache<const Value *> &LHSCache,
const WithCache<const Value *> &RHSCache,
const SimplifyQuery &SQ) {
const Value *LHS = LHSCache.getValue();
const Value *RHS = RHSCache.getValue();

assert(LHS->getType() == RHS->getType() &&
"LHS and RHS should have the same type");
assert(LHS->getType()->isIntOrIntVectorTy() &&
"LHS and RHS should be integers");
static bool haveNoCommonBitsSetSpecialCases(const Value *LHS,
const Value *RHS) {
// Look for an inverted mask: (X & ~M) op (Y & M).
{
Value *M;
if (match(LHS, m_c_And(m_Not(m_Value(M)), m_Value())) &&
match(RHS, m_c_And(m_Specific(M), m_Value())))
return true;
if (match(RHS, m_c_And(m_Not(m_Value(M)), m_Value())) &&
match(LHS, m_c_And(m_Specific(M), m_Value())))
return true;
}

// X op (Y & ~X)
if (match(RHS, m_c_And(m_Not(m_Specific(LHS)), m_Value())) ||
match(LHS, m_c_And(m_Not(m_Specific(RHS)), m_Value())))
if (match(RHS, m_c_And(m_Not(m_Specific(LHS)), m_Value())))
return true;

// X op ((X & Y) ^ Y) -- this is the canonical form of the previous pattern
// for constant Y.
Value *Y;
if (match(RHS,
m_c_Xor(m_c_And(m_Specific(LHS), m_Value(Y)), m_Deferred(Y))) ||
match(LHS, m_c_Xor(m_c_And(m_Specific(RHS), m_Value(Y)), m_Deferred(Y))))
if (match(RHS, m_c_Xor(m_c_And(m_Specific(LHS), m_Value(Y)), m_Deferred(Y))))
return true;

// Peek through extends to find a 'not' of the other side:
// (ext Y) op ext(~Y)
// (ext ~Y) op ext(Y)
if ((match(LHS, m_ZExtOrSExt(m_Value(Y))) &&
match(RHS, m_ZExtOrSExt(m_Not(m_Specific(Y))))) ||
(match(RHS, m_ZExtOrSExt(m_Value(Y))) &&
match(LHS, m_ZExtOrSExt(m_Not(m_Specific(Y))))))
if (match(LHS, m_ZExtOrSExt(m_Value(Y))) &&
match(RHS, m_ZExtOrSExt(m_Not(m_Specific(Y)))))
return true;

// Look for: (A & B) op ~(A | B)
Expand All @@ -235,11 +218,26 @@ bool llvm::haveNoCommonBitsSet(const WithCache<const Value *> &LHSCache,
if (match(LHS, m_And(m_Value(A), m_Value(B))) &&
match(RHS, m_Not(m_c_Or(m_Specific(A), m_Specific(B)))))
return true;
if (match(RHS, m_And(m_Value(A), m_Value(B))) &&
match(LHS, m_Not(m_c_Or(m_Specific(A), m_Specific(B)))))
return true;
}

return false;
}

bool llvm::haveNoCommonBitsSet(const WithCache<const Value *> &LHSCache,
const WithCache<const Value *> &RHSCache,
const SimplifyQuery &SQ) {
const Value *LHS = LHSCache.getValue();
const Value *RHS = RHSCache.getValue();

assert(LHS->getType() == RHS->getType() &&
"LHS and RHS should have the same type");
assert(LHS->getType()->isIntOrIntVectorTy() &&
"LHS and RHS should be integers");

if (haveNoCommonBitsSetSpecialCases(LHS, RHS) ||
haveNoCommonBitsSetSpecialCases(RHS, LHS))
return true;

return KnownBits::haveNoCommonBitsSet(LHSCache.getKnownBits(SQ),
RHSCache.getKnownBits(SQ));
}
Expand Down

0 comments on commit da86d4a

Please sign in to comment.