[mips][micromips] Use call instructions with short delay slots
[oota-llvm.git] / test / CodeGen / Mips / msa / basic_operations.ll
1 ; RUN: llc -march=mips -mattr=+msa,+fp64 < %s | FileCheck -check-prefix=MIPS32-AE -check-prefix=MIPS32-BE %s
2 ; RUN: llc -march=mipsel -mattr=+msa,+fp64 < %s | FileCheck -check-prefix=MIPS32-AE -check-prefix=MIPS32-LE %s
3
4 @v4i8 = global <4 x i8> <i8 0, i8 0, i8 0, i8 0>
5 @v16i8 = global <16 x i8> <i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0>
6 @v8i16 = global <8 x i16> <i16 0, i16 0, i16 0, i16 0, i16 0, i16 0, i16 0, i16 0>
7 @v4i32 = global <4 x i32> <i32 0, i32 0, i32 0, i32 0>
8 @v2i64 = global <2 x i64> <i64 0, i64 0>
9 @i32 = global i32 0
10 @i64 = global i64 0
11
12 define void @const_v16i8() nounwind {
13   ; MIPS32-AE-LABEL: const_v16i8:
14
15   store volatile <16 x i8> <i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0, i8 0>, <16 x i8>*@v16i8
16   ; MIPS32-AE: ldi.b [[R1:\$w[0-9]+]], 0
17
18   store volatile <16 x i8> <i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1>, <16 x i8>*@v16i8
19   ; MIPS32-AE: ldi.b [[R1:\$w[0-9]+]], 1
20
21   store volatile <16 x i8> <i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 1, i8 31>, <16 x i8>*@v16i8
22   ; MIPS32-AE: addiu [[G_PTR:\$[0-9]+]], {{.*}}, %lo($
23   ; MIPS32-AE: ld.b  [[R1:\$w[0-9]+]], 0([[G_PTR]])
24
25   store volatile <16 x i8> <i8 1, i8 2, i8 3, i8 4, i8 5, i8 6, i8 7, i8 8, i8 9, i8 0, i8 1, i8 2, i8 3, i8 4, i8 5, i8 6>, <16 x i8>*@v16i8
26   ; MIPS32-AE: addiu [[G_PTR:\$[0-9]+]], {{.*}}, %lo($
27   ; MIPS32-AE: ld.b  [[R1:\$w[0-9]+]], 0([[G_PTR]])
28
29   store volatile <16 x i8> <i8 1, i8 0, i8 1, i8 0, i8 1, i8 0, i8 1, i8 0, i8 1, i8 0, i8 1, i8 0, i8 1, i8 0, i8 1, i8 0>, <16 x i8>*@v16i8
30   ; MIPS32-BE: ldi.h [[R1:\$w[0-9]+]], 256
31   ; MIPS32-LE: ldi.h [[R1:\$w[0-9]+]], 1
32
33   store volatile <16 x i8> <i8 1, i8 2, i8 3, i8 4, i8 1, i8 2, i8 3, i8 4, i8 1, i8 2, i8 3, i8 4, i8 1, i8 2, i8 3, i8 4>, <16 x i8>*@v16i8
34   ; MIPS32-BE-DAG: lui [[R2:\$[0-9]+]], 258
35   ; MIPS32-LE-DAG: lui [[R2:\$[0-9]+]], 1027
36   ; MIPS32-BE-DAG: ori [[R2]], [[R2]], 772
37   ; MIPS32-LE-DAG: ori [[R2]], [[R2]], 513
38   ; MIPS32-AE-DAG: fill.w [[R1:\$w[0-9]+]], [[R2]]
39
40   store volatile <16 x i8> <i8 1, i8 2, i8 3, i8 4, i8 5, i8 6, i8 7, i8 8, i8 1, i8 2, i8 3, i8 4, i8 5, i8 6, i8 7, i8 8>, <16 x i8>*@v16i8
41   ; MIPS32-AE: addiu [[G_PTR:\$[0-9]+]], {{.*}}, %lo($
42   ; MIPS32-AE: ld.b  [[R1:\$w[0-9]+]], 0([[G_PTR]])
43
44   ret void
45   ; MIPS32-AE: .size const_v16i8
46 }
47
48 define void @const_v8i16() nounwind {
49   ; MIPS32-AE-LABEL: const_v8i16:
50
51   store volatile <8 x i16> <i16 0, i16 0, i16 0, i16 0, i16 0, i16 0, i16 0, i16 0>, <8 x i16>*@v8i16
52   ; MIPS32-AE: ldi.b [[R1:\$w[0-9]+]], 0
53
54   store volatile <8 x i16> <i16 1, i16 1, i16 1, i16 1, i16 1, i16 1, i16 1, i16 1>, <8 x i16>*@v8i16
55   ; MIPS32-AE: ldi.h [[R1:\$w[0-9]+]], 1
56
57   store volatile <8 x i16> <i16 1, i16 1, i16 1, i16 2, i16 1, i16 1, i16 1, i16 31>, <8 x i16>*@v8i16
58   ; MIPS32-AE: addiu [[G_PTR:\$[0-9]+]], {{.*}}, %lo($
59   ; MIPS32-AE: ld.h  [[R1:\$w[0-9]+]], 0([[G_PTR]])
60
61   store volatile <8 x i16> <i16 1028, i16 1028, i16 1028, i16 1028, i16 1028, i16 1028, i16 1028, i16 1028>, <8 x i16>*@v8i16
62   ; MIPS32-AE: ldi.b [[R1:\$w[0-9]+]], 4
63
64   store volatile <8 x i16> <i16 1, i16 2, i16 1, i16 2, i16 1, i16 2, i16 1, i16 2>, <8 x i16>*@v8i16
65   ; MIPS32-BE-DAG: lui [[R2:\$[0-9]+]], 1
66   ; MIPS32-LE-DAG: lui [[R2:\$[0-9]+]], 2
67   ; MIPS32-BE-DAG: ori [[R2]], [[R2]], 2
68   ; MIPS32-LE-DAG: ori [[R2]], [[R2]], 1
69   ; MIPS32-AE-DAG: fill.w [[R1:\$w[0-9]+]], [[R2]]
70
71   store volatile <8 x i16> <i16 1, i16 2, i16 3, i16 4, i16 1, i16 2, i16 3, i16 4>, <8 x i16>*@v8i16
72   ; MIPS32-AE: addiu [[G_PTR:\$[0-9]+]], {{.*}}, %lo($
73   ; MIPS32-AE: ld.h  [[R1:\$w[0-9]+]], 0([[G_PTR]])
74
75   ret void
76   ; MIPS32-AE: .size const_v8i16
77 }
78
79 define void @const_v4i32() nounwind {
80   ; MIPS32-AE-LABEL: const_v4i32:
81
82   store volatile <4 x i32> <i32 0, i32 0, i32 0, i32 0>, <4 x i32>*@v4i32
83   ; MIPS32-AE: ldi.b [[R1:\$w[0-9]+]], 0
84
85   store volatile <4 x i32> <i32 1, i32 1, i32 1, i32 1>, <4 x i32>*@v4i32
86   ; MIPS32-AE: ldi.w [[R1:\$w[0-9]+]], 1
87
88   store volatile <4 x i32> <i32 1, i32 1, i32 1, i32 31>, <4 x i32>*@v4i32
89   ; MIPS32-AE: addiu [[G_PTR:\$[0-9]+]], {{.*}}, %lo($
90   ; MIPS32-AE: ld.w  [[R1:\$w[0-9]+]], 0([[G_PTR]])
91
92   store volatile <4 x i32> <i32 16843009, i32 16843009, i32 16843009, i32 16843009>, <4 x i32>*@v4i32
93   ; MIPS32-AE: ldi.b [[R1:\$w[0-9]+]], 1
94
95   store volatile <4 x i32> <i32 65537, i32 65537, i32 65537, i32 65537>, <4 x i32>*@v4i32
96   ; MIPS32-AE: ldi.h [[R1:\$w[0-9]+]], 1
97
98   store volatile <4 x i32> <i32 1, i32 2, i32 1, i32 2>, <4 x i32>*@v4i32
99   ; MIPS32-AE: addiu [[G_PTR:\$[0-9]+]], {{.*}}, %lo($
100   ; MIPS32-AE: ld.w  [[R1:\$w[0-9]+]], 0([[G_PTR]])
101
102   store volatile <4 x i32> <i32 3, i32 4, i32 5, i32 6>, <4 x i32>*@v4i32
103   ; MIPS32-AE: addiu [[G_PTR:\$[0-9]+]], {{.*}}, %lo($
104   ; MIPS32-AE: ld.w  [[R1:\$w[0-9]+]], 0([[G_PTR]])
105
106   ret void
107   ; MIPS32-AE: .size const_v4i32
108 }
109
110 define void @const_v2i64() nounwind {
111   ; MIPS32-AE-LABEL: const_v2i64:
112
113   store volatile <2 x i64> <i64 0, i64 0>, <2 x i64>*@v2i64
114   ; MIPS32-AE: ldi.b [[R1:\$w[0-9]+]], 0
115
116   store volatile <2 x i64> <i64 72340172838076673, i64 72340172838076673>, <2 x i64>*@v2i64
117   ; MIPS32-AE: ldi.b [[R1:\$w[0-9]+]], 1
118
119   store volatile <2 x i64> <i64 281479271743489, i64 281479271743489>, <2 x i64>*@v2i64
120   ; MIPS32-AE: ldi.h [[R1:\$w[0-9]+]], 1
121
122   store volatile <2 x i64> <i64 4294967297, i64 4294967297>, <2 x i64>*@v2i64
123   ; MIPS32-AE: ldi.w [[R1:\$w[0-9]+]], 1
124
125   store volatile <2 x i64> <i64 1, i64 1>, <2 x i64>*@v2i64
126   ; MIPS32-AE: ldi.d [[R1:\$w[0-9]+]], 1
127
128   store volatile <2 x i64> <i64 1, i64 31>, <2 x i64>*@v2i64
129   ; MIPS32-AE: addiu [[G_PTR:\$[0-9]+]], {{.*}}, %lo($
130   ; MIPS32-AE: ld.w  [[R1:\$w[0-9]+]], 0([[G_PTR]])
131
132   store volatile <2 x i64> <i64 3, i64 4>, <2 x i64>*@v2i64
133   ; MIPS32-AE: addiu [[G_PTR:\$[0-9]+]], {{.*}}, %lo($
134   ; MIPS32-AE: ld.w  [[R1:\$w[0-9]+]], 0([[G_PTR]])
135
136   ret void
137   ; MIPS32-AE: .size const_v2i64
138 }
139
140 define void @nonconst_v16i8(i8 %a, i8 %b, i8 %c, i8 %d, i8 %e, i8 %f, i8 %g, i8 %h) nounwind {
141   ; MIPS32-AE-LABEL: nonconst_v16i8:
142
143   %1 = insertelement <16 x i8> undef, i8 %a, i32 0
144   %2 = insertelement <16 x i8> %1, i8 %b, i32 1
145   %3 = insertelement <16 x i8> %2, i8 %c, i32 2
146   %4 = insertelement <16 x i8> %3, i8 %d, i32 3
147   %5 = insertelement <16 x i8> %4, i8 %e, i32 4
148   %6 = insertelement <16 x i8> %5, i8 %f, i32 5
149   %7 = insertelement <16 x i8> %6, i8 %g, i32 6
150   %8 = insertelement <16 x i8> %7, i8 %h, i32 7
151   %9 = insertelement <16 x i8> %8, i8 %h, i32 8
152   %10 = insertelement <16 x i8> %9, i8 %h, i32 9
153   %11 = insertelement <16 x i8> %10, i8 %h, i32 10
154   %12 = insertelement <16 x i8> %11, i8 %h, i32 11
155   %13 = insertelement <16 x i8> %12, i8 %h, i32 12
156   %14 = insertelement <16 x i8> %13, i8 %h, i32 13
157   %15 = insertelement <16 x i8> %14, i8 %h, i32 14
158   %16 = insertelement <16 x i8> %15, i8 %h, i32 15
159   ; MIPS32-AE-DAG: insert.b [[R1:\$w[0-9]+]][0], $4
160   ; MIPS32-AE-DAG: insert.b [[R1]][1], $5
161   ; MIPS32-AE-DAG: insert.b [[R1]][2], $6
162   ; MIPS32-AE-DAG: insert.b [[R1]][3], $7
163   ; MIPS32-BE-DAG: lbu [[R2:\$[0-9]+]], 19($sp)
164   ; MIPS32-LE-DAG: lbu [[R2:\$[0-9]+]], 16($sp)
165   ; MIPS32-AE-DAG: insert.b [[R1]][4], [[R2]]
166   ; MIPS32-BE-DAG: lbu [[R3:\$[0-9]+]], 23($sp)
167   ; MIPS32-LE-DAG: lbu [[R3:\$[0-9]+]], 20($sp)
168   ; MIPS32-AE-DAG: insert.b [[R1]][5], [[R3]]
169   ; MIPS32-BE-DAG: lbu [[R4:\$[0-9]+]], 27($sp)
170   ; MIPS32-LE-DAG: lbu [[R4:\$[0-9]+]], 24($sp)
171   ; MIPS32-AE-DAG: insert.b [[R1]][6], [[R4]]
172   ; MIPS32-BE-DAG: lbu [[R5:\$[0-9]+]], 31($sp)
173   ; MIPS32-LE-DAG: lbu [[R5:\$[0-9]+]], 28($sp)
174   ; MIPS32-AE-DAG: insert.b [[R1]][7], [[R5]]
175   ; MIPS32-AE-DAG: insert.b [[R1]][8], [[R5]]
176   ; MIPS32-AE-DAG: insert.b [[R1]][9], [[R5]]
177   ; MIPS32-AE-DAG: insert.b [[R1]][10], [[R5]]
178   ; MIPS32-AE-DAG: insert.b [[R1]][11], [[R5]]
179   ; MIPS32-AE-DAG: insert.b [[R1]][12], [[R5]]
180   ; MIPS32-AE-DAG: insert.b [[R1]][13], [[R5]]
181   ; MIPS32-AE-DAG: insert.b [[R1]][14], [[R5]]
182   ; MIPS32-AE-DAG: insert.b [[R1]][15], [[R5]]
183
184   store volatile <16 x i8> %16, <16 x i8>*@v16i8
185
186   ret void
187   ; MIPS32-AE: .size nonconst_v16i8
188 }
189
190 define void @nonconst_v8i16(i16 %a, i16 %b, i16 %c, i16 %d, i16 %e, i16 %f, i16 %g, i16 %h) nounwind {
191   ; MIPS32-AE-LABEL: nonconst_v8i16:
192
193   %1 = insertelement <8 x i16> undef, i16 %a, i32 0
194   %2 = insertelement <8 x i16> %1, i16 %b, i32 1
195   %3 = insertelement <8 x i16> %2, i16 %c, i32 2
196   %4 = insertelement <8 x i16> %3, i16 %d, i32 3
197   %5 = insertelement <8 x i16> %4, i16 %e, i32 4
198   %6 = insertelement <8 x i16> %5, i16 %f, i32 5
199   %7 = insertelement <8 x i16> %6, i16 %g, i32 6
200   %8 = insertelement <8 x i16> %7, i16 %h, i32 7
201   ; MIPS32-AE-DAG: insert.h [[R1:\$w[0-9]+]][0], $4
202   ; MIPS32-AE-DAG: insert.h [[R1]][1], $5
203   ; MIPS32-AE-DAG: insert.h [[R1]][2], $6
204   ; MIPS32-AE-DAG: insert.h [[R1]][3], $7
205   ; MIPS32-BE-DAG: lhu [[R2:\$[0-9]+]], 18($sp)
206   ; MIPS32-LE-DAG: lhu [[R2:\$[0-9]+]], 16($sp)
207   ; MIPS32-AE-DAG: insert.h [[R1]][4], [[R2]]
208   ; MIPS32-BE-DAG: lhu [[R2:\$[0-9]+]], 22($sp)
209   ; MIPS32-LE-DAG: lhu [[R2:\$[0-9]+]], 20($sp)
210   ; MIPS32-AE-DAG: insert.h [[R1]][5], [[R2]]
211   ; MIPS32-BE-DAG: lhu [[R2:\$[0-9]+]], 26($sp)
212   ; MIPS32-LE-DAG: lhu [[R2:\$[0-9]+]], 24($sp)
213   ; MIPS32-AE-DAG: insert.h [[R1]][6], [[R2]]
214   ; MIPS32-BE-DAG: lhu [[R2:\$[0-9]+]], 30($sp)
215   ; MIPS32-LE-DAG: lhu [[R2:\$[0-9]+]], 28($sp)
216   ; MIPS32-AE-DAG: insert.h [[R1]][7], [[R2]]
217
218   store volatile <8 x i16> %8, <8 x i16>*@v8i16
219
220   ret void
221   ; MIPS32-AE: .size nonconst_v8i16
222 }
223
224 define void @nonconst_v4i32(i32 %a, i32 %b, i32 %c, i32 %d) nounwind {
225   ; MIPS32-AE-LABEL: nonconst_v4i32:
226
227   %1 = insertelement <4 x i32> undef, i32 %a, i32 0
228   %2 = insertelement <4 x i32> %1, i32 %b, i32 1
229   %3 = insertelement <4 x i32> %2, i32 %c, i32 2
230   %4 = insertelement <4 x i32> %3, i32 %d, i32 3
231   ; MIPS32-AE: insert.w [[R1:\$w[0-9]+]][0], $4
232   ; MIPS32-AE: insert.w [[R1]][1], $5
233   ; MIPS32-AE: insert.w [[R1]][2], $6
234   ; MIPS32-AE: insert.w [[R1]][3], $7
235
236   store volatile <4 x i32> %4, <4 x i32>*@v4i32
237
238   ret void
239   ; MIPS32-AE: .size nonconst_v4i32
240 }
241
242 define void @nonconst_v2i64(i64 %a, i64 %b) nounwind {
243   ; MIPS32-AE-LABEL: nonconst_v2i64:
244
245   %1 = insertelement <2 x i64> undef, i64 %a, i32 0
246   %2 = insertelement <2 x i64> %1, i64 %b, i32 1
247   ; MIPS32-AE: insert.w [[R1:\$w[0-9]+]][0], $4
248   ; MIPS32-AE: insert.w [[R1]][1], $5
249   ; MIPS32-AE: insert.w [[R1]][2], $6
250   ; MIPS32-AE: insert.w [[R1]][3], $7
251
252   store volatile <2 x i64> %2, <2 x i64>*@v2i64
253
254   ret void
255   ; MIPS32-AE: .size nonconst_v2i64
256 }
257
258 define i32 @extract_sext_v16i8() nounwind {
259   ; MIPS32-AE-LABEL: extract_sext_v16i8:
260
261   %1 = load <16 x i8>* @v16i8
262   ; MIPS32-AE-DAG: ld.b [[R1:\$w[0-9]+]],
263
264   %2 = add <16 x i8> %1, %1
265   ; MIPS32-AE-DAG: addv.b [[R2:\$w[0-9]+]], [[R1]], [[R1]]
266
267   %3 = extractelement <16 x i8> %2, i32 1
268   %4 = sext i8 %3 to i32
269   ; MIPS32-AE-DAG: copy_s.b [[R3:\$[0-9]+]], [[R1]][1]
270   ; MIPS32-AE-NOT: sll
271   ; MIPS32-AE-NOT: sra
272
273   ret i32 %4
274   ; MIPS32-AE: .size extract_sext_v16i8
275 }
276
277 define i32 @extract_sext_v8i16() nounwind {
278   ; MIPS32-AE-LABEL: extract_sext_v8i16:
279
280   %1 = load <8 x i16>* @v8i16
281   ; MIPS32-AE-DAG: ld.h [[R1:\$w[0-9]+]],
282
283   %2 = add <8 x i16> %1, %1
284   ; MIPS32-AE-DAG: addv.h [[R2:\$w[0-9]+]], [[R1]], [[R1]]
285
286   %3 = extractelement <8 x i16> %2, i32 1
287   %4 = sext i16 %3 to i32
288   ; MIPS32-AE-DAG: copy_s.h [[R3:\$[0-9]+]], [[R1]][1]
289   ; MIPS32-AE-NOT: sll
290   ; MIPS32-AE-NOT: sra
291
292   ret i32 %4
293   ; MIPS32-AE: .size extract_sext_v8i16
294 }
295
296 define i32 @extract_sext_v4i32() nounwind {
297   ; MIPS32-AE-LABEL: extract_sext_v4i32:
298
299   %1 = load <4 x i32>* @v4i32
300   ; MIPS32-AE-DAG: ld.w [[R1:\$w[0-9]+]],
301
302   %2 = add <4 x i32> %1, %1
303   ; MIPS32-AE-DAG: addv.w [[R2:\$w[0-9]+]], [[R1]], [[R1]]
304
305   %3 = extractelement <4 x i32> %2, i32 1
306   ; MIPS32-AE-DAG: copy_s.w [[R3:\$[0-9]+]], [[R1]][1]
307
308   ret i32 %3
309   ; MIPS32-AE: .size extract_sext_v4i32
310 }
311
312 define i64 @extract_sext_v2i64() nounwind {
313   ; MIPS32-AE-LABEL: extract_sext_v2i64:
314
315   %1 = load <2 x i64>* @v2i64
316   ; MIPS32-AE-DAG: ld.d [[R1:\$w[0-9]+]],
317
318   %2 = add <2 x i64> %1, %1
319   ; MIPS32-AE-DAG: addv.d [[R2:\$w[0-9]+]], [[R1]], [[R1]]
320
321   %3 = extractelement <2 x i64> %2, i32 1
322   ; MIPS32-AE-DAG: copy_s.w [[R3:\$[0-9]+]], [[R1]][2]
323   ; MIPS32-AE-DAG: copy_s.w [[R4:\$[0-9]+]], [[R1]][3]
324   ; MIPS32-AE-NOT: sll
325   ; MIPS32-AE-NOT: sra
326
327   ret i64 %3
328   ; MIPS32-AE: .size extract_sext_v2i64
329 }
330
331 define i32 @extract_zext_v16i8() nounwind {
332   ; MIPS32-AE-LABEL: extract_zext_v16i8:
333
334   %1 = load <16 x i8>* @v16i8
335   ; MIPS32-AE-DAG: ld.b [[R1:\$w[0-9]+]],
336
337   %2 = add <16 x i8> %1, %1
338   ; MIPS32-AE-DAG: addv.b [[R2:\$w[0-9]+]], [[R1]], [[R1]]
339
340   %3 = extractelement <16 x i8> %2, i32 1
341   %4 = zext i8 %3 to i32
342   ; MIPS32-AE-DAG: copy_u.b [[R3:\$[0-9]+]], [[R1]][1]
343   ; MIPS32-AE-NOT: andi
344
345   ret i32 %4
346   ; MIPS32-AE: .size extract_zext_v16i8
347 }
348
349 define i32 @extract_zext_v8i16() nounwind {
350   ; MIPS32-AE-LABEL: extract_zext_v8i16:
351
352   %1 = load <8 x i16>* @v8i16
353   ; MIPS32-AE-DAG: ld.h [[R1:\$w[0-9]+]],
354
355   %2 = add <8 x i16> %1, %1
356   ; MIPS32-AE-DAG: addv.h [[R2:\$w[0-9]+]], [[R1]], [[R1]]
357
358   %3 = extractelement <8 x i16> %2, i32 1
359   %4 = zext i16 %3 to i32
360   ; MIPS32-AE-DAG: copy_u.h [[R3:\$[0-9]+]], [[R1]][1]
361   ; MIPS32-AE-NOT: andi
362
363   ret i32 %4
364   ; MIPS32-AE: .size extract_zext_v8i16
365 }
366
367 define i32 @extract_zext_v4i32() nounwind {
368   ; MIPS32-AE-LABEL: extract_zext_v4i32:
369
370   %1 = load <4 x i32>* @v4i32
371   ; MIPS32-AE-DAG: ld.w [[R1:\$w[0-9]+]],
372
373   %2 = add <4 x i32> %1, %1
374   ; MIPS32-AE-DAG: addv.w [[R2:\$w[0-9]+]], [[R1]], [[R1]]
375
376   %3 = extractelement <4 x i32> %2, i32 1
377   ; MIPS32-AE-DAG: copy_{{[su]}}.w [[R3:\$[0-9]+]], [[R1]][1]
378
379   ret i32 %3
380   ; MIPS32-AE: .size extract_zext_v4i32
381 }
382
383 define i64 @extract_zext_v2i64() nounwind {
384   ; MIPS32-AE-LABEL: extract_zext_v2i64:
385
386   %1 = load <2 x i64>* @v2i64
387   ; MIPS32-AE-DAG: ld.d [[R1:\$w[0-9]+]],
388
389   %2 = add <2 x i64> %1, %1
390   ; MIPS32-AE-DAG: addv.d [[R2:\$w[0-9]+]], [[R1]], [[R1]]
391
392   %3 = extractelement <2 x i64> %2, i32 1
393   ; MIPS32-AE-DAG: copy_{{[su]}}.w [[R3:\$[0-9]+]], [[R1]][2]
394   ; MIPS32-AE-DAG: copy_{{[su]}}.w [[R4:\$[0-9]+]], [[R1]][3]
395   ; MIPS32-AE-NOT: andi
396
397   ret i64 %3
398   ; MIPS32-AE: .size extract_zext_v2i64
399 }
400
401 define i32 @extract_sext_v16i8_vidx() nounwind {
402   ; MIPS32-AE-LABEL: extract_sext_v16i8_vidx:
403
404   %1 = load <16 x i8>* @v16i8
405   ; MIPS32-AE-DAG: lw [[PTR_V:\$[0-9]+]], %got(v16i8)(
406   ; MIPS32-AE-DAG: ld.b [[R1:\$w[0-9]+]], 0([[PTR_V]])
407
408   %2 = add <16 x i8> %1, %1
409   ; MIPS32-AE-DAG: addv.b [[R2:\$w[0-9]+]], [[R1]], [[R1]]
410
411   %3 = load i32* @i32
412   ; MIPS32-AE-DAG: lw [[PTR_I:\$[0-9]+]], %got(i32)(
413   ; MIPS32-AE-DAG: lw [[IDX:\$[0-9]+]], 0([[PTR_I]])
414
415   %4 = extractelement <16 x i8> %2, i32 %3
416   %5 = sext i8 %4 to i32
417   ; MIPS32-AE-DAG: splat.b $w[[R3:[0-9]+]], [[R1]]{{\[}}[[IDX]]]
418   ; MIPS32-AE-DAG: mfc1 [[R5:\$[0-9]+]], $f[[R3]]
419   ; MIPS32-AE-DAG: sra [[R6:\$[0-9]+]], [[R5]], 24
420
421   ret i32 %5
422   ; MIPS32-AE: .size extract_sext_v16i8_vidx
423 }
424
425 define i32 @extract_sext_v8i16_vidx() nounwind {
426   ; MIPS32-AE-LABEL: extract_sext_v8i16_vidx:
427
428   %1 = load <8 x i16>* @v8i16
429   ; MIPS32-AE-DAG: lw [[PTR_V:\$[0-9]+]], %got(v8i16)(
430   ; MIPS32-AE-DAG: ld.h [[R1:\$w[0-9]+]], 0([[PTR_V]])
431
432   %2 = add <8 x i16> %1, %1
433   ; MIPS32-AE-DAG: addv.h [[R2:\$w[0-9]+]], [[R1]], [[R1]]
434
435   %3 = load i32* @i32
436   ; MIPS32-AE-DAG: lw [[PTR_I:\$[0-9]+]], %got(i32)(
437   ; MIPS32-AE-DAG: lw [[IDX:\$[0-9]+]], 0([[PTR_I]])
438
439   %4 = extractelement <8 x i16> %2, i32 %3
440   %5 = sext i16 %4 to i32
441   ; MIPS32-AE-DAG: splat.h $w[[R3:[0-9]+]], [[R1]]{{\[}}[[IDX]]]
442   ; MIPS32-AE-DAG: mfc1 [[R5:\$[0-9]+]], $f[[R3]]
443   ; MIPS32-AE-DAG: sra [[R6:\$[0-9]+]], [[R5]], 16
444
445   ret i32 %5
446   ; MIPS32-AE: .size extract_sext_v8i16_vidx
447 }
448
449 define i32 @extract_sext_v4i32_vidx() nounwind {
450   ; MIPS32-AE-LABEL: extract_sext_v4i32_vidx:
451
452   %1 = load <4 x i32>* @v4i32
453   ; MIPS32-AE-DAG: lw [[PTR_V:\$[0-9]+]], %got(v4i32)(
454   ; MIPS32-AE-DAG: ld.w [[R1:\$w[0-9]+]], 0([[PTR_V]])
455
456   %2 = add <4 x i32> %1, %1
457   ; MIPS32-AE-DAG: addv.w [[R2:\$w[0-9]+]], [[R1]], [[R1]]
458
459   %3 = load i32* @i32
460   ; MIPS32-AE-DAG: lw [[PTR_I:\$[0-9]+]], %got(i32)(
461   ; MIPS32-AE-DAG: lw [[IDX:\$[0-9]+]], 0([[PTR_I]])
462
463   %4 = extractelement <4 x i32> %2, i32 %3
464   ; MIPS32-AE-DAG: splat.w $w[[R3:[0-9]+]], [[R1]]{{\[}}[[IDX]]]
465   ; MIPS32-AE-DAG: mfc1 [[R5:\$[0-9]+]], $f[[R3]]
466   ; MIPS32-AE-NOT: sra
467
468   ret i32 %4
469   ; MIPS32-AE: .size extract_sext_v4i32_vidx
470 }
471
472 define i64 @extract_sext_v2i64_vidx() nounwind {
473   ; MIPS32-AE-LABEL: extract_sext_v2i64_vidx:
474
475   %1 = load <2 x i64>* @v2i64
476   ; MIPS32-AE-DAG: lw [[PTR_V:\$[0-9]+]], %got(v2i64)(
477   ; MIPS32-AE-DAG: ld.d [[R1:\$w[0-9]+]], 0([[PTR_V]])
478
479   %2 = add <2 x i64> %1, %1
480   ; MIPS32-AE-DAG: addv.d [[R2:\$w[0-9]+]], [[R1]], [[R1]]
481
482   %3 = load i32* @i32
483   ; MIPS32-AE-DAG: lw [[PTR_I:\$[0-9]+]], %got(i32)(
484   ; MIPS32-AE-DAG: lw [[IDX:\$[0-9]+]], 0([[PTR_I]])
485
486   %4 = extractelement <2 x i64> %2, i32 %3
487   ; MIPS32-AE-DAG: splat.w $w[[R3:[0-9]+]], [[R1]]{{\[}}[[IDX]]]
488   ; MIPS32-AE-DAG: mfc1 [[R5:\$[0-9]+]], $f[[R3]]
489   ; MIPS32-AE-DAG: splat.w $w[[R4:[0-9]+]], [[R1]]{{\[}}[[IDX]]]
490   ; MIPS32-AE-DAG: mfc1 [[R6:\$[0-9]+]], $f[[R4]]
491   ; MIPS32-AE-NOT: sra
492
493   ret i64 %4
494   ; MIPS32-AE: .size extract_sext_v2i64_vidx
495 }
496
497 define i32 @extract_zext_v16i8_vidx() nounwind {
498   ; MIPS32-AE-LABEL: extract_zext_v16i8_vidx:
499
500   %1 = load <16 x i8>* @v16i8
501   ; MIPS32-AE-DAG: lw [[PTR_V:\$[0-9]+]], %got(v16i8)(
502   ; MIPS32-AE-DAG: ld.b [[R1:\$w[0-9]+]], 0([[PTR_V]])
503
504   %2 = add <16 x i8> %1, %1
505   ; MIPS32-AE-DAG: addv.b [[R2:\$w[0-9]+]], [[R1]], [[R1]]
506
507   %3 = load i32* @i32
508   ; MIPS32-AE-DAG: lw [[PTR_I:\$[0-9]+]], %got(i32)(
509   ; MIPS32-AE-DAG: lw [[IDX:\$[0-9]+]], 0([[PTR_I]])
510
511   %4 = extractelement <16 x i8> %2, i32 %3
512   %5 = zext i8 %4 to i32
513   ; MIPS32-AE-DAG: splat.b $w[[R3:[0-9]+]], [[R1]]{{\[}}[[IDX]]]
514   ; MIPS32-AE-DAG: mfc1 [[R5:\$[0-9]+]], $f[[R3]]
515   ; MIPS32-AE-DAG: srl [[R6:\$[0-9]+]], [[R5]], 24
516
517   ret i32 %5
518   ; MIPS32-AE: .size extract_zext_v16i8_vidx
519 }
520
521 define i32 @extract_zext_v8i16_vidx() nounwind {
522   ; MIPS32-AE-LABEL: extract_zext_v8i16_vidx:
523
524   %1 = load <8 x i16>* @v8i16
525   ; MIPS32-AE-DAG: lw [[PTR_V:\$[0-9]+]], %got(v8i16)(
526   ; MIPS32-AE-DAG: ld.h [[R1:\$w[0-9]+]], 0([[PTR_V]])
527
528   %2 = add <8 x i16> %1, %1
529   ; MIPS32-AE-DAG: addv.h [[R2:\$w[0-9]+]], [[R1]], [[R1]]
530
531   %3 = load i32* @i32
532   ; MIPS32-AE-DAG: lw [[PTR_I:\$[0-9]+]], %got(i32)(
533   ; MIPS32-AE-DAG: lw [[IDX:\$[0-9]+]], 0([[PTR_I]])
534
535   %4 = extractelement <8 x i16> %2, i32 %3
536   %5 = zext i16 %4 to i32
537   ; MIPS32-AE-DAG: splat.h $w[[R3:[0-9]+]], [[R1]]{{\[}}[[IDX]]]
538   ; MIPS32-AE-DAG: mfc1 [[R5:\$[0-9]+]], $f[[R3]]
539   ; MIPS32-AE-DAG: srl [[R6:\$[0-9]+]], [[R5]], 16
540
541   ret i32 %5
542   ; MIPS32-AE: .size extract_zext_v8i16_vidx
543 }
544
545 define i32 @extract_zext_v4i32_vidx() nounwind {
546   ; MIPS32-AE-LABEL: extract_zext_v4i32_vidx:
547
548   %1 = load <4 x i32>* @v4i32
549   ; MIPS32-AE-DAG: lw [[PTR_V:\$[0-9]+]], %got(v4i32)(
550   ; MIPS32-AE-DAG: ld.w [[R1:\$w[0-9]+]], 0([[PTR_V]])
551
552   %2 = add <4 x i32> %1, %1
553   ; MIPS32-AE-DAG: addv.w [[R2:\$w[0-9]+]], [[R1]], [[R1]]
554
555   %3 = load i32* @i32
556   ; MIPS32-AE-DAG: lw [[PTR_I:\$[0-9]+]], %got(i32)(
557   ; MIPS32-AE-DAG: lw [[IDX:\$[0-9]+]], 0([[PTR_I]])
558
559   %4 = extractelement <4 x i32> %2, i32 %3
560   ; MIPS32-AE-DAG: splat.w $w[[R3:[0-9]+]], [[R1]]{{\[}}[[IDX]]]
561   ; MIPS32-AE-DAG: mfc1 [[R5:\$[0-9]+]], $f[[R3]]
562   ; MIPS32-AE-NOT: srl
563
564   ret i32 %4
565   ; MIPS32-AE: .size extract_zext_v4i32_vidx
566 }
567
568 define i64 @extract_zext_v2i64_vidx() nounwind {
569   ; MIPS32-AE-LABEL: extract_zext_v2i64_vidx:
570
571   %1 = load <2 x i64>* @v2i64
572   ; MIPS32-AE-DAG: lw [[PTR_V:\$[0-9]+]], %got(v2i64)(
573   ; MIPS32-AE-DAG: ld.d [[R1:\$w[0-9]+]], 0([[PTR_V]])
574
575   %2 = add <2 x i64> %1, %1
576   ; MIPS32-AE-DAG: addv.d [[R2:\$w[0-9]+]], [[R1]], [[R1]]
577
578   %3 = load i32* @i32
579   ; MIPS32-AE-DAG: lw [[PTR_I:\$[0-9]+]], %got(i32)(
580   ; MIPS32-AE-DAG: lw [[IDX:\$[0-9]+]], 0([[PTR_I]])
581
582   %4 = extractelement <2 x i64> %2, i32 %3
583   ; MIPS32-AE-DAG: splat.w $w[[R3:[0-9]+]], [[R1]]{{\[}}[[IDX]]]
584   ; MIPS32-AE-DAG: mfc1 [[R5:\$[0-9]+]], $f[[R3]]
585   ; MIPS32-AE-DAG: splat.w $w[[R4:[0-9]+]], [[R1]]{{\[}}[[IDX]]]
586   ; MIPS32-AE-DAG: mfc1 [[R6:\$[0-9]+]], $f[[R4]]
587   ; MIPS32-AE-NOT: srl
588
589   ret i64 %4
590   ; MIPS32-AE: .size extract_zext_v2i64_vidx
591 }
592
593 define void @insert_v16i8(i32 %a) nounwind {
594   ; MIPS32-AE-LABEL: insert_v16i8:
595
596   %1 = load <16 x i8>* @v16i8
597   ; MIPS32-AE-DAG: ld.b [[R1:\$w[0-9]+]],
598
599   %a2 = trunc i32 %a to i8
600   %a3 = sext i8 %a2 to i32
601   %a4 = trunc i32 %a3 to i8
602   ; MIPS32-AE-NOT: andi
603   ; MIPS32-AE-NOT: sra
604
605   %2 = insertelement <16 x i8> %1, i8 %a4, i32 1
606   ; MIPS32-AE-DAG: insert.b [[R1]][1], $4
607
608   store <16 x i8> %2, <16 x i8>* @v16i8
609   ; MIPS32-AE-DAG: st.b [[R1]]
610
611   ret void
612   ; MIPS32-AE: .size insert_v16i8
613 }
614
615 define void @insert_v8i16(i32 %a) nounwind {
616   ; MIPS32-AE-LABEL: insert_v8i16:
617
618   %1 = load <8 x i16>* @v8i16
619   ; MIPS32-AE-DAG: ld.h [[R1:\$w[0-9]+]],
620
621   %a2 = trunc i32 %a to i16
622   %a3 = sext i16 %a2 to i32
623   %a4 = trunc i32 %a3 to i16
624   ; MIPS32-AE-NOT: andi
625   ; MIPS32-AE-NOT: sra
626
627   %2 = insertelement <8 x i16> %1, i16 %a4, i32 1
628   ; MIPS32-AE-DAG: insert.h [[R1]][1], $4
629
630   store <8 x i16> %2, <8 x i16>* @v8i16
631   ; MIPS32-AE-DAG: st.h [[R1]]
632
633   ret void
634   ; MIPS32-AE: .size insert_v8i16
635 }
636
637 define void @insert_v4i32(i32 %a) nounwind {
638   ; MIPS32-AE-LABEL: insert_v4i32:
639
640   %1 = load <4 x i32>* @v4i32
641   ; MIPS32-AE-DAG: ld.w [[R1:\$w[0-9]+]],
642
643   ; MIPS32-AE-NOT: andi
644   ; MIPS32-AE-NOT: sra
645
646   %2 = insertelement <4 x i32> %1, i32 %a, i32 1
647   ; MIPS32-AE-DAG: insert.w [[R1]][1], $4
648
649   store <4 x i32> %2, <4 x i32>* @v4i32
650   ; MIPS32-AE-DAG: st.w [[R1]]
651
652   ret void
653   ; MIPS32-AE: .size insert_v4i32
654 }
655
656 define void @insert_v2i64(i64 %a) nounwind {
657   ; MIPS32-AE-LABEL: insert_v2i64:
658
659   %1 = load <2 x i64>* @v2i64
660   ; MIPS32-AE-DAG: ld.w [[R1:\$w[0-9]+]],
661
662   ; MIPS32-AE-NOT: andi
663   ; MIPS32-AE-NOT: sra
664
665   %2 = insertelement <2 x i64> %1, i64 %a, i32 1
666   ; MIPS32-AE-DAG: insert.w [[R1]][2], $4
667   ; MIPS32-AE-DAG: insert.w [[R1]][3], $5
668
669   store <2 x i64> %2, <2 x i64>* @v2i64
670   ; MIPS32-AE-DAG: st.w [[R1]]
671
672   ret void
673   ; MIPS32-AE: .size insert_v2i64
674 }
675
676 define void @insert_v16i8_vidx(i32 %a) nounwind {
677   ; MIPS32-AE: insert_v16i8_vidx:
678
679   %1 = load <16 x i8>* @v16i8
680   ; MIPS32-AE-DAG: ld.b [[R1:\$w[0-9]+]],
681
682   %2 = load i32* @i32
683   ; MIPS32-AE-DAG: lw [[PTR_I:\$[0-9]+]], %got(i32)(
684   ; MIPS32-AE-DAG: lw [[IDX:\$[0-9]+]], 0([[PTR_I]])
685
686   %a2 = trunc i32 %a to i8
687   %a3 = sext i8 %a2 to i32
688   %a4 = trunc i32 %a3 to i8
689   ; MIPS32-AE-NOT: andi
690   ; MIPS32-AE-NOT: sra
691
692   %3 = insertelement <16 x i8> %1, i8 %a4, i32 %2
693   ; MIPS32-AE-DAG: sld.b [[R1]], [[R1]]{{\[}}[[IDX]]]
694   ; MIPS32-AE-DAG: insert.b [[R1]][0], $4
695   ; MIPS32-AE-DAG: neg [[NIDX:\$[0-9]+]], [[IDX]]
696   ; MIPS32-AE-DAG: sld.b [[R1]], [[R1]]{{\[}}[[NIDX]]]
697
698   store <16 x i8> %3, <16 x i8>* @v16i8
699   ; MIPS32-AE-DAG: st.b [[R1]]
700
701   ret void
702   ; MIPS32-AE: .size insert_v16i8_vidx
703 }
704
705 define void @insert_v8i16_vidx(i32 %a) nounwind {
706   ; MIPS32-AE: insert_v8i16_vidx:
707
708   %1 = load <8 x i16>* @v8i16
709   ; MIPS32-AE-DAG: ld.h [[R1:\$w[0-9]+]],
710
711   %2 = load i32* @i32
712   ; MIPS32-AE-DAG: lw [[PTR_I:\$[0-9]+]], %got(i32)(
713   ; MIPS32-AE-DAG: lw [[IDX:\$[0-9]+]], 0([[PTR_I]])
714
715   %a2 = trunc i32 %a to i16
716   %a3 = sext i16 %a2 to i32
717   %a4 = trunc i32 %a3 to i16
718   ; MIPS32-AE-NOT: andi
719   ; MIPS32-AE-NOT: sra
720
721   %3 = insertelement <8 x i16> %1, i16 %a4, i32 %2
722   ; MIPS32-AE-DAG: sll [[BIDX:\$[0-9]+]], [[IDX]], 1
723   ; MIPS32-AE-DAG: sld.b [[R1]], [[R1]]{{\[}}[[BIDX]]]
724   ; MIPS32-AE-DAG: insert.h [[R1]][0], $4
725   ; MIPS32-AE-DAG: neg [[NIDX:\$[0-9]+]], [[BIDX]]
726   ; MIPS32-AE-DAG: sld.b [[R1]], [[R1]]{{\[}}[[NIDX]]]
727
728   store <8 x i16> %3, <8 x i16>* @v8i16
729   ; MIPS32-AE-DAG: st.h [[R1]]
730
731   ret void
732   ; MIPS32-AE: .size insert_v8i16_vidx
733 }
734
735 define void @insert_v4i32_vidx(i32 %a) nounwind {
736   ; MIPS32-AE: insert_v4i32_vidx:
737
738   %1 = load <4 x i32>* @v4i32
739   ; MIPS32-AE-DAG: ld.w [[R1:\$w[0-9]+]],
740
741   %2 = load i32* @i32
742   ; MIPS32-AE-DAG: lw [[PTR_I:\$[0-9]+]], %got(i32)(
743   ; MIPS32-AE-DAG: lw [[IDX:\$[0-9]+]], 0([[PTR_I]])
744
745   ; MIPS32-AE-NOT: andi
746   ; MIPS32-AE-NOT: sra
747
748   %3 = insertelement <4 x i32> %1, i32 %a, i32 %2
749   ; MIPS32-AE-DAG: sll [[BIDX:\$[0-9]+]], [[IDX]], 2
750   ; MIPS32-AE-DAG: sld.b [[R1]], [[R1]]{{\[}}[[BIDX]]]
751   ; MIPS32-AE-DAG: insert.w [[R1]][0], $4
752   ; MIPS32-AE-DAG: neg [[NIDX:\$[0-9]+]], [[BIDX]]
753   ; MIPS32-AE-DAG: sld.b [[R1]], [[R1]]{{\[}}[[NIDX]]]
754
755   store <4 x i32> %3, <4 x i32>* @v4i32
756   ; MIPS32-AE-DAG: st.w [[R1]]
757
758   ret void
759   ; MIPS32-AE: .size insert_v4i32_vidx
760 }
761
762 define void @insert_v2i64_vidx(i64 %a) nounwind {
763   ; MIPS32-AE: insert_v2i64_vidx:
764
765   %1 = load <2 x i64>* @v2i64
766   ; MIPS32-AE-DAG: ld.w [[R1:\$w[0-9]+]],
767
768   %2 = load i32* @i32
769   ; MIPS32-AE-DAG: lw [[PTR_I:\$[0-9]+]], %got(i32)(
770   ; MIPS32-AE-DAG: lw [[IDX:\$[0-9]+]], 0([[PTR_I]])
771
772   ; MIPS32-AE-NOT: andi
773   ; MIPS32-AE-NOT: sra
774
775   %3 = insertelement <2 x i64> %1, i64 %a, i32 %2
776   ; TODO: This code could be a lot better but it works. The legalizer splits
777   ; 64-bit inserts into two 32-bit inserts because there is no i64 type on
778   ; MIPS32. The obvious optimisation is to perform both insert.w's at once while
779   ; the vector is rotated.
780   ; MIPS32-AE-DAG: sll [[BIDX:\$[0-9]+]], [[IDX]], 2
781   ; MIPS32-AE-DAG: sld.b [[R1]], [[R1]]{{\[}}[[BIDX]]]
782   ; MIPS32-AE-DAG: insert.w [[R1]][0], $4
783   ; MIPS32-AE-DAG: neg [[NIDX:\$[0-9]+]], [[BIDX]]
784   ; MIPS32-AE-DAG: sld.b [[R1]], [[R1]]{{\[}}[[NIDX]]]
785   ; MIPS32-AE-DAG: addiu [[IDX2:\$[0-9]+]], [[IDX]], 1
786   ; MIPS32-AE-DAG: sll [[BIDX:\$[0-9]+]], [[IDX2]], 2
787   ; MIPS32-AE-DAG: sld.b [[R1]], [[R1]]{{\[}}[[BIDX]]]
788   ; MIPS32-AE-DAG: insert.w [[R1]][0], $5
789   ; MIPS32-AE-DAG: neg [[NIDX:\$[0-9]+]], [[BIDX]]
790   ; MIPS32-AE-DAG: sld.b [[R1]], [[R1]]{{\[}}[[NIDX]]]
791
792   store <2 x i64> %3, <2 x i64>* @v2i64
793   ; MIPS32-AE-DAG: st.w [[R1]]
794
795   ret void
796   ; MIPS32-AE: .size insert_v2i64_vidx
797 }
798
799 define void @truncstore() nounwind {
800   ; MIPS32-AE-LABEL: truncstore:
801
802   store volatile <4 x i8> <i8 -1, i8 -1, i8 -1, i8 -1>, <4 x i8>*@v4i8
803   ; TODO: What code should be emitted?
804
805   ret void
806   ; MIPS32-AE: .size truncstore
807 }