aboutsummaryrefslogtreecommitdiff
path: root/contrib/llvm-project/llvm/lib/Analysis/VectorUtils.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'contrib/llvm-project/llvm/lib/Analysis/VectorUtils.cpp')
-rw-r--r--contrib/llvm-project/llvm/lib/Analysis/VectorUtils.cpp67
1 files changed, 60 insertions, 7 deletions
diff --git a/contrib/llvm-project/llvm/lib/Analysis/VectorUtils.cpp b/contrib/llvm-project/llvm/lib/Analysis/VectorUtils.cpp
index bc20f33f174c..1e48d3e2fbca 100644
--- a/contrib/llvm-project/llvm/lib/Analysis/VectorUtils.cpp
+++ b/contrib/llvm-project/llvm/lib/Analysis/VectorUtils.cpp
@@ -398,7 +398,7 @@ bool llvm::isSplatValue(const Value *V, int Index, unsigned Depth) {
if (auto *Shuf = dyn_cast<ShuffleVectorInst>(V)) {
// FIXME: We can safely allow undefs here. If Index was specified, we will
// check that the mask elt is defined at the required index.
- if (!is_splat(Shuf->getShuffleMask()))
+ if (!all_equal(Shuf->getShuffleMask()))
return false;
// Match any index.
@@ -429,6 +429,43 @@ bool llvm::isSplatValue(const Value *V, int Index, unsigned Depth) {
return false;
}
+bool llvm::getShuffleDemandedElts(int SrcWidth, ArrayRef<int> Mask,
+ const APInt &DemandedElts, APInt &DemandedLHS,
+ APInt &DemandedRHS, bool AllowUndefElts) {
+ DemandedLHS = DemandedRHS = APInt::getZero(SrcWidth);
+
+ // Early out if we don't demand any elements.
+ if (DemandedElts.isZero())
+ return true;
+
+ // Simple case of a shuffle with zeroinitializer.
+ if (all_of(Mask, [](int Elt) { return Elt == 0; })) {
+ DemandedLHS.setBit(0);
+ return true;
+ }
+
+ for (unsigned I = 0, E = Mask.size(); I != E; ++I) {
+ int M = Mask[I];
+ assert((-1 <= M) && (M < (SrcWidth * 2)) &&
+ "Invalid shuffle mask constant");
+
+ if (!DemandedElts[I] || (AllowUndefElts && (M < 0)))
+ continue;
+
+ // For undef elements, we don't know anything about the common state of
+ // the shuffle result.
+ if (M < 0)
+ return false;
+
+ if (M < SrcWidth)
+ DemandedLHS.setBit(M);
+ else
+ DemandedRHS.setBit(M - SrcWidth);
+ }
+
+ return true;
+}
+
void llvm::narrowShuffleMaskElts(int Scale, ArrayRef<int> Mask,
SmallVectorImpl<int> &ScaledMask) {
assert(Scale > 0 && "Unexpected scaling factor");
@@ -478,7 +515,7 @@ bool llvm::widenShuffleMaskElts(int Scale, ArrayRef<int> Mask,
if (SliceFront < 0) {
// Negative values (undef or other "sentinel" values) must be equal across
// the entire slice.
- if (!is_splat(MaskSlice))
+ if (!all_equal(MaskSlice))
return false;
ScaledMask.push_back(SliceFront);
} else {
@@ -501,6 +538,20 @@ bool llvm::widenShuffleMaskElts(int Scale, ArrayRef<int> Mask,
return true;
}
+void llvm::getShuffleMaskWithWidestElts(ArrayRef<int> Mask,
+ SmallVectorImpl<int> &ScaledMask) {
+ std::array<SmallVector<int, 16>, 2> TmpMasks;
+ SmallVectorImpl<int> *Output = &TmpMasks[0], *Tmp = &TmpMasks[1];
+ ArrayRef<int> InputMask = Mask;
+ for (unsigned Scale = 2; Scale <= InputMask.size(); ++Scale) {
+ while (widenShuffleMaskElts(Scale, InputMask, *Output)) {
+ InputMask = *Output;
+ std::swap(Output, Tmp);
+ }
+ }
+ ScaledMask.assign(InputMask.begin(), InputMask.end());
+}
+
void llvm::processShuffleMasks(
ArrayRef<int> Mask, unsigned NumOfSrcRegs, unsigned NumOfDestRegs,
unsigned NumOfUsedRegs, function_ref<void()> NoInputAction,
@@ -1123,8 +1174,9 @@ void InterleavedAccessInfo::collectConstStrideAccesses(
// wrap around the address space we would do a memory access at nullptr
// even without the transformation. The wrapping checks are therefore
// deferred until after we've formed the interleaved groups.
- int64_t Stride = getPtrStride(PSE, ElementTy, Ptr, TheLoop, Strides,
- /*Assume=*/true, /*ShouldCheckWrap=*/false);
+ int64_t Stride =
+ getPtrStride(PSE, ElementTy, Ptr, TheLoop, Strides,
+ /*Assume=*/true, /*ShouldCheckWrap=*/false).value_or(0);
const SCEV *Scev = replaceSymbolicStrideSCEV(PSE, Strides, Ptr);
AccessStrideInfo[&I] = StrideDescriptor(Stride, Scev, Size,
@@ -1343,7 +1395,7 @@ void InterleavedAccessInfo::analyzeInterleaving(
Value *MemberPtr = getLoadStorePointerOperand(Member);
Type *AccessTy = getLoadStoreType(Member);
if (getPtrStride(PSE, AccessTy, MemberPtr, TheLoop, Strides,
- /*Assume=*/false, /*ShouldCheckWrap=*/true))
+ /*Assume=*/false, /*ShouldCheckWrap=*/true).value_or(0))
return false;
LLVM_DEBUG(dbgs() << "LV: Invalidate candidate interleaved group due to "
<< FirstOrLast
@@ -1505,9 +1557,10 @@ void VFABI::getVectorVariantNames(
for (const auto &S : SetVector<StringRef>(ListAttr.begin(), ListAttr.end())) {
#ifndef NDEBUG
LLVM_DEBUG(dbgs() << "VFABI: adding mapping '" << S << "'\n");
- Optional<VFInfo> Info = VFABI::tryDemangleForVFABI(S, *(CI.getModule()));
+ std::optional<VFInfo> Info =
+ VFABI::tryDemangleForVFABI(S, *(CI.getModule()));
assert(Info && "Invalid name for a VFABI variant.");
- assert(CI.getModule()->getFunction(Info.value().VectorName) &&
+ assert(CI.getModule()->getFunction(Info->VectorName) &&
"Vector function is missing.");
#endif
VariantMappings.push_back(std::string(S));