1; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
2; NOTE: Assertions have been autogenerated by update_llc_test_checks.py
3; RUN: llc < %s -mtriple=x86_64-unknown-unknown -mcpu=x86-64 -mattr=+avx | FileCheck %s --check-prefix=ALL --check-prefix=AVX --check-prefix=AVX1
4; RUN: llc < %s -mtriple=x86_64-unknown-unknown -mcpu=x86-64 -mattr=+avx2 | FileCheck %s --check-prefix=ALL --check-prefix=AVX --check-prefix=AVX2
5
6;
7; Unary shuffle indices from registers
8;
9
10define <4 x double> @var_shuffle_v4f64_v4f64_xxxx_i64(<4 x double> %x, i64 %i0, i64 %i1, i64 %i2, i64 %i3) nounwind {
11; ALL-LABEL: var_shuffle_v4f64_v4f64_xxxx_i64:
12; ALL:       # BB#0:
13; ALL-NEXT:    pushq %rbp
14; ALL-NEXT:    movq %rsp, %rbp
15; ALL-NEXT:    andq $-32, %rsp
16; ALL-NEXT:    subq $64, %rsp
17; ALL-NEXT:    andl $3, %esi
18; ALL-NEXT:    andl $3, %edi
19; ALL-NEXT:    andl $3, %ecx
20; ALL-NEXT:    andl $3, %edx
21; ALL-NEXT:    vmovaps %ymm0, (%rsp)
22; ALL-NEXT:    vmovsd {{.*#+}} xmm0 = mem[0],zero
23; ALL-NEXT:    vmovhpd {{.*#+}} xmm0 = xmm0[0],mem[0]
24; ALL-NEXT:    vmovsd {{.*#+}} xmm1 = mem[0],zero
25; ALL-NEXT:    vmovhpd {{.*#+}} xmm1 = xmm1[0],mem[0]
26; ALL-NEXT:    vinsertf128 $1, %xmm0, %ymm1, %ymm0
27; ALL-NEXT:    movq %rbp, %rsp
28; ALL-NEXT:    popq %rbp
29; ALL-NEXT:    retq
30  %x0 = extractelement <4 x double> %x, i64 %i0
31  %x1 = extractelement <4 x double> %x, i64 %i1
32  %x2 = extractelement <4 x double> %x, i64 %i2
33  %x3 = extractelement <4 x double> %x, i64 %i3
34  %r0 = insertelement <4 x double> undef, double %x0, i32 0
35  %r1 = insertelement <4 x double>   %r0, double %x1, i32 1
36  %r2 = insertelement <4 x double>   %r1, double %x2, i32 2
37  %r3 = insertelement <4 x double>   %r2, double %x3, i32 3
38  ret <4 x double> %r3
39}
40
41define <4 x double> @var_shuffle_v4f64_v4f64_uxx0_i64(<4 x double> %x, i64 %i0, i64 %i1, i64 %i2, i64 %i3) nounwind {
42; ALL-LABEL: var_shuffle_v4f64_v4f64_uxx0_i64:
43; ALL:       # BB#0:
44; ALL-NEXT:    pushq %rbp
45; ALL-NEXT:    movq %rsp, %rbp
46; ALL-NEXT:    andq $-32, %rsp
47; ALL-NEXT:    subq $64, %rsp
48; ALL-NEXT:    andl $3, %edx
49; ALL-NEXT:    andl $3, %esi
50; ALL-NEXT:    vmovaps %ymm0, (%rsp)
51; ALL-NEXT:    vmovsd {{.*#+}} xmm0 = mem[0],zero
52; ALL-NEXT:    vmovddup {{.*#+}} xmm0 = xmm0[0,0]
53; ALL-NEXT:    vmovsd {{.*#+}} xmm1 = mem[0],zero
54; ALL-NEXT:    vinsertf128 $1, %xmm1, %ymm0, %ymm0
55; ALL-NEXT:    movq %rbp, %rsp
56; ALL-NEXT:    popq %rbp
57; ALL-NEXT:    retq
58  %x0 = extractelement <4 x double> %x, i64 %i0
59  %x1 = extractelement <4 x double> %x, i64 %i1
60  %x2 = extractelement <4 x double> %x, i64 %i2
61  %x3 = extractelement <4 x double> %x, i64 %i3
62  %r0 = insertelement <4 x double> undef, double undef, i32 0
63  %r1 = insertelement <4 x double>   %r0, double   %x1, i32 1
64  %r2 = insertelement <4 x double>   %r1, double   %x2, i32 2
65  %r3 = insertelement <4 x double>   %r2, double   0.0, i32 3
66  ret <4 x double> %r3
67}
68
69define <4 x double> @var_shuffle_v4f64_v2f64_xxxx_i64(<2 x double> %x, i64 %i0, i64 %i1, i64 %i2, i64 %i3) nounwind {
70; ALL-LABEL: var_shuffle_v4f64_v2f64_xxxx_i64:
71; ALL:       # BB#0:
72; ALL-NEXT:    andl $1, %esi
73; ALL-NEXT:    andl $1, %edi
74; ALL-NEXT:    andl $1, %ecx
75; ALL-NEXT:    andl $1, %edx
76; ALL-NEXT:    vmovaps %xmm0, -{{[0-9]+}}(%rsp)
77; ALL-NEXT:    vmovsd {{.*#+}} xmm0 = mem[0],zero
78; ALL-NEXT:    vmovhpd {{.*#+}} xmm0 = xmm0[0],mem[0]
79; ALL-NEXT:    vmovsd {{.*#+}} xmm1 = mem[0],zero
80; ALL-NEXT:    vmovhpd {{.*#+}} xmm1 = xmm1[0],mem[0]
81; ALL-NEXT:    vinsertf128 $1, %xmm0, %ymm1, %ymm0
82; ALL-NEXT:    retq
83  %x0 = extractelement <2 x double> %x, i64 %i0
84  %x1 = extractelement <2 x double> %x, i64 %i1
85  %x2 = extractelement <2 x double> %x, i64 %i2
86  %x3 = extractelement <2 x double> %x, i64 %i3
87  %r0 = insertelement <4 x double> undef, double %x0, i32 0
88  %r1 = insertelement <4 x double>   %r0, double %x1, i32 1
89  %r2 = insertelement <4 x double>   %r1, double %x2, i32 2
90  %r3 = insertelement <4 x double>   %r2, double %x3, i32 3
91  ret <4 x double> %r3
92}
93
94define <4 x i64> @var_shuffle_v4i64_v4i64_xxxx_i64(<4 x i64> %x, i64 %i0, i64 %i1, i64 %i2, i64 %i3) nounwind {
95; AVX1-LABEL: var_shuffle_v4i64_v4i64_xxxx_i64:
96; AVX1:       # BB#0:
97; AVX1-NEXT:    pushq %rbp
98; AVX1-NEXT:    movq %rsp, %rbp
99; AVX1-NEXT:    andq $-32, %rsp
100; AVX1-NEXT:    subq $64, %rsp
101; AVX1-NEXT:    andl $3, %edi
102; AVX1-NEXT:    andl $3, %esi
103; AVX1-NEXT:    andl $3, %edx
104; AVX1-NEXT:    andl $3, %ecx
105; AVX1-NEXT:    vmovaps %ymm0, (%rsp)
106; AVX1-NEXT:    vmovq {{.*#+}} xmm0 = mem[0],zero
107; AVX1-NEXT:    vmovq {{.*#+}} xmm1 = mem[0],zero
108; AVX1-NEXT:    vpunpcklqdq {{.*#+}} xmm0 = xmm1[0],xmm0[0]
109; AVX1-NEXT:    vmovq {{.*#+}} xmm1 = mem[0],zero
110; AVX1-NEXT:    vmovq {{.*#+}} xmm2 = mem[0],zero
111; AVX1-NEXT:    vpunpcklqdq {{.*#+}} xmm1 = xmm2[0],xmm1[0]
112; AVX1-NEXT:    vinsertf128 $1, %xmm0, %ymm1, %ymm0
113; AVX1-NEXT:    movq %rbp, %rsp
114; AVX1-NEXT:    popq %rbp
115; AVX1-NEXT:    retq
116;
117; AVX2-LABEL: var_shuffle_v4i64_v4i64_xxxx_i64:
118; AVX2:       # BB#0:
119; AVX2-NEXT:    pushq %rbp
120; AVX2-NEXT:    movq %rsp, %rbp
121; AVX2-NEXT:    andq $-32, %rsp
122; AVX2-NEXT:    subq $64, %rsp
123; AVX2-NEXT:    andl $3, %edi
124; AVX2-NEXT:    andl $3, %esi
125; AVX2-NEXT:    andl $3, %edx
126; AVX2-NEXT:    andl $3, %ecx
127; AVX2-NEXT:    vmovaps %ymm0, (%rsp)
128; AVX2-NEXT:    vmovq {{.*#+}} xmm0 = mem[0],zero
129; AVX2-NEXT:    vmovq {{.*#+}} xmm1 = mem[0],zero
130; AVX2-NEXT:    vpunpcklqdq {{.*#+}} xmm0 = xmm1[0],xmm0[0]
131; AVX2-NEXT:    vmovq {{.*#+}} xmm1 = mem[0],zero
132; AVX2-NEXT:    vmovq {{.*#+}} xmm2 = mem[0],zero
133; AVX2-NEXT:    vpunpcklqdq {{.*#+}} xmm1 = xmm2[0],xmm1[0]
134; AVX2-NEXT:    vinserti128 $1, %xmm0, %ymm1, %ymm0
135; AVX2-NEXT:    movq %rbp, %rsp
136; AVX2-NEXT:    popq %rbp
137; AVX2-NEXT:    retq
138  %x0 = extractelement <4 x i64> %x, i64 %i0
139  %x1 = extractelement <4 x i64> %x, i64 %i1
140  %x2 = extractelement <4 x i64> %x, i64 %i2
141  %x3 = extractelement <4 x i64> %x, i64 %i3
142  %r0 = insertelement <4 x i64> undef, i64 %x0, i32 0
143  %r1 = insertelement <4 x i64>   %r0, i64 %x1, i32 1
144  %r2 = insertelement <4 x i64>   %r1, i64 %x2, i32 2
145  %r3 = insertelement <4 x i64>   %r2, i64 %x3, i32 3
146  ret <4 x i64> %r3
147}
148
149define <4 x i64> @var_shuffle_v4i64_v4i64_xx00_i64(<4 x i64> %x, i64 %i0, i64 %i1, i64 %i2, i64 %i3) nounwind {
150; AVX1-LABEL: var_shuffle_v4i64_v4i64_xx00_i64:
151; AVX1:       # BB#0:
152; AVX1-NEXT:    pushq %rbp
153; AVX1-NEXT:    movq %rsp, %rbp
154; AVX1-NEXT:    andq $-32, %rsp
155; AVX1-NEXT:    subq $64, %rsp
156; AVX1-NEXT:    andl $3, %edi
157; AVX1-NEXT:    andl $3, %esi
158; AVX1-NEXT:    vmovaps %ymm0, (%rsp)
159; AVX1-NEXT:    vmovq {{.*#+}} xmm0 = mem[0],zero
160; AVX1-NEXT:    vmovq {{.*#+}} xmm1 = mem[0],zero
161; AVX1-NEXT:    vpunpcklqdq {{.*#+}} xmm0 = xmm1[0],xmm0[0]
162; AVX1-NEXT:    vpxor %xmm1, %xmm1, %xmm1
163; AVX1-NEXT:    vinsertf128 $1, %xmm1, %ymm0, %ymm0
164; AVX1-NEXT:    movq %rbp, %rsp
165; AVX1-NEXT:    popq %rbp
166; AVX1-NEXT:    retq
167;
168; AVX2-LABEL: var_shuffle_v4i64_v4i64_xx00_i64:
169; AVX2:       # BB#0:
170; AVX2-NEXT:    pushq %rbp
171; AVX2-NEXT:    movq %rsp, %rbp
172; AVX2-NEXT:    andq $-32, %rsp
173; AVX2-NEXT:    subq $64, %rsp
174; AVX2-NEXT:    andl $3, %edi
175; AVX2-NEXT:    andl $3, %esi
176; AVX2-NEXT:    vmovaps %ymm0, (%rsp)
177; AVX2-NEXT:    vmovq {{.*#+}} xmm0 = mem[0],zero
178; AVX2-NEXT:    vmovq {{.*#+}} xmm1 = mem[0],zero
179; AVX2-NEXT:    vpunpcklqdq {{.*#+}} xmm0 = xmm1[0],xmm0[0]
180; AVX2-NEXT:    vpxor %xmm1, %xmm1, %xmm1
181; AVX2-NEXT:    vinserti128 $1, %xmm1, %ymm0, %ymm0
182; AVX2-NEXT:    movq %rbp, %rsp
183; AVX2-NEXT:    popq %rbp
184; AVX2-NEXT:    retq
185  %x0 = extractelement <4 x i64> %x, i64 %i0
186  %x1 = extractelement <4 x i64> %x, i64 %i1
187  %x2 = extractelement <4 x i64> %x, i64 %i2
188  %x3 = extractelement <4 x i64> %x, i64 %i3
189  %r0 = insertelement <4 x i64> undef, i64 %x0, i32 0
190  %r1 = insertelement <4 x i64>   %r0, i64 %x1, i32 1
191  %r2 = insertelement <4 x i64>   %r1, i64   0, i32 2
192  %r3 = insertelement <4 x i64>   %r2, i64   0, i32 3
193  ret <4 x i64> %r3
194}
195
196define <4 x i64> @var_shuffle_v4i64_v2i64_xxxx_i64(<2 x i64> %x, i64 %i0, i64 %i1, i64 %i2, i64 %i3) nounwind {
197; AVX1-LABEL: var_shuffle_v4i64_v2i64_xxxx_i64:
198; AVX1:       # BB#0:
199; AVX1-NEXT:    andl $1, %edi
200; AVX1-NEXT:    andl $1, %esi
201; AVX1-NEXT:    andl $1, %edx
202; AVX1-NEXT:    andl $1, %ecx
203; AVX1-NEXT:    vmovaps %xmm0, -{{[0-9]+}}(%rsp)
204; AVX1-NEXT:    vmovq {{.*#+}} xmm0 = mem[0],zero
205; AVX1-NEXT:    vmovq {{.*#+}} xmm1 = mem[0],zero
206; AVX1-NEXT:    vpunpcklqdq {{.*#+}} xmm0 = xmm1[0],xmm0[0]
207; AVX1-NEXT:    vmovq {{.*#+}} xmm1 = mem[0],zero
208; AVX1-NEXT:    vmovq {{.*#+}} xmm2 = mem[0],zero
209; AVX1-NEXT:    vpunpcklqdq {{.*#+}} xmm1 = xmm2[0],xmm1[0]
210; AVX1-NEXT:    vinsertf128 $1, %xmm0, %ymm1, %ymm0
211; AVX1-NEXT:    retq
212;
213; AVX2-LABEL: var_shuffle_v4i64_v2i64_xxxx_i64:
214; AVX2:       # BB#0:
215; AVX2-NEXT:    andl $1, %edi
216; AVX2-NEXT:    andl $1, %esi
217; AVX2-NEXT:    andl $1, %edx
218; AVX2-NEXT:    andl $1, %ecx
219; AVX2-NEXT:    vmovaps %xmm0, -{{[0-9]+}}(%rsp)
220; AVX2-NEXT:    vmovq {{.*#+}} xmm0 = mem[0],zero
221; AVX2-NEXT:    vmovq {{.*#+}} xmm1 = mem[0],zero
222; AVX2-NEXT:    vpunpcklqdq {{.*#+}} xmm0 = xmm1[0],xmm0[0]
223; AVX2-NEXT:    vmovq {{.*#+}} xmm1 = mem[0],zero
224; AVX2-NEXT:    vmovq {{.*#+}} xmm2 = mem[0],zero
225; AVX2-NEXT:    vpunpcklqdq {{.*#+}} xmm1 = xmm2[0],xmm1[0]
226; AVX2-NEXT:    vinserti128 $1, %xmm0, %ymm1, %ymm0
227; AVX2-NEXT:    retq
228  %x0 = extractelement <2 x i64> %x, i64 %i0
229  %x1 = extractelement <2 x i64> %x, i64 %i1
230  %x2 = extractelement <2 x i64> %x, i64 %i2
231  %x3 = extractelement <2 x i64> %x, i64 %i3
232  %r0 = insertelement <4 x i64> undef, i64 %x0, i32 0
233  %r1 = insertelement <4 x i64>   %r0, i64 %x1, i32 1
234  %r2 = insertelement <4 x i64>   %r1, i64 %x2, i32 2
235  %r3 = insertelement <4 x i64>   %r2, i64 %x3, i32 3
236  ret <4 x i64> %r3
237}
238
239define <8 x float> @var_shuffle_v8f32_v8f32_xxxxxxxx_i32(<8 x float> %x, i32 %i0, i32 %i1, i32 %i2, i32 %i3, i32 %i4, i32 %i5, i32 %i6, i32 %i7) nounwind {
240; ALL-LABEL: var_shuffle_v8f32_v8f32_xxxxxxxx_i32:
241; ALL:       # BB#0:
242; ALL-NEXT:    pushq %rbp
243; ALL-NEXT:    movq %rsp, %rbp
244; ALL-NEXT:    andq $-32, %rsp
245; ALL-NEXT:    subq $64, %rsp
246; ALL-NEXT:    # kill: %R9D<def> %R9D<kill> %R9<def>
247; ALL-NEXT:    # kill: %R8D<def> %R8D<kill> %R8<def>
248; ALL-NEXT:    # kill: %ECX<def> %ECX<kill> %RCX<def>
249; ALL-NEXT:    # kill: %EDX<def> %EDX<kill> %RDX<def>
250; ALL-NEXT:    # kill: %ESI<def> %ESI<kill> %RSI<def>
251; ALL-NEXT:    # kill: %EDI<def> %EDI<kill> %RDI<def>
252; ALL-NEXT:    andl $7, %edi
253; ALL-NEXT:    andl $7, %esi
254; ALL-NEXT:    andl $7, %edx
255; ALL-NEXT:    andl $7, %ecx
256; ALL-NEXT:    andl $7, %r8d
257; ALL-NEXT:    vmovaps %ymm0, (%rsp)
258; ALL-NEXT:    andl $7, %r9d
259; ALL-NEXT:    movl 16(%rbp), %r10d
260; ALL-NEXT:    andl $7, %r10d
261; ALL-NEXT:    movl 24(%rbp), %eax
262; ALL-NEXT:    andl $7, %eax
263; ALL-NEXT:    vmovss {{.*#+}} xmm0 = mem[0],zero,zero,zero
264; ALL-NEXT:    vinsertps {{.*#+}} xmm0 = xmm0[0],mem[0],xmm0[2,3]
265; ALL-NEXT:    vinsertps {{.*#+}} xmm0 = xmm0[0,1],mem[0],xmm0[3]
266; ALL-NEXT:    vinsertps {{.*#+}} xmm0 = xmm0[0,1,2],mem[0]
267; ALL-NEXT:    vmovss {{.*#+}} xmm1 = mem[0],zero,zero,zero
268; ALL-NEXT:    vinsertps {{.*#+}} xmm1 = xmm1[0],mem[0],xmm1[2,3]
269; ALL-NEXT:    vinsertps {{.*#+}} xmm1 = xmm1[0,1],mem[0],xmm1[3]
270; ALL-NEXT:    vinsertps {{.*#+}} xmm1 = xmm1[0,1,2],mem[0]
271; ALL-NEXT:    vinsertf128 $1, %xmm0, %ymm1, %ymm0
272; ALL-NEXT:    movq %rbp, %rsp
273; ALL-NEXT:    popq %rbp
274; ALL-NEXT:    retq
275  %x0 = extractelement <8 x float> %x, i32 %i0
276  %x1 = extractelement <8 x float> %x, i32 %i1
277  %x2 = extractelement <8 x float> %x, i32 %i2
278  %x3 = extractelement <8 x float> %x, i32 %i3
279  %x4 = extractelement <8 x float> %x, i32 %i4
280  %x5 = extractelement <8 x float> %x, i32 %i5
281  %x6 = extractelement <8 x float> %x, i32 %i6
282  %x7 = extractelement <8 x float> %x, i32 %i7
283  %r0 = insertelement <8 x float> undef, float %x0, i32 0
284  %r1 = insertelement <8 x float>   %r0, float %x1, i32 1
285  %r2 = insertelement <8 x float>   %r1, float %x2, i32 2
286  %r3 = insertelement <8 x float>   %r2, float %x3, i32 3
287  %r4 = insertelement <8 x float>   %r3, float %x4, i32 4
288  %r5 = insertelement <8 x float>   %r4, float %x5, i32 5
289  %r6 = insertelement <8 x float>   %r5, float %x6, i32 6
290  %r7 = insertelement <8 x float>   %r6, float %x7, i32 7
291  ret <8 x float> %r7
292}
293
294define <8 x float> @var_shuffle_v8f32_v4f32_xxxxxxxx_i32(<4 x float> %x, i32 %i0, i32 %i1, i32 %i2, i32 %i3, i32 %i4, i32 %i5, i32 %i6, i32 %i7) nounwind {
295; ALL-LABEL: var_shuffle_v8f32_v4f32_xxxxxxxx_i32:
296; ALL:       # BB#0:
297; ALL-NEXT:    # kill: %R9D<def> %R9D<kill> %R9<def>
298; ALL-NEXT:    # kill: %R8D<def> %R8D<kill> %R8<def>
299; ALL-NEXT:    # kill: %ECX<def> %ECX<kill> %RCX<def>
300; ALL-NEXT:    # kill: %EDX<def> %EDX<kill> %RDX<def>
301; ALL-NEXT:    # kill: %ESI<def> %ESI<kill> %RSI<def>
302; ALL-NEXT:    # kill: %EDI<def> %EDI<kill> %RDI<def>
303; ALL-NEXT:    andl $3, %edi
304; ALL-NEXT:    andl $3, %esi
305; ALL-NEXT:    andl $3, %edx
306; ALL-NEXT:    andl $3, %ecx
307; ALL-NEXT:    andl $3, %r8d
308; ALL-NEXT:    vmovaps %xmm0, -{{[0-9]+}}(%rsp)
309; ALL-NEXT:    andl $3, %r9d
310; ALL-NEXT:    movl {{[0-9]+}}(%rsp), %r10d
311; ALL-NEXT:    andl $3, %r10d
312; ALL-NEXT:    movl {{[0-9]+}}(%rsp), %eax
313; ALL-NEXT:    andl $3, %eax
314; ALL-NEXT:    vmovss {{.*#+}} xmm0 = mem[0],zero,zero,zero
315; ALL-NEXT:    vinsertps {{.*#+}} xmm0 = xmm0[0],mem[0],xmm0[2,3]
316; ALL-NEXT:    vinsertps {{.*#+}} xmm0 = xmm0[0,1],mem[0],xmm0[3]
317; ALL-NEXT:    vinsertps {{.*#+}} xmm0 = xmm0[0,1,2],mem[0]
318; ALL-NEXT:    vmovss {{.*#+}} xmm1 = mem[0],zero,zero,zero
319; ALL-NEXT:    vinsertps {{.*#+}} xmm1 = xmm1[0],mem[0],xmm1[2,3]
320; ALL-NEXT:    vinsertps {{.*#+}} xmm1 = xmm1[0,1],mem[0],xmm1[3]
321; ALL-NEXT:    vinsertps {{.*#+}} xmm1 = xmm1[0,1,2],mem[0]
322; ALL-NEXT:    vinsertf128 $1, %xmm0, %ymm1, %ymm0
323; ALL-NEXT:    retq
324  %x0 = extractelement <4 x float> %x, i32 %i0
325  %x1 = extractelement <4 x float> %x, i32 %i1
326  %x2 = extractelement <4 x float> %x, i32 %i2
327  %x3 = extractelement <4 x float> %x, i32 %i3
328  %x4 = extractelement <4 x float> %x, i32 %i4
329  %x5 = extractelement <4 x float> %x, i32 %i5
330  %x6 = extractelement <4 x float> %x, i32 %i6
331  %x7 = extractelement <4 x float> %x, i32 %i7
332  %r0 = insertelement <8 x float> undef, float %x0, i32 0
333  %r1 = insertelement <8 x float>   %r0, float %x1, i32 1
334  %r2 = insertelement <8 x float>   %r1, float %x2, i32 2
335  %r3 = insertelement <8 x float>   %r2, float %x3, i32 3
336  %r4 = insertelement <8 x float>   %r3, float %x4, i32 4
337  %r5 = insertelement <8 x float>   %r4, float %x5, i32 5
338  %r6 = insertelement <8 x float>   %r5, float %x6, i32 6
339  %r7 = insertelement <8 x float>   %r6, float %x7, i32 7
340  ret <8 x float> %r7
341}
342
343define <16 x i16> @var_shuffle_v16i16_v16i16_xxxxxxxxxxxxxxxx_i16(<16 x i16> %x, i32 %i0, i32 %i1, i32 %i2, i32 %i3, i32 %i4, i32 %i5, i32 %i6, i32 %i7, i32 %i8, i32 %i9, i32 %i10, i32 %i11, i32 %i12, i32 %i13, i32 %i14, i32 %i15) nounwind {
344; AVX1-LABEL: var_shuffle_v16i16_v16i16_xxxxxxxxxxxxxxxx_i16:
345; AVX1:       # BB#0:
346; AVX1-NEXT:    pushq %rbp
347; AVX1-NEXT:    movq %rsp, %rbp
348; AVX1-NEXT:    andq $-32, %rsp
349; AVX1-NEXT:    subq $64, %rsp
350; AVX1-NEXT:    # kill: %R9D<def> %R9D<kill> %R9<def>
351; AVX1-NEXT:    # kill: %R8D<def> %R8D<kill> %R8<def>
352; AVX1-NEXT:    # kill: %ECX<def> %ECX<kill> %RCX<def>
353; AVX1-NEXT:    # kill: %EDX<def> %EDX<kill> %RDX<def>
354; AVX1-NEXT:    # kill: %ESI<def> %ESI<kill> %RSI<def>
355; AVX1-NEXT:    # kill: %EDI<def> %EDI<kill> %RDI<def>
356; AVX1-NEXT:    vmovaps %ymm0, (%rsp)
357; AVX1-NEXT:    movl 32(%rbp), %eax
358; AVX1-NEXT:    andl $15, %eax
359; AVX1-NEXT:    movzwl (%rsp,%rax,2), %eax
360; AVX1-NEXT:    vmovd %eax, %xmm0
361; AVX1-NEXT:    movl 40(%rbp), %eax
362; AVX1-NEXT:    andl $15, %eax
363; AVX1-NEXT:    vpinsrw $1, (%rsp,%rax,2), %xmm0, %xmm0
364; AVX1-NEXT:    movl 48(%rbp), %eax
365; AVX1-NEXT:    andl $15, %eax
366; AVX1-NEXT:    vpinsrw $2, (%rsp,%rax,2), %xmm0, %xmm0
367; AVX1-NEXT:    movl 56(%rbp), %eax
368; AVX1-NEXT:    andl $15, %eax
369; AVX1-NEXT:    vpinsrw $3, (%rsp,%rax,2), %xmm0, %xmm0
370; AVX1-NEXT:    movl 64(%rbp), %eax
371; AVX1-NEXT:    andl $15, %eax
372; AVX1-NEXT:    vpinsrw $4, (%rsp,%rax,2), %xmm0, %xmm0
373; AVX1-NEXT:    movl 72(%rbp), %eax
374; AVX1-NEXT:    andl $15, %eax
375; AVX1-NEXT:    vpinsrw $5, (%rsp,%rax,2), %xmm0, %xmm0
376; AVX1-NEXT:    movl 80(%rbp), %eax
377; AVX1-NEXT:    andl $15, %eax
378; AVX1-NEXT:    vpinsrw $6, (%rsp,%rax,2), %xmm0, %xmm0
379; AVX1-NEXT:    movl 88(%rbp), %eax
380; AVX1-NEXT:    andl $15, %eax
381; AVX1-NEXT:    vpinsrw $7, (%rsp,%rax,2), %xmm0, %xmm0
382; AVX1-NEXT:    andl $15, %edi
383; AVX1-NEXT:    movzwl (%rsp,%rdi,2), %eax
384; AVX1-NEXT:    vmovd %eax, %xmm1
385; AVX1-NEXT:    andl $15, %esi
386; AVX1-NEXT:    vpinsrw $1, (%rsp,%rsi,2), %xmm1, %xmm1
387; AVX1-NEXT:    andl $15, %edx
388; AVX1-NEXT:    vpinsrw $2, (%rsp,%rdx,2), %xmm1, %xmm1
389; AVX1-NEXT:    andl $15, %ecx
390; AVX1-NEXT:    vpinsrw $3, (%rsp,%rcx,2), %xmm1, %xmm1
391; AVX1-NEXT:    andl $15, %r8d
392; AVX1-NEXT:    vpinsrw $4, (%rsp,%r8,2), %xmm1, %xmm1
393; AVX1-NEXT:    andl $15, %r9d
394; AVX1-NEXT:    vpinsrw $5, (%rsp,%r9,2), %xmm1, %xmm1
395; AVX1-NEXT:    movl 16(%rbp), %eax
396; AVX1-NEXT:    andl $15, %eax
397; AVX1-NEXT:    vpinsrw $6, (%rsp,%rax,2), %xmm1, %xmm1
398; AVX1-NEXT:    movl 24(%rbp), %eax
399; AVX1-NEXT:    andl $15, %eax
400; AVX1-NEXT:    vpinsrw $7, (%rsp,%rax,2), %xmm1, %xmm1
401; AVX1-NEXT:    vinsertf128 $1, %xmm0, %ymm1, %ymm0
402; AVX1-NEXT:    movq %rbp, %rsp
403; AVX1-NEXT:    popq %rbp
404; AVX1-NEXT:    retq
405;
406; AVX2-LABEL: var_shuffle_v16i16_v16i16_xxxxxxxxxxxxxxxx_i16:
407; AVX2:       # BB#0:
408; AVX2-NEXT:    pushq %rbp
409; AVX2-NEXT:    movq %rsp, %rbp
410; AVX2-NEXT:    andq $-32, %rsp
411; AVX2-NEXT:    subq $64, %rsp
412; AVX2-NEXT:    # kill: %R9D<def> %R9D<kill> %R9<def>
413; AVX2-NEXT:    # kill: %R8D<def> %R8D<kill> %R8<def>
414; AVX2-NEXT:    # kill: %ECX<def> %ECX<kill> %RCX<def>
415; AVX2-NEXT:    # kill: %EDX<def> %EDX<kill> %RDX<def>
416; AVX2-NEXT:    # kill: %ESI<def> %ESI<kill> %RSI<def>
417; AVX2-NEXT:    # kill: %EDI<def> %EDI<kill> %RDI<def>
418; AVX2-NEXT:    vmovaps %ymm0, (%rsp)
419; AVX2-NEXT:    movl 32(%rbp), %eax
420; AVX2-NEXT:    andl $15, %eax
421; AVX2-NEXT:    movzwl (%rsp,%rax,2), %eax
422; AVX2-NEXT:    vmovd %eax, %xmm0
423; AVX2-NEXT:    movl 40(%rbp), %eax
424; AVX2-NEXT:    andl $15, %eax
425; AVX2-NEXT:    vpinsrw $1, (%rsp,%rax,2), %xmm0, %xmm0
426; AVX2-NEXT:    movl 48(%rbp), %eax
427; AVX2-NEXT:    andl $15, %eax
428; AVX2-NEXT:    vpinsrw $2, (%rsp,%rax,2), %xmm0, %xmm0
429; AVX2-NEXT:    movl 56(%rbp), %eax
430; AVX2-NEXT:    andl $15, %eax
431; AVX2-NEXT:    vpinsrw $3, (%rsp,%rax,2), %xmm0, %xmm0
432; AVX2-NEXT:    movl 64(%rbp), %eax
433; AVX2-NEXT:    andl $15, %eax
434; AVX2-NEXT:    vpinsrw $4, (%rsp,%rax,2), %xmm0, %xmm0
435; AVX2-NEXT:    movl 72(%rbp), %eax
436; AVX2-NEXT:    andl $15, %eax
437; AVX2-NEXT:    vpinsrw $5, (%rsp,%rax,2), %xmm0, %xmm0
438; AVX2-NEXT:    movl 80(%rbp), %eax
439; AVX2-NEXT:    andl $15, %eax
440; AVX2-NEXT:    vpinsrw $6, (%rsp,%rax,2), %xmm0, %xmm0
441; AVX2-NEXT:    movl 88(%rbp), %eax
442; AVX2-NEXT:    andl $15, %eax
443; AVX2-NEXT:    vpinsrw $7, (%rsp,%rax,2), %xmm0, %xmm0
444; AVX2-NEXT:    andl $15, %edi
445; AVX2-NEXT:    movzwl (%rsp,%rdi,2), %eax
446; AVX2-NEXT:    vmovd %eax, %xmm1
447; AVX2-NEXT:    andl $15, %esi
448; AVX2-NEXT:    vpinsrw $1, (%rsp,%rsi,2), %xmm1, %xmm1
449; AVX2-NEXT:    andl $15, %edx
450; AVX2-NEXT:    vpinsrw $2, (%rsp,%rdx,2), %xmm1, %xmm1
451; AVX2-NEXT:    andl $15, %ecx
452; AVX2-NEXT:    vpinsrw $3, (%rsp,%rcx,2), %xmm1, %xmm1
453; AVX2-NEXT:    andl $15, %r8d
454; AVX2-NEXT:    vpinsrw $4, (%rsp,%r8,2), %xmm1, %xmm1
455; AVX2-NEXT:    andl $15, %r9d
456; AVX2-NEXT:    vpinsrw $5, (%rsp,%r9,2), %xmm1, %xmm1
457; AVX2-NEXT:    movl 16(%rbp), %eax
458; AVX2-NEXT:    andl $15, %eax
459; AVX2-NEXT:    vpinsrw $6, (%rsp,%rax,2), %xmm1, %xmm1
460; AVX2-NEXT:    movl 24(%rbp), %eax
461; AVX2-NEXT:    andl $15, %eax
462; AVX2-NEXT:    vpinsrw $7, (%rsp,%rax,2), %xmm1, %xmm1
463; AVX2-NEXT:    vinserti128 $1, %xmm0, %ymm1, %ymm0
464; AVX2-NEXT:    movq %rbp, %rsp
465; AVX2-NEXT:    popq %rbp
466; AVX2-NEXT:    retq
467  %x0  = extractelement <16 x i16> %x, i32 %i0
468  %x1  = extractelement <16 x i16> %x, i32 %i1
469  %x2  = extractelement <16 x i16> %x, i32 %i2
470  %x3  = extractelement <16 x i16> %x, i32 %i3
471  %x4  = extractelement <16 x i16> %x, i32 %i4
472  %x5  = extractelement <16 x i16> %x, i32 %i5
473  %x6  = extractelement <16 x i16> %x, i32 %i6
474  %x7  = extractelement <16 x i16> %x, i32 %i7
475  %x8  = extractelement <16 x i16> %x, i32 %i8
476  %x9  = extractelement <16 x i16> %x, i32 %i9
477  %x10 = extractelement <16 x i16> %x, i32 %i10
478  %x11 = extractelement <16 x i16> %x, i32 %i11
479  %x12 = extractelement <16 x i16> %x, i32 %i12
480  %x13 = extractelement <16 x i16> %x, i32 %i13
481  %x14 = extractelement <16 x i16> %x, i32 %i14
482  %x15 = extractelement <16 x i16> %x, i32 %i15
483  %r0  = insertelement <16 x i16> undef, i16 %x0 , i32 0
484  %r1  = insertelement <16 x i16>  %r0 , i16 %x1 , i32 1
485  %r2  = insertelement <16 x i16>  %r1 , i16 %x2 , i32 2
486  %r3  = insertelement <16 x i16>  %r2 , i16 %x3 , i32 3
487  %r4  = insertelement <16 x i16>  %r3 , i16 %x4 , i32 4
488  %r5  = insertelement <16 x i16>  %r4 , i16 %x5 , i32 5
489  %r6  = insertelement <16 x i16>  %r5 , i16 %x6 , i32 6
490  %r7  = insertelement <16 x i16>  %r6 , i16 %x7 , i32 7
491  %r8  = insertelement <16 x i16>  %r7 , i16 %x8 , i32 8
492  %r9  = insertelement <16 x i16>  %r8 , i16 %x9 , i32 9
493  %r10 = insertelement <16 x i16>  %r9 , i16 %x10, i32 10
494  %r11 = insertelement <16 x i16>  %r10, i16 %x11, i32 11
495  %r12 = insertelement <16 x i16>  %r11, i16 %x12, i32 12
496  %r13 = insertelement <16 x i16>  %r12, i16 %x13, i32 13
497  %r14 = insertelement <16 x i16>  %r13, i16 %x14, i32 14
498  %r15 = insertelement <16 x i16>  %r14, i16 %x15, i32 15
499  ret <16 x i16> %r15
500}
501
502define <16 x i16> @var_shuffle_v16i16_v8i16_xxxxxxxxxxxxxxxx_i16(<8 x i16> %x, i32 %i0, i32 %i1, i32 %i2, i32 %i3, i32 %i4, i32 %i5, i32 %i6, i32 %i7, i32 %i8, i32 %i9, i32 %i10, i32 %i11, i32 %i12, i32 %i13, i32 %i14, i32 %i15) nounwind {
503; AVX1-LABEL: var_shuffle_v16i16_v8i16_xxxxxxxxxxxxxxxx_i16:
504; AVX1:       # BB#0:
505; AVX1-NEXT:    # kill: %R9D<def> %R9D<kill> %R9<def>
506; AVX1-NEXT:    # kill: %R8D<def> %R8D<kill> %R8<def>
507; AVX1-NEXT:    # kill: %ECX<def> %ECX<kill> %RCX<def>
508; AVX1-NEXT:    # kill: %EDX<def> %EDX<kill> %RDX<def>
509; AVX1-NEXT:    # kill: %ESI<def> %ESI<kill> %RSI<def>
510; AVX1-NEXT:    # kill: %EDI<def> %EDI<kill> %RDI<def>
511; AVX1-NEXT:    vmovaps %xmm0, -{{[0-9]+}}(%rsp)
512; AVX1-NEXT:    movl {{[0-9]+}}(%rsp), %eax
513; AVX1-NEXT:    andl $7, %eax
514; AVX1-NEXT:    movzwl -24(%rsp,%rax,2), %eax
515; AVX1-NEXT:    vmovd %eax, %xmm0
516; AVX1-NEXT:    movl {{[0-9]+}}(%rsp), %eax
517; AVX1-NEXT:    andl $7, %eax
518; AVX1-NEXT:    vpinsrw $1, -24(%rsp,%rax,2), %xmm0, %xmm0
519; AVX1-NEXT:    movl {{[0-9]+}}(%rsp), %eax
520; AVX1-NEXT:    andl $7, %eax
521; AVX1-NEXT:    vpinsrw $2, -24(%rsp,%rax,2), %xmm0, %xmm0
522; AVX1-NEXT:    movl {{[0-9]+}}(%rsp), %eax
523; AVX1-NEXT:    andl $7, %eax
524; AVX1-NEXT:    vpinsrw $3, -24(%rsp,%rax,2), %xmm0, %xmm0
525; AVX1-NEXT:    movl {{[0-9]+}}(%rsp), %eax
526; AVX1-NEXT:    andl $7, %eax
527; AVX1-NEXT:    vpinsrw $4, -24(%rsp,%rax,2), %xmm0, %xmm0
528; AVX1-NEXT:    movl {{[0-9]+}}(%rsp), %eax
529; AVX1-NEXT:    andl $7, %eax
530; AVX1-NEXT:    vpinsrw $5, -24(%rsp,%rax,2), %xmm0, %xmm0
531; AVX1-NEXT:    movl {{[0-9]+}}(%rsp), %eax
532; AVX1-NEXT:    andl $7, %eax
533; AVX1-NEXT:    vpinsrw $6, -24(%rsp,%rax,2), %xmm0, %xmm0
534; AVX1-NEXT:    movl {{[0-9]+}}(%rsp), %eax
535; AVX1-NEXT:    andl $7, %eax
536; AVX1-NEXT:    vpinsrw $7, -24(%rsp,%rax,2), %xmm0, %xmm0
537; AVX1-NEXT:    andl $7, %edi
538; AVX1-NEXT:    movzwl -24(%rsp,%rdi,2), %eax
539; AVX1-NEXT:    vmovd %eax, %xmm1
540; AVX1-NEXT:    andl $7, %esi
541; AVX1-NEXT:    vpinsrw $1, -24(%rsp,%rsi,2), %xmm1, %xmm1
542; AVX1-NEXT:    andl $7, %edx
543; AVX1-NEXT:    vpinsrw $2, -24(%rsp,%rdx,2), %xmm1, %xmm1
544; AVX1-NEXT:    andl $7, %ecx
545; AVX1-NEXT:    vpinsrw $3, -24(%rsp,%rcx,2), %xmm1, %xmm1
546; AVX1-NEXT:    andl $7, %r8d
547; AVX1-NEXT:    vpinsrw $4, -24(%rsp,%r8,2), %xmm1, %xmm1
548; AVX1-NEXT:    andl $7, %r9d
549; AVX1-NEXT:    vpinsrw $5, -24(%rsp,%r9,2), %xmm1, %xmm1
550; AVX1-NEXT:    movl {{[0-9]+}}(%rsp), %eax
551; AVX1-NEXT:    andl $7, %eax
552; AVX1-NEXT:    vpinsrw $6, -24(%rsp,%rax,2), %xmm1, %xmm1
553; AVX1-NEXT:    movl {{[0-9]+}}(%rsp), %eax
554; AVX1-NEXT:    andl $7, %eax
555; AVX1-NEXT:    vpinsrw $7, -24(%rsp,%rax,2), %xmm1, %xmm1
556; AVX1-NEXT:    vinsertf128 $1, %xmm0, %ymm1, %ymm0
557; AVX1-NEXT:    retq
558;
559; AVX2-LABEL: var_shuffle_v16i16_v8i16_xxxxxxxxxxxxxxxx_i16:
560; AVX2:       # BB#0:
561; AVX2-NEXT:    # kill: %R9D<def> %R9D<kill> %R9<def>
562; AVX2-NEXT:    # kill: %R8D<def> %R8D<kill> %R8<def>
563; AVX2-NEXT:    # kill: %ECX<def> %ECX<kill> %RCX<def>
564; AVX2-NEXT:    # kill: %EDX<def> %EDX<kill> %RDX<def>
565; AVX2-NEXT:    # kill: %ESI<def> %ESI<kill> %RSI<def>
566; AVX2-NEXT:    # kill: %EDI<def> %EDI<kill> %RDI<def>
567; AVX2-NEXT:    vmovaps %xmm0, -{{[0-9]+}}(%rsp)
568; AVX2-NEXT:    movl {{[0-9]+}}(%rsp), %eax
569; AVX2-NEXT:    andl $7, %eax
570; AVX2-NEXT:    movzwl -24(%rsp,%rax,2), %eax
571; AVX2-NEXT:    vmovd %eax, %xmm0
572; AVX2-NEXT:    movl {{[0-9]+}}(%rsp), %eax
573; AVX2-NEXT:    andl $7, %eax
574; AVX2-NEXT:    vpinsrw $1, -24(%rsp,%rax,2), %xmm0, %xmm0
575; AVX2-NEXT:    movl {{[0-9]+}}(%rsp), %eax
576; AVX2-NEXT:    andl $7, %eax
577; AVX2-NEXT:    vpinsrw $2, -24(%rsp,%rax,2), %xmm0, %xmm0
578; AVX2-NEXT:    movl {{[0-9]+}}(%rsp), %eax
579; AVX2-NEXT:    andl $7, %eax
580; AVX2-NEXT:    vpinsrw $3, -24(%rsp,%rax,2), %xmm0, %xmm0
581; AVX2-NEXT:    movl {{[0-9]+}}(%rsp), %eax
582; AVX2-NEXT:    andl $7, %eax
583; AVX2-NEXT:    vpinsrw $4, -24(%rsp,%rax,2), %xmm0, %xmm0
584; AVX2-NEXT:    movl {{[0-9]+}}(%rsp), %eax
585; AVX2-NEXT:    andl $7, %eax
586; AVX2-NEXT:    vpinsrw $5, -24(%rsp,%rax,2), %xmm0, %xmm0
587; AVX2-NEXT:    movl {{[0-9]+}}(%rsp), %eax
588; AVX2-NEXT:    andl $7, %eax
589; AVX2-NEXT:    vpinsrw $6, -24(%rsp,%rax,2), %xmm0, %xmm0
590; AVX2-NEXT:    movl {{[0-9]+}}(%rsp), %eax
591; AVX2-NEXT:    andl $7, %eax
592; AVX2-NEXT:    vpinsrw $7, -24(%rsp,%rax,2), %xmm0, %xmm0
593; AVX2-NEXT:    andl $7, %edi
594; AVX2-NEXT:    movzwl -24(%rsp,%rdi,2), %eax
595; AVX2-NEXT:    vmovd %eax, %xmm1
596; AVX2-NEXT:    andl $7, %esi
597; AVX2-NEXT:    vpinsrw $1, -24(%rsp,%rsi,2), %xmm1, %xmm1
598; AVX2-NEXT:    andl $7, %edx
599; AVX2-NEXT:    vpinsrw $2, -24(%rsp,%rdx,2), %xmm1, %xmm1
600; AVX2-NEXT:    andl $7, %ecx
601; AVX2-NEXT:    vpinsrw $3, -24(%rsp,%rcx,2), %xmm1, %xmm1
602; AVX2-NEXT:    andl $7, %r8d
603; AVX2-NEXT:    vpinsrw $4, -24(%rsp,%r8,2), %xmm1, %xmm1
604; AVX2-NEXT:    andl $7, %r9d
605; AVX2-NEXT:    vpinsrw $5, -24(%rsp,%r9,2), %xmm1, %xmm1
606; AVX2-NEXT:    movl {{[0-9]+}}(%rsp), %eax
607; AVX2-NEXT:    andl $7, %eax
608; AVX2-NEXT:    vpinsrw $6, -24(%rsp,%rax,2), %xmm1, %xmm1
609; AVX2-NEXT:    movl {{[0-9]+}}(%rsp), %eax
610; AVX2-NEXT:    andl $7, %eax
611; AVX2-NEXT:    vpinsrw $7, -24(%rsp,%rax,2), %xmm1, %xmm1
612; AVX2-NEXT:    vinserti128 $1, %xmm0, %ymm1, %ymm0
613; AVX2-NEXT:    retq
614  %x0  = extractelement <8 x i16> %x, i32 %i0
615  %x1  = extractelement <8 x i16> %x, i32 %i1
616  %x2  = extractelement <8 x i16> %x, i32 %i2
617  %x3  = extractelement <8 x i16> %x, i32 %i3
618  %x4  = extractelement <8 x i16> %x, i32 %i4
619  %x5  = extractelement <8 x i16> %x, i32 %i5
620  %x6  = extractelement <8 x i16> %x, i32 %i6
621  %x7  = extractelement <8 x i16> %x, i32 %i7
622  %x8  = extractelement <8 x i16> %x, i32 %i8
623  %x9  = extractelement <8 x i16> %x, i32 %i9
624  %x10 = extractelement <8 x i16> %x, i32 %i10
625  %x11 = extractelement <8 x i16> %x, i32 %i11
626  %x12 = extractelement <8 x i16> %x, i32 %i12
627  %x13 = extractelement <8 x i16> %x, i32 %i13
628  %x14 = extractelement <8 x i16> %x, i32 %i14
629  %x15 = extractelement <8 x i16> %x, i32 %i15
630  %r0  = insertelement <16 x i16> undef, i16 %x0 , i32 0
631  %r1  = insertelement <16 x i16>  %r0 , i16 %x1 , i32 1
632  %r2  = insertelement <16 x i16>  %r1 , i16 %x2 , i32 2
633  %r3  = insertelement <16 x i16>  %r2 , i16 %x3 , i32 3
634  %r4  = insertelement <16 x i16>  %r3 , i16 %x4 , i32 4
635  %r5  = insertelement <16 x i16>  %r4 , i16 %x5 , i32 5
636  %r6  = insertelement <16 x i16>  %r5 , i16 %x6 , i32 6
637  %r7  = insertelement <16 x i16>  %r6 , i16 %x7 , i32 7
638  %r8  = insertelement <16 x i16>  %r7 , i16 %x8 , i32 8
639  %r9  = insertelement <16 x i16>  %r8 , i16 %x9 , i32 9
640  %r10 = insertelement <16 x i16>  %r9 , i16 %x10, i32 10
641  %r11 = insertelement <16 x i16>  %r10, i16 %x11, i32 11
642  %r12 = insertelement <16 x i16>  %r11, i16 %x12, i32 12
643  %r13 = insertelement <16 x i16>  %r12, i16 %x13, i32 13
644  %r14 = insertelement <16 x i16>  %r13, i16 %x14, i32 14
645  %r15 = insertelement <16 x i16>  %r14, i16 %x15, i32 15
646  ret <16 x i16> %r15
647}
648
649;
650; Unary shuffle indices from memory
651;
652
653define <4 x i64> @mem_shuffle_v4i64_v4i64_xxxx_i64(<4 x i64> %x, i64* %i) nounwind {
654; AVX1-LABEL: mem_shuffle_v4i64_v4i64_xxxx_i64:
655; AVX1:       # BB#0:
656; AVX1-NEXT:    pushq %rbp
657; AVX1-NEXT:    movq %rsp, %rbp
658; AVX1-NEXT:    andq $-32, %rsp
659; AVX1-NEXT:    subq $64, %rsp
660; AVX1-NEXT:    movq (%rdi), %rax
661; AVX1-NEXT:    movq 8(%rdi), %rcx
662; AVX1-NEXT:    andl $3, %eax
663; AVX1-NEXT:    andl $3, %ecx
664; AVX1-NEXT:    movq 16(%rdi), %rdx
665; AVX1-NEXT:    andl $3, %edx
666; AVX1-NEXT:    movq 24(%rdi), %rsi
667; AVX1-NEXT:    andl $3, %esi
668; AVX1-NEXT:    vmovaps %ymm0, (%rsp)
669; AVX1-NEXT:    vmovq {{.*#+}} xmm0 = mem[0],zero
670; AVX1-NEXT:    vmovq {{.*#+}} xmm1 = mem[0],zero
671; AVX1-NEXT:    vpunpcklqdq {{.*#+}} xmm0 = xmm1[0],xmm0[0]
672; AVX1-NEXT:    vmovq {{.*#+}} xmm1 = mem[0],zero
673; AVX1-NEXT:    vmovq {{.*#+}} xmm2 = mem[0],zero
674; AVX1-NEXT:    vpunpcklqdq {{.*#+}} xmm1 = xmm2[0],xmm1[0]
675; AVX1-NEXT:    vinsertf128 $1, %xmm0, %ymm1, %ymm0
676; AVX1-NEXT:    movq %rbp, %rsp
677; AVX1-NEXT:    popq %rbp
678; AVX1-NEXT:    retq
679;
680; AVX2-LABEL: mem_shuffle_v4i64_v4i64_xxxx_i64:
681; AVX2:       # BB#0:
682; AVX2-NEXT:    pushq %rbp
683; AVX2-NEXT:    movq %rsp, %rbp
684; AVX2-NEXT:    andq $-32, %rsp
685; AVX2-NEXT:    subq $64, %rsp
686; AVX2-NEXT:    movq (%rdi), %rax
687; AVX2-NEXT:    movq 8(%rdi), %rcx
688; AVX2-NEXT:    andl $3, %eax
689; AVX2-NEXT:    andl $3, %ecx
690; AVX2-NEXT:    movq 16(%rdi), %rdx
691; AVX2-NEXT:    andl $3, %edx
692; AVX2-NEXT:    movq 24(%rdi), %rsi
693; AVX2-NEXT:    andl $3, %esi
694; AVX2-NEXT:    vmovaps %ymm0, (%rsp)
695; AVX2-NEXT:    vmovq {{.*#+}} xmm0 = mem[0],zero
696; AVX2-NEXT:    vmovq {{.*#+}} xmm1 = mem[0],zero
697; AVX2-NEXT:    vpunpcklqdq {{.*#+}} xmm0 = xmm1[0],xmm0[0]
698; AVX2-NEXT:    vmovq {{.*#+}} xmm1 = mem[0],zero
699; AVX2-NEXT:    vmovq {{.*#+}} xmm2 = mem[0],zero
700; AVX2-NEXT:    vpunpcklqdq {{.*#+}} xmm1 = xmm2[0],xmm1[0]
701; AVX2-NEXT:    vinserti128 $1, %xmm0, %ymm1, %ymm0
702; AVX2-NEXT:    movq %rbp, %rsp
703; AVX2-NEXT:    popq %rbp
704; AVX2-NEXT:    retq
705  %p0  = getelementptr inbounds i64, i64* %i, i32 0
706  %p1  = getelementptr inbounds i64, i64* %i, i32 1
707  %p2  = getelementptr inbounds i64, i64* %i, i32 2
708  %p3  = getelementptr inbounds i64, i64* %i, i32 3
709  %i0  = load i64, i64* %p0, align 4
710  %i1  = load i64, i64* %p1, align 4
711  %i2  = load i64, i64* %p2, align 4
712  %i3  = load i64, i64* %p3, align 4
713  %x0 = extractelement <4 x i64> %x, i64 %i0
714  %x1 = extractelement <4 x i64> %x, i64 %i1
715  %x2 = extractelement <4 x i64> %x, i64 %i2
716  %x3 = extractelement <4 x i64> %x, i64 %i3
717  %r0 = insertelement <4 x i64> undef, i64 %x0, i32 0
718  %r1 = insertelement <4 x i64>   %r0, i64 %x1, i32 1
719  %r2 = insertelement <4 x i64>   %r1, i64 %x2, i32 2
720  %r3 = insertelement <4 x i64>   %r2, i64 %x3, i32 3
721  ret <4 x i64> %r3
722}
723
724define <4 x i64> @mem_shuffle_v4i64_v2i64_xxxx_i64(<2 x i64> %x, i64* %i) nounwind {
725; AVX1-LABEL: mem_shuffle_v4i64_v2i64_xxxx_i64:
726; AVX1:       # BB#0:
727; AVX1-NEXT:    movq (%rdi), %rax
728; AVX1-NEXT:    movq 8(%rdi), %rcx
729; AVX1-NEXT:    andl $1, %eax
730; AVX1-NEXT:    andl $1, %ecx
731; AVX1-NEXT:    movq 16(%rdi), %rdx
732; AVX1-NEXT:    andl $1, %edx
733; AVX1-NEXT:    movq 24(%rdi), %rsi
734; AVX1-NEXT:    andl $1, %esi
735; AVX1-NEXT:    vmovaps %xmm0, -{{[0-9]+}}(%rsp)
736; AVX1-NEXT:    vmovq {{.*#+}} xmm0 = mem[0],zero
737; AVX1-NEXT:    vmovq {{.*#+}} xmm1 = mem[0],zero
738; AVX1-NEXT:    vpunpcklqdq {{.*#+}} xmm0 = xmm1[0],xmm0[0]
739; AVX1-NEXT:    vmovq {{.*#+}} xmm1 = mem[0],zero
740; AVX1-NEXT:    vmovq {{.*#+}} xmm2 = mem[0],zero
741; AVX1-NEXT:    vpunpcklqdq {{.*#+}} xmm1 = xmm2[0],xmm1[0]
742; AVX1-NEXT:    vinsertf128 $1, %xmm0, %ymm1, %ymm0
743; AVX1-NEXT:    retq
744;
745; AVX2-LABEL: mem_shuffle_v4i64_v2i64_xxxx_i64:
746; AVX2:       # BB#0:
747; AVX2-NEXT:    movq (%rdi), %rax
748; AVX2-NEXT:    movq 8(%rdi), %rcx
749; AVX2-NEXT:    andl $1, %eax
750; AVX2-NEXT:    andl $1, %ecx
751; AVX2-NEXT:    movq 16(%rdi), %rdx
752; AVX2-NEXT:    andl $1, %edx
753; AVX2-NEXT:    movq 24(%rdi), %rsi
754; AVX2-NEXT:    andl $1, %esi
755; AVX2-NEXT:    vmovaps %xmm0, -{{[0-9]+}}(%rsp)
756; AVX2-NEXT:    vmovq {{.*#+}} xmm0 = mem[0],zero
757; AVX2-NEXT:    vmovq {{.*#+}} xmm1 = mem[0],zero
758; AVX2-NEXT:    vpunpcklqdq {{.*#+}} xmm0 = xmm1[0],xmm0[0]
759; AVX2-NEXT:    vmovq {{.*#+}} xmm1 = mem[0],zero
760; AVX2-NEXT:    vmovq {{.*#+}} xmm2 = mem[0],zero
761; AVX2-NEXT:    vpunpcklqdq {{.*#+}} xmm1 = xmm2[0],xmm1[0]
762; AVX2-NEXT:    vinserti128 $1, %xmm0, %ymm1, %ymm0
763; AVX2-NEXT:    retq
764  %p0  = getelementptr inbounds i64, i64* %i, i32 0
765  %p1  = getelementptr inbounds i64, i64* %i, i32 1
766  %p2  = getelementptr inbounds i64, i64* %i, i32 2
767  %p3  = getelementptr inbounds i64, i64* %i, i32 3
768  %i0  = load i64, i64* %p0, align 4
769  %i1  = load i64, i64* %p1, align 4
770  %i2  = load i64, i64* %p2, align 4
771  %i3  = load i64, i64* %p3, align 4
772  %x0 = extractelement <2 x i64> %x, i64 %i0
773  %x1 = extractelement <2 x i64> %x, i64 %i1
774  %x2 = extractelement <2 x i64> %x, i64 %i2
775  %x3 = extractelement <2 x i64> %x, i64 %i3
776  %r0 = insertelement <4 x i64> undef, i64 %x0, i32 0
777  %r1 = insertelement <4 x i64>   %r0, i64 %x1, i32 1
778  %r2 = insertelement <4 x i64>   %r1, i64 %x2, i32 2
779  %r3 = insertelement <4 x i64>   %r2, i64 %x3, i32 3
780  ret <4 x i64> %r3
781}
782