@@ -1886,6 +1886,23 @@ DEFINE_TRANSPARENT_OPERAND_ACCESSORS(InsertElementInst, Value)
1886
1886
// ShuffleVectorInst Class
1887
1887
// ===----------------------------------------------------------------------===//
1888
1888
1889
+ struct ShuffleMaskAttrs {
1890
+ bool SingleSource : 1 ;
1891
+ bool Identity : 1 ;
1892
+ // bool IdentityWithPadding : 1;
1893
+ // bool IdentityWithExtract : 1;
1894
+ // bool Concat : 1;
1895
+ bool Reverse : 1 ;
1896
+ bool ZeroEltSplat : 1 ;
1897
+ bool Select : 1 ;
1898
+ bool Transpose : 1 ;
1899
+ bool Splice : 1 ;
1900
+ int SpliceIndex;
1901
+ };
1902
+
1903
+ static_assert (sizeof (ShuffleMaskAttrs) <= sizeof(uint64_t ),
1904
+ "ShuffleMaskAttrs is too large!");
1905
+
1889
1906
constexpr int PoisonMaskElem = -1 ;
1890
1907
1891
1908
// / This instruction constructs a fixed permutation of two
@@ -1903,6 +1920,27 @@ class ShuffleVectorInst : public Instruction {
1903
1920
1904
1921
SmallVector<int , 4 > ShuffleMask;
1905
1922
Constant *ShuffleMaskForBitcode;
1923
+ mutable ShuffleMaskAttrs ShuffleAttrs;
1924
+
1925
+ // This function is const so that it's callable from other const functions.
1926
+ void computeShuffleAttrs () const {
1927
+ ShuffleAttrs = {}; // reset
1928
+ ShuffleAttrs.SingleSource =
1929
+ !changesLength () && isSingleSourceMask (ShuffleMask, ShuffleMask.size ());
1930
+ ShuffleAttrs.Identity =
1931
+ !changesLength () && isIdentityMask (ShuffleMask, ShuffleMask.size ());
1932
+ ShuffleAttrs.Select =
1933
+ !changesLength () && isSelectMask (ShuffleMask, ShuffleMask.size ());
1934
+ ShuffleAttrs.Reverse =
1935
+ !changesLength () && isReverseMask (ShuffleMask, ShuffleMask.size ());
1936
+ ShuffleAttrs.ZeroEltSplat =
1937
+ !changesLength () && isZeroEltSplatMask (ShuffleMask, ShuffleMask.size ());
1938
+ ShuffleAttrs.Transpose =
1939
+ !changesLength () && isTransposeMask (ShuffleMask, ShuffleMask.size ());
1940
+ ShuffleAttrs.Splice =
1941
+ !changesLength () &&
1942
+ isSpliceMask (ShuffleMask, ShuffleMask.size (), ShuffleAttrs.SpliceIndex );
1943
+ }
1906
1944
1907
1945
protected:
1908
1946
// Note: Instruction needs to be a friend here to call cloneImpl.
@@ -2013,10 +2051,7 @@ class ShuffleVectorInst : public Instruction {
2013
2051
// / vector without changing the length of that vector.
2014
2052
// / Example: shufflevector <4 x n> A, <4 x n> B, <3,0,undef,3>
2015
2053
// / TODO: Optionally allow length-changing shuffles.
2016
- bool isSingleSource () const {
2017
- return !changesLength () &&
2018
- isSingleSourceMask (ShuffleMask, ShuffleMask.size ());
2019
- }
2054
+ bool isSingleSource () const { return ShuffleAttrs.SingleSource ; }
2020
2055
2021
2056
// / Return true if this shuffle mask chooses elements from exactly one source
2022
2057
// / vector without lane crossings. A shuffle using this mask is not
@@ -2047,7 +2082,7 @@ class ShuffleVectorInst : public Instruction {
2047
2082
if (isa<ScalableVectorType>(getType ()))
2048
2083
return false ;
2049
2084
2050
- return ! changesLength () && isIdentityMask (ShuffleMask, ShuffleMask. size ()) ;
2085
+ return ShuffleAttrs. Identity ;
2051
2086
}
2052
2087
2053
2088
// / Return true if this shuffle lengthens exactly one source vector with
@@ -2087,9 +2122,7 @@ class ShuffleVectorInst : public Instruction {
2087
2122
// / This returns false if the mask does not choose from both input vectors.
2088
2123
// / In that case, the shuffle is better classified as an identity shuffle.
2089
2124
// / TODO: Optionally allow length-changing shuffles.
2090
- bool isSelect () const {
2091
- return !changesLength () && isSelectMask (ShuffleMask, ShuffleMask.size ());
2092
- }
2125
+ bool isSelect () const { return ShuffleAttrs.Select ; }
2093
2126
2094
2127
// / Return true if this shuffle mask swaps the order of elements from exactly
2095
2128
// / one source vector.
@@ -2108,9 +2141,7 @@ class ShuffleVectorInst : public Instruction {
2108
2141
// / one source vector.
2109
2142
// / Example: shufflevector <4 x n> A, <4 x n> B, <3,undef,1,undef>
2110
2143
// / TODO: Optionally allow length-changing shuffles.
2111
- bool isReverse () const {
2112
- return !changesLength () && isReverseMask (ShuffleMask, ShuffleMask.size ());
2113
- }
2144
+ bool isReverse () const { return ShuffleAttrs.Reverse ; }
2114
2145
2115
2146
// / Return true if this shuffle mask chooses all elements with the same value
2116
2147
// / as the first element of exactly one source vector.
@@ -2131,10 +2162,7 @@ class ShuffleVectorInst : public Instruction {
2131
2162
// / Example: shufflevector <4 x n> A, <4 x n> B, <undef,0,undef,0>
2132
2163
// / TODO: Optionally allow length-changing shuffles.
2133
2164
// / TODO: Optionally allow splats from other elements.
2134
- bool isZeroEltSplat () const {
2135
- return !changesLength () &&
2136
- isZeroEltSplatMask (ShuffleMask, ShuffleMask.size ());
2137
- }
2165
+ bool isZeroEltSplat () const { return ShuffleAttrs.ZeroEltSplat ; }
2138
2166
2139
2167
// / Return true if this shuffle mask is a transpose mask.
2140
2168
// / Transpose vector masks transpose a 2xn matrix. They read corresponding
@@ -2181,9 +2209,7 @@ class ShuffleVectorInst : public Instruction {
2181
2209
// / merge or interleave. See the description for isTransposeMask() for the
2182
2210
// / exact specification.
2183
2211
// / Example: shufflevector <4 x n> A, <4 x n> B, <0,4,2,6>
2184
- bool isTranspose () const {
2185
- return !changesLength () && isTransposeMask (ShuffleMask, ShuffleMask.size ());
2186
- }
2212
+ bool isTranspose () const { return ShuffleAttrs.Transpose ; }
2187
2213
2188
2214
// / Return true if this shuffle mask is a splice mask, concatenating the two
2189
2215
// / inputs together and then extracts an original width vector starting from
@@ -2204,8 +2230,9 @@ class ShuffleVectorInst : public Instruction {
2204
2230
// / then extracts an original width vector starting from the splice index.
2205
2231
// / Example: shufflevector <4 x n> A, <4 x n> B, <1,2,3,4>
2206
2232
bool isSplice (int &Index) const {
2207
- return !changesLength () &&
2208
- isSpliceMask (ShuffleMask, ShuffleMask.size (), Index);
2233
+ if (ShuffleAttrs.Splice )
2234
+ Index = ShuffleAttrs.SpliceIndex ;
2235
+ return ShuffleAttrs.Splice ;
2209
2236
}
2210
2237
2211
2238
// / Return true if this shuffle mask is an extract subvector mask.
0 commit comments