50 case Instruction::Sub:
51 return Instruction::Add;
52 case Instruction::FSub:
53 return Instruction::FAdd;
60 if (
I->getOpcode() == Instruction::Sub)
62 if (
I->getOpcode() == Instruction::FSub)
63 return I->hasAllowReassoc();
64 return I->isAssociative();
72 switch (
I->getOpcode()) {
73 case Instruction::ExtractValue:
74 case Instruction::InsertValue:
76 case Instruction::ExtractElement:
79 case Instruction::InsertElement:
89 "ScalableVectorType is not supported.");
100 return std::min<unsigned>(PartNumElems,
Size - Part * PartNumElems);
108 OS <<
"Idx: " << Idx <<
", ";
109 OS <<
"n=" << VL.
size() <<
" [" << *VL.
front() <<
", ..]";
124 return !isa<PoisonValue>(V);
130 if (BB !=
II->getParent())
143 Value *FirstNonUndef =
nullptr;
146 if (!FirstNonUndef) {
150 if (V != FirstNonUndef)
153 return FirstNonUndef !=
nullptr;
159 if ((LHS == Intrinsic::fma || LHS == Intrinsic::fmuladd) &&
160 (RHS == Intrinsic::fma || RHS == Intrinsic::fmuladd))
161 return Intrinsic::fma;
168 return Cmp->isCommutative();
170 return BO->isCommutative() ||
171 (BO->getOpcode() == Instruction::Sub && ValWithUses->
hasUseList() &&
178 if (match(U.getUser(),
179 m_ICmp(Pred, m_Specific(U.get()), m_Zero())) &&
180 (Pred == ICmpInst::ICMP_EQ || Pred == ICmpInst::ICMP_NE))
184 auto *I = dyn_cast<BinaryOperator>(U.get());
185 return match(U.getUser(),
186 m_Intrinsic<Intrinsic::abs>(
187 m_Specific(U.get()), m_ConstantInt(Flag))) &&
188 ((!IsCopyable && I && !I->hasNoSignedWrap()) ||
191 (BO->getOpcode() == Instruction::FSub && ValWithUses->
hasUseList() &&
194 return match(U.getUser(),
195 m_Intrinsic<Intrinsic::fabs>(m_Specific(U.get())));
197 return I->isCommutative();
205 "The instruction is not commutative.");
209 switch (BO->getOpcode()) {
210 case Instruction::Sub:
211 case Instruction::FSub:
217 return I->isCommutableOperand(
Op);
224 constexpr unsigned IntrinsicNumOperands = 2;
225 return IntrinsicNumOperands;
227 return I->getNumOperands();
242 Type *CurrentType =
IV->getType();
243 for (
unsigned I :
IV->indices()) {
245 Index *= ST->getNumElements();
246 CurrentType = ST->getElementType(
I);
248 Index *= AT->getNumElements();
249 CurrentType = AT->getElementType();
268 if (auto *CI = dyn_cast<CmpInst>(V))
269 return BasePred == CI->getPredicate();
270 if (auto *I = dyn_cast<Instruction>(V))
271 return I->getOpcode() == Opcode;
272 return isa<PoisonValue>(V);
277 unsigned Opcode = E->getOpcode();
278 assert((Opcode == Instruction::ExtractElement ||
279 Opcode == Instruction::ExtractValue) &&
280 "Expected extractelement or extractvalue instruction.");
281 if (Opcode == Instruction::ExtractElement) {
287 unsigned Idx = CI->getZExtValue();
295 if (EI->getNumIndices() != 1)
297 return *EI->idx_begin();
303 const unsigned E = Indices.
size();
305 for (
unsigned I = 0;
I < E; ++
I)
306 Mask[Indices[
I]] =
I;
310 assert(!Mask.empty() &&
"Expected non-empty mask.");
314 for (
unsigned I = 0, E = Prev.
size();
I < E; ++
I)
316 Scalars[Mask[
I]] = Prev[
I];
320 assert(!Mask.empty() && Reuses.
size() == Mask.size() &&
321 "Expected non-empty mask.");
324 for (
unsigned I = 0, E = Prev.
size();
I < E; ++
I)
326 Reuses[Mask[
I]] = Prev[
I];
331 assert(!Mask.empty() &&
"Expected non-empty mask.");
332 unsigned Sz = Mask.size();
337 std::iota(PrevOrder.
begin(), PrevOrder.
end(), 0);
339 PrevOrder.
swap(Order);
342 for (
unsigned I = 0;
I < Sz; ++
I)
344 Order[
I] = PrevOrder[Mask[
I]];
346 return Data.value() == Sz ||
Data.index() ==
Data.value();
357 std::iota(MaskOrder.
begin(), MaskOrder.
end(), 0);
367 for (
unsigned I = 0;
I < Sz; ++
I)
369 Order[MaskOrder[
I]] =
I;
375 "Order is empty. Please check it before using isReverseOrder.");
376 unsigned Sz = Order.
size();
378 return Pair.value() == Sz || Sz - Pair.index() - 1 == Pair.value();
386 for (
unsigned I = Sz, E = Mask.size();
I < E;
I += Sz) {
397 "Expected same size of orders");
398 size_t Sz = Order.
size();
401 if (Order[Idx] != Sz)
402 UsedIndices.
set(Order[Idx]);
404 if (SecondaryOrder.
empty()) {
406 if (Order[Idx] == Sz && !UsedIndices.
test(Idx))
410 if (SecondaryOrder[Idx] != Sz && Order[Idx] == Sz &&
411 !UsedIndices.
test(SecondaryOrder[Idx]))
412 Order[Idx] = SecondaryOrder[Idx];
417 assert(!VL.
empty() &&
"Expected non-empty list of values.");
419 return all_of(VL, [&](
Value *V) {
return V->getType() == Ty; });
425 static_assert(std::is_same_v<T, InsertElementInst> ||
426 std::is_same_v<T, ExtractElementInst>,
433 constexpr bool IsInsert = std::is_same_v<T, InsertElementInst>;
434 Type *VecTy = IsInsert ? IE->getType() : IE->getOperand(0)->getType();
441 if (CI->getValue().uge(VT->getNumElements()))
444 Index *= VT->getNumElements();
445 Index += CI->getZExtValue();
451template std::optional<unsigned>
453template std::optional<unsigned>
463 return isa<PHINode>(IO) || IO->getParent() != I->getParent();
472 return !
I->mayReadOrWriteMemory() && !
I->hasNUsesOrMore(
UsesLimit) &&
474 auto *IU = dyn_cast<Instruction>(U);
477 return IU->getParent() != I->getParent() || isa<PHINode>(IU);
486 return !VL.
empty() &&
499 I * VecTyNumElements, VecTyNumElements)))
501 : Mask[
I] * VecTyNumElements + J;
511 unsigned SVNumElements =
513 unsigned ShuffleMaskSize = SV->getShuffleMask().size();
514 if (SVNumElements % ShuffleMaskSize != 0)
516 unsigned GroupSize = SVNumElements / ShuffleMaskSize;
517 if (GroupSize == 0 || (VL.
size() % GroupSize) != 0)
519 unsigned NumGroup = 0;
520 for (
size_t I = 0, E = VL.
size();
I != E;
I += GroupSize) {
522 Value *Src = SV->getOperand(0);
528 if (SV->getOperand(0) != Src)
531 if (!SV->isExtractSubvectorMask(Index))
533 ExpectedIndex.
set(Index / ShuffleMaskSize);
537 if (!ExpectedIndex.
all())
541 assert(NumGroup == (VL.
size() / GroupSize) &&
"Unexpected number of groups");
548 unsigned SVNumElements =
551 unsigned AccumulateLength = 0;
552 for (
Value *V : VL) {
554 for (
int M : SV->getShuffleMask())
556 : AccumulateLength + M);
557 AccumulateLength += SVNumElements;
584std::optional<TargetTransformInfo::ShuffleKind>
597 return std::max(S, VTy->getNumElements());
600 Value *Vec1 =
nullptr;
601 Value *Vec2 =
nullptr;
610 ShuffleMode CommonShuffleMode =
Unknown;
612 for (
unsigned I = 0, E = VL.
size();
I < E; ++
I) {
622 auto *Vec = EI->getVectorOperand();
636 if (Idx->getValue().uge(
Size))
638 unsigned IntIdx = Idx->getValue().getZExtValue();
645 if (!Vec1 || Vec1 == Vec) {
647 }
else if (!Vec2 || Vec2 == Vec) {
653 if (CommonShuffleMode == Permute)
657 if (Mask[
I] %
Size !=
I) {
658 CommonShuffleMode = Permute;
661 CommonShuffleMode =
Select;
664 if (CommonShuffleMode ==
Select && Vec2)
683 auto *Begin = std::next(Mask.begin(), Index);
684 std::iota(Begin, std::next(Begin, SubVecVF), 0);
685 Vec = Builder.CreateShuffleVector(V, Mask);
688 std::iota(Mask.begin(), Mask.end(), 0);
689 std::iota(std::next(Mask.begin(), Index),
690 std::next(Mask.begin(), Index + SubVecVF), VecVF);
692 return Generator(Vec, V, Mask);
695 std::iota(ResizeMask.
begin(), std::next(ResizeMask.
begin(), SubVecVF), 0);
696 V = Builder.CreateShuffleVector(V, ResizeMask);
698 return Builder.CreateShuffleVector(Vec, V, Mask);
702 unsigned SubVecVF,
unsigned Index) {
704 std::iota(Mask.begin(), Mask.end(), Index);
705 return Builder.CreateShuffleVector(Vec, Mask);
724template <
bool IsPoisonOnly>
727 using T = std::conditional_t<IsPoisonOnly, PoisonValue, UndefValue>;
761 for (
unsigned I = 0, E = VecTy->getNumElements();
I != E; ++
I) {
762 if (
Constant *Elem =
C->getAggregateElement(
I))
782 case Instruction::Load: {
786 case Instruction::Store: {
788 return (
SI->getPointerOperand() == Scalar);
790 case Instruction::Call: {
794 return isVectorIntrinsicWithScalarOpAtArg(ID, Arg.index(), TTI) &&
795 Arg.value().get() == Scalar;
813 return LI->isSimple();
815 return SI->isSimple();
817 return !
MI->isVolatile();
827 uint64_t ScalarSize =
DL.getTypeStoreSize(ScalarTy);
828 Conditions.
assign(PointerOps.
size(),
nullptr);
833 APInt OffsetAP(
DL.getIndexTypeSizeInBits(
GEP->getType()), 0);
834 if (!
GEP->accumulateConstantOffset(
DL, OffsetAP) || OffsetAP.
isNegative())
837 Base =
GEP->getPointerOperand();
842 Value *
T = Sel->getTrueValue();
843 Value *
F = Sel->getFalseValue();
849 }
else if (TrueBase !=
T || FalseBase !=
F) {
854 if (
Offset !=
static_cast<uint64_t
>(Idx) * ScalarSize)
856 Conditions[Idx] = Sel->getCondition();
858 return TrueBase !=
nullptr;
864 constexpr unsigned IndexIdx = 1;
868 bool AllSameTy =
true;
869 bool HasNonConstIdx =
false;
870 bool ConstsFitVL0Ty =
true;
873 if (
Op->getType() != VL0Ty)
878 if (
Op->getType() != VL0Ty)
880 HasNonConstIdx =
true;
884 ConstsFitVL0Ty =
false;
888 if (!HasNonConstIdx || VL0Ty == PtrIdxTy)
890 return ConstsFitVL0Ty ? VL0Ty :
nullptr;
895 if (UniquePtrs.
size() != PointerOps.
size())
897 auto IsConstantOffsetPtr = [](
Value *
P) {
902 auto *RefIt =
find_if_not(PointerOps, IsConstantOffsetPtr);
903 if (RefIt == PointerOps.
end())
906 if (!RefGEP || RefGEP->getNumOperands() != 2)
908 Value *
Base = RefGEP->getPointerOperand();
909 Type *PtrTy = RefGEP->getType();
910 Type *SrcElemTy = RefGEP->getSourceElementType();
912 Value *Stride =
nullptr;
913 unsigned CastOpcode = 0;
914 for (
Value *
P : PointerOps) {
915 if (
P->getType() != PtrTy)
920 if (!
GEP ||
GEP->getNumOperands() != 2 ||
921 GEP->getPointerOperand() !=
Base ||
922 GEP->getSourceElementType() != SrcElemTy)
927 unsigned LaneCastOpcode = 0;
929 LaneCastOpcode = Cast->getOpcode();
930 Idx = Cast->getOperand(0);
932 Value *LaneStride = Idx;
935 LaneStride = BO->getOperand(0);
937 LaneStride = BO->getOperand(1);
941 CastOpcode = LaneCastOpcode;
944 if (LaneStride != Stride || LaneCastOpcode != CastOpcode)
947 return Stride !=
nullptr;
951 bool ExtendingManyInputs) {
955 (!ExtendingManyInputs || SubMask.
size() > Mask.size() ||
958 "SubMask with many inputs support must be larger than the mask.");
960 Mask.append(SubMask.
begin(), SubMask.
end());
964 int TermValue = std::min(Mask.size(), SubMask.
size());
965 for (
int I = 0, E = SubMask.
size();
I < E; ++
I) {
967 (!ExtendingManyInputs &&
968 (SubMask[
I] >= TermValue || Mask[SubMask[
I]] >= TermValue)))
970 NewMask[
I] = Mask[SubMask[
I]];
976 const size_t Sz = Order.
size();
979 for (
unsigned I = 0;
I < Sz; ++
I) {
981 UnusedIndices.
reset(Order[
I]);
983 MaskedIndices.
set(
I);
985 if (MaskedIndices.
none())
988 "Non-synced masked/available indices.");
992 assert(Idx >= 0 &&
"Indices must be synced.");
1000 unsigned Opcode0,
unsigned Opcode1) {
1007 OpcodeMask.
set(Lane * ScalarTyNumElements,
1008 Lane * ScalarTyNumElements + ScalarTyNumElements);
1015 "Expected scalar constants.");
1018 std::fill_n(NewVal.begin() +
I * VF, VF, V);
1024 case Instruction::UDiv:
1025 return Intrinsic::masked_udiv;
1026 case Instruction::SDiv:
1027 return Intrinsic::masked_sdiv;
1028 case Instruction::URem:
1029 return Intrinsic::masked_urem;
1030 case Instruction::SRem:
1031 return Intrinsic::masked_srem;
1042 constexpr unsigned MaxIndexChainLength = 3;
1045 auto IsProfitableOperand = [](
const Value *V) {
1049 V = Cast->getOperand(0);
1052 const User *U =
I->user_back();
1053 for ([[maybe_unused]]
unsigned _ :
seq<unsigned>(MaxIndexChainLength)) {
1056 none_of(
I->operand_values(), IsProfitableOperand);
1070 unsigned Opcode = BO->getOpcode();
1071 Type *Ty = BO->getType();
1075 Opcode, Ty, Idx == 1) ||
1077 Opcode, Ty, Idx == 0)))
1081 const User *U =
I->user_back();
1093 if (!Wide || !Wide->hasOneUse())
1096 if (!Narrow || !Narrow->hasOneUse())
1098 Value *Src = Narrow->getOperand(0);
1101 if (MustBeElidable && !(Wide->hasAllowContract() && Wide->hasNoNaNs() &&
1102 Wide->hasNoInfs() && Narrow->hasAllowContract()))
1112struct NarrowedChainState {
1114 unsigned NarrowShift = 0;
1115 unsigned NarrowBW = 0;
1133 NarrowedChainState S,
unsigned Depth,
1137 if (
Depth < MaxDepth) {
1139 Z && Z->getSrcTy()->isIntegerTy() && !Z->getSrcTy()->isIntegerTy(1)) {
1142 Depth + 1, MaxDepth, Leaves, ChainInsts);
1145 if (BO->getOpcode() == RdxOpcode) {
1148 Depth + 1, MaxDepth, Leaves, ChainInsts);
1150 Depth + 1, MaxDepth, Leaves, ChainInsts);
1154 unsigned BW = V->getType()->getScalarSizeInBits();
1156 if (BO->getOpcode() == Instruction::Shl && Z && S.NarrowBW == 0 &&
1158 Z->getSrcTy()->isIntegerTy() && !Z->getSrcTy()->isIntegerTy(1) &&
1160 Z->getSrcTy()->getIntegerBitWidth() + Amt->
getZExtValue() <= BW) &&
1166 Depth + 1, MaxDepth, Leaves,
1173 if (BW < WideBW && (S.NarrowBW == 0 || BW == S.NarrowBW)) {
1174 if (BO->getOpcode() == Instruction::Shl &&
1177 S.Shift + S.NarrowShift + Amt->
getZExtValue() < WideBW) {
1179 if (BO->hasNoUnsignedWrap() && S.NarrowBW == 0) {
1186 if (S.NarrowBW == 0) {
1193 S,
Depth + 1, MaxDepth, Leaves,
1199 if (S.NarrowBW == 0) {
1203 S.NarrowMask &= *Amt << S.NarrowShift;
1205 MaxDepth, Leaves, ChainInsts);
1211 S.getMask(V->getType()->getScalarSizeInBits()));
1219 0, MaxDepth, Leaves, ChainInsts);
1223 assert(
F &&
"Expected function.");
1229static std::optional<std::tuple<Value *, unsigned, unsigned>>
1231 if (!V->getType()->isIntegerTy())
1232 return std::nullopt;
1235 auto GetFieldOffset = [](
const APInt *Amt,
unsigned BitWidth,
1236 unsigned FieldWidth) -> std::optional<unsigned> {
1238 if (ShAmt % FieldWidth != 0 || ShAmt + FieldWidth >
BitWidth)
1239 return std::nullopt;
1240 return ShAmt / FieldWidth;
1245 auto MatchLowField =
1247 unsigned FieldWidth) -> std::optional<std::pair<Value *, unsigned>> {
1253 if (std::optional<unsigned>
Offset = GetFieldOffset(
1254 Amt, Src->getType()->getIntegerBitWidth(), FieldWidth)) {
1257 return std::make_pair(Src, *
Offset);
1259 return std::nullopt;
1262 Src->getType()->getIntegerBitWidth() >= FieldWidth)
1263 return std::make_pair(Src, 0u);
1266 return std::make_pair(Val, 0u);
1267 return std::nullopt;
1273 unsigned FieldWidth = 0;
1275 FieldWidth = Mask->popcount();
1278 if (FieldWidth != 0) {
1279 if (std::optional<std::pair<Value *, unsigned>>
Field =
1280 MatchLowField(Val, FieldWidth))
1281 return std::make_tuple(
Field->first, FieldWidth,
Field->second);
1282 return std::nullopt;
1284 unsigned LaneWidth = V->getType()->getIntegerBitWidth();
1288 unsigned SrcWidth = Src->getType()->getIntegerBitWidth();
1291 if (std::optional<unsigned>
Offset =
1292 GetFieldOffset(Amt, SrcWidth, LaneWidth))
1293 return std::make_tuple(Src, LaneWidth, *
Offset);
1295 unsigned FieldWidth = SrcWidth - ShAmt;
1296 if (FieldWidth > 0 && FieldWidth < LaneWidth && ShAmt % FieldWidth == 0)
1297 return std::make_tuple(Src, FieldWidth, ShAmt / FieldWidth);
1298 return std::nullopt;
1303 unsigned ShfWidth = Src->getType()->getIntegerBitWidth();
1305 unsigned FieldWidth = ShfWidth - ShAmt;
1306 if (FieldWidth > 0 && ShAmt % FieldWidth == 0) {
1308 return std::make_tuple(Src, FieldWidth, ShAmt / FieldWidth);
1310 return std::nullopt;
1313 return std::make_tuple(Src, LaneWidth, 0u);
1314 return std::nullopt;
1317std::optional<std::tuple<Value *, unsigned, SmallVector<int>>>
1322 if (VL.
size() < 2 || !VL.
front()->getType()->isIntegerTy() ||
isSplat(VL) ||
1324 return std::nullopt;
1325 Value *Src =
nullptr;
1326 unsigned FieldWidth = 0;
1331 if (V->getType() != VL.
front()->getType())
1332 return std::nullopt;
1333 std::optional<std::tuple<Value *, unsigned, unsigned>>
Field =
1335 if (!
Field || (Src && (Src != std::get<0>(*
Field) ||
1336 FieldWidth != std::get<1>(*
Field))))
1337 return std::nullopt;
1338 Src = std::get<0>(*
Field);
1339 FieldWidth = std::get<1>(*
Field);
1340 Mask[Idx] = std::get<2>(*
Field);
1346 Src->getType()->getIntegerBitWidth() % FieldWidth != 0)
1347 return std::nullopt;
1353 return std::nullopt;
1354 return std::make_tuple(Src, FieldWidth, std::move(Mask));
1362 unsigned BitWidth = V->getType()->getScalarSizeInBits();
1412 unsigned NumElts = PossibleBits.
size();
1415 for (
unsigned Idx :
seq(NumElts)) {
1416 APInt Possible = PossibleBits[Idx].shl(ShlAmts[Idx]) & Masks[Idx];
1421 return std::nullopt;
1422 if (Info.FieldWidth == 0) {
1423 if (W % 8 != 0 ||
BitWidth % W != 0)
1424 return std::nullopt;
1425 Info.FieldWidth = W;
1428 if (W != Info.FieldWidth ||
Lo % W != 0)
1429 return std::nullopt;
1432 return std::nullopt;
1433 Info.LaneOfField[
Field] = Idx;
1434 Info.LShrAmts[Idx] =
Lo - ShlAmts[Idx];
1436 if (Info.FieldWidth == 0)
1437 return std::nullopt;
1442 unsigned NumElts,
unsigned BytesPerLane) {
1443 unsigned BytesPerField = Info.FieldWidth / 8;
1445 for (
unsigned J :
seq(NumBytes)) {
1446 unsigned Lane = Info.LaneOfField[J / BytesPerField];
1448 ? (
int)(NumElts * BytesPerLane)
1449 : (
int)(Lane * BytesPerLane + J % BytesPerField));
1455 unsigned ShiftWidth,
unsigned &NumInsts) {
1458 unsigned BitWidth = VecTy->getScalarSizeInBits();
1460 "The byte-multiple field width divides the result bit width.");
1461 unsigned NumElts = VecTy->getNumElements();
1467 Y = Z->getOperand(0);
1469 Y = Builder.CreateTrunc(
1475 if (Info.needsShift()) {
1477 for (uint64_t
A : Info.LShrAmts)
1483 unsigned InBytes = NumElts * (ShiftWidth / 8);
1491 return Builder.CreateUnaryIntrinsic(Intrinsic::bswap,
1492 Builder.CreateBitCast(
Y, IntTy));
1497 return Builder.CreateBitCast(
Y, IntTy);
1499 Value *Packed = Builder.CreateShuffleVector(
1500 Builder.CreateBitCast(
Y, ByteTy),
1506 return Builder.CreateBitCast(Packed, IntTy);
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
AMDGPU Register Bank Select
This file implements a class to represent arbitrary precision integral constant values and operations...
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
static GCRegistry::Add< ShadowStackGC > C("shadow-stack", "Very portable GC for uncooperative code generators")
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 std::pair< Value *, APInt > getMask(Value *WideMask, unsigned Factor, ElementCount LeafValueEC)
uint64_t IntrinsicInst * II
OptimizedStructLayoutField Field
Provides some synthesis utilities to produce sequences of values.
This file defines the SmallPtrSet class.
static TableGen::Emitter::Opt Y("gen-skeleton-entry", EmitSkeleton, "Generate example skeleton entry")
static const uint32_t IV[8]
Class for arbitrary precision integers.
static APInt getAllOnes(unsigned numBits)
Return an APInt of a specified width with all bits set.
LLVM_ABI APInt zext(unsigned width) const
Zero extend to a new width.
uint64_t getZExtValue() const
Get zero extended value.
unsigned getActiveBits() const
Compute the number of active bits in the value.
bool isZero() const
Determine if this value is zero, i.e. all bits are clear.
bool ult(const APInt &RHS) const
Unsigned less than comparison.
bool isNegative() const
Determine sign of this APInt.
bool isShiftedMask() const
Return true if this APInt value contains a non-empty sequence of ones with the remainder zero.
uint64_t getLimitedValue(uint64_t Limit=UINT64_MAX) const
If this value is smaller than the specified limit, return it, otherwise return the limit value.
LLVM_ABI APInt uadd_sat(const APInt &RHS) const
APInt shl(unsigned shiftAmt) const
Left-shift function.
LLVM_ABI APInt umul_sat(const APInt &RHS) const
static APInt getLowBitsSet(unsigned numBits, unsigned loBitsSet)
Constructs an APInt value that has the bottom loBitsSet bits set.
APInt lshr(unsigned shiftAmt) const
Logical right-shift function.
Represent a constant reference to an array (0 or more elements consecutively in memory),...
const T & front() const
Get the first element.
size_t size() const
Get the array size.
bool empty() const
Check if the array is empty.
ArrayRef< T > slice(size_t N, size_t M) const
slice(n, m) - Chop off the first N elements of the array, and keep M elements in the array.
const T & consume_front()
consume_front() - Returns the first element and drops it from ArrayRef.
A cache of @llvm.assume calls within a function.
LLVM Basic Block Representation.
iterator_range< User::op_iterator > args()
Iteration adapter for range-for loops.
This class represents a function call, abstracting a target machine's calling convention.
Predicate
This enumeration lists the possible predicates for CmpInst subclasses.
static LLVM_ABI Constant * getBinOpAbsorber(unsigned Opcode, Type *Ty, bool AllowLHSConstant=false)
Return the absorbing element for the given binary operation, i.e.
static LLVM_ABI Constant * getBinOpIdentity(unsigned Opcode, Type *Ty, bool AllowRHSConstant=false, bool NSZ=false)
Return the identity constant for a binary opcode.
static LLVM_ABI Constant * get(ArrayRef< Constant * > V)
This is an important base class in LLVM.
static LLVM_ABI Constant * getNullValue(Type *Ty)
Constructor to create a '0' constant of arbitrary type.
A parsed version of the target data layout string in and methods for querying it.
static LLVM_ABI FixedVectorType * get(Type *ElementType, unsigned NumElts)
Common base class shared among various IRBuilders.
unsigned getOpcode() const
Returns a member of one of the enums like Instruction::Add.
static LLVM_ABI IntegerType * get(LLVMContext &C, unsigned NumBits)
This static method is the primary way of constructing an IntegerType.
An instruction for reading from memory.
Value * getPointerOperand()
This is the common base class for memset/memcpy/memmove.
Representation for a specific memory location.
static LLVM_ABI MemoryLocation get(const LoadInst *LI)
Return a location with information about the memory reference by the given instruction.
Represent a mutable reference to an array (0 or more elements consecutively in memory),...
static LLVM_ABI PoisonValue * get(Type *T)
Static factory methods - Return an 'poison' object of the specified type.
static LLVM_ABI bool isIdentityMask(ArrayRef< int > Mask, int NumSrcElts)
Return true if this shuffle mask chooses elements from exactly one source vector without lane crossin...
static LLVM_ABI bool isReverseMask(ArrayRef< int > Mask, int NumSrcElts)
Return true if this shuffle mask swaps the order of elements from exactly one source vector.
This is a 'bitvector' (really, a variable-sized bit array), optimized for the case when the array is ...
int find_first() const
Returns the index of the first set bit, -1 if none of the bits are set.
bool test(unsigned Idx) const
Returns true if bit Idx is set.
int find_next(unsigned Prev) const
Returns the index of the next set bit following the "Prev" bit.
bool all() const
Returns true if all bits are set.
size_type count() const
Returns the number of bits which are set.
bool none() const
Returns true if none of the bits are set.
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 assign(size_type NumElts, ValueParamT Elt)
reference emplace_back(ArgTypes &&... Args)
void swap(SmallVectorImpl &RHS)
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.
The instances of the Type class are immutable: once they are created, they are never changed.
LLVM_ABI unsigned getIntegerBitWidth() const
Type * getScalarType() const
If this is a vector type, return the element type, otherwise return 'this'.
A Use represents the edge between a Value definition and its users.
Value * getOperand(unsigned i) const
LLVM Value Representation.
Type * getType() const
All values are typed, get the type of this value.
bool hasUseList() const
Check if this Value has a use-list.
LLVM_ABI bool hasNUsesOrMore(unsigned N) const
Return true if this value has N uses or more.
iterator_range< use_iterator > uses()
constexpr ScalarTy getFixedValue() const
An efficient, type-erasing, non-owning reference to a callable.
const ParentTy * getParent() const
A raw_ostream that writes to an std::string.
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
const APInt & umin(const APInt &A, const APInt &B)
Determine the smaller of two APInts considered to be unsigned.
const APInt & umax(const APInt &A, const APInt &B)
Determine the larger of two APInts considered to be unsigned.
BinaryOp_match< LHS, RHS, Instruction::And > m_And(const LHS &L, const RHS &R)
BinaryOp_match< LHS, RHS, Instruction::Add > m_Add(const LHS &L, const RHS &R)
ap_match< APInt > m_APInt(const APInt *&Res)
Match a ConstantInt or splatted ConstantVector, binding the specified pointer to the contained APInt.
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.
CastInst_match< OpTy, TruncInst > m_Trunc(const OpTy &Op)
Matches Trunc.
BinaryOp_match< LHS, RHS, Instruction::Xor > m_Xor(const LHS &L, const RHS &R)
bool match(Val *V, const Pattern &P)
BinOpPred_match< LHS, RHS, is_right_shift_op > m_Shr(const LHS &L, const RHS &R)
Matches logical shift operations.
ThreeOps_match< Cond, LHS, RHS, Instruction::Select > m_Select(const Cond &C, const LHS &L, const RHS &R)
Matches SelectInst.
auto m_Value()
Match an arbitrary value and ignore it.
BinaryOp_match< LHS, RHS, Instruction::Mul > m_Mul(const LHS &L, const RHS &R)
CastInst_match< OpTy, ZExtInst > m_ZExt(const OpTy &Op)
Matches ZExt.
OverflowingBinaryOp_match< LHS, RHS, Instruction::Sub, OverflowingBinaryOperator::NoUnsignedWrap > m_NUWSub(const LHS &L, const RHS &R)
BinaryOp_match< LHS, RHS, Instruction::LShr > m_LShr(const LHS &L, const RHS &R)
BinaryOp_match< LHS, RHS, Instruction::Shl > m_Shl(const LHS &L, const RHS &R)
BinaryOp_match< LHS, RHS, Instruction::Or > m_Or(const LHS &L, const RHS &R)
CastInst_match< OpTy, SExtInst > m_SExt(const OpTy &Op)
Matches SExt.
A private "module" namespace for types and utilities used by this pass.
std::optional< unsigned > getExtractIndex(const Instruction *E)
template SmallBitVector isUndefVector< true >(const Value *, const SmallBitVector &)
Value * createInsertVector(IRBuilderBase &Builder, Value *Vec, Value *V, unsigned Index, function_ref< Value *(Value *, Value *, ArrayRef< int >)> Generator)
Creates subvector insert.
bool areAllOperandsNonInsts(Value *V)
Checks if the provided value does not require scheduling.
std::optional< unsigned > getElementIndex(const Value *Inst, unsigned Offset)
bool doesInTreeUserNeedToExtract(Value *Scalar, Instruction *UserInst, TargetLibraryInfo *TLI, const TargetTransformInfo *TTI)
bool isCopyableGEPAddressVector(ArrayRef< Value * > PointerOps)
Checks if the pointers PointerOps of the gathered loads, which are not compatible in the usual sense ...
std::optional< std::tuple< Value *, unsigned, SmallVector< int > > > matchGatheredExtractedFields(ArrayRef< Value * > VL, const DataLayout &DL)
Checks if the values in VL are zero-extended sub-fields of the same wider integer scalar.
MemoryLocation getLocation(Instruction *I)
std::optional< BitPackInfo > computeBitPackInfo(unsigned BitWidth, ArrayRef< APInt > PossibleBits, ArrayRef< uint64_t > ShlAmts, ArrayRef< APInt > Masks)
Computes the bitfield packing layout from the per-lane possibly set bits of the source values,...
bool isSelectedBaseLoad(Type *ScalarTy, ArrayRef< Value * > PointerOps, const DataLayout &DL, Value *&TrueBase, Value *&FalseBase, SmallVectorImpl< Value * > &Conditions)
Checks if the loads with scalar type ScalarTy and pointer operands PointerOps are each (optionally vi...
SmallBitVector getAltInstrMask(ArrayRef< Value * > VL, Type *ScalarTy, unsigned Opcode0, unsigned Opcode1)
SmallBitVector isUndefVector(const Value *V, const SmallBitVector &UseMask)
Checks if the given value is actually an undefined constant vector.
Intrinsic::ID getMaskedDivRemIntrinsic(unsigned Opcode)
bool isUsedOutsideBlock(Value *V)
Checks if the provided value does not require scheduling.
bool doesNotNeedToSchedule(ArrayRef< Value * > VL)
Checks if the specified array of instructions does not require scheduling.
std::optional< unsigned > getInsertExtractIndex(const Value *Inst, unsigned Offset)
Value * buildBitPack(IRBuilderBase &Builder, Value *X, const BitPackInfo &Info, unsigned ShiftWidth, unsigned &NumInsts)
Builds the bitfield packing of X per the layout and the shift width.
void reorderScalars(SmallVectorImpl< Value * > &Scalars, ArrayRef< int > Mask)
Reorders the list of scalars in accordance with the given Mask.
SmallVector< int > getBitPackMask(const BitPackInfo &Info, unsigned NumBytes, unsigned NumElts, unsigned BytesPerLane)
Returns the byte shuffle mask packing the per-lane fields of the shifted lanes (BytesPerLane bytes ea...
static std::optional< std::tuple< Value *, unsigned, unsigned > > matchExtractedField(Value *V)
Checks if V is a zero-extended sub-field of a wider integer scalar.
bool allSameType(ArrayRef< Value * > VL)
void combineOrders(MutableArrayRef< unsigned > Order, ArrayRef< unsigned > SecondaryOrder)
Fills unset elements of Order (marked with the sentinel value equal to the order size) with the corre...
bool allSameOpcode(ArrayRef< Value * > VL)
bool isSplat(ArrayRef< Value * > VL)
unsigned getNumElements(Type *Ty)
std::string shortBundleName(ArrayRef< Value * > VL, int Idx)
Print a short descriptor of the instruction bundle suitable for debug output.
bool isOnceUsedSeed(const Instruction *I)
Returns true if I forms a vectorizable bundle on its own and its single user does not tear the vector...
unsigned getPartNumElems(unsigned Size, unsigned NumParts)
Returns power-of-2 number of elements in a single register (part), given the total number of elements...
constexpr unsigned MaxBitPackAnalysisDepth
Deeper than the standard analysis recursion depth to keep the numeric bound precise through arithmeti...
bool isCommutableOperand(const Instruction *I, Value *ValWithUses, unsigned Op, bool IsCopyable)
Checks if the operand is commutative.
TargetTransformInfo::TargetCostKind getSLPCostKind(const Function *F)
bool isReverseOrder(ArrayRef< unsigned > Order)
Check if Order represents reverse order.
Type * getCommonGEPIndexType(ArrayRef< Value * > VL, Instruction *VL0, function_ref< bool(Value *)> IsGEPLane, const DataLayout &DL)
Returns the common type for the indices of the single-index GEP lanes of a GEP node with the main op ...
void transformScalarShuffleIndiciesToVector(unsigned VecTyNumElements, SmallVectorImpl< int > &Mask)
SmallVector< int > calculateShufflevectorMask(ArrayRef< Value * > VL)
SmallBitVector buildUseMask(int VF, ArrayRef< int > Mask, UseMask MaskArg)
Prepares a use bitset for the given mask either for the first argument or for the second.
bool isCommutative(const Instruction *I, const Value *ValWithUses, bool IsCopyable)
template SmallBitVector isUndefVector< false >(const Value *, const SmallBitVector &)
unsigned getNumberOfPotentiallyCommutativeOps(Instruction *I)
bool allConstant(ArrayRef< Value * > VL)
template std::optional< unsigned > getInsertExtractIndex< InsertElementInst >(const Value *, unsigned)
void inversePermutation(ArrayRef< unsigned > Indices, SmallVectorImpl< int > &Mask)
Compute the inverse permutation Mask of Indices.
bool allSameBlock(ArrayRef< Value * > VL)
bool isReassocChainLink(const Instruction *I)
Intrinsic::ID isEquivalentIntrinsicID(Intrinsic::ID LHS, Intrinsic::ID RHS)
Checks if LHS and RHS are the same intrinsic, or one is llvm.fma and the other is llvm....
UseMask
Specifies the way the mask should be analyzed for undefs/poisonous elements in the shuffle mask.
@ SecondArg
The mask is expected to be for permutation of 2 vectors, check for the mask elements for the second a...
@ UndefsAsMask
Consider undef mask elements (-1) as placeholders for future shuffle elements and mark them as ones a...
@ FirstArg
The mask is expected to be for permutation of 1-2 vectors, check for the mask elements for the first ...
void reorderOrder(SmallVectorImpl< unsigned > &Order, ArrayRef< int > Mask, bool BottomOrder)
Reorders the given Order according to the given Mask.
static void collectNarrowedLeavesImpl(Value *V, unsigned RdxOpcode, unsigned WideBW, NarrowedChainState S, unsigned Depth, unsigned MaxDepth, SmallVectorImpl< NarrowedLeafInfo > &Leaves, SmallVectorImpl< Instruction * > &ChainInsts)
void reorderReuses(SmallVectorImpl< int > &Reuses, ArrayRef< int > Mask)
Reorders the given Reuses mask according to the given Mask.
void addMask(SmallVectorImpl< int > &Mask, ArrayRef< int > SubMask, bool ExtendingManyInputs)
Shuffles Mask in accordance with the given SubMask.
bool isSimple(Instruction *I)
Instruction * lookThroughCastRoundTrip(Value *V, bool MustBeElidable)
If V is a single-use fpext of a single-use fptrunc forming a round-trip back to the type of V,...
bool isBinOpIdentityConstant(const Value *V, unsigned Opcode)
APInt getScalarMaxValue(const Value *V, unsigned Depth)
Returns a saturating unsigned upper bound of the scalar V.
unsigned getShufflevectorNumGroups(ArrayRef< Value * > VL)
std::optional< TargetTransformInfo::ShuffleKind > isFixedVectorShuffle(ArrayRef< Value * > VL, SmallVectorImpl< int > &Mask, AssumptionCache *AC)
Checks if the vector of instructions can be represented as a shuffle, like: x0 = extractelement <4 x ...
SmallVector< Constant * > replicateMask(ArrayRef< Constant * > Val, unsigned VF)
Replicates the given Val VF times.
unsigned getReassocCombineOpcode(unsigned Opcode)
bool isVectorLikeInstWithConstOps(Value *V)
Checks if V is one of vector-like instructions, i.e.
bool doesNotNeedToBeScheduled(Value *V)
Checks if the specified value does not require scheduling.
unsigned getNumElems(unsigned Size, unsigned PartNumElems, unsigned Part)
Returns correct remaining number of elements, considering total amount Size, (power-of-2 number) of e...
constexpr int UsesLimit
Limit of the number of uses for potentially transformed instructions/values, used in checks to avoid ...
void collectNarrowedLeaves(Value *V, unsigned RdxOpcode, unsigned WideBW, unsigned MaxDepth, SmallVectorImpl< NarrowedLeafInfo > &Leaves, SmallVectorImpl< Instruction * > &ChainInsts)
Recursively collects the narrow leaves of the widened reduction value V.
bool isRepeatedNonIdentityClusteredMask(ArrayRef< int > Mask, unsigned Sz)
Checks if the given mask is a "clustered" mask with the same clusters of size Sz, which are not ident...
bool isConstant(Value *V)
static bool isNonProfitableIndex(const Instruction *I)
Returns true if I is a part of a single-use chain, computing an address, which does not pay off the v...
Value * createExtractVector(IRBuilderBase &Builder, Value *Vec, unsigned SubVecVF, unsigned Index)
Generates subvector extract.
template std::optional< unsigned > getInsertExtractIndex< ExtractElementInst >(const Value *, unsigned)
void fixupOrderingIndices(MutableArrayRef< unsigned > Order)
Order may have elements assigned special value (size) which is out of bounds.
This is an optimization pass for GlobalISel generic memory operations.
constexpr auto not_equal_to(T &&Arg)
Functor variant of std::not_equal_to that can be used as a UnaryPredicate in functional algorithms li...
bool all_of(R &&range, UnaryPredicate P)
Provide wrappers to std::all_of which take ranges instead of having to pass begin/end explicitly.
LLVM_ABI Intrinsic::ID getVectorIntrinsicIDForCall(const CallInst *CI, const TargetLibraryInfo *TLI)
Returns intrinsic ID for call.
@ Unknown
Not known to have no common set bits.
auto enumerate(FirstRange &&First, RestRanges &&...Rest)
Given two or more input ranges, returns a new range whose values are tuples (A, B,...
decltype(auto) dyn_cast(const From &Val)
dyn_cast<X> - Return the argument parameter cast to the specified type.
auto accumulate(R &&Range, E &&Init)
Wrapper for std::accumulate.
constexpr from_range_t from_range
iterator_range< T > make_range(T x, T y)
Convenience function for iterating over sub-ranges.
bool isVectorizedTy(Type *Ty)
Returns true if Ty is a vector type or a struct of vector types where all vector types share the same...
T bit_ceil(T Value)
Returns the smallest integral power of two no smaller than Value if Value is nonzero.
auto make_isa_range(RangeT &&Range)
Return a range over Range containing only elements for which isa<T> holds, casting each of them to T.
bool any_of(R &&range, UnaryPredicate P)
Provide wrappers to std::any_of which take ranges instead of having to pass begin/end explicitly.
constexpr unsigned MaxAnalysisRecursionDepth
ElementCount getVectorizedTypeVF(Type *Ty)
Returns the number of vector elements for a vectorized type.
auto find_if_not(R &&Range, UnaryPredicate P)
bool none_of(R &&Range, UnaryPredicate P)
Provide wrappers to std::none_of which take ranges instead of having to pass begin/end explicitly.
iterator_range< filter_iterator< detail::IterOfRange< RangeT >, PredicateT > > make_filter_range(RangeT &&Range, PredicateT Pred)
Convenience function that takes a range of elements and a predicate, and return a new filter_iterator...
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...
MutableArrayRef(T &OneElt) -> MutableArrayRef< T >
constexpr int PoisonMaskElem
iterator_range(Container &&) -> iterator_range< llvm::detail::IterOfRange< Container > >
constexpr T divideCeil(U Numerator, V Denominator)
Returns the integer ceil(Numerator / Denominator).
@ First
Helpers to iterate all locations in the MemoryEffectsBase class.
DWARFExpression::Operation Op
constexpr unsigned BitWidth
decltype(auto) cast(const From &Val)
cast<X> - Return the argument parameter cast to the specified type.
auto find_if(R &&Range, UnaryPredicate P)
Provide wrappers to std::find_if which take ranges instead of having to pass begin/end explicitly.
constexpr auto seq(T Begin, T End)
Iterate over an integral type from Begin up to - but not including - End.
bool is_contained(R &&Range, const E &Element)
Returns true if Element is found in Range.
LLVM_ABI bool isGuaranteedNotToBePoison(const Value *V, AssumptionCache *AC=nullptr, const Instruction *CtxI=nullptr, const DominatorTree *DT=nullptr, unsigned Depth=0)
Returns true if V cannot be poison, but may be undef.
LLVM_ABI bool mayHaveNonDefUseDependency(const Instruction &I)
Returns true if the result or effects of the given instructions I depend values not reachable through...
constexpr detail::IsaCheckPredicate< Types... > IsaPred
Function object wrapper for the llvm::isa type check.
Description of a bitfield packing of vector lanes into a scalar value: every lane contributes a disjo...
static constexpr unsigned NoLane
SmallVector< uint64_t, 8 > LShrAmts
Per-lane right-shift amounts bringing the field content to the low bits.