55 #define DEBUG_TYPE "demanded-bits" 60 "Demanded bits analysis",
false,
false)
86 void DemandedBits::determineLiveOperandBits(
89 bool &KnownBitsComputed) {
98 auto ComputeKnownBits =
99 [&](
unsigned BitWidth,
const Value *V1,
const Value *
V2) {
100 if (KnownBitsComputed)
102 KnownBitsComputed =
true;
117 case Instruction::Invoke:
118 if (
const IntrinsicInst *II = dyn_cast<IntrinsicInst>(UserI))
119 switch (II->getIntrinsicID()) {
132 if (OperandNo == 0) {
136 ComputeKnownBits(BitWidth, Val,
nullptr);
142 if (OperandNo == 0) {
146 ComputeKnownBits(BitWidth, Val,
nullptr);
154 if (OperandNo == 2) {
162 uint64_t ShiftAmt = SA->
urem(BitWidth);
164 ShiftAmt = BitWidth - ShiftAmt;
167 AB = AOut.
lshr(ShiftAmt);
168 else if (OperandNo == 1)
169 AB = AOut.
shl(BitWidth - ShiftAmt);
176 case Instruction::Sub:
177 case Instruction::Mul:
183 case Instruction::Shl:
184 if (OperandNo == 0) {
185 const APInt *ShiftAmtC;
188 AB = AOut.
lshr(ShiftAmt);
200 case Instruction::LShr:
201 if (OperandNo == 0) {
202 const APInt *ShiftAmtC;
205 AB = AOut.
shl(ShiftAmt);
209 if (cast<LShrOperator>(UserI)->isExact())
214 case Instruction::AShr:
215 if (OperandNo == 0) {
216 const APInt *ShiftAmtC;
219 AB = AOut.
shl(ShiftAmt);
229 if (cast<AShrOperator>(UserI)->isExact())
234 case Instruction::And:
247 case Instruction::Or:
258 AB &= ~(Known.
One & ~Known2.
One);
260 case Instruction::Xor:
261 case Instruction::PHI:
264 case Instruction::Trunc:
265 AB = AOut.
zext(BitWidth);
267 case Instruction::ZExt:
268 AB = AOut.
trunc(BitWidth);
270 case Instruction::SExt:
271 AB = AOut.
trunc(BitWidth);
284 case Instruction::ExtractElement:
288 case Instruction::InsertElement:
289 case Instruction::ShuffleVector:
290 if (OperandNo == 0 || OperandNo == 1)
297 auto &AC = getAnalysis<AssumptionCacheTracker>().getAssumptionCache(F);
298 auto &DT = getAnalysis<DominatorTreeWrapperPass>().getDomTree();
299 DB.emplace(F, AC, DT);
307 void DemandedBits::performAnalysis() {
338 for (
Use &OI :
I.operands()) {
340 Type *T = J->getType();
353 while (!Worklist.
empty()) {
359 AOut = AliveBits[UserI];
366 Visited.insert(UserI);
369 bool KnownBitsComputed =
false;
377 if (!I && !isa<Argument>(OI))
380 Type *
T = OI->getType();
388 AB =
APInt(BitWidth, 0);
392 determineLiveOperandBits(UserI, OI, OI.getOperandNo(), AOut, AB,
393 Known, Known2, KnownBitsComputed);
396 if (AB.isNullValue())
397 DeadUses.insert(&OI);
406 APInt ABPrev(BitWidth, 0);
407 auto ABI = AliveBits.find(I);
408 if (ABI != AliveBits.end())
409 ABPrev = ABI->second;
411 APInt ABNew = AB | ABPrev;
412 if (ABNew != ABPrev || ABI == AliveBits.end()) {
413 AliveBits[
I] = std::move(ABNew);
417 }
else if (I && !Visited.count(I)) {
427 auto Found = AliveBits.find(I);
428 if (Found != AliveBits.end())
429 return Found->second;
439 return !Visited.count(I) && AliveBits.find(I) == AliveBits.end() &&
445 if (!(*U)->getType()->isIntOrIntVectorTy())
449 Instruction *UserI = cast<Instruction>(U->getUser());
454 if (DeadUses.count(U))
460 auto Found = AliveBits.find(UserI);
461 if (Found != AliveBits.end() && Found->second.isNullValue())
470 for (
auto &KV : AliveBits) {
472 <<
" for " << *KV.first <<
'\n';
void computeKnownBits(const Value *V, KnownBits &Known, const DataLayout &DL, unsigned Depth=0, AssumptionCache *AC=nullptr, const Instruction *CxtI=nullptr, const DominatorTree *DT=nullptr, OptimizationRemarkEmitter *ORE=nullptr, bool UseInstrInfo=true)
Determine which bits of V are known to be either zero or one and return them in the KnownZero/KnownOn...
A parsed version of the target data layout string in and methods for querying it. ...
void initializeDemandedBitsWrapperPassPass(PassRegistry &)
void setSignBit()
Set the sign bit to 1.
static PassRegistry * getPassRegistry()
getPassRegistry - Access the global registry object, which is automatically initialized at applicatio...
static APInt getAllOnesValue(unsigned numBits)
Get the all-ones value.
PassT::Result & getResult(IRUnitT &IR, ExtraArgTs... ExtraArgs)
Get the result of an analysis pass for a given IR unit.
LLVM_NODISCARD T pop_back_val()
This class represents lattice values for constants.
A Module instance is used to store all the information related to an LLVM module. ...
bool isInstructionDead(Instruction *I)
Return true if, during analysis, I could not be reached.
APInt zext(unsigned width) const
Zero extend to a new width.
static APInt getLowBitsSet(unsigned numBits, unsigned loBitsSet)
Get a value with low bits set.
An immutable pass that tracks lazily created AssumptionCache objects.
bool isTerminator() const
APInt trunc(unsigned width) const
Truncate to new width.
Analysis pass which computes a DominatorTree.
unsigned countMaxTrailingZeros() const
Returns the maximum number of trailing zero bits possible.
This defines the Use class.
unsigned getBitWidth() const
Return the number of bits in the APInt.
bool match(Val *V, const Pattern &P)
AnalysisUsage & addRequired()
#define INITIALIZE_PASS_DEPENDENCY(depName)
const DataLayout & getDataLayout() const
Get the data layout for the module's target platform.
APInt shl(unsigned shiftAmt) const
Left-shift function.
bool runOnFunction(Function &F) override
runOnFunction - Virtual method overriden by subclasses to do the per-function processing of the pass...
A Use represents the edge between a Value definition and its users.
void getAnalysisUsage(AnalysisUsage &AU) const override
getAnalysisUsage - This function should be overriden by passes that need analysis information to do t...
An analysis that produces DemandedBits for a function.
This file implements a class to represent arbitrary precision integral constant values and operations...
unsigned getActiveBits() const
Compute the number of active bits in the value.
Type * getType() const
All values are typed, get the type of this value.
bool insert(const value_type &X)
Insert a new element into the SetVector.
unsigned getOpcode() const
Returns a member of one of the enums like Instruction::Add.
DemandedBits run(Function &F, FunctionAnalysisManager &AM)
Run the analysis pass over a function and produce demanded bits information.
bool isIntOrIntVectorTy() const
Return true if this is an integer type or a vector of integer types.
APInt reverseBits() const
Value * getOperand(unsigned i) const
Type * getScalarType() const
If this is a vector type, return the element type, otherwise return 'this'.
static APInt getHighBitsSet(unsigned numBits, unsigned hiBitsSet)
Get a value with high bits set.
A set of analyses that are preserved following a run of a transformation pass.
* if(!EatIfPresent(lltok::kw_thread_local)) return false
ParseOptionalThreadLocal := /*empty.
apint_match m_APInt(const APInt *&Res)
Match a ConstantInt or splatted ConstantVector, binding the specified pointer to the contained APInt...
APInt urem(const APInt &RHS) const
Unsigned remainder operation.
constexpr bool isPowerOf2_32(uint32_t Value)
Return true if the argument is a power of two > 0.
The instances of the Type class are immutable: once they are created, they are never changed...
INITIALIZE_PASS_BEGIN(DemandedBitsWrapperPass, "demanded-bits", "Demanded bits analysis", false, false) INITIALIZE_PASS_END(DemandedBitsWrapperPass
This file contains the declarations for the subclasses of Constant, which represent the different fla...
bool mayHaveSideEffects() const
Return true if the instruction may have side effects.
Represent the analysis usage information of a pass.
FunctionPass class - This class is used to implement most global optimizations.
static void print(raw_ostream &Out, object::Archive::Kind Kind, T Val)
demanded Demanded bits analysis
static PreservedAnalyses all()
Construct a special preserved set that preserves all passes.
INITIALIZE_PASS_END(RegBankSelect, DEBUG_TYPE, "Assign register bank of generic virtual registers", false, false) RegBankSelect
APInt lshr(unsigned shiftAmt) const
Logical right-shift function.
A function analysis which provides an AssumptionCache.
PreservedAnalyses run(Function &F, FunctionAnalysisManager &AM)
A SetVector that performs no allocations if smaller than a certain size.
unsigned countMaxLeadingZeros() const
Returns the maximum number of leading zero bits possible.
unsigned getScalarSizeInBits() const LLVM_READONLY
If this is a vector type, return the getPrimitiveSizeInBits value for the element type...
Module.h This file contains the declarations for the Module class.
static Twine utohexstr(const uint64_t &Val)
void setPreservesCFG()
This function should be called by the pass, iff they do not:
APInt getDemandedBits(Instruction *I)
Return the bits demanded from instruction I.
raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
const Module * getModule() const
Return the module owning the function this instruction belongs to or nullptr it the function does not...
Class for arbitrary precision integers.
void setPreservesAll()
Set by analyses that do not transform their input at all.
bool hasNoSignedWrap() const
Test whether this operation is known to never undergo signed overflow, aka the nsw property...
void print(raw_ostream &OS, const Module *M) const override
print - Print out the internal state of the pass.
uint64_t getLimitedValue(uint64_t Limit=UINT64_MAX) const
If this value is smaller than the specified limit, return it, otherwise return the limit value...
bool empty() const
Determine if the SetVector is empty or not.
LLVM_NODISCARD std::enable_if<!is_simple_type< Y >::value, typename cast_retty< X, const Y >::ret_type >::type dyn_cast(const Y &Val)
bool isUseDead(Use *U)
Return whether this use is dead by means of not having any demanded bits.
LLVM Value Representation.
static bool isAlwaysLive(Instruction *I)
This class implements an extremely fast bulk output stream that can only output to a stream...
bool isEHPad() const
Return true if the instruction is a variety of EH-block.
inst_range instructions(Function *F)
A container for analyses that lazily runs them and caches their results.
Legacy analysis pass which computes a DominatorTree.
This header defines various interfaces for pass management in LLVM.
FunctionPass * createDemandedBitsWrapperPass()
Create a demanded bits analysis pass.
A special type used by analysis passes to provide an address that identifies that particular analysis...
void releaseMemory() override
Clean up memory in between runs.
void print(raw_ostream &OS)
A wrapper class for inspecting calls to intrinsic functions.
bool hasNoUnsignedWrap() const
Test whether this operation is known to never undergo unsigned overflow, aka the nuw property...