96#define DEBUG_TYPE "loop-idiom" 
   98STATISTIC(NumMemSet, 
"Number of memset's formed from loop stores");
 
   99STATISTIC(NumMemCpy, 
"Number of memcpy's formed from loop load+stores");
 
  100STATISTIC(NumMemMove, 
"Number of memmove's formed from loop load+stores");
 
  101STATISTIC(NumStrLen, 
"Number of strlen's and wcslen's formed from loop loads");
 
  103    NumShiftUntilBitTest,
 
  104    "Number of uncountable loops recognized as 'shift until bitttest' idiom");
 
  106          "Number of uncountable loops recognized as 'shift until zero' idiom");
 
  111                   cl::desc(
"Options to disable Loop Idiom Recognize Pass."),
 
  118                      cl::desc(
"Proceed with loop idiom recognize pass, but do " 
  119                               "not convert loop(s) to memset."),
 
  126                      cl::desc(
"Proceed with loop idiom recognize pass, but do " 
  127                               "not convert loop(s) to memcpy."),
 
  134                      cl::desc(
"Proceed with loop idiom recognize pass, but do " 
  135                               "not convert loop(s) to strlen."),
 
  142                     cl::desc(
"Proceed with loop idiom recognize pass, " 
  143                              "enable conversion of loop(s) to wcslen."),
 
  150                             cl::desc(
"Proceed with loop idiom recognize pass, " 
  151                                      "but do not optimize CRC loops."),
 
  156    "use-lir-code-size-heurs",
 
  157    cl::desc(
"Use loop idiom recognition code size heuristics when compiling " 
  162    "loop-idiom-force-memset-pattern-intrinsic",
 
  163    cl::desc(
"Use memset.pattern intrinsic whenever possible"), 
cl::init(
false),
 
  168class LoopIdiomRecognize {
 
  169  Loop *CurLoop = 
nullptr;
 
  178  bool ApplyCodeSizeHeuristics;
 
  179  std::unique_ptr<MemorySSAUpdater> MSSAU;
 
  188      : 
AA(
AA), DT(DT), LI(LI), SE(SE), TLI(TLI), 
TTI(
TTI), 
DL(
DL), ORE(ORE) {
 
  190      MSSAU = std::make_unique<MemorySSAUpdater>(MSSA);
 
  193  bool runOnLoop(Loop *L);
 
  196  using StoreList = SmallVector<StoreInst *, 8>;
 
  197  using StoreListMap = MapVector<Value *, StoreList>;
 
  199  StoreListMap StoreRefsForMemset;
 
  200  StoreListMap StoreRefsForMemsetPattern;
 
  201  StoreList StoreRefsForMemcpy;
 
  203  bool HasMemsetPattern;
 
  207  enum LegalStoreKind {
 
  212    UnorderedAtomicMemcpy,
 
  220  bool runOnCountableLoop();
 
  221  bool runOnLoopBlock(BasicBlock *BB, 
const SCEV *BECount,
 
  222                      SmallVectorImpl<BasicBlock *> &ExitBlocks);
 
  224  void collectStores(BasicBlock *BB);
 
  225  LegalStoreKind isLegalStore(StoreInst *SI);
 
  226  enum class ForMemset { 
No, 
Yes };
 
  227  bool processLoopStores(SmallVectorImpl<StoreInst *> &SL, 
const SCEV *BECount,
 
  230  template <
typename MemInst>
 
  231  bool processLoopMemIntrinsic(
 
  233      bool (LoopIdiomRecognize::*Processor)(MemInst *, 
const SCEV *),
 
  234      const SCEV *BECount);
 
  235  bool processLoopMemCpy(MemCpyInst *MCI, 
const SCEV *BECount);
 
  236  bool processLoopMemSet(MemSetInst *MSI, 
const SCEV *BECount);
 
  238  bool processLoopStridedStore(
Value *DestPtr, 
const SCEV *StoreSizeSCEV,
 
  239                               MaybeAlign StoreAlignment, 
Value *StoredVal,
 
  240                               Instruction *TheStore,
 
  241                               SmallPtrSetImpl<Instruction *> &Stores,
 
  242                               const SCEVAddRecExpr *Ev, 
const SCEV *BECount,
 
  243                               bool IsNegStride, 
bool IsLoopMemset = 
false);
 
  244  bool processLoopStoreOfLoopLoad(StoreInst *SI, 
const SCEV *BECount);
 
  245  bool processLoopStoreOfLoopLoad(
Value *DestPtr, 
Value *SourcePtr,
 
  246                                  const SCEV *StoreSize, MaybeAlign StoreAlign,
 
  247                                  MaybeAlign LoadAlign, Instruction *TheStore,
 
  248                                  Instruction *TheLoad,
 
  249                                  const SCEVAddRecExpr *StoreEv,
 
  250                                  const SCEVAddRecExpr *LoadEv,
 
  251                                  const SCEV *BECount);
 
  252  bool avoidLIRForMultiBlockLoop(
bool IsMemset = 
false,
 
  253                                 bool IsLoopMemset = 
false);
 
  254  bool optimizeCRCLoop(
const PolynomialInfo &
Info);
 
  260  bool runOnNoncountableLoop();
 
  262  bool recognizePopcount();
 
  263  void transformLoopToPopcount(BasicBlock *PreCondBB, Instruction *CntInst,
 
  264                               PHINode *CntPhi, 
Value *Var);
 
  266                               bool ZeroCheck, 
size_t CanonicalSize);
 
  268                             Instruction *DefX, PHINode *CntPhi,
 
  269                             Instruction *CntInst);
 
  270  bool recognizeAndInsertFFS();  
 
  271  bool recognizeShiftUntilLessThan();
 
  272  void transformLoopToCountable(
Intrinsic::ID IntrinID, BasicBlock *PreCondBB,
 
  273                                Instruction *CntInst, PHINode *CntPhi,
 
  274                                Value *Var, Instruction *DefX,
 
  276                                bool IsCntPhiUsedOutsideLoop,
 
  277                                bool InsertSub = 
false);
 
  279  bool recognizeShiftUntilBitTest();
 
  280  bool recognizeShiftUntilZero();
 
  281  bool recognizeAndInsertStrLen();
 
  293  const auto *
DL = &L.getHeader()->getDataLayout();
 
  300  std::optional<PolynomialInfo> HR;
 
  302  LoopIdiomRecognize LIR(&AR.
AA, &AR.
DT, &AR.
LI, &AR.
SE, &AR.
TLI, &AR.
TTI,
 
  304  if (!LIR.runOnLoop(&L))
 
 
  315  I->eraseFromParent();
 
 
  324bool LoopIdiomRecognize::runOnLoop(
Loop *L) {
 
  328  if (!
L->getLoopPreheader())
 
  333  if (Name == 
"memset" || Name == 
"memcpy" || Name == 
"strlen" ||
 
  338  ApplyCodeSizeHeuristics =
 
  341  HasMemset = TLI->
has(LibFunc_memset);
 
  347  HasMemsetPattern = TLI->
has(LibFunc_memset_pattern16);
 
  348  HasMemcpy = TLI->
has(LibFunc_memcpy);
 
  353      return runOnCountableLoop();
 
  355  return runOnNoncountableLoop();
 
  358bool LoopIdiomRecognize::runOnCountableLoop() {
 
  361         "runOnCountableLoop() called on a loop without a predictable" 
  362         "backedge-taken count");
 
  384  bool MadeChange = 
false;
 
  392    MadeChange |= runOnLoopBlock(BB, BECount, ExitBlocks);
 
  399      optimizeCRCLoop(*Res);
 
  434  if (
DL->isBigEndian())
 
  446  Type *CTy = 
C->getType();
 
 
  453LoopIdiomRecognize::LegalStoreKind
 
  456  if (
SI->isVolatile())
 
  457    return LegalStoreKind::None;
 
  459  if (!
SI->isUnordered())
 
  460    return LegalStoreKind::None;
 
  463  if (
SI->getMetadata(LLVMContext::MD_nontemporal))
 
  464    return LegalStoreKind::None;
 
  466  Value *StoredVal = 
SI->getValueOperand();
 
  467  Value *StorePtr = 
SI->getPointerOperand();
 
  472    return LegalStoreKind::None;
 
  480    return LegalStoreKind::None;
 
  489    return LegalStoreKind::None;
 
  500  bool UnorderedAtomic = 
SI->isUnordered() && !
SI->isSimple();
 
  509    return LegalStoreKind::Memset;
 
  517    return LegalStoreKind::MemsetPattern;
 
  524    unsigned StoreSize = 
DL->getTypeStoreSize(
SI->getValueOperand()->getType());
 
  526    if (StoreSize != StrideAP && StoreSize != -StrideAP)
 
  527      return LegalStoreKind::None;
 
  534      return LegalStoreKind::None;
 
  537      return LegalStoreKind::None;
 
  547      return LegalStoreKind::None;
 
  550    UnorderedAtomic = UnorderedAtomic || LI->
isAtomic();
 
  551    return UnorderedAtomic ? LegalStoreKind::UnorderedAtomicMemcpy
 
  552                           : LegalStoreKind::Memcpy;
 
  555  return LegalStoreKind::None;
 
  558void LoopIdiomRecognize::collectStores(
BasicBlock *BB) {
 
  559  StoreRefsForMemset.clear();
 
  560  StoreRefsForMemsetPattern.clear();
 
  561  StoreRefsForMemcpy.clear();
 
  568    switch (isLegalStore(
SI)) {
 
  569    case LegalStoreKind::None:
 
  572    case LegalStoreKind::Memset: {
 
  575      StoreRefsForMemset[
Ptr].push_back(
SI);
 
  577    case LegalStoreKind::MemsetPattern: {
 
  580      StoreRefsForMemsetPattern[
Ptr].push_back(
SI);
 
  582    case LegalStoreKind::Memcpy:
 
  583    case LegalStoreKind::UnorderedAtomicMemcpy:
 
  584      StoreRefsForMemcpy.push_back(
SI);
 
  587      assert(
false && 
"unhandled return value");
 
  596bool LoopIdiomRecognize::runOnLoopBlock(
 
  606  bool MadeChange = 
false;
 
  613  for (
auto &SL : StoreRefsForMemset)
 
  614    MadeChange |= processLoopStores(SL.second, BECount, ForMemset::Yes);
 
  616  for (
auto &SL : StoreRefsForMemsetPattern)
 
  617    MadeChange |= processLoopStores(SL.second, BECount, ForMemset::No);
 
  620  for (
auto &
SI : StoreRefsForMemcpy)
 
  621    MadeChange |= processLoopStoreOfLoopLoad(
SI, BECount);
 
  623  MadeChange |= processLoopMemIntrinsic<MemCpyInst>(
 
  624      BB, &LoopIdiomRecognize::processLoopMemCpy, BECount);
 
  625  MadeChange |= processLoopMemIntrinsic<MemSetInst>(
 
  626      BB, &LoopIdiomRecognize::processLoopMemSet, BECount);
 
  633                                           const SCEV *BECount, ForMemset For) {
 
  641  for (
unsigned i = 0, e = SL.
size(); i < e; ++i) {
 
  642    assert(SL[i]->
isSimple() && 
"Expected only non-volatile stores.");
 
  644    Value *FirstStoredVal = SL[i]->getValueOperand();
 
  645    Value *FirstStorePtr = SL[i]->getPointerOperand();
 
  649    unsigned FirstStoreSize = 
DL->getTypeStoreSize(SL[i]->getValueOperand()->
getType());
 
  652    if (FirstStride == FirstStoreSize || -FirstStride == FirstStoreSize) {
 
  657    Value *FirstSplatValue = 
nullptr;
 
  658    Constant *FirstPatternValue = 
nullptr;
 
  660    if (For == ForMemset::Yes)
 
  665    assert((FirstSplatValue || FirstPatternValue) &&
 
  666           "Expected either splat value or pattern value.");
 
  674    for (j = i + 1; 
j < 
e; ++
j)
 
  676    for (j = i; 
j > 0; --
j)
 
  679    for (
auto &k : IndexQueue) {
 
  680      assert(SL[k]->
isSimple() && 
"Expected only non-volatile stores.");
 
  681      Value *SecondStorePtr = SL[
k]->getPointerOperand();
 
  686      if (FirstStride != SecondStride)
 
  689      Value *SecondStoredVal = SL[
k]->getValueOperand();
 
  690      Value *SecondSplatValue = 
nullptr;
 
  691      Constant *SecondPatternValue = 
nullptr;
 
  693      if (For == ForMemset::Yes)
 
  698      assert((SecondSplatValue || SecondPatternValue) &&
 
  699             "Expected either splat value or pattern value.");
 
  702        if (For == ForMemset::Yes) {
 
  704            FirstSplatValue = SecondSplatValue;
 
  705          if (FirstSplatValue != SecondSplatValue)
 
  709            FirstPatternValue = SecondPatternValue;
 
  710          if (FirstPatternValue != SecondPatternValue)
 
  715        ConsecutiveChain[SL[i]] = SL[
k];
 
  735    unsigned StoreSize = 0;
 
  738    while (Tails.
count(
I) || Heads.count(
I)) {
 
  739      if (TransformedStores.
count(
I))
 
  743      StoreSize += 
DL->getTypeStoreSize(
I->getValueOperand()->getType());
 
  745      I = ConsecutiveChain[
I];
 
  755    if (StoreSize != Stride && StoreSize != -Stride)
 
  758    bool IsNegStride = StoreSize == -Stride;
 
  762    if (processLoopStridedStore(StorePtr, StoreSizeSCEV,
 
  764                                HeadStore, AdjacentStores, StoreEv, BECount,
 
  776template <
typename MemInst>
 
  777bool LoopIdiomRecognize::processLoopMemIntrinsic(
 
  779    bool (LoopIdiomRecognize::*Processor)(MemInst *, 
const SCEV *),
 
  780    const SCEV *BECount) {
 
  781  bool MadeChange = 
false;
 
  787      if (!(this->*Processor)(
MI, BECount))
 
  801bool LoopIdiomRecognize::processLoopMemCpy(
MemCpyInst *MCI,
 
  802                                           const SCEV *BECount) {
 
  813  if (!Dest || !Source)
 
  821  const APInt *StoreStrideValue, *LoadStrideValue;
 
  832  if ((SizeInBytes >> 32) != 0)
 
  840  if (SizeInBytes != *StoreStrideValue && SizeInBytes != -*StoreStrideValue) {
 
  843             << 
ore::NV(
"Inst", 
"memcpy") << 
" in " 
  845             << 
" function will not be hoisted: " 
  846             << 
ore::NV(
"Reason", 
"memcpy size is not equal to stride");
 
  851  int64_t StoreStrideInt = StoreStrideValue->
getSExtValue();
 
  852  int64_t LoadStrideInt = LoadStrideValue->
getSExtValue();
 
  854  if (StoreStrideInt != LoadStrideInt)
 
  857  return processLoopStoreOfLoopLoad(
 
  864bool LoopIdiomRecognize::processLoopMemSet(
MemSetInst *MSI,
 
  865                                           const SCEV *BECount) {
 
  880  const SCEV *PointerStrideSCEV;
 
  889  bool IsNegStride = 
false;
 
  892  if (IsConstantSize) {
 
  902    if (SizeInBytes != *Stride && SizeInBytes != -*Stride)
 
  905    IsNegStride = SizeInBytes == -*Stride;
 
  913    if (
Pointer->getType()->getPointerAddressSpace() != 0) {
 
  926    const SCEV *PositiveStrideSCEV =
 
  929    LLVM_DEBUG(
dbgs() << 
"  MemsetSizeSCEV: " << *MemsetSizeSCEV << 
"\n" 
  930                      << 
"  PositiveStrideSCEV: " << *PositiveStrideSCEV
 
  933    if (PositiveStrideSCEV != MemsetSizeSCEV) {
 
  936      const SCEV *FoldedPositiveStride =
 
  938      const SCEV *FoldedMemsetSize =
 
  942                        << 
"    FoldedMemsetSize: " << *FoldedMemsetSize << 
"\n" 
  943                        << 
"    FoldedPositiveStride: " << *FoldedPositiveStride
 
  946      if (FoldedPositiveStride != FoldedMemsetSize) {
 
  972                      const SCEV *BECount, 
const SCEV *StoreSizeSCEV,
 
  982  const APInt *BECst, *ConstSize;
 
  986    std::optional<uint64_t> SizeInt = ConstSize->
tryZExtValue();
 
  988    if (BEInt && SizeInt)
 
 
 1010                                        Type *IntPtr, 
const SCEV *StoreSizeSCEV,
 
 1013  if (!StoreSizeSCEV->
isOne()) {
 
 
 1028                               const SCEV *StoreSizeSCEV, 
Loop *CurLoop,
 
 1030  const SCEV *TripCountSCEV =
 
 
 1039bool LoopIdiomRecognize::processLoopStridedStore(
 
 1043    const SCEV *BECount, 
bool IsNegStride, 
bool IsLoopMemset) {
 
 1055  Type *DestInt8PtrTy = Builder.getPtrTy(DestAS);
 
 1066  if (!Expander.isSafeToExpand(Start))
 
 1075      Expander.expandCodeFor(Start, DestInt8PtrTy, Preheader->
getTerminator());
 
 1087                            StoreSizeSCEV, *
AA, Stores))
 
 1090  if (avoidLIRForMultiBlockLoop(
true, IsLoopMemset))
 
 1102  std::optional<int64_t> BytesWritten;
 
 1105    const SCEV *TripCountS =
 
 1107    if (!Expander.isSafeToExpand(TripCountS))
 
 1110    if (!ConstStoreSize)
 
 1112    Value *TripCount = Expander.expandCodeFor(TripCountS, IntIdxTy,
 
 1114    uint64_t PatternRepsPerTrip =
 
 1115        (ConstStoreSize->
getValue()->getZExtValue() * 8) /
 
 1116        DL->getTypeSizeInBits(PatternValue->
getType());
 
 1121        PatternRepsPerTrip == 1
 
 1123            : Builder.CreateMul(TripCount,
 
 1125                                                PatternRepsPerTrip));
 
 1131    const SCEV *NumBytesS =
 
 1132        getNumBytes(BECount, IntIdxTy, StoreSizeSCEV, CurLoop, 
DL, SE);
 
 1136    if (!Expander.isSafeToExpand(NumBytesS))
 
 1139        Expander.expandCodeFor(NumBytesS, IntIdxTy, Preheader->
getTerminator());
 
 1141      BytesWritten = CI->getZExtValue();
 
 1143  assert(MemsetArg && 
"MemsetArg should have been set");
 
 1147    AATags = AATags.
merge(
Store->getAAMetadata());
 
 1149    AATags = AATags.
extendTo(BytesWritten.value());
 
 1155    NewCall = Builder.CreateMemSet(BasePtr, SplatValue, MemsetArg,
 
 1162    NewCall = Builder.CreateIntrinsic(
 
 1163        Intrinsic::experimental_memset_pattern,
 
 1164        {DestInt8PtrTy, PatternValue->
getType(), IntIdxTy},
 
 1165        {
BasePtr, PatternValue, MemsetArg,
 
 1178    MemoryAccess *NewMemAcc = MSSAU->createMemoryAccessInBB(
 
 1184                    << 
"    from store to: " << *Ev << 
" at: " << *TheStore
 
 1190    R << 
"Transformed loop-strided store in " 
 1192      << 
" function into a call to " 
 1195    if (!Stores.empty())
 
 1197    for (
auto *
I : Stores) {
 
 1198      R << 
ore::NV(
"FromBlock", 
I->getParent()->getName())
 
 1206  for (
auto *
I : Stores) {
 
 1208      MSSAU->removeMemoryAccess(
I, 
true);
 
 1212    MSSAU->getMemorySSA()->verifyMemorySSA();
 
 1214  ExpCleaner.markResultUsed();
 
 1221bool LoopIdiomRecognize::processLoopStoreOfLoopLoad(
StoreInst *
SI,
 
 1222                                                    const SCEV *BECount) {
 
 1223  assert(
SI->isUnordered() && 
"Expected only non-volatile non-ordered stores.");
 
 1225  Value *StorePtr = 
SI->getPointerOperand();
 
 1227  unsigned StoreSize = 
DL->getTypeStoreSize(
SI->getValueOperand()->getType());
 
 1240  return processLoopStoreOfLoopLoad(StorePtr, LoadPtr, StoreSizeSCEV,
 
 1242                                    StoreEv, LoadEv, BECount);
 
 1246class MemmoveVerifier {
 
 1248  explicit MemmoveVerifier(
const Value &LoadBasePtr, 
const Value &StoreBasePtr,
 
 1249                           const DataLayout &
DL)
 
 1251                    LoadBasePtr.stripPointerCasts(), LoadOff, 
DL)),
 
 1253            StoreBasePtr.stripPointerCasts(), StoreOff, 
DL)),
 
 1254        IsSameObject(BP1 == BP2) {}
 
 1256  bool loadAndStoreMayFormMemmove(
unsigned StoreSize, 
bool IsNegStride,
 
 1257                                  const Instruction &TheLoad,
 
 1258                                  bool IsMemCpy)
 const {
 
 1262      if ((!IsNegStride && LoadOff <= StoreOff) ||
 
 1263          (IsNegStride && LoadOff >= StoreOff))
 
 1269          DL.getTypeSizeInBits(TheLoad.
getType()).getFixedValue() / 8;
 
 1270      if (BP1 != BP2 || LoadSize != int64_t(StoreSize))
 
 1272      if ((!IsNegStride && LoadOff < StoreOff + int64_t(StoreSize)) ||
 
 1273          (IsNegStride && LoadOff + LoadSize > StoreOff))
 
 1280  const DataLayout &
DL;
 
 1281  int64_t LoadOff = 0;
 
 1282  int64_t StoreOff = 0;
 
 1287  const bool IsSameObject;
 
 1291bool LoopIdiomRecognize::processLoopStoreOfLoopLoad(
 
 1321  assert(ConstStoreSize && 
"store size is expected to be a constant");
 
 1324  bool IsNegStride = StoreSize == -Stride;
 
 1337  Value *StoreBasePtr = Expander.expandCodeFor(
 
 1338      StrStart, Builder.getPtrTy(StrAS), Preheader->
getTerminator());
 
 1350  IgnoredInsts.
insert(TheStore);
 
 1353  const StringRef InstRemark = IsMemCpy ? 
"memcpy" : 
"load and store";
 
 1355  bool LoopAccessStore =
 
 1357                            StoreSizeSCEV, *
AA, IgnoredInsts);
 
 1358  if (LoopAccessStore) {
 
 1364    IgnoredInsts.
insert(TheLoad);
 
 1366                              BECount, StoreSizeSCEV, *
AA, IgnoredInsts)) {
 
 1370               << 
ore::NV(
"Inst", InstRemark) << 
" in " 
 1372               << 
" function will not be hoisted: " 
 1373               << 
ore::NV(
"Reason", 
"The loop may access store location");
 
 1377    IgnoredInsts.
erase(TheLoad);
 
 1390  Value *LoadBasePtr = Expander.expandCodeFor(LdStart, Builder.getPtrTy(LdAS),
 
 1395  MemmoveVerifier 
Verifier(*LoadBasePtr, *StoreBasePtr, *
DL);
 
 1396  if (IsMemCpy && !
Verifier.IsSameObject)
 
 1397    IgnoredInsts.
erase(TheStore);
 
 1399                            StoreSizeSCEV, *
AA, IgnoredInsts)) {
 
 1402             << 
ore::NV(
"Inst", InstRemark) << 
" in " 
 1404             << 
" function will not be hoisted: " 
 1405             << 
ore::NV(
"Reason", 
"The loop may access load location");
 
 1411  bool UseMemMove = IsMemCpy ? 
Verifier.IsSameObject : LoopAccessStore;
 
 1420    assert((StoreAlign && LoadAlign) &&
 
 1421           "Expect unordered load/store to have align.");
 
 1422    if (*StoreAlign < StoreSize || *LoadAlign < StoreSize)
 
 1429    if (StoreSize > 
TTI->getAtomicMemIntrinsicMaxElementSize())
 
 1434    if (!
Verifier.loadAndStoreMayFormMemmove(StoreSize, IsNegStride, *TheLoad,
 
 1438  if (avoidLIRForMultiBlockLoop())
 
 1443  const SCEV *NumBytesS =
 
 1444      getNumBytes(BECount, IntIdxTy, StoreSizeSCEV, CurLoop, 
DL, SE);
 
 1447      Expander.expandCodeFor(NumBytesS, IntIdxTy, Preheader->
getTerminator());
 
 1451  AATags = AATags.
merge(StoreAATags);
 
 1453    AATags = AATags.
extendTo(CI->getZExtValue());
 
 1463      NewCall = Builder.CreateMemMove(StoreBasePtr, StoreAlign, LoadBasePtr,
 
 1464                                      LoadAlign, NumBytes,
 
 1468          Builder.CreateMemCpy(StoreBasePtr, StoreAlign, LoadBasePtr, LoadAlign,
 
 1469                               NumBytes, 
false, AATags);
 
 1474    NewCall = Builder.CreateElementUnorderedAtomicMemCpy(
 
 1475        StoreBasePtr, *StoreAlign, LoadBasePtr, *LoadAlign, NumBytes, StoreSize,
 
 1481    MemoryAccess *NewMemAcc = MSSAU->createMemoryAccessInBB(
 
 1487                    << 
"    from load ptr=" << *LoadEv << 
" at: " << *TheLoad
 
 1489                    << 
"    from store ptr=" << *StoreEv << 
" at: " << *TheStore
 
 1495           << 
"Formed a call to " 
 1497           << 
"() intrinsic from " << 
ore::NV(
"Inst", InstRemark)
 
 1508    MSSAU->removeMemoryAccess(TheStore, 
true);
 
 1511    MSSAU->getMemorySSA()->verifyMemorySSA();
 
 1516  ExpCleaner.markResultUsed();
 
 1523bool LoopIdiomRecognize::avoidLIRForMultiBlockLoop(
bool IsMemset,
 
 1524                                                   bool IsLoopMemset) {
 
 1525  if (ApplyCodeSizeHeuristics && CurLoop->
getNumBlocks() > 1) {
 
 1526    if (CurLoop->
isOutermost() && (!IsMemset || !IsLoopMemset)) {
 
 1528                        << 
" : LIR " << (IsMemset ? 
"Memset" : 
"Memcpy")
 
 1529                        << 
" avoided: multi-block top-level loop\n");
 
 1552  std::array<Constant *, 256> CRCConstants;
 
 1554            CRCConstants.begin(),
 
 1555            [CRCTy](
const APInt &
E) { return ConstantInt::get(CRCTy, E); });
 
 1577    unsigned NewBTC = (
Info.TripCount / 8) - 1;
 
 1584    Value *ExitLimit = ConstantInt::get(
IV->getType(), NewBTC);
 
 1586    Value *NewExitCond =
 
 1587        Builder.CreateICmp(ExitPred, 
IV, ExitLimit, 
"exit.cond");
 
 1606      Type *OpTy = 
Op->getType();
 
 1610      return LoByte(Builder,
 
 1611                    CRCBW > 8 ? Builder.CreateLShr(
 
 1612                                    Op, ConstantInt::get(OpTy, CRCBW - 8), Name)
 
 1622    PHINode *CRCPhi = Builder.CreatePHI(CRCTy, 2, 
"crc");
 
 1626    Value *CRC = CRCPhi;
 
 1630    Value *Indexer = CRC;
 
 1638      Value *IVBits = Builder.CreateZExtOrTrunc(
 
 1639          Builder.CreateShl(
IV, 3, 
"iv.bits"), DataTy, 
"iv.indexer");
 
 1640      Value *DataIndexer =
 
 1641          Info.ByteOrderSwapped
 
 1642              ? Builder.CreateShl(
Data, IVBits, 
"data.indexer")
 
 1643              : Builder.CreateLShr(
Data, IVBits, 
"data.indexer");
 
 1644      Indexer = Builder.CreateXor(
 
 1646          Builder.CreateZExtOrTrunc(Indexer, DataTy, 
"crc.indexer.cast"),
 
 1647          "crc.data.indexer");
 
 1650    Indexer = 
Info.ByteOrderSwapped ? HiIdx(Builder, Indexer, 
"indexer.hi")
 
 1651                                    : LoByte(Builder, Indexer, 
"indexer.lo");
 
 1654    Indexer = Builder.CreateZExt(
 
 1659    Value *CRCTableGEP =
 
 1660        Builder.CreateInBoundsGEP(CRCTy, GV, Indexer, 
"tbl.ptradd");
 
 1661    Value *CRCTableLd = Builder.CreateLoad(CRCTy, CRCTableGEP, 
"tbl.ld");
 
 1665    Value *CRCNext = CRCTableLd;
 
 1668                            ? Builder.CreateShl(CRC, 8, 
"crc.be.shift")
 
 1669                            : Builder.CreateLShr(CRC, 8, 
"crc.le.shift");
 
 1670      CRCNext = Builder.CreateXor(CRCShift, CRCTableLd, 
"crc.next");
 
 1675    Info.ComputedValue->replaceUsesOutsideBlock(CRCNext,
 
 1688bool LoopIdiomRecognize::runOnNoncountableLoop() {
 
 1691                    << 
"] Noncountable Loop %" 
 1694  return recognizePopcount() || recognizeAndInsertFFS() ||
 
 1695         recognizeShiftUntilBitTest() || recognizeShiftUntilZero() ||
 
 1696         recognizeShiftUntilLessThan() || recognizeAndInsertStrLen();
 
 1706                             bool JmpOnZero = 
false) {
 
 1715  if (!CmpZero || !CmpZero->isZero())
 
 1726    return Cond->getOperand(0);
 
 
 1733class StrlenVerifier {
 
 1735  explicit StrlenVerifier(
const Loop *CurLoop, ScalarEvolution *SE,
 
 1736                          const TargetLibraryInfo *TLI)
 
 1737      : CurLoop(CurLoop), SE(SE), TLI(TLI) {}
 
 1739  bool isValidStrlenIdiom() {
 
 1761    if (!LoopBody || LoopBody->
size() >= 15)
 
 1780    const SCEV *LoadEv = SE->
getSCEV(IncPtr);
 
 1793    if (OpWidth != StepSize * 8)
 
 1795    if (OpWidth != 8 && OpWidth != 16 && OpWidth != 32)
 
 1798      if (OpWidth != WcharSize * 8)
 
 1802    for (Instruction &
I : *LoopBody)
 
 1803      if (
I.mayHaveSideEffects())
 
 1810    for (PHINode &PN : LoopExitBB->
phis()) {
 
 1814      const SCEV *Ev = SE->
getSCEV(&PN);
 
 1824      if (!AddRecEv || !AddRecEv->
isAffine())
 
 1838  const Loop *CurLoop;
 
 1839  ScalarEvolution *SE;
 
 1840  const TargetLibraryInfo *TLI;
 
 1843  ConstantInt *StepSizeCI;
 
 1844  const SCEV *LoadBaseEv;
 
 1909bool LoopIdiomRecognize::recognizeAndInsertStrLen() {
 
 1913  StrlenVerifier 
Verifier(CurLoop, SE, TLI);
 
 1915  if (!
Verifier.isValidStrlenIdiom())
 
 1922  assert(Preheader && LoopBody && LoopExitBB && LoopTerm &&
 
 1923         "Should be verified to be valid by StrlenVerifier");
 
 1938  Builder.SetCurrentDebugLocation(CurLoop->
getStartLoc());
 
 1941  Value *MaterialzedBase = Expander.expandCodeFor(
 
 1943      Builder.GetInsertPoint());
 
 1945  Value *StrLenFunc = 
nullptr;
 
 1947    StrLenFunc = 
emitStrLen(MaterialzedBase, Builder, *
DL, TLI);
 
 1949    StrLenFunc = 
emitWcsLen(MaterialzedBase, Builder, *
DL, TLI);
 
 1951  assert(StrLenFunc && 
"Failed to emit strlen function.");
 
 1970                                       StrlenEv, 
Base->getType())));
 
 1972    Value *MaterializedPHI = Expander.expandCodeFor(NewEv, NewEv->
getType(),
 
 1973                                                    Builder.GetInsertPoint());
 
 1989         "loop body must have a successor that is it self");
 
 1991                                 ? Builder.getFalse()
 
 1992                                 : Builder.getTrue();
 
 1997  LLVM_DEBUG(
dbgs() << 
"  Formed strlen idiom: " << *StrLenFunc << 
"\n");
 
 2001           << 
"Transformed " << StrLenFunc->
getName() << 
" loop idiom";
 
 2029    return Cond->getOperand(0);
 
 
 2040  if (PhiX && PhiX->getParent() == LoopEntry &&
 
 2041      (PhiX->getOperand(0) == DefX || PhiX->
getOperand(1) == DefX))
 
 
 2107  if (DefX->
getOpcode() != Instruction::LShr)
 
 2110  IntrinID = Intrinsic::ctlz;
 
 2112  if (!Shft || !Shft->
isOne())
 
 2126    if (Inst.
getOpcode() != Instruction::Add)
 
 
 2178  Value *VarX1, *VarX0;
 
 2181  DefX2 = CountInst = 
nullptr;
 
 2182  VarX1 = VarX0 = 
nullptr;
 
 2183  PhiX = CountPhi = 
nullptr;
 
 2197    if (!DefX2 || DefX2->
getOpcode() != Instruction::And)
 
 2208    if (!SubOneOp || SubOneOp->
getOperand(0) != VarX1)
 
 2214          (SubOneOp->
getOpcode() == Instruction::Add &&
 
 2227    CountInst = 
nullptr;
 
 2230      if (Inst.
getOpcode() != Instruction::Add)
 
 2234      if (!Inc || !Inc->
isOne())
 
 2242      bool LiveOutLoop = 
false;
 
 2269    CntInst = CountInst;
 
 
 2309  Value *VarX = 
nullptr;
 
 2324  if (!DefX || !DefX->
isShift())
 
 2326  IntrinID = DefX->
getOpcode() == Instruction::Shl ? Intrinsic::cttz :
 
 2329  if (!Shft || !Shft->
isOne())
 
 2354    if (Inst.
getOpcode() != Instruction::Add)
 
 
 2377bool LoopIdiomRecognize::isProfitableToInsertFFS(
Intrinsic::ID IntrinID,
 
 2378                                                 Value *InitX, 
bool ZeroCheck,
 
 2379                                                 size_t CanonicalSize) {
 
 2386      std::distance(InstWithoutDebugIt.begin(), InstWithoutDebugIt.end());
 
 2400bool LoopIdiomRecognize::insertFFSIfProfitable(
Intrinsic::ID IntrinID,
 
 2404  bool IsCntPhiUsedOutsideLoop = 
false;
 
 2407      IsCntPhiUsedOutsideLoop = 
true;
 
 2410  bool IsCntInstUsedOutsideLoop = 
false;
 
 2413      IsCntInstUsedOutsideLoop = 
true;
 
 2418  if (IsCntInstUsedOutsideLoop && IsCntPhiUsedOutsideLoop)
 
 2424  bool ZeroCheck = 
false;
 
 2433  if (!IsCntPhiUsedOutsideLoop) {
 
 2452  size_t IdiomCanonicalSize = 6;
 
 2453  if (!isProfitableToInsertFFS(IntrinID, InitX, ZeroCheck, IdiomCanonicalSize))
 
 2456  transformLoopToCountable(IntrinID, PH, CntInst, CntPhi, InitX, DefX,
 
 2458                           IsCntPhiUsedOutsideLoop);
 
 2465bool LoopIdiomRecognize::recognizeAndInsertFFS() {
 
 2480  return insertFFSIfProfitable(IntrinID, InitX, DefX, CntPhi, CntInst);
 
 2483bool LoopIdiomRecognize::recognizeShiftUntilLessThan() {
 
 2494  APInt LoopThreshold;
 
 2496                                     CntPhi, DefX, LoopThreshold))
 
 2499  if (LoopThreshold == 2) {
 
 2501    return insertFFSIfProfitable(IntrinID, InitX, DefX, CntPhi, CntInst);
 
 2505  if (LoopThreshold != 4)
 
 2523  APInt PreLoopThreshold;
 
 2525      PreLoopThreshold != 2)
 
 2528  bool ZeroCheck = 
true;
 
 2537  size_t IdiomCanonicalSize = 6;
 
 2538  if (!isProfitableToInsertFFS(IntrinID, InitX, ZeroCheck, IdiomCanonicalSize))
 
 2542  transformLoopToCountable(IntrinID, PH, CntInst, CntPhi, InitX, DefX,
 
 2553bool LoopIdiomRecognize::recognizePopcount() {
 
 2567  if (LoopBody->
size() >= 20) {
 
 2586  if (!PreCondBI || PreCondBI->isUnconditional())
 
 2595  transformLoopToPopcount(PreCondBB, CntInst, CntPhi, Val);
 
 2653void LoopIdiomRecognize::transformLoopToCountable(
 
 2656    bool ZeroCheck, 
bool IsCntPhiUsedOutsideLoop, 
bool InsertSub) {
 
 2661  Builder.SetCurrentDebugLocation(
DL);
 
 2670  if (IsCntPhiUsedOutsideLoop) {
 
 2671    if (DefX->
getOpcode() == Instruction::AShr)
 
 2672      InitXNext = Builder.CreateAShr(InitX, 1);
 
 2673    else if (DefX->
getOpcode() == Instruction::LShr)
 
 2674      InitXNext = Builder.CreateLShr(InitX, 1);
 
 2675    else if (DefX->
getOpcode() == Instruction::Shl) 
 
 2676      InitXNext = Builder.CreateShl(InitX, 1);
 
 2684  Count = Builder.CreateSub(
 
 2687    Count = Builder.CreateSub(
Count, ConstantInt::get(CountTy, 1));
 
 2689  if (IsCntPhiUsedOutsideLoop)
 
 2690    Count = Builder.CreateAdd(
Count, ConstantInt::get(CountTy, 1));
 
 2692  NewCount = Builder.CreateZExtOrTrunc(NewCount, CntInst->
getType());
 
 2699    if (!InitConst || !InitConst->
isZero())
 
 2700      NewCount = Builder.CreateAdd(NewCount, CntInitVal);
 
 2704    NewCount = Builder.CreateSub(CntInitVal, NewCount);
 
 2722  Builder.SetInsertPoint(LbCond);
 
 2724      TcPhi, ConstantInt::get(CountTy, 1), 
"tcdec", 
false, 
true));
 
 2733  LbCond->
setOperand(1, ConstantInt::get(CountTy, 0));
 
 2737  if (IsCntPhiUsedOutsideLoop)
 
 2747void LoopIdiomRecognize::transformLoopToPopcount(
BasicBlock *PreCondBB,
 
 2760  Value *PopCnt, *PopCntZext, *NewCount, *TripCnt;
 
 2763    NewCount = PopCntZext =
 
 2766    if (NewCount != PopCnt)
 
 2775    if (!InitConst || !InitConst->
isZero()) {
 
 2776      NewCount = Builder.CreateAdd(NewCount, CntInitVal);
 
 2788    Value *Opnd0 = PopCntZext;
 
 2789    Value *Opnd1 = ConstantInt::get(PopCntZext->
getType(), 0);
 
 2794        Builder.CreateICmp(PreCond->
getPredicate(), Opnd0, Opnd1));
 
 2795    PreCondBr->setCondition(NewPreCond);
 
 2829    Builder.SetInsertPoint(LbCond);
 
 2831        Builder.CreateSub(TcPhi, ConstantInt::get(Ty, 1),
 
 2832                          "tcdec", 
false, 
true));
 
 2841    LbCond->
setOperand(1, ConstantInt::get(Ty, 0));
 
 2862  template <
typename ITy> 
bool match(ITy *V)
 const {
 
 2863    return L->isLoopInvariant(V) && 
SubPattern.match(V);
 
 
 
 2868template <
typename Ty>
 
 2899             " Performing shift-until-bittest idiom detection.\n");
 
 2909  assert(LoopPreheaderBB && 
"There is always a loop preheader.");
 
 2916  Value *CmpLHS, *CmpRHS;
 
 2927  auto MatchVariableBitMask = [&]() {
 
 2937  auto MatchDecomposableConstantBitMask = [&]() {
 
 2939        CmpLHS, CmpRHS, Pred, 
true,
 
 2941    if (Res && Res->Mask.isPowerOf2()) {
 
 2945      BitMask = ConstantInt::get(CurrX->
getType(), Res->Mask);
 
 2946      BitPos = ConstantInt::get(CurrX->
getType(), Res->Mask.logBase2());
 
 2952  if (!MatchVariableBitMask() && !MatchDecomposableConstantBitMask()) {
 
 2959  if (!CurrXPN || CurrXPN->getParent() != LoopHeaderBB) {
 
 2964  BaseX = CurrXPN->getIncomingValueForBlock(LoopPreheaderBB);
 
 2969         "Expected BaseX to be available in the preheader!");
 
 2980         "Should only get equality predicates here.");
 
 2990  if (TrueBB != LoopHeaderBB) {
 
 
 3049bool LoopIdiomRecognize::recognizeShiftUntilBitTest() {
 
 3050  bool MadeChange = 
false;
 
 3052  Value *
X, *BitMask, *BitPos, *XCurr;
 
 3057               " shift-until-bittest idiom detection failed.\n");
 
 3067  assert(LoopPreheaderBB && 
"There is always a loop preheader.");
 
 3070  assert(SuccessorBB && 
"There is only a single successor.");
 
 3076  Type *Ty = 
X->getType();
 
 3090               " Intrinsic is too costly, not beneficial\n");
 
 3093  if (
TTI->getArithmeticInstrCost(Instruction::Shl, Ty, 
CostKind) >
 
 3105    std::optional<BasicBlock::iterator> InsertPt = std::nullopt;
 
 3107      InsertPt = BitPosI->getInsertionPointAfterDef();
 
 3115      return U.getUser() != BitPosFrozen;
 
 3117    BitPos = BitPosFrozen;
 
 3123                                        BitPos->
getName() + 
".lowbitmask");
 
 3125      Builder.CreateOr(LowBitMask, BitMask, BitPos->
getName() + 
".mask");
 
 3126  Value *XMasked = Builder.CreateAnd(
X, Mask, 
X->getName() + 
".masked");
 
 3127  CallInst *XMaskedNumLeadingZeros = Builder.CreateIntrinsic(
 
 3128      IntrID, Ty, {XMasked, Builder.getTrue()},
 
 3129      nullptr, XMasked->
getName() + 
".numleadingzeros");
 
 3130  Value *XMaskedNumActiveBits = Builder.CreateSub(
 
 3132      XMasked->
getName() + 
".numactivebits", 
true,
 
 3134  Value *XMaskedLeadingOnePos =
 
 3136                        XMasked->
getName() + 
".leadingonepos", 
false,
 
 3139  Value *LoopBackedgeTakenCount = Builder.CreateSub(
 
 3140      BitPos, XMaskedLeadingOnePos, CurLoop->
getName() + 
".backedgetakencount",
 
 3144  Value *LoopTripCount =
 
 3145      Builder.CreateAdd(LoopBackedgeTakenCount, ConstantInt::get(Ty, 1),
 
 3146                        CurLoop->
getName() + 
".tripcount", 
true,
 
 3153  Value *NewX = Builder.CreateShl(
X, LoopBackedgeTakenCount);
 
 3156    I->copyIRFlags(XNext, 
true);
 
 3168    NewXNext = Builder.CreateShl(
X, LoopTripCount);
 
 3173    NewXNext = Builder.CreateShl(NewX, ConstantInt::get(Ty, 1));
 
 3178    I->copyIRFlags(XNext, 
true);
 
 3189  Builder.SetInsertPoint(LoopHeaderBB, LoopHeaderBB->
begin());
 
 3190  auto *
IV = Builder.CreatePHI(Ty, 2, CurLoop->
getName() + 
".iv");
 
 3196      Builder.CreateAdd(
IV, ConstantInt::get(Ty, 1), 
IV->getName() + 
".next",
 
 3197                        true, Bitwidth != 2);
 
 3200  auto *IVCheck = Builder.CreateICmpEQ(IVNext, LoopTripCount,
 
 3201                                       CurLoop->
getName() + 
".ivcheck");
 
 3202  Builder.CreateCondBr(IVCheck, SuccessorBB, LoopHeaderBB);
 
 3206  IV->addIncoming(ConstantInt::get(Ty, 0), LoopPreheaderBB);
 
 3207  IV->addIncoming(IVNext, LoopHeaderBB);
 
 3218  ++NumShiftUntilBitTest;
 
 3254                                      const SCEV *&ExtraOffsetExpr,
 
 3255                                      bool &InvertedCond) {
 
 3257             " Performing shift-until-zero idiom detection.\n");
 
 3270  assert(LoopPreheaderBB && 
"There is always a loop preheader.");
 
 3281      !
match(ValShiftedIsZero,
 
 3295  IntrinID = ValShifted->
getOpcode() == Instruction::Shl ? Intrinsic::cttz
 
 3304  else if (
match(NBits,
 
 3308    ExtraOffsetExpr = SE->
getSCEV(ExtraOffset);
 
 3316  if (!IVPN || IVPN->getParent() != LoopHeaderBB) {
 
 3321  Start = IVPN->getIncomingValueForBlock(LoopPreheaderBB);
 
 3332         "Should only get equality predicates here.");
 
 3343  if (FalseBB != LoopHeaderBB) {
 
 3354  if (ValShifted->
getOpcode() == Instruction::AShr &&
 
 
 3418bool LoopIdiomRecognize::recognizeShiftUntilZero() {
 
 3419  bool MadeChange = 
false;
 
 3425  const SCEV *ExtraOffsetExpr;
 
 3428                                 Start, Val, ExtraOffsetExpr, InvertedCond)) {
 
 3430               " shift-until-zero idiom detection failed.\n");
 
 3440  assert(LoopPreheaderBB && 
"There is always a loop preheader.");
 
 3443  assert(SuccessorBB && 
"There is only a single successor.");
 
 3446  Builder.SetCurrentDebugLocation(
IV->getDebugLoc());
 
 3462               " Intrinsic is too costly, not beneficial\n");
 
 3469  bool OffsetIsZero = ExtraOffsetExpr->
isZero();
 
 3473  CallInst *ValNumLeadingZeros = Builder.CreateIntrinsic(
 
 3474      IntrID, Ty, {Val, Builder.getFalse()},
 
 3475      nullptr, Val->
getName() + 
".numleadingzeros");
 
 3476  Value *ValNumActiveBits = Builder.CreateSub(
 
 3478      Val->
getName() + 
".numactivebits", 
true,
 
 3482  Expander.setInsertPoint(&*Builder.GetInsertPoint());
 
 3483  Value *ExtraOffset = Expander.expandCodeFor(ExtraOffsetExpr);
 
 3485  Value *ValNumActiveBitsOffset = Builder.CreateAdd(
 
 3486      ValNumActiveBits, ExtraOffset, ValNumActiveBits->
getName() + 
".offset",
 
 3487      OffsetIsZero, 
true);
 
 3488  Value *IVFinal = Builder.CreateIntrinsic(Intrinsic::smax, {Ty},
 
 3489                                           {ValNumActiveBitsOffset, 
Start},
 
 3490                                           nullptr, 
"iv.final");
 
 3493      IVFinal, Start, CurLoop->
getName() + 
".backedgetakencount",
 
 3494      OffsetIsZero, 
true));
 
 3498  Value *LoopTripCount =
 
 3499      Builder.CreateAdd(LoopBackedgeTakenCount, ConstantInt::get(Ty, 1),
 
 3500                        CurLoop->
getName() + 
".tripcount", 
true,
 
 3506  IV->replaceUsesOutsideBlock(IVFinal, LoopHeaderBB);
 
 3511  Builder.SetInsertPoint(LoopHeaderBB, LoopHeaderBB->
begin());
 
 3512  auto *CIV = Builder.CreatePHI(Ty, 2, CurLoop->
getName() + 
".iv");
 
 3517      Builder.CreateAdd(CIV, ConstantInt::get(Ty, 1), CIV->getName() + 
".next",
 
 3518                        true, Bitwidth != 2);
 
 3521  auto *CIVCheck = Builder.CreateICmpEQ(CIVNext, LoopTripCount,
 
 3522                                        CurLoop->
getName() + 
".ivcheck");
 
 3523  auto *NewIVCheck = CIVCheck;
 
 3525    NewIVCheck = Builder.CreateNot(CIVCheck);
 
 3526    NewIVCheck->takeName(ValShiftedIsZero);
 
 3530  auto *IVDePHId = Builder.CreateAdd(CIV, Start, 
"", 
false,
 
 3532  IVDePHId->takeName(
IV);
 
 3536  Builder.CreateCondBr(CIVCheck, SuccessorBB, LoopHeaderBB);
 
 3540  CIV->addIncoming(ConstantInt::get(Ty, 0), LoopPreheaderBB);
 
 3541  CIV->addIncoming(CIVNext, LoopHeaderBB);
 
 3549  IV->replaceAllUsesWith(IVDePHId);
 
 3550  IV->eraseFromParent();
 
 3559  ++NumShiftUntilZero;
 
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
 
This file implements a class to represent arbitrary precision integral constant values and operations...
 
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
 
static const Function * getParent(const Value *V)
 
static GCRegistry::Add< CoreCLRGC > E("coreclr", "CoreCLR-compatible GC")
 
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
 
Analysis containing CSE Info
 
This file contains the declarations for the subclasses of Constant, which represent the different fla...
 
static cl::opt< OutputCostKind > CostKind("cost-kind", cl::desc("Target cost kind"), cl::init(OutputCostKind::RecipThroughput), cl::values(clEnumValN(OutputCostKind::RecipThroughput, "throughput", "Reciprocal throughput"), clEnumValN(OutputCostKind::Latency, "latency", "Instruction latency"), clEnumValN(OutputCostKind::CodeSize, "code-size", "Code size"), clEnumValN(OutputCostKind::SizeAndLatency, "size-latency", "Code size and latency"), clEnumValN(OutputCostKind::All, "all", "Print all cost kinds")))
 
This file defines the DenseMap class.
 
static const HTTPClientCleanup Cleanup
 
static bool mayLoopAccessLocation(Value *Ptr, ModRefInfo Access, Loop *L, const SCEV *BECount, unsigned StoreSize, AliasAnalysis &AA, SmallPtrSetImpl< Instruction * > &Ignored)
mayLoopAccessLocation - Return true if the specified loop might access the specified pointer location...
 
Module.h This file contains the declarations for the Module class.
 
This header defines various interfaces for pass management in LLVM.
 
This file defines an InstructionCost class that is used when calculating the cost of an instruction,...
 
const AbstractManglingParser< Derived, Alloc >::OperatorInfo AbstractManglingParser< Derived, Alloc >::Ops[]
 
static Value * matchCondition(BranchInst *BI, BasicBlock *LoopEntry, bool JmpOnZero=false)
Check if the given conditional branch is based on the comparison between a variable and zero,...
 
static PHINode * getRecurrenceVar(Value *VarX, Instruction *DefX, BasicBlock *LoopEntry)
 
static cl::opt< bool, true > DisableLIRPMemset("disable-" DEBUG_TYPE "-memset", cl::desc("Proceed with loop idiom recognize pass, but do " "not convert loop(s) to memset."), cl::location(DisableLIRP::Memset), cl::init(false), cl::ReallyHidden)
 
static cl::opt< bool > ForceMemsetPatternIntrinsic("loop-idiom-force-memset-pattern-intrinsic", cl::desc("Use memset.pattern intrinsic whenever possible"), cl::init(false), cl::Hidden)
 
static CallInst * createFFSIntrinsic(IRBuilder<> &IRBuilder, Value *Val, const DebugLoc &DL, bool ZeroCheck, Intrinsic::ID IID)
 
static cl::opt< bool, true > EnableLIRPWcslen("disable-loop-idiom-wcslen", cl::desc("Proceed with loop idiom recognize pass, " "enable conversion of loop(s) to wcslen."), cl::location(DisableLIRP::Wcslen), cl::init(false), cl::ReallyHidden)
 
static bool detectShiftUntilLessThanIdiom(Loop *CurLoop, const DataLayout &DL, Intrinsic::ID &IntrinID, Value *&InitX, Instruction *&CntInst, PHINode *&CntPhi, Instruction *&DefX, APInt &Threshold)
Return true if the idiom is detected in the loop.
 
static bool detectShiftUntilBitTestIdiom(Loop *CurLoop, Value *&BaseX, Value *&BitMask, Value *&BitPos, Value *&CurrX, Instruction *&NextX)
Return true if the idiom is detected in the loop.
 
static bool detectPopcountIdiom(Loop *CurLoop, BasicBlock *PreCondBB, Instruction *&CntInst, PHINode *&CntPhi, Value *&Var)
Return true iff the idiom is detected in the loop.
 
static Constant * getMemSetPatternValue(Value *V, const DataLayout *DL)
getMemSetPatternValue - If a strided store of the specified value is safe to turn into a memset....
 
static cl::opt< bool, true > DisableLIRPMemcpy("disable-" DEBUG_TYPE "-memcpy", cl::desc("Proceed with loop idiom recognize pass, but do " "not convert loop(s) to memcpy."), cl::location(DisableLIRP::Memcpy), cl::init(false), cl::ReallyHidden)
 
static CallInst * createPopcntIntrinsic(IRBuilder<> &IRBuilder, Value *Val, const DebugLoc &DL)
 
static const SCEV * getNumBytes(const SCEV *BECount, Type *IntPtr, const SCEV *StoreSizeSCEV, Loop *CurLoop, const DataLayout *DL, ScalarEvolution *SE)
Compute the number of bytes as a SCEV from the backedge taken count.
 
static bool detectShiftUntilZeroIdiom(Loop *CurLoop, const DataLayout &DL, Intrinsic::ID &IntrinID, Value *&InitX, Instruction *&CntInst, PHINode *&CntPhi, Instruction *&DefX)
Return true if the idiom is detected in the loop.
 
static cl::opt< bool, true > DisableLIRPStrlen("disable-loop-idiom-strlen", cl::desc("Proceed with loop idiom recognize pass, but do " "not convert loop(s) to strlen."), cl::location(DisableLIRP::Strlen), cl::init(false), cl::ReallyHidden)
 
static const SCEV * getStartForNegStride(const SCEV *Start, const SCEV *BECount, Type *IntPtr, const SCEV *StoreSizeSCEV, ScalarEvolution *SE)
 
static APInt getStoreStride(const SCEVAddRecExpr *StoreEv)
 
static Value * matchShiftULTCondition(BranchInst *BI, BasicBlock *LoopEntry, APInt &Threshold)
Check if the given conditional branch is based on an unsigned less-than comparison between a variable...
 
match_LoopInvariant< Ty > m_LoopInvariant(const Ty &M, const Loop *L)
Matches if the value is loop-invariant.
 
static cl::opt< bool, true > DisableLIRPAll("disable-" DEBUG_TYPE "-all", cl::desc("Options to disable Loop Idiom Recognize Pass."), cl::location(DisableLIRP::All), cl::init(false), cl::ReallyHidden)
 
static void deleteDeadInstruction(Instruction *I)
 
static cl::opt< bool, true > DisableLIRPHashRecognize("disable-" DEBUG_TYPE "-hashrecognize", cl::desc("Proceed with loop idiom recognize pass, " "but do not optimize CRC loops."), cl::location(DisableLIRP::HashRecognize), cl::init(false), cl::ReallyHidden)
 
static cl::opt< bool > UseLIRCodeSizeHeurs("use-lir-code-size-heurs", cl::desc("Use loop idiom recognition code size heuristics when compiling " "with -Os/-Oz"), cl::init(true), cl::Hidden)
 
static DebugLoc getDebugLoc(MachineBasicBlock::instr_iterator FirstMI, MachineBasicBlock::instr_iterator LastMI)
Return the first found DebugLoc that has a DILocation, given a range of instructions.
 
This file implements a map that provides insertion order iteration.
 
This file provides utility analysis objects describing memory locations.
 
This file exposes an interface to building/using memory SSA to walk memory instructions using a use/d...
 
Contains a collection of routines for determining if a given instruction is guaranteed to execute if ...
 
const SmallVectorImpl< MachineOperand > & Cond
 
static bool isSimple(Instruction *I)
 
verify safepoint Safepoint IR Verifier
 
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)
 
static TableGen::Emitter::OptClass< SkeletonEmitter > X("gen-skeleton-class", "Generate example skeleton class")
 
static SymbolRef::Type getType(const Symbol *Sym)
 
static const uint32_t IV[8]
 
Class for arbitrary precision integers.
 
std::optional< uint64_t > tryZExtValue() const
Get zero extended value if possible.
 
uint64_t getZExtValue() const
Get zero extended value.
 
unsigned getBitWidth() const
Return the number of bits in the APInt.
 
int64_t getSExtValue() const
Get sign extended value.
 
static LLVM_ABI ArrayType * get(Type *ElementType, uint64_t NumElements)
This static method is the primary way to construct an ArrayType.
 
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 Function * getParent() const
Return the enclosing method, or null if none.
 
LLVM_ABI iterator_range< filter_iterator< BasicBlock::const_iterator, std::function< bool(const Instruction &)> > > instructionsWithoutDebug(bool SkipPseudoOp=true) const
Return a const iterator range over the instructions in the block, skipping any debug instructions.
 
LLVM_ABI InstListType::const_iterator getFirstNonPHIIt() const
Returns an iterator to the first instruction in this block that is not a PHINode instruction.
 
LLVM_ABI const BasicBlock * getSinglePredecessor() const
Return the predecessor of this block if it has a single predecessor block.
 
const Instruction & front() const
 
InstListType::iterator iterator
Instruction iterators...
 
LLVM_ABI const_iterator getFirstNonPHIOrDbgOrAlloca() const
Returns an iterator to the first instruction in this block that is not a PHINode, a debug intrinsic,...
 
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...
 
LLVM_ABI const Module * getModule() const
Return the module owning the function this basic block belongs to, or nullptr if the function does no...
 
BinaryOps getOpcode() const
 
Conditional or Unconditional Branch instruction.
 
void setCondition(Value *V)
 
bool isConditional() const
 
unsigned getNumSuccessors() const
 
BasicBlock * getSuccessor(unsigned i) const
 
Value * getCondition() const
 
Function * getCalledFunction() const
Returns the function called, or null if this is an indirect function invocation or the function signa...
 
This class represents a function call, abstracting a target machine's calling convention.
 
void setPredicate(Predicate P)
Set the predicate for this instruction to the specified value.
 
Predicate
This enumeration lists the possible predicates for CmpInst subclasses.
 
@ ICMP_SLE
signed less or equal
 
@ ICMP_UGT
unsigned greater than
 
@ ICMP_ULT
unsigned less than
 
Predicate getInversePredicate() const
For example, EQ -> NE, UGT -> ULE, SLT -> SGE, OEQ -> UNE, UGT -> OLE, OLT -> UGE,...
 
Predicate getPredicate() const
Return the predicate for this instruction.
 
An abstraction over a floating-point predicate, and a pack of an integer predicate with samesign info...
 
static LLVM_ABI Constant * get(ArrayType *T, ArrayRef< Constant * > V)
 
This is the shared class of boolean and integer constants.
 
bool isMinusOne() const
This function will return true iff every bit in this constant is set to true.
 
bool isOne() const
This is just a convenience method to make client code smaller for a common case.
 
bool isZero() const
This is just a convenience method to make client code smaller for a common code.
 
static LLVM_ABI ConstantInt * getFalse(LLVMContext &Context)
 
uint64_t getZExtValue() const
Return the constant as a 64-bit unsigned integer value after it has been zero extended as appropriate...
 
const APInt & getValue() const
Return the constant as an APInt value reference.
 
static LLVM_ABI ConstantInt * getBool(LLVMContext &Context, bool V)
 
This is an important base class in LLVM.
 
static LLVM_ABI Constant * getAllOnesValue(Type *Ty)
 
A parsed version of the target data layout string in and methods for querying it.
 
LLVM_ABI IntegerType * getIndexType(LLVMContext &C, unsigned AddressSpace) const
Returns the type of a GEP index in AddressSpace.
 
Concrete subclass of DominatorTreeBase that is used to compute a normal dominator tree.
 
LLVM_ABI bool dominates(const BasicBlock *BB, const Use &U) const
Return true if the (end of the) basic block BB dominates the use U.
 
This class represents a freeze function that returns random concrete value if an operand is either a ...
 
PointerType * getType() const
Global values are always pointers.
 
@ PrivateLinkage
Like Internal, but omit from symbol table.
 
static CRCTable genSarwateTable(const APInt &GenPoly, bool ByteOrderSwapped)
Generate a lookup table of 256 entries by interleaving the generating polynomial.
 
This instruction compares its operands according to the predicate given to the constructor.
 
bool isEquality() const
Return true if this predicate is either EQ or NE.
 
static bool isEquality(Predicate P)
Return true if this predicate is either EQ or NE.
 
Common base class shared among various IRBuilders.
 
ConstantInt * getInt1(bool V)
Get a constant value representing either true or false.
 
Value * CreateZExtOrTrunc(Value *V, Type *DestTy, const Twine &Name="")
Create a ZExt or Trunc from the integer value V to DestTy.
 
LLVM_ABI CallInst * CreateIntrinsic(Intrinsic::ID ID, ArrayRef< Type * > Types, ArrayRef< Value * > Args, FMFSource FMFSource={}, const Twine &Name="")
Create a call to intrinsic ID with Args, mangled using Types.
 
This provides a uniform API for creating instructions and inserting them into a basic block: either a...
 
LLVM_ABI bool hasNoUnsignedWrap() const LLVM_READONLY
Determine whether the no unsigned wrap flag is set.
 
LLVM_ABI bool hasNoSignedWrap() const LLVM_READONLY
Determine whether the no signed wrap flag is set.
 
const DebugLoc & getDebugLoc() const
Return the debug location for this node as a DebugLoc.
 
LLVM_ABI const Module * getModule() const
Return the module owning the function this instruction belongs to or nullptr it the function does not...
 
LLVM_ABI void setAAMetadata(const AAMDNodes &N)
Sets the AA metadata on this instruction from the AAMDNodes structure.
 
LLVM_ABI bool isAtomic() const LLVM_READONLY
Return true if this instruction has an AtomicOrdering of unordered or higher.
 
LLVM_ABI void insertBefore(InstListType::iterator InsertPos)
Insert an unlinked instruction into a basic block immediately before the specified position.
 
LLVM_ABI InstListType::iterator eraseFromParent()
This method unlinks 'this' from the containing basic block and deletes it.
 
LLVM_ABI const Function * getFunction() const
Return the function this instruction belongs to.
 
LLVM_ABI AAMDNodes getAAMetadata() const
Returns the AA metadata for this instruction.
 
unsigned getOpcode() const
Returns a member of one of the enums like Instruction::Add.
 
void setDebugLoc(DebugLoc Loc)
Set the debug location information for this instruction.
 
This class provides an interface for updating the loop pass manager based on mutations to the loop ne...
 
An instruction for reading from memory.
 
unsigned getPointerAddressSpace() const
Returns the address space of the pointer operand.
 
Value * getPointerOperand()
 
bool isVolatile() const
Return true if this is a load from a volatile memory location.
 
Align getAlign() const
Return the alignment of the access that is being performed.
 
static LocationSize precise(uint64_t Value)
 
static constexpr LocationSize afterPointer()
Any location after the base pointer (but still within the underlying object).
 
bool contains(const LoopT *L) const
Return true if the specified loop is contained within in this loop.
 
bool isOutermost() const
Return true if the loop does not have a parent (natural) loop.
 
BlockT * getLoopLatch() const
If there is a single latch block for this loop, return it.
 
unsigned getNumBlocks() const
Get the number of blocks in this loop in constant time.
 
unsigned getNumBackEdges() const
Calculate the number of back edges to the loop header.
 
BlockT * getHeader() const
 
BlockT * getExitBlock() const
If getExitBlocks would return exactly one block, return that block.
 
BlockT * getLoopPreheader() const
If there is a preheader for this loop, return it.
 
ArrayRef< BlockT * > getBlocks() const
Get a list of the basic blocks which make up this loop.
 
void getUniqueExitBlocks(SmallVectorImpl< BlockT * > &ExitBlocks) const
Return all unique successor blocks of this loop.
 
block_iterator block_begin() const
 
BlockT * getUniqueExitBlock() const
If getUniqueExitBlocks would return exactly one block, return that block.
 
PreservedAnalyses run(Loop &L, LoopAnalysisManager &AM, LoopStandardAnalysisResults &AR, LPMUpdater &U)
 
LoopT * getLoopFor(const BlockT *BB) const
Return the inner most loop that BB lives in.
 
Represents a single loop in the control flow graph.
 
DebugLoc getStartLoc() const
Return the debug location of the start of this loop.
 
bool isLoopInvariant(const Value *V) const
Return true if the specified value is loop invariant.
 
ICmpInst * getLatchCmpInst() const
Get the latch condition instruction.
 
StringRef getName() const
 
PHINode * getCanonicalInductionVariable() const
Check to see if the loop has a canonical induction variable: an integer recurrence that starts at 0 a...
 
This class wraps the llvm.memcpy intrinsic.
 
Value * getLength() const
 
Value * getDest() const
This is just like getRawDest, but it strips off any cast instructions (including addrspacecast) that ...
 
MaybeAlign getDestAlign() const
 
bool isForceInlined() const
 
This class wraps the llvm.memset and llvm.memset.inline intrinsics.
 
MaybeAlign getSourceAlign() const
 
Value * getSource() const
This is just like getRawSource, but it strips off any cast instructions that feed it,...
 
Representation for a specific memory location.
 
An analysis that produces MemorySSA for a function.
 
Encapsulates MemorySSA, including all data associated with memory accesses.
 
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.
 
Value * getIncomingValueForBlock(const BasicBlock *BB) const
 
Value * getIncomingValue(unsigned i) const
Return incoming value number x.
 
int getBasicBlockIndex(const BasicBlock *BB) const
Return the first index of the specified basic block in the value list for this PHI.
 
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 LLVM_ABI PoisonValue * get(Type *T)
Static factory methods - Return an 'poison' object of the specified type.
 
A set of analyses that are preserved following a run of a transformation pass.
 
static PreservedAnalyses all()
Construct a special preserved set that preserves all passes.
 
This node represents a polynomial recurrence on the trip count of the specified loop.
 
const SCEV * getStart() const
 
const SCEV * getStepRecurrence(ScalarEvolution &SE) const
Constructs and returns the recurrence indicating how much this expression steps by.
 
bool isAffine() const
Return true if this represents an expression A + B*x where A and B are loop invariant values.
 
This class represents a constant integer value.
 
ConstantInt * getValue() const
 
const APInt & getAPInt() const
 
Helper to remove instructions inserted during SCEV expansion, unless they are marked as used.
 
This class uses information about analyze scalars to rewrite expressions in canonical form.
 
const SCEV * getOperand(unsigned i) const
 
This class represents an analyzed expression in the program.
 
LLVM_ABI bool isOne() const
Return true if the expression is a constant one.
 
LLVM_ABI bool isZero() const
Return true if the expression is a constant zero.
 
LLVM_ABI bool isNonConstantNegative() const
Return true if the specified scev is negated, but not a constant.
 
LLVM_ABI Type * getType() const
Return the LLVM type of this SCEV expression.
 
The main scalar evolution driver.
 
const DataLayout & getDataLayout() const
Return the DataLayout associated with the module this SCEV instance is operating on.
 
LLVM_ABI bool isKnownNonNegative(const SCEV *S)
Test if the given expression is known to be non-negative.
 
LLVM_ABI const SCEV * getNegativeSCEV(const SCEV *V, SCEV::NoWrapFlags Flags=SCEV::FlagAnyWrap)
Return the SCEV object corresponding to -V.
 
LLVM_ABI const SCEV * getBackedgeTakenCount(const Loop *L, ExitCountKind Kind=Exact)
If the specified loop has a predictable backedge-taken count, return it, otherwise return a SCEVCould...
 
const SCEV * getZero(Type *Ty)
Return a SCEV for the constant 0 of a specific type.
 
LLVM_ABI const SCEV * getConstant(ConstantInt *V)
 
LLVM_ABI const SCEV * getSCEV(Value *V)
Return a SCEV expression for the full generality of the specified expression.
 
LLVM_ABI const SCEV * getTripCountFromExitCount(const SCEV *ExitCount)
A version of getTripCountFromExitCount below which always picks an evaluation type which can not resu...
 
LLVM_ABI void forgetLoop(const Loop *L)
This method should be called by the client when it has changed a loop in a way that may effect Scalar...
 
LLVM_ABI bool isLoopInvariant(const SCEV *S, const Loop *L)
Return true if the value of the given SCEV is unchanging in the specified loop.
 
LLVM_ABI bool isSCEVable(Type *Ty) const
Test if values of the given type are analyzable within the SCEV framework.
 
LLVM_ABI const SCEV * getMinusSCEV(const SCEV *LHS, const SCEV *RHS, SCEV::NoWrapFlags Flags=SCEV::FlagAnyWrap, unsigned Depth=0)
Return LHS-RHS.
 
LLVM_ABI bool hasLoopInvariantBackedgeTakenCount(const Loop *L)
Return true if the specified loop has an analyzable loop-invariant backedge-taken count.
 
LLVM_ABI const SCEV * applyLoopGuards(const SCEV *Expr, const Loop *L)
Try to apply information from loop guards for L to Expr.
 
LLVM_ABI const SCEV * getMulExpr(SmallVectorImpl< const SCEV * > &Ops, SCEV::NoWrapFlags Flags=SCEV::FlagAnyWrap, unsigned Depth=0)
Get a canonical multiply expression, or something simpler if possible.
 
LLVM_ABI const SCEV * getTruncateOrZeroExtend(const SCEV *V, Type *Ty, unsigned Depth=0)
Return a SCEV corresponding to a conversion of the input value to the specified type.
 
LLVM_ABI const SCEV * getAddExpr(SmallVectorImpl< const SCEV * > &Ops, SCEV::NoWrapFlags Flags=SCEV::FlagAnyWrap, unsigned Depth=0)
Get a canonical add expression, or something simpler if possible.
 
LLVM_ABI const SCEV * getTruncateOrSignExtend(const SCEV *V, Type *Ty, unsigned Depth=0)
Return a SCEV corresponding to a conversion of the input value to the specified type.
 
A vector that has set insertion semantics.
 
size_type count(const key_type &key) const
Count the number of elements of a given key in the SetVector.
 
bool insert(const value_type &X)
Insert a new element into the SetVector.
 
Simple and conservative implementation of LoopSafetyInfo that can give false-positive answers to its ...
 
void computeLoopSafetyInfo(const Loop *CurLoop) override
Computes safety information for a loop checks loop body & header for the possibility of may throw exc...
 
bool anyBlockMayThrow() const override
Returns true iff any block of the loop for which this info is contains an instruction that may throw ...
 
A templated base class for SmallPtrSet which provides the typesafe interface that is common across al...
 
bool erase(PtrType Ptr)
Remove pointer from the set.
 
size_type count(ConstPtrType Ptr) const
count - Return 1 if the specified pointer is in the set, 0 otherwise.
 
void insert_range(Range &&R)
 
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.
 
This class consists of common code factored out of the SmallVector class to reduce code duplication b...
 
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.
 
Value * getValueOperand()
 
Value * getPointerOperand()
 
StringRef - Represent a constant reference to a string, i.e.
 
Provides information about what library functions are available for the current target.
 
unsigned getWCharSize(const Module &M) const
Returns the size of the wchar_t type in bytes or 0 if the size is unknown.
 
bool has(LibFunc F) const
Tests whether a library function is available.
 
Triple - Helper class for working with autoconf configuration names.
 
Twine - A lightweight data structure for efficiently representing the concatenation of temporary valu...
 
The instances of the Type class are immutable: once they are created, they are never changed.
 
LLVM_ABI unsigned getIntegerBitWidth() const
 
LLVM_ABI unsigned getPointerAddressSpace() const
Get the address space of this pointer or pointer vector type.
 
static LLVM_ABI IntegerType * getInt8Ty(LLVMContext &C)
 
Type * getScalarType() const
If this is a vector type, return the element type, otherwise return 'this'.
 
LLVM_ABI unsigned getScalarSizeInBits() const LLVM_READONLY
If this is a vector type, return the getPrimitiveSizeInBits value for the element type.
 
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 LLVM_ABI IntegerType * getIntNTy(LLVMContext &C, unsigned N)
 
A Use represents the edge between a Value definition and its users.
 
void setOperand(unsigned i, Value *Val)
 
Value * getOperand(unsigned i) const
 
unsigned getNumOperands() const
 
LLVM Value Representation.
 
Type * getType() const
All values are typed, get the type of this value.
 
bool hasOneUse() const
Return true if there is exactly one use of this value.
 
LLVM_ABI void replaceAllUsesWith(Value *V)
Change all uses of this to point to a new Value.
 
iterator_range< user_iterator > users()
 
LLVM_ABI 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...
 
LLVM_ABI void replaceUsesOutsideBlock(Value *V, BasicBlock *BB)
replaceUsesOutsideBlock - Go through the uses list for this definition and make each use point to "V"...
 
LLVM_ABI LLVMContext & getContext() const
All values hold a context through their type.
 
LLVM_ABI StringRef getName() const
Return a constant reference to the value's name.
 
LLVM_ABI void takeName(Value *V)
Transfer the name from V to this value.
 
Value handle that is nullable, but tries to track the Value.
 
constexpr ScalarTy getFixedValue() const
 
constexpr bool isScalable() const
Returns whether the quantity is scaled by a runtime quantity (vscale).
 
const ParentTy * getParent() const
 
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
 
Abstract Attribute helper functions.
 
constexpr char Args[]
Key for Kernel::Metadata::mArgs.
 
constexpr char Attrs[]
Key for Kernel::Metadata::mAttrs.
 
constexpr std::underlying_type_t< E > Mask()
Get a bitmask with 1s in all places up to the high-order bit of E's largest value.
 
@ C
The default llvm calling convention, compatible with C.
 
@ BasicBlock
Various leaf nodes.
 
OperandType
Operands are tagged with one of the values of this enum.
 
BinaryOp_match< LHS, RHS, Instruction::Add > m_Add(const LHS &L, const RHS &R)
 
BinaryOp_match< LHS, RHS, Instruction::And, true > m_c_And(const LHS &L, const RHS &R)
Matches an And with LHS and RHS in either order.
 
bool match(Val *V, const Pattern &P)
 
bind_ty< Instruction > m_Instruction(Instruction *&I)
Match an instruction, capturing it if we match.
 
specificval_ty m_Specific(const Value *V)
Match if we have a specific specified value.
 
cst_pred_ty< is_one > m_One()
Match an integer 1 or a vector with all elements equal to 1.
 
match_combine_and< LTy, RTy > m_CombineAnd(const LTy &L, const RTy &R)
Combine two pattern matchers matching L && R.
 
brc_match< Cond_t, bind_ty< BasicBlock >, bind_ty< BasicBlock > > m_Br(const Cond_t &C, BasicBlock *&T, BasicBlock *&F)
 
BinaryOp_match< LHS, RHS, Instruction::Add, true > m_c_Add(const LHS &L, const RHS &R)
Matches a Add with LHS and RHS in either order.
 
class_match< Value > m_Value()
Match an arbitrary value and ignore it.
 
CmpClass_match< LHS, RHS, ICmpInst > m_ICmp(CmpPredicate &Pred, const LHS &L, const RHS &R)
 
BinOpPred_match< LHS, RHS, is_shift_op > m_Shift(const LHS &L, const RHS &R)
Matches shift operations.
 
BinaryOp_match< LHS, RHS, Instruction::Shl > m_Shl(const LHS &L, const RHS &R)
 
class_match< BasicBlock > m_BasicBlock()
Match an arbitrary basic block value and ignore it.
 
is_zero m_Zero()
Match any null constant or a vector with all elements equal to 0.
 
BinaryOp_match< LHS, RHS, Instruction::Sub > m_Sub(const LHS &L, const RHS &R)
 
cst_pred_ty< icmp_pred_with_threshold > m_SpecificInt_ICMP(ICmpInst::Predicate Predicate, const APInt &Threshold)
Match an integer or vector with every element comparing 'pred' (eg/ne/...) to Threshold.
 
bind_cst_ty m_scev_APInt(const APInt *&C)
Match an SCEV constant and bind it to an APInt.
 
class_match< const SCEVConstant > m_SCEVConstant()
 
specificloop_ty m_SpecificLoop(const Loop *L)
 
SCEVAffineAddRec_match< Op0_t, Op1_t, class_match< const Loop > > m_scev_AffineAddRec(const Op0_t &Op0, const Op1_t &Op1)
 
bool match(const SCEV *S, const Pattern &P)
 
specificscev_ty m_scev_Specific(const SCEV *S)
Match if we have a specific specified SCEV.
 
class_match< const SCEV > m_SCEV()
 
initializer< Ty > init(const Ty &Val)
 
LocationClass< Ty > location(Ty &L)
 
DiagnosticInfoOptimizationBase::Argument NV
 
DiagnosticInfoOptimizationBase::setExtraArgs setExtraArgs
 
This is an optimization pass for GlobalISel generic memory operations.
 
FunctionAddr VTableAddr Value
 
LLVM_ABI 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.
 
decltype(auto) dyn_cast(const From &Val)
dyn_cast<X> - Return the argument parameter cast to the specified type.
 
iterator_range< T > make_range(T x, T y)
Convenience function for iterating over sub-ranges.
 
Value * GetPointerBaseWithConstantOffset(Value *Ptr, int64_t &Offset, const DataLayout &DL, bool AllowNonInbounds=true)
Analyze the specified pointer to see if it can be expressed as a base pointer plus a constant offset.
 
LLVM_ABI bool isLibFuncEmittable(const Module *M, const TargetLibraryInfo *TLI, LibFunc TheLibFunc)
Check whether the library function is available on target and also that it in the current Module is a...
 
AnalysisManager< Loop, LoopStandardAnalysisResults & > LoopAnalysisManager
The loop analysis manager.
 
OutputIt transform(R &&Range, OutputIt d_first, UnaryFunction F)
Wrapper function around std::transform to apply a function to a range and store the result elsewhere.
 
LLVM_ABI bool isMustProgress(const Loop *L)
Return true if this loop can be assumed to make progress.
 
LLVM_ABI raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
 
FunctionAddr VTableAddr Count
 
bool isModOrRefSet(const ModRefInfo MRI)
 
LLVM_ABI Value * emitStrLen(Value *Ptr, IRBuilderBase &B, const DataLayout &DL, const TargetLibraryInfo *TLI)
Emit a call to the strlen function to the builder, for the specified pointer.
 
bool isa(const From &Val)
isa<X> - Return true if the parameter to the template is an instance of one of the template type argu...
 
ModRefInfo
Flags indicating whether a memory access modifies or references memory.
 
@ ModRef
The access may reference and may modify the value stored in memory.
 
@ Mod
The access may modify the value stored in memory.
 
FunctionAddr VTableAddr uintptr_t uintptr_t Data
 
LLVM_ABI bool VerifyMemorySSA
Enables verification of MemorySSA.
 
LLVM_ABI bool isConsecutiveAccess(Value *A, Value *B, const DataLayout &DL, ScalarEvolution &SE, bool CheckType=true)
Returns true if the memory operations A and B are consecutive.
 
DWARFExpression::Operation Op
 
LLVM_ABI bool isGuaranteedNotToBeUndefOrPoison(const Value *V, AssumptionCache *AC=nullptr, const Instruction *CtxI=nullptr, const DominatorTree *DT=nullptr, unsigned Depth=0)
Return true if this function can prove that V does not have undef bits and is never poison.
 
LLVM_ABI Value * emitWcsLen(Value *Ptr, IRBuilderBase &B, const DataLayout &DL, const TargetLibraryInfo *TLI)
Emit a call to the wcslen function to the builder, for the specified pointer.
 
decltype(auto) cast(const From &Val)
cast<X> - Return the argument parameter cast to the specified type.
 
LLVM_ABI PreservedAnalyses getLoopPassPreservedAnalyses()
Returns the minimum set of Analyses that all loop passes must preserve.
 
LLVM_ABI Value * isBytewiseValue(Value *V, const DataLayout &DL)
If the specified value can be set by repeating the same byte in memory, return the i8 value that it i...
 
LLVM_ABI 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...
 
LLVM_ABI const Value * getUnderlyingObject(const Value *V, unsigned MaxLookup=MaxLookupSearchDepth)
This method strips off any GEP address adjustments, pointer casts or llvm.threadlocal....
 
AAResults AliasAnalysis
Temporary typedef for legacy code that uses a generic AliasAnalysis pointer or reference.
 
LLVM_ABI bool isKnownNonNegative(const Value *V, const SimplifyQuery &SQ, unsigned Depth=0)
Returns true if the give value is known to be non-negative.
 
std::optional< DecomposedBitTest > decomposeBitTestICmp(Value *LHS, Value *RHS, CmpInst::Predicate Pred, bool LookThroughTrunc=true, bool AllowNonZeroC=false, bool DecomposeAnd=false)
Decompose an icmp into the form ((X & Mask) pred C) if possible.
 
void swap(llvm::BitVector &LHS, llvm::BitVector &RHS)
Implement std::swap in terms of BitVector swap.
 
A collection of metadata nodes that might be associated with a memory access used by the alias-analys...
 
LLVM_ABI AAMDNodes merge(const AAMDNodes &Other) const
Given two sets of AAMDNodes applying to potentially different locations, determine the best AAMDNodes...
 
AAMDNodes extendTo(ssize_t Len) const
Create a new AAMDNode that describes this AAMDNode after extending it to apply to a series of bytes o...
 
static bool Wcslen
When true, Wcslen is disabled.
 
static bool HashRecognize
When true, HashRecognize is disabled.
 
static bool Strlen
When true, Strlen is disabled.
 
static bool Memset
When true, Memset is disabled.
 
static bool All
When true, the entire pass is disabled.
 
static bool Memcpy
When true, Memcpy is disabled.
 
The adaptor from a function pass to a loop pass computes these analyses and makes them available to t...
 
TargetTransformInfo & TTI
 
This struct is a compact representation of a valid (power of two) or undefined (0) alignment.
 
The structure that is returned when a polynomial algorithm was recognized by the analysis.
 
Match loop-invariant value.
 
match_LoopInvariant(const SubPattern_t &SP, const Loop *L)