59#include "llvm/IR/IntrinsicsWebAssembly.h"
93#define DEBUG_TYPE "local"
95STATISTIC(NumRemoved,
"Number of unreachable basic blocks removed");
96STATISTIC(NumPHICSEs,
"Number of PHI's that got CSE'd");
100#ifdef EXPENSIVE_CHECKS
106 cl::desc(
"Perform extra assertion checking to verify that PHINodes's hash "
107 "function is well-behaved w.r.t. its isEqual predicate"));
112 "When the basic block contains not more than this number of PHI nodes, "
113 "perform a (faster!) exhaustive search instead of set-driven one."));
116 "max-phi-entries-increase-after-removing-empty-block",
cl::init(1000),
118 cl::desc(
"Stop removing an empty block if removing it will introduce more "
119 "than this number of phi entries in its successor"));
143 if (
auto *BI = dyn_cast<BranchInst>(
T)) {
144 if (BI->isUnconditional())
return false;
149 if (Dest2 == Dest1) {
155 assert(BI->getParent() &&
"Terminator not inserted in block!");
162 NewBI->
copyMetadata(*BI, {LLVMContext::MD_loop, LLVMContext::MD_dbg,
163 LLVMContext::MD_annotation});
166 BI->eraseFromParent();
167 if (DeleteDeadConditions)
172 if (
auto *
Cond = dyn_cast<ConstantInt>(BI->getCondition())) {
186 NewBI->
copyMetadata(*BI, {LLVMContext::MD_loop, LLVMContext::MD_dbg,
187 LLVMContext::MD_annotation});
189 BI->eraseFromParent();
191 DTU->
applyUpdates({{DominatorTree::Delete, BB, OldDest}});
198 if (
auto *SI = dyn_cast<SwitchInst>(
T)) {
201 auto *CI = dyn_cast<ConstantInt>(SI->getCondition());
202 BasicBlock *DefaultDest = SI->getDefaultDest();
207 SI->getNumCases() > 0) {
208 TheOnlyDest = SI->case_begin()->getCaseSuccessor();
211 bool Changed =
false;
214 for (
auto It = SI->case_begin(),
End = SI->case_end(); It !=
End;) {
216 if (It->getCaseValue() == CI) {
217 TheOnlyDest = It->getCaseSuccessor();
223 if (It->getCaseSuccessor() == DefaultDest) {
225 unsigned NCases = SI->getNumCases();
228 if (NCases > 1 && MD) {
234 unsigned Idx = It->getCaseIndex();
236 Weights[0] += Weights[
Idx + 1];
245 It = SI->removeCase(It);
246 End = SI->case_end();
250 if (
auto *NewCI = dyn_cast<ConstantInt>(SI->getCondition())) {
252 It = SI->case_begin();
262 if (It->getCaseSuccessor() != TheOnlyDest)
263 TheOnlyDest =
nullptr;
269 if (CI && !TheOnlyDest) {
272 TheOnlyDest = SI->getDefaultDest();
287 if (DTU && Succ != TheOnlyDest)
288 RemovedSuccessors.
insert(Succ);
290 if (Succ == SuccToKeep) {
291 SuccToKeep =
nullptr;
299 SI->eraseFromParent();
300 if (DeleteDeadConditions)
303 std::vector<DominatorTree::UpdateType> Updates;
304 Updates.reserve(RemovedSuccessors.
size());
305 for (
auto *RemovedSuccessor : RemovedSuccessors)
306 Updates.push_back({DominatorTree::Delete, BB, RemovedSuccessor});
312 if (SI->getNumCases() == 1) {
315 auto FirstCase = *SI->case_begin();
317 FirstCase.getCaseValue(),
"cond");
321 FirstCase.getCaseSuccessor(),
322 SI->getDefaultDest());
334 MDNode *MakeImplicitMD = SI->getMetadata(LLVMContext::MD_make_implicit);
336 NewBr->
setMetadata(LLVMContext::MD_make_implicit, MakeImplicitMD);
339 SI->eraseFromParent();
345 if (
auto *IBI = dyn_cast<IndirectBrInst>(
T)) {
348 dyn_cast<BlockAddress>(IBI->getAddress()->stripPointerCasts())) {
349 BasicBlock *TheOnlyDest = BA->getBasicBlock();
356 for (
unsigned i = 0, e = IBI->getNumDestinations(); i != e; ++i) {
358 if (DTU && DestBB != TheOnlyDest)
359 RemovedSuccessors.
insert(DestBB);
360 if (IBI->getDestination(i) == SuccToKeep) {
361 SuccToKeep =
nullptr;
367 IBI->eraseFromParent();
368 if (DeleteDeadConditions)
375 BA->destroyConstant();
386 std::vector<DominatorTree::UpdateType> Updates;
387 Updates.reserve(RemovedSuccessors.
size());
388 for (
auto *RemovedSuccessor : RemovedSuccessors)
389 Updates.push_back({DominatorTree::Delete, BB, RemovedSuccessor});
418 if (
II->getIntrinsicID() == Intrinsic::stacksave ||
419 II->getIntrinsicID() == Intrinsic::launder_invariant_group ||
420 II->isLifetimeStartOrEnd())
427 if (
I->isTerminator())
436 if (isa<DbgVariableIntrinsic>(
I))
445 if (
auto *CB = dyn_cast<CallBase>(
I))
449 if (!
I->willReturn()) {
450 auto *
II = dyn_cast<IntrinsicInst>(
I);
454 switch (
II->getIntrinsicID()) {
455 case Intrinsic::experimental_guard: {
459 auto *
Cond = dyn_cast<ConstantInt>(
II->getArgOperand(0));
464 case Intrinsic::wasm_trunc_signed:
465 case Intrinsic::wasm_trunc_unsigned:
466 case Intrinsic::ptrauth_auth:
467 case Intrinsic::ptrauth_resign:
474 if (!
I->mayHaveSideEffects())
481 if (
II->getIntrinsicID() == Intrinsic::stacksave ||
482 II->getIntrinsicID() == Intrinsic::launder_invariant_group)
487 if (
II->getIntrinsicID() == Intrinsic::allow_runtime_check ||
488 II->getIntrinsicID() == Intrinsic::allow_ubsan_check)
491 if (
II->isLifetimeStartOrEnd()) {
492 auto *Arg =
II->getArgOperand(1);
494 if (isa<UndefValue>(Arg))
498 if (isa<AllocaInst>(Arg) || isa<GlobalValue>(Arg) || isa<Argument>(Arg))
500 return isa<LifetimeIntrinsic>(Use.getUser());
506 if (
II->getIntrinsicID() == Intrinsic::assume &&
509 return !
Cond->isZero();
514 if (
auto *FPI = dyn_cast<ConstrainedFPIntrinsic>(
I)) {
515 std::optional<fp::ExceptionBehavior> ExBehavior =
516 FPI->getExceptionBehavior();
521 if (
auto *Call = dyn_cast<CallBase>(
I)) {
523 if (
Constant *
C = dyn_cast<Constant>(FreedOp))
524 return C->isNullValue() || isa<UndefValue>(
C);
530 if (
auto *LI = dyn_cast<LoadInst>(
I))
531 if (
auto *GV = dyn_cast<GlobalVariable>(
532 LI->getPointerOperand()->stripPointerCasts()))
533 if (!LI->isVolatile() && GV->isConstant())
545 std::function<
void(
Value *)> AboutToDeleteCallback) {
553 AboutToDeleteCallback);
561 std::function<
void(
Value *)> AboutToDeleteCallback) {
562 unsigned S = 0, E = DeadInsts.
size(), Alive = 0;
563 for (; S != E; ++S) {
564 auto *
I = dyn_cast_or_null<Instruction>(DeadInsts[S]);
566 DeadInsts[S] =
nullptr;
573 AboutToDeleteCallback);
580 std::function<
void(
Value *)> AboutToDeleteCallback) {
582 while (!DeadInsts.
empty()) {
588 "Live instruction found in dead worklist!");
589 assert(
I->use_empty() &&
"Instructions with uses are not dead.");
594 if (AboutToDeleteCallback)
595 AboutToDeleteCallback(
I);
599 for (
Use &OpU :
I->operands()) {
600 Value *OpV = OpU.get();
616 I->eraseFromParent();
624 for (
auto *DII : DbgUsers)
625 DII->setKillLocation();
626 for (
auto *DVR : DPUsers)
627 DVR->setKillLocation();
642 for (++UI; UI != UE; ++UI) {
659 I = cast<Instruction>(*
I->user_begin())) {
665 if (!Visited.
insert(
I).second) {
685 for (
unsigned i = 0, e =
I->getNumOperands(); i != e; ++i) {
686 Value *OpV =
I->getOperand(i);
687 I->setOperand(i,
nullptr);
700 I->eraseFromParent();
708 for (
User *U :
I->users()) {
710 WorkList.
insert(cast<Instruction>(U));
715 bool Changed =
false;
716 if (!
I->use_empty()) {
717 I->replaceAllUsesWith(SimpleV);
721 I->eraseFromParent();
736 bool MadeChange =
false;
753 assert(!BI->isTerminator());
763 while (!WorkList.
empty()) {
778 while (
PHINode *PN = dyn_cast<PHINode>(DestBB->
begin())) {
779 Value *NewVal = PN->getIncomingValue(0);
782 PN->replaceAllUsesWith(NewVal);
783 PN->eraseFromParent();
787 assert(PredBB &&
"Block doesn't have a single predecessor!");
801 if (PredOfPredBB != PredBB)
802 if (SeenPreds.
insert(PredOfPredBB).second)
803 Updates.
push_back({DominatorTree::Insert, PredOfPredBB, DestBB});
806 if (SeenPreds.
insert(PredOfPredBB).second)
807 Updates.
push_back({DominatorTree::Delete, PredOfPredBB, PredBB});
808 Updates.
push_back({DominatorTree::Delete, PredBB, DestBB});
838 "The successor list of PredBB isn't empty before "
839 "applying corresponding DTU updates.");
860 return First == Second || isa<UndefValue>(
First) || isa<UndefValue>(Second);
891 if (BBPreds.
count(IBB) &&
895 <<
"Can't fold, phi node " << PN->
getName() <<
" in "
896 << Succ->
getName() <<
" is conflicting with "
897 << BBPN->
getName() <<
" with regard to common predecessor "
909 if (BBPreds.
count(IBB) &&
913 <<
" is conflicting with regard to common "
914 <<
"predecessor " << IBB->
getName() <<
"\n");
941 if (!isa<UndefValue>(OldVal)) {
943 IncomingValues.
find(BB)->second == OldVal) &&
944 "Expected OldVal to match incoming value from BB!");
946 IncomingValues.
insert(std::make_pair(BB, OldVal));
951 if (It != IncomingValues.
end())
return It->second;
970 if (!isa<UndefValue>(V))
971 IncomingValues.
insert(std::make_pair(BB, V));
986 if (!isa<UndefValue>(V))
continue;
995 if (It == IncomingValues.
end()) {
1008 unsigned PoisonCount =
count_if(TrueUndefOps, [&](
unsigned i) {
1011 if (PoisonCount != 0 && PoisonCount != TrueUndefOps.
size()) {
1012 for (
unsigned i : TrueUndefOps)
1026 if (BB->
phis().empty() || Succ->
phis().empty())
1041 if (BBPreds.
count(SuccPred)) {
1044 CommonPred = SuccPred;
1060 unsigned NumChangedPhi = 0;
1061 for (
auto &Phi : Succ->
phis()) {
1064 if (
auto *IncomingPhi = dyn_cast<PHINode>(Phi.getIncomingValueForBlock(BB)))
1065 if (IncomingPhi->getParent() == BB)
1074 return (NumPreds - 1) * NumChangedPhi >
1091 assert(OldVal &&
"No entry in PHI for Pred BB!");
1108 if (isa<PHINode>(OldVal) && cast<PHINode>(OldVal)->
getParent() == BB) {
1109 PHINode *OldValPN = cast<PHINode>(OldVal);
1118 if (PredBB == CommonPred)
1136 if (PredBB == CommonPred)
1156 "TryToSimplifyUncondBranchFromEmptyBlock called on entry block!");
1173 BB, Succ, BBPreds, CommonPred);
1195 while (isa<PHINode>(*BBI)) {
1196 for (
Use &U : BBI->uses()) {
1197 if (
PHINode* PN = dyn_cast<PHINode>(U.getUser())) {
1198 if (PN->getIncomingBlock(U) != BB)
1208 if (BBPhisMergeable && CommonPred)
1210 <<
" and " << Succ->
getName() <<
" : "
1211 << CommonPred->
getName() <<
"\n");
1279 if (TI->hasNonDebugLocLoopMetadata())
1282 if (PredTI->hasNonDebugLocLoopMetadata())
1287 else if (BBPhisMergeable)
1302 if (SeenPreds.
insert(PredOfBB).second)
1303 Updates.
push_back({DominatorTree::Insert, PredOfBB, Succ});
1311 if (SeenPreds.
insert(PredOfBB).second && PredOfBB != CommonPred)
1312 Updates.
push_back({DominatorTree::Delete, PredOfBB, BB});
1315 Updates.
push_back({DominatorTree::Delete, BB, Succ});
1318 if (isa<PHINode>(Succ->
begin())) {
1338 while (
PHINode *PN = dyn_cast<PHINode>(&BB->
front())) {
1340 assert(PN->use_empty() &&
"There shouldn't be any uses here!");
1341 PN->eraseFromParent();
1349 if (TI->hasNonDebugLocLoopMetadata()) {
1350 MDNode *LoopMD = TI->getMetadata(LLVMContext::MD_loop);
1352 Pred->getTerminator()->setMetadata(LLVMContext::MD_loop, LoopMD);
1368 "applying corresponding DTU updates.");
1369 }
else if (BBPhisMergeable) {
1372 if (
Instruction *UseInst = dyn_cast<Instruction>(U.getUser()))
1373 return UseInst->
getParent() != CommonPred &&
1374 BBPreds.
contains(UseInst->getParent());
1395 bool Changed =
false;
1400 for (
auto I = BB->
begin();
PHINode *PN = dyn_cast<PHINode>(
I);) {
1405 for (
auto J =
I;
PHINode *DuplicatePN = dyn_cast<PHINode>(J); ++J) {
1406 if (
ToRemove.contains(DuplicatePN))
1431 struct PHIDenseMapInfo {
1432 static PHINode *getEmptyKey() {
1436 static PHINode *getTombstoneKey() {
1441 return PN == getEmptyKey() || PN == getTombstoneKey();
1455 static unsigned getHashValue(
PHINode *PN) {
1470 return LHS->isIdenticalTo(
RHS);
1488 bool Changed =
false;
1489 for (
auto I = BB->
begin();
PHINode *PN = dyn_cast<PHINode>(
I++);) {
1492 auto Inserted = PHISet.
insert(PN);
1493 if (!Inserted.second) {
1496 PN->replaceAllUsesWith(*Inserted.first);
1525 PN->eraseFromParent();
1531 V = V->stripPointerCasts();
1533 if (
AllocaInst *AI = dyn_cast<AllocaInst>(V)) {
1539 Align CurrentAlign = AI->getAlign();
1540 if (PrefAlign <= CurrentAlign)
1541 return CurrentAlign;
1546 if (StackAlign && PrefAlign > *StackAlign)
1547 return CurrentAlign;
1548 AI->setAlignment(PrefAlign);
1552 if (
auto *GO = dyn_cast<GlobalObject>(V)) {
1554 Align CurrentAlign = GO->getPointerAlignment(
DL);
1555 if (PrefAlign <= CurrentAlign)
1556 return CurrentAlign;
1562 if (!GO->canIncreaseAlignment())
1563 return CurrentAlign;
1565 if (GO->isThreadLocal()) {
1566 unsigned MaxTLSAlign = GO->getParent()->getMaxTLSAlignment() / CHAR_BIT;
1567 if (MaxTLSAlign && PrefAlign >
Align(MaxTLSAlign))
1568 PrefAlign =
Align(MaxTLSAlign);
1571 GO->setAlignment(PrefAlign);
1583 assert(V->getType()->isPointerTy() &&
1584 "getOrEnforceKnownAlignment expects a pointer!");
1596 if (PrefAlign && *PrefAlign > Alignment)
1617 for (
auto *DVI : DbgValues) {
1619 if ((DVI->getVariable() == DIVar) && (DVI->getExpression() == DIExpr))
1622 for (
auto *DVR : DbgVariableRecords) {
1624 if ((DVR->getVariable() == DIVar) && (DVR->getExpression() == DIExpr))
1640 TypeSize ValueSize =
DL.getTypeAllocSizeInBits(ValTy);
1641 if (std::optional<uint64_t> FragmentSize =
1651 "address of variable must have exactly 1 location operand.");
1654 if (std::optional<TypeSize> FragmentSize =
1655 AI->getAllocationSizeInBits(
DL)) {
1656 return TypeSize::isKnownGE(ValueSize, *FragmentSize);
1667 TypeSize ValueSize =
DL.getTypeAllocSizeInBits(ValTy);
1668 if (std::optional<uint64_t> FragmentSize =
1678 "address of variable must have exactly 1 location operand.");
1681 if (std::optional<TypeSize> FragmentSize = AI->getAllocationSizeInBits(
DL)) {
1682 return TypeSize::isKnownGE(ValueSize, *FragmentSize);
1696 auto DbgVal = Builder.insertDbgValueIntrinsic(DV, DIVar, DIExpr, NewLoc,
1698 cast<Instruction *>(DbgVal)->insertBefore(Instr);
1705 Instr->getParent()->insertDbgRecordBefore(DV, Instr);
1713 auto DbgVal = Builder.insertDbgValueIntrinsic(DV, DIVar, DIExpr, NewLoc,
1715 cast<Instruction *>(DbgVal)->insertAfter(Instr);
1722 Instr->getParent()->insertDbgRecordAfter(DV, &*Instr);
1732 assert(DIVar &&
"Missing variable");
1734 Value *DV = SI->getValueOperand();
1751 DIExpr->isDeref() || (!DIExpr->startsWithDeref() &&
1761 LLVM_DEBUG(
dbgs() <<
"Failed to convert dbg.declare to dbg.value: " << *DII
1773 return DIExpression::get(DIExpr->
getContext(),
1780 assert(DIVar &&
"Missing variable");
1783 Value *DV = SI->getValueOperand();
1797 assert(DIVar &&
"Missing variable");
1803 LLVM_DEBUG(
dbgs() <<
"Failed to convert dbg.declare to dbg.value: "
1822 assert(DIVar &&
"Missing variable");
1824 Value *DV = SI->getValueOperand();
1841 DIExpr->isDeref() || (!DIExpr->startsWithDeref() &&
1851 LLVM_DEBUG(
dbgs() <<
"Failed to convert dbg.declare to dbg.value: " << *DVR
1862 SI->getParent()->insertDbgRecordBefore(NewDVR, SI->getIterator());
1868 assert(DIVar &&
"Missing variable");
1871 Value *DV = SI->getValueOperand();
1885 assert(DIVar &&
"Missing variable");
1894 LLVM_DEBUG(
dbgs() <<
"Failed to convert dbg.declare to dbg.value: "
1907 if (InsertionPt != BB->
end()) {
1917 assert(DIVar &&
"Missing variable");
1923 LLVM_DEBUG(
dbgs() <<
"Failed to convert dbg.declare to DbgVariableRecord: "
1940 LI->
getParent()->insertDbgRecordAfter(DV, LI);
1957 assert(DIVar &&
"Missing variable");
1966 LLVM_DEBUG(
dbgs() <<
"Failed to convert dbg.declare to DbgVariableRecord: "
1979 if (InsertionPt != BB->
end()) {
1988 bool Changed =
false;
1992 for (
auto &FI :
F) {
1994 if (
auto *DDI = dyn_cast<DbgDeclareInst>(&BI))
1997 if (DVR.getType() == DbgVariableRecord::LocationType::Declare)
2006 auto LowerOne = [&](
auto *DDI) {
2008 dyn_cast_or_null<AllocaInst>(DDI->getVariableLocationOp(0));
2020 if (LoadInst *LI = dyn_cast<LoadInst>(U))
2021 return LI->isVolatile();
2022 if (StoreInst *SI = dyn_cast<StoreInst>(U))
2023 return SI->isVolatile();
2030 while (!WorkList.
empty()) {
2032 for (
const auto &AIUse : V->uses()) {
2033 User *U = AIUse.getUser();
2034 if (
StoreInst *SI = dyn_cast<StoreInst>(U)) {
2035 if (AIUse.getOperandNo() == 1)
2037 }
else if (
LoadInst *LI = dyn_cast<LoadInst>(U)) {
2039 }
else if (
CallInst *CI = dyn_cast<CallInst>(U)) {
2043 if (!CI->isLifetimeStartOrEnd()) {
2051 }
else if (
BitCastInst *BI = dyn_cast<BitCastInst>(U)) {
2052 if (BI->getType()->isPointerTy())
2057 DDI->eraseFromParent();
2077 assert(BB &&
"No BasicBlock to clone DbgVariableRecord(s) from.");
2078 if (InsertedPHIs.
size() == 0)
2083 for (
auto &
I : *BB) {
2085 for (
Value *V : DVR.location_ops())
2086 if (
auto *Loc = dyn_cast_or_null<PHINode>(V))
2087 DbgValueMap.
insert({Loc, &DVR});
2090 if (DbgValueMap.
size() == 0)
2105 for (
auto PHI : InsertedPHIs) {
2110 for (
auto VI :
PHI->operand_values()) {
2111 auto V = DbgValueMap.
find(VI);
2112 if (V != DbgValueMap.
end()) {
2114 auto NewDI = NewDbgValueMap.
find({Parent, DbgII});
2115 if (NewDI == NewDbgValueMap.
end()) {
2117 NewDI = NewDbgValueMap.
insert({{Parent, DbgII}, NewDbgII}).first;
2128 for (
auto DI : NewDbgValueMap) {
2132 assert(InsertionPt != Parent->
end() &&
"Ill-formed basic block");
2141 assert(BB &&
"No BasicBlock to clone dbg.value(s) from.");
2142 if (InsertedPHIs.
size() == 0)
2149 for (
auto &
I : *BB) {
2150 if (
auto DbgII = dyn_cast<DbgVariableIntrinsic>(&
I)) {
2151 for (
Value *V : DbgII->location_ops())
2152 if (
auto *Loc = dyn_cast_or_null<PHINode>(V))
2153 DbgValueMap.
insert({Loc, DbgII});
2156 if (DbgValueMap.
size() == 0)
2171 for (
auto *
PHI : InsertedPHIs) {
2176 for (
auto *VI :
PHI->operand_values()) {
2177 auto V = DbgValueMap.
find(VI);
2178 if (V != DbgValueMap.
end()) {
2179 auto *DbgII = cast<DbgVariableIntrinsic>(V->second);
2180 auto [NewDI, Inserted] = NewDbgValueMap.
try_emplace({Parent, DbgII});
2182 NewDI->second = cast<DbgVariableIntrinsic>(DbgII->clone());
2192 for (
auto DI : NewDbgValueMap) {
2194 auto *NewDbgII = DI.second;
2196 assert(InsertionPt != Parent->
end() &&
"Ill-formed basic block");
2197 NewDbgII->insertBefore(InsertionPt);
2207 auto ReplaceOne = [&](
auto *DII) {
2208 assert(DII->getVariable() &&
"Missing variable");
2209 auto *DIExpr = DII->getExpression();
2211 DII->setExpression(DIExpr);
2212 DII->replaceVariableLocationOp(
Address, NewAddress);
2218 return !DbgDeclares.
empty() || !DVRDeclares.
empty();
2227 assert(DIVar &&
"Missing variable");
2257 for (
auto *DVI : DbgUsers)
2259 DVI->getExpression(), NewAllocaAddress, DVI,
2260 nullptr, Builder,
Offset);
2265 DVR->getExpression(), NewAllocaAddress,
nullptr,
2279 Instruction *
I = dyn_cast<Instruction>(Assign->getAddress());
2284 assert(!Assign->getAddressExpression()->getFragmentInfo().has_value() &&
2285 "address-expression shouldn't have fragment info");
2298 Assign->getAddressExpression(), Ops, 0,
false);
2300 "address-expression shouldn't have fragment info");
2305 if (AdditionalValues.
empty()) {
2306 Assign->setAddress(NewV);
2307 Assign->setAddressExpression(SalvagedExpr);
2309 Assign->setKillAddress();
2319 const unsigned MaxDebugArgs = 16;
2320 const unsigned MaxExpressionSize = 128;
2321 bool Salvaged =
false;
2323 for (
auto *DII : DbgUsers) {
2324 if (
auto *DAI = dyn_cast<DbgAssignIntrinsic>(DII)) {
2325 if (DAI->getAddress() == &
I) {
2329 if (DAI->getValue() != &
I)
2335 bool StackValue = isa<DbgValueInst>(DII);
2336 auto DIILocation = DII->location_ops();
2339 "DbgVariableIntrinsic must use salvaged instruction as its location");
2345 Value *Op0 =
nullptr;
2347 auto LocItr =
find(DIILocation, &
I);
2348 while (SalvagedExpr && LocItr != DIILocation.end()) {
2350 unsigned LocNo = std::distance(DIILocation.begin(), LocItr);
2357 LocItr = std::find(++LocItr, DIILocation.end(), &
I);
2365 DII->replaceVariableLocationOp(&
I, Op0);
2366 bool IsValidSalvageExpr = SalvagedExpr->
getNumElements() <= MaxExpressionSize;
2367 if (AdditionalValues.
empty() && IsValidSalvageExpr) {
2368 DII->setExpression(SalvagedExpr);
2369 }
else if (isa<DbgValueInst>(DII) && IsValidSalvageExpr &&
2370 DII->getNumVariableLocationOps() + AdditionalValues.
size() <=
2372 DII->addVariableLocationOps(AdditionalValues, SalvagedExpr);
2377 DII->setKillLocation();
2383 for (
auto *DVR : DPUsers) {
2384 if (DVR->isDbgAssign()) {
2385 if (DVR->getAddress() == &
I) {
2389 if (DVR->getValue() != &
I)
2397 DVR->getType() != DbgVariableRecord::LocationType::Declare;
2398 auto DVRLocation = DVR->location_ops();
2401 "DbgVariableIntrinsic must use salvaged instruction as its location");
2407 Value *Op0 =
nullptr;
2409 auto LocItr =
find(DVRLocation, &
I);
2410 while (SalvagedExpr && LocItr != DVRLocation.end()) {
2412 unsigned LocNo = std::distance(DVRLocation.begin(), LocItr);
2419 LocItr = std::find(++LocItr, DVRLocation.end(), &
I);
2427 DVR->replaceVariableLocationOp(&
I, Op0);
2428 bool IsValidSalvageExpr =
2430 if (AdditionalValues.
empty() && IsValidSalvageExpr) {
2431 DVR->setExpression(SalvagedExpr);
2432 }
else if (DVR->getType() != DbgVariableRecord::LocationType::Declare &&
2433 IsValidSalvageExpr &&
2434 DVR->getNumVariableLocationOps() + AdditionalValues.
size() <=
2436 DVR->addVariableLocationOps(AdditionalValues, SalvagedExpr);
2442 DVR->setKillLocation();
2451 for (
auto *DII : DbgUsers)
2452 DII->setKillLocation();
2454 for (
auto *DVR : DPUsers)
2455 DVR->setKillLocation();
2462 unsigned BitWidth =
DL.getIndexSizeInBits(
GEP->getPointerAddressSpace());
2466 if (!
GEP->collectOffset(
DL,
BitWidth, VariableOffsets, ConstantOffset))
2468 if (!VariableOffsets.
empty() && !CurrentLocOps) {
2469 Opcodes.
insert(Opcodes.
begin(), {dwarf::DW_OP_LLVM_arg, 0});
2472 for (
const auto &
Offset : VariableOffsets) {
2475 "Expected strictly positive multiplier for offset.");
2477 Offset.second.getZExtValue(), dwarf::DW_OP_mul,
2478 dwarf::DW_OP_plus});
2481 return GEP->getOperand(0);
2486 case Instruction::Add:
2487 return dwarf::DW_OP_plus;
2488 case Instruction::Sub:
2489 return dwarf::DW_OP_minus;
2490 case Instruction::Mul:
2491 return dwarf::DW_OP_mul;
2492 case Instruction::SDiv:
2493 return dwarf::DW_OP_div;
2494 case Instruction::SRem:
2495 return dwarf::DW_OP_mod;
2496 case Instruction::Or:
2497 return dwarf::DW_OP_or;
2498 case Instruction::And:
2499 return dwarf::DW_OP_and;
2500 case Instruction::Xor:
2501 return dwarf::DW_OP_xor;
2502 case Instruction::Shl:
2503 return dwarf::DW_OP_shl;
2504 case Instruction::LShr:
2505 return dwarf::DW_OP_shr;
2506 case Instruction::AShr:
2507 return dwarf::DW_OP_shra;
2518 if (!CurrentLocOps) {
2523 AdditionalValues.
push_back(
I->getOperand(1));
2530 auto *ConstInt = dyn_cast<ConstantInt>(BI->
getOperand(1));
2532 if (ConstInt && ConstInt->getBitWidth() > 64)
2538 uint64_t Val = ConstInt->getSExtValue();
2541 if (BinOpcode == Instruction::Add || BinOpcode == Instruction::Sub) {
2542 uint64_t Offset = BinOpcode == Instruction::Add ? Val : -int64_t(Val);
2546 Opcodes.
append({dwarf::DW_OP_constu, Val});
2565 return dwarf::DW_OP_eq;
2567 return dwarf::DW_OP_ne;
2570 return dwarf::DW_OP_gt;
2573 return dwarf::DW_OP_ge;
2576 return dwarf::DW_OP_lt;
2579 return dwarf::DW_OP_le;
2589 auto *ConstInt = dyn_cast<ConstantInt>(Icmp->
getOperand(1));
2591 if (ConstInt && ConstInt->getBitWidth() > 64)
2599 uint64_t Val = ConstInt->getSExtValue();
2617 auto &M = *
I.getModule();
2618 auto &
DL = M.getDataLayout();
2620 if (
auto *CI = dyn_cast<CastInst>(&
I)) {
2621 Value *FromValue = CI->getOperand(0);
2623 if (CI->isNoopCast(
DL)) {
2632 !(isa<TruncInst>(&
I) || isa<SExtInst>(&
I) || isa<ZExtInst>(&
I) ||
2633 isa<IntToPtrInst>(&
I) || isa<PtrToIntInst>(&
I)))
2637 if (FromType->isPointerTy())
2638 FromType =
DL.getIntPtrType(FromType);
2640 unsigned FromTypeBitSize = FromType->getScalarSizeInBits();
2645 Ops.
append(ExtOps.begin(), ExtOps.end());
2649 if (
auto *
GEP = dyn_cast<GetElementPtrInst>(&
I))
2651 if (
auto *BI = dyn_cast<BinaryOperator>(&
I))
2653 if (
auto *IC = dyn_cast<ICmpInst>(&
I))
2680 bool Changed =
false;
2684 if (isa<Instruction>(&To)) {
2685 bool DomPointAfterFrom =
From.getNextNonDebugInstruction() == &DomPoint;
2687 for (
auto *DII :
Users) {
2697 }
else if (!DT.
dominates(&DomPoint, DII)) {
2698 UndefOrSalvage.
insert(DII);
2703 for (
auto *DVR : DPUsers) {
2707 if (isa<DbgVariableIntrinsic>(NextNonDebug))
2710 if (DomPointAfterFrom && NextNonDebug == &DomPoint) {
2714 DomPoint.
getParent()->insertDbgRecordAfter(DVR, &DomPoint);
2716 }
else if (!DT.
dominates(&DomPoint, MarkedInstr)) {
2717 UndefOrSalvageDVR.
insert(DVR);
2723 for (
auto *DII :
Users) {
2724 if (UndefOrSalvage.
count(DII))
2736 for (
auto *DVR : DPUsers) {
2737 if (UndefOrSalvageDVR.
count(DVR))
2750 if (!UndefOrSalvage.
empty() || !UndefOrSalvageDVR.
empty()) {
2774 bool SameSize =
DL.getTypeSizeInBits(FromTy) ==
DL.getTypeSizeInBits(ToTy);
2775 bool LosslessConversion = !
DL.isNonIntegralPointerType(FromTy) &&
2776 !
DL.isNonIntegralPointerType(ToTy);
2777 return SameSize && LosslessConversion;
2787 if (!
From.isUsedByMetadata())
2790 assert(&
From != &To &&
"Can't replace something with itself");
2799 return DVR.getExpression();
2813 assert(FromBits != ToBits &&
"Unexpected no-op conversion");
2817 if (FromBits < ToBits)
2828 return std::nullopt;
2830 bool Signed = *Signedness == DIBasicType::Signedness::Signed;
2842 return std::nullopt;
2844 bool Signed = *Signedness == DIBasicType::Signedness::Signed;
2858 bool Changed =
false;
2860 I->dropDbgRecords();
2861 for (
Use &U :
I->operands()) {
2863 if (isa<Instruction>(
Op) && !
Op->getType()->isTokenTy()) {
2873std::pair<unsigned, unsigned>
2875 unsigned NumDeadInst = 0;
2876 unsigned NumDeadDbgInst = 0;
2883 while (EndInst != &BB->
front()) {
2895 if (isa<DbgInfoIntrinsic>(Inst))
2903 return {NumDeadInst, NumDeadDbgInst};
2919 Successor->removePredecessor(BB, PreserveLCSSA);
2924 UI->setDebugLoc(
I->getDebugLoc());
2927 unsigned NumInstrsRemoved = 0;
2929 while (BBI != BBE) {
2930 if (!BBI->use_empty())
2932 BBI++->eraseFromParent();
2938 for (
BasicBlock *UniqueSuccessor : UniqueSuccessors)
2939 Updates.
push_back({DominatorTree::Delete, BB, UniqueSuccessor});
2943 return NumInstrsRemoved;
2949 II->getOperandBundlesAsDefs(OpBundles);
2951 II->getCalledOperand(), Args, OpBundles);
2962 auto NewWeights =
uint32_t(TotalWeight) != TotalWeight
2965 NewCall->
setMetadata(LLVMContext::MD_prof, NewWeights);
2976 II->replaceAllUsesWith(NewCall);
2986 II->eraseFromParent();
2988 DTU->
applyUpdates({{DominatorTree::Delete, BB, UnwindDestBB}});
3017 UnwindEdge, InvokeArgs, OpBundles, CI->
getName(), BB);
3021 II->setMetadata(LLVMContext::MD_prof, CI->
getMetadata(LLVMContext::MD_prof));
3024 DTU->
applyUpdates({{DominatorTree::Insert, BB, UnwindEdge}});
3031 Split->front().eraseFromParent();
3042 bool Changed =
false;
3050 if (
auto *CI = dyn_cast<CallInst>(&
I)) {
3051 Value *Callee = CI->getCalledOperand();
3053 if (
Function *
F = dyn_cast<Function>(Callee)) {
3054 auto IntrinsicID =
F->getIntrinsicID();
3059 if (IntrinsicID == Intrinsic::assume) {
3066 }
else if (IntrinsicID == Intrinsic::experimental_guard) {
3077 if (!isa<UnreachableInst>(CI->getNextNode())) {
3083 }
else if ((isa<ConstantPointerNull>(Callee) &&
3085 cast<PointerType>(Callee->getType())
3086 ->getAddressSpace())) ||
3087 isa<UndefValue>(Callee)) {
3092 if (CI->doesNotReturn() && !CI->isMustTailCall()) {
3096 if (!isa<UnreachableInst>(CI->getNextNonDebugInstruction())) {
3103 }
else if (
auto *SI = dyn_cast<StoreInst>(&
I)) {
3109 if (SI->isVolatile())
continue;
3113 if (isa<UndefValue>(
Ptr) ||
3114 (isa<ConstantPointerNull>(
Ptr) &&
3116 SI->getPointerAddressSpace()))) {
3125 if (
auto *
II = dyn_cast<InvokeInst>(Terminator)) {
3127 Value *Callee =
II->getCalledOperand();
3128 if ((isa<ConstantPointerNull>(Callee) &&
3130 isa<UndefValue>(Callee)) {
3134 if (
II->doesNotReturn() &&
3135 !isa<UnreachableInst>(
II->getNormalDest()->front())) {
3145 Ctx, OrigNormalDest->
getName() +
".unreachable",
3146 II->getFunction(), OrigNormalDest);
3148 II->setNormalDest(UnreachableNormalDest);
3151 {{DominatorTree::Delete, BB, OrigNormalDest},
3152 {DominatorTree::Insert, BB, UnreachableNormalDest}});
3156 if (
II->use_empty() && !
II->mayHaveSideEffects()) {
3162 II->eraseFromParent();
3164 DTU->applyUpdates({{DominatorTree::Delete, BB, UnwindDestBB}});
3170 }
else if (
auto *CatchSwitch = dyn_cast<CatchSwitchInst>(Terminator)) {
3172 struct CatchPadDenseMapInfo {
3187 if (
LHS == getEmptyKey() ||
LHS == getTombstoneKey() ||
3188 RHS == getEmptyKey() ||
RHS == getTombstoneKey())
3190 return LHS->isIdenticalTo(
RHS);
3201 E = CatchSwitch->handler_end();
3205 ++NumPerSuccessorCases[HandlerBB];
3207 if (!HandlerSet.insert({CatchPad, Empty}).second) {
3209 --NumPerSuccessorCases[HandlerBB];
3210 CatchSwitch->removeHandler(
I);
3217 std::vector<DominatorTree::UpdateType> Updates;
3218 for (
const std::pair<BasicBlock *, int> &
I : NumPerSuccessorCases)
3220 Updates.push_back({DominatorTree::Delete, BB,
I.first});
3221 DTU->applyUpdates(Updates);
3229 }
while (!Worklist.
empty());
3236 if (
auto *
II = dyn_cast<InvokeInst>(TI))
3242 if (
auto *CRI = dyn_cast<CleanupReturnInst>(TI)) {
3244 UnwindDest = CRI->getUnwindDest();
3245 }
else if (
auto *CatchSwitch = dyn_cast<CatchSwitchInst>(TI)) {
3247 CatchSwitch->getParentPad(),
nullptr, CatchSwitch->getNumHandlers(),
3248 CatchSwitch->getName(), CatchSwitch->getIterator());
3249 for (
BasicBlock *PadBB : CatchSwitch->handlers())
3250 NewCatchSwitch->addHandler(PadBB);
3252 NewTI = NewCatchSwitch;
3253 UnwindDest = CatchSwitch->getUnwindDest();
3264 DTU->
applyUpdates({{DominatorTree::Delete, BB, UnwindDest}});
3277 if (Reachable.
size() ==
F.size())
3286 if (Reachable.
count(&BB))
3291 BlocksToRemove.
insert(&BB);
3294 if (BlocksToRemove.
empty())
3298 NumRemoved += BlocksToRemove.
size();
3311 bool DoesKMove,
bool AAOnly =
false) {
3313 K->getAllMetadataOtherThanDebugLoc(
Metadata);
3315 unsigned Kind = MD.first;
3322 K->setMetadata(Kind,
nullptr);
3324 case LLVMContext::MD_dbg:
3326 case LLVMContext::MD_DIAssignID:
3328 K->mergeDIAssignID(J);
3330 case LLVMContext::MD_tbaa:
3334 case LLVMContext::MD_alias_scope:
3338 case LLVMContext::MD_noalias:
3339 case LLVMContext::MD_mem_parallel_loop_access:
3343 case LLVMContext::MD_access_group:
3345 K->setMetadata(LLVMContext::MD_access_group,
3348 case LLVMContext::MD_range:
3349 if (!AAOnly && (DoesKMove || !K->hasMetadata(LLVMContext::MD_noundef)))
3352 case LLVMContext::MD_fpmath:
3356 case LLVMContext::MD_invariant_load:
3360 K->setMetadata(Kind, JMD);
3362 case LLVMContext::MD_nonnull:
3363 if (!AAOnly && (DoesKMove || !K->hasMetadata(LLVMContext::MD_noundef)))
3364 K->setMetadata(Kind, JMD);
3366 case LLVMContext::MD_invariant_group:
3369 case LLVMContext::MD_mmra:
3372 case LLVMContext::MD_align:
3373 if (!AAOnly && (DoesKMove || !K->hasMetadata(LLVMContext::MD_noundef)))
3377 case LLVMContext::MD_dereferenceable:
3378 case LLVMContext::MD_dereferenceable_or_null:
3379 if (!AAOnly && DoesKMove)
3380 K->setMetadata(Kind,
3383 case LLVMContext::MD_memprof:
3387 case LLVMContext::MD_callsite:
3391 case LLVMContext::MD_preserve_access_index:
3394 case LLVMContext::MD_noundef:
3396 if (!AAOnly && DoesKMove)
3397 K->setMetadata(Kind, JMD);
3399 case LLVMContext::MD_nontemporal:
3402 K->setMetadata(Kind, JMD);
3404 case LLVMContext::MD_prof:
3405 if (!AAOnly && DoesKMove)
3408 case LLVMContext::MD_noalias_addrspace:
3410 K->setMetadata(Kind,
3421 if (
auto *JMD = J->
getMetadata(LLVMContext::MD_invariant_group))
3422 if (isa<LoadInst>(K) || isa<StoreInst>(K))
3423 K->setMetadata(LLVMContext::MD_invariant_group, JMD);
3428 auto JMMRA = J->
getMetadata(LLVMContext::MD_mmra);
3429 auto KMMRA = K->getMetadata(LLVMContext::MD_mmra);
3430 if (JMMRA || KMMRA) {
3431 K->setMetadata(LLVMContext::MD_mmra,
3447 Source.getAllMetadata(MD);
3451 for (
const auto &MDPair : MD) {
3452 unsigned ID = MDPair.first;
3462 case LLVMContext::MD_dbg:
3463 case LLVMContext::MD_tbaa:
3464 case LLVMContext::MD_prof:
3465 case LLVMContext::MD_fpmath:
3466 case LLVMContext::MD_tbaa_struct:
3467 case LLVMContext::MD_invariant_load:
3468 case LLVMContext::MD_alias_scope:
3469 case LLVMContext::MD_noalias:
3470 case LLVMContext::MD_nontemporal:
3471 case LLVMContext::MD_mem_parallel_loop_access:
3472 case LLVMContext::MD_access_group:
3473 case LLVMContext::MD_noundef:
3478 case LLVMContext::MD_nonnull:
3482 case LLVMContext::MD_align:
3483 case LLVMContext::MD_dereferenceable:
3484 case LLVMContext::MD_dereferenceable_or_null:
3490 case LLVMContext::MD_range:
3498 auto *ReplInst = dyn_cast<Instruction>(Repl);
3507 if (isa<OverflowingBinaryOperator>(ReplInst) &&
3514 else if (!isa<LoadInst>(
I))
3515 ReplInst->andIRFlags(
I);
3518 if (
auto *CB1 = dyn_cast<CallBase>(ReplInst)) {
3519 if (
auto *CB2 = dyn_cast<CallBase>(
I)) {
3520 bool Success = CB1->tryIntersectAttributes(CB2);
3521 assert(
Success &&
"We should not be trying to sink callbases "
3522 "with non-intersectable attributes");
3540template <
typename RootType,
typename ShouldReplaceFn>
3542 const RootType &Root,
3543 const ShouldReplaceFn &ShouldReplace) {
3548 auto *
II = dyn_cast<IntrinsicInst>(U.getUser());
3549 if (
II &&
II->getIntrinsicID() == Intrinsic::fake_use)
3551 if (!ShouldReplace(Root, U))
3555 dbgs() <<
"' with " << *To <<
" in " << *U.getUser() <<
"\n");
3564 auto *BB =
From->getParent();
3568 auto *
I = cast<Instruction>(U.getUser());
3569 if (
I->getParent() == BB)
3583 return ::replaceDominatedUsesWith(
From, To, Root, Dominates);
3589 auto Dominates = [&DT](
const BasicBlock *BB,
const Use &U) {
3592 return ::replaceDominatedUsesWith(
From, To, BB, Dominates);
3598 auto DominatesAndShouldReplace =
3600 return DT.
dominates(Root, U) && ShouldReplace(U, To);
3602 return ::replaceDominatedUsesWith(
From, To, Root, DominatesAndShouldReplace);
3608 auto DominatesAndShouldReplace = [&DT, &ShouldReplace,
3610 return DT.
dominates(BB, U) && ShouldReplace(U, To);
3612 return ::replaceDominatedUsesWith(
From, To, BB, DominatesAndShouldReplace);
3618 if (Call->hasFnAttr(
"gc-leaf-function"))
3620 if (
const Function *
F = Call->getCalledFunction()) {
3621 if (
F->hasFnAttribute(
"gc-leaf-function"))
3624 if (
auto IID =
F->getIntrinsicID()) {
3626 return IID != Intrinsic::experimental_gc_statepoint &&
3627 IID != Intrinsic::experimental_deoptimize &&
3628 IID != Intrinsic::memcpy_element_unordered_atomic &&
3629 IID != Intrinsic::memmove_element_unordered_atomic;
3646 auto *NewTy = NewLI.
getType();
3649 if (NewTy->isPointerTy()) {
3656 if (!NewTy->isIntegerTy())
3661 auto *ITy = cast<IntegerType>(NewTy);
3671 auto *NewTy = NewLI.
getType();
3673 if (NewTy == OldLI.
getType()) {
3682 if (!NewTy->isPointerTy())
3685 unsigned BitWidth =
DL.getPointerTypeSizeInBits(NewTy);
3697 for (
auto *DII : DbgUsers)
3699 for (
auto *DVR : DPUsers)
3700 DVR->eraseFromParent();
3729 I->dropUBImplyingAttrsAndMetadata();
3730 if (
I->isUsedByMetadata())
3733 I->dropDbgRecords();
3734 if (
I->isDebugOrPseudoInst()) {
3736 II =
I->eraseFromParent();
3750 const APInt &API = cast<ConstantInt>(&CV)->getValue();
3751 std::optional<int64_t> InitIntOpt = API.
trySExtValue();
3753 static_cast<uint64_t>(*InitIntOpt))
3757 if (isa<ConstantInt>(
C))
3758 return createIntegerExpression(
C);
3760 auto *
FP = dyn_cast<ConstantFP>(&
C);
3772 if (isa<ConstantPointerNull>(
C))
3776 if (CE->getOpcode() == Instruction::IntToPtr) {
3777 const Value *V = CE->getOperand(0);
3778 if (
auto CI = dyn_cast_or_null<ConstantInt>(V))
3779 return createIntegerExpression(*CI);
3785 auto RemapDebugOperands = [&Mapping](
auto *DV,
auto Set) {
3786 for (
auto *
Op : Set) {
3788 if (
I != Mapping.
end())
3789 DV->replaceVariableLocationOp(
Op,
I->second,
true);
3792 auto RemapAssignAddress = [&Mapping](
auto *DA) {
3793 auto I = Mapping.
find(DA->getAddress());
3794 if (
I != Mapping.
end())
3795 DA->setAddress(
I->second);
3797 if (
auto DVI = dyn_cast<DbgVariableIntrinsic>(Inst))
3798 RemapDebugOperands(DVI, DVI->location_ops());
3799 if (
auto DAI = dyn_cast<DbgAssignIntrinsic>(Inst))
3800 RemapAssignAddress(DAI);
3802 RemapDebugOperands(&DVR, DVR.location_ops());
3803 if (DVR.isDbgAssign())
3804 RemapAssignAddress(&DVR);
3813 BitPart(
Value *
P,
unsigned BW) : Provider(
P) {
3824 enum { Unset = -1 };
3856static const std::optional<BitPart> &
3858 std::map<
Value *, std::optional<BitPart>> &BPS,
int Depth,
3860 auto [
I, Inserted] = BPS.try_emplace(V);
3864 auto &Result =
I->second;
3865 auto BitWidth = V->getType()->getScalarSizeInBits();
3873 LLVM_DEBUG(
dbgs() <<
"collectBitParts max recursion depth reached.\n");
3877 if (
auto *
I = dyn_cast<Instruction>(V)) {
3885 Depth + 1, FoundRoot);
3886 if (!
A || !
A->Provider)
3890 Depth + 1, FoundRoot);
3891 if (!
B ||
A->Provider !=
B->Provider)
3895 Result = BitPart(
A->Provider,
BitWidth);
3896 for (
unsigned BitIdx = 0; BitIdx <
BitWidth; ++BitIdx) {
3897 if (
A->Provenance[BitIdx] != BitPart::Unset &&
3898 B->Provenance[BitIdx] != BitPart::Unset &&
3899 A->Provenance[BitIdx] !=
B->Provenance[BitIdx])
3900 return Result = std::nullopt;
3902 if (
A->Provenance[BitIdx] == BitPart::Unset)
3903 Result->Provenance[BitIdx] =
B->Provenance[BitIdx];
3905 Result->Provenance[BitIdx] =
A->Provenance[BitIdx];
3913 const APInt &BitShift = *
C;
3920 if (!MatchBitReversals && (BitShift.
getZExtValue() % 8) != 0)
3924 Depth + 1, FoundRoot);
3930 auto &
P = Result->Provenance;
3931 if (
I->getOpcode() == Instruction::Shl) {
3945 const APInt &AndMask = *
C;
3949 unsigned NumMaskedBits = AndMask.
popcount();
3950 if (!MatchBitReversals && (NumMaskedBits % 8) != 0)
3954 Depth + 1, FoundRoot);
3959 for (
unsigned BitIdx = 0; BitIdx <
BitWidth; ++BitIdx)
3961 if (AndMask[BitIdx] == 0)
3962 Result->Provenance[BitIdx] = BitPart::Unset;
3969 Depth + 1, FoundRoot);
3973 Result = BitPart(Res->Provider,
BitWidth);
3974 auto NarrowBitWidth =
X->getType()->getScalarSizeInBits();
3975 for (
unsigned BitIdx = 0; BitIdx < NarrowBitWidth; ++BitIdx)
3976 Result->Provenance[BitIdx] = Res->Provenance[BitIdx];
3977 for (
unsigned BitIdx = NarrowBitWidth; BitIdx <
BitWidth; ++BitIdx)
3978 Result->Provenance[BitIdx] = BitPart::Unset;
3985 Depth + 1, FoundRoot);
3989 Result = BitPart(Res->Provider,
BitWidth);
3990 for (
unsigned BitIdx = 0; BitIdx <
BitWidth; ++BitIdx)
3991 Result->Provenance[BitIdx] = Res->Provenance[BitIdx];
3999 Depth + 1, FoundRoot);
4003 Result = BitPart(Res->Provider,
BitWidth);
4004 for (
unsigned BitIdx = 0; BitIdx <
BitWidth; ++BitIdx)
4005 Result->Provenance[(
BitWidth - 1) - BitIdx] = Res->Provenance[BitIdx];
4012 Depth + 1, FoundRoot);
4017 Result = BitPart(Res->Provider,
BitWidth);
4018 for (
unsigned ByteIdx = 0; ByteIdx < ByteWidth; ++ByteIdx) {
4019 unsigned ByteBitOfs = ByteIdx * 8;
4020 for (
unsigned BitIdx = 0; BitIdx < 8; ++BitIdx)
4021 Result->Provenance[(
BitWidth - 8 - ByteBitOfs) + BitIdx] =
4022 Res->Provenance[ByteBitOfs + BitIdx];
4039 if (!MatchBitReversals && (ModAmt % 8) != 0)
4044 Depth + 1, FoundRoot);
4045 if (!
LHS || !
LHS->Provider)
4049 Depth + 1, FoundRoot);
4050 if (!
RHS ||
LHS->Provider !=
RHS->Provider)
4053 unsigned StartBitRHS =
BitWidth - ModAmt;
4055 for (
unsigned BitIdx = 0; BitIdx < StartBitRHS; ++BitIdx)
4056 Result->Provenance[BitIdx + ModAmt] =
LHS->Provenance[BitIdx];
4057 for (
unsigned BitIdx = 0; BitIdx < ModAmt; ++BitIdx)
4058 Result->Provenance[BitIdx] =
RHS->Provenance[BitIdx + StartBitRHS];
4072 for (
unsigned BitIdx = 0; BitIdx <
BitWidth; ++BitIdx)
4073 Result->Provenance[BitIdx] = BitIdx;
4079 if (
From % 8 != To % 8)
4094 Instruction *
I,
bool MatchBSwaps,
bool MatchBitReversals,
4101 if (!MatchBSwaps && !MatchBitReversals)
4103 Type *ITy =
I->getType();
4108 bool FoundRoot =
false;
4109 std::map<Value *, std::optional<BitPart>> BPS;
4116 [](int8_t
I) {
return I == BitPart::Unset || 0 <=
I; }) &&
4117 "Illegal bit provenance index");
4120 Type *DemandedTy = ITy;
4121 if (BitProvenance.
back() == BitPart::Unset) {
4122 while (!BitProvenance.
empty() && BitProvenance.
back() == BitPart::Unset)
4123 BitProvenance = BitProvenance.
drop_back();
4124 if (BitProvenance.
empty())
4127 if (
auto *IVecTy = dyn_cast<VectorType>(ITy))
4128 DemandedTy = VectorType::get(DemandedTy, IVecTy);
4139 bool OKForBSwap = MatchBSwaps && (DemandedBW % 16) == 0;
4140 bool OKForBitReverse = MatchBitReversals;
4141 for (
unsigned BitIdx = 0;
4142 (BitIdx < DemandedBW) && (OKForBSwap || OKForBitReverse); ++BitIdx) {
4143 if (BitProvenance[BitIdx] == BitPart::Unset) {
4150 BitIdx, DemandedBW);
4155 Intrin = Intrinsic::bswap;
4156 else if (OKForBitReverse)
4157 Intrin = Intrinsic::bitreverse;
4163 Value *Provider = Res->Provider;
4166 if (DemandedTy != Provider->
getType()) {
4177 auto *Mask = ConstantInt::get(DemandedTy, DemandedMask);
4183 if (ITy != Result->getType()) {
4200 if (
F && !
F->hasLocalLinkage() &&
F->hasName() &&
4202 !
F->doesNotAccessMemory())
4208 if (
I->getOperand(OpIdx)->getType()->isMetadataTy())
4212 if (!isa<Constant>(
I->getOperand(OpIdx)))
4215 switch (
I->getOpcode()) {
4218 case Instruction::Call:
4219 case Instruction::Invoke: {
4220 const auto &CB = cast<CallBase>(*
I);
4223 if (CB.isInlineAsm())
4228 if (CB.isBundleOperand(OpIdx))
4231 if (OpIdx < CB.arg_size()) {
4234 if (isa<IntrinsicInst>(CB) &&
4235 OpIdx >= CB.getFunctionType()->getNumParams()) {
4237 return CB.getIntrinsicID() == Intrinsic::experimental_stackmap;
4242 if (CB.getIntrinsicID() == Intrinsic::gcroot)
4246 return !CB.paramHasAttr(OpIdx, Attribute::ImmArg);
4251 return !isa<IntrinsicInst>(CB);
4253 case Instruction::ShuffleVector:
4256 case Instruction::Switch:
4257 case Instruction::ExtractValue:
4260 case Instruction::InsertValue:
4263 case Instruction::Alloca:
4267 return !cast<AllocaInst>(
I)->isStaticAlloca();
4268 case Instruction::GetElementPtr:
4272 for (
auto E = std::next(It, OpIdx); It != E; ++It)
4281 if (
Constant *
C = dyn_cast<Constant>(Condition))
4285 Value *NotCondition;
4287 return NotCondition;
4290 Instruction *Inst = dyn_cast<Instruction>(Condition);
4293 else if (
Argument *Arg = dyn_cast<Argument>(Condition))
4295 assert(Parent &&
"Unsupported condition to invert");
4306 if (Inst && !isa<PHINode>(Inst))
4317 bool Changed =
false;
4319 if (!
F.hasFnAttribute(Attribute::NoSync) &&
4320 F.doesNotAccessMemory() && !
F.isConvergent()) {
4326 if (!
F.hasFnAttribute(Attribute::NoFree) &&
F.onlyReadsMemory()) {
4327 F.setDoesNotFreeMemory();
4332 if (!
F.hasFnAttribute(Attribute::MustProgress) &&
F.willReturn()) {
4333 F.setMustProgress();
for(const MachineOperand &MO :llvm::drop_begin(OldMI.operands(), Desc.getNumOperands()))
static unsigned getIntrinsicID(const SDNode *N)
This file implements a class to represent arbitrary precision integral constant values and operations...
ReachingDefAnalysis InstSet & ToRemove
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
static bool isEqual(const Function &Caller, const Function &Callee)
This file contains the simple types necessary to represent the attributes associated with functions a...
static const Function * getParent(const Value *V)
BlockVerifier::State From
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
static GCRegistry::Add< ErlangGC > A("erlang", "erlang-compatible garbage collector")
This file contains the declarations for the subclasses of Constant, which represent the different fla...
static bool isSentinel(const DWARFDebugNames::AttributeEncoding &AE)
Returns the sub type a function will return at a given Idx Should correspond to the result type of an ExtractValue instruction executed with just that one unsigned Idx
This file defines DenseMapInfo traits for DenseMap.
This file defines the DenseMap class.
This file defines the DenseSet and SmallDenseSet classes.
This file contains constants used for implementing Dwarf debug support.
static unsigned getHashValueImpl(SimpleValue Val)
static bool isEqualImpl(SimpleValue LHS, SimpleValue RHS)
static GCMetadataPrinterRegistry::Add< ErlangGCPrinter > X("erlang", "erlang-compatible garbage collector")
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.
This defines the Use class.
iv Induction Variable Users
This file provides utility for Memory Model Relaxation Annotations (MMRAs).
uint64_t IntrinsicInst * II
static GCMetadataPrinterRegistry::Add< OcamlGCMetadataPrinter > Y("ocaml", "ocaml 3.10-compatible collector")
This file contains the declarations for profiling metadata utility functions.
const SmallVectorImpl< MachineOperand > & Cond
Remove Loads Into Fake Uses
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
This file implements a set that has insertion order iteration characteristics.
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)
APInt bitcastToAPInt() const
Class for arbitrary precision integers.
static APInt getAllOnes(unsigned numBits)
Return an APInt of a specified width with all bits set.
void clearBit(unsigned BitPosition)
Set a given bit to 0.
uint64_t getZExtValue() const
Get zero extended value.
unsigned popcount() const
Count the number of bits set.
bool isAllOnes() const
Determine if all bits are set. This is true for zero-width values.
const uint64_t * getRawData() const
This function returns a pointer to the internal storage of the APInt.
std::optional< int64_t > trySExtValue() const
Get sign extended value if possible.
int64_t getSExtValue() const
Get sign extended value.
bool uge(const APInt &RHS) const
Unsigned greater or equal comparison.
an instruction to allocate memory on the stack
Type * getAllocatedType() const
Return the type that is being allocated by the instruction.
bool isArrayAllocation() const
Return true if there is an allocation size parameter to the allocation instruction that is not 1.
This class represents an incoming formal argument to a Function.
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory),...
const T & back() const
back - Get the last element.
ArrayRef< T > drop_front(size_t N=1) const
Drop the first N elements of the array.
size_t size() const
size - Get the array size.
ArrayRef< T > drop_back(size_t N=1) const
Drop the last N elements of the array.
bool empty() const
empty - Check if the array is empty.
Value handle that asserts if the Value is deleted.
A cache of @llvm.assume calls within a function.
LLVM Basic Block Representation.
iterator begin()
Instruction iterator methods.
iterator_range< const_phi_iterator > phis() const
Returns a range that iterates over the phis in the basic block.
const_iterator getFirstInsertionPt() const
Returns an iterator to the first instruction in this block that is suitable for inserting a non-PHI i...
bool hasAddressTaken() const
Returns true if there are any uses of this basic block other than direct branches,...
InstListType::const_iterator getFirstNonPHIIt() const
Returns an iterator to the first instruction in this block that is not a PHINode instruction.
void insertDbgRecordBefore(DbgRecord *DR, InstListType::iterator Here)
Insert a DbgRecord into a block at the position given by Here.
const Instruction & front() const
static BasicBlock * Create(LLVMContext &Context, const Twine &Name="", Function *Parent=nullptr, BasicBlock *InsertBefore=nullptr)
Creates a new BasicBlock.
bool isEntryBlock() const
Return true if this is the entry block of the containing function.
void moveAfter(BasicBlock *MovePos)
Unlink this basic block from its current function and insert it right after MovePos in the function M...
InstListType::const_iterator getFirstNonPHIOrDbg(bool SkipPseudoOp=true) const
Returns a pointer to the first instruction in this block that is not a PHINode or a debug intrinsic,...
bool hasNPredecessors(unsigned N) const
Return true if this block has exactly N predecessors.
const BasicBlock * getSinglePredecessor() const
Return the predecessor of this block if it has a single predecessor block.
void flushTerminatorDbgRecords()
Eject any debug-info trailing at the end of a block.
const Function * getParent() const
Return the enclosing method, or null if none.
const DataLayout & getDataLayout() const
Get the data layout of the module this basic block belongs to.
SymbolTableList< BasicBlock >::iterator eraseFromParent()
Unlink 'this' from the containing function and delete it.
InstListType::iterator iterator
Instruction iterators...
LLVMContext & getContext() const
Get the context in which this basic block lives.
const Instruction * getTerminator() const LLVM_READONLY
Returns the terminator instruction if the block is well formed or null if the block is not well forme...
bool hasNPredecessorsOrMore(unsigned N) const
Return true if this block has N predecessors or more.
void splice(BasicBlock::iterator ToIt, BasicBlock *FromBB)
Transfer all instructions from FromBB to this basic block at ToIt.
const Instruction & back() const
void removePredecessor(BasicBlock *Pred, bool KeepOneInputPHIs=false)
Update PHI nodes in this BasicBlock before removal of predecessor Pred.
BinaryOps getOpcode() const
static BinaryOperator * CreateNot(Value *Op, const Twine &Name="", InsertPosition InsertBefore=nullptr)
static BinaryOperator * Create(BinaryOps Op, Value *S1, Value *S2, const Twine &Name=Twine(), InsertPosition InsertBefore=nullptr)
Construct a binary instruction, given the opcode and the two operands.
This class represents a no-op cast from one type to another.
The address of a basic block.
static BlockAddress * get(Function *F, BasicBlock *BB)
Return a BlockAddress for the specified function and basic block.
Conditional or Unconditional Branch instruction.
static BranchInst * Create(BasicBlock *IfTrue, InsertPosition InsertBefore=nullptr)
Base class for all callable instructions (InvokeInst and CallInst) Holds everything related to callin...
void setCallingConv(CallingConv::ID CC)
void addFnAttr(Attribute::AttrKind Kind)
Adds the attribute to the function.
void getOperandBundlesAsDefs(SmallVectorImpl< OperandBundleDef > &Defs) const
Return the list of operand bundles attached to this instruction as a vector of OperandBundleDefs.
Function * getCalledFunction() const
Returns the function called, or null if this is an indirect function invocation or the function signa...
CallingConv::ID getCallingConv() const
Value * getCalledOperand() const
void setAttributes(AttributeList A)
Set the attributes for this call.
FunctionType * getFunctionType() const
iterator_range< User::op_iterator > args()
Iteration adapter for range-for loops.
AttributeList getAttributes() const
Return the attributes for this call.
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 CastInst * CreateIntegerCast(Value *S, Type *Ty, bool isSigned, const Twine &Name="", InsertPosition InsertBefore=nullptr)
Create a ZExt, BitCast, or Trunc for int -> int casts.
static CatchSwitchInst * Create(Value *ParentPad, BasicBlock *UnwindDest, unsigned NumHandlers, const Twine &NameStr="", InsertPosition InsertBefore=nullptr)
static CleanupReturnInst * Create(Value *CleanupPad, BasicBlock *UnwindBB=nullptr, InsertPosition InsertBefore=nullptr)
Predicate
This enumeration lists the possible predicates for CmpInst subclasses.
@ ICMP_SLT
signed less than
@ ICMP_SLE
signed less or equal
@ ICMP_UGE
unsigned greater or equal
@ ICMP_UGT
unsigned greater than
@ ICMP_SGT
signed greater than
@ ICMP_ULT
unsigned less than
@ ICMP_SGE
signed greater or equal
@ ICMP_ULE
unsigned less or equal
Predicate getPredicate() const
Return the predicate for this instruction.
A constant value that is initialized with an expression using other constant values.
static Constant * getIntToPtr(Constant *C, Type *Ty, bool OnlyIfReduced=false)
static Constant * getNot(Constant *C)
static Constant * getPtrToInt(Constant *C, Type *Ty, bool OnlyIfReduced=false)
static Constant * getAdd(Constant *C1, Constant *C2, bool HasNUW=false, bool HasNSW=false)
This is the shared class of boolean and integer constants.
static ConstantPointerNull * get(PointerType *T)
Static factory methods - Return objects of the specified value.
bool contains(const APInt &Val) const
Return true if the specified value is in the set.
This is an important base class in LLVM.
void destroyConstant()
Called if some element of this constant is no longer valid.
DIExpression * createConstantValueExpression(uint64_t Val)
Create an expression for a variable that does not have an address, but does have a constant value.
static DIExpression * append(const DIExpression *Expr, ArrayRef< uint64_t > Ops)
Append the opcodes Ops to DIExpr.
unsigned getNumElements() const
static ExtOps getExtOps(unsigned FromSize, unsigned ToSize, bool Signed)
Returns the ops for a zero- or sign-extension in a DIExpression.
static void appendOffset(SmallVectorImpl< uint64_t > &Ops, int64_t Offset)
Append Ops with operations to apply the Offset.
static DIExpression * appendOpsToArg(const DIExpression *Expr, ArrayRef< uint64_t > Ops, unsigned ArgNo, bool StackValue=false)
Create a copy of Expr by appending the given list of Ops to each instance of the operand DW_OP_LLVM_a...
static std::optional< FragmentInfo > getFragmentInfo(expr_op_iterator Start, expr_op_iterator End)
Retrieve the details of this fragment expression.
DIExpression * foldConstantMath()
Try to shorten an expression with constant math operations that can be evaluated at compile time.
uint64_t getNumLocationOperands() const
Return the number of unique location operands referred to (via DW_OP_LLVM_arg) in this expression; th...
ArrayRef< uint64_t > getElements() const
std::optional< uint64_t > getActiveBits(DIVariable *Var)
Return the number of bits that have an active value, i.e.
uint64_t getElement(unsigned I) const
static DIExpression * prepend(const DIExpression *Expr, uint8_t Flags, int64_t Offset=0)
Prepend DIExpr with a deref and offset operation and optionally turn it into a stack value or/and an ...
static DIExpression * appendExt(const DIExpression *Expr, unsigned FromSize, unsigned ToSize, bool Signed)
Append a zero- or sign-extension to Expr.
std::optional< DIBasicType::Signedness > getSignedness() const
Return the signedness of this variable's type, or std::nullopt if this type is neither signed nor uns...
This class represents an Operation in the Expression.
A parsed version of the target data layout string in and methods for querying it.
This represents the llvm.dbg.label instruction.
Instruction * MarkedInstr
Link back to the Instruction that owns this marker.
This represents the llvm.dbg.value instruction.
This is the common base class for debug info intrinsics for variables.
iterator_range< location_op_iterator > location_ops() const
Get the locations corresponding to the variable referenced by the debug info intrinsic.
void replaceVariableLocationOp(Value *OldValue, Value *NewValue, bool AllowEmpty=false)
Value * getVariableLocationOp(unsigned OpIdx) const
void setExpression(DIExpression *NewExpr)
DILocalVariable * getVariable() const
unsigned getNumVariableLocationOps() const
bool isAddressOfVariable() const
Does this describe the address of a local variable.
DIExpression * getExpression() const
Record of a variable value-assignment, aka a non instruction representation of the dbg....
bool isAddressOfVariable() const
Does this describe the address of a local variable.
DbgVariableRecord * clone() const
void setExpression(DIExpression *NewExpr)
DIExpression * getExpression() const
Value * getVariableLocationOp(unsigned OpIdx) const
DILocalVariable * getVariable() const
unsigned getNumVariableLocationOps() const
void replaceVariableLocationOp(Value *OldValue, Value *NewValue, bool AllowEmpty=false)
iterator_range< location_op_iterator > location_ops() const
Get the locations corresponding to the variable referenced by the debug info intrinsic.
DILocation * get() const
Get the underlying DILocation.
iterator find(const_arg_type_t< KeyT > Val)
size_type count(const_arg_type_t< KeyT > Val) const
Return 1 if the specified key is in the map, 0 otherwise.
std::pair< iterator, bool > insert(const std::pair< KeyT, ValueT > &KV)
Implements a dense probed hash-table based set.
void deleteBB(BasicBlock *DelBB)
Delete DelBB.
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.
const BasicBlock & getEntryBlock() const
void applyUpdatesPermissive(ArrayRef< UpdateT > Updates)
Submit updates to all available trees.
void applyUpdates(ArrayRef< UpdateT > Updates)
Submit updates to all available trees.
bool hasDomTree() const
Returns true if it holds a DomTreeT.
bool isBBPendingDeletion(BasicBlockT *DelBB) const
Returns true if DelBB is awaiting deletion.
void recalculate(FuncT &F)
Notify DTU that the entry block was replaced.
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.
Value * CreateICmpEQ(Value *LHS, Value *RHS, const Twine &Name="")
BranchInst * CreateCondBr(Value *Cond, BasicBlock *True, BasicBlock *False, MDNode *BranchWeights=nullptr, MDNode *Unpredictable=nullptr)
Create a conditional 'br Cond, TrueDest, FalseDest' instruction.
BranchInst * CreateBr(BasicBlock *Dest)
Create an unconditional 'br label X' instruction.
This provides a uniform API for creating instructions and inserting them into a basic block: either a...
iterator_range< simple_ilist< DbgRecord >::iterator > getDbgRecordRange() const
Return a range over the DbgRecords attached to this instruction.
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.
bool extractProfTotalWeight(uint64_t &TotalVal) const
Retrieve total raw weight values of a branch.
void moveAfter(Instruction *MovePos)
Unlink this instruction from its current basic block and insert it into the basic block that MovePos ...
bool isEHPad() const
Return true if the instruction is a variety of EH-block.
InstListType::iterator eraseFromParent()
This method unlinks 'this' from the containing basic block and deletes it.
bool isIdenticalToWhenDefined(const Instruction *I, bool IntersectAttrs=false) const LLVM_READONLY
This is like isIdenticalTo, except that it ignores the SubclassOptionalData flags,...
MDNode * getMetadata(unsigned KindID) const
Get the metadata of given kind attached to this Instruction.
const Instruction * getNextNonDebugInstruction(bool SkipPseudoOp=false) const
Return a pointer to the next non-debug instruction in the same basic block as 'this',...
void setMetadata(unsigned KindID, MDNode *Node)
Set the metadata of the specified kind to the specified node.
void dropPoisonGeneratingFlags()
Drops flags that may cause this instruction to evaluate to poison despite having non-poison inputs.
void setDebugLoc(DebugLoc Loc)
Set the debug location information for this instruction.
void copyMetadata(const Instruction &SrcInst, ArrayRef< unsigned > WL=ArrayRef< unsigned >())
Copy metadata from SrcInst to this instruction.
void dropDbgRecords()
Erase any DbgRecords attached to this instruction.
const DataLayout & getDataLayout() const
Get the data layout of the module this instruction belongs to.
A wrapper class for inspecting calls to intrinsic functions.
static InvokeInst * Create(FunctionType *Ty, Value *Func, BasicBlock *IfNormal, BasicBlock *IfException, ArrayRef< Value * > Args, const Twine &NameStr, InsertPosition InsertBefore=nullptr)
This is an important class for using LLVM in a threaded context.
An instruction for reading from memory.
Value * getPointerOperand()
MDNode * createBranchWeights(uint32_t TrueWeight, uint32_t FalseWeight, bool IsExpected=false)
Return metadata containing two branch weights.
MDNode * createRange(const APInt &Lo, const APInt &Hi)
Return metadata describing the range [Lo, Hi).
static MDNode * getMostGenericAliasScope(MDNode *A, MDNode *B)
static MDNode * getMergedCallsiteMetadata(MDNode *A, MDNode *B)
static MDNode * getMostGenericTBAA(MDNode *A, MDNode *B)
static MDNode * getMostGenericNoaliasAddrspace(MDNode *A, MDNode *B)
static MDTuple * get(LLVMContext &Context, ArrayRef< Metadata * > MDs)
static MDNode * getMergedProfMetadata(MDNode *A, MDNode *B, const Instruction *AInstr, const Instruction *BInstr)
Merge !prof metadata from two instructions.
static MDNode * getMostGenericFPMath(MDNode *A, MDNode *B)
static MDNode * getMostGenericRange(MDNode *A, MDNode *B)
static MDNode * getMergedMemProfMetadata(MDNode *A, MDNode *B)
static MDNode * intersect(MDNode *A, MDNode *B)
LLVMContext & getContext() const
static MDNode * getMostGenericAlignmentOrDereferenceable(MDNode *A, MDNode *B)
This class implements a map that also provides access to all stored values in a deterministic order.
iterator find(const KeyT &Key)
std::pair< iterator, bool > try_emplace(const KeyT &Key, Ts &&...Args)
std::pair< iterator, bool > insert(const std::pair< KeyT, ValueT > &KV)
void changeToUnreachable(const Instruction *I)
Instruction I will be changed to an unreachable.
void removeBlocks(const SmallSetVector< BasicBlock *, 8 > &DeadBlocks)
Remove all MemoryAcceses in a set of BasicBlocks about to be deleted.
void removeMemoryAccess(MemoryAccess *, bool OptimizePhis=false)
Remove a MemoryAccess from MemorySSA, including updating all definitions and uses.
A Module instance is used to store all the information related to an LLVM module.
const DataLayout & getDataLayout() const
Get the data layout for the module's target platform.
void addIncoming(Value *V, BasicBlock *BB)
Add an incoming value to the end of the PHI list.
const_block_iterator block_begin() const
Value * removeIncomingValue(unsigned Idx, bool DeletePHIIfEmpty=true)
Remove an incoming value.
void setIncomingValue(unsigned i, Value *V)
const_block_iterator block_end() const
Value * getIncomingValueForBlock(const BasicBlock *BB) const
BasicBlock * getIncomingBlock(unsigned i) const
Return incoming basic block number i.
Value * getIncomingValue(unsigned i) const
Return incoming value number x.
unsigned getNumIncomingValues() const
Return the number of incoming edges.
static PoisonValue * get(Type *T)
Static factory methods - Return an 'poison' object of the specified type.
size_type size() const
Determine the number of elements in the SetVector.
Vector takeVector()
Clear the SetVector and return the underlying vector.
size_type count(const key_type &key) const
Count the number of elements of a given key in the SetVector.
bool empty() const
Determine if the SetVector is empty or not.
bool insert(const value_type &X)
Insert a new element into the SetVector.
value_type pop_back_val()
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.
bool contains(ConstPtrType Ptr) const
SmallPtrSet - This class implements a set which is optimized for holding SmallSize or less elements.
A SetVector that performs no allocations if smaller than a certain size.
SmallSet - This maintains a set of unique values, optimizing for the case when the set is small (less...
std::pair< const_iterator, bool > insert(const T &V)
insert - Insert an element into the set if it isn't already there.
This class consists of common code factored out of the SmallVector class to reduce code duplication b...
void reserve(size_type N)
void append(ItTy in_start, ItTy in_end)
Add the specified range to the end of the SmallVector.
iterator insert(iterator I, T &&Elt)
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.
Provides information about what library functions are available for the current target.
bool hasOptimizedCodeGen(LibFunc F) const
Tests if the function is both available and a candidate for optimized code generation.
bool has(LibFunc F) const
Tests whether a library function is available.
bool getLibFunc(StringRef funcName, LibFunc &F) const
Searches for a particular function name.
TinyPtrVector - This class is specialized for cases where there are normally 0 or 1 element in a vect...
static constexpr TypeSize getFixed(ScalarTy ExactSize)
The instances of the Type class are immutable: once they are created, they are never changed.
bool isVectorTy() const
True if this is an instance of VectorType.
bool isArrayTy() const
True if this is an instance of ArrayType.
bool isIntOrIntVectorTy() const
Return true if this is an integer type or a vector of integer types.
bool isPointerTy() const
True if this is an instance of PointerType.
static IntegerType * getIntNTy(LLVMContext &C, unsigned N)
unsigned getScalarSizeInBits() const LLVM_READONLY
If this is a vector type, return the getPrimitiveSizeInBits value for the element type.
bool isStructTy() const
True if this is an instance of StructType.
bool isFloatingPointTy() const
Return true if this is one of the floating-point types.
bool isIntOrPtrTy() const
Return true if this is an integer type or a pointer type.
static IntegerType * getInt32Ty(LLVMContext &C)
bool isIntegerTy() const
True if this is an instance of IntegerType.
bool isTokenTy() const
Return true if this is 'token'.
TypeSize getPrimitiveSizeInBits() const LLVM_READONLY
Return the basic size of this type if it is a primitive type.
static UndefValue * get(Type *T)
Static factory methods - Return an 'undef' object of the specified type.
This function has undefined behavior.
A Use represents the edge between a Value definition and its users.
value_op_iterator value_op_end()
Value * getOperand(unsigned i) const
value_op_iterator value_op_begin()
iterator find(const KeyT &Val)
std::pair< iterator, bool > insert(const std::pair< KeyT, ValueT > &KV)
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()
void replaceUsesWithIf(Value *New, llvm::function_ref< bool(Use &U)> ShouldReplace)
Go through the uses list for this definition and make each use point to "V" if the callback ShouldRep...
LLVMContext & getContext() const
All values hold a context through their type.
static constexpr unsigned MaxAlignmentExponent
The maximum alignment for instructions.
user_iterator_impl< User > user_iterator
StringRef getName() const
Return a constant reference to the value's name.
void takeName(Value *V)
Transfer the name from V to this value.
Represents an op.with.overflow intrinsic.
std::pair< iterator, bool > insert(const ValueT &V)
void reserve(size_t Size)
Grow the DenseSet so that it can contain at least NumEntries items before resizing again.
An efficient, type-erasing, non-owning reference to a callable.
const ParentTy * getParent() const
self_iterator getIterator()
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
@ C
The default llvm calling convention, compatible with C.
Function * getOrInsertDeclaration(Module *M, ID id, ArrayRef< Type * > Tys={})
Look up the Function declaration of the intrinsic id in the Module M.
BinaryOp_match< LHS, RHS, Instruction::And > m_And(const LHS &L, const RHS &R)
m_Intrinsic_Ty< Opnd0 >::Ty m_BitReverse(const Opnd0 &Op0)
CastInst_match< OpTy, TruncInst > m_Trunc(const OpTy &Op)
Matches Trunc.
bool match(Val *V, const Pattern &P)
specificval_ty m_Specific(const Value *V)
Match if we have a specific specified value.
BinOpPred_match< LHS, RHS, is_logical_shift_op > m_LogicalShift(const LHS &L, const RHS &R)
Matches logical shift operations.
bind_ty< WithOverflowInst > m_WithOverflowInst(WithOverflowInst *&I)
Match a with overflow intrinsic, capturing it if we match.
CastInst_match< OpTy, ZExtInst > m_ZExt(const OpTy &Op)
Matches ZExt.
m_Intrinsic_Ty< Opnd0, Opnd1, Opnd2 >::Ty m_FShl(const Opnd0 &Op0, const Opnd1 &Op1, const Opnd2 &Op2)
apint_match m_APInt(const APInt *&Res)
Match a ConstantInt or splatted ConstantVector, binding the specified pointer to the contained APInt.
class_match< Value > m_Value()
Match an arbitrary value and ignore it.
m_Intrinsic_Ty< Opnd0, Opnd1, Opnd2 >::Ty m_FShr(const Opnd0 &Op0, const Opnd1 &Op1, const Opnd2 &Op2)
auto m_Undef()
Match an arbitrary undef constant.
BinaryOp_match< cst_pred_ty< is_all_ones >, ValTy, Instruction::Xor, true > m_Not(const ValTy &V)
Matches a 'Not' as 'xor V, -1' or 'xor -1, V'.
BinaryOp_match< LHS, RHS, Instruction::Or > m_Or(const LHS &L, const RHS &R)
m_Intrinsic_Ty< Opnd0 >::Ty m_BSwap(const Opnd0 &Op0)
is_zero m_Zero()
Match any null constant or a vector with all elements equal to 0.
match_combine_or< LTy, RTy > m_CombineOr(const LTy &L, const RTy &R)
Combine two pattern matchers matching L || R.
initializer< Ty > init(const Ty &Val)
@ DW_OP_LLVM_arg
Only used in LLVM metadata.
@ ebStrict
This corresponds to "fpexcept.strict".
This is an optimization pass for GlobalISel generic memory operations.
auto find(R &&Range, const T &Val)
Provide wrappers to std::find which take ranges instead of having to pass begin/end explicitly.
bool RemoveRedundantDbgInstrs(BasicBlock *BB)
Try to remove redundant dbg.value instructions from given basic block.
UnaryFunction for_each(R &&Range, UnaryFunction F)
Provide wrappers to std::for_each which take ranges instead of having to pass begin/end explicitly.
bool all_of(R &&range, UnaryPredicate P)
Provide wrappers to std::all_of which take ranges instead of having to pass begin/end explicitly.
bool RecursivelyDeleteTriviallyDeadInstructions(Value *V, const TargetLibraryInfo *TLI=nullptr, MemorySSAUpdater *MSSAU=nullptr, std::function< void(Value *)> AboutToDeleteCallback=std::function< void(Value *)>())
If the specified value is a trivially dead instruction, delete it.
bool succ_empty(const Instruction *I)
BasicBlock * changeToInvokeAndSplitBasicBlock(CallInst *CI, BasicBlock *UnwindEdge, DomTreeUpdater *DTU=nullptr)
Convert the CallInst to InvokeInst with the specified unwind edge basic block.
bool ConstantFoldTerminator(BasicBlock *BB, bool DeleteDeadConditions=false, const TargetLibraryInfo *TLI=nullptr, DomTreeUpdater *DTU=nullptr)
If a terminator instruction is predicated on a constant value, convert it into an unconditional branc...
unsigned replaceDominatedUsesWithIf(Value *From, Value *To, DominatorTree &DT, const BasicBlockEdge &Edge, function_ref< bool(const Use &U, const Value *To)> ShouldReplace)
Replace each use of 'From' with 'To' if that use is dominated by the given edge and the callback Shou...
TinyPtrVector< DbgDeclareInst * > findDbgDeclares(Value *V)
Finds dbg.declare intrinsics declaring local variables as living in the memory that 'V' points to.
std::pair< unsigned, unsigned > removeAllNonTerminatorAndEHPadInstructions(BasicBlock *BB)
Remove all instructions from a basic block other than its terminator and any present EH pad instructi...
auto pred_end(const MachineBasicBlock *BB)
unsigned replaceNonLocalUsesWith(Instruction *From, Value *To)
void salvageDebugInfoForDbgValues(Instruction &I, ArrayRef< DbgVariableIntrinsic * > Insns, ArrayRef< DbgVariableRecord * > DPInsns)
Implementation of salvageDebugInfo, applying only to instructions in Insns, rather than all debug use...
void findDbgUsers(SmallVectorImpl< DbgVariableIntrinsic * > &DbgInsts, Value *V, SmallVectorImpl< DbgVariableRecord * > *DbgVariableRecords=nullptr)
Finds the debug info intrinsics describing a value.
void salvageDebugInfo(const MachineRegisterInfo &MRI, MachineInstr &MI)
Assuming the instruction MI is going to be deleted, attempt to salvage debug users of MI by writing t...
auto successors(const MachineBasicBlock *BB)
bool isRemovableAlloc(const CallBase *V, const TargetLibraryInfo *TLI)
Return true if this is a call to an allocation function that does not have side effects that we are r...
CallInst * changeToCall(InvokeInst *II, DomTreeUpdater *DTU=nullptr)
This function converts the specified invoke into a normal call.
bool isMathLibCallNoop(const CallBase *Call, const TargetLibraryInfo *TLI)
Check whether the given call has no side-effects.
void copyMetadataForLoad(LoadInst &Dest, const LoadInst &Source)
Copy the metadata from the source instruction to the destination (the replacement for the source inst...
void InsertDebugValueAtStoreLoc(DbgVariableRecord *DVR, StoreInst *SI, DIBuilder &Builder)
===------------------------------------------------------------------—===// Dbg Intrinsic utilities
bool hasNItemsOrLess(IterTy &&Begin, IterTy &&End, unsigned N, Pred &&ShouldBeCounted=[](const decltype(*std::declval< IterTy >()) &) { return true;})
Returns true if the sequence [Begin, End) has N or less items.
void remapDebugVariable(ValueToValueMapTy &Mapping, Instruction *Inst)
Remap the operands of the debug records attached to Inst, and the operands of Inst itself if it's a d...
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...
auto pred_size(const MachineBasicBlock *BB)
bool SimplifyInstructionsInBlock(BasicBlock *BB, const TargetLibraryInfo *TLI=nullptr)
Scan the specified basic block and try to simplify any instructions in it and recursively delete dead...
bool isAssumeWithEmptyBundle(const AssumeInst &Assume)
Return true iff the operand bundles of the provided llvm.assume doesn't contain any valuable informat...
void DeleteDeadBlock(BasicBlock *BB, DomTreeUpdater *DTU=nullptr, bool KeepOneInputPHIs=false)
Delete the specified block, which must have no predecessors.
bool hasBranchWeightOrigin(const Instruction &I)
Check if Branch Weight Metadata has an "expected" field from an llvm.expect* intrinsic.
void findDbgValues(SmallVectorImpl< DbgValueInst * > &DbgValues, Value *V, SmallVectorImpl< DbgVariableRecord * > *DbgVariableRecords=nullptr)
Finds the llvm.dbg.value intrinsics describing a value.
void insertDebugValuesForPHIs(BasicBlock *BB, SmallVectorImpl< PHINode * > &InsertedPHIs)
Propagate dbg.value intrinsics through the newly inserted PHIs.
ConstantRange getConstantRangeFromMetadata(const MDNode &RangeMD)
Parse out a conservative ConstantRange from !range metadata.
MDNode * intersectAccessGroups(const Instruction *Inst1, const Instruction *Inst2)
Compute the access-group list of access groups that Inst1 and Inst2 are both in.
bool handleUnreachableTerminator(Instruction *I, SmallVectorImpl< Value * > &PoisonedValues)
If a terminator in an unreachable basic block has an operand of type Instruction, transform it into p...
bool canSimplifyInvokeNoUnwind(const Function *F)
Value * simplifyInstruction(Instruction *I, const SimplifyQuery &Q)
See if we can compute a simplified version of this instruction.
bool any_of(R &&range, UnaryPredicate P)
Provide wrappers to std::any_of which take ranges instead of having to pass begin/end explicitly.
bool isInstructionTriviallyDead(Instruction *I, const TargetLibraryInfo *TLI=nullptr)
Return true if the result produced by the instruction is not used, and the instruction will return.
bool TryToSimplifyUncondBranchFromEmptyBlock(BasicBlock *BB, DomTreeUpdater *DTU=nullptr)
BB is known to contain an unconditional branch, and contains no instructions other than PHI nodes,...
bool recognizeBSwapOrBitReverseIdiom(Instruction *I, bool MatchBSwaps, bool MatchBitReversals, SmallVectorImpl< Instruction * > &InsertedInsts)
Try to match a bswap or bitreverse idiom.
void setBranchWeights(Instruction &I, ArrayRef< uint32_t > Weights, bool IsExpected)
Create a new branch_weights metadata node and add or overwrite a prof metadata reference to instructi...
MDNode * getValidBranchWeightMDNode(const Instruction &I)
Get the valid branch weights metadata node.
Align getOrEnforceKnownAlignment(Value *V, MaybeAlign PrefAlign, const DataLayout &DL, const Instruction *CxtI=nullptr, AssumptionCache *AC=nullptr, const DominatorTree *DT=nullptr)
Try to ensure that the alignment of V is at least PrefAlign bytes.
bool wouldInstructionBeTriviallyDeadOnUnusedPaths(Instruction *I, const TargetLibraryInfo *TLI=nullptr)
Return true if the result produced by the instruction has no side effects on any paths other than whe...
bool LowerDbgDeclare(Function &F)
Lowers llvm.dbg.declare intrinsics into appropriate set of llvm.dbg.value intrinsics.
bool NullPointerIsDefined(const Function *F, unsigned AS=0)
Check whether null pointer dereferencing is considered undefined behavior for a given function or an ...
DIExpression * getExpressionForConstant(DIBuilder &DIB, const Constant &C, Type &Ty)
Given a constant, create a debug information expression.
CallInst * createCallMatchingInvoke(InvokeInst *II)
Create a call that matches the invoke II in terms of arguments, attributes, debug information,...
raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
Instruction * removeUnwindEdge(BasicBlock *BB, DomTreeUpdater *DTU=nullptr)
Replace 'BB's terminator with one that does not have an unwind successor block.
bool wouldInstructionBeTriviallyDead(const Instruction *I, const TargetLibraryInfo *TLI=nullptr)
Return true if the result produced by the instruction would have no side effects if it was not used.
void patchReplacementInstruction(Instruction *I, Value *Repl)
Patch the replacement so that it is not more restrictive than the value being replaced.
DebugLoc getDebugValueLoc(DbgVariableIntrinsic *DII)
Produce a DebugLoc to use for each dbg.declare that is promoted to a dbg.value.
void ConvertDebugDeclareToDebugValue(DbgVariableIntrinsic *DII, StoreInst *SI, DIBuilder &Builder)
Inserts a llvm.dbg.value intrinsic before a store to an alloca'd value that has an associated llvm....
unsigned replaceDominatedUsesWith(Value *From, Value *To, DominatorTree &DT, const BasicBlockEdge &Edge)
Replace each use of 'From' with 'To' if that use is dominated by the given edge.
unsigned changeToUnreachable(Instruction *I, bool PreserveLCSSA=false, DomTreeUpdater *DTU=nullptr, MemorySSAUpdater *MSSAU=nullptr)
Insert an unreachable instruction before the specified instruction, making it and the rest of the cod...
bool replaceAllDbgUsesWith(Instruction &From, Value &To, Instruction &DomPoint, DominatorTree &DT)
Point debug users of From to To or salvage them.
Value * salvageDebugInfoImpl(Instruction &I, uint64_t CurrentLocOps, SmallVectorImpl< uint64_t > &Ops, SmallVectorImpl< Value * > &AdditionalValues)
RNSuccIterator< NodeRef, BlockT, RegionT > succ_begin(NodeRef Node)
void combineMetadataForCSE(Instruction *K, const Instruction *J, bool DoesKMove)
Combine the metadata of two instructions so that K can replace J.
void dropDebugUsers(Instruction &I)
Remove the debug intrinsic instructions for the given instruction.
@ First
Helpers to iterate all locations in the MemoryEffectsBase class.
void MergeBasicBlockIntoOnlyPred(BasicBlock *BB, DomTreeUpdater *DTU=nullptr)
BB is a block with one predecessor and its predecessor is known to have one successor (BB!...
bool replaceDbgUsesWithUndef(Instruction *I)
Replace all the uses of an SSA value in @llvm.dbg intrinsics with undef.
void hoistAllInstructionsInto(BasicBlock *DomBlock, Instruction *InsertPt, BasicBlock *BB)
Hoist all of the instructions in the IfBlock to the dominant block DomBlock, by moving its instructio...
void copyRangeMetadata(const DataLayout &DL, const LoadInst &OldLI, MDNode *N, LoadInst &NewLI)
Copy a range metadata node to a new load instruction.
void copyNonnullMetadata(const LoadInst &OldLI, MDNode *N, LoadInst &NewLI)
Copy a nonnull metadata node to a new load instruction.
void computeKnownBits(const Value *V, KnownBits &Known, const DataLayout &DL, unsigned Depth=0, AssumptionCache *AC=nullptr, const Instruction *CxtI=nullptr, const DominatorTree *DT=nullptr, bool UseInstrInfo=true)
Determine which bits of V are known to be either zero or one and return them in the KnownZero/KnownOn...
bool canReplaceOperandWithVariable(const Instruction *I, unsigned OpIdx)
Given an instruction, is it legal to set operand OpIdx to a non-constant value?
void replaceDbgValueForAlloca(AllocaInst *AI, Value *NewAllocaAddress, DIBuilder &Builder, int Offset=0)
Replaces multiple llvm.dbg.value instructions when the alloca it describes is replaced with a new val...
Align tryEnforceAlignment(Value *V, Align PrefAlign, const DataLayout &DL)
If the specified pointer points to an object that we control, try to modify the object's alignment to...
Value * getFreedOperand(const CallBase *CB, const TargetLibraryInfo *TLI)
If this if a call to a free function, return the freed operand.
bool RecursivelyDeleteTriviallyDeadInstructionsPermissive(SmallVectorImpl< WeakTrackingVH > &DeadInsts, const TargetLibraryInfo *TLI=nullptr, MemorySSAUpdater *MSSAU=nullptr, std::function< void(Value *)> AboutToDeleteCallback=std::function< void(Value *)>())
Same functionality as RecursivelyDeleteTriviallyDeadInstructions, but allow instructions that are not...
constexpr unsigned BitWidth
bool extractBranchWeights(const MDNode *ProfileData, SmallVectorImpl< uint32_t > &Weights)
Extract branch weights from MD_prof metadata.
auto count_if(R &&Range, UnaryPredicate P)
Wrapper function around std::count_if to count the number of times an element satisfying a given pred...
auto pred_begin(const MachineBasicBlock *BB)
BasicBlock * SplitBlock(BasicBlock *Old, BasicBlock::iterator SplitPt, DominatorTree *DT, LoopInfo *LI=nullptr, MemorySSAUpdater *MSSAU=nullptr, const Twine &BBName="", bool Before=false)
Split the specified block at the specified instruction.
gep_type_iterator gep_type_begin(const User *GEP)
TinyPtrVector< DbgVariableRecord * > findDVRDeclares(Value *V)
As above, for DVRDeclares.
auto predecessors(const MachineBasicBlock *BB)
bool is_contained(R &&Range, const E &Element)
Returns true if Element is found in Range.
void combineAAMetadata(Instruction *K, const Instruction *J)
Combine metadata of two instructions, where instruction J is a memory access that has been merged int...
bool RecursivelyDeleteDeadPHINode(PHINode *PN, const TargetLibraryInfo *TLI=nullptr, MemorySSAUpdater *MSSAU=nullptr)
If the specified value is an effectively dead PHI node, due to being a def-use chain of single-use no...
bool inferAttributesFromOthers(Function &F)
If we can infer one attribute from another on the declaration of a function, explicitly materialize t...
Value * invertCondition(Value *Condition)
Invert the given true/false value, possibly reusing an existing copy.
hash_code hash_combine(const Ts &...args)
Combine values into a single hash_code.
void DeleteDeadBlocks(ArrayRef< BasicBlock * > BBs, DomTreeUpdater *DTU=nullptr, bool KeepOneInputPHIs=false)
Delete the specified blocks from BB.
void maybeMarkSanitizerLibraryCallNoBuiltin(CallInst *CI, const TargetLibraryInfo *TLI)
Given a CallInst, check if it calls a string function known to CodeGen, and mark it with NoBuiltin if...
static auto filterDbgVars(iterator_range< simple_ilist< DbgRecord >::iterator > R)
Filter the DbgRecord range to DbgVariableRecord types only and downcast.
bool removeUnreachableBlocks(Function &F, DomTreeUpdater *DTU=nullptr, MemorySSAUpdater *MSSAU=nullptr)
Remove all blocks that can not be reached from the function's entry.
bool EliminateDuplicatePHINodes(BasicBlock *BB)
Check for and eliminate duplicate PHI nodes in this block.
bool callsGCLeafFunction(const CallBase *Call, const TargetLibraryInfo &TLI)
Return true if this call calls a gc leaf function.
hash_code hash_combine_range(InputIteratorT first, InputIteratorT last)
Compute a hash_code for a sequence of values.
bool replaceDbgDeclare(Value *Address, Value *NewAddress, DIBuilder &Builder, uint8_t DIExprFlags, int Offset)
Replaces llvm.dbg.declare instruction when the address it describes is replaced with a new value.
void swap(llvm::BitVector &LHS, llvm::BitVector &RHS)
Implement std::swap in terms of BitVector swap.
This struct is a compact representation of a valid (non-zero power of two) alignment.
An information struct used to provide DenseMap with the various necessary components for a given valu...
unsigned countMinTrailingZeros() const
Returns the minimum number of trailing zero bits.
unsigned getBitWidth() const
Get the bit width of this value.
This struct is a compact representation of a valid (power of two) or undefined (0) alignment.
A MapVector that performs no allocations if smaller than a certain size.