blob: b21468a98a8ba63e0c04bacf68db6b119b44dbbb [file] [log] [blame]
Scott Michel8b6b4202007-12-04 22:35:58 +00001//==- SPUInstrInfo.td - Describe the Cell SPU Instructions -*- tablegen -*-==//
2//
3// The LLVM Compiler Infrastructure
4//
Chris Lattner081ce942007-12-29 20:36:04 +00005// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
Scott Michel8b6b4202007-12-04 22:35:58 +00007//
8//===----------------------------------------------------------------------===//
9// Cell SPU Instructions:
10//===----------------------------------------------------------------------===//
11
12//===----------------------------------------------------------------------===//
13// TODO Items (not urgent today, but would be nice, low priority)
14//
15// ANDBI, ORBI: SPU constructs a 4-byte constant for these instructions by
16// concatenating the byte argument b as "bbbb". Could recognize this bit pattern
17// in 16-bit and 32-bit constants and reduce instruction count.
18//===----------------------------------------------------------------------===//
19
20//===----------------------------------------------------------------------===//
21// Pseudo instructions:
22//===----------------------------------------------------------------------===//
23
24let hasCtrlDep = 1, Defs = [R1], Uses = [R1] in {
25 def ADJCALLSTACKDOWN : Pseudo<(outs), (ins u16imm:$amt),
26 "${:comment} ADJCALLSTACKDOWN",
27 [(callseq_start imm:$amt)]>;
28 def ADJCALLSTACKUP : Pseudo<(outs), (ins u16imm:$amt),
29 "${:comment} ADJCALLSTACKUP",
30 [(callseq_end imm:$amt)]>;
31}
32
33//===----------------------------------------------------------------------===//
34// DWARF debugging Pseudo Instructions
35//===----------------------------------------------------------------------===//
36
37def DWARF_LOC : Pseudo<(outs), (ins i32imm:$line, i32imm:$col, i32imm:$file),
38 "${:comment} .loc $file, $line, $col",
39 [(dwarf_loc (i32 imm:$line), (i32 imm:$col),
40 (i32 imm:$file))]>;
41
42//===----------------------------------------------------------------------===//
43// Loads:
44// NB: The ordering is actually important, since the instruction selection
45// will try each of the instructions in sequence, i.e., the D-form first with
46// the 10-bit displacement, then the A-form with the 16 bit displacement, and
47// finally the X-form with the register-register.
48//===----------------------------------------------------------------------===//
49
Chris Lattner1a1932c2008-01-06 23:38:27 +000050let isSimpleLoad = 1 in {
Scott Michelf9f42e62008-01-29 02:16:57 +000051 class LoadDFormVec<ValueType vectype>
52 : RI10Form<0b00101100, (outs VECREG:$rT), (ins memri10:$src),
53 "lqd\t$rT, $src",
54 LoadStore,
55 [(set (vectype VECREG:$rT), (load dform_addr:$src))]>
56 { }
Scott Michel8b6b4202007-12-04 22:35:58 +000057
Scott Michelf9f42e62008-01-29 02:16:57 +000058 class LoadDForm<RegisterClass rclass>
59 : RI10Form<0b00101100, (outs rclass:$rT), (ins memri10:$src),
60 "lqd\t$rT, $src",
61 LoadStore,
62 [(set rclass:$rT, (load dform_addr:$src))]>
63 { }
Scott Michel8b6b4202007-12-04 22:35:58 +000064
Scott Michelf9f42e62008-01-29 02:16:57 +000065 multiclass LoadDForms
66 {
67 def v16i8: LoadDFormVec<v16i8>;
68 def v8i16: LoadDFormVec<v8i16>;
69 def v4i32: LoadDFormVec<v4i32>;
70 def v2i64: LoadDFormVec<v2i64>;
71 def v4f32: LoadDFormVec<v4f32>;
72 def v2f64: LoadDFormVec<v2f64>;
Scott Michel8b6b4202007-12-04 22:35:58 +000073
Scott Michelf9f42e62008-01-29 02:16:57 +000074 def r128: LoadDForm<GPRC>;
75 def r64: LoadDForm<R64C>;
76 def r32: LoadDForm<R32C>;
77 def f32: LoadDForm<R32FP>;
78 def f64: LoadDForm<R64FP>;
79 def r16: LoadDForm<R16C>;
80 def r8: LoadDForm<R8C>;
81 }
Scott Michel8b6b4202007-12-04 22:35:58 +000082
Scott Michelf9f42e62008-01-29 02:16:57 +000083 class LoadAFormVec<ValueType vectype>
84 : RI16Form<0b100001100, (outs VECREG:$rT), (ins addr256k:$src),
85 "lqa\t$rT, $src",
86 LoadStore,
87 [(set (vectype VECREG:$rT), (load aform_addr:$src))]>
88 { }
Scott Michel8b6b4202007-12-04 22:35:58 +000089
Scott Michelf9f42e62008-01-29 02:16:57 +000090 class LoadAForm<RegisterClass rclass>
91 : RI16Form<0b100001100, (outs rclass:$rT), (ins addr256k:$src),
92 "lqa\t$rT, $src",
93 LoadStore,
94 [(set rclass:$rT, (load aform_addr:$src))]>
95 { }
Scott Michel8b6b4202007-12-04 22:35:58 +000096
Scott Michelf9f42e62008-01-29 02:16:57 +000097 multiclass LoadAForms
98 {
99 def v16i8: LoadAFormVec<v16i8>;
100 def v8i16: LoadAFormVec<v8i16>;
101 def v4i32: LoadAFormVec<v4i32>;
102 def v2i64: LoadAFormVec<v2i64>;
103 def v4f32: LoadAFormVec<v4f32>;
104 def v2f64: LoadAFormVec<v2f64>;
Scott Michel8b6b4202007-12-04 22:35:58 +0000105
Scott Michelf9f42e62008-01-29 02:16:57 +0000106 def r128: LoadAForm<GPRC>;
107 def r64: LoadAForm<R64C>;
108 def r32: LoadAForm<R32C>;
109 def f32: LoadAForm<R32FP>;
110 def f64: LoadAForm<R64FP>;
111 def r16: LoadAForm<R16C>;
112 def r8: LoadAForm<R8C>;
113 }
Scott Michel8b6b4202007-12-04 22:35:58 +0000114
Scott Michelf9f42e62008-01-29 02:16:57 +0000115 class LoadXFormVec<ValueType vectype>
116 : RRForm<0b00100011100, (outs VECREG:$rT), (ins memrr:$src),
117 "lqx\t$rT, $src",
118 LoadStore,
119 [(set (vectype VECREG:$rT), (load xform_addr:$src))]>
120 { }
Scott Michel8b6b4202007-12-04 22:35:58 +0000121
Scott Michelf9f42e62008-01-29 02:16:57 +0000122 class LoadXForm<RegisterClass rclass>
123 : RRForm<0b00100011100, (outs rclass:$rT), (ins memrr:$src),
124 "lqx\t$rT, $src",
125 LoadStore,
126 [(set rclass:$rT, (load xform_addr:$src))]>
127 { }
Scott Michel8b6b4202007-12-04 22:35:58 +0000128
Scott Michelf9f42e62008-01-29 02:16:57 +0000129 multiclass LoadXForms
130 {
131 def v16i8: LoadXFormVec<v16i8>;
132 def v8i16: LoadXFormVec<v8i16>;
133 def v4i32: LoadXFormVec<v4i32>;
134 def v2i64: LoadXFormVec<v2i64>;
135 def v4f32: LoadXFormVec<v4f32>;
136 def v2f64: LoadXFormVec<v2f64>;
Scott Michel8b6b4202007-12-04 22:35:58 +0000137
Scott Michelf9f42e62008-01-29 02:16:57 +0000138 def r128: LoadXForm<GPRC>;
139 def r64: LoadXForm<R64C>;
140 def r32: LoadXForm<R32C>;
141 def f32: LoadXForm<R32FP>;
142 def f64: LoadXForm<R64FP>;
143 def r16: LoadXForm<R16C>;
144 def r8: LoadXForm<R8C>;
145 }
Scott Michel8b6b4202007-12-04 22:35:58 +0000146
Scott Michelf9f42e62008-01-29 02:16:57 +0000147 defm LQA : LoadAForms;
148 defm LQD : LoadDForms;
149 defm LQX : LoadXForms;
Scott Michel438be252007-12-17 22:32:34 +0000150
Scott Michel8b6b4202007-12-04 22:35:58 +0000151/* Load quadword, PC relative: Not much use at this point in time.
Scott Michelf9f42e62008-01-29 02:16:57 +0000152 Might be of use later for relocatable code. It's effectively the
153 same as LQA, but uses PC-relative addressing.
Scott Michel8b6b4202007-12-04 22:35:58 +0000154 def LQR : RI16Form<0b111001100, (outs VECREG:$rT), (ins s16imm:$disp),
155 "lqr\t$rT, $disp", LoadStore,
156 [(set VECREG:$rT, (load iaddr:$disp))]>;
157 */
Scott Michel8b6b4202007-12-04 22:35:58 +0000158}
159
160//===----------------------------------------------------------------------===//
161// Stores:
162//===----------------------------------------------------------------------===//
Scott Michelf9f42e62008-01-29 02:16:57 +0000163class StoreDFormVec<ValueType vectype>
164 : RI10Form<0b00100100, (outs), (ins VECREG:$rT, memri10:$src),
165 "stqd\t$rT, $src",
166 LoadStore,
167 [(store (vectype VECREG:$rT), dform_addr:$src)]>
168{ }
Scott Michel8b6b4202007-12-04 22:35:58 +0000169
Scott Michelf9f42e62008-01-29 02:16:57 +0000170class StoreDForm<RegisterClass rclass>
171 : RI10Form<0b00100100, (outs), (ins rclass:$rT, memri10:$src),
172 "stqd\t$rT, $src",
173 LoadStore,
174 [(store rclass:$rT, dform_addr:$src)]>
175{ }
Scott Michel8b6b4202007-12-04 22:35:58 +0000176
Scott Michelf9f42e62008-01-29 02:16:57 +0000177multiclass StoreDForms
178{
179 def v16i8: StoreDFormVec<v16i8>;
180 def v8i16: StoreDFormVec<v8i16>;
181 def v4i32: StoreDFormVec<v4i32>;
182 def v2i64: StoreDFormVec<v2i64>;
183 def v4f32: StoreDFormVec<v4f32>;
184 def v2f64: StoreDFormVec<v2f64>;
Scott Michel8b6b4202007-12-04 22:35:58 +0000185
Scott Michelf9f42e62008-01-29 02:16:57 +0000186 def r128: StoreDForm<GPRC>;
187 def r64: StoreDForm<R64C>;
188 def r32: StoreDForm<R32C>;
189 def f32: StoreDForm<R32FP>;
190 def f64: StoreDForm<R64FP>;
191 def r16: StoreDForm<R16C>;
192 def r8: StoreDForm<R8C>;
193}
Scott Michel8b6b4202007-12-04 22:35:58 +0000194
Scott Michelf9f42e62008-01-29 02:16:57 +0000195class StoreAFormVec<ValueType vectype>
196 : RI16Form<0b0010010, (outs), (ins VECREG:$rT, addr256k:$src),
197 "stqa\t$rT, $src",
198 LoadStore,
199 [(store (vectype VECREG:$rT), aform_addr:$src)]>
200{ }
Scott Michel8b6b4202007-12-04 22:35:58 +0000201
Scott Michelf9f42e62008-01-29 02:16:57 +0000202class StoreAForm<RegisterClass rclass>
203 : RI16Form<0b001001, (outs), (ins rclass:$rT, addr256k:$src),
204 "stqa\t$rT, $src",
205 LoadStore,
206 [(store rclass:$rT, aform_addr:$src)]>
207{ }
Scott Michel8b6b4202007-12-04 22:35:58 +0000208
Scott Michelf9f42e62008-01-29 02:16:57 +0000209multiclass StoreAForms
210{
211 def v16i8: StoreAFormVec<v16i8>;
212 def v8i16: StoreAFormVec<v8i16>;
213 def v4i32: StoreAFormVec<v4i32>;
214 def v2i64: StoreAFormVec<v2i64>;
215 def v4f32: StoreAFormVec<v4f32>;
216 def v2f64: StoreAFormVec<v2f64>;
Scott Michel8b6b4202007-12-04 22:35:58 +0000217
Scott Michelf9f42e62008-01-29 02:16:57 +0000218 def r128: StoreAForm<GPRC>;
219 def r64: StoreAForm<R64C>;
220 def r32: StoreAForm<R32C>;
221 def f32: StoreAForm<R32FP>;
222 def f64: StoreAForm<R64FP>;
223 def r16: StoreAForm<R16C>;
224 def r8: StoreAForm<R8C>;
225}
Scott Michel8b6b4202007-12-04 22:35:58 +0000226
Scott Michelf9f42e62008-01-29 02:16:57 +0000227class StoreXFormVec<ValueType vectype>
228 : RRForm<0b00100100, (outs), (ins VECREG:$rT, memrr:$src),
229 "stqx\t$rT, $src",
230 LoadStore,
231 [(store (vectype VECREG:$rT), xform_addr:$src)]>
232{ }
Scott Michel8b6b4202007-12-04 22:35:58 +0000233
Scott Michelf9f42e62008-01-29 02:16:57 +0000234class StoreXForm<RegisterClass rclass>
235 : RRForm<0b00100100, (outs), (ins rclass:$rT, memrr:$src),
236 "stqx\t$rT, $src",
237 LoadStore,
238 [(store rclass:$rT, xform_addr:$src)]>
239{ }
Scott Michel8b6b4202007-12-04 22:35:58 +0000240
Scott Michelf9f42e62008-01-29 02:16:57 +0000241multiclass StoreXForms
242{
243 def v16i8: StoreXFormVec<v16i8>;
244 def v8i16: StoreXFormVec<v8i16>;
245 def v4i32: StoreXFormVec<v4i32>;
246 def v2i64: StoreXFormVec<v2i64>;
247 def v4f32: StoreXFormVec<v4f32>;
248 def v2f64: StoreXFormVec<v2f64>;
Scott Michel8b6b4202007-12-04 22:35:58 +0000249
Scott Michelf9f42e62008-01-29 02:16:57 +0000250 def r128: StoreXForm<GPRC>;
251 def r64: StoreXForm<R64C>;
252 def r32: StoreXForm<R32C>;
253 def f32: StoreXForm<R32FP>;
254 def f64: StoreXForm<R64FP>;
255 def r16: StoreXForm<R16C>;
256 def r8: StoreXForm<R8C>;
257}
Scott Michel8b6b4202007-12-04 22:35:58 +0000258
Scott Michelf9f42e62008-01-29 02:16:57 +0000259defm STQD : StoreDForms;
260defm STQA : StoreAForms;
261defm STQX : StoreXForms;
Scott Michel8b6b4202007-12-04 22:35:58 +0000262
263/* Store quadword, PC relative: Not much use at this point in time. Might
Scott Michelf9f42e62008-01-29 02:16:57 +0000264 be useful for relocatable code.
Chris Lattneref8d6082008-01-06 06:44:58 +0000265def STQR : RI16Form<0b111000100, (outs), (ins VECREG:$rT, s16imm:$disp),
266 "stqr\t$rT, $disp", LoadStore,
267 [(store VECREG:$rT, iaddr:$disp)]>;
268*/
Scott Michel8b6b4202007-12-04 22:35:58 +0000269
270//===----------------------------------------------------------------------===//
271// Generate Controls for Insertion:
272//===----------------------------------------------------------------------===//
273
274def CBD :
275 RI7Form<0b10101111100, (outs VECREG:$rT), (ins memri7:$src),
276 "cbd\t$rT, $src", ShuffleOp,
277 [(set (v16i8 VECREG:$rT), (SPUvecinsmask dform2_addr:$src))]>;
278
279def CBX : RRForm<0b00101011100, (outs VECREG:$rT), (ins memrr:$src),
280 "cbx\t$rT, $src", ShuffleOp,
281 [(set (v16i8 VECREG:$rT), (SPUvecinsmask xform_addr:$src))]>;
282
283def CHD : RI7Form<0b10101111100, (outs VECREG:$rT), (ins memri7:$src),
284 "chd\t$rT, $src", ShuffleOp,
285 [(set (v8i16 VECREG:$rT), (SPUvecinsmask dform2_addr:$src))]>;
286
287def CHX : RRForm<0b10101011100, (outs VECREG:$rT), (ins memrr:$src),
288 "chx\t$rT, $src", ShuffleOp,
289 [(set (v8i16 VECREG:$rT), (SPUvecinsmask xform_addr:$src))]>;
290
291def CWD : RI7Form<0b01101111100, (outs VECREG:$rT), (ins memri7:$src),
292 "cwd\t$rT, $src", ShuffleOp,
293 [(set (v4i32 VECREG:$rT), (SPUvecinsmask dform2_addr:$src))]>;
294
295def CWX : RRForm<0b01101011100, (outs VECREG:$rT), (ins memrr:$src),
296 "cwx\t$rT, $src", ShuffleOp,
297 [(set (v4i32 VECREG:$rT), (SPUvecinsmask xform_addr:$src))]>;
298
299def CDD : RI7Form<0b11101111100, (outs VECREG:$rT), (ins memri7:$src),
300 "cdd\t$rT, $src", ShuffleOp,
301 [(set (v2i64 VECREG:$rT), (SPUvecinsmask dform2_addr:$src))]>;
302
303def CDX : RRForm<0b11101011100, (outs VECREG:$rT), (ins memrr:$src),
304 "cdx\t$rT, $src", ShuffleOp,
305 [(set (v2i64 VECREG:$rT), (SPUvecinsmask xform_addr:$src))]>;
306
307//===----------------------------------------------------------------------===//
308// Constant formation:
309//===----------------------------------------------------------------------===//
310
311def ILHv8i16:
312 RI16Form<0b110000010, (outs VECREG:$rT), (ins s16imm:$val),
313 "ilh\t$rT, $val", ImmLoad,
314 [(set (v8i16 VECREG:$rT), (v8i16 v8i16SExt16Imm:$val))]>;
315
316def ILHr16:
317 RI16Form<0b110000010, (outs R16C:$rT), (ins s16imm:$val),
318 "ilh\t$rT, $val", ImmLoad,
319 [(set R16C:$rT, immSExt16:$val)]>;
320
Scott Michel438be252007-12-17 22:32:34 +0000321// Cell SPU doesn't have a native 8-bit immediate load, but ILH works ("with
322// the right constant")
323def ILHr8:
324 RI16Form<0b110000010, (outs R8C:$rT), (ins s16imm_i8:$val),
325 "ilh\t$rT, $val", ImmLoad,
326 [(set R8C:$rT, immSExt8:$val)]>;
327
Scott Michel8b6b4202007-12-04 22:35:58 +0000328// IL does sign extension!
329def ILr64:
330 RI16Form<0b100000010, (outs R64C:$rT), (ins s16imm_i64:$val),
331 "il\t$rT, $val", ImmLoad,
332 [(set R64C:$rT, immSExt16:$val)]>;
333
334def ILv2i64:
335 RI16Form<0b100000010, (outs VECREG:$rT), (ins s16imm_i64:$val),
336 "il\t$rT, $val", ImmLoad,
337 [(set VECREG:$rT, (v2i64 v2i64SExt16Imm:$val))]>;
338
339def ILv4i32:
340 RI16Form<0b100000010, (outs VECREG:$rT), (ins s16imm:$val),
341 "il\t$rT, $val", ImmLoad,
342 [(set VECREG:$rT, (v4i32 v4i32SExt16Imm:$val))]>;
343
344def ILr32:
345 RI16Form<0b100000010, (outs R32C:$rT), (ins s16imm_i32:$val),
346 "il\t$rT, $val", ImmLoad,
347 [(set R32C:$rT, immSExt16:$val)]>;
348
349def ILf32:
350 RI16Form<0b100000010, (outs R32FP:$rT), (ins s16imm_f32:$val),
351 "il\t$rT, $val", ImmLoad,
352 [(set R32FP:$rT, (SPUFPconstant fpimmSExt16:$val))]>;
353
354def ILf64:
355 RI16Form<0b100000010, (outs R64FP:$rT), (ins s16imm_f64:$val),
356 "il\t$rT, $val", ImmLoad,
357 [(set R64FP:$rT, (SPUFPconstant fpimmSExt16:$val))]>;
358
359def ILHUv4i32:
360 RI16Form<0b010000010, (outs VECREG:$rT), (ins u16imm:$val),
361 "ilhu\t$rT, $val", ImmLoad,
362 [(set VECREG:$rT, (v4i32 immILHUvec:$val))]>;
363
364def ILHUr32:
365 RI16Form<0b010000010, (outs R32C:$rT), (ins u16imm:$val),
366 "ilhu\t$rT, $val", ImmLoad,
367 [(set R32C:$rT, hi16:$val)]>;
368
369// ILHUf32: Used to custom lower float constant loads
370def ILHUf32:
371 RI16Form<0b010000010, (outs R32FP:$rT), (ins f16imm:$val),
372 "ilhu\t$rT, $val", ImmLoad,
373 [(set R32FP:$rT, (SPUFPconstant hi16_f32:$val))]>;
374
375// ILHUhi: Used for loading high portion of an address. Note the symbolHi
376// printer used for the operand.
377def ILHUhi : RI16Form<0b010000010, (outs R32C:$rT), (ins symbolHi:$val),
378 "ilhu\t$rT, $val", ImmLoad,
379 [(set R32C:$rT, hi16:$val)]>;
380
381// Immediate load address (can also be used to load 18-bit unsigned constants,
382// see the zext 16->32 pattern)
383def ILAr64:
384 RI18Form<0b1000010, (outs R64C:$rT), (ins u18imm_i64:$val),
385 "ila\t$rT, $val", LoadNOP,
386 [(set R64C:$rT, imm18:$val)]>;
387
388// TODO: ILAv2i64
389
390def ILAv2i64:
391 RI18Form<0b1000010, (outs VECREG:$rT), (ins u18imm:$val),
392 "ila\t$rT, $val", LoadNOP,
393 [(set (v2i64 VECREG:$rT), v2i64Uns18Imm:$val)]>;
394
395def ILAv4i32:
396 RI18Form<0b1000010, (outs VECREG:$rT), (ins u18imm:$val),
397 "ila\t$rT, $val", LoadNOP,
398 [(set (v4i32 VECREG:$rT), v4i32Uns18Imm:$val)]>;
399
400def ILAr32:
401 RI18Form<0b1000010, (outs R32C:$rT), (ins u18imm:$val),
402 "ila\t$rT, $val", LoadNOP,
403 [(set R32C:$rT, imm18:$val)]>;
404
405def ILAf32:
406 RI18Form<0b1000010, (outs R32FP:$rT), (ins f18imm:$val),
407 "ila\t$rT, $val", LoadNOP,
408 [(set R32FP:$rT, (SPUFPconstant fpimm18:$val))]>;
409
410def ILAf64:
411 RI18Form<0b1000010, (outs R64FP:$rT), (ins f18imm_f64:$val),
412 "ila\t$rT, $val", LoadNOP,
413 [(set R64FP:$rT, (SPUFPconstant fpimm18:$val))]>;
414
415def ILAlo:
416 RI18Form<0b1000010, (outs R32C:$rT), (ins symbolLo:$val),
417 "ila\t$rT, $val", ImmLoad,
418 [(set R32C:$rT, imm18:$val)]>;
419
420def ILAlsa:
421 RI18Form<0b1000010, (outs R32C:$rT), (ins symbolLSA:$val),
422 "ila\t$rT, $val", ImmLoad,
423 [/* no pattern */]>;
424
425// Immediate OR, Halfword Lower: The "other" part of loading large constants
426// into 32-bit registers. See the anonymous pattern Pat<(i32 imm:$imm), ...>
427// Note that these are really two operand instructions, but they're encoded
428// as three operands with the first two arguments tied-to each other.
429
430def IOHLvec:
431 RI16Form<0b100000110, (outs VECREG:$rT), (ins VECREG:$rS, u16imm:$val),
432 "iohl\t$rT, $val", ImmLoad,
433 [/* insert intrinsic here */]>,
434 RegConstraint<"$rS = $rT">,
435 NoEncode<"$rS">;
436
437def IOHLr32:
438 RI16Form<0b100000110, (outs R32C:$rT), (ins R32C:$rS, i32imm:$val),
439 "iohl\t$rT, $val", ImmLoad,
440 [/* insert intrinsic here */]>,
441 RegConstraint<"$rS = $rT">,
442 NoEncode<"$rS">;
443
444def IOHLf32:
445 RI16Form<0b100000110, (outs R32FP:$rT), (ins R32FP:$rS, f32imm:$val),
446 "iohl\t$rT, $val", ImmLoad,
447 [/* insert intrinsic here */]>,
448 RegConstraint<"$rS = $rT">,
449 NoEncode<"$rS">;
450
Scott Micheldbac4cf2008-01-11 02:53:15 +0000451def IOHLlo:
452 RI16Form<0b100000110, (outs R32C:$rT), (ins R32C:$rS, symbolLo:$val),
453 "iohl\t$rT, $val", ImmLoad,
454 [/* no pattern */]>,
455 RegConstraint<"$rS = $rT">,
456 NoEncode<"$rS">;
457
Scott Michel8b6b4202007-12-04 22:35:58 +0000458// Form select mask for bytes using immediate, used in conjunction with the
459// SELB instruction:
460
Scott Michelf9f42e62008-01-29 02:16:57 +0000461class FSMBIVec<ValueType vectype>
462 : RI16Form<0b101001100, (outs VECREG:$rT), (ins u16imm:$val),
463 "fsmbi\t$rT, $val",
464 SelectOp,
465 [(set (vectype VECREG:$rT), (SPUfsmbi immU16:$val))]>
466{ }
Scott Michel8b6b4202007-12-04 22:35:58 +0000467
Scott Michelf9f42e62008-01-29 02:16:57 +0000468multiclass FSMBIs
469{
470 def v16i8: FSMBIVec<v16i8>;
471 def v8i16: FSMBIVec<v8i16>;
472 def v4i32: FSMBIVec<v4i32>;
473 def v2i64: FSMBIVec<v2i64>;
474}
Scott Michel8b6b4202007-12-04 22:35:58 +0000475
Scott Michelf9f42e62008-01-29 02:16:57 +0000476defm FSMBI : FSMBIs;
Scott Michel8b6b4202007-12-04 22:35:58 +0000477
478//===----------------------------------------------------------------------===//
479// Integer and Logical Operations:
480//===----------------------------------------------------------------------===//
481
482def AHv8i16:
483 RRForm<0b00010011000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
484 "ah\t$rT, $rA, $rB", IntegerOp,
485 [(set (v8i16 VECREG:$rT), (int_spu_si_ah VECREG:$rA, VECREG:$rB))]>;
486
487def : Pat<(add (v8i16 VECREG:$rA), (v8i16 VECREG:$rB)),
488 (AHv8i16 VECREG:$rA, VECREG:$rB)>;
489
490// [(set (v8i16 VECREG:$rT), (add (v8i16 VECREG:$rA), (v8i16 VECREG:$rB)))]>;
491
492def AHr16:
493 RRForm<0b00010011000, (outs R16C:$rT), (ins R16C:$rA, R16C:$rB),
494 "ah\t$rT, $rA, $rB", IntegerOp,
495 [(set R16C:$rT, (add R16C:$rA, R16C:$rB))]>;
496
497def AHIvec:
498 RI10Form<0b10111000, (outs VECREG:$rT), (ins VECREG:$rA, s10imm:$val),
499 "ahi\t$rT, $rA, $val", IntegerOp,
500 [(set (v8i16 VECREG:$rT), (add (v8i16 VECREG:$rA),
501 v8i16SExt10Imm:$val))]>;
502
503def AHIr16 : RI10Form<0b10111000, (outs R16C:$rT), (ins R16C:$rA, s10imm:$val),
504 "ahi\t$rT, $rA, $val", IntegerOp,
505 [(set R16C:$rT, (add R16C:$rA, v8i16SExt10Imm:$val))]>;
506
507def Avec : RRForm<0b00000011000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
508 "a\t$rT, $rA, $rB", IntegerOp,
509 [(set (v4i32 VECREG:$rT), (add (v4i32 VECREG:$rA), (v4i32 VECREG:$rB)))]>;
510
511def : Pat<(add (v16i8 VECREG:$rA), (v16i8 VECREG:$rB)),
512 (Avec VECREG:$rA, VECREG:$rB)>;
513
514def Ar32 : RRForm<0b00000011000, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
515 "a\t$rT, $rA, $rB", IntegerOp,
516 [(set R32C:$rT, (add R32C:$rA, R32C:$rB))]>;
517
Scott Michel438be252007-12-17 22:32:34 +0000518def Ar8:
519 RRForm<0b00000011000, (outs R8C:$rT), (ins R8C:$rA, R8C:$rB),
520 "a\t$rT, $rA, $rB", IntegerOp,
521 [(set R8C:$rT, (add R8C:$rA, R8C:$rB))]>;
522
Scott Michel8b6b4202007-12-04 22:35:58 +0000523def AIvec:
524 RI10Form<0b00111000, (outs VECREG:$rT), (ins VECREG:$rA, s10imm:$val),
525 "ai\t$rT, $rA, $val", IntegerOp,
526 [(set (v4i32 VECREG:$rT), (add (v4i32 VECREG:$rA),
527 v4i32SExt10Imm:$val))]>;
528
Scott Michel438be252007-12-17 22:32:34 +0000529def AIr32:
530 RI10Form<0b00111000, (outs R32C:$rT), (ins R32C:$rA, s10imm_i32:$val),
531 "ai\t$rT, $rA, $val", IntegerOp,
532 [(set R32C:$rT, (add R32C:$rA, i32ImmSExt10:$val))]>;
Scott Michel8b6b4202007-12-04 22:35:58 +0000533
Scott Michel438be252007-12-17 22:32:34 +0000534def SFHvec:
535 RRForm<0b00010010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
536 "sfh\t$rT, $rA, $rB", IntegerOp,
537 [(set (v8i16 VECREG:$rT), (sub (v8i16 VECREG:$rA),
538 (v8i16 VECREG:$rB)))]>;
Scott Michel8b6b4202007-12-04 22:35:58 +0000539
Scott Michel438be252007-12-17 22:32:34 +0000540def SFHr16:
541 RRForm<0b00010010000, (outs R16C:$rT), (ins R16C:$rA, R16C:$rB),
542 "sfh\t$rT, $rA, $rB", IntegerOp,
543 [(set R16C:$rT, (sub R16C:$rA, R16C:$rB))]>;
Scott Michel8b6b4202007-12-04 22:35:58 +0000544
545def SFHIvec:
546 RI10Form<0b10110000, (outs VECREG:$rT), (ins VECREG:$rA, s10imm:$val),
547 "sfhi\t$rT, $rA, $val", IntegerOp,
548 [(set (v8i16 VECREG:$rT), (sub v8i16SExt10Imm:$val,
549 (v8i16 VECREG:$rA)))]>;
550
551def SFHIr16 : RI10Form<0b10110000, (outs R16C:$rT), (ins R16C:$rA, s10imm:$val),
552 "sfhi\t$rT, $rA, $val", IntegerOp,
553 [(set R16C:$rT, (sub i16ImmSExt10:$val, R16C:$rA))]>;
554
555def SFvec : RRForm<0b00000010000, (outs VECREG:$rT),
556 (ins VECREG:$rA, VECREG:$rB),
557 "sf\t$rT, $rA, $rB", IntegerOp,
558 [(set (v4i32 VECREG:$rT), (sub (v4i32 VECREG:$rA), (v4i32 VECREG:$rB)))]>;
559
560def SFr32 : RRForm<0b00000010000, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
561 "sf\t$rT, $rA, $rB", IntegerOp,
562 [(set R32C:$rT, (sub R32C:$rA, R32C:$rB))]>;
563
564def SFIvec:
565 RI10Form<0b00110000, (outs VECREG:$rT), (ins VECREG:$rA, s10imm:$val),
566 "sfi\t$rT, $rA, $val", IntegerOp,
567 [(set (v4i32 VECREG:$rT), (sub v4i32SExt10Imm:$val,
568 (v4i32 VECREG:$rA)))]>;
569
570def SFIr32 : RI10Form<0b00110000, (outs R32C:$rT),
571 (ins R32C:$rA, s10imm_i32:$val),
572 "sfi\t$rT, $rA, $val", IntegerOp,
573 [(set R32C:$rT, (sub i32ImmSExt10:$val, R32C:$rA))]>;
574
575// ADDX: only available in vector form, doesn't match a pattern.
576def ADDXvec:
577 RRForm<0b00000010110, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB,
578 VECREG:$rCarry),
579 "addx\t$rT, $rA, $rB", IntegerOp,
580 []>,
581 RegConstraint<"$rCarry = $rT">,
582 NoEncode<"$rCarry">;
583
584// CG: only available in vector form, doesn't match a pattern.
585def CGvec:
586 RRForm<0b01000011000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB,
587 VECREG:$rCarry),
588 "cg\t$rT, $rA, $rB", IntegerOp,
589 []>,
590 RegConstraint<"$rCarry = $rT">,
591 NoEncode<"$rCarry">;
592
593// SFX: only available in vector form, doesn't match a pattern
594def SFXvec:
595 RRForm<0b10000010110, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB,
596 VECREG:$rCarry),
597 "sfx\t$rT, $rA, $rB", IntegerOp,
598 []>,
599 RegConstraint<"$rCarry = $rT">,
600 NoEncode<"$rCarry">;
601
602// BG: only available in vector form, doesn't match a pattern.
603def BGvec:
604 RRForm<0b01000010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB,
605 VECREG:$rCarry),
606 "bg\t$rT, $rA, $rB", IntegerOp,
607 []>,
608 RegConstraint<"$rCarry = $rT">,
609 NoEncode<"$rCarry">;
610
611// BGX: only available in vector form, doesn't match a pattern.
612def BGXvec:
613 RRForm<0b11000010110, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB,
614 VECREG:$rCarry),
615 "bgx\t$rT, $rA, $rB", IntegerOp,
616 []>,
617 RegConstraint<"$rCarry = $rT">,
618 NoEncode<"$rCarry">;
619
620// Halfword multiply variants:
621// N.B: These can be used to build up larger quantities (16x16 -> 32)
622
623def MPYv8i16:
624 RRForm<0b00100011110, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
625 "mpy\t$rT, $rA, $rB", IntegerMulDiv,
626 [(set (v8i16 VECREG:$rT), (SPUmpy_v8i16 (v8i16 VECREG:$rA),
627 (v8i16 VECREG:$rB)))]>;
628
629def MPYr16:
630 RRForm<0b00100011110, (outs R16C:$rT), (ins R16C:$rA, R16C:$rB),
631 "mpy\t$rT, $rA, $rB", IntegerMulDiv,
632 [(set R16C:$rT, (mul R16C:$rA, R16C:$rB))]>;
633
634def MPYUv4i32:
635 RRForm<0b00110011110, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
636 "mpyu\t$rT, $rA, $rB", IntegerMulDiv,
637 [(set (v4i32 VECREG:$rT),
638 (SPUmpyu_v4i32 (v4i32 VECREG:$rA), (v4i32 VECREG:$rB)))]>;
639
640def MPYUr16:
641 RRForm<0b00110011110, (outs R32C:$rT), (ins R16C:$rA, R16C:$rB),
642 "mpyu\t$rT, $rA, $rB", IntegerMulDiv,
643 [(set R32C:$rT, (mul (zext R16C:$rA),
644 (zext R16C:$rB)))]>;
645
646def MPYUr32:
647 RRForm<0b00110011110, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
648 "mpyu\t$rT, $rA, $rB", IntegerMulDiv,
649 [(set R32C:$rT, (SPUmpyu_i32 R32C:$rA, R32C:$rB))]>;
650
651// mpyi: multiply 16 x s10imm -> 32 result (custom lowering for 32 bit result,
652// this only produces the lower 16 bits)
653def MPYIvec:
654 RI10Form<0b00101110, (outs VECREG:$rT), (ins VECREG:$rA, s10imm:$val),
655 "mpyi\t$rT, $rA, $val", IntegerMulDiv,
656 [(set (v8i16 VECREG:$rT), (mul (v8i16 VECREG:$rA), v8i16SExt10Imm:$val))]>;
657
658def MPYIr16:
659 RI10Form<0b00101110, (outs R16C:$rT), (ins R16C:$rA, s10imm:$val),
660 "mpyi\t$rT, $rA, $val", IntegerMulDiv,
661 [(set R16C:$rT, (mul R16C:$rA, i16ImmSExt10:$val))]>;
662
663// mpyui: same issues as other multiplies, plus, this doesn't match a
664// pattern... but may be used during target DAG selection or lowering
665def MPYUIvec:
666 RI10Form<0b10101110, (outs VECREG:$rT), (ins VECREG:$rA, s10imm:$val),
667 "mpyui\t$rT, $rA, $val", IntegerMulDiv,
668 []>;
669
670def MPYUIr16:
671 RI10Form<0b10101110, (outs R16C:$rT), (ins R16C:$rA, s10imm:$val),
672 "mpyui\t$rT, $rA, $val", IntegerMulDiv,
673 []>;
674
675// mpya: 16 x 16 + 16 -> 32 bit result
676def MPYAvec:
677 RRRForm<0b0011, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB, VECREG:$rC),
678 "mpya\t$rT, $rA, $rB, $rC", IntegerMulDiv,
679 [(set (v4i32 VECREG:$rT), (add (v4i32 (bitconvert (mul (v8i16 VECREG:$rA),
680 (v8i16 VECREG:$rB)))),
681 (v4i32 VECREG:$rC)))]>;
682
683def MPYAr32:
684 RRRForm<0b0011, (outs R32C:$rT), (ins R16C:$rA, R16C:$rB, R32C:$rC),
685 "mpya\t$rT, $rA, $rB, $rC", IntegerMulDiv,
686 [(set R32C:$rT, (add (sext (mul R16C:$rA, R16C:$rB)),
687 R32C:$rC))]>;
688
689def : Pat<(add (mul (sext R16C:$rA), (sext R16C:$rB)), R32C:$rC),
690 (MPYAr32 R16C:$rA, R16C:$rB, R32C:$rC)>;
691
692def MPYAr32_sextinreg:
693 RRRForm<0b0011, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB, R32C:$rC),
694 "mpya\t$rT, $rA, $rB, $rC", IntegerMulDiv,
695 [(set R32C:$rT, (add (mul (sext_inreg R32C:$rA, i16),
696 (sext_inreg R32C:$rB, i16)),
697 R32C:$rC))]>;
698
699//def MPYAr32:
700// RRRForm<0b0011, (outs R32C:$rT), (ins R16C:$rA, R16C:$rB, R32C:$rC),
701// "mpya\t$rT, $rA, $rB, $rC", IntegerMulDiv,
702// [(set R32C:$rT, (add (sext (mul R16C:$rA, R16C:$rB)),
703// R32C:$rC))]>;
704
705// mpyh: multiply high, used to synthesize 32-bit multiplies
706def MPYHv4i32:
707 RRForm<0b10100011110, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
708 "mpyh\t$rT, $rA, $rB", IntegerMulDiv,
709 [(set (v4i32 VECREG:$rT),
710 (SPUmpyh_v4i32 (v4i32 VECREG:$rA), (v4i32 VECREG:$rB)))]>;
711
712def MPYHr32:
713 RRForm<0b10100011110, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
714 "mpyh\t$rT, $rA, $rB", IntegerMulDiv,
715 [(set R32C:$rT, (SPUmpyh_i32 R32C:$rA, R32C:$rB))]>;
716
717// mpys: multiply high and shift right (returns the top half of
718// a 16-bit multiply, sign extended to 32 bits.)
719def MPYSvec:
720 RRForm<0b11100011110, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
721 "mpys\t$rT, $rA, $rB", IntegerMulDiv,
722 []>;
723
724def MPYSr16:
725 RRForm<0b11100011110, (outs R32C:$rT), (ins R16C:$rA, R16C:$rB),
726 "mpys\t$rT, $rA, $rB", IntegerMulDiv,
727 []>;
728
729// mpyhh: multiply high-high (returns the 32-bit result from multiplying
730// the top 16 bits of the $rA, $rB)
731def MPYHHv8i16:
732 RRForm<0b01100011110, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
733 "mpyhh\t$rT, $rA, $rB", IntegerMulDiv,
734 [(set (v8i16 VECREG:$rT),
735 (SPUmpyhh_v8i16 (v8i16 VECREG:$rA), (v8i16 VECREG:$rB)))]>;
736
737def MPYHHr32:
738 RRForm<0b01100011110, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
739 "mpyhh\t$rT, $rA, $rB", IntegerMulDiv,
740 []>;
741
742// mpyhha: Multiply high-high, add to $rT:
743def MPYHHAvec:
744 RRForm<0b01100010110, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
745 "mpyhha\t$rT, $rA, $rB", IntegerMulDiv,
746 []>;
747
748def MPYHHAr32:
749 RRForm<0b01100010110, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
750 "mpyhha\t$rT, $rA, $rB", IntegerMulDiv,
751 []>;
752
753// mpyhhu: Multiply high-high, unsigned
754def MPYHHUvec:
755 RRForm<0b01110011110, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
756 "mpyhhu\t$rT, $rA, $rB", IntegerMulDiv,
757 []>;
758
759def MPYHHUr32:
760 RRForm<0b01110011110, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
761 "mpyhhu\t$rT, $rA, $rB", IntegerMulDiv,
762 []>;
763
764// mpyhhau: Multiply high-high, unsigned
765def MPYHHAUvec:
766 RRForm<0b01110010110, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
767 "mpyhhau\t$rT, $rA, $rB", IntegerMulDiv,
768 []>;
769
770def MPYHHAUr32:
771 RRForm<0b01110010110, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
772 "mpyhhau\t$rT, $rA, $rB", IntegerMulDiv,
773 []>;
774
775// clz: Count leading zeroes
776def CLZv4i32:
777 RRForm_1<0b10100101010, (outs VECREG:$rT), (ins VECREG:$rA),
778 "clz\t$rT, $rA", IntegerOp,
779 [/* intrinsic */]>;
780
781def CLZr32:
782 RRForm_1<0b10100101010, (outs R32C:$rT), (ins R32C:$rA),
783 "clz\t$rT, $rA", IntegerOp,
784 [(set R32C:$rT, (ctlz R32C:$rA))]>;
785
786// cntb: Count ones in bytes (aka "population count")
787// NOTE: This instruction is really a vector instruction, but the custom
788// lowering code uses it in unorthodox ways to support CTPOP for other
789// data types!
790def CNTBv16i8:
791 RRForm_1<0b00101101010, (outs VECREG:$rT), (ins VECREG:$rA),
792 "cntb\t$rT, $rA", IntegerOp,
793 [(set (v16i8 VECREG:$rT), (SPUcntb_v16i8 (v16i8 VECREG:$rA)))]>;
794
795def CNTBv8i16 :
796 RRForm_1<0b00101101010, (outs VECREG:$rT), (ins VECREG:$rA),
797 "cntb\t$rT, $rA", IntegerOp,
798 [(set (v8i16 VECREG:$rT), (SPUcntb_v8i16 (v8i16 VECREG:$rA)))]>;
799
800def CNTBv4i32 :
801 RRForm_1<0b00101101010, (outs VECREG:$rT), (ins VECREG:$rA),
802 "cntb\t$rT, $rA", IntegerOp,
803 [(set (v4i32 VECREG:$rT), (SPUcntb_v4i32 (v4i32 VECREG:$rA)))]>;
804
805// fsmb: Form select mask for bytes. N.B. Input operand, $rA, is 16-bits
806def FSMB:
807 RRForm_1<0b01101101100, (outs VECREG:$rT), (ins R16C:$rA),
808 "fsmb\t$rT, $rA", SelectOp,
809 []>;
810
811// fsmh: Form select mask for halfwords. N.B., Input operand, $rA, is
812// only 8-bits wide (even though it's input as 16-bits here)
813def FSMH:
814 RRForm_1<0b10101101100, (outs VECREG:$rT), (ins R16C:$rA),
815 "fsmh\t$rT, $rA", SelectOp,
816 []>;
817
818// fsm: Form select mask for words. Like the other fsm* instructions,
819// only the lower 4 bits of $rA are significant.
820def FSM:
821 RRForm_1<0b00101101100, (outs VECREG:$rT), (ins R16C:$rA),
822 "fsm\t$rT, $rA", SelectOp,
823 []>;
824
825// gbb: Gather all low order bits from each byte in $rA into a single 16-bit
826// quantity stored into $rT
827def GBB:
828 RRForm_1<0b01001101100, (outs R16C:$rT), (ins VECREG:$rA),
829 "gbb\t$rT, $rA", GatherOp,
830 []>;
831
832// gbh: Gather all low order bits from each halfword in $rA into a single
833// 8-bit quantity stored in $rT
834def GBH:
835 RRForm_1<0b10001101100, (outs R16C:$rT), (ins VECREG:$rA),
836 "gbh\t$rT, $rA", GatherOp,
837 []>;
838
839// gb: Gather all low order bits from each word in $rA into a single
840// 4-bit quantity stored in $rT
841def GB:
842 RRForm_1<0b00001101100, (outs R16C:$rT), (ins VECREG:$rA),
843 "gb\t$rT, $rA", GatherOp,
844 []>;
845
846// avgb: average bytes
847def AVGB:
848 RRForm<0b11001011000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
849 "avgb\t$rT, $rA, $rB", ByteOp,
850 []>;
851
852// absdb: absolute difference of bytes
853def ABSDB:
854 RRForm<0b11001010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
855 "absdb\t$rT, $rA, $rB", ByteOp,
856 []>;
857
858// sumb: sum bytes into halfwords
859def SUMB:
860 RRForm<0b11001010010, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
861 "sumb\t$rT, $rA, $rB", ByteOp,
862 []>;
863
864// Sign extension operations:
865def XSBHvec:
866 RRForm_1<0b01101101010, (outs VECREG:$rDst), (ins VECREG:$rSrc),
867 "xsbh\t$rDst, $rSrc", IntegerOp,
868 [(set (v8i16 VECREG:$rDst), (sext (v16i8 VECREG:$rSrc)))]>;
869
870// Ordinary form for XSBH
871def XSBHr16:
872 RRForm_1<0b01101101010, (outs R16C:$rDst), (ins R16C:$rSrc),
873 "xsbh\t$rDst, $rSrc", IntegerOp,
874 [(set R16C:$rDst, (sext_inreg R16C:$rSrc, i8))]>;
875
Scott Michel438be252007-12-17 22:32:34 +0000876def XSBHr8:
877 RRForm_1<0b01101101010, (outs R16C:$rDst), (ins R8C:$rSrc),
878 "xsbh\t$rDst, $rSrc", IntegerOp,
879 [(set R16C:$rDst, (sext R8C:$rSrc))]>;
880
Scott Michel8b6b4202007-12-04 22:35:58 +0000881// 32-bit form for XSBH: used to sign extend 8-bit quantities to 16-bit
882// quantities to 32-bit quantities via a 32-bit register (see the sext 8->32
883// pattern below). Intentionally doesn't match a pattern because we want the
884// sext 8->32 pattern to do the work for us, namely because we need the extra
885// XSHWr32.
886def XSBHr32:
887 RRForm_1<0b01101101010, (outs R32C:$rDst), (ins R32C:$rSrc),
888 "xsbh\t$rDst, $rSrc", IntegerOp,
889 [(set R32C:$rDst, (sext_inreg R32C:$rSrc, i8))]>;
890
891// Sign extend halfwords to words:
892def XSHWvec:
893 RRForm_1<0b01101101010, (outs VECREG:$rDest), (ins VECREG:$rSrc),
894 "xshw\t$rDest, $rSrc", IntegerOp,
895 [(set (v4i32 VECREG:$rDest), (sext (v8i16 VECREG:$rSrc)))]>;
896
897def XSHWr32:
898 RRForm_1<0b01101101010, (outs R32C:$rDst), (ins R32C:$rSrc),
899 "xshw\t$rDst, $rSrc", IntegerOp,
900 [(set R32C:$rDst, (sext_inreg R32C:$rSrc, i16))]>;
901
902def XSHWr16:
903 RRForm_1<0b01101101010, (outs R32C:$rDst), (ins R16C:$rSrc),
904 "xshw\t$rDst, $rSrc", IntegerOp,
905 [(set R32C:$rDst, (sext R16C:$rSrc))]>;
906
907def XSWDvec:
908 RRForm_1<0b01100101010, (outs VECREG:$rDst), (ins VECREG:$rSrc),
909 "xswd\t$rDst, $rSrc", IntegerOp,
910 [(set (v2i64 VECREG:$rDst), (sext (v4i32 VECREG:$rSrc)))]>;
911
912def XSWDr64:
913 RRForm_1<0b01100101010, (outs R64C:$rDst), (ins R64C:$rSrc),
914 "xswd\t$rDst, $rSrc", IntegerOp,
915 [(set R64C:$rDst, (sext_inreg R64C:$rSrc, i32))]>;
916
917def XSWDr32:
918 RRForm_1<0b01100101010, (outs R64C:$rDst), (ins R32C:$rSrc),
919 "xswd\t$rDst, $rSrc", IntegerOp,
920 [(set R64C:$rDst, (SPUsext32_to_64 R32C:$rSrc))]>;
921
922def : Pat<(sext R32C:$inp),
923 (XSWDr32 R32C:$inp)>;
924
925// AND operations
926def ANDv16i8:
927 RRForm<0b10000011000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
928 "and\t$rT, $rA, $rB", IntegerOp,
929 [(set (v16i8 VECREG:$rT), (and (v16i8 VECREG:$rA),
930 (v16i8 VECREG:$rB)))]>;
931
932def ANDv8i16:
933 RRForm<0b10000011000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
934 "and\t$rT, $rA, $rB", IntegerOp,
935 [(set (v8i16 VECREG:$rT), (and (v8i16 VECREG:$rA),
936 (v8i16 VECREG:$rB)))]>;
937
938def ANDv4i32:
939 RRForm<0b10000011000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
940 "and\t$rT, $rA, $rB", IntegerOp,
941 [(set (v4i32 VECREG:$rT), (and (v4i32 VECREG:$rA),
942 (v4i32 VECREG:$rB)))]>;
943
944def ANDr32:
945 RRForm<0b10000011000, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
946 "and\t$rT, $rA, $rB", IntegerOp,
947 [(set R32C:$rT, (and R32C:$rA, R32C:$rB))]>;
948
949//===---------------------------------------------
950// Special instructions to perform the fabs instruction
951def ANDfabs32:
952 RRForm<0b10000011000, (outs R32FP:$rT), (ins R32FP:$rA, R32C:$rB),
953 "and\t$rT, $rA, $rB", IntegerOp,
954 [/* Intentionally does not match a pattern */]>;
955
956def ANDfabs64:
957 RRForm<0b10000011000, (outs R64FP:$rT), (ins R64FP:$rA, VECREG:$rB),
958 "and\t$rT, $rA, $rB", IntegerOp,
959 [/* Intentionally does not match a pattern */]>;
960
961// Could use ANDv4i32, but won't for clarity
962def ANDfabsvec:
963 RRForm<0b10000011000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
964 "and\t$rT, $rA, $rB", IntegerOp,
965 [/* Intentionally does not match a pattern */]>;
966
967//===---------------------------------------------
968
969def ANDr16:
970 RRForm<0b10000011000, (outs R16C:$rT), (ins R16C:$rA, R16C:$rB),
971 "and\t$rT, $rA, $rB", IntegerOp,
972 [(set R16C:$rT, (and R16C:$rA, R16C:$rB))]>;
973
Scott Michel438be252007-12-17 22:32:34 +0000974def ANDr8:
975 RRForm<0b10000011000, (outs R8C:$rT), (ins R8C:$rA, R8C:$rB),
976 "and\t$rT, $rA, $rB", IntegerOp,
977 [(set R8C:$rT, (and R8C:$rA, R8C:$rB))]>;
978
Scott Michel8b6b4202007-12-04 22:35:58 +0000979// Hacked form of AND to zero-extend 16-bit quantities to 32-bit
980// quantities -- see 16->32 zext pattern.
981//
982// This pattern is somewhat artificial, since it might match some
983// compiler generated pattern but it is unlikely to do so.
984def AND2To4:
985 RRForm<0b10000011000, (outs R32C:$rT), (ins R16C:$rA, R32C:$rB),
986 "and\t$rT, $rA, $rB", IntegerOp,
987 [(set R32C:$rT, (and (zext R16C:$rA), R32C:$rB))]>;
988
989// N.B.: vnot_conv is one of those special target selection pattern fragments,
990// in which we expect there to be a bit_convert on the constant. Bear in mind
991// that llvm translates "not <reg>" to "xor <reg>, -1" (or in this case, a
992// constant -1 vector.)
993def ANDCv16i8:
994 RRForm<0b10000011010, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
995 "andc\t$rT, $rA, $rB", IntegerOp,
996 [(set (v16i8 VECREG:$rT), (and (v16i8 VECREG:$rA),
997 (vnot (v16i8 VECREG:$rB))))]>;
998
999def ANDCv8i16:
1000 RRForm<0b10000011010, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1001 "andc\t$rT, $rA, $rB", IntegerOp,
1002 [(set (v8i16 VECREG:$rT), (and (v8i16 VECREG:$rA),
1003 (vnot (v8i16 VECREG:$rB))))]>;
1004
1005def ANDCv4i32:
1006 RRForm<0b10000011010, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1007 "andc\t$rT, $rA, $rB", IntegerOp,
1008 [(set (v4i32 VECREG:$rT), (and (v4i32 VECREG:$rA),
1009 (vnot (v4i32 VECREG:$rB))))]>;
1010
1011def ANDCr32:
1012 RRForm<0b10000011010, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
1013 "andc\t$rT, $rA, $rB", IntegerOp,
1014 [(set R32C:$rT, (and R32C:$rA, (not R32C:$rB)))]>;
1015
1016def ANDCr16:
1017 RRForm<0b10000011010, (outs R16C:$rT), (ins R16C:$rA, R16C:$rB),
1018 "andc\t$rT, $rA, $rB", IntegerOp,
1019 [(set R16C:$rT, (and R16C:$rA, (not R16C:$rB)))]>;
1020
Scott Michel438be252007-12-17 22:32:34 +00001021def ANDCr8:
1022 RRForm<0b10000011010, (outs R8C:$rT), (ins R8C:$rA, R8C:$rB),
1023 "andc\t$rT, $rA, $rB", IntegerOp,
1024 [(set R8C:$rT, (and R8C:$rA, (not R8C:$rB)))]>;
1025
Scott Michel8b6b4202007-12-04 22:35:58 +00001026def ANDBIv16i8:
1027 RI10Form<0b01101000, (outs VECREG:$rT), (ins VECREG:$rA, u10imm:$val),
1028 "andbi\t$rT, $rA, $val", IntegerOp,
1029 [(set (v16i8 VECREG:$rT),
1030 (and (v16i8 VECREG:$rA), (v16i8 v16i8U8Imm:$val)))]>;
1031
Scott Michel438be252007-12-17 22:32:34 +00001032def ANDBIr8:
1033 RI10Form<0b01101000, (outs R8C:$rT), (ins R8C:$rA, u10imm_i8:$val),
1034 "andbi\t$rT, $rA, $val", IntegerOp,
1035 [(set R8C:$rT, (and R8C:$rA, immU8:$val))]>;
1036
Scott Michel8b6b4202007-12-04 22:35:58 +00001037def ANDHIv8i16:
1038 RI10Form<0b10101000, (outs VECREG:$rT), (ins VECREG:$rA, s10imm:$val),
1039 "andhi\t$rT, $rA, $val", IntegerOp,
1040 [(set (v8i16 VECREG:$rT),
1041 (and (v8i16 VECREG:$rA), v8i16SExt10Imm:$val))]>;
1042
1043def ANDHIr16:
1044 RI10Form<0b10101000, (outs R16C:$rT), (ins R16C:$rA, s10imm:$val),
1045 "andhi\t$rT, $rA, $val", IntegerOp,
Scott Michel438be252007-12-17 22:32:34 +00001046 [(set R16C:$rT, (and R16C:$rA, i16ImmUns10:$val))]>;
1047
1048def ANDHI1To2:
1049 RI10Form<0b10101000, (outs R16C:$rT), (ins R8C:$rA, s10imm:$val),
1050 "andhi\t$rT, $rA, $val", IntegerOp,
1051 [(set R16C:$rT, (and (zext R8C:$rA), i16ImmSExt10:$val))]>;
Scott Michel8b6b4202007-12-04 22:35:58 +00001052
1053def ANDIv4i32:
1054 RI10Form<0b00101000, (outs VECREG:$rT), (ins VECREG:$rA, s10imm:$val),
1055 "andi\t$rT, $rA, $val", IntegerOp,
1056 [(set (v4i32 VECREG:$rT),
1057 (and (v4i32 VECREG:$rA), v4i32SExt10Imm:$val))]>;
1058
1059def ANDIr32:
1060 RI10Form<0b10101000, (outs R32C:$rT), (ins R32C:$rA, s10imm_i32:$val),
1061 "andi\t$rT, $rA, $val", IntegerOp,
1062 [(set R32C:$rT, (and R32C:$rA, i32ImmSExt10:$val))]>;
1063
Scott Michel438be252007-12-17 22:32:34 +00001064// Hacked form of ANDI to zero-extend i8 quantities to i32. See the zext 8->32
1065// pattern below.
1066def ANDI1To4:
1067 RI10Form<0b10101000, (outs R32C:$rT), (ins R8C:$rA, s10imm_i32:$val),
1068 "andi\t$rT, $rA, $val", IntegerOp,
1069 [(set R32C:$rT, (and (zext R8C:$rA), i32ImmSExt10:$val))]>;
1070
Scott Michel8b6b4202007-12-04 22:35:58 +00001071// Hacked form of ANDI to zero-extend i16 quantities to i32. See the
1072// zext 16->32 pattern below.
1073//
1074// Note that this pattern is somewhat artificial, since it might match
1075// something the compiler generates but is unlikely to occur in practice.
1076def ANDI2To4:
1077 RI10Form<0b10101000, (outs R32C:$rT), (ins R16C:$rA, s10imm_i32:$val),
1078 "andi\t$rT, $rA, $val", IntegerOp,
1079 [(set R32C:$rT, (and (zext R16C:$rA), i32ImmSExt10:$val))]>;
1080
1081// Bitwise OR group:
1082// Bitwise "or" (N.B.: These are also register-register copy instructions...)
1083def ORv16i8:
1084 RRForm<0b10000010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1085 "or\t$rT, $rA, $rB", IntegerOp,
1086 [(set (v16i8 VECREG:$rT), (or (v16i8 VECREG:$rA), (v16i8 VECREG:$rB)))]>;
1087
1088def ORv8i16:
1089 RRForm<0b10000010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1090 "or\t$rT, $rA, $rB", IntegerOp,
1091 [(set (v8i16 VECREG:$rT), (or (v8i16 VECREG:$rA), (v8i16 VECREG:$rB)))]>;
1092
1093def ORv4i32:
1094 RRForm<0b10000010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1095 "or\t$rT, $rA, $rB", IntegerOp,
1096 [(set (v4i32 VECREG:$rT), (or (v4i32 VECREG:$rA), (v4i32 VECREG:$rB)))]>;
1097
1098def ORv4f32:
1099 RRForm<0b10000010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1100 "or\t$rT, $rA, $rB", IntegerOp,
1101 [(set (v4f32 VECREG:$rT),
1102 (v4f32 (bitconvert (or (v4i32 VECREG:$rA), (v4i32 VECREG:$rB)))))]>;
1103
1104def ORv2f64:
1105 RRForm<0b10000010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1106 "or\t$rT, $rA, $rB", IntegerOp,
1107 [(set (v2f64 VECREG:$rT),
1108 (v2f64 (bitconvert (or (v2i64 VECREG:$rA), (v2i64 VECREG:$rB)))))]>;
1109
1110def ORgprc:
1111 RRForm<0b10000010000, (outs GPRC:$rT), (ins GPRC:$rA, GPRC:$rB),
1112 "or\t$rT, $rA, $rB", IntegerOp,
1113 [(set GPRC:$rT, (or GPRC:$rA, GPRC:$rB))]>;
1114
1115def ORr64:
1116 RRForm<0b10000010000, (outs R64C:$rT), (ins R64C:$rA, R64C:$rB),
1117 "or\t$rT, $rA, $rB", IntegerOp,
1118 [(set R64C:$rT, (or R64C:$rA, R64C:$rB))]>;
1119
1120def ORr32:
1121 RRForm<0b10000010000, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
1122 "or\t$rT, $rA, $rB", IntegerOp,
1123 [(set R32C:$rT, (or R32C:$rA, R32C:$rB))]>;
1124
1125def ORr16:
1126 RRForm<0b10000010000, (outs R16C:$rT), (ins R16C:$rA, R16C:$rB),
1127 "or\t$rT, $rA, $rB", IntegerOp,
1128 [(set R16C:$rT, (or R16C:$rA, R16C:$rB))]>;
1129
Scott Michel438be252007-12-17 22:32:34 +00001130def ORr8:
1131 RRForm<0b10000010000, (outs R8C:$rT), (ins R8C:$rA, R8C:$rB),
1132 "or\t$rT, $rA, $rB", IntegerOp,
1133 [(set R8C:$rT, (or R8C:$rA, R8C:$rB))]>;
1134
Scott Michel754d8662007-12-20 00:44:13 +00001135// OR instruction forms that are used to copy f32 and f64 registers.
1136// They do not match patterns.
1137def ORf32:
1138 RRForm<0b10000010000, (outs R32FP:$rT), (ins R32FP:$rA, R32FP:$rB),
1139 "or\t$rT, $rA, $rB", IntegerOp,
1140 [/* no pattern */]>;
1141
1142def ORf64:
1143 RRForm<0b10000010000, (outs R64FP:$rT), (ins R64FP:$rA, R64FP:$rB),
1144 "or\t$rT, $rA, $rB", IntegerOp,
1145 [/* no pattern */]>;
1146
Scott Michel8b6b4202007-12-04 22:35:58 +00001147// ORv*_*: Used in scalar->vector promotions:
Scott Michel438be252007-12-17 22:32:34 +00001148def ORv16i8_i8:
1149 RRForm<0b10000010000, (outs VECREG:$rT), (ins R8C:$rA, R8C:$rB),
1150 "or\t$rT, $rA, $rB", IntegerOp,
1151 [/* no pattern */]>;
1152
1153def : Pat<(v16i8 (SPUpromote_scalar R8C:$rA)),
1154 (ORv16i8_i8 R8C:$rA, R8C:$rA)>;
1155
Scott Michel8b6b4202007-12-04 22:35:58 +00001156def ORv8i16_i16:
1157 RRForm<0b10000010000, (outs VECREG:$rT), (ins R16C:$rA, R16C:$rB),
1158 "or\t$rT, $rA, $rB", IntegerOp,
1159 [/* no pattern */]>;
1160
1161def : Pat<(v8i16 (SPUpromote_scalar R16C:$rA)),
1162 (ORv8i16_i16 R16C:$rA, R16C:$rA)>;
1163
1164def ORv4i32_i32:
1165 RRForm<0b10000010000, (outs VECREG:$rT), (ins R32C:$rA, R32C:$rB),
1166 "or\t$rT, $rA, $rB", IntegerOp,
1167 [/* no pattern */]>;
1168
1169def : Pat<(v4i32 (SPUpromote_scalar R32C:$rA)),
1170 (ORv4i32_i32 R32C:$rA, R32C:$rA)>;
1171
1172def ORv2i64_i64:
1173 RRForm<0b10000010000, (outs VECREG:$rT), (ins R64C:$rA, R64C:$rB),
1174 "or\t$rT, $rA, $rB", IntegerOp,
1175 [/* no pattern */]>;
1176
1177def : Pat<(v2i64 (SPUpromote_scalar R64C:$rA)),
1178 (ORv2i64_i64 R64C:$rA, R64C:$rA)>;
1179
1180def ORv4f32_f32:
1181 RRForm<0b10000010000, (outs VECREG:$rT), (ins R32FP:$rA, R32FP:$rB),
1182 "or\t$rT, $rA, $rB", IntegerOp,
1183 [/* no pattern */]>;
1184
1185def : Pat<(v4f32 (SPUpromote_scalar R32FP:$rA)),
1186 (ORv4f32_f32 R32FP:$rA, R32FP:$rA)>;
1187
1188def ORv2f64_f64:
1189 RRForm<0b10000010000, (outs VECREG:$rT), (ins R64FP:$rA, R64FP:$rB),
1190 "or\t$rT, $rA, $rB", IntegerOp,
1191 [/* no pattern */]>;
1192
1193def : Pat<(v2f64 (SPUpromote_scalar R64FP:$rA)),
1194 (ORv2f64_f64 R64FP:$rA, R64FP:$rA)>;
1195
1196// ORi*_v*: Used to extract vector element 0 (the preferred slot)
Scott Michel438be252007-12-17 22:32:34 +00001197def ORi8_v16i8:
1198 RRForm<0b10000010000, (outs R8C:$rT), (ins VECREG:$rA, VECREG:$rB),
1199 "or\t$rT, $rA, $rB", IntegerOp,
1200 [/* no pattern */]>;
1201
1202def : Pat<(SPUextract_elt0 (v16i8 VECREG:$rA)),
1203 (ORi8_v16i8 VECREG:$rA, VECREG:$rA)>;
1204
Scott Michel394e26d2008-01-17 20:38:41 +00001205def : Pat<(SPUextract_elt0_chained (v16i8 VECREG:$rA)),
1206 (ORi8_v16i8 VECREG:$rA, VECREG:$rA)>;
1207
Scott Michel8b6b4202007-12-04 22:35:58 +00001208def ORi16_v8i16:
1209 RRForm<0b10000010000, (outs R16C:$rT), (ins VECREG:$rA, VECREG:$rB),
1210 "or\t$rT, $rA, $rB", IntegerOp,
1211 [/* no pattern */]>;
1212
1213def : Pat<(SPUextract_elt0 (v8i16 VECREG:$rA)),
1214 (ORi16_v8i16 VECREG:$rA, VECREG:$rA)>;
1215
1216def : Pat<(SPUextract_elt0_chained (v8i16 VECREG:$rA)),
1217 (ORi16_v8i16 VECREG:$rA, VECREG:$rA)>;
1218
1219def ORi32_v4i32:
1220 RRForm<0b10000010000, (outs R32C:$rT), (ins VECREG:$rA, VECREG:$rB),
1221 "or\t$rT, $rA, $rB", IntegerOp,
1222 [/* no pattern */]>;
1223
1224def : Pat<(SPUextract_elt0 (v4i32 VECREG:$rA)),
1225 (ORi32_v4i32 VECREG:$rA, VECREG:$rA)>;
1226
1227def : Pat<(SPUextract_elt0_chained (v4i32 VECREG:$rA)),
1228 (ORi32_v4i32 VECREG:$rA, VECREG:$rA)>;
1229
1230def ORi64_v2i64:
1231 RRForm<0b10000010000, (outs R64C:$rT), (ins VECREG:$rA, VECREG:$rB),
1232 "or\t$rT, $rA, $rB", IntegerOp,
1233 [/* no pattern */]>;
1234
1235def : Pat<(SPUextract_elt0 (v2i64 VECREG:$rA)),
1236 (ORi64_v2i64 VECREG:$rA, VECREG:$rA)>;
1237
1238def : Pat<(SPUextract_elt0_chained (v2i64 VECREG:$rA)),
1239 (ORi64_v2i64 VECREG:$rA, VECREG:$rA)>;
1240
1241def ORf32_v4f32:
1242 RRForm<0b10000010000, (outs R32FP:$rT), (ins VECREG:$rA, VECREG:$rB),
1243 "or\t$rT, $rA, $rB", IntegerOp,
1244 [/* no pattern */]>;
1245
1246def : Pat<(SPUextract_elt0 (v4f32 VECREG:$rA)),
1247 (ORf32_v4f32 VECREG:$rA, VECREG:$rA)>;
1248
1249def : Pat<(SPUextract_elt0_chained (v4f32 VECREG:$rA)),
1250 (ORf32_v4f32 VECREG:$rA, VECREG:$rA)>;
1251
1252def ORf64_v2f64:
1253 RRForm<0b10000010000, (outs R64FP:$rT), (ins VECREG:$rA, VECREG:$rB),
1254 "or\t$rT, $rA, $rB", IntegerOp,
1255 [/* no pattern */]>;
1256
1257def : Pat<(SPUextract_elt0 (v2f64 VECREG:$rA)),
1258 (ORf64_v2f64 VECREG:$rA, VECREG:$rA)>;
1259
1260def : Pat<(SPUextract_elt0_chained (v2f64 VECREG:$rA)),
1261 (ORf64_v2f64 VECREG:$rA, VECREG:$rA)>;
1262
1263// ORC: Bitwise "or" with complement (match before ORvec, ORr32)
1264def ORCv16i8:
1265 RRForm<0b10010010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1266 "orc\t$rT, $rA, $rB", IntegerOp,
1267 [(set (v16i8 VECREG:$rT), (or (v16i8 VECREG:$rA),
1268 (vnot (v16i8 VECREG:$rB))))]>;
1269
1270def ORCv8i16:
1271 RRForm<0b10010010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1272 "orc\t$rT, $rA, $rB", IntegerOp,
1273 [(set (v8i16 VECREG:$rT), (or (v8i16 VECREG:$rA),
1274 (vnot (v8i16 VECREG:$rB))))]>;
1275
1276def ORCv4i32:
1277 RRForm<0b10010010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1278 "orc\t$rT, $rA, $rB", IntegerOp,
1279 [(set (v4i32 VECREG:$rT), (or (v4i32 VECREG:$rA),
1280 (vnot (v4i32 VECREG:$rB))))]>;
1281
1282def ORCr32:
1283 RRForm<0b10010010000, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
1284 "orc\t$rT, $rA, $rB", IntegerOp,
1285 [(set R32C:$rT, (or R32C:$rA, (not R32C:$rB)))]>;
1286
1287def ORCr16:
1288 RRForm<0b10010010000, (outs R16C:$rT), (ins R16C:$rA, R16C:$rB),
1289 "orc\t$rT, $rA, $rB", IntegerOp,
1290 [(set R16C:$rT, (or R16C:$rA, (not R16C:$rB)))]>;
1291
Scott Michel438be252007-12-17 22:32:34 +00001292def ORCr8:
1293 RRForm<0b10010010000, (outs R8C:$rT), (ins R8C:$rA, R8C:$rB),
1294 "orc\t$rT, $rA, $rB", IntegerOp,
1295 [(set R8C:$rT, (or R8C:$rA, (not R8C:$rB)))]>;
1296
Scott Michel8b6b4202007-12-04 22:35:58 +00001297// OR byte immediate
1298def ORBIv16i8:
1299 RI10Form<0b01100000, (outs VECREG:$rT), (ins VECREG:$rA, u10imm:$val),
1300 "orbi\t$rT, $rA, $val", IntegerOp,
1301 [(set (v16i8 VECREG:$rT),
1302 (or (v16i8 VECREG:$rA), (v16i8 v16i8U8Imm:$val)))]>;
1303
Scott Michel438be252007-12-17 22:32:34 +00001304def ORBIr8:
1305 RI10Form<0b01100000, (outs R8C:$rT), (ins R8C:$rA, u10imm_i8:$val),
1306 "orbi\t$rT, $rA, $val", IntegerOp,
1307 [(set R8C:$rT, (or R8C:$rA, immU8:$val))]>;
1308
Scott Michel8b6b4202007-12-04 22:35:58 +00001309// OR halfword immediate
1310def ORHIv8i16:
Scott Michel438be252007-12-17 22:32:34 +00001311 RI10Form<0b10100000, (outs VECREG:$rT), (ins VECREG:$rA, u10imm:$val),
Scott Michel8b6b4202007-12-04 22:35:58 +00001312 "orhi\t$rT, $rA, $val", IntegerOp,
1313 [(set (v8i16 VECREG:$rT), (or (v8i16 VECREG:$rA),
Scott Michel438be252007-12-17 22:32:34 +00001314 v8i16Uns10Imm:$val))]>;
Scott Michel8b6b4202007-12-04 22:35:58 +00001315
1316def ORHIr16:
Scott Michel438be252007-12-17 22:32:34 +00001317 RI10Form<0b10100000, (outs R16C:$rT), (ins R16C:$rA, u10imm:$val),
Scott Michel8b6b4202007-12-04 22:35:58 +00001318 "orhi\t$rT, $rA, $val", IntegerOp,
Scott Michel438be252007-12-17 22:32:34 +00001319 [(set R16C:$rT, (or R16C:$rA, i16ImmUns10:$val))]>;
1320
1321// Hacked form of ORHI used to promote 8-bit registers to 16-bit
1322def ORHI1To2:
1323 RI10Form<0b10100000, (outs R16C:$rT), (ins R8C:$rA, s10imm:$val),
1324 "orhi\t$rT, $rA, $val", IntegerOp,
1325 [(set R16C:$rT, (or (anyext R8C:$rA), i16ImmSExt10:$val))]>;
Scott Michel8b6b4202007-12-04 22:35:58 +00001326
1327// Bitwise "or" with immediate
1328def ORIv4i32:
Scott Michel438be252007-12-17 22:32:34 +00001329 RI10Form<0b00100000, (outs VECREG:$rT), (ins VECREG:$rA, u10imm:$val),
Scott Michel8b6b4202007-12-04 22:35:58 +00001330 "ori\t$rT, $rA, $val", IntegerOp,
1331 [(set (v4i32 VECREG:$rT), (or (v4i32 VECREG:$rA),
Scott Michel438be252007-12-17 22:32:34 +00001332 v4i32Uns10Imm:$val))]>;
Scott Michel8b6b4202007-12-04 22:35:58 +00001333
1334def ORIr32:
Scott Michel438be252007-12-17 22:32:34 +00001335 RI10Form<0b00100000, (outs R32C:$rT), (ins R32C:$rA, u10imm_i32:$val),
Scott Michel8b6b4202007-12-04 22:35:58 +00001336 "ori\t$rT, $rA, $val", IntegerOp,
Scott Michel438be252007-12-17 22:32:34 +00001337 [(set R32C:$rT, (or R32C:$rA, i32ImmUns10:$val))]>;
Scott Michel8b6b4202007-12-04 22:35:58 +00001338
Scott Michel8b6b4202007-12-04 22:35:58 +00001339def ORIr64:
1340 RI10Form_1<0b00100000, (outs R64C:$rT), (ins R64C:$rA, s10imm_i32:$val),
1341 "ori\t$rT, $rA, $val", IntegerOp,
1342 [/* no pattern */]>;
1343
1344// ORI2To4: hacked version of the ori instruction to extend 16-bit quantities
1345// to 32-bit quantities. used exclusively to match "anyext" conversions (vide
1346// infra "anyext 16->32" pattern.)
1347def ORI2To4:
1348 RI10Form<0b00100000, (outs R32C:$rT), (ins R16C:$rA, s10imm_i32:$val),
1349 "ori\t$rT, $rA, $val", IntegerOp,
1350 [(set R32C:$rT, (or (anyext R16C:$rA), i32ImmSExt10:$val))]>;
1351
Scott Michel438be252007-12-17 22:32:34 +00001352// ORI1To4: Hacked version of the ORI instruction to extend 16-bit quantities
1353// to 32-bit quantities. Used exclusively to match "anyext" conversions (vide
1354// infra "anyext 16->32" pattern.)
1355def ORI1To4:
1356 RI10Form<0b00100000, (outs R32C:$rT), (ins R8C:$rA, s10imm_i32:$val),
1357 "ori\t$rT, $rA, $val", IntegerOp,
1358 [(set R32C:$rT, (or (anyext R8C:$rA), i32ImmSExt10:$val))]>;
1359
Scott Michel8b6b4202007-12-04 22:35:58 +00001360// ORX: "or" across the vector: or's $rA's word slots leaving the result in
1361// $rT[0], slots 1-3 are zeroed.
1362//
Scott Michel438be252007-12-17 22:32:34 +00001363// FIXME: Needs to match an intrinsic pattern.
Scott Michel8b6b4202007-12-04 22:35:58 +00001364def ORXv4i32:
1365 RRForm<0b10010010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1366 "orx\t$rT, $rA, $rB", IntegerOp,
1367 []>;
1368
Scott Michel438be252007-12-17 22:32:34 +00001369// XOR:
Scott Michel8b6b4202007-12-04 22:35:58 +00001370def XORv16i8:
1371 RRForm<0b10010010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1372 "xor\t$rT, $rA, $rB", IntegerOp,
1373 [(set (v16i8 VECREG:$rT), (xor (v16i8 VECREG:$rA), (v16i8 VECREG:$rB)))]>;
1374
1375def XORv8i16:
1376 RRForm<0b10010010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1377 "xor\t$rT, $rA, $rB", IntegerOp,
1378 [(set (v8i16 VECREG:$rT), (xor (v8i16 VECREG:$rA), (v8i16 VECREG:$rB)))]>;
1379
1380def XORv4i32:
1381 RRForm<0b10010010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1382 "xor\t$rT, $rA, $rB", IntegerOp,
1383 [(set (v4i32 VECREG:$rT), (xor (v4i32 VECREG:$rA), (v4i32 VECREG:$rB)))]>;
1384
1385def XORr32:
1386 RRForm<0b10010010000, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
1387 "xor\t$rT, $rA, $rB", IntegerOp,
1388 [(set R32C:$rT, (xor R32C:$rA, R32C:$rB))]>;
1389
1390//==----------------------------------------------------------
1391// Special forms for floating point instructions.
1392// Bitwise ORs and ANDs don't make sense for normal floating
1393// point numbers. These operations (fneg and fabs), however,
1394// require bitwise logical ops to manipulate the sign bit.
1395def XORfneg32:
1396 RRForm<0b10010010000, (outs R32FP:$rT), (ins R32FP:$rA, R32C:$rB),
1397 "xor\t$rT, $rA, $rB", IntegerOp,
1398 [/* Intentionally does not match a pattern, see fneg32 */]>;
1399
1400// KLUDGY! Better way to do this without a VECREG? bitconvert?
1401// VECREG is assumed to contain two identical 64-bit masks, so
1402// it doesn't matter which word we select for the xor
1403def XORfneg64:
1404 RRForm<0b10010010000, (outs R64FP:$rT), (ins R64FP:$rA, VECREG:$rB),
1405 "xor\t$rT, $rA, $rB", IntegerOp,
1406 [/* Intentionally does not match a pattern, see fneg64 */]>;
1407
1408// Could use XORv4i32, but will use this for clarity
1409def XORfnegvec:
1410 RRForm<0b10010010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1411 "xor\t$rT, $rA, $rB", IntegerOp,
1412 [/* Intentionally does not match a pattern, see fneg{32,64} */]>;
1413
1414//==----------------------------------------------------------
1415
1416def XORr16:
1417 RRForm<0b10010010000, (outs R16C:$rT), (ins R16C:$rA, R16C:$rB),
1418 "xor\t$rT, $rA, $rB", IntegerOp,
1419 [(set R16C:$rT, (xor R16C:$rA, R16C:$rB))]>;
1420
Scott Michel438be252007-12-17 22:32:34 +00001421def XORr8:
1422 RRForm<0b10010010000, (outs R8C:$rT), (ins R8C:$rA, R8C:$rB),
1423 "xor\t$rT, $rA, $rB", IntegerOp,
1424 [(set R8C:$rT, (xor R8C:$rA, R8C:$rB))]>;
1425
Scott Michel8b6b4202007-12-04 22:35:58 +00001426def XORBIv16i8:
1427 RI10Form<0b01100000, (outs VECREG:$rT), (ins VECREG:$rA, u10imm:$val),
1428 "xorbi\t$rT, $rA, $val", IntegerOp,
1429 [(set (v16i8 VECREG:$rT), (xor (v16i8 VECREG:$rA), v16i8U8Imm:$val))]>;
1430
Scott Michel438be252007-12-17 22:32:34 +00001431def XORBIr8:
1432 RI10Form<0b01100000, (outs R8C:$rT), (ins R8C:$rA, u10imm_i8:$val),
1433 "xorbi\t$rT, $rA, $val", IntegerOp,
1434 [(set R8C:$rT, (xor R8C:$rA, immU8:$val))]>;
1435
Scott Michel8b6b4202007-12-04 22:35:58 +00001436def XORHIv8i16:
1437 RI10Form<0b10100000, (outs VECREG:$rT), (ins VECREG:$rA, s10imm:$val),
1438 "xorhi\t$rT, $rA, $val", IntegerOp,
1439 [(set (v8i16 VECREG:$rT), (xor (v8i16 VECREG:$rA),
1440 v8i16SExt10Imm:$val))]>;
1441
1442def XORHIr16:
1443 RI10Form<0b10100000, (outs R16C:$rT), (ins R16C:$rA, s10imm:$val),
1444 "xorhi\t$rT, $rA, $val", IntegerOp,
1445 [(set R16C:$rT, (xor R16C:$rA, i16ImmSExt10:$val))]>;
1446
1447def XORIv4i32:
1448 RI10Form<0b00100000, (outs VECREG:$rT), (ins VECREG:$rA, s10imm:$val),
1449 "xori\t$rT, $rA, $val", IntegerOp,
1450 [(set (v4i32 VECREG:$rT), (xor (v4i32 VECREG:$rA),
1451 v4i32SExt10Imm:$val))]>;
1452
1453def XORIr32:
1454 RI10Form<0b00100000, (outs R32C:$rT), (ins R32C:$rA, s10imm_i32:$val),
1455 "xori\t$rT, $rA, $val", IntegerOp,
1456 [(set R32C:$rT, (xor R32C:$rA, i32ImmSExt10:$val))]>;
1457
1458// NAND:
1459def NANDv16i8:
1460 RRForm<0b10010010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1461 "nand\t$rT, $rA, $rB", IntegerOp,
1462 [(set (v16i8 VECREG:$rT), (vnot (and (v16i8 VECREG:$rA),
1463 (v16i8 VECREG:$rB))))]>;
1464
1465def NANDv8i16:
1466 RRForm<0b10010010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1467 "nand\t$rT, $rA, $rB", IntegerOp,
1468 [(set (v8i16 VECREG:$rT), (vnot (and (v8i16 VECREG:$rA),
1469 (v8i16 VECREG:$rB))))]>;
1470
1471def NANDv4i32:
1472 RRForm<0b10010010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1473 "nand\t$rT, $rA, $rB", IntegerOp,
1474 [(set (v4i32 VECREG:$rT), (vnot (and (v4i32 VECREG:$rA),
1475 (v4i32 VECREG:$rB))))]>;
1476
1477def NANDr32:
1478 RRForm<0b10010010000, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
1479 "nand\t$rT, $rA, $rB", IntegerOp,
1480 [(set R32C:$rT, (not (and R32C:$rA, R32C:$rB)))]>;
1481
1482def NANDr16:
1483 RRForm<0b10010010000, (outs R16C:$rT), (ins R16C:$rA, R16C:$rB),
1484 "nand\t$rT, $rA, $rB", IntegerOp,
1485 [(set R16C:$rT, (not (and R16C:$rA, R16C:$rB)))]>;
1486
Scott Michel438be252007-12-17 22:32:34 +00001487def NANDr8:
1488 RRForm<0b10010010000, (outs R8C:$rT), (ins R8C:$rA, R8C:$rB),
1489 "nand\t$rT, $rA, $rB", IntegerOp,
1490 [(set R8C:$rT, (not (and R8C:$rA, R8C:$rB)))]>;
1491
Scott Michel8b6b4202007-12-04 22:35:58 +00001492// NOR:
1493def NORv16i8:
1494 RRForm<0b10010010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1495 "nor\t$rT, $rA, $rB", IntegerOp,
1496 [(set (v16i8 VECREG:$rT), (vnot (or (v16i8 VECREG:$rA),
1497 (v16i8 VECREG:$rB))))]>;
1498
1499def NORv8i16:
1500 RRForm<0b10010010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1501 "nor\t$rT, $rA, $rB", IntegerOp,
1502 [(set (v8i16 VECREG:$rT), (vnot (or (v8i16 VECREG:$rA),
1503 (v8i16 VECREG:$rB))))]>;
1504
1505def NORv4i32:
1506 RRForm<0b10010010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1507 "nor\t$rT, $rA, $rB", IntegerOp,
1508 [(set (v4i32 VECREG:$rT), (vnot (or (v4i32 VECREG:$rA),
1509 (v4i32 VECREG:$rB))))]>;
1510
1511def NORr32:
1512 RRForm<0b10010010000, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
1513 "nor\t$rT, $rA, $rB", IntegerOp,
1514 [(set R32C:$rT, (not (or R32C:$rA, R32C:$rB)))]>;
1515
1516def NORr16:
1517 RRForm<0b10010010000, (outs R16C:$rT), (ins R16C:$rA, R16C:$rB),
1518 "nor\t$rT, $rA, $rB", IntegerOp,
1519 [(set R16C:$rT, (not (or R16C:$rA, R16C:$rB)))]>;
1520
Scott Michel438be252007-12-17 22:32:34 +00001521def NORr8:
1522 RRForm<0b10010010000, (outs R8C:$rT), (ins R8C:$rA, R8C:$rB),
1523 "nor\t$rT, $rA, $rB", IntegerOp,
1524 [(set R8C:$rT, (not (or R8C:$rA, R8C:$rB)))]>;
1525
Scott Michel8b6b4202007-12-04 22:35:58 +00001526// EQV: Equivalence (1 for each same bit, otherwise 0)
1527def EQVv16i8:
1528 RRForm<0b10010010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1529 "eqv\t$rT, $rA, $rB", IntegerOp,
1530 [(set (v16i8 VECREG:$rT), (or (and (v16i8 VECREG:$rA),
1531 (v16i8 VECREG:$rB)),
1532 (and (vnot (v16i8 VECREG:$rA)),
1533 (vnot (v16i8 VECREG:$rB)))))]>;
1534
1535def : Pat<(xor (v16i8 VECREG:$rA), (vnot (v16i8 VECREG:$rB))),
1536 (EQVv16i8 VECREG:$rA, VECREG:$rB)>;
1537
1538def : Pat<(xor (vnot (v16i8 VECREG:$rA)), (v16i8 VECREG:$rB)),
1539 (EQVv16i8 VECREG:$rA, VECREG:$rB)>;
1540
1541def EQVv8i16:
1542 RRForm<0b10010010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1543 "eqv\t$rT, $rA, $rB", IntegerOp,
1544 [(set (v8i16 VECREG:$rT), (or (and (v8i16 VECREG:$rA),
1545 (v8i16 VECREG:$rB)),
1546 (and (vnot (v8i16 VECREG:$rA)),
1547 (vnot (v8i16 VECREG:$rB)))))]>;
1548
1549def : Pat<(xor (v8i16 VECREG:$rA), (vnot (v8i16 VECREG:$rB))),
1550 (EQVv8i16 VECREG:$rA, VECREG:$rB)>;
1551
1552def : Pat<(xor (vnot (v8i16 VECREG:$rA)), (v8i16 VECREG:$rB)),
1553 (EQVv8i16 VECREG:$rA, VECREG:$rB)>;
1554
1555def EQVv4i32:
1556 RRForm<0b10010010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
1557 "eqv\t$rT, $rA, $rB", IntegerOp,
1558 [(set (v4i32 VECREG:$rT), (or (and (v4i32 VECREG:$rA),
1559 (v4i32 VECREG:$rB)),
1560 (and (vnot (v4i32 VECREG:$rA)),
1561 (vnot (v4i32 VECREG:$rB)))))]>;
1562
1563def : Pat<(xor (v4i32 VECREG:$rA), (vnot (v4i32 VECREG:$rB))),
1564 (EQVv4i32 VECREG:$rA, VECREG:$rB)>;
1565
1566def : Pat<(xor (vnot (v4i32 VECREG:$rA)), (v4i32 VECREG:$rB)),
1567 (EQVv4i32 VECREG:$rA, VECREG:$rB)>;
1568
1569def EQVr32:
1570 RRForm<0b10010010000, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
1571 "eqv\t$rT, $rA, $rB", IntegerOp,
1572 [(set R32C:$rT, (or (and R32C:$rA, R32C:$rB),
1573 (and (not R32C:$rA), (not R32C:$rB))))]>;
1574
1575def : Pat<(xor R32C:$rA, (not R32C:$rB)),
1576 (EQVr32 R32C:$rA, R32C:$rB)>;
1577
1578def : Pat<(xor (not R32C:$rA), R32C:$rB),
1579 (EQVr32 R32C:$rA, R32C:$rB)>;
1580
1581def EQVr16:
1582 RRForm<0b10010010000, (outs R16C:$rT), (ins R16C:$rA, R16C:$rB),
1583 "eqv\t$rT, $rA, $rB", IntegerOp,
1584 [(set R16C:$rT, (or (and R16C:$rA, R16C:$rB),
1585 (and (not R16C:$rA), (not R16C:$rB))))]>;
1586
1587def : Pat<(xor R16C:$rA, (not R16C:$rB)),
1588 (EQVr16 R16C:$rA, R16C:$rB)>;
1589
1590def : Pat<(xor (not R16C:$rA), R16C:$rB),
1591 (EQVr16 R16C:$rA, R16C:$rB)>;
1592
Scott Michel438be252007-12-17 22:32:34 +00001593def EQVr8:
1594 RRForm<0b10010010000, (outs R8C:$rT), (ins R8C:$rA, R8C:$rB),
1595 "eqv\t$rT, $rA, $rB", IntegerOp,
1596 [(set R8C:$rT, (or (and R8C:$rA, R8C:$rB),
1597 (and (not R8C:$rA), (not R8C:$rB))))]>;
1598
1599def : Pat<(xor R8C:$rA, (not R8C:$rB)),
1600 (EQVr8 R8C:$rA, R8C:$rB)>;
1601
1602def : Pat<(xor (not R8C:$rA), R8C:$rB),
1603 (EQVr8 R8C:$rA, R8C:$rB)>;
1604
Scott Michel8b6b4202007-12-04 22:35:58 +00001605// gcc optimizes (p & q) | (~p & ~q) -> ~(p | q) | (p & q), so match that
1606// pattern also:
1607def : Pat<(or (vnot (or (v16i8 VECREG:$rA), (v16i8 VECREG:$rB))),
1608 (and (v16i8 VECREG:$rA), (v16i8 VECREG:$rB))),
1609 (EQVv16i8 VECREG:$rA, VECREG:$rB)>;
1610
1611def : Pat<(or (vnot (or (v8i16 VECREG:$rA), (v8i16 VECREG:$rB))),
1612 (and (v8i16 VECREG:$rA), (v8i16 VECREG:$rB))),
1613 (EQVv8i16 VECREG:$rA, VECREG:$rB)>;
1614
1615def : Pat<(or (vnot (or (v4i32 VECREG:$rA), (v4i32 VECREG:$rB))),
1616 (and (v4i32 VECREG:$rA), (v4i32 VECREG:$rB))),
1617 (EQVv4i32 VECREG:$rA, VECREG:$rB)>;
1618
1619def : Pat<(or (not (or R32C:$rA, R32C:$rB)), (and R32C:$rA, R32C:$rB)),
1620 (EQVr32 R32C:$rA, R32C:$rB)>;
1621
1622def : Pat<(or (not (or R16C:$rA, R16C:$rB)), (and R16C:$rA, R16C:$rB)),
1623 (EQVr16 R16C:$rA, R16C:$rB)>;
1624
Scott Michel438be252007-12-17 22:32:34 +00001625def : Pat<(or (not (or R8C:$rA, R8C:$rB)), (and R8C:$rA, R8C:$rB)),
1626 (EQVr8 R8C:$rA, R8C:$rB)>;
1627
Scott Michel8b6b4202007-12-04 22:35:58 +00001628// Select bits:
1629def SELBv16i8:
1630 RRRForm<0b1000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB, VECREG:$rC),
1631 "selb\t$rT, $rA, $rB, $rC", IntegerOp,
1632 [(set (v16i8 VECREG:$rT),
1633 (SPUselb_v16i8 (v16i8 VECREG:$rA), (v16i8 VECREG:$rB),
1634 (v16i8 VECREG:$rC)))]>;
1635
1636def : Pat<(or (and (v16i8 VECREG:$rA), (v16i8 VECREG:$rC)),
1637 (and (v16i8 VECREG:$rB), (vnot (v16i8 VECREG:$rC)))),
1638 (SELBv16i8 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1639
1640def : Pat<(or (and (v16i8 VECREG:$rC), (v16i8 VECREG:$rA)),
1641 (and (v16i8 VECREG:$rB), (vnot (v16i8 VECREG:$rC)))),
1642 (SELBv16i8 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1643
1644def : Pat<(or (and (v16i8 VECREG:$rA), (v16i8 VECREG:$rC)),
1645 (and (vnot (v16i8 VECREG:$rC)), (v16i8 VECREG:$rB))),
1646 (SELBv16i8 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1647
1648def : Pat<(or (and (v16i8 VECREG:$rC), (v16i8 VECREG:$rA)),
1649 (and (vnot (v16i8 VECREG:$rC)), (v16i8 VECREG:$rB))),
1650 (SELBv16i8 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1651
1652def : Pat<(or (and (v16i8 VECREG:$rA), (vnot (v16i8 VECREG:$rC))),
1653 (and (v16i8 VECREG:$rB), (v16i8 VECREG:$rC))),
1654 (SELBv16i8 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1655
1656def : Pat<(or (and (v16i8 VECREG:$rA), (vnot (v16i8 VECREG:$rC))),
1657 (and (v16i8 VECREG:$rC), (v16i8 VECREG:$rB))),
1658 (SELBv16i8 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1659
1660def : Pat<(or (and (vnot (v16i8 VECREG:$rC)), (v16i8 VECREG:$rA)),
1661 (and (v16i8 VECREG:$rB), (v16i8 VECREG:$rC))),
1662 (SELBv16i8 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1663
1664def : Pat<(or (and (vnot (v16i8 VECREG:$rC)), (v16i8 VECREG:$rA)),
1665 (and (v16i8 VECREG:$rC), (v16i8 VECREG:$rB))),
1666 (SELBv16i8 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1667
1668def : Pat<(or (and (v16i8 VECREG:$rA), (v16i8 VECREG:$rC)),
1669 (and (v16i8 VECREG:$rB), (vnot (v16i8 VECREG:$rC)))),
1670 (SELBv16i8 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1671
1672def : Pat<(or (and (v16i8 VECREG:$rC), (v16i8 VECREG:$rA)),
1673 (and (v16i8 VECREG:$rB), (vnot (v16i8 VECREG:$rC)))),
1674 (SELBv16i8 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1675
1676def : Pat<(or (and (v16i8 VECREG:$rA), (v16i8 VECREG:$rC)),
1677 (and (vnot (v16i8 VECREG:$rC)), (v16i8 VECREG:$rB))),
1678 (SELBv16i8 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1679
1680def : Pat<(or (and (v16i8 VECREG:$rC), (v16i8 VECREG:$rA)),
1681 (and (vnot (v16i8 VECREG:$rC)), (v16i8 VECREG:$rB))),
1682 (SELBv16i8 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1683
1684def : Pat<(or (and (v16i8 VECREG:$rA), (vnot (v16i8 VECREG:$rC))),
1685 (and (v16i8 VECREG:$rB), (v16i8 VECREG:$rC))),
1686 (SELBv16i8 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1687
1688def : Pat<(or (and (v16i8 VECREG:$rA), (vnot (v16i8 VECREG:$rC))),
1689 (and (v16i8 VECREG:$rC), (v16i8 VECREG:$rB))),
1690 (SELBv16i8 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1691
1692def : Pat<(or (and (vnot (v16i8 VECREG:$rC)), (v16i8 VECREG:$rA)),
1693 (and (v16i8 VECREG:$rB), (v16i8 VECREG:$rC))),
1694 (SELBv16i8 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1695
1696def : Pat<(or (and (vnot (v16i8 VECREG:$rC)), (v16i8 VECREG:$rA)),
1697 (and (v16i8 VECREG:$rC), (v16i8 VECREG:$rB))),
1698 (SELBv16i8 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1699
1700def SELBv8i16:
1701 RRRForm<0b1000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB, VECREG:$rC),
1702 "selb\t$rT, $rA, $rB, $rC", IntegerOp,
1703 [(set (v8i16 VECREG:$rT),
1704 (SPUselb_v8i16 (v8i16 VECREG:$rA), (v8i16 VECREG:$rB),
1705 (v8i16 VECREG:$rC)))]>;
1706
1707def : Pat<(or (and (v8i16 VECREG:$rA), (v8i16 VECREG:$rC)),
1708 (and (v8i16 VECREG:$rB), (vnot (v8i16 VECREG:$rC)))),
1709 (SELBv8i16 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1710
1711def : Pat<(or (and (v8i16 VECREG:$rC), (v8i16 VECREG:$rA)),
1712 (and (v8i16 VECREG:$rB), (vnot (v8i16 VECREG:$rC)))),
1713 (SELBv8i16 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1714
1715def : Pat<(or (and (v8i16 VECREG:$rA), (v8i16 VECREG:$rC)),
1716 (and (vnot (v8i16 VECREG:$rC)), (v8i16 VECREG:$rB))),
1717 (SELBv8i16 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1718
1719def : Pat<(or (and (v8i16 VECREG:$rC), (v8i16 VECREG:$rA)),
1720 (and (vnot (v8i16 VECREG:$rC)), (v8i16 VECREG:$rB))),
1721 (SELBv8i16 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1722
1723def : Pat<(or (and (v8i16 VECREG:$rA), (vnot (v8i16 VECREG:$rC))),
1724 (and (v8i16 VECREG:$rB), (v8i16 VECREG:$rC))),
1725 (SELBv8i16 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1726
1727def : Pat<(or (and (v8i16 VECREG:$rA), (vnot (v8i16 VECREG:$rC))),
1728 (and (v8i16 VECREG:$rC), (v8i16 VECREG:$rB))),
1729 (SELBv8i16 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1730
1731def : Pat<(or (and (vnot (v8i16 VECREG:$rC)), (v8i16 VECREG:$rA)),
1732 (and (v8i16 VECREG:$rB), (v8i16 VECREG:$rC))),
1733 (SELBv8i16 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1734
1735def : Pat<(or (and (vnot (v8i16 VECREG:$rC)), (v8i16 VECREG:$rA)),
1736 (and (v8i16 VECREG:$rC), (v8i16 VECREG:$rB))),
1737 (SELBv8i16 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1738
1739def : Pat<(or (and (v8i16 VECREG:$rA), (v8i16 VECREG:$rC)),
1740 (and (v8i16 VECREG:$rB), (vnot (v8i16 VECREG:$rC)))),
1741 (SELBv8i16 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1742
1743def : Pat<(or (and (v8i16 VECREG:$rC), (v8i16 VECREG:$rA)),
1744 (and (v8i16 VECREG:$rB), (vnot (v8i16 VECREG:$rC)))),
1745 (SELBv8i16 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1746
1747def : Pat<(or (and (v8i16 VECREG:$rA), (v8i16 VECREG:$rC)),
1748 (and (vnot (v8i16 VECREG:$rC)), (v8i16 VECREG:$rB))),
1749 (SELBv8i16 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1750
1751def : Pat<(or (and (v8i16 VECREG:$rC), (v8i16 VECREG:$rA)),
1752 (and (vnot (v8i16 VECREG:$rC)), (v8i16 VECREG:$rB))),
1753 (SELBv8i16 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1754
1755def : Pat<(or (and (v8i16 VECREG:$rA), (vnot (v8i16 VECREG:$rC))),
1756 (and (v8i16 VECREG:$rB), (v8i16 VECREG:$rC))),
1757 (SELBv8i16 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1758
1759def : Pat<(or (and (v8i16 VECREG:$rA), (vnot (v8i16 VECREG:$rC))),
1760 (and (v8i16 VECREG:$rC), (v8i16 VECREG:$rB))),
1761 (SELBv8i16 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1762
1763def : Pat<(or (and (vnot (v8i16 VECREG:$rC)), (v8i16 VECREG:$rA)),
1764 (and (v8i16 VECREG:$rB), (v8i16 VECREG:$rC))),
1765 (SELBv8i16 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1766
1767def : Pat<(or (and (vnot (v8i16 VECREG:$rC)), (v8i16 VECREG:$rA)),
1768 (and (v8i16 VECREG:$rC), (v8i16 VECREG:$rB))),
1769 (SELBv8i16 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1770
1771def SELBv4i32:
1772 RRRForm<0b1000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB, VECREG:$rC),
1773 "selb\t$rT, $rA, $rB, $rC", IntegerOp,
1774 [(set (v4i32 VECREG:$rT),
1775 (SPUselb_v4i32 (v4i32 VECREG:$rA), (v4i32 VECREG:$rB),
1776 (v4i32 VECREG:$rC)))]>;
1777
1778def : Pat<(or (and (v4i32 VECREG:$rA), (v4i32 VECREG:$rC)),
1779 (and (v4i32 VECREG:$rB), (vnot (v4i32 VECREG:$rC)))),
1780 (SELBv4i32 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1781
1782def : Pat<(or (and (v4i32 VECREG:$rC), (v4i32 VECREG:$rA)),
1783 (and (v4i32 VECREG:$rB), (vnot (v4i32 VECREG:$rC)))),
1784 (SELBv4i32 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1785
1786def : Pat<(or (and (v4i32 VECREG:$rA), (v4i32 VECREG:$rC)),
1787 (and (vnot (v4i32 VECREG:$rC)), (v4i32 VECREG:$rB))),
1788 (SELBv4i32 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1789
1790def : Pat<(or (and (v4i32 VECREG:$rC), (v4i32 VECREG:$rA)),
1791 (and (vnot (v4i32 VECREG:$rC)), (v4i32 VECREG:$rB))),
1792 (SELBv4i32 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1793
1794def : Pat<(or (and (v4i32 VECREG:$rA), (vnot (v4i32 VECREG:$rC))),
1795 (and (v4i32 VECREG:$rB), (v4i32 VECREG:$rC))),
1796 (SELBv4i32 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1797
1798def : Pat<(or (and (v4i32 VECREG:$rA), (vnot (v4i32 VECREG:$rC))),
1799 (and (v4i32 VECREG:$rC), (v4i32 VECREG:$rB))),
1800 (SELBv4i32 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1801
1802def : Pat<(or (and (vnot (v4i32 VECREG:$rC)), (v4i32 VECREG:$rA)),
1803 (and (v4i32 VECREG:$rB), (v4i32 VECREG:$rC))),
1804 (SELBv4i32 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1805
1806def : Pat<(or (and (vnot (v4i32 VECREG:$rC)), (v4i32 VECREG:$rA)),
1807 (and (v4i32 VECREG:$rC), (v4i32 VECREG:$rB))),
1808 (SELBv4i32 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1809
1810def : Pat<(or (and (v4i32 VECREG:$rA), (v4i32 VECREG:$rC)),
1811 (and (v4i32 VECREG:$rB), (vnot (v4i32 VECREG:$rC)))),
1812 (SELBv4i32 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1813
1814def : Pat<(or (and (v4i32 VECREG:$rC), (v4i32 VECREG:$rA)),
1815 (and (v4i32 VECREG:$rB), (vnot (v4i32 VECREG:$rC)))),
1816 (SELBv4i32 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1817
1818def : Pat<(or (and (v4i32 VECREG:$rA), (v4i32 VECREG:$rC)),
1819 (and (vnot (v4i32 VECREG:$rC)), (v4i32 VECREG:$rB))),
1820 (SELBv4i32 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1821
1822def : Pat<(or (and (v4i32 VECREG:$rC), (v4i32 VECREG:$rA)),
1823 (and (vnot (v4i32 VECREG:$rC)), (v4i32 VECREG:$rB))),
1824 (SELBv4i32 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1825
1826def : Pat<(or (and (v4i32 VECREG:$rA), (vnot (v4i32 VECREG:$rC))),
1827 (and (v4i32 VECREG:$rB), (v4i32 VECREG:$rC))),
1828 (SELBv4i32 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1829
1830def : Pat<(or (and (v4i32 VECREG:$rA), (vnot (v4i32 VECREG:$rC))),
1831 (and (v4i32 VECREG:$rC), (v4i32 VECREG:$rB))),
1832 (SELBv4i32 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1833
1834def : Pat<(or (and (vnot (v4i32 VECREG:$rC)), (v4i32 VECREG:$rA)),
1835 (and (v4i32 VECREG:$rB), (v4i32 VECREG:$rC))),
1836 (SELBv4i32 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1837
1838def : Pat<(or (and (vnot (v4i32 VECREG:$rC)), (v4i32 VECREG:$rA)),
1839 (and (v4i32 VECREG:$rC), (v4i32 VECREG:$rB))),
1840 (SELBv4i32 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1841
1842def SELBr32:
1843 RRRForm<0b1000, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB, R32C:$rC),
1844 "selb\t$rT, $rA, $rB, $rC", IntegerOp,
1845 []>;
1846
1847// And the various patterns that can be matched... (all 8 of them :-)
1848def : Pat<(or (and R32C:$rA, R32C:$rC),
1849 (and R32C:$rB, (not R32C:$rC))),
1850 (SELBr32 R32C:$rA, R32C:$rB, R32C:$rC)>;
1851
1852def : Pat<(or (and R32C:$rC, R32C:$rA),
1853 (and R32C:$rB, (not R32C:$rC))),
1854 (SELBr32 R32C:$rA, R32C:$rB, R32C:$rC)>;
1855
1856def : Pat<(or (and R32C:$rA, R32C:$rC),
1857 (and (not R32C:$rC), R32C:$rB)),
1858 (SELBr32 R32C:$rA, R32C:$rB, R32C:$rC)>;
1859
1860def : Pat<(or (and R32C:$rC, R32C:$rA),
1861 (and (not R32C:$rC), R32C:$rB)),
1862 (SELBr32 R32C:$rA, R32C:$rB, R32C:$rC)>;
1863
1864def : Pat<(or (and R32C:$rA, (not R32C:$rC)),
1865 (and R32C:$rB, R32C:$rC)),
1866 (SELBr32 R32C:$rA, R32C:$rB, R32C:$rC)>;
1867
1868def : Pat<(or (and R32C:$rA, (not R32C:$rC)),
1869 (and R32C:$rC, R32C:$rB)),
1870 (SELBr32 R32C:$rA, R32C:$rB, R32C:$rC)>;
1871
1872def : Pat<(or (and (not R32C:$rC), R32C:$rA),
1873 (and R32C:$rB, R32C:$rC)),
1874 (SELBr32 R32C:$rA, R32C:$rB, R32C:$rC)>;
1875
1876def : Pat<(or (and (not R32C:$rC), R32C:$rA),
1877 (and R32C:$rC, R32C:$rB)),
1878 (SELBr32 R32C:$rA, R32C:$rB, R32C:$rC)>;
1879
1880def SELBr16:
1881 RRRForm<0b1000, (outs R16C:$rT), (ins R16C:$rA, R16C:$rB, R16C:$rC),
1882 "selb\t$rT, $rA, $rB, $rC", IntegerOp,
1883 []>;
1884
1885def : Pat<(or (and R16C:$rA, R16C:$rC),
1886 (and R16C:$rB, (not R16C:$rC))),
1887 (SELBr16 R16C:$rA, R16C:$rB, R16C:$rC)>;
1888
1889def : Pat<(or (and R16C:$rC, R16C:$rA),
1890 (and R16C:$rB, (not R16C:$rC))),
1891 (SELBr16 R16C:$rA, R16C:$rB, R16C:$rC)>;
1892
1893def : Pat<(or (and R16C:$rA, R16C:$rC),
1894 (and (not R16C:$rC), R16C:$rB)),
1895 (SELBr16 R16C:$rA, R16C:$rB, R16C:$rC)>;
1896
1897def : Pat<(or (and R16C:$rC, R16C:$rA),
1898 (and (not R16C:$rC), R16C:$rB)),
1899 (SELBr16 R16C:$rA, R16C:$rB, R16C:$rC)>;
1900
1901def : Pat<(or (and R16C:$rA, (not R16C:$rC)),
1902 (and R16C:$rB, R16C:$rC)),
1903 (SELBr16 R16C:$rA, R16C:$rB, R16C:$rC)>;
1904
1905def : Pat<(or (and R16C:$rA, (not R16C:$rC)),
1906 (and R16C:$rC, R16C:$rB)),
1907 (SELBr16 R16C:$rA, R16C:$rB, R16C:$rC)>;
1908
1909def : Pat<(or (and (not R16C:$rC), R16C:$rA),
1910 (and R16C:$rB, R16C:$rC)),
1911 (SELBr16 R16C:$rA, R16C:$rB, R16C:$rC)>;
1912
1913def : Pat<(or (and (not R16C:$rC), R16C:$rA),
1914 (and R16C:$rC, R16C:$rB)),
1915 (SELBr16 R16C:$rA, R16C:$rB, R16C:$rC)>;
Scott Michel438be252007-12-17 22:32:34 +00001916
1917def SELBr8:
1918 RRRForm<0b1000, (outs R8C:$rT), (ins R8C:$rA, R8C:$rB, R8C:$rC),
1919 "selb\t$rT, $rA, $rB, $rC", IntegerOp,
1920 []>;
1921
1922def : Pat<(or (and R8C:$rA, R8C:$rC),
1923 (and R8C:$rB, (not R8C:$rC))),
1924 (SELBr8 R8C:$rA, R8C:$rB, R8C:$rC)>;
1925
1926def : Pat<(or (and R8C:$rC, R8C:$rA),
1927 (and R8C:$rB, (not R8C:$rC))),
1928 (SELBr8 R8C:$rA, R8C:$rB, R8C:$rC)>;
1929
1930def : Pat<(or (and R8C:$rA, R8C:$rC),
1931 (and (not R8C:$rC), R8C:$rB)),
1932 (SELBr8 R8C:$rA, R8C:$rB, R8C:$rC)>;
1933
1934def : Pat<(or (and R8C:$rC, R8C:$rA),
1935 (and (not R8C:$rC), R8C:$rB)),
1936 (SELBr8 R8C:$rA, R8C:$rB, R8C:$rC)>;
1937
1938def : Pat<(or (and R8C:$rA, (not R8C:$rC)),
1939 (and R8C:$rB, R8C:$rC)),
1940 (SELBr8 R8C:$rA, R8C:$rB, R8C:$rC)>;
1941
1942def : Pat<(or (and R8C:$rA, (not R8C:$rC)),
1943 (and R8C:$rC, R8C:$rB)),
1944 (SELBr8 R8C:$rA, R8C:$rB, R8C:$rC)>;
1945
1946def : Pat<(or (and (not R8C:$rC), R8C:$rA),
1947 (and R8C:$rB, R8C:$rC)),
1948 (SELBr8 R8C:$rA, R8C:$rB, R8C:$rC)>;
1949
1950def : Pat<(or (and (not R8C:$rC), R8C:$rA),
1951 (and R8C:$rC, R8C:$rB)),
1952 (SELBr8 R8C:$rA, R8C:$rB, R8C:$rC)>;
Scott Michel8b6b4202007-12-04 22:35:58 +00001953
1954//===----------------------------------------------------------------------===//
1955// Vector shuffle...
1956//===----------------------------------------------------------------------===//
1957
1958def SHUFB:
1959 RRRForm<0b1000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB, VECREG:$rC),
1960 "shufb\t$rT, $rA, $rB, $rC", IntegerOp,
Scott Michel754d8662007-12-20 00:44:13 +00001961 [/* no pattern */]>;
Scott Michel8b6b4202007-12-04 22:35:58 +00001962
1963// SPUshuffle is generated in LowerVECTOR_SHUFFLE and gets replaced with SHUFB.
1964// See the SPUshuffle SDNode operand above, which sets up the DAG pattern
1965// matcher to emit something when the LowerVECTOR_SHUFFLE generates a node with
1966// the SPUISD::SHUFB opcode.
1967def : Pat<(SPUshuffle (v16i8 VECREG:$rA), (v16i8 VECREG:$rB), VECREG:$rC),
1968 (SHUFB VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1969
1970def : Pat<(SPUshuffle (v8i16 VECREG:$rA), (v8i16 VECREG:$rB), VECREG:$rC),
1971 (SHUFB VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1972
1973def : Pat<(SPUshuffle (v4i32 VECREG:$rA), (v4i32 VECREG:$rB), VECREG:$rC),
1974 (SHUFB VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1975
Scott Michel754d8662007-12-20 00:44:13 +00001976def : Pat<(SPUshuffle (v4f32 VECREG:$rA), (v4f32 VECREG:$rB), VECREG:$rC),
1977 (SHUFB VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1978
Scott Michel8b6b4202007-12-04 22:35:58 +00001979def : Pat<(SPUshuffle (v2i64 VECREG:$rA), (v2i64 VECREG:$rB), VECREG:$rC),
1980 (SHUFB VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1981
Scott Michel754d8662007-12-20 00:44:13 +00001982def : Pat<(SPUshuffle (v2f64 VECREG:$rA), (v2f64 VECREG:$rB), VECREG:$rC),
1983 (SHUFB VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
1984
Scott Michel8b6b4202007-12-04 22:35:58 +00001985//===----------------------------------------------------------------------===//
1986// Shift and rotate group:
1987//===----------------------------------------------------------------------===//
1988
1989def SHLHv8i16:
1990 RRForm<0b11111010000, (outs VECREG:$rT), (ins VECREG:$rA, R16C:$rB),
1991 "shlh\t$rT, $rA, $rB", RotateShift,
1992 [(set (v8i16 VECREG:$rT),
1993 (SPUvec_shl_v8i16 (v8i16 VECREG:$rA), R16C:$rB))]>;
1994
1995// $rB gets promoted to 32-bit register type when confronted with
1996// this llvm assembly code:
1997//
1998// define i16 @shlh_i16_1(i16 %arg1, i16 %arg2) {
1999// %A = shl i16 %arg1, %arg2
2000// ret i16 %A
2001// }
2002//
2003// However, we will generate this code when lowering 8-bit shifts and rotates.
2004
2005def SHLHr16:
2006 RRForm<0b11111010000, (outs R16C:$rT), (ins R16C:$rA, R16C:$rB),
2007 "shlh\t$rT, $rA, $rB", RotateShift,
2008 [(set R16C:$rT, (shl R16C:$rA, R16C:$rB))]>;
2009
2010def SHLHr16_r32:
2011 RRForm<0b11111010000, (outs R16C:$rT), (ins R16C:$rA, R32C:$rB),
2012 "shlh\t$rT, $rA, $rB", RotateShift,
2013 [(set R16C:$rT, (shl R16C:$rA, R32C:$rB))]>;
2014
2015def SHLHIv8i16:
Scott Michel438be252007-12-17 22:32:34 +00002016 RI7Form<0b11111010000, (outs VECREG:$rT), (ins VECREG:$rA, u7imm_i8:$val),
Scott Michel8b6b4202007-12-04 22:35:58 +00002017 "shlhi\t$rT, $rA, $val", RotateShift,
2018 [(set (v8i16 VECREG:$rT),
Scott Michel438be252007-12-17 22:32:34 +00002019 (SPUvec_shl_v8i16 (v8i16 VECREG:$rA), (i8 uimm7:$val)))]>;
2020
2021def : Pat<(SPUvec_shl_v8i16 (v8i16 VECREG:$rA), (i16 uimm7:$val)),
2022 (SHLHIv8i16 VECREG:$rA, imm:$val)>;
Scott Michel8b6b4202007-12-04 22:35:58 +00002023
2024def : Pat<(SPUvec_shl_v8i16 (v8i16 VECREG:$rA), (i32 uimm7:$val)),
2025 (SHLHIv8i16 VECREG:$rA, imm:$val)>;
2026
2027def SHLHIr16:
2028 RI7Form<0b11111010000, (outs R16C:$rT), (ins R16C:$rA, u7imm_i32:$val),
2029 "shlhi\t$rT, $rA, $val", RotateShift,
2030 [(set R16C:$rT, (shl R16C:$rA, (i32 uimm7:$val)))]>;
Scott Michel438be252007-12-17 22:32:34 +00002031
2032def : Pat<(shl R16C:$rA, (i8 uimm7:$val)),
2033 (SHLHIr16 R16C:$rA, uimm7:$val)>;
Scott Michel8b6b4202007-12-04 22:35:58 +00002034
2035def : Pat<(shl R16C:$rA, (i16 uimm7:$val)),
2036 (SHLHIr16 R16C:$rA, uimm7:$val)>;
2037
2038def SHLv4i32:
2039 RRForm<0b11111010000, (outs VECREG:$rT), (ins VECREG:$rA, R16C:$rB),
2040 "shl\t$rT, $rA, $rB", RotateShift,
2041 [(set (v4i32 VECREG:$rT),
2042 (SPUvec_shl_v4i32 (v4i32 VECREG:$rA), R16C:$rB))]>;
2043
2044def SHLr32:
2045 RRForm<0b11111010000, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
2046 "shl\t$rT, $rA, $rB", RotateShift,
2047 [(set R32C:$rT, (shl R32C:$rA, R32C:$rB))]>;
2048
2049def SHLIv4i32:
Scott Michel438be252007-12-17 22:32:34 +00002050 RI7Form<0b11111010000, (outs VECREG:$rT), (ins VECREG:$rA, u7imm_i8:$val),
Scott Michel8b6b4202007-12-04 22:35:58 +00002051 "shli\t$rT, $rA, $val", RotateShift,
2052 [(set (v4i32 VECREG:$rT),
Scott Michel438be252007-12-17 22:32:34 +00002053 (SPUvec_shl_v4i32 (v4i32 VECREG:$rA), (i8 uimm7:$val)))]>;
2054
2055def: Pat<(SPUvec_shl_v4i32 (v4i32 VECREG:$rA), (i16 uimm7:$val)),
2056 (SHLIv4i32 VECREG:$rA, uimm7:$val)>;
Scott Michel8b6b4202007-12-04 22:35:58 +00002057
2058def: Pat<(SPUvec_shl_v4i32 (v4i32 VECREG:$rA), (i32 uimm7:$val)),
2059 (SHLIv4i32 VECREG:$rA, uimm7:$val)>;
2060
2061def SHLIr32:
2062 RI7Form<0b11111010000, (outs R32C:$rT), (ins R32C:$rA, u7imm_i32:$val),
2063 "shli\t$rT, $rA, $val", RotateShift,
2064 [(set R32C:$rT, (shl R32C:$rA, (i32 uimm7:$val)))]>;
2065
2066def : Pat<(shl R32C:$rA, (i16 uimm7:$val)),
2067 (SHLIr32 R32C:$rA, uimm7:$val)>;
2068
Scott Michel438be252007-12-17 22:32:34 +00002069def : Pat<(shl R32C:$rA, (i8 uimm7:$val)),
2070 (SHLIr32 R32C:$rA, uimm7:$val)>;
2071
Scott Michel8b6b4202007-12-04 22:35:58 +00002072// SHLQBI vec form: Note that this will shift the entire vector (the 128-bit
2073// register) to the left. Vector form is here to ensure type correctness.
2074def SHLQBIvec:
2075 RRForm<0b11011011100, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
2076 "shlqbi\t$rT, $rA, $rB", RotateShift,
2077 [/* intrinsic */]>;
2078
2079// See note above on SHLQBI.
2080def SHLQBIIvec:
2081 RI7Form<0b11011111100, (outs VECREG:$rT), (ins VECREG:$rA, u7imm:$val),
2082 "shlqbii\t$rT, $rA, $val", RotateShift,
2083 [/* intrinsic */]>;
2084
2085// SHLQBY, SHLQBYI vector forms: Shift the entire vector to the left by bytes,
2086// not by bits.
2087def SHLQBYvec:
2088 RI7Form<0b11111011100, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
2089 "shlqbyi\t$rT, $rA, $rB", RotateShift,
2090 [/* intrinsic */]>;
2091
2092def SHLQBYIvec:
2093 RI7Form<0b11111111100, (outs VECREG:$rT), (ins VECREG:$rA, u7imm:$val),
2094 "shlqbyi\t$rT, $rA, $val", RotateShift,
2095 [/* intrinsic */]>;
2096
2097// ROTH v8i16 form:
2098def ROTHv8i16:
2099 RRForm<0b00111010000, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
2100 "roth\t$rT, $rA, $rB", RotateShift,
2101 [(set (v8i16 VECREG:$rT),
2102 (SPUvec_rotl_v8i16 VECREG:$rA, VECREG:$rB))]>;
2103
2104def ROTHr16:
2105 RRForm<0b00111010000, (outs R16C:$rT), (ins R16C:$rA, R16C:$rB),
2106 "roth\t$rT, $rA, $rB", RotateShift,
2107 [(set R16C:$rT, (rotl R16C:$rA, R16C:$rB))]>;
2108
2109def ROTHr16_r32:
2110 RRForm<0b00111010000, (outs R16C:$rT), (ins R16C:$rA, R32C:$rB),
2111 "roth\t$rT, $rA, $rB", RotateShift,
2112 [(set R16C:$rT, (rotl R16C:$rA, R32C:$rB))]>;
2113
Scott Michel438be252007-12-17 22:32:34 +00002114// The rotate amount is in the same bits whether we've got an 8-bit, 16-bit or
2115// 32-bit register
2116def ROTHr16_r8:
2117 RRForm<0b00111010000, (outs R16C:$rT), (ins R16C:$rA, R8C:$rB),
2118 "roth\t$rT, $rA, $rB", RotateShift,
2119 [(set R16C:$rT, (rotl R16C:$rA, (i32 (zext R8C:$rB))))]>;
2120
2121def : Pat<(rotl R16C:$rA, (i32 (sext R8C:$rB))),
2122 (ROTHr16_r8 R16C:$rA, R8C:$rB)>;
2123
2124def : Pat<(rotl R16C:$rA, (i32 (zext R8C:$rB))),
2125 (ROTHr16_r8 R16C:$rA, R8C:$rB)>;
2126
2127def : Pat<(rotl R16C:$rA, (i32 (anyext R8C:$rB))),
2128 (ROTHr16_r8 R16C:$rA, R8C:$rB)>;
2129
Scott Michel8b6b4202007-12-04 22:35:58 +00002130def ROTHIv8i16:
Scott Michel438be252007-12-17 22:32:34 +00002131 RI7Form<0b00111110000, (outs VECREG:$rT), (ins VECREG:$rA, u7imm_i8:$val),
Scott Michel8b6b4202007-12-04 22:35:58 +00002132 "rothi\t$rT, $rA, $val", RotateShift,
2133 [(set (v8i16 VECREG:$rT),
Scott Michel438be252007-12-17 22:32:34 +00002134 (SPUvec_rotl_v8i16 VECREG:$rA, (i8 uimm7:$val)))]>;
Scott Michel8b6b4202007-12-04 22:35:58 +00002135
2136def : Pat<(SPUvec_rotl_v8i16 VECREG:$rA, (i16 uimm7:$val)),
2137 (ROTHIv8i16 VECREG:$rA, imm:$val)>;
2138
2139def : Pat<(SPUvec_rotl_v8i16 VECREG:$rA, (i32 uimm7:$val)),
2140 (ROTHIv8i16 VECREG:$rA, imm:$val)>;
2141
2142def ROTHIr16:
2143 RI7Form<0b00111110000, (outs R16C:$rT), (ins R16C:$rA, u7imm:$val),
2144 "rothi\t$rT, $rA, $val", RotateShift,
2145 [(set R16C:$rT, (rotl R16C:$rA, (i16 uimm7:$val)))]>;
2146
2147def ROTHIr16_i32:
2148 RI7Form<0b00111110000, (outs R16C:$rT), (ins R16C:$rA, u7imm_i32:$val),
2149 "rothi\t$rT, $rA, $val", RotateShift,
2150 [(set R16C:$rT, (rotl R16C:$rA, (i32 uimm7:$val)))]>;
2151
Scott Michel438be252007-12-17 22:32:34 +00002152def ROTHIr16_i8:
2153 RI7Form<0b00111110000, (outs R16C:$rT), (ins R16C:$rA, u7imm_i8:$val),
2154 "rothi\t$rT, $rA, $val", RotateShift,
2155 [(set R16C:$rT, (rotl R16C:$rA, (i8 uimm7:$val)))]>;
2156
Scott Michel8b6b4202007-12-04 22:35:58 +00002157def ROTv4i32:
2158 RRForm<0b00011010000, (outs VECREG:$rT), (ins VECREG:$rA, R32C:$rB),
2159 "rot\t$rT, $rA, $rB", RotateShift,
2160 [(set (v4i32 VECREG:$rT),
2161 (SPUvec_rotl_v4i32 (v4i32 VECREG:$rA), R32C:$rB))]>;
2162
2163def ROTr32:
2164 RRForm<0b00011010000, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
2165 "rot\t$rT, $rA, $rB", RotateShift,
2166 [(set R32C:$rT, (rotl R32C:$rA, R32C:$rB))]>;
2167
Scott Michel438be252007-12-17 22:32:34 +00002168// The rotate amount is in the same bits whether we've got an 8-bit, 16-bit or
2169// 32-bit register
2170def ROTr32_r16_anyext:
2171 RRForm<0b00011010000, (outs R32C:$rT), (ins R32C:$rA, R16C:$rB),
2172 "rot\t$rT, $rA, $rB", RotateShift,
2173 [(set R32C:$rT, (rotl R32C:$rA, (i32 (anyext R16C:$rB))))]>;
2174
2175def : Pat<(rotl R32C:$rA, (i32 (zext R16C:$rB))),
2176 (ROTr32_r16_anyext R32C:$rA, R16C:$rB)>;
2177
2178def : Pat<(rotl R32C:$rA, (i32 (sext R16C:$rB))),
2179 (ROTr32_r16_anyext R32C:$rA, R16C:$rB)>;
2180
2181def ROTr32_r8_anyext:
2182 RRForm<0b00011010000, (outs R32C:$rT), (ins R32C:$rA, R8C:$rB),
2183 "rot\t$rT, $rA, $rB", RotateShift,
2184 [(set R32C:$rT, (rotl R32C:$rA, (i32 (anyext R8C:$rB))))]>;
2185
2186def : Pat<(rotl R32C:$rA, (i32 (zext R8C:$rB))),
2187 (ROTr32_r8_anyext R32C:$rA, R8C:$rB)>;
2188
2189def : Pat<(rotl R32C:$rA, (i32 (sext R8C:$rB))),
2190 (ROTr32_r8_anyext R32C:$rA, R8C:$rB)>;
2191
Scott Michel8b6b4202007-12-04 22:35:58 +00002192def ROTIv4i32:
2193 RI7Form<0b00011110000, (outs VECREG:$rT), (ins VECREG:$rA, u7imm_i32:$val),
2194 "roti\t$rT, $rA, $val", RotateShift,
2195 [(set (v4i32 VECREG:$rT),
2196 (SPUvec_rotl_v4i32 (v4i32 VECREG:$rA), (i32 uimm7:$val)))]>;
2197
2198def : Pat<(SPUvec_rotl_v4i32 (v4i32 VECREG:$rA), (i16 uimm7:$val)),
2199 (ROTIv4i32 VECREG:$rA, imm:$val)>;
2200
Scott Michel438be252007-12-17 22:32:34 +00002201def : Pat<(SPUvec_rotl_v4i32 (v4i32 VECREG:$rA), (i8 uimm7:$val)),
2202 (ROTIv4i32 VECREG:$rA, imm:$val)>;
2203
Scott Michel8b6b4202007-12-04 22:35:58 +00002204def ROTIr32:
2205 RI7Form<0b00011110000, (outs R32C:$rT), (ins R32C:$rA, u7imm_i32:$val),
2206 "roti\t$rT, $rA, $val", RotateShift,
2207 [(set R32C:$rT, (rotl R32C:$rA, (i32 uimm7:$val)))]>;
2208
2209def ROTIr32_i16:
2210 RI7Form<0b00111110000, (outs R32C:$rT), (ins R32C:$rA, u7imm:$val),
2211 "roti\t$rT, $rA, $val", RotateShift,
2212 [(set R32C:$rT, (rotl R32C:$rA, (i16 uimm7:$val)))]>;
2213
Scott Michel438be252007-12-17 22:32:34 +00002214def ROTIr32_i8:
2215 RI7Form<0b00111110000, (outs R32C:$rT), (ins R32C:$rA, u7imm_i8:$val),
2216 "roti\t$rT, $rA, $val", RotateShift,
2217 [(set R32C:$rT, (rotl R32C:$rA, (i8 uimm7:$val)))]>;
2218
Scott Michel8b6b4202007-12-04 22:35:58 +00002219// ROTQBY* vector forms: This rotates the entire vector, but vector registers
2220// are used here for type checking (instances where ROTQBI is used actually
2221// use vector registers)
2222def ROTQBYvec:
Scott Micheldbac4cf2008-01-11 02:53:15 +00002223 RRForm<0b00111011100, (outs VECREG:$rT), (ins VECREG:$rA, R32C:$rB),
Scott Michel8b6b4202007-12-04 22:35:58 +00002224 "rotqby\t$rT, $rA, $rB", RotateShift,
Scott Micheldbac4cf2008-01-11 02:53:15 +00002225 [(set (v16i8 VECREG:$rT), (SPUrotbytes_left (v16i8 VECREG:$rA), R32C:$rB))]>;
Scott Michel8b6b4202007-12-04 22:35:58 +00002226
Scott Micheldbac4cf2008-01-11 02:53:15 +00002227def : Pat<(SPUrotbytes_left_chained (v16i8 VECREG:$rA), R32C:$rB),
2228 (ROTQBYvec VECREG:$rA, R32C:$rB)>;
Scott Michel8b6b4202007-12-04 22:35:58 +00002229
2230// See ROTQBY note above.
2231def ROTQBYIvec:
2232 RI7Form<0b00111111100, (outs VECREG:$rT), (ins VECREG:$rA, u7imm:$val),
2233 "rotqbyi\t$rT, $rA, $val", RotateShift,
2234 [(set (v16i8 VECREG:$rT),
2235 (SPUrotbytes_left (v16i8 VECREG:$rA), (i16 uimm7:$val)))]>;
2236
2237def : Pat<(SPUrotbytes_left_chained (v16i8 VECREG:$rA), (i16 uimm7:$val)),
2238 (ROTQBYIvec VECREG:$rA, uimm7:$val)>;
2239
2240// See ROTQBY note above.
2241def ROTQBYBIvec:
2242 RI7Form<0b00110011100, (outs VECREG:$rT), (ins VECREG:$rA, u7imm:$val),
2243 "rotqbybi\t$rT, $rA, $val", RotateShift,
2244 [/* intrinsic */]>;
2245
2246// See ROTQBY note above.
2247//
2248// Assume that the user of this instruction knows to shift the rotate count
2249// into bit 29
2250def ROTQBIvec:
2251 RRForm<0b00011011100, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
2252 "rotqbi\t$rT, $rA, $rB", RotateShift,
2253 [/* insert intrinsic here */]>;
2254
2255// See ROTQBY note above.
2256def ROTQBIIvec:
2257 RI7Form<0b00011111100, (outs VECREG:$rT), (ins VECREG:$rA, u7imm_i32:$val),
2258 "rotqbii\t$rT, $rA, $val", RotateShift,
2259 [/* insert intrinsic here */]>;
2260
2261// ROTHM v8i16 form:
2262// NOTE(1): No vector rotate is generated by the C/C++ frontend (today),
2263// so this only matches a synthetically generated/lowered code
2264// fragment.
2265// NOTE(2): $rB must be negated before the right rotate!
2266def ROTHMv8i16:
2267 RRForm<0b10111010000, (outs VECREG:$rT), (ins VECREG:$rA, R32C:$rB),
2268 "rothm\t$rT, $rA, $rB", RotateShift,
2269 [/* see patterns below - $rB must be negated */]>;
2270
2271def : Pat<(SPUvec_srl_v8i16 (v8i16 VECREG:$rA), R32C:$rB),
2272 (ROTHMv8i16 VECREG:$rA, (SFIr32 R32C:$rB, 0))>;
2273
2274def : Pat<(SPUvec_srl_v8i16 (v8i16 VECREG:$rA), R16C:$rB),
2275 (ROTHMv8i16 VECREG:$rA,
2276 (SFIr32 (XSHWr16 R16C:$rB), 0))>;
2277
Scott Michel438be252007-12-17 22:32:34 +00002278def : Pat<(SPUvec_srl_v8i16 (v8i16 VECREG:$rA), R8C:$rB),
Scott Michel8b6b4202007-12-04 22:35:58 +00002279 (ROTHMv8i16 VECREG:$rA,
Scott Michel438be252007-12-17 22:32:34 +00002280 (SFIr32 (XSHWr16 (XSBHr8 R8C:$rB) ), 0))>;
Scott Michel8b6b4202007-12-04 22:35:58 +00002281
2282// ROTHM r16 form: Rotate 16-bit quantity to right, zero fill at the left
2283// Note: This instruction doesn't match a pattern because rB must be negated
2284// for the instruction to work. Thus, the pattern below the instruction!
2285def ROTHMr16:
2286 RRForm<0b10111010000, (outs R16C:$rT), (ins R16C:$rA, R32C:$rB),
2287 "rothm\t$rT, $rA, $rB", RotateShift,
2288 [/* see patterns below - $rB must be negated! */]>;
2289
2290def : Pat<(srl R16C:$rA, R32C:$rB),
2291 (ROTHMr16 R16C:$rA, (SFIr32 R32C:$rB, 0))>;
2292
2293def : Pat<(srl R16C:$rA, R16C:$rB),
2294 (ROTHMr16 R16C:$rA,
2295 (SFIr32 (XSHWr16 R16C:$rB), 0))>;
2296
Scott Michel438be252007-12-17 22:32:34 +00002297def : Pat<(srl R16C:$rA, R8C:$rB),
Scott Michel8b6b4202007-12-04 22:35:58 +00002298 (ROTHMr16 R16C:$rA,
Scott Michel438be252007-12-17 22:32:34 +00002299 (SFIr32 (XSHWr16 (XSBHr8 R8C:$rB) ), 0))>;
Scott Michel8b6b4202007-12-04 22:35:58 +00002300
2301// ROTHMI v8i16 form: See the comment for ROTHM v8i16. The difference here is
2302// that the immediate can be complemented, so that the user doesn't have to
2303// worry about it.
2304def ROTHMIv8i16:
2305 RI7Form<0b10111110000, (outs VECREG:$rT), (ins VECREG:$rA, rothNeg7imm:$val),
2306 "rothmi\t$rT, $rA, $val", RotateShift,
2307 [(set (v8i16 VECREG:$rT),
2308 (SPUvec_srl_v8i16 (v8i16 VECREG:$rA), (i32 imm:$val)))]>;
2309
2310def: Pat<(SPUvec_srl_v8i16 (v8i16 VECREG:$rA), (i16 imm:$val)),
2311 (ROTHMIv8i16 VECREG:$rA, imm:$val)>;
Scott Michel438be252007-12-17 22:32:34 +00002312
2313def: Pat<(SPUvec_srl_v8i16 (v8i16 VECREG:$rA), (i8 imm:$val)),
2314 (ROTHMIv8i16 VECREG:$rA, imm:$val)>;
Scott Michel8b6b4202007-12-04 22:35:58 +00002315
2316def ROTHMIr16:
2317 RI7Form<0b10111110000, (outs R16C:$rT), (ins R16C:$rA, rothNeg7imm:$val),
2318 "rothmi\t$rT, $rA, $val", RotateShift,
2319 [(set R16C:$rT, (srl R16C:$rA, (i32 uimm7:$val)))]>;
2320
2321def: Pat<(srl R16C:$rA, (i16 uimm7:$val)),
2322 (ROTHMIr16 R16C:$rA, uimm7:$val)>;
2323
Scott Michel438be252007-12-17 22:32:34 +00002324def: Pat<(srl R16C:$rA, (i8 uimm7:$val)),
2325 (ROTHMIr16 R16C:$rA, uimm7:$val)>;
2326
Scott Michel8b6b4202007-12-04 22:35:58 +00002327// ROTM v4i32 form: See the ROTHM v8i16 comments.
2328def ROTMv4i32:
2329 RRForm<0b10011010000, (outs VECREG:$rT), (ins VECREG:$rA, R32C:$rB),
2330 "rotm\t$rT, $rA, $rB", RotateShift,
2331 [/* see patterns below - $rB must be negated */]>;
2332
2333def : Pat<(SPUvec_srl_v4i32 VECREG:$rA, R32C:$rB),
2334 (ROTMv4i32 VECREG:$rA, (SFIr32 R32C:$rB, 0))>;
2335
2336def : Pat<(SPUvec_srl_v4i32 VECREG:$rA, R16C:$rB),
2337 (ROTMv4i32 VECREG:$rA,
2338 (SFIr32 (XSHWr16 R16C:$rB), 0))>;
2339
2340def : Pat<(SPUvec_srl_v4i32 VECREG:$rA, /* R8C */ R16C:$rB),
2341 (ROTMv4i32 VECREG:$rA,
2342 (SFIr32 (XSHWr16 /* (XSBHr8 R8C */ R16C:$rB) /*)*/, 0))>;
2343
2344def ROTMr32:
2345 RRForm<0b10011010000, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
2346 "rotm\t$rT, $rA, $rB", RotateShift,
2347 [/* see patterns below - $rB must be negated */]>;
2348
2349def : Pat<(srl R32C:$rA, R32C:$rB),
2350 (ROTMr32 R32C:$rA, (SFIr32 R32C:$rB, 0))>;
2351
2352def : Pat<(srl R32C:$rA, R16C:$rB),
2353 (ROTMr32 R32C:$rA,
2354 (SFIr32 (XSHWr16 R16C:$rB), 0))>;
2355
Scott Michel438be252007-12-17 22:32:34 +00002356def : Pat<(srl R32C:$rA, R8C:$rB),
2357 (ROTMr32 R32C:$rA,
2358 (SFIr32 (XSHWr16 (XSBHr8 R8C:$rB)), 0))>;
2359
Scott Michel8b6b4202007-12-04 22:35:58 +00002360// ROTMI v4i32 form: See the comment for ROTHM v8i16.
2361def ROTMIv4i32:
2362 RI7Form<0b10011110000, (outs VECREG:$rT), (ins VECREG:$rA, rotNeg7imm:$val),
2363 "rotmi\t$rT, $rA, $val", RotateShift,
2364 [(set (v4i32 VECREG:$rT),
2365 (SPUvec_srl_v4i32 VECREG:$rA, (i32 uimm7:$val)))]>;
2366
2367def : Pat<(SPUvec_srl_v4i32 VECREG:$rA, (i16 uimm7:$val)),
2368 (ROTMIv4i32 VECREG:$rA, uimm7:$val)>;
Scott Michel438be252007-12-17 22:32:34 +00002369
2370def : Pat<(SPUvec_srl_v4i32 VECREG:$rA, (i8 uimm7:$val)),
2371 (ROTMIv4i32 VECREG:$rA, uimm7:$val)>;
Scott Michel8b6b4202007-12-04 22:35:58 +00002372
2373// ROTMI r32 form: know how to complement the immediate value.
2374def ROTMIr32:
2375 RI7Form<0b10011110000, (outs R32C:$rT), (ins R32C:$rA, rotNeg7imm:$val),
2376 "rotmi\t$rT, $rA, $val", RotateShift,
2377 [(set R32C:$rT, (srl R32C:$rA, (i32 uimm7:$val)))]>;
2378
2379def : Pat<(srl R32C:$rA, (i16 imm:$val)),
2380 (ROTMIr32 R32C:$rA, uimm7:$val)>;
2381
Scott Michel438be252007-12-17 22:32:34 +00002382def : Pat<(srl R32C:$rA, (i8 imm:$val)),
2383 (ROTMIr32 R32C:$rA, uimm7:$val)>;
2384
Scott Michel8b6b4202007-12-04 22:35:58 +00002385// ROTQMBYvec: This is a vector form merely so that when used in an
2386// instruction pattern, type checking will succeed. This instruction assumes
2387// that the user knew to complement $rB.
2388def ROTQMBYvec:
2389 RRForm<0b10111011100, (outs VECREG:$rT), (ins VECREG:$rA, R32C:$rB),
2390 "rotqmby\t$rT, $rA, $rB", RotateShift,
2391 [(set (v16i8 VECREG:$rT),
2392 (SPUrotbytes_right_zfill (v16i8 VECREG:$rA), R32C:$rB))]>;
2393
2394def ROTQMBYIvec:
2395 RI7Form<0b10111111100, (outs VECREG:$rT), (ins VECREG:$rA, rotNeg7imm:$val),
2396 "rotqmbyi\t$rT, $rA, $val", RotateShift,
2397 [(set (v16i8 VECREG:$rT),
2398 (SPUrotbytes_right_zfill (v16i8 VECREG:$rA), (i32 uimm7:$val)))]>;
2399
2400def : Pat<(SPUrotbytes_right_zfill VECREG:$rA, (i16 uimm7:$val)),
2401 (ROTQMBYIvec VECREG:$rA, uimm7:$val)>;
2402
2403def ROTQMBYBIvec:
2404 RRForm<0b10110011100, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
2405 "rotqmbybi\t$rT, $rA, $rB", RotateShift,
2406 [/* intrinsic */]>;
2407
2408def ROTQMBIvec:
2409 RRForm<0b10011011100, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
2410 "rotqmbi\t$rT, $rA, $rB", RotateShift,
2411 [/* intrinsic */]>;
2412
2413def ROTQMBIIvec:
2414 RI7Form<0b10011111100, (outs VECREG:$rT), (ins VECREG:$rA, rotNeg7imm:$val),
2415 "rotqmbii\t$rT, $rA, $val", RotateShift,
2416 [/* intrinsic */]>;
2417
2418def ROTMAHv8i16:
2419 RRForm<0b01111010000, (outs VECREG:$rT), (ins VECREG:$rA, R32C:$rB),
2420 "rotmah\t$rT, $rA, $rB", RotateShift,
2421 [/* see patterns below - $rB must be negated */]>;
2422
2423def : Pat<(SPUvec_sra_v8i16 VECREG:$rA, R32C:$rB),
2424 (ROTMAHv8i16 VECREG:$rA, (SFIr32 R32C:$rB, 0))>;
2425
2426def : Pat<(SPUvec_sra_v8i16 VECREG:$rA, R16C:$rB),
2427 (ROTMAHv8i16 VECREG:$rA,
2428 (SFIr32 (XSHWr16 R16C:$rB), 0))>;
2429
Scott Michel438be252007-12-17 22:32:34 +00002430def : Pat<(SPUvec_sra_v8i16 VECREG:$rA, R8C:$rB),
2431 (ROTMAHv8i16 VECREG:$rA,
2432 (SFIr32 (XSHWr16 (XSBHr8 R8C:$rB)), 0))>;
2433
Scott Michel8b6b4202007-12-04 22:35:58 +00002434def ROTMAHr16:
2435 RRForm<0b01111010000, (outs R16C:$rT), (ins R16C:$rA, R32C:$rB),
2436 "rotmah\t$rT, $rA, $rB", RotateShift,
2437 [/* see patterns below - $rB must be negated */]>;
2438
2439def : Pat<(sra R16C:$rA, R32C:$rB),
2440 (ROTMAHr16 R16C:$rA, (SFIr32 R32C:$rB, 0))>;
2441
2442def : Pat<(sra R16C:$rA, R16C:$rB),
2443 (ROTMAHr16 R16C:$rA,
2444 (SFIr32 (XSHWr16 R16C:$rB), 0))>;
2445
Scott Michel438be252007-12-17 22:32:34 +00002446def : Pat<(sra R16C:$rA, R8C:$rB),
2447 (ROTMAHr16 R16C:$rA,
2448 (SFIr32 (XSHWr16 (XSBHr8 R8C:$rB)), 0))>;
2449
Scott Michel8b6b4202007-12-04 22:35:58 +00002450def ROTMAHIv8i16:
2451 RRForm<0b01111110000, (outs VECREG:$rT), (ins VECREG:$rA, rothNeg7imm:$val),
2452 "rotmahi\t$rT, $rA, $val", RotateShift,
2453 [(set (v8i16 VECREG:$rT),
2454 (SPUvec_sra_v8i16 (v8i16 VECREG:$rA), (i32 uimm7:$val)))]>;
2455
2456def : Pat<(SPUvec_sra_v8i16 (v8i16 VECREG:$rA), (i16 uimm7:$val)),
2457 (ROTMAHIv8i16 (v8i16 VECREG:$rA), (i32 uimm7:$val))>;
2458
Scott Michel438be252007-12-17 22:32:34 +00002459def : Pat<(SPUvec_sra_v8i16 (v8i16 VECREG:$rA), (i8 uimm7:$val)),
2460 (ROTMAHIv8i16 (v8i16 VECREG:$rA), (i32 uimm7:$val))>;
2461
Scott Michel8b6b4202007-12-04 22:35:58 +00002462def ROTMAHIr16:
2463 RRForm<0b01111110000, (outs R16C:$rT), (ins R16C:$rA, rothNeg7imm_i16:$val),
2464 "rotmahi\t$rT, $rA, $val", RotateShift,
2465 [(set R16C:$rT, (sra R16C:$rA, (i16 uimm7:$val)))]>;
2466
2467def : Pat<(sra R16C:$rA, (i32 imm:$val)),
2468 (ROTMAHIr16 R16C:$rA, uimm7:$val)>;
2469
Scott Michel438be252007-12-17 22:32:34 +00002470def : Pat<(sra R16C:$rA, (i8 imm:$val)),
2471 (ROTMAHIr16 R16C:$rA, uimm7:$val)>;
2472
Scott Michel8b6b4202007-12-04 22:35:58 +00002473def ROTMAv4i32:
2474 RRForm<0b01011010000, (outs VECREG:$rT), (ins VECREG:$rA, R32C:$rB),
2475 "rotma\t$rT, $rA, $rB", RotateShift,
2476 [/* see patterns below - $rB must be negated */]>;
2477
2478def : Pat<(SPUvec_sra_v4i32 VECREG:$rA, R32C:$rB),
2479 (ROTMAv4i32 (v4i32 VECREG:$rA), (SFIr32 R32C:$rB, 0))>;
2480
2481def : Pat<(SPUvec_sra_v4i32 VECREG:$rA, R16C:$rB),
2482 (ROTMAv4i32 (v4i32 VECREG:$rA),
2483 (SFIr32 (XSHWr16 R16C:$rB), 0))>;
2484
Scott Michel438be252007-12-17 22:32:34 +00002485def : Pat<(SPUvec_sra_v4i32 VECREG:$rA, R8C:$rB),
2486 (ROTMAv4i32 (v4i32 VECREG:$rA),
2487 (SFIr32 (XSHWr16 (XSBHr8 R8C:$rB)), 0))>;
2488
Scott Michel8b6b4202007-12-04 22:35:58 +00002489def ROTMAr32:
2490 RRForm<0b01011010000, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
2491 "rotma\t$rT, $rA, $rB", RotateShift,
2492 [/* see patterns below - $rB must be negated */]>;
2493
2494def : Pat<(sra R32C:$rA, R32C:$rB),
2495 (ROTMAr32 R32C:$rA, (SFIr32 R32C:$rB, 0))>;
2496
2497def : Pat<(sra R32C:$rA, R16C:$rB),
2498 (ROTMAr32 R32C:$rA,
2499 (SFIr32 (XSHWr16 R16C:$rB), 0))>;
2500
Scott Michel438be252007-12-17 22:32:34 +00002501def : Pat<(sra R32C:$rA, R8C:$rB),
2502 (ROTMAr32 R32C:$rA,
2503 (SFIr32 (XSHWr16 (XSBHr8 R8C:$rB)), 0))>;
2504
Scott Michel8b6b4202007-12-04 22:35:58 +00002505def ROTMAIv4i32:
2506 RRForm<0b01011110000, (outs VECREG:$rT), (ins VECREG:$rA, rotNeg7imm:$val),
2507 "rotmai\t$rT, $rA, $val", RotateShift,
2508 [(set (v4i32 VECREG:$rT),
2509 (SPUvec_sra_v4i32 VECREG:$rA, (i32 uimm7:$val)))]>;
2510
2511def : Pat<(SPUvec_sra_v4i32 VECREG:$rA, (i16 uimm7:$val)),
2512 (ROTMAIv4i32 VECREG:$rA, uimm7:$val)>;
2513
2514def ROTMAIr32:
2515 RRForm<0b01011110000, (outs R32C:$rT), (ins R32C:$rA, rotNeg7imm:$val),
2516 "rotmai\t$rT, $rA, $val", RotateShift,
2517 [(set R32C:$rT, (sra R32C:$rA, (i32 uimm7:$val)))]>;
2518
2519def : Pat<(sra R32C:$rA, (i16 uimm7:$val)),
2520 (ROTMAIr32 R32C:$rA, uimm7:$val)>;
2521
Scott Michel438be252007-12-17 22:32:34 +00002522def : Pat<(sra R32C:$rA, (i8 uimm7:$val)),
2523 (ROTMAIr32 R32C:$rA, uimm7:$val)>;
2524
Scott Michel8b6b4202007-12-04 22:35:58 +00002525//===----------------------------------------------------------------------===//
2526// Branch and conditionals:
2527//===----------------------------------------------------------------------===//
2528
2529let isTerminator = 1, isBarrier = 1 in {
2530 // Halt If Equal (r32 preferred slot only, no vector form)
2531 def HEQr32:
2532 RRForm_3<0b00011011110, (outs), (ins R32C:$rA, R32C:$rB),
2533 "heq\t$rA, $rB", BranchResolv,
2534 [/* no pattern to match */]>;
2535
2536 def HEQIr32 :
2537 RI10Form_2<0b11111110, (outs), (ins R32C:$rA, s10imm:$val),
2538 "heqi\t$rA, $val", BranchResolv,
2539 [/* no pattern to match */]>;
2540
2541 // HGT/HGTI: These instructions use signed arithmetic for the comparison,
2542 // contrasting with HLGT/HLGTI, which use unsigned comparison:
2543 def HGTr32:
2544 RRForm_3<0b00011010010, (outs), (ins R32C:$rA, R32C:$rB),
2545 "hgt\t$rA, $rB", BranchResolv,
2546 [/* no pattern to match */]>;
2547
2548 def HGTIr32:
2549 RI10Form_2<0b11110010, (outs), (ins R32C:$rA, s10imm:$val),
2550 "hgti\t$rA, $val", BranchResolv,
2551 [/* no pattern to match */]>;
2552
2553 def HLGTr32:
2554 RRForm_3<0b00011011010, (outs), (ins R32C:$rA, R32C:$rB),
2555 "hlgt\t$rA, $rB", BranchResolv,
2556 [/* no pattern to match */]>;
2557
2558 def HLGTIr32:
2559 RI10Form_2<0b11111010, (outs), (ins R32C:$rA, s10imm:$val),
2560 "hlgti\t$rA, $val", BranchResolv,
2561 [/* no pattern to match */]>;
2562}
2563
2564// Comparison operators:
Scott Michel438be252007-12-17 22:32:34 +00002565def CEQBr8:
2566 RRForm<0b00001011110, (outs R8C:$rT), (ins R8C:$rA, R8C:$rB),
2567 "ceqb\t$rT, $rA, $rB", ByteOp,
2568 [/* no pattern to match */]>;
Scott Michel8b6b4202007-12-04 22:35:58 +00002569
2570def CEQBv16i8:
2571 RRForm<0b00001011110, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
2572 "ceqb\t$rT, $rA, $rB", ByteOp,
2573 [/* no pattern to match: intrinsic */]>;
2574
Scott Michel438be252007-12-17 22:32:34 +00002575def CEQBIr8:
Scott Micheldbac4cf2008-01-11 02:53:15 +00002576 RI10Form<0b01111110, (outs R8C:$rT), (ins R8C:$rA, s7imm_i8:$val),
Scott Michel438be252007-12-17 22:32:34 +00002577 "ceqbi\t$rT, $rA, $val", ByteOp,
2578 [/* no pattern to match: intrinsic */]>;
2579
Scott Michel8b6b4202007-12-04 22:35:58 +00002580def CEQBIv16i8:
Scott Micheldbac4cf2008-01-11 02:53:15 +00002581 RI10Form<0b01111110, (outs VECREG:$rT), (ins VECREG:$rA, s7imm_i8:$val),
Scott Michel8b6b4202007-12-04 22:35:58 +00002582 "ceqbi\t$rT, $rA, $val", ByteOp,
2583 [/* no pattern to match: intrinsic */]>;
2584
2585def CEQHr16:
2586 RRForm<0b00010011110, (outs R16C:$rT), (ins R16C:$rA, R16C:$rB),
2587 "ceqh\t$rT, $rA, $rB", ByteOp,
2588 [/* no pattern to match */]>;
2589
2590def CEQHv8i16:
2591 RRForm<0b00010011110, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
2592 "ceqh\t$rT, $rA, $rB", ByteOp,
2593 [/* no pattern to match: intrinsic */]>;
2594
2595def CEQHIr16:
2596 RI10Form<0b10111110, (outs R16C:$rT), (ins R16C:$rA, s10imm:$val),
2597 "ceqhi\t$rT, $rA, $val", ByteOp,
2598 [/* no pattern to match: intrinsic */]>;
2599
2600def CEQHIv8i16:
2601 RI10Form<0b10111110, (outs VECREG:$rT), (ins VECREG:$rA, s10imm:$val),
2602 "ceqhi\t$rT, $rA, $val", ByteOp,
2603 [/* no pattern to match: intrinsic */]>;
2604
2605def CEQr32:
2606 RRForm<0b00000011110, (outs R32C:$rT), (ins R32C:$rA, R32C:$rB),
2607 "ceq\t$rT, $rA, $rB", ByteOp,
Scott Michelf9f42e62008-01-29 02:16:57 +00002608 [(set R32C:$rT, (seteq R32C:$rA, R32C:$rB))]>;
Scott Michel8b6b4202007-12-04 22:35:58 +00002609
2610def CEQv4i32:
2611 RRForm<0b00000011110, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
2612 "ceq\t$rT, $rA, $rB", ByteOp,
Scott Michelf9f42e62008-01-29 02:16:57 +00002613 [(set (v4i32 VECREG:$rT), (seteq (v4i32 VECREG:$rA), (v4i32 VECREG:$rB)))]>;
Scott Michel8b6b4202007-12-04 22:35:58 +00002614
2615def CEQIr32:
Scott Michelf9f42e62008-01-29 02:16:57 +00002616 RI10Form<0b00111110, (outs R32C:$rT), (ins R32C:$rA, s10imm_i32:$val),
Scott Michel8b6b4202007-12-04 22:35:58 +00002617 "ceqi\t$rT, $rA, $val", ByteOp,
Scott Michelf9f42e62008-01-29 02:16:57 +00002618 [(set R32C:$rT, (seteq R32C:$rA, i32ImmSExt10:$val))]>;
Scott Michel8b6b4202007-12-04 22:35:58 +00002619
2620def CEQIv4i32:
2621 RI10Form<0b00111110, (outs VECREG:$rT), (ins VECREG:$rA, s10imm:$val),
2622 "ceqi\t$rT, $rA, $val", ByteOp,
2623 [/* no pattern to match: intrinsic */]>;
2624
2625let isCall = 1,
2626 // All calls clobber the non-callee-saved registers:
2627 Defs = [R0, R1, R2, R3, R4, R5, R6, R7, R8, R9,
2628 R10,R11,R12,R13,R14,R15,R16,R17,R18,R19,
2629 R20,R21,R22,R23,R24,R25,R26,R27,R28,R29,
2630 R30,R31,R32,R33,R34,R35,R36,R37,R38,R39,
2631 R40,R41,R42,R43,R44,R45,R46,R47,R48,R49,
2632 R50,R51,R52,R53,R54,R55,R56,R57,R58,R59,
2633 R60,R61,R62,R63,R64,R65,R66,R67,R68,R69,
2634 R70,R71,R72,R73,R74,R75,R76,R77,R78,R79],
2635 // All of these instructions use $lr (aka $0)
2636 Uses = [R0] in {
2637 // Branch relative and set link: Used if we actually know that the target
2638 // is within [-32768, 32767] bytes of the target
2639 def BRSL:
2640 BranchSetLink<0b011001100, (outs), (ins relcalltarget:$func, variable_ops),
2641 "brsl\t$$lr, $func",
2642 [(SPUcall (SPUpcrel tglobaladdr:$func, 0))]>;
2643
2644 // Branch absolute and set link: Used if we actually know that the target
2645 // is an absolute address
2646 def BRASL:
2647 BranchSetLink<0b011001100, (outs), (ins calltarget:$func, variable_ops),
2648 "brasl\t$$lr, $func",
Scott Micheldbac4cf2008-01-11 02:53:15 +00002649 [(SPUcall (SPUaform tglobaladdr:$func, 0))]>;
Scott Michel8b6b4202007-12-04 22:35:58 +00002650
2651 // Branch indirect and set link if external data. These instructions are not
2652 // actually generated, matched by an intrinsic:
2653 def BISLED_00: BISLEDForm<0b11, "bisled\t$$lr, $func", [/* empty pattern */]>;
2654 def BISLED_E0: BISLEDForm<0b10, "bisled\t$$lr, $func", [/* empty pattern */]>;
2655 def BISLED_0D: BISLEDForm<0b01, "bisled\t$$lr, $func", [/* empty pattern */]>;
2656 def BISLED_ED: BISLEDForm<0b00, "bisled\t$$lr, $func", [/* empty pattern */]>;
2657
2658 // Branch indirect and set link. This is the "X-form" address version of a
2659 // function call
2660 def BISL:
2661 BIForm<0b10010101100, "bisl\t$$lr, $func", [(SPUcall R32C:$func)]>;
2662}
2663
2664// Unconditional branches:
2665let isBranch = 1, isTerminator = 1, hasCtrlDep = 1, isBarrier = 1 in {
2666 def BR :
2667 UncondBranch<0b001001100, (outs), (ins brtarget:$dest),
2668 "br\t$dest",
2669 [(br bb:$dest)]>;
2670
2671 // Unconditional, absolute address branch
2672 def BRA:
2673 UncondBranch<0b001100000, (outs), (ins brtarget:$dest),
2674 "bra\t$dest",
2675 [/* no pattern */]>;
2676
2677 // Indirect branch
2678 def BI:
2679 BIForm<0b00010101100, "bi\t$func", [(brind R32C:$func)]>;
2680
2681 // Various branches:
2682 def BRNZ:
2683 RI16Form<0b010000100, (outs), (ins R32C:$rCond, brtarget:$dest),
2684 "brnz\t$rCond,$dest",
2685 BranchResolv,
2686 [(brcond R32C:$rCond, bb:$dest)]>;
2687
2688 def BRZ:
2689 RI16Form<0b000000100, (outs), (ins R32C:$rT, brtarget:$dest),
2690 "brz\t$rT,$dest",
2691 BranchResolv,
2692 [/* no pattern */]>;
2693
2694 def BRHNZ:
2695 RI16Form<0b011000100, (outs), (ins R16C:$rCond, brtarget:$dest),
2696 "brhnz\t$rCond,$dest",
2697 BranchResolv,
2698 [(brcond R16C:$rCond, bb:$dest)]>;
2699
2700 def BRHZ:
2701 RI16Form<0b001000100, (outs), (ins R16C:$rT, brtarget:$dest),
2702 "brhz\t$rT,$dest",
2703 BranchResolv,
2704 [/* no pattern */]>;
2705
2706/*
2707 def BINZ:
2708 BICondForm<0b10010100100, "binz\t$rA, $func",
2709 [(SPUbinz R32C:$rA, R32C:$func)]>;
2710
2711 def BIZ:
2712 BICondForm<0b00010100100, "biz\t$rA, $func",
2713 [(SPUbiz R32C:$rA, R32C:$func)]>;
2714*/
2715}
2716
Scott Michel394e26d2008-01-17 20:38:41 +00002717//===----------------------------------------------------------------------===//
Scott Michelf9f42e62008-01-29 02:16:57 +00002718// setcc and brcond patterns:
Scott Michel394e26d2008-01-17 20:38:41 +00002719//===----------------------------------------------------------------------===//
Scott Michelf9f42e62008-01-29 02:16:57 +00002720
Scott Michel8b6b4202007-12-04 22:35:58 +00002721def : Pat<(brcond (i16 (seteq R16C:$rA, 0)), bb:$dest),
2722 (BRHZ R16C:$rA, bb:$dest)>;
Scott Michel8b6b4202007-12-04 22:35:58 +00002723def : Pat<(brcond (i32 (seteq R32C:$rA, 0)), bb:$dest),
2724 (BRZ R32C:$rA, bb:$dest)>;
Scott Michelf9f42e62008-01-29 02:16:57 +00002725
2726def : Pat<(brcond (i16 (setne R16C:$rA, 0)), bb:$dest),
2727 (BRHNZ R16C:$rA, bb:$dest)>;
Scott Michel8b6b4202007-12-04 22:35:58 +00002728def : Pat<(brcond (i32 (setne R32C:$rA, 0)), bb:$dest),
Scott Michel394e26d2008-01-17 20:38:41 +00002729 (BRNZ R32C:$rA, bb:$dest)>;
Scott Michel8b6b4202007-12-04 22:35:58 +00002730
Scott Michelf9f42e62008-01-29 02:16:57 +00002731def : Pat<(brcond (i16 (setne R16C:$rA, i16ImmSExt10:$val)), bb:$dest),
2732 (BRHNZ (CEQHIr16 R16C:$rA, i16ImmSExt10:$val), bb:$dest)>;
2733def : Pat<(brcond (i32 (setne R32C:$rA, i32ImmSExt10:$val)), bb:$dest),
2734 (BRNZ (CEQIr32 R32C:$rA, i32ImmSExt10:$val), bb:$dest)>;
2735
2736def : Pat<(brcond (i16 (setne R16C:$rA, R16C:$rB)), bb:$dest),
2737 (BRHNZ (CEQHr16 R16C:$rA, R16:$rB), bb:$dest)>;
2738def : Pat<(brcond (i32 (setne R32C:$rA, R32C:$rB)), bb:$dest),
2739 (BRNZ (CEQr32 R32C:$rA, R32C:$rB), bb:$dest)>;
2740
Scott Michel8b6b4202007-12-04 22:35:58 +00002741let isTerminator = 1, isBarrier = 1 in {
2742 let isReturn = 1 in {
2743 def RET:
2744 RETForm<"bi\t$$lr", [(retflag)]>;
2745 }
2746}
2747
2748//===----------------------------------------------------------------------===//
Scott Michel8b6b4202007-12-04 22:35:58 +00002749// Single precision floating point instructions
2750//===----------------------------------------------------------------------===//
2751
2752def FAv4f32:
2753 RRForm<0b00100011010, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
2754 "fa\t$rT, $rA, $rB", SPrecFP,
2755 [(set (v4f32 VECREG:$rT), (fadd (v4f32 VECREG:$rA), (v4f32 VECREG:$rB)))]>;
2756
2757def FAf32 :
2758 RRForm<0b00100011010, (outs R32FP:$rT), (ins R32FP:$rA, R32FP:$rB),
2759 "fa\t$rT, $rA, $rB", SPrecFP,
2760 [(set R32FP:$rT, (fadd R32FP:$rA, R32FP:$rB))]>;
2761
2762def FSv4f32:
2763 RRForm<0b00100011010, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
2764 "fs\t$rT, $rA, $rB", SPrecFP,
2765 [(set (v4f32 VECREG:$rT), (fsub (v4f32 VECREG:$rA), (v4f32 VECREG:$rB)))]>;
2766
2767def FSf32 :
2768 RRForm<0b10100011010, (outs R32FP:$rT), (ins R32FP:$rA, R32FP:$rB),
2769 "fs\t$rT, $rA, $rB", SPrecFP,
2770 [(set R32FP:$rT, (fsub R32FP:$rA, R32FP:$rB))]>;
2771
2772// Floating point reciprocal estimate
2773def FREv4f32 :
2774 RRForm_1<0b00011101100, (outs VECREG:$rT), (ins VECREG:$rA),
2775 "frest\t$rT, $rA", SPrecFP,
2776 [(set (v4f32 VECREG:$rT), (SPUreciprocalEst (v4f32 VECREG:$rA)))]>;
2777
2778def FREf32 :
2779 RRForm_1<0b00011101100, (outs R32FP:$rT), (ins R32FP:$rA),
2780 "frest\t$rT, $rA", SPrecFP,
2781 [(set R32FP:$rT, (SPUreciprocalEst R32FP:$rA))]>;
2782
2783// Floating point interpolate (used in conjunction with reciprocal estimate)
2784def FIv4f32 :
2785 RRForm<0b00101011110, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
2786 "fi\t$rT, $rA, $rB", SPrecFP,
2787 [(set (v4f32 VECREG:$rT), (SPUinterpolate (v4f32 VECREG:$rA),
2788 (v4f32 VECREG:$rB)))]>;
2789
2790def FIf32 :
2791 RRForm<0b00101011110, (outs R32FP:$rT), (ins R32FP:$rA, R32FP:$rB),
2792 "fi\t$rT, $rA, $rB", SPrecFP,
2793 [(set R32FP:$rT, (SPUinterpolate R32FP:$rA, R32FP:$rB))]>;
2794
2795// Floating Compare Equal
2796def FCEQf32 :
2797 RRForm<0b01000011110, (outs R32C:$rT), (ins R32FP:$rA, R32FP:$rB),
2798 "fceq\t$rT, $rA, $rB", SPrecFP,
2799 [(set R32C:$rT, (setoeq R32FP:$rA, R32FP:$rB))]>;
2800
2801def FCMEQf32 :
2802 RRForm<0b01010011110, (outs R32C:$rT), (ins R32FP:$rA, R32FP:$rB),
2803 "fcmeq\t$rT, $rA, $rB", SPrecFP,
2804 [(set R32C:$rT, (setoeq (fabs R32FP:$rA), (fabs R32FP:$rB)))]>;
2805
2806def FCGTf32 :
2807 RRForm<0b01000011010, (outs R32C:$rT), (ins R32FP:$rA, R32FP:$rB),
2808 "fcgt\t$rT, $rA, $rB", SPrecFP,
2809 [(set R32C:$rT, (setogt R32FP:$rA, R32FP:$rB))]>;
2810
2811def FCMGTf32 :
2812 RRForm<0b01010011010, (outs R32C:$rT), (ins R32FP:$rA, R32FP:$rB),
2813 "fcmgt\t$rT, $rA, $rB", SPrecFP,
2814 [(set R32C:$rT, (setogt (fabs R32FP:$rA), (fabs R32FP:$rB)))]>;
2815
2816// FP Status and Control Register Write
2817// Why isn't rT a don't care in the ISA?
2818// Should we create a special RRForm_3 for this guy and zero out the rT?
2819def FSCRWf32 :
2820 RRForm_1<0b01011101110, (outs R32FP:$rT), (ins R32FP:$rA),
2821 "fscrwr\t$rA", SPrecFP,
2822 [/* This instruction requires an intrinsic. Note: rT is unused. */]>;
2823
2824// FP Status and Control Register Read
2825def FSCRRf32 :
2826 RRForm_2<0b01011101110, (outs R32FP:$rT), (ins),
2827 "fscrrd\t$rT", SPrecFP,
2828 [/* This instruction requires an intrinsic */]>;
2829
2830// llvm instruction space
2831// How do these map onto cell instructions?
2832// fdiv rA rB
2833// frest rC rB # c = 1/b (both lines)
2834// fi rC rB rC
2835// fm rD rA rC # d = a * 1/b
2836// fnms rB rD rB rA # b = - (d * b - a) --should == 0 in a perfect world
2837// fma rB rB rC rD # b = b * c + d
2838// = -(d *b -a) * c + d
2839// = a * c - c ( a *b *c - a)
2840
2841// fcopysign (???)
2842
2843// Library calls:
2844// These llvm instructions will actually map to library calls.
2845// All that's needed, then, is to check that the appropriate library is
2846// imported and do a brsl to the proper function name.
2847// frem # fmod(x, y): x - (x/y) * y
2848// (Note: fmod(double, double), fmodf(float,float)
2849// fsqrt?
2850// fsin?
2851// fcos?
2852// Unimplemented SPU instruction space
2853// floating reciprocal absolute square root estimate (frsqest)
2854
2855// The following are probably just intrinsics
2856// status and control register write
2857// status and control register read
2858
2859//--------------------------------------
2860// Floating point multiply instructions
2861//--------------------------------------
2862
2863def FMv4f32:
2864 RRForm<0b00100011010, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
2865 "fm\t$rT, $rA, $rB", SPrecFP,
2866 [(set (v4f32 VECREG:$rT), (fmul (v4f32 VECREG:$rA),
2867 (v4f32 VECREG:$rB)))]>;
2868
2869def FMf32 :
2870 RRForm<0b01100011010, (outs R32FP:$rT), (ins R32FP:$rA, R32FP:$rB),
2871 "fm\t$rT, $rA, $rB", SPrecFP,
2872 [(set R32FP:$rT, (fmul R32FP:$rA, R32FP:$rB))]>;
2873
2874// Floating point multiply and add
2875// e.g. d = c + (a * b)
2876def FMAv4f32:
2877 RRRForm<0b0111, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB, VECREG:$rC),
2878 "fma\t$rT, $rA, $rB, $rC", SPrecFP,
2879 [(set (v4f32 VECREG:$rT),
2880 (fadd (v4f32 VECREG:$rC),
2881 (fmul (v4f32 VECREG:$rA), (v4f32 VECREG:$rB))))]>;
2882
2883def FMAf32:
2884 RRRForm<0b0111, (outs R32FP:$rT), (ins R32FP:$rA, R32FP:$rB, R32FP:$rC),
2885 "fma\t$rT, $rA, $rB, $rC", SPrecFP,
2886 [(set R32FP:$rT, (fadd R32FP:$rC, (fmul R32FP:$rA, R32FP:$rB)))]>;
2887
2888// FP multiply and subtract
2889// Subtracts value in rC from product
2890// res = a * b - c
2891def FMSv4f32 :
2892 RRRForm<0b0111, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB, VECREG:$rC),
2893 "fms\t$rT, $rA, $rB, $rC", SPrecFP,
2894 [(set (v4f32 VECREG:$rT),
2895 (fsub (fmul (v4f32 VECREG:$rA), (v4f32 VECREG:$rB)),
2896 (v4f32 VECREG:$rC)))]>;
2897
2898def FMSf32 :
2899 RRRForm<0b0111, (outs R32FP:$rT), (ins R32FP:$rA, R32FP:$rB, R32FP:$rC),
2900 "fms\t$rT, $rA, $rB, $rC", SPrecFP,
2901 [(set R32FP:$rT,
2902 (fsub (fmul R32FP:$rA, R32FP:$rB), R32FP:$rC))]>;
2903
2904// Floating Negative Mulitply and Subtract
2905// Subtracts product from value in rC
2906// res = fneg(fms a b c)
2907// = - (a * b - c)
2908// = c - a * b
2909// NOTE: subtraction order
2910// fsub a b = a - b
2911// fs a b = b - a?
2912def FNMSf32 :
2913 RRRForm<0b1101, (outs R32FP:$rT), (ins R32FP:$rA, R32FP:$rB, R32FP:$rC),
2914 "fnms\t$rT, $rA, $rB, $rC", SPrecFP,
2915 [(set R32FP:$rT, (fsub R32FP:$rC, (fmul R32FP:$rA, R32FP:$rB)))]>;
2916
2917def FNMSv4f32 :
2918 RRRForm<0b1101, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB, VECREG:$rC),
2919 "fnms\t$rT, $rA, $rB, $rC", SPrecFP,
2920 [(set (v4f32 VECREG:$rT),
2921 (fsub (v4f32 VECREG:$rC),
2922 (fmul (v4f32 VECREG:$rA),
2923 (v4f32 VECREG:$rB))))]>;
2924
2925//--------------------------------------
2926// Floating Point Conversions
2927// Signed conversions:
2928def CSiFv4f32:
2929 CVTIntFPForm<0b0101101110, (outs VECREG:$rT), (ins VECREG:$rA),
2930 "csflt\t$rT, $rA, 0", SPrecFP,
2931 [(set (v4f32 VECREG:$rT), (sint_to_fp (v4i32 VECREG:$rA)))]>;
2932
2933// Convert signed integer to floating point
2934def CSiFf32 :
2935 CVTIntFPForm<0b0101101110, (outs R32FP:$rT), (ins R32C:$rA),
2936 "csflt\t$rT, $rA, 0", SPrecFP,
2937 [(set R32FP:$rT, (sint_to_fp R32C:$rA))]>;
2938
2939// Convert unsigned into to float
2940def CUiFv4f32 :
2941 CVTIntFPForm<0b1101101110, (outs VECREG:$rT), (ins VECREG:$rA),
2942 "cuflt\t$rT, $rA, 0", SPrecFP,
2943 [(set (v4f32 VECREG:$rT), (uint_to_fp (v4i32 VECREG:$rA)))]>;
2944
2945def CUiFf32 :
2946 CVTIntFPForm<0b1101101110, (outs R32FP:$rT), (ins R32C:$rA),
2947 "cuflt\t$rT, $rA, 0", SPrecFP,
2948 [(set R32FP:$rT, (uint_to_fp R32C:$rA))]>;
2949
2950// Convert float to unsigned int
2951// Assume that scale = 0
2952
2953def CFUiv4f32 :
2954 CVTIntFPForm<0b1101101110, (outs VECREG:$rT), (ins VECREG:$rA),
2955 "cfltu\t$rT, $rA, 0", SPrecFP,
2956 [(set (v4i32 VECREG:$rT), (fp_to_uint (v4f32 VECREG:$rA)))]>;
2957
2958def CFUif32 :
2959 CVTIntFPForm<0b1101101110, (outs R32C:$rT), (ins R32FP:$rA),
2960 "cfltu\t$rT, $rA, 0", SPrecFP,
2961 [(set R32C:$rT, (fp_to_uint R32FP:$rA))]>;
2962
2963// Convert float to signed int
2964// Assume that scale = 0
2965
2966def CFSiv4f32 :
2967 CVTIntFPForm<0b1101101110, (outs VECREG:$rT), (ins VECREG:$rA),
2968 "cflts\t$rT, $rA, 0", SPrecFP,
2969 [(set (v4i32 VECREG:$rT), (fp_to_sint (v4f32 VECREG:$rA)))]>;
2970
2971def CFSif32 :
2972 CVTIntFPForm<0b1101101110, (outs R32C:$rT), (ins R32FP:$rA),
2973 "cflts\t$rT, $rA, 0", SPrecFP,
2974 [(set R32C:$rT, (fp_to_sint R32FP:$rA))]>;
2975
2976//===----------------------------------------------------------------------==//
2977// Single<->Double precision conversions
2978//===----------------------------------------------------------------------==//
2979
2980// NOTE: We use "vec" name suffix here to avoid confusion (e.g. input is a
2981// v4f32, output is v2f64--which goes in the name?)
2982
2983// Floating point extend single to double
2984// NOTE: Not sure if passing in v4f32 to FESDvec is correct since it
2985// operates on two double-word slots (i.e. 1st and 3rd fp numbers
2986// are ignored).
2987def FESDvec :
2988 RRForm_1<0b00011101110, (outs VECREG:$rT), (ins VECREG:$rA),
2989 "fesd\t$rT, $rA", SPrecFP,
2990 [(set (v2f64 VECREG:$rT), (fextend (v4f32 VECREG:$rA)))]>;
2991
2992def FESDf32 :
2993 RRForm_1<0b00011101110, (outs R64FP:$rT), (ins R32FP:$rA),
2994 "fesd\t$rT, $rA", SPrecFP,
2995 [(set R64FP:$rT, (fextend R32FP:$rA))]>;
2996
2997// Floating point round double to single
2998//def FRDSvec :
2999// RRForm_1<0b10011101110, (outs VECREG:$rT), (ins VECREG:$rA),
3000// "frds\t$rT, $rA,", SPrecFP,
3001// [(set (v4f32 R32FP:$rT), (fround (v2f64 R64FP:$rA)))]>;
3002
3003def FRDSf64 :
3004 RRForm_1<0b10011101110, (outs R32FP:$rT), (ins R64FP:$rA),
3005 "frds\t$rT, $rA", SPrecFP,
3006 [(set R32FP:$rT, (fround R64FP:$rA))]>;
3007
3008//ToDo include anyextend?
3009
3010//===----------------------------------------------------------------------==//
3011// Double precision floating point instructions
3012//===----------------------------------------------------------------------==//
3013def FAf64 :
3014 RRForm<0b00110011010, (outs R64FP:$rT), (ins R64FP:$rA, R64FP:$rB),
3015 "dfa\t$rT, $rA, $rB", DPrecFP,
3016 [(set R64FP:$rT, (fadd R64FP:$rA, R64FP:$rB))]>;
3017
3018def FAv2f64 :
3019 RRForm<0b00110011010, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
3020 "dfa\t$rT, $rA, $rB", DPrecFP,
3021 [(set (v2f64 VECREG:$rT), (fadd (v2f64 VECREG:$rA), (v2f64 VECREG:$rB)))]>;
3022
3023def FSf64 :
3024 RRForm<0b10100011010, (outs R64FP:$rT), (ins R64FP:$rA, R64FP:$rB),
3025 "dfs\t$rT, $rA, $rB", DPrecFP,
3026 [(set R64FP:$rT, (fsub R64FP:$rA, R64FP:$rB))]>;
3027
3028def FSv2f64 :
3029 RRForm<0b10100011010, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
3030 "dfs\t$rT, $rA, $rB", DPrecFP,
3031 [(set (v2f64 VECREG:$rT),
3032 (fsub (v2f64 VECREG:$rA), (v2f64 VECREG:$rB)))]>;
3033
3034def FMf64 :
3035 RRForm<0b01100011010, (outs R64FP:$rT), (ins R64FP:$rA, R64FP:$rB),
3036 "dfm\t$rT, $rA, $rB", DPrecFP,
3037 [(set R64FP:$rT, (fmul R64FP:$rA, R64FP:$rB))]>;
3038
3039def FMv2f64:
3040 RRForm<0b00100011010, (outs VECREG:$rT), (ins VECREG:$rA, VECREG:$rB),
3041 "dfm\t$rT, $rA, $rB", DPrecFP,
3042 [(set (v2f64 VECREG:$rT),
3043 (fmul (v2f64 VECREG:$rA), (v2f64 VECREG:$rB)))]>;
3044
3045def FMAf64:
3046 RRForm<0b00111010110, (outs R64FP:$rT),
3047 (ins R64FP:$rA, R64FP:$rB, R64FP:$rC),
3048 "dfma\t$rT, $rA, $rB", DPrecFP,
3049 [(set R64FP:$rT, (fadd R64FP:$rC, (fmul R64FP:$rA, R64FP:$rB)))]>,
3050 RegConstraint<"$rC = $rT">,
3051 NoEncode<"$rC">;
3052
3053def FMAv2f64:
3054 RRForm<0b00111010110, (outs VECREG:$rT),
3055 (ins VECREG:$rA, VECREG:$rB, VECREG:$rC),
3056 "dfma\t$rT, $rA, $rB", DPrecFP,
3057 [(set (v2f64 VECREG:$rT),
3058 (fadd (v2f64 VECREG:$rC),
3059 (fmul (v2f64 VECREG:$rA), (v2f64 VECREG:$rB))))]>,
3060 RegConstraint<"$rC = $rT">,
3061 NoEncode<"$rC">;
3062
3063def FMSf64 :
3064 RRForm<0b10111010110, (outs R64FP:$rT),
3065 (ins R64FP:$rA, R64FP:$rB, R64FP:$rC),
3066 "dfms\t$rT, $rA, $rB", DPrecFP,
3067 [(set R64FP:$rT, (fsub (fmul R64FP:$rA, R64FP:$rB), R64FP:$rC))]>,
3068 RegConstraint<"$rC = $rT">,
3069 NoEncode<"$rC">;
3070
3071def FMSv2f64 :
3072 RRForm<0b10111010110, (outs VECREG:$rT),
3073 (ins VECREG:$rA, VECREG:$rB, VECREG:$rC),
3074 "dfms\t$rT, $rA, $rB", DPrecFP,
3075 [(set (v2f64 VECREG:$rT),
3076 (fsub (fmul (v2f64 VECREG:$rA), (v2f64 VECREG:$rB)),
3077 (v2f64 VECREG:$rC)))]>;
3078
3079// FNMS: - (a * b - c)
3080// - (a * b) + c => c - (a * b)
3081def FNMSf64 :
3082 RRForm<0b01111010110, (outs R64FP:$rT),
3083 (ins R64FP:$rA, R64FP:$rB, R64FP:$rC),
3084 "dfnms\t$rT, $rA, $rB", DPrecFP,
3085 [(set R64FP:$rT, (fsub R64FP:$rC, (fmul R64FP:$rA, R64FP:$rB)))]>,
3086 RegConstraint<"$rC = $rT">,
3087 NoEncode<"$rC">;
3088
3089def : Pat<(fneg (fsub (fmul R64FP:$rA, R64FP:$rB), R64FP:$rC)),
3090 (FNMSf64 R64FP:$rA, R64FP:$rB, R64FP:$rC)>;
3091
3092def FNMSv2f64 :
3093 RRForm<0b01111010110, (outs VECREG:$rT),
3094 (ins VECREG:$rA, VECREG:$rB, VECREG:$rC),
3095 "dfnms\t$rT, $rA, $rB", DPrecFP,
3096 [(set (v2f64 VECREG:$rT),
3097 (fsub (v2f64 VECREG:$rC),
3098 (fmul (v2f64 VECREG:$rA),
3099 (v2f64 VECREG:$rB))))]>,
3100 RegConstraint<"$rC = $rT">,
3101 NoEncode<"$rC">;
3102
3103def : Pat<(fneg (fsub (fmul (v2f64 VECREG:$rA), (v2f64 VECREG:$rB)),
3104 (v2f64 VECREG:$rC))),
3105 (FNMSv2f64 VECREG:$rA, VECREG:$rB, VECREG:$rC)>;
3106
3107// - (a * b + c)
3108// - (a * b) - c
3109def FNMAf64 :
3110 RRForm<0b11111010110, (outs R64FP:$rT),
3111 (ins R64FP:$rA, R64FP:$rB, R64FP:$rC),
3112 "dfnma\t$rT, $rA, $rB", DPrecFP,
3113 [(set R64FP:$rT, (fneg (fadd R64FP:$rC, (fmul R64FP:$rA, R64FP:$rB))))]>,
3114 RegConstraint<"$rC = $rT">,
3115 NoEncode<"$rC">;
3116
3117def FNMAv2f64 :
3118 RRForm<0b11111010110, (outs VECREG:$rT),
3119 (ins VECREG:$rA, VECREG:$rB, VECREG:$rC),
3120 "dfnma\t$rT, $rA, $rB", DPrecFP,
3121 [(set (v2f64 VECREG:$rT),
3122 (fneg (fadd (v2f64 VECREG:$rC),
3123 (fmul (v2f64 VECREG:$rA),
3124 (v2f64 VECREG:$rB)))))]>,
3125 RegConstraint<"$rC = $rT">,
3126 NoEncode<"$rC">;
3127
3128//===----------------------------------------------------------------------==//
3129// Floating point negation and absolute value
3130//===----------------------------------------------------------------------==//
3131
3132def : Pat<(fneg (v4f32 VECREG:$rA)),
3133 (XORfnegvec (v4f32 VECREG:$rA),
3134 (v4f32 (ILHUv4i32 0x8000)))>;
3135
3136def : Pat<(fneg R32FP:$rA),
3137 (XORfneg32 R32FP:$rA, (ILHUr32 0x8000))>;
3138
3139def : Pat<(fneg (v2f64 VECREG:$rA)),
3140 (XORfnegvec (v2f64 VECREG:$rA),
3141 (v2f64 (ANDBIv16i8 (FSMBIv16i8 0x8080), 0x80)))>;
3142
3143def : Pat<(fneg R64FP:$rA),
3144 (XORfneg64 R64FP:$rA,
3145 (ANDBIv16i8 (FSMBIv16i8 0x8080), 0x80))>;
3146
3147// Floating point absolute value
3148
3149def : Pat<(fabs R32FP:$rA),
3150 (ANDfabs32 R32FP:$rA, (IOHLr32 (ILHUr32 0x7fff), 0xffff))>;
3151
3152def : Pat<(fabs (v4f32 VECREG:$rA)),
3153 (ANDfabsvec (v4f32 VECREG:$rA),
3154 (v4f32 (ANDBIv16i8 (FSMBIv16i8 0xffff), 0x7f)))>;
3155
3156def : Pat<(fabs R64FP:$rA),
3157 (ANDfabs64 R64FP:$rA, (ANDBIv16i8 (FSMBIv16i8 0xffff), 0x7f))>;
3158
3159def : Pat<(fabs (v2f64 VECREG:$rA)),
3160 (ANDfabsvec (v2f64 VECREG:$rA),
3161 (v2f64 (ANDBIv16i8 (FSMBIv16i8 0xffff), 0x7f)))>;
3162
3163//===----------------------------------------------------------------------===//
3164// Execution, Load NOP (execute NOPs belong in even pipeline, load NOPs belong
3165// in the odd pipeline)
3166//===----------------------------------------------------------------------===//
3167
3168def ENOP : I<(outs), (ins), "enop", ExecNOP> {
3169 let Pattern = [];
3170
3171 let Inst{0-10} = 0b10000000010;
3172 let Inst{11-17} = 0;
3173 let Inst{18-24} = 0;
3174 let Inst{25-31} = 0;
3175}
3176
3177def LNOP : I<(outs), (ins), "lnop", LoadNOP> {
3178 let Pattern = [];
3179
3180 let Inst{0-10} = 0b10000000000;
3181 let Inst{11-17} = 0;
3182 let Inst{18-24} = 0;
3183 let Inst{25-31} = 0;
3184}
3185
3186//===----------------------------------------------------------------------===//
3187// Bit conversions (type conversions between vector/packed types)
3188// NOTE: Promotions are handled using the XS* instructions. Truncation
3189// is not handled.
3190//===----------------------------------------------------------------------===//
3191def : Pat<(v16i8 (bitconvert (v8i16 VECREG:$src))), (v16i8 VECREG:$src)>;
3192def : Pat<(v16i8 (bitconvert (v4i32 VECREG:$src))), (v16i8 VECREG:$src)>;
3193def : Pat<(v16i8 (bitconvert (v2i64 VECREG:$src))), (v16i8 VECREG:$src)>;
3194def : Pat<(v16i8 (bitconvert (v4f32 VECREG:$src))), (v16i8 VECREG:$src)>;
3195def : Pat<(v16i8 (bitconvert (v2f64 VECREG:$src))), (v16i8 VECREG:$src)>;
3196
3197def : Pat<(v8i16 (bitconvert (v16i8 VECREG:$src))), (v8i16 VECREG:$src)>;
3198def : Pat<(v8i16 (bitconvert (v4i32 VECREG:$src))), (v8i16 VECREG:$src)>;
3199def : Pat<(v8i16 (bitconvert (v2i64 VECREG:$src))), (v8i16 VECREG:$src)>;
3200def : Pat<(v8i16 (bitconvert (v4f32 VECREG:$src))), (v8i16 VECREG:$src)>;
3201def : Pat<(v8i16 (bitconvert (v2f64 VECREG:$src))), (v8i16 VECREG:$src)>;
3202
3203def : Pat<(v4i32 (bitconvert (v16i8 VECREG:$src))), (v4i32 VECREG:$src)>;
3204def : Pat<(v4i32 (bitconvert (v8i16 VECREG:$src))), (v4i32 VECREG:$src)>;
3205def : Pat<(v4i32 (bitconvert (v2i64 VECREG:$src))), (v4i32 VECREG:$src)>;
3206def : Pat<(v4i32 (bitconvert (v4f32 VECREG:$src))), (v4i32 VECREG:$src)>;
3207def : Pat<(v4i32 (bitconvert (v2f64 VECREG:$src))), (v4i32 VECREG:$src)>;
3208
3209def : Pat<(v2i64 (bitconvert (v16i8 VECREG:$src))), (v2i64 VECREG:$src)>;
3210def : Pat<(v2i64 (bitconvert (v8i16 VECREG:$src))), (v2i64 VECREG:$src)>;
3211def : Pat<(v2i64 (bitconvert (v4i32 VECREG:$src))), (v2i64 VECREG:$src)>;
3212def : Pat<(v2i64 (bitconvert (v4f32 VECREG:$src))), (v2i64 VECREG:$src)>;
3213def : Pat<(v2i64 (bitconvert (v2f64 VECREG:$src))), (v2i64 VECREG:$src)>;
3214
3215def : Pat<(v4f32 (bitconvert (v16i8 VECREG:$src))), (v4f32 VECREG:$src)>;
3216def : Pat<(v4f32 (bitconvert (v8i16 VECREG:$src))), (v4f32 VECREG:$src)>;
3217def : Pat<(v4f32 (bitconvert (v2i64 VECREG:$src))), (v4f32 VECREG:$src)>;
3218def : Pat<(v4f32 (bitconvert (v4i32 VECREG:$src))), (v4f32 VECREG:$src)>;
3219def : Pat<(v4f32 (bitconvert (v2f64 VECREG:$src))), (v4f32 VECREG:$src)>;
3220
3221def : Pat<(v2f64 (bitconvert (v16i8 VECREG:$src))), (v2f64 VECREG:$src)>;
3222def : Pat<(v2f64 (bitconvert (v8i16 VECREG:$src))), (v2f64 VECREG:$src)>;
3223def : Pat<(v2f64 (bitconvert (v4i32 VECREG:$src))), (v2f64 VECREG:$src)>;
3224def : Pat<(v2f64 (bitconvert (v2i64 VECREG:$src))), (v2f64 VECREG:$src)>;
3225def : Pat<(v2f64 (bitconvert (v2f64 VECREG:$src))), (v2f64 VECREG:$src)>;
3226
3227def : Pat<(f32 (bitconvert (i32 R32C:$src))), (f32 R32FP:$src)>;
Scott Michel754d8662007-12-20 00:44:13 +00003228def : Pat<(f64 (bitconvert (i64 R64C:$src))), (f64 R64FP:$src)>;
Scott Michel8b6b4202007-12-04 22:35:58 +00003229
3230//===----------------------------------------------------------------------===//
3231// Instruction patterns:
3232//===----------------------------------------------------------------------===//
3233
3234// General 32-bit constants:
3235def : Pat<(i32 imm:$imm),
3236 (IOHLr32 (ILHUr32 (HI16 imm:$imm)), (LO16 imm:$imm))>;
3237
3238// Single precision float constants:
3239def : Pat<(SPUFPconstant (f32 fpimm:$imm)),
3240 (IOHLf32 (ILHUf32 (HI16_f32 fpimm:$imm)), (LO16_f32 fpimm:$imm))>;
3241
3242// General constant 32-bit vectors
3243def : Pat<(v4i32 v4i32Imm:$imm),
3244 (IOHLvec (v4i32 (ILHUv4i32 (HI16_vec v4i32Imm:$imm))),
3245 (LO16_vec v4i32Imm:$imm))>;
Scott Michel438be252007-12-17 22:32:34 +00003246
3247// 8-bit constants
3248def : Pat<(i8 imm:$imm),
3249 (ILHr8 imm:$imm)>;
Scott Michel8b6b4202007-12-04 22:35:58 +00003250
3251//===----------------------------------------------------------------------===//
3252// Call instruction patterns:
3253//===----------------------------------------------------------------------===//
3254// Return void
3255def : Pat<(ret),
3256 (RET)>;
3257
3258//===----------------------------------------------------------------------===//
3259// Zero/Any/Sign extensions
3260//===----------------------------------------------------------------------===//
3261
3262// zext 1->32: Zero extend i1 to i32
3263def : Pat<(SPUextract_i1_zext R32C:$rSrc),
3264 (ANDIr32 R32C:$rSrc, 0x1)>;
3265
3266// sext 8->32: Sign extend bytes to words
3267def : Pat<(sext_inreg R32C:$rSrc, i8),
3268 (XSHWr32 (XSBHr32 R32C:$rSrc))>;
3269
Scott Michel438be252007-12-17 22:32:34 +00003270def : Pat<(i32 (sext R8C:$rSrc)),
3271 (XSHWr16 (XSBHr8 R8C:$rSrc))>;
3272
Scott Michel8b6b4202007-12-04 22:35:58 +00003273def : Pat<(SPUextract_i8_sext VECREG:$rSrc),
3274 (XSHWr32 (XSBHr32 (ORi32_v4i32 (v4i32 VECREG:$rSrc),
3275 (v4i32 VECREG:$rSrc))))>;
3276
Scott Michel438be252007-12-17 22:32:34 +00003277// zext 8->16: Zero extend bytes to halfwords
3278def : Pat<(i16 (zext R8C:$rSrc)),
3279 (ANDHI1To2 R8C:$rSrc, 0xff)>;
3280
3281// zext 8->32 from preferred slot in load/store
Scott Michel8b6b4202007-12-04 22:35:58 +00003282def : Pat<(SPUextract_i8_zext VECREG:$rSrc),
3283 (ANDIr32 (ORi32_v4i32 (v4i32 VECREG:$rSrc), (v4i32 VECREG:$rSrc)),
3284 0xff)>;
3285
Scott Michel438be252007-12-17 22:32:34 +00003286// zext 8->32: Zero extend bytes to words
3287def : Pat<(i32 (zext R8C:$rSrc)),
3288 (ANDI1To4 R8C:$rSrc, 0xff)>;
3289
3290// anyext 8->16: Extend 8->16 bits, irrespective of sign
3291def : Pat<(i16 (anyext R8C:$rSrc)),
3292 (ORHI1To2 R8C:$rSrc, 0)>;
3293
3294// anyext 8->32: Extend 8->32 bits, irrespective of sign
3295def : Pat<(i32 (anyext R8C:$rSrc)),
3296 (ORI1To4 R8C:$rSrc, 0)>;
3297
Scott Michel8b6b4202007-12-04 22:35:58 +00003298// zext 16->32: Zero extend halfwords to words (note that we have to juggle the
3299// 0xffff constant since it will not fit into an immediate.)
3300def : Pat<(i32 (zext R16C:$rSrc)),
3301 (AND2To4 R16C:$rSrc, (ILAr32 0xffff))>;
3302
3303def : Pat<(i32 (zext (and R16C:$rSrc, 0xf))),
3304 (ANDI2To4 R16C:$rSrc, 0xf)>;
3305
3306def : Pat<(i32 (zext (and R16C:$rSrc, 0xff))),
3307 (ANDI2To4 R16C:$rSrc, 0xff)>;
3308
3309def : Pat<(i32 (zext (and R16C:$rSrc, 0xfff))),
3310 (ANDI2To4 R16C:$rSrc, 0xfff)>;
3311
3312// anyext 16->32: Extend 16->32 bits, irrespective of sign
3313def : Pat<(i32 (anyext R16C:$rSrc)),
3314 (ORI2To4 R16C:$rSrc, 0)>;
3315
3316//===----------------------------------------------------------------------===//
Scott Michelf9f42e62008-01-29 02:16:57 +00003317// Address generation: SPU, like PPC, has to split addresses into high and
Scott Michel8b6b4202007-12-04 22:35:58 +00003318// low parts in order to load them into a register.
3319//===----------------------------------------------------------------------===//
3320
Scott Michelf9f42e62008-01-29 02:16:57 +00003321def : Pat<(SPUaform tglobaladdr:$in, 0), (ILAlsa tglobaladdr:$in)>;
3322def : Pat<(SPUaform texternalsym:$in, 0), (ILAlsa texternalsym:$in)>;
3323def : Pat<(SPUaform tjumptable:$in, 0), (ILAlsa tjumptable:$in)>;
3324def : Pat<(SPUaform tconstpool:$in, 0), (ILAlsa tconstpool:$in)>;
3325
3326def : Pat<(SPUindirect (SPUhi tglobaladdr:$in, 0),
3327 (SPUlo tglobaladdr:$in, 0)),
Scott Micheldbac4cf2008-01-11 02:53:15 +00003328 (IOHLlo (ILHUhi tglobaladdr:$in), tglobaladdr:$in)>;
Scott Michel394e26d2008-01-17 20:38:41 +00003329
Scott Michelf9f42e62008-01-29 02:16:57 +00003330def : Pat<(SPUindirect (SPUhi texternalsym:$in, 0),
3331 (SPUlo texternalsym:$in, 0)),
3332 (IOHLlo (ILHUhi texternalsym:$in), texternalsym:$in)>;
3333
3334def : Pat<(SPUindirect (SPUhi tjumptable:$in, 0),
3335 (SPUlo tjumptable:$in, 0)),
Scott Micheldbac4cf2008-01-11 02:53:15 +00003336 (IOHLlo (ILHUhi tjumptable:$in), tjumptable:$in)>;
Scott Michel394e26d2008-01-17 20:38:41 +00003337
Scott Michelf9f42e62008-01-29 02:16:57 +00003338def : Pat<(SPUindirect (SPUhi tconstpool:$in, 0),
3339 (SPUlo tconstpool:$in, 0)),
3340 (IOHLlo (ILHUhi tconstpool:$in), tconstpool:$in)>;
3341
3342def : Pat<(add (SPUhi tglobaladdr:$in, 0), (SPUlo tglobaladdr:$in, 0)),
3343 (IOHLlo (ILHUhi tglobaladdr:$in), tglobaladdr:$in)>;
3344
3345def : Pat<(add (SPUhi texternalsym:$in, 0), (SPUlo texternalsym:$in, 0)),
3346 (IOHLlo (ILHUhi texternalsym:$in), texternalsym:$in)>;
3347
3348def : Pat<(add (SPUhi tjumptable:$in, 0), (SPUlo tjumptable:$in, 0)),
3349 (IOHLlo (ILHUhi tjumptable:$in), tjumptable:$in)>;
3350
3351def : Pat<(add (SPUhi tconstpool:$in, 0), (SPUlo tconstpool:$in, 0)),
3352 (IOHLlo (ILHUhi tconstpool:$in), tconstpool:$in)>;
Scott Michel8b6b4202007-12-04 22:35:58 +00003353
Scott Michel8b6b4202007-12-04 22:35:58 +00003354// Instrinsics:
3355include "CellSDKIntrinsics.td"