[ValueTracking] Introduce a KnownBits struct to wrap the two APInts for computeKnownBits
This patch introduces a new KnownBits struct that wraps the two APInt used by computeKnownBits. This allows us to treat them as more of a unit. Initially I've just altered the signatures of computeKnownBits and InstCombine's simplifyDemandedBits to pass a KnownBits reference instead of two separate APInt references. I'll do similar to the SelectionDAG version of computeKnownBits/simplifyDemandedBits as a separate patch. I've added a constructor that allows initializing both APInts to the same bit width with a starting value of 0. This reduces the repeated pattern of initializing both APInts. Once place default constructed the APInts so I added a default constructor for those cases. Going forward I would like to add more methods that will work on the pairs. For example trunc, zext, and sext occur on both APInts together in several places. We should probably add a clear method that can be used to clear both pieces. Maybe a method to check for conflicting information. A method to return (Zero|One) so we don't write it out everywhere. Maybe a method for (Zero|One).isAllOnesValue() to determine if all bits are known. I'm sure there are many other methods we can come up with. Differential Revision: https://reviews.llvm.org/D32376 llvm-svn: 301432
This commit is contained in:
@@ -60,6 +60,7 @@
|
||||
#include "llvm/Support/CommandLine.h"
|
||||
#include "llvm/Support/Debug.h"
|
||||
#include "llvm/Support/ErrorHandling.h"
|
||||
#include "llvm/Support/KnownBits.h"
|
||||
#include "llvm/Support/MathExtras.h"
|
||||
#include "llvm/Support/raw_ostream.h"
|
||||
#include "llvm/Transforms/Utils/BasicBlockUtils.h"
|
||||
@@ -4367,8 +4368,8 @@ static bool EliminateDeadSwitchCases(SwitchInst *SI, AssumptionCache *AC,
|
||||
const DataLayout &DL) {
|
||||
Value *Cond = SI->getCondition();
|
||||
unsigned Bits = Cond->getType()->getIntegerBitWidth();
|
||||
APInt KnownZero(Bits, 0), KnownOne(Bits, 0);
|
||||
computeKnownBits(Cond, KnownZero, KnownOne, DL, 0, AC, SI);
|
||||
KnownBits Known(Bits);
|
||||
computeKnownBits(Cond, Known, DL, 0, AC, SI);
|
||||
|
||||
// We can also eliminate cases by determining that their values are outside of
|
||||
// the limited range of the condition based on how many significant (non-sign)
|
||||
@@ -4380,7 +4381,7 @@ static bool EliminateDeadSwitchCases(SwitchInst *SI, AssumptionCache *AC,
|
||||
SmallVector<ConstantInt *, 8> DeadCases;
|
||||
for (auto &Case : SI->cases()) {
|
||||
APInt CaseVal = Case.getCaseValue()->getValue();
|
||||
if (KnownZero.intersects(CaseVal) || !KnownOne.isSubsetOf(CaseVal) ||
|
||||
if (Known.Zero.intersects(CaseVal) || !Known.One.isSubsetOf(CaseVal) ||
|
||||
(CaseVal.getMinSignedBits() > MaxSignificantBitsInCond)) {
|
||||
DeadCases.push_back(Case.getCaseValue());
|
||||
DEBUG(dbgs() << "SimplifyCFG: switch case " << CaseVal << " is dead.\n");
|
||||
@@ -4394,7 +4395,7 @@ static bool EliminateDeadSwitchCases(SwitchInst *SI, AssumptionCache *AC,
|
||||
bool HasDefault =
|
||||
!isa<UnreachableInst>(SI->getDefaultDest()->getFirstNonPHIOrDbg());
|
||||
const unsigned NumUnknownBits =
|
||||
Bits - (KnownZero | KnownOne).countPopulation();
|
||||
Bits - (Known.Zero | Known.One).countPopulation();
|
||||
assert(NumUnknownBits <= Bits);
|
||||
if (HasDefault && DeadCases.empty() &&
|
||||
NumUnknownBits < 64 /* avoid overflow */ &&
|
||||
|
||||
Reference in New Issue
Block a user