58#define DEBUG_TYPE "mem2reg"
60STATISTIC(NumLocalPromoted,
"Number of alloca's promoted within one block");
61STATISTIC(NumSingleStore,
"Number of alloca's promoted with a single store");
62STATISTIC(NumDeadAlloca,
"Number of dead alloca's removed");
63STATISTIC(NumPHIInsert,
"Number of PHI nodes inserted");
68 if (
const LoadInst *LI = dyn_cast<LoadInst>(U)) {
73 }
else if (
const StoreInst *SI = dyn_cast<StoreInst>(U)) {
74 if (SI->getValueOperand() == AI ||
82 if (!
II->isLifetimeStartOrEnd() && !
II->isDroppable())
84 }
else if (
const BitCastInst *BCI = dyn_cast<BitCastInst>(U)) {
88 if (!GEPI->hasAllZeroIndices())
120 DIB.insertDbgValueIntrinsic(NewValue, Variable,
Expression, DI, InsertBefore);
124class AssignmentTrackingInfo {
146 void updateForDeletedStore(
162 auto InsertValueForAssign = [&](
auto *DbgAssign,
auto *&AssignList) {
164 AssignList->insert(DbgAssign);
165 createDebugValue(DIB, DbgAssign->getValue(), DbgAssign->getVariable(),
166 DbgAssign->getExpression(), DbgAssign->getDebugLoc(),
170 InsertValueForAssign(Assign, DbgAssignsToDelete);
172 InsertValueForAssign(Assign, DVRAssignsToDelete);
182 auto ConvertUnlinkedAssignToValue = [&](
auto *
Assign) {
187 for_each(DbgAssigns, ConvertUnlinkedAssignToValue);
188 for_each(DVRAssigns, ConvertUnlinkedAssignToValue);
197 for (
auto *DAI : DbgAssigns)
199 for (
auto *DVR : DVRAssigns)
207 bool empty() {
return DbgAssigns.empty() && DVRAssigns.
empty(); }
219 bool OnlyUsedInOneBlock;
225 AssignmentTrackingInfo AssignmentTracking;
228 DefiningBlocks.
clear();
232 OnlyUsedInOneBlock =
true;
235 AssignmentTracking.clear();
260 if (OnlyUsedInOneBlock) {
262 OnlyBlock =
User->getParent();
263 else if (OnlyBlock !=
User->getParent())
264 OnlyUsedInOneBlock =
false;
267 DbgUserVec AllDbgUsers;
270 std::copy_if(AllDbgUsers.begin(), AllDbgUsers.end(),
272 return !isa<DbgAssignIntrinsic>(DII);
274 std::copy_if(AllDPUsers.
begin(), AllDPUsers.
end(),
275 std::back_inserter(DPUsers),
277 AssignmentTracking.init(AI);
282struct RenamePassData {
283 using ValVector = std::vector<Value *>;
284 using LocationVector = std::vector<DebugLoc>;
300class LargeBlockInfo {
311 static bool isInterestingInstruction(
const Instruction *
I) {
312 return (isa<LoadInst>(
I) && isa<AllocaInst>(
I->getOperand(0))) ||
313 (isa<StoreInst>(
I) && isa<AllocaInst>(
I->getOperand(1)));
318 assert(isInterestingInstruction(
I) &&
319 "Not a load/store to/from an alloca?");
323 if (It != InstNumbers.
end())
332 if (isInterestingInstruction(&BBI))
333 InstNumbers[&BBI] = InstNo++;
334 It = InstNumbers.
find(
I);
336 assert(It != InstNumbers.
end() &&
"Didn't insert instruction?");
345struct PromoteMem2Reg {
347 std::vector<AllocaInst *> Allocas;
402 : Allocas(Allocas.
begin(), Allocas.
end()), DT(DT),
404 AC(AC), SQ(DT.getRoot()->getDataLayout(),
410 void RemoveFromAllocasList(
unsigned &AllocaIdx) {
411 Allocas[AllocaIdx] = Allocas.back();
417 unsigned &NP = BBNumPreds[BB];
427 RenamePassData::ValVector &IncVals,
428 RenamePassData::LocationVector &IncLocs,
429 std::vector<RenamePassData> &Worklist);
430 bool QueuePhiNode(
BasicBlock *BB,
unsigned AllocaIdx,
unsigned &Version);
433 void cleanUpDbgAssigns() {
434 for (
auto *DAI : DbgAssignsToDelete)
435 DAI->eraseFromParent();
436 DbgAssignsToDelete.clear();
437 for (
auto *DVR : DVRAssignsToDelete)
438 DVR->eraseFromParent();
439 DVRAssignsToDelete.clear();
460 if (isa<UndefValue>(Val) && LI->
hasMetadata(LLVMContext::MD_noundef)) {
465 false,
Align(1), LI);
473 if (AC && LI->
getMetadata(LLVMContext::MD_nonnull) &&
485 if (isa<LoadInst>(
I) || isa<StoreInst>(
I))
489 if (
I->isDroppable()) {
490 I->dropDroppableUse(U);
494 if (!
I->getType()->isVoidTy()) {
499 Instruction *Inst = cast<Instruction>(UU.getUser());
509 I->eraseFromParent();
533 bool RequireDominatingStore =
539 Info.UsingBlocks.clear();
543 if (UserInst == OnlyStore)
545 LoadInst *LI = cast<LoadInst>(UserInst);
551 if (RequireDominatingStore) {
556 if (StoreIndex == -1)
557 StoreIndex = LBI.getInstructionIndex(OnlyStore);
559 if (
unsigned(StoreIndex) > LBI.getInstructionIndex(LI)) {
561 Info.UsingBlocks.push_back(StoreBB);
586 if (!
Info.UsingBlocks.empty())
591 Info.AssignmentTracking.updateForDeletedStore(
592 Info.OnlyStore, DIB, DbgAssignsToDelete, DVRAssignsToDelete);
596 auto ConvertDebugInfoForStore = [&](
auto &Container) {
597 for (
auto *DbgItem : Container) {
598 if (DbgItem->isAddressOfVariable()) {
600 DbgItem->eraseFromParent();
601 }
else if (DbgItem->getExpression()->startsWithDeref()) {
602 DbgItem->eraseFromParent();
606 ConvertDebugInfoForStore(
Info.DbgUsers);
607 ConvertDebugInfoForStore(
Info.DPUsers);
613 Info.OnlyStore->eraseFromParent();
614 LBI.deleteValue(
Info.OnlyStore);
649 StoresByIndexTy StoresByIndex;
652 if (
StoreInst *SI = dyn_cast<StoreInst>(U))
653 StoresByIndex.
push_back(std::make_pair(LBI.getInstructionIndex(SI), SI));
662 LoadInst *LI = dyn_cast<LoadInst>(U);
666 unsigned LoadIdx = LBI.getInstructionIndex(LI);
671 std::make_pair(LoadIdx,
static_cast<StoreInst *
>(
nullptr)),
674 if (
I == StoresByIndex.begin()) {
675 if (StoresByIndex.empty())
685 ReplVal = std::prev(
I)->second->getOperand(0);
705 Info.AssignmentTracking.updateForDeletedStore(SI, DIB, DbgAssignsToDelete,
708 auto DbgUpdateForStore = [&](
auto &Container) {
709 for (
auto *DbgItem : Container) {
710 if (DbgItem->isAddressOfVariable()) {
715 DbgUpdateForStore(
Info.DbgUsers);
716 DbgUpdateForStore(
Info.DPUsers);
718 SI->eraseFromParent();
727 auto DbgUpdateForAlloca = [&](
auto &Container) {
728 for (
auto *DbgItem : Container)
729 if (DbgItem->isAddressOfVariable() ||
730 DbgItem->getExpression()->startsWithDeref())
731 DbgItem->eraseFromParent();
733 DbgUpdateForAlloca(
Info.DbgUsers);
734 DbgUpdateForAlloca(
Info.DPUsers);
740void PromoteMem2Reg::run() {
743 AllocaDbgUsers.
resize(Allocas.size());
744 AllocaATInfo.
resize(Allocas.size());
745 AllocaDPUsers.
resize(Allocas.size());
751 NoSignedZeros =
F.getFnAttribute(
"no-signed-zeros-fp-math").getValueAsBool();
753 for (
unsigned AllocaNum = 0; AllocaNum != Allocas.size(); ++AllocaNum) {
758 "All allocas should be in the same function, which is same as DF!");
767 RemoveFromAllocasList(AllocaNum);
774 Info.AnalyzeAlloca(AI);
778 if (
Info.DefiningBlocks.size() == 1) {
780 &DbgAssignsToDelete, &DVRAssignsToDelete)) {
782 RemoveFromAllocasList(AllocaNum);
790 if (
Info.OnlyUsedInOneBlock &&
792 &DbgAssignsToDelete, &DVRAssignsToDelete)) {
794 RemoveFromAllocasList(AllocaNum);
800 if (BBNumbers.
empty()) {
803 BBNumbers[&BB] =
ID++;
807 if (!
Info.DbgUsers.empty())
808 AllocaDbgUsers[AllocaNum] =
Info.DbgUsers;
809 if (!
Info.AssignmentTracking.empty())
810 AllocaATInfo[AllocaNum] =
Info.AssignmentTracking;
811 if (!
Info.DPUsers.empty())
812 AllocaDPUsers[AllocaNum] =
Info.DPUsers;
815 AllocaLookup[Allocas[AllocaNum]] = AllocaNum;
819 Info.DefiningBlocks.end());
830 IDF.setLiveInBlocks(LiveInBlocks);
831 IDF.setDefiningBlocks(DefBlocks);
833 IDF.calculate(PHIBlocks);
835 return BBNumbers.
find(
A)->second < BBNumbers.
find(
B)->second;
840 QueuePhiNode(BB, AllocaNum, CurrentVersion);
843 if (Allocas.empty()) {
852 RenamePassData::ValVector Values(Allocas.size());
853 for (
unsigned i = 0, e = Allocas.size(); i != e; ++i)
858 RenamePassData::LocationVector
Locations(Allocas.size());
862 std::vector<RenamePassData> RenamePassWorkList;
863 RenamePassWorkList.emplace_back(&
F.front(),
nullptr, std::move(Values),
864 std::move(Locations));
866 RenamePassData RPD = std::move(RenamePassWorkList.back());
867 RenamePassWorkList.pop_back();
869 RenamePass(RPD.BB, RPD.Pred, RPD.Values, RPD.Locations, RenamePassWorkList);
870 }
while (!RenamePassWorkList.empty());
884 A->eraseFromParent();
888 auto RemoveDbgDeclares = [&](
auto &Container) {
889 for (
auto &DbgUsers : Container) {
890 for (
auto *DbgItem : DbgUsers)
891 if (DbgItem->isAddressOfVariable() ||
892 DbgItem->getExpression()->startsWithDeref())
893 DbgItem->eraseFromParent();
896 RemoveDbgDeclares(AllocaDbgUsers);
897 RemoveDbgDeclares(AllocaDPUsers);
903 bool EliminatedAPHI =
true;
904 while (EliminatedAPHI) {
905 EliminatedAPHI =
false;
913 E = NewPhiNodes.
end();
922 EliminatedAPHI =
true;
936 E = NewPhiNodes.
end();
942 if (&BB->
front() != SomePHI)
958 return BBNumbers.
find(
A)->second < BBNumbers.
find(
B)->second;
969 "PHI node has entry for a block which is not a predecessor!");
981 while ((SomePHI = dyn_cast<PHINode>(BBI++)) &&
998void PromoteMem2Reg::ComputeLiveInBlocks(
1006 Info.UsingBlocks.end());
1011 for (
unsigned i = 0, e = LiveInBlockWorklist.size(); i != e; ++i) {
1013 if (!DefBlocks.
count(BB))
1019 if (
StoreInst *SI = dyn_cast<StoreInst>(
I)) {
1020 if (
SI->getOperand(1) != AI)
1025 LiveInBlockWorklist[i] = LiveInBlockWorklist.
back();
1026 LiveInBlockWorklist.pop_back();
1032 if (
LoadInst *LI = dyn_cast<LoadInst>(
I))
1042 while (!LiveInBlockWorklist.empty()) {
1043 BasicBlock *BB = LiveInBlockWorklist.pop_back_val();
1047 if (!LiveInBlocks.
insert(BB).second)
1059 LiveInBlockWorklist.push_back(
P);
1067bool PromoteMem2Reg::QueuePhiNode(
BasicBlock *BB,
unsigned AllocaNo,
1068 unsigned &Version) {
1070 PHINode *&PN = NewPhiNodes[std::make_pair(BBNumbers[BB], AllocaNo)];
1078 PN =
PHINode::Create(Allocas[AllocaNo]->getAllocatedType(), getNumPreds(BB),
1079 Allocas[AllocaNo]->
getName() +
"." +
Twine(Version++));
1082 PhiToAllocaMap[PN] = AllocaNo;
1089 bool ApplyMergedLoc) {
1102 RenamePassData::ValVector &IncomingVals,
1103 RenamePassData::LocationVector &IncomingLocs,
1104 std::vector<RenamePassData> &Worklist) {
1111 if (PhiToAllocaMap.
count(APN)) {
1118 unsigned NewPHINumOperands = APN->getNumOperands();
1121 assert(NumEdges &&
"Must be at least one edge from Pred to BB!");
1126 unsigned AllocaNo = PhiToAllocaMap[APN];
1130 APN->getNumIncomingValues() > 0);
1133 for (
unsigned i = 0; i != NumEdges; ++i)
1134 APN->addIncoming(IncomingVals[AllocaNo], Pred);
1141 if (isa<FPMathOperator>(APN) && NoSignedZeros)
1142 APN->setHasNoSignedZeros(
true);
1145 IncomingVals[AllocaNo] = APN;
1146 AllocaATInfo[AllocaNo].updateForNewPhi(APN, DIB);
1147 auto ConvertDbgDeclares = [&](
auto &Container) {
1148 for (
auto *DbgItem : Container)
1149 if (DbgItem->isAddressOfVariable())
1152 ConvertDbgDeclares(AllocaDbgUsers[AllocaNo]);
1153 ConvertDbgDeclares(AllocaDPUsers[AllocaNo]);
1157 APN = dyn_cast<PHINode>(PNI);
1163 }
while (APN->getNumOperands() == NewPHINumOperands);
1168 if (!Visited.
insert(BB).second)
1174 if (
LoadInst *LI = dyn_cast<LoadInst>(
I)) {
1180 if (AI == AllocaLookup.
end())
1183 Value *
V = IncomingVals[AI->second];
1189 }
else if (
StoreInst *SI = dyn_cast<StoreInst>(
I)) {
1192 AllocaInst *Dest = dyn_cast<AllocaInst>(
SI->getPointerOperand());
1197 if (ai == AllocaLookup.
end())
1201 unsigned AllocaNo = ai->second;
1202 IncomingVals[AllocaNo] =
SI->getOperand(0);
1205 IncomingLocs[AllocaNo] =
SI->getDebugLoc();
1206 AllocaATInfo[AllocaNo].updateForDeletedStore(SI, DIB, &DbgAssignsToDelete,
1207 &DVRAssignsToDelete);
1208 auto ConvertDbgDeclares = [&](
auto &Container) {
1209 for (
auto *DbgItem : Container)
1210 if (DbgItem->isAddressOfVariable())
1213 ConvertDbgDeclares(AllocaDbgUsers[ai->second]);
1214 ConvertDbgDeclares(AllocaDPUsers[ai->second]);
1215 SI->eraseFromParent();
1234 if (VisitedSuccs.
insert(*I).second)
1235 Worklist.emplace_back(*
I, Pred, IncomingVals, IncomingLocs);
1243 if (Allocas.
empty())
1246 PromoteMem2Reg(Allocas, DT, AC).run();
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
static const Function * getParent(const Value *V)
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
static GCRegistry::Add< ErlangGC > A("erlang", "erlang-compatible garbage collector")
Analysis containing CSE Info
This file contains the declarations for the subclasses of Constant, which represent the different fla...
static void clear(coro::Shape &Shape)
This file defines the DenseMap class.
This file provides various utilities for inspecting and working with the control flow graph in LLVM I...
Module.h This file contains the declarations for the Module class.
uint64_t IntrinsicInst * II
static StringRef getName(Value *V)
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
static void ComputeLiveInBlocks(const SmallPtrSetImpl< BasicBlock * > &UsingBlocks, const SmallPtrSetImpl< BasicBlock * > &DefBlocks, SmallPtrSetImpl< BasicBlock * > &LiveInBlocks, PredIteratorCache &PredCache)
Given sets of UsingBlocks and DefBlocks, compute the set of LiveInBlocks.
This file defines the SmallPtrSet class.
This file defines the SmallVector class.
This file defines the 'Statistic' class, which is designed to be an easy way to expose various metric...
#define STATISTIC(VARNAME, DESC)
This class represents a conversion between pointers from one address space to another.
an instruction to allocate memory on the stack
Type * getAllocatedType() const
Return the type that is being allocated by the instruction.
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory),...
bool empty() const
empty - Check if the array is empty.
A cache of @llvm.assume calls within a function.
void registerAssumption(AssumeInst *CI)
Add an @llvm.assume intrinsic to this function's cache.
LLVM Basic Block Representation.
iterator begin()
Instruction iterator methods.
const Instruction & front() const
const Function * getParent() const
Return the enclosing method, or null if none.
InstListType::iterator iterator
Instruction iterators...
const Instruction & back() const
This class represents a no-op cast from one type to another.
This class represents a function call, abstracting a target machine's calling convention.
static CallInst * Create(FunctionType *Ty, Value *F, const Twine &NameStr="", InsertPosition InsertBefore=nullptr)
static ConstantInt * getTrue(LLVMContext &Context)
static Constant * getNullValue(Type *Ty)
Constructor to create a '0' constant of arbitrary type.
A parsed version of the target data layout string in and methods for querying it.
This represents the llvm.dbg.assign instruction.
This is the common base class for debug info intrinsics for variables.
Record of a variable value-assignment, aka a non instruction representation of the dbg....
static DbgVariableRecord * createDbgVariableRecord(Value *Location, DILocalVariable *DV, DIExpression *Expr, const DILocation *DI)
Identifies a unique instance of a whole variable (discards/ignores fragment information).
Identifies a unique instance of a variable.
iterator find(const_arg_type_t< KeyT > Val)
bool erase(const KeyT &Val)
size_type count(const_arg_type_t< KeyT > Val) const
Return 1 if the specified key is in the map, 0 otherwise.
Concrete subclass of DominatorTreeBase that is used to compute a normal dominator tree.
bool dominates(const BasicBlock *BB, const Use &U) const
Return true if the (end of the) basic block BB dominates the use U.
Class representing an expression and its matching format.
an instruction for type-safe pointer arithmetic to access elements of arrays and structs
This instruction compares its operands according to the predicate given to the constructor.
void insertBefore(Instruction *InsertPos)
Insert an unlinked instruction into a basic block immediately before the specified instruction.
const DebugLoc & getDebugLoc() const
Return the debug location for this node as a DebugLoc.
const Module * getModule() const
Return the module owning the function this instruction belongs to or nullptr it the function does not...
bool hasMetadata() const
Return true if this instruction has any metadata attached to it.
InstListType::iterator eraseFromParent()
This method unlinks 'this' from the containing basic block and deletes it.
Instruction * user_back()
Specialize the methods defined in Value, as we know that an instruction can only be used by other ins...
MDNode * getMetadata(unsigned KindID) const
Get the metadata of given kind attached to this Instruction.
void applyMergedLocation(DILocation *LocA, DILocation *LocB)
Merge 2 debug locations and apply it to the Instruction.
void setDebugLoc(DebugLoc Loc)
Set the debug location information for this instruction.
void insertAfter(Instruction *InsertPos)
Insert an unlinked instruction into a basic block immediately after the specified instruction.
A wrapper class for inspecting calls to intrinsic functions.
This is an important class for using LLVM in a threaded context.
An instruction for reading from memory.
Value * getPointerOperand()
void addIncoming(Value *V, BasicBlock *BB)
Add an incoming value to the end of the PHI list.
BasicBlock * getIncomingBlock(unsigned i) const
Return incoming basic block number i.
unsigned getNumIncomingValues() const
Return the number of incoming edges.
static PHINode * Create(Type *Ty, unsigned NumReservedValues, const Twine &NameStr="", InsertPosition InsertBefore=nullptr)
Constructors - NumReservedValues is a hint for the number of incoming edges that this phi node will h...
static PoisonValue * get(Type *T)
Static factory methods - Return an 'poison' object of the specified type.
A templated base class for SmallPtrSet which provides the typesafe interface that is common across al...
size_type count(ConstPtrType Ptr) const
count - Return 1 if the specified pointer is in the set, 0 otherwise.
std::pair< iterator, bool > insert(PtrType Ptr)
Inserts Ptr if and only if there is no element in the container equal to Ptr.
SmallPtrSet - This class implements a set which is optimized for holding SmallSize or less elements.
SmallSet - This maintains a set of unique values, optimizing for the case when the set is small (less...
bool contains(const T &V) const
Check if the SmallSet contains the given element.
std::pair< const_iterator, bool > insert(const T &V)
insert - Insert an element into the set if it isn't already there.
typename SuperClass::iterator iterator
void push_back(const T &Elt)
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
An instruction for storing to memory.
Twine - A lightweight data structure for efficiently representing the concatenation of temporary valu...
static UndefValue * get(Type *T)
Static factory methods - Return an 'undef' object of the specified type.
A Use represents the edge between a Value definition and its users.
Value * getOperand(unsigned i) const
bool isDroppable() const
A droppable user is a user for which uses can be dropped without affecting correctness and should be ...
LLVM Value Representation.
Type * getType() const
All values are typed, get the type of this value.
void replaceAllUsesWith(Value *V)
Change all uses of this to point to a new Value.
iterator_range< user_iterator > users()
static void dropDroppableUse(Use &U)
Remove the droppable use U.
LLVMContext & getContext() const
All values hold a context through their type.
iterator_range< use_iterator > uses()
const ParentTy * getParent() const
Function * getDeclaration(Module *M, ID id, ArrayRef< Type * > Tys=std::nullopt)
Create or insert an LLVM Function declaration for an intrinsic, and return it.
AssignmentMarkerRange getAssignmentMarkers(DIAssignID *ID)
Return a range of dbg.assign intrinsics which use \ID as an operand.
SmallVector< DbgVariableRecord * > getDVRAssignmentMarkers(const Instruction *Inst)
void deleteAssignmentMarkers(const Instruction *Inst)
Delete the llvm.dbg.assign intrinsics linked to Inst.
initializer< Ty > init(const Ty &Val)
PointerTypeMap run(const Module &M)
Compute the PointerTypeMap for the module M.
const_iterator begin(StringRef path, Style style=Style::native)
Get begin iterator over path.
const_iterator end(StringRef path)
Get end iterator over path.
This is an optimization pass for GlobalISel generic memory operations.
UnaryFunction for_each(R &&Range, UnaryFunction F)
Provide wrappers to std::for_each which take ranges instead of having to pass begin/end explicitly.
void PromoteMemToReg(ArrayRef< AllocaInst * > Allocas, DominatorTree &DT, AssumptionCache *AC=nullptr)
Promote the specified list of alloca instructions into scalar registers, inserting PHI nodes as appro...
void findDbgUsers(SmallVectorImpl< DbgVariableIntrinsic * > &DbgInsts, Value *V, SmallVectorImpl< DbgVariableRecord * > *DbgVariableRecords=nullptr)
Finds the debug info intrinsics describing a value.
auto successors(const MachineBasicBlock *BB)
bool onlyUsedByLifetimeMarkersOrDroppableInsts(const Value *V)
Return true if the only users of this pointer are lifetime markers or droppable instructions.
iterator_range< early_inc_iterator_impl< detail::IterOfRange< RangeT > > > make_early_inc_range(RangeT &&Range)
Make a range that does early increment to allow mutation of the underlying range without disrupting i...
bool isAllocaPromotable(const AllocaInst *AI)
Return true if this alloca is legal for promotion.
Value * simplifyInstruction(Instruction *I, const SimplifyQuery &Q)
See if we can compute a simplified version of this instruction.
void sort(IteratorTy Start, IteratorTy End)
void ConvertDebugDeclareToDebugValue(DbgVariableIntrinsic *DII, StoreInst *SI, DIBuilder &Builder)
===------------------------------------------------------------------—===// Dbg Intrinsic utilities
bool isKnownNonZero(const Value *V, const SimplifyQuery &Q, unsigned Depth=0)
Return true if the given value is known to be non-zero when defined.
RNSuccIterator< NodeRef, BlockT, RegionT > succ_begin(NodeRef Node)
bool onlyUsedByLifetimeMarkers(const Value *V)
Return true if the only users of this pointer are lifetime markers.
RNSuccIterator< NodeRef, BlockT, RegionT > succ_end(NodeRef Node)
auto lower_bound(R &&Range, T &&Value)
Provide wrappers to std::lower_bound which take ranges instead of having to pass begin/end explicitly...
auto count(R &&Range, const E &Element)
Wrapper function around std::count to count the number of times an element Element occurs in the give...
OutputIt move(R &&Range, OutputIt Out)
Provide wrappers to std::move which take ranges instead of having to pass begin/end explicitly.
auto predecessors(const MachineBasicBlock *BB)
bool isGuaranteedNotToBePoison(const Value *V, AssumptionCache *AC=nullptr, const Instruction *CtxI=nullptr, const DominatorTree *DT=nullptr, unsigned Depth=0)
Returns true if V cannot be poison, but may be undef.
unsigned pred_size(const MachineBasicBlock *BB)
Implement std::hash so that hash_code can be used in STL containers.
This struct is a compact representation of a valid (non-zero power of two) alignment.
Function object to check whether the first component of a container supported by std::get (like std::...