[llvm] [X86] matchPMADDWD - add support for larger source types (PR #205391)
Simon Pilgrim via llvm-commits
llvm-commits at lists.llvm.org
Wed Jun 24 03:26:16 PDT 2026
https://github.com/RKSimon updated https://github.com/llvm/llvm-project/pull/205391
>From 2496a8a9970af018fedc0b92d60548deebb885f7 Mon Sep 17 00:00:00 2001
From: Simon Pilgrim <llvm-dev at redking.me.uk>
Date: Tue, 23 Jun 2026 18:35:46 +0100
Subject: [PATCH 1/2] [X86] matchPMADDWD - add support for larger source types
Handle cases where the source vector type came from a vXi32 type wider than 2 x the original vXi16 type
The matcher only bothers with the lower elements - it doesn't matter if we're extracting from a wider vector
Fixes a number of SSE/AVX512 targets that failed to legalize to recoverable vector widths
---
llvm/lib/Target/X86/X86ISelLowering.cpp | 24 ++--
llvm/test/CodeGen/X86/madd.ll | 160 ++++--------------------
2 files changed, 41 insertions(+), 143 deletions(-)
diff --git a/llvm/lib/Target/X86/X86ISelLowering.cpp b/llvm/lib/Target/X86/X86ISelLowering.cpp
index 291124bb485cb..492abbc0037a9 100644
--- a/llvm/lib/Target/X86/X86ISelLowering.cpp
+++ b/llvm/lib/Target/X86/X86ISelLowering.cpp
@@ -59617,12 +59617,12 @@ static SDValue matchPMADDWD(SelectionDAG &DAG, SDNode *N,
return SDValue();
if (!Mul) {
// First time an extract_elt's source vector is visited. Must be a MUL
- // with 2X number of vector elements than the BUILD_VECTOR.
+ // with at least 2X number of vector elements than the BUILD_VECTOR.
// Both extracts must be from same MUL.
Mul = Vec0L;
if ((Mul.getOpcode() != ISD::MUL && Mul.getOpcode() != ISD::SHL &&
Mul.getOpcode() != ISD::SIGN_EXTEND) ||
- Mul.getValueType().getVectorNumElements() != 2 * e)
+ Mul.getValueType().getVectorNumElements() < (2 * e))
return SDValue();
}
// Check that the extract is from the same MUL previously seen.
@@ -59632,6 +59632,7 @@ static SDValue matchPMADDWD(SelectionDAG &DAG, SDNode *N,
EVT TruncVT = EVT::getVectorVT(*DAG.getContext(), MVT::i16,
VT.getVectorNumElements() * 2);
+ EVT MulVT = TruncVT.changeVectorElementType(*DAG.getContext(), MVT::i32);
SDValue N0, N1;
if (Mul.getOpcode() == ISD::MUL) {
@@ -59641,15 +59642,17 @@ static SDValue matchPMADDWD(SelectionDAG &DAG, SDNode *N,
Mode == ShrinkMode::MULU16)
return SDValue();
- N0 = DAG.getNode(ISD::TRUNCATE, DL, TruncVT, Mul.getOperand(0));
- N1 = DAG.getNode(ISD::TRUNCATE, DL, TruncVT, Mul.getOperand(1));
+ N0 = DAG.getExtractSubvector(DL, MulVT, Mul.getOperand(0), 0);
+ N1 = DAG.getExtractSubvector(DL, MulVT, Mul.getOperand(1), 0);
+ N0 = DAG.getNode(ISD::TRUNCATE, DL, TruncVT, N0);
+ N1 = DAG.getNode(ISD::TRUNCATE, DL, TruncVT, N1);
} else if (Mul.getOpcode() == ISD::SHL) {
SDValue ShVal = Mul.getOperand(0);
if (ShVal.getOpcode() != ISD::SIGN_EXTEND)
return SDValue();
N0 = ShVal.getOperand(0);
- if (N0.getValueType() != TruncVT)
+ if (N0.getValueType().getScalarType() != MVT::i16)
return SDValue();
// A shift by more than 15 would overflow an i16.
@@ -59658,17 +59661,18 @@ static SDValue matchPMADDWD(SelectionDAG &DAG, SDNode *N,
}))
return SDValue();
+ N0 = DAG.getExtractSubvector(DL, TruncVT, N0, 0);
+ N1 = DAG.getExtractSubvector(DL, MulVT, Mul.getOperand(1), 0);
N1 = DAG.getNode(ISD::SHL, DL, TruncVT, DAG.getConstant(1, DL, TruncVT),
- DAG.getZExtOrTrunc(Mul.getOperand(1), DL, TruncVT));
+ DAG.getZExtOrTrunc(N1, DL, TruncVT));
} else {
assert(Mul.getOpcode() == ISD::SIGN_EXTEND);
- // Add a trivial multiplication with 1 so that we can make use of VPMADDWD.
- N0 = Mul.getOperand(0);
-
- if (N0.getValueType() != TruncVT)
+ if (Mul.getOperand(0).getValueType().getScalarType() != MVT::i16)
return SDValue();
+ // Add a trivial multiplication with 1 so that we can make use of VPMADDWD.
+ N0 = DAG.getExtractSubvector(DL, TruncVT, Mul.getOperand(0), 0);
N1 = DAG.getConstant(1, DL, TruncVT);
}
diff --git a/llvm/test/CodeGen/X86/madd.ll b/llvm/test/CodeGen/X86/madd.ll
index 056712cc5a66c..5e2bc2038f73c 100644
--- a/llvm/test/CodeGen/X86/madd.ll
+++ b/llvm/test/CodeGen/X86/madd.ll
@@ -2083,56 +2083,17 @@ define <4 x i32> @pmaddwd_8_swapped(<8 x i16> %A, <8 x i16> %B) {
ret <4 x i32> %ret
}
-; FIXME: SSE2 fails to match PMADDWD
define <4 x i32> @larger_mul(<16 x i16> %A, <16 x i16> %B) {
-; SSE2-LABEL: larger_mul:
-; SSE2: # %bb.0:
-; SSE2-NEXT: movdqa %xmm0, %xmm1
-; SSE2-NEXT: pmulhw %xmm2, %xmm1
-; SSE2-NEXT: pmullw %xmm2, %xmm0
-; SSE2-NEXT: movdqa %xmm0, %xmm2
-; SSE2-NEXT: punpckhwd {{.*#+}} xmm2 = xmm2[4],xmm1[4],xmm2[5],xmm1[5],xmm2[6],xmm1[6],xmm2[7],xmm1[7]
-; SSE2-NEXT: punpcklwd {{.*#+}} xmm0 = xmm0[0],xmm1[0],xmm0[1],xmm1[1],xmm0[2],xmm1[2],xmm0[3],xmm1[3]
-; SSE2-NEXT: movdqa %xmm0, %xmm1
-; SSE2-NEXT: shufps {{.*#+}} xmm1 = xmm1[0,2],xmm2[0,2]
-; SSE2-NEXT: shufps {{.*#+}} xmm0 = xmm0[1,3],xmm2[1,3]
-; SSE2-NEXT: paddd %xmm1, %xmm0
-; SSE2-NEXT: retq
-;
-; SSE42-LABEL: larger_mul:
-; SSE42: # %bb.0:
-; SSE42-NEXT: pxor %xmm1, %xmm1
-; SSE42-NEXT: pmovzxwd {{.*#+}} xmm3 = xmm2[0],zero,xmm2[1],zero,xmm2[2],zero,xmm2[3],zero
-; SSE42-NEXT: punpckhwd {{.*#+}} xmm2 = xmm2[4],xmm1[4],xmm2[5],xmm1[5],xmm2[6],xmm1[6],xmm2[7],xmm1[7]
-; SSE42-NEXT: pmovzxwd {{.*#+}} xmm1 = xmm0[0],zero,xmm0[1],zero,xmm0[2],zero,xmm0[3],zero
-; SSE42-NEXT: punpckhwd {{.*#+}} xmm0 = xmm0[4,4,5,5,6,6,7,7]
-; SSE42-NEXT: pmaddwd %xmm2, %xmm0
-; SSE42-NEXT: pmaddwd %xmm3, %xmm1
-; SSE42-NEXT: phaddd %xmm0, %xmm1
-; SSE42-NEXT: movdqa %xmm1, %xmm0
-; SSE42-NEXT: retq
-;
-; AVX1-LABEL: larger_mul:
-; AVX1: # %bb.0:
-; AVX1-NEXT: vpmaddwd %xmm1, %xmm0, %xmm0
-; AVX1-NEXT: vzeroupper
-; AVX1-NEXT: retq
-;
-; AVX2-LABEL: larger_mul:
-; AVX2: # %bb.0:
-; AVX2-NEXT: vpmaddwd %xmm1, %xmm0, %xmm0
-; AVX2-NEXT: vzeroupper
-; AVX2-NEXT: retq
+; SSE-LABEL: larger_mul:
+; SSE: # %bb.0:
+; SSE-NEXT: pmaddwd %xmm2, %xmm0
+; SSE-NEXT: retq
;
-; AVX512-LABEL: larger_mul:
-; AVX512: # %bb.0:
-; AVX512-NEXT: vpmovsxwd %ymm0, %zmm0
-; AVX512-NEXT: vpmovsxwd %ymm1, %zmm1
-; AVX512-NEXT: vpmulld %zmm1, %zmm0, %zmm0
-; AVX512-NEXT: vextracti128 $1, %ymm0, %xmm1
-; AVX512-NEXT: vphaddd %xmm1, %xmm0, %xmm0
-; AVX512-NEXT: vzeroupper
-; AVX512-NEXT: retq
+; AVX-LABEL: larger_mul:
+; AVX: # %bb.0:
+; AVX-NEXT: vpmaddwd %xmm1, %xmm0, %xmm0
+; AVX-NEXT: vzeroupper
+; AVX-NEXT: retq
%a = sext <16 x i16> %A to <16 x i32>
%b = sext <16 x i16> %B to <16 x i32>
%m = mul nsw <16 x i32> %a, %b
@@ -2142,48 +2103,17 @@ define <4 x i32> @larger_mul(<16 x i16> %A, <16 x i16> %B) {
ret <4 x i32> %ret
}
-; FIXME: SSE fails to match PMADDWD
define <4 x i32> @larger_sext(<16 x i16> %A) {
-; SSE2-LABEL: larger_sext:
-; SSE2: # %bb.0:
-; SSE2-NEXT: punpckhwd {{.*#+}} xmm1 = xmm1[4],xmm0[4],xmm1[5],xmm0[5],xmm1[6],xmm0[6],xmm1[7],xmm0[7]
-; SSE2-NEXT: psrad $16, %xmm1
-; SSE2-NEXT: punpcklwd {{.*#+}} xmm0 = xmm0[0,0,1,1,2,2,3,3]
-; SSE2-NEXT: psrad $16, %xmm0
-; SSE2-NEXT: movdqa %xmm0, %xmm2
-; SSE2-NEXT: shufps {{.*#+}} xmm2 = xmm2[0,2],xmm1[0,2]
-; SSE2-NEXT: shufps {{.*#+}} xmm0 = xmm0[1,3],xmm1[1,3]
-; SSE2-NEXT: paddd %xmm2, %xmm0
-; SSE2-NEXT: retq
-;
-; SSE42-LABEL: larger_sext:
-; SSE42: # %bb.0:
-; SSE42-NEXT: pmovsxwd %xmm0, %xmm1
-; SSE42-NEXT: pshufd {{.*#+}} xmm0 = xmm0[2,3,2,3]
-; SSE42-NEXT: pmovsxwd %xmm0, %xmm0
-; SSE42-NEXT: phaddd %xmm0, %xmm1
-; SSE42-NEXT: movdqa %xmm1, %xmm0
-; SSE42-NEXT: retq
-;
-; AVX1-LABEL: larger_sext:
-; AVX1: # %bb.0:
-; AVX1-NEXT: vpmaddwd {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 # [1,1,1,1,1,1,1,1]
-; AVX1-NEXT: vzeroupper
-; AVX1-NEXT: retq
-;
-; AVX2-LABEL: larger_sext:
-; AVX2: # %bb.0:
-; AVX2-NEXT: vpmaddwd {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 # [1,1,1,1,1,1,1,1]
-; AVX2-NEXT: vzeroupper
-; AVX2-NEXT: retq
+; SSE-LABEL: larger_sext:
+; SSE: # %bb.0:
+; SSE-NEXT: pmaddwd {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 # [1,1,1,1,1,1,1,1]
+; SSE-NEXT: retq
;
-; AVX512-LABEL: larger_sext:
-; AVX512: # %bb.0:
-; AVX512-NEXT: vpmovsxwd %ymm0, %zmm0
-; AVX512-NEXT: vextracti128 $1, %ymm0, %xmm1
-; AVX512-NEXT: vphaddd %xmm1, %xmm0, %xmm0
-; AVX512-NEXT: vzeroupper
-; AVX512-NEXT: retq
+; AVX-LABEL: larger_sext:
+; AVX: # %bb.0:
+; AVX-NEXT: vpmaddwd {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 # [1,1,1,1,1,1,1,1]
+; AVX-NEXT: vzeroupper
+; AVX-NEXT: retq
%a = sext <16 x i16> %A to <16 x i32>
%odd = shufflevector <16 x i32> %a, <16 x i32> undef, <4 x i32> <i32 0, i32 2, i32 4, i32 6>
%even = shufflevector <16 x i32> %a, <16 x i32> undef, <4 x i32> <i32 1, i32 3, i32 5, i32 7>
@@ -2191,53 +2121,17 @@ define <4 x i32> @larger_sext(<16 x i16> %A) {
ret <4 x i32> %ret
}
-; FIXME: SSE fails to match PMADDWD
define <4 x i32> @larger_shl(<16 x i16> %A) {
-; SSE2-LABEL: larger_shl:
-; SSE2: # %bb.0:
-; SSE2-NEXT: punpcklwd {{.*#+}} xmm1 = xmm1[0],xmm0[0],xmm1[1],xmm0[1],xmm1[2],xmm0[2],xmm1[3],xmm0[3]
-; SSE2-NEXT: psrad $16, %xmm1
-; SSE2-NEXT: punpckhwd {{.*#+}} xmm0 = xmm0[4,4,5,5,6,6,7,7]
-; SSE2-NEXT: psrad $16, %xmm0
-; SSE2-NEXT: pslld $7, %xmm0
-; SSE2-NEXT: pslld $7, %xmm1
-; SSE2-NEXT: movdqa %xmm1, %xmm2
-; SSE2-NEXT: shufps {{.*#+}} xmm2 = xmm2[0,2],xmm0[0,2]
-; SSE2-NEXT: shufps {{.*#+}} xmm1 = xmm1[1,3],xmm0[1,3]
-; SSE2-NEXT: paddd %xmm2, %xmm1
-; SSE2-NEXT: movdqa %xmm1, %xmm0
-; SSE2-NEXT: retq
-;
-; SSE42-LABEL: larger_shl:
-; SSE42: # %bb.0:
-; SSE42-NEXT: pshufd {{.*#+}} xmm1 = xmm0[2,3,2,3]
-; SSE42-NEXT: pmovsxwd %xmm1, %xmm1
-; SSE42-NEXT: pmovsxwd %xmm0, %xmm0
-; SSE42-NEXT: pslld $7, %xmm0
-; SSE42-NEXT: pslld $7, %xmm1
-; SSE42-NEXT: phaddd %xmm1, %xmm0
-; SSE42-NEXT: retq
-;
-; AVX1-LABEL: larger_shl:
-; AVX1: # %bb.0:
-; AVX1-NEXT: vpmaddwd {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 # [128,128,128,128,128,128,128,128]
-; AVX1-NEXT: vzeroupper
-; AVX1-NEXT: retq
-;
-; AVX2-LABEL: larger_shl:
-; AVX2: # %bb.0:
-; AVX2-NEXT: vpmaddwd {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 # [128,128,128,128,128,128,128,128]
-; AVX2-NEXT: vzeroupper
-; AVX2-NEXT: retq
+; SSE-LABEL: larger_shl:
+; SSE: # %bb.0:
+; SSE-NEXT: pmaddwd {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 # [128,128,128,128,128,128,128,128]
+; SSE-NEXT: retq
;
-; AVX512-LABEL: larger_shl:
-; AVX512: # %bb.0:
-; AVX512-NEXT: vpmovsxwd %xmm0, %ymm0
-; AVX512-NEXT: vpslld $7, %ymm0, %ymm0
-; AVX512-NEXT: vextracti128 $1, %ymm0, %xmm1
-; AVX512-NEXT: vphaddd %xmm1, %xmm0, %xmm0
-; AVX512-NEXT: vzeroupper
-; AVX512-NEXT: retq
+; AVX-LABEL: larger_shl:
+; AVX: # %bb.0:
+; AVX-NEXT: vpmaddwd {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 # [128,128,128,128,128,128,128,128]
+; AVX-NEXT: vzeroupper
+; AVX-NEXT: retq
%a = sext <16 x i16> %A to <16 x i32>
%shl = shl <16 x i32> %a, splat (i32 7)
%odd = shufflevector <16 x i32> %shl, <16 x i32> undef, <4 x i32> <i32 0, i32 2, i32 4, i32 6>
>From 49f4591a37c77a33e1fbff4e0882cff5984cbe73 Mon Sep 17 00:00:00 2001
From: Simon Pilgrim <llvm-dev at redking.me.uk>
Date: Wed, 24 Jun 2026 11:26:01 +0100
Subject: [PATCH 2/2] regenerate odd vector tests
---
llvm/test/CodeGen/X86/madd.ll | 68 ++++++++++++++---------------------
1 file changed, 26 insertions(+), 42 deletions(-)
diff --git a/llvm/test/CodeGen/X86/madd.ll b/llvm/test/CodeGen/X86/madd.ll
index 3c58e4aa30b39..2b208050553ad 100644
--- a/llvm/test/CodeGen/X86/madd.ll
+++ b/llvm/test/CodeGen/X86/madd.ll
@@ -3736,22 +3736,22 @@ define <5 x i32> @oddvector_mul(<16 x i16> %A, <16 x i16> %B) {
define <4 x i32> @oddvector_sext(<13 x i16> %A) {
; SSE2-LABEL: oddvector_sext:
; SSE2: # %bb.0:
-; SSE2-NEXT: pxor %xmm0, %xmm0
-; SSE2-NEXT: pxor %xmm1, %xmm1
-; SSE2-NEXT: pinsrw $1, %r8d, %xmm1
-; SSE2-NEXT: pinsrw $3, %r9d, %xmm1
-; SSE2-NEXT: pinsrw $5, {{[0-9]+}}(%rsp), %xmm1
-; SSE2-NEXT: pinsrw $7, {{[0-9]+}}(%rsp), %xmm1
-; SSE2-NEXT: psrad $16, %xmm1
-; SSE2-NEXT: pinsrw $1, %edi, %xmm0
-; SSE2-NEXT: pinsrw $3, %esi, %xmm0
-; SSE2-NEXT: pinsrw $5, %edx, %xmm0
-; SSE2-NEXT: pinsrw $7, %ecx, %xmm0
-; SSE2-NEXT: psrad $16, %xmm0
-; SSE2-NEXT: movdqa %xmm0, %xmm2
-; SSE2-NEXT: shufps {{.*#+}} xmm2 = xmm2[0,2],xmm1[0,2]
-; SSE2-NEXT: shufps {{.*#+}} xmm0 = xmm0[1,3],xmm1[1,3]
-; SSE2-NEXT: paddd %xmm2, %xmm0
+; SSE2-NEXT: movd {{.*#+}} xmm0 = mem[0],zero,zero,zero
+; SSE2-NEXT: movd {{.*#+}} xmm1 = mem[0],zero,zero,zero
+; SSE2-NEXT: punpcklwd {{.*#+}} xmm1 = xmm1[0],xmm0[0],xmm1[1],xmm0[1],xmm1[2],xmm0[2],xmm1[3],xmm0[3]
+; SSE2-NEXT: movd %r9d, %xmm0
+; SSE2-NEXT: movd %r8d, %xmm2
+; SSE2-NEXT: punpcklwd {{.*#+}} xmm2 = xmm2[0],xmm0[0],xmm2[1],xmm0[1],xmm2[2],xmm0[2],xmm2[3],xmm0[3]
+; SSE2-NEXT: punpckldq {{.*#+}} xmm2 = xmm2[0],xmm1[0],xmm2[1],xmm1[1]
+; SSE2-NEXT: movd %ecx, %xmm0
+; SSE2-NEXT: movd %edx, %xmm1
+; SSE2-NEXT: punpcklwd {{.*#+}} xmm1 = xmm1[0],xmm0[0],xmm1[1],xmm0[1],xmm1[2],xmm0[2],xmm1[3],xmm0[3]
+; SSE2-NEXT: movd %esi, %xmm3
+; SSE2-NEXT: movd %edi, %xmm0
+; SSE2-NEXT: punpcklwd {{.*#+}} xmm0 = xmm0[0],xmm3[0],xmm0[1],xmm3[1],xmm0[2],xmm3[2],xmm0[3],xmm3[3]
+; SSE2-NEXT: punpckldq {{.*#+}} xmm0 = xmm0[0],xmm1[0],xmm0[1],xmm1[1]
+; SSE2-NEXT: punpcklqdq {{.*#+}} xmm0 = xmm0[0],xmm2[0]
+; SSE2-NEXT: pmaddwd {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 # [1,1,1,1,1,1,1,1]
; SSE2-NEXT: retq
;
; SSE42-LABEL: oddvector_sext:
@@ -3760,34 +3760,18 @@ define <4 x i32> @oddvector_sext(<13 x i16> %A) {
; SSE42-NEXT: pinsrw $1, %esi, %xmm0
; SSE42-NEXT: pinsrw $2, %edx, %xmm0
; SSE42-NEXT: pinsrw $3, %ecx, %xmm0
-; SSE42-NEXT: movd %r8d, %xmm1
-; SSE42-NEXT: pinsrw $1, %r9d, %xmm1
-; SSE42-NEXT: pinsrw $2, {{[0-9]+}}(%rsp), %xmm1
-; SSE42-NEXT: pinsrw $3, {{[0-9]+}}(%rsp), %xmm1
-; SSE42-NEXT: pmovsxwd %xmm1, %xmm1
-; SSE42-NEXT: pmovsxwd %xmm0, %xmm0
-; SSE42-NEXT: phaddd %xmm1, %xmm0
+; SSE42-NEXT: pinsrw $4, %r8d, %xmm0
+; SSE42-NEXT: pinsrw $5, %r9d, %xmm0
+; SSE42-NEXT: pinsrw $6, {{[0-9]+}}(%rsp), %xmm0
+; SSE42-NEXT: pinsrw $7, {{[0-9]+}}(%rsp), %xmm0
+; SSE42-NEXT: pmaddwd {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 # [1,1,1,1,1,1,1,1]
; SSE42-NEXT: retq
;
-; AVX1-LABEL: oddvector_sext:
-; AVX1: # %bb.0:
-; AVX1-NEXT: vpmaddwd {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 # [1,1,1,1,1,1,1,1]
-; AVX1-NEXT: vzeroupper
-; AVX1-NEXT: retq
-;
-; AVX2-LABEL: oddvector_sext:
-; AVX2: # %bb.0:
-; AVX2-NEXT: vpmaddwd {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 # [1,1,1,1,1,1,1,1]
-; AVX2-NEXT: vzeroupper
-; AVX2-NEXT: retq
-;
-; AVX512-LABEL: oddvector_sext:
-; AVX512: # %bb.0:
-; AVX512-NEXT: vpmovsxwd %ymm0, %zmm0
-; AVX512-NEXT: vextracti128 $1, %ymm0, %xmm1
-; AVX512-NEXT: vphaddd %xmm1, %xmm0, %xmm0
-; AVX512-NEXT: vzeroupper
-; AVX512-NEXT: retq
+; AVX-LABEL: oddvector_sext:
+; AVX: # %bb.0:
+; AVX-NEXT: vpmaddwd {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0, %xmm0 # [1,1,1,1,1,1,1,1]
+; AVX-NEXT: vzeroupper
+; AVX-NEXT: retq
%a = sext <13 x i16> %A to <13 x i32>
%odd = shufflevector <13 x i32> %a, <13 x i32> undef, <4 x i32> <i32 0, i32 2, i32 4, i32 6>
%even = shufflevector <13 x i32> %a, <13 x i32> undef, <4 x i32> <i32 1, i32 3, i32 5, i32 7>
More information about the llvm-commits
mailing list