summaryrefslogtreecommitdiffstats
path: root/llvm/lib
diff options
context:
space:
mode:
authorChandler Carruth <chandlerc@gmail.com>2014-10-03 12:01:55 +0000
committerChandler Carruth <chandlerc@gmail.com>2014-10-03 12:01:55 +0000
commit4bf341de3c0fa43b117cccd40b4273218ed43883 (patch)
treecfe952ad70ec672ecc76e6b600bde197e432c043 /llvm/lib
parent39ddb3e54741d340b0c6b26023f03cc834fd9f18 (diff)
downloadbcm5719-llvm-4bf341de3c0fa43b117cccd40b4273218ed43883.tar.gz
bcm5719-llvm-4bf341de3c0fa43b117cccd40b4273218ed43883.zip
[x86] Refactor the element insertion logic in the new vector shuffle
lowering to handle the potential mirroring of 2-element vectors (because we can't reliably sort them one way) in the caller rather than in the insertion logic. This will simplify things considerably as more ways to fail to match the insertion are added because now we have a nice try and retry point. llvm-svn: 218980
Diffstat (limited to 'llvm/lib')
-rw-r--r--llvm/lib/Target/X86/X86ISelLowering.cpp40
1 files changed, 21 insertions, 19 deletions
diff --git a/llvm/lib/Target/X86/X86ISelLowering.cpp b/llvm/lib/Target/X86/X86ISelLowering.cpp
index fdced3555fb..702e163b46a 100644
--- a/llvm/lib/Target/X86/X86ISelLowering.cpp
+++ b/llvm/lib/Target/X86/X86ISelLowering.cpp
@@ -7783,23 +7783,9 @@ static SDValue lowerVectorShuffleAsElementInsertion(
int V2Index = std::find_if(Mask.begin(), Mask.end(),
[&Mask](int M) { return M >= (int)Mask.size(); }) -
Mask.begin();
- if (Mask.size() == 2) {
- if (!Zeroable[V2Index ^ 1]) {
- // For 2-wide masks we may be able to just invert the inputs. We use an xor
- // with 2 to flip from {2,3} to {0,1} and vice versa.
- int InverseMask[2] = {Mask[0] < 0 ? -1 : (Mask[0] ^ 2),
- Mask[1] < 0 ? -1 : (Mask[1] ^ 2)};
- if (Zeroable[V2Index])
- return lowerVectorShuffleAsElementInsertion(VT, DL, V2, V1, InverseMask,
- Subtarget, DAG);
- else
- return SDValue();
- }
- } else {
- for (int i = 0, Size = Mask.size(); i < Size; ++i)
- if (i != V2Index && !Zeroable[i])
- return SDValue(); // Not inserting into a zero vector.
- }
+ for (int i = 0, Size = Mask.size(); i < Size; ++i)
+ if (i != V2Index && !Zeroable[i])
+ return SDValue(); // Not inserting into a zero vector.
MVT ExtVT = VT;
MVT EltVT = VT.getVectorElementType();
@@ -7940,10 +7926,18 @@ static SDValue lowerV2F64VectorShuffle(SDValue Op, SDValue V1, SDValue V2,
return DAG.getNode(X86ISD::UNPCKH, DL, MVT::v2f64, V1, V2);
// If we have a single input, insert that into V1 if we can do so cheaply.
- if ((Mask[0] >= 2) + (Mask[1] >= 2) == 1)
+ if ((Mask[0] >= 2) + (Mask[1] >= 2) == 1) {
if (SDValue Insertion = lowerVectorShuffleAsElementInsertion(
MVT::v2f64, DL, V1, V2, Mask, Subtarget, DAG))
return Insertion;
+ // Try inverting the insertion since for v2 masks it is easy to do and we
+ // can't reliably sort the mask one way or the other.
+ int InverseMask[2] = {Mask[0] < 0 ? -1 : (Mask[0] ^ 2),
+ Mask[1] < 0 ? -1 : (Mask[1] ^ 2)};
+ if (SDValue Insertion = lowerVectorShuffleAsElementInsertion(
+ MVT::v2f64, DL, V2, V1, InverseMask, Subtarget, DAG))
+ return Insertion;
+ }
// Try to use one of the special instruction patterns to handle two common
// blend patterns if a zero-blend above didn't work.
@@ -8004,10 +7998,18 @@ static SDValue lowerV2I64VectorShuffle(SDValue Op, SDValue V1, SDValue V2,
// If we have a single input from V2 insert that into V1 if we can do so
// cheaply.
- if ((Mask[0] >= 2) + (Mask[1] >= 2) == 1)
+ if ((Mask[0] >= 2) + (Mask[1] >= 2) == 1) {
if (SDValue Insertion = lowerVectorShuffleAsElementInsertion(
MVT::v2i64, DL, V1, V2, Mask, Subtarget, DAG))
return Insertion;
+ // Try inverting the insertion since for v2 masks it is easy to do and we
+ // can't reliably sort the mask one way or the other.
+ int InverseMask[2] = {Mask[0] < 0 ? -1 : (Mask[0] ^ 2),
+ Mask[1] < 0 ? -1 : (Mask[1] ^ 2)};
+ if (SDValue Insertion = lowerVectorShuffleAsElementInsertion(
+ MVT::v2i64, DL, V2, V1, InverseMask, Subtarget, DAG))
+ return Insertion;
+ }
// Use dedicated unpack instructions for masks that match their pattern.
if (isShuffleEquivalent(Mask, 0, 2))
OpenPOWER on IntegriCloud