diff options
author | Craig Topper <craig.topper@gmail.com> | 2012-02-06 07:17:51 +0000 |
---|---|---|
committer | Craig Topper <craig.topper@gmail.com> | 2012-02-06 07:17:51 +0000 |
commit | d156dc11f9acd83e3369c069d5006a0203be13d6 (patch) | |
tree | 77c950c1af8490a5e6a3139838cded3c391ad595 /lib/Target/X86/Utils | |
parent | 1230ad6e8cb7977527ac64dcf5005464d7d6c20b (diff) | |
download | external_llvm-d156dc11f9acd83e3369c069d5006a0203be13d6.zip external_llvm-d156dc11f9acd83e3369c069d5006a0203be13d6.tar.gz external_llvm-d156dc11f9acd83e3369c069d5006a0203be13d6.tar.bz2 |
Add shuffle decoding support for 256-bit pshufd. Merge vpermilp* and pshufd decoding.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@149859 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Target/X86/Utils')
-rw-r--r-- | lib/Target/X86/Utils/X86ShuffleDecode.cpp | 80 | ||||
-rw-r--r-- | lib/Target/X86/Utils/X86ShuffleDecode.h | 24 |
2 files changed, 41 insertions, 63 deletions
diff --git a/lib/Target/X86/Utils/X86ShuffleDecode.cpp b/lib/Target/X86/Utils/X86ShuffleDecode.cpp index e7631b6..f4b85ae 100644 --- a/lib/Target/X86/Utils/X86ShuffleDecode.cpp +++ b/lib/Target/X86/Utils/X86ShuffleDecode.cpp @@ -63,11 +63,23 @@ void DecodeMOVLHPSMask(unsigned NElts, ShuffleMask.push_back(NElts+i); } -void DecodePSHUFMask(unsigned NElts, unsigned Imm, +/// DecodePSHUFMask - This decodes the shuffle masks for pshufd, and vpermilp*. +/// VT indicates the type of the vector allowing it to handle different +/// datatypes and vector widths. +void DecodePSHUFMask(EVT VT, unsigned Imm, SmallVectorImpl<unsigned> &ShuffleMask) { - for (unsigned i = 0; i != NElts; ++i) { - ShuffleMask.push_back(Imm % NElts); - Imm /= NElts; + unsigned NumElts = VT.getVectorNumElements(); + + unsigned NumLanes = VT.getSizeInBits() / 128; + unsigned NumLaneElts = NumElts / NumLanes; + + int NewImm = Imm; + for (unsigned l = 0; l != NumElts; l += NumLaneElts) { + for (unsigned i = 0; i != NumLaneElts; ++i) { + ShuffleMask.push_back(NewImm % NumLaneElts + l); + NewImm /= NumLaneElts; + } + if (NumLaneElts == 4) NewImm = Imm; // reload imm } } @@ -95,6 +107,9 @@ void DecodePSHUFLWMask(unsigned Imm, ShuffleMask.push_back(7); } +/// DecodeSHUFPMask - This decodes the shuffle masks for shufp*. VT indicates +/// the type of the vector allowing it to handle different datatypes and vector +/// widths. void DecodeSHUFPMask(EVT VT, unsigned Imm, SmallVectorImpl<unsigned> &ShuffleMask) { unsigned NumElts = VT.getVectorNumElements(); @@ -103,22 +118,24 @@ void DecodeSHUFPMask(EVT VT, unsigned Imm, unsigned NumLaneElts = NumElts / NumLanes; int NewImm = Imm; - for (unsigned l = 0; l < NumLanes; ++l) { - unsigned LaneStart = l * NumLaneElts; + for (unsigned l = 0; l != NumElts; l += NumLaneElts) { // Part that reads from dest. for (unsigned i = 0; i != NumLaneElts/2; ++i) { - ShuffleMask.push_back(NewImm % NumLaneElts + LaneStart); + ShuffleMask.push_back(NewImm % NumLaneElts + l); NewImm /= NumLaneElts; } // Part that reads from src. for (unsigned i = 0; i != NumLaneElts/2; ++i) { - ShuffleMask.push_back(NewImm % NumLaneElts + NumElts + LaneStart); + ShuffleMask.push_back(NewImm % NumLaneElts + NumElts + l); NewImm /= NumLaneElts; } if (NumLaneElts == 4) NewImm = Imm; // reload imm } } +/// DecodeUNPCKHMask - This decodes the shuffle masks for unpckhps/unpckhpd +/// and punpckh*. VT indicates the type of the vector allowing it to handle +/// different datatypes and vector widths. void DecodeUNPCKHMask(EVT VT, SmallVectorImpl<unsigned> &ShuffleMask) { unsigned NumElts = VT.getVectorNumElements(); @@ -128,10 +145,8 @@ void DecodeUNPCKHMask(EVT VT, SmallVectorImpl<unsigned> &ShuffleMask) { if (NumLanes == 0 ) NumLanes = 1; // Handle MMX unsigned NumLaneElts = NumElts / NumLanes; - for (unsigned s = 0; s < NumLanes; ++s) { - unsigned Start = s * NumLaneElts + NumLaneElts/2; - unsigned End = s * NumLaneElts + NumLaneElts; - for (unsigned i = Start; i != End; ++i) { + for (unsigned l = 0; l != NumElts; l += NumLaneElts) { + for (unsigned i = l + NumLaneElts/2, e = l + NumLaneElts; i != e; ++i) { ShuffleMask.push_back(i); // Reads from dest/src1 ShuffleMask.push_back(i+NumElts); // Reads from src/src2 } @@ -139,8 +154,8 @@ void DecodeUNPCKHMask(EVT VT, SmallVectorImpl<unsigned> &ShuffleMask) { } /// DecodeUNPCKLMask - This decodes the shuffle masks for unpcklps/unpcklpd -/// etc. VT indicates the type of the vector allowing it to handle different -/// datatypes and vector widths. +/// and punpckl*. VT indicates the type of the vector allowing it to handle +/// different datatypes and vector widths. void DecodeUNPCKLMask(EVT VT, SmallVectorImpl<unsigned> &ShuffleMask) { unsigned NumElts = VT.getVectorNumElements(); @@ -150,38 +165,15 @@ void DecodeUNPCKLMask(EVT VT, SmallVectorImpl<unsigned> &ShuffleMask) { if (NumLanes == 0 ) NumLanes = 1; // Handle MMX unsigned NumLaneElts = NumElts / NumLanes; - for (unsigned s = 0; s < NumLanes; ++s) { - unsigned Start = s * NumLaneElts; - unsigned End = s * NumLaneElts + NumLaneElts/2; - for (unsigned i = Start; i != End; ++i) { + for (unsigned l = 0; l != NumElts; l += NumLaneElts) { + for (unsigned i = l, e = l + NumLaneElts/2; i != e; ++i) { ShuffleMask.push_back(i); // Reads from dest/src1 ShuffleMask.push_back(i+NumElts); // Reads from src/src2 } } } -// DecodeVPERMILPMask - Decodes VPERMILPS/ VPERMILPD permutes for any 128-bit -// 32-bit or 64-bit elements. For 256-bit vectors, it's considered as two 128 -// lanes. For VPERMILPS, referenced elements can't cross lanes and the mask of -// the first lane must be the same of the second. -void DecodeVPERMILPMask(EVT VT, unsigned Imm, - SmallVectorImpl<unsigned> &ShuffleMask) { - unsigned NumElts = VT.getVectorNumElements(); - - unsigned NumLanes = VT.getSizeInBits() / 128; - unsigned NumLaneElts = NumElts / NumLanes; - - for (unsigned l = 0; l != NumLanes; ++l) { - unsigned LaneStart = l*NumLaneElts; - for (unsigned i = 0; i != NumLaneElts; ++i) { - unsigned Idx = NumLaneElts == 4 ? (Imm >> (i*2)) & 0x3 - : (Imm >> (i+LaneStart)) & 0x1; - ShuffleMask.push_back(Idx+LaneStart); - } - } -} - -void DecodeVPERM2F128Mask(EVT VT, unsigned Imm, +void DecodeVPERM2X128Mask(EVT VT, unsigned Imm, SmallVectorImpl<unsigned> &ShuffleMask) { unsigned HalfSize = VT.getVectorNumElements()/2; unsigned FstHalfBegin = (Imm & 0x3) * HalfSize; @@ -193,12 +185,4 @@ void DecodeVPERM2F128Mask(EVT VT, unsigned Imm, ShuffleMask.push_back(i); } -void DecodeVPERM2F128Mask(unsigned Imm, - SmallVectorImpl<unsigned> &ShuffleMask) { - // VPERM2F128 is used by any 256-bit EVT, but X86InstComments only - // has information about the instruction and not the types. So for - // instruction comments purpose, assume the 256-bit vector is v4i64. - return DecodeVPERM2F128Mask(MVT::v4i64, Imm, ShuffleMask); -} - } // llvm namespace diff --git a/lib/Target/X86/Utils/X86ShuffleDecode.h b/lib/Target/X86/Utils/X86ShuffleDecode.h index 243728f..877c9bd 100644 --- a/lib/Target/X86/Utils/X86ShuffleDecode.h +++ b/lib/Target/X86/Utils/X86ShuffleDecode.h @@ -37,7 +37,7 @@ void DecodeMOVHLPSMask(unsigned NElts, void DecodeMOVLHPSMask(unsigned NElts, SmallVectorImpl<unsigned> &ShuffleMask); -void DecodePSHUFMask(unsigned NElts, unsigned Imm, +void DecodePSHUFMask(EVT VT, unsigned Imm, SmallVectorImpl<unsigned> &ShuffleMask); void DecodePSHUFHWMask(unsigned Imm, @@ -46,30 +46,24 @@ void DecodePSHUFHWMask(unsigned Imm, void DecodePSHUFLWMask(unsigned Imm, SmallVectorImpl<unsigned> &ShuffleMask); +/// DecodeSHUFPMask - This decodes the shuffle masks for shufp*. VT indicates +/// the type of the vector allowing it to handle different datatypes and vector +/// widths. void DecodeSHUFPMask(EVT VT, unsigned Imm, SmallVectorImpl<unsigned> &ShuffleMask); /// DecodeUNPCKHMask - This decodes the shuffle masks for unpckhps/unpckhpd -/// etc. VT indicates the type of the vector allowing it to handle different -/// datatypes and vector widths. +/// and punpckh*. VT indicates the type of the vector allowing it to handle +/// different datatypes and vector widths. void DecodeUNPCKHMask(EVT VT, SmallVectorImpl<unsigned> &ShuffleMask); /// DecodeUNPCKLMask - This decodes the shuffle masks for unpcklps/unpcklpd -/// etc. VT indicates the type of the vector allowing it to handle different -/// datatypes and vector widths. +/// and punpckl*. VT indicates the type of the vector allowing it to handle +/// different datatypes and vector widths. void DecodeUNPCKLMask(EVT VT, SmallVectorImpl<unsigned> &ShuffleMask); -// DecodeVPERMILPMask - Decodes VPERMILPS/ VPERMILPD permutes for any 128-bit -// 32-bit or 64-bit elements. For 256-bit vectors, it's considered as two 128 -// lanes. For VPERMILPS, referenced elements can't cross lanes and the mask of -// the first lane must be the same of the second. -void DecodeVPERMILPMask(EVT VT, unsigned Imm, - SmallVectorImpl<unsigned> &ShuffleMask); - -void DecodeVPERM2F128Mask(unsigned Imm, - SmallVectorImpl<unsigned> &ShuffleMask); -void DecodeVPERM2F128Mask(EVT VT, unsigned Imm, +void DecodeVPERM2X128Mask(EVT VT, unsigned Imm, SmallVectorImpl<unsigned> &ShuffleMask); } // llvm namespace |