Add bunch of reg-mem inst patterns
[oota-llvm.git] / lib / Target / MSP430 / MSP430InstrInfo.td
1 //===- MSP430InstrInfo.td - MSP430 Instruction defs -----------*- tblgen-*-===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source 
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 // This file describes the MSP430 instructions in TableGen format.
11 //
12 //===----------------------------------------------------------------------===//
13
14 include "MSP430InstrFormats.td"
15
16 //===----------------------------------------------------------------------===//
17 // Type Constraints.
18 //===----------------------------------------------------------------------===//
19 class SDTCisI8<int OpNum> : SDTCisVT<OpNum, i8>;
20 class SDTCisI16<int OpNum> : SDTCisVT<OpNum, i16>;
21
22 //===----------------------------------------------------------------------===//
23 // Type Profiles.
24 //===----------------------------------------------------------------------===//
25
26 //===----------------------------------------------------------------------===//
27 // MSP430 Specific Node Definitions.
28 //===----------------------------------------------------------------------===//
29 def MSP430retflag : SDNode<"MSP430ISD::RET_FLAG", SDTNone,
30                      [SDNPHasChain, SDNPOptInFlag]>;
31
32 def MSP430rra     : SDNode<"MSP430ISD::RRA", SDTIntUnaryOp, []>;
33
34 //===----------------------------------------------------------------------===//
35 // MSP430 Operand Definitions.
36 //===----------------------------------------------------------------------===//
37
38 // Address operands
39 def memsrc : Operand<i16> {
40   let PrintMethod = "printSrcMemOperand";
41   let MIOperandInfo = (ops i16imm, GR16);
42 }
43
44 def memdst : Operand<i16> {
45   let PrintMethod = "printSrcMemOperand";
46   let MIOperandInfo = (ops i16imm, GR16);
47 }
48
49
50 //===----------------------------------------------------------------------===//
51 // MSP430 Complex Pattern Definitions.
52 //===----------------------------------------------------------------------===//
53
54 def addr : ComplexPattern<iPTR, 2, "SelectAddr", [], []>;
55
56 //===----------------------------------------------------------------------===//
57 // Pattern Fragments
58 def zextloadi16i8 : PatFrag<(ops node:$ptr), (i16 (zextloadi8 node:$ptr))>;
59 def  extloadi16i8 : PatFrag<(ops node:$ptr), (i16 ( extloadi8 node:$ptr))>;
60
61 //===----------------------------------------------------------------------===//
62 // Pseudo Instructions
63
64 let neverHasSideEffects = 1 in
65 def NOP : Pseudo<(outs), (ins), "nop", []>;
66
67 //===----------------------------------------------------------------------===//
68 // Real Instructions
69
70 // FIXME: Provide proper encoding!
71 let isReturn = 1, isTerminator = 1 in {
72   def RETI : Pseudo<(outs), (ins), "ret", [(MSP430retflag)]>;
73 }
74
75 //===----------------------------------------------------------------------===//
76 // Move Instructions
77
78 // FIXME: Provide proper encoding!
79 let neverHasSideEffects = 1 in {
80 def MOV8rr  : Pseudo<(outs GR8:$dst), (ins GR8:$src),
81                      "mov.b\t{$src, $dst|$dst, $src}",
82                      []>;
83 def MOV16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src),
84                      "mov.w\t{$src, $dst|$dst, $src}",
85                      []>;
86 }
87
88 // FIXME: Provide proper encoding!
89 let isReMaterializable = 1, isAsCheapAsAMove = 1 in {
90 def MOV8ri  : Pseudo<(outs GR8:$dst), (ins i8imm:$src),
91                      "mov.b\t{$src, $dst|$dst, $src}",
92                      [(set GR8:$dst, imm:$src)]>;
93 def MOV16ri : Pseudo<(outs GR16:$dst), (ins i16imm:$src),
94                      "mov.w\t{$src, $dst|$dst, $src}",
95                      [(set GR16:$dst, imm:$src)]>;
96 }
97
98 let canFoldAsLoad = 1, isReMaterializable = 1, mayHaveSideEffects = 1 in {
99 def MOV8rm  : Pseudo<(outs GR8:$dst), (ins memsrc:$src),
100                 "mov.b\t{$src, $dst|$dst, $src}",
101                 [(set GR8:$dst, (load addr:$src))]>;
102 def MOV16rm : Pseudo<(outs GR16:$dst), (ins memsrc:$src),
103                 "mov.w\t{$src, $dst|$dst, $src}",
104                 [(set GR16:$dst, (load addr:$src))]>;
105 }
106
107 def MOVZX16rr8 : Pseudo<(outs GR16:$dst), (ins GR8:$src),
108                 "mov.b\t{$src, $dst|$dst, $src}",
109                 [(set GR16:$dst, (zext GR8:$src))]>;
110 def MOVZX16rm8 : Pseudo<(outs GR16:$dst), (ins memsrc:$src),
111                 "mov.b\t{$src, $dst|$dst, $src}",
112                 [(set GR16:$dst, (zextloadi16i8 addr:$src))]>;
113
114 def MOV8mi  : Pseudo<(outs), (ins memdst:$dst, i8imm:$src),
115                 "mov.b\t{$src, $dst|$dst, $src}",
116                 [(store (i8 imm:$src), addr:$dst)]>;
117 def MOV16mi : Pseudo<(outs), (ins memdst:$dst, i16imm:$src),
118                 "mov.w\t{$src, $dst|$dst, $src}",
119                 [(store (i16 imm:$src), addr:$dst)]>;
120
121 def MOV8mr  : Pseudo<(outs), (ins memdst:$dst, GR8:$src),
122                 "mov.b\t{$src, $dst|$dst, $src}",
123                 [(store GR8:$src, addr:$dst)]>;
124 def MOV16mr : Pseudo<(outs), (ins memdst:$dst, GR16:$src),
125                 "mov.w\t{$src, $dst|$dst, $src}",
126                 [(store GR16:$src, addr:$dst)]>;
127
128 //===----------------------------------------------------------------------===//
129 // Arithmetic Instructions
130
131 let isTwoAddress = 1 in {
132
133 let Defs = [SRW] in {
134
135 let isCommutable = 1 in { // X = ADD Y, Z  == X = ADD Z, Y
136 // FIXME: Provide proper encoding!
137 def ADD8rr  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2),
138                      "add.b\t{$src2, $dst|$dst, $src2}",
139                      [(set GR8:$dst, (add GR8:$src1, GR8:$src2)),
140                       (implicit SRW)]>;
141 def ADD16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2),
142                      "add.w\t{$src2, $dst|$dst, $src2}",
143                      [(set GR16:$dst, (add GR16:$src1, GR16:$src2)),
144                       (implicit SRW)]>;
145 }
146
147 def ADD8rm  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2),
148                      "add.b\t{$src2, $dst|$dst, $src2}",
149                      [(set GR8:$dst, (add GR8:$src1, (load addr:$src2))),
150                       (implicit SRW)]>;
151 def ADD16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2),
152                      "add.w\t{$src2, $dst|$dst, $src2}",
153                      [(set GR16:$dst, (add GR16:$src1, (load addr:$src2))),
154                       (implicit SRW)]>;
155
156 def ADD8ri  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2),
157                      "add.b\t{$src2, $dst|$dst, $src2}",
158                      [(set GR8:$dst, (add GR8:$src1, imm:$src2)),
159                       (implicit SRW)]>;
160 def ADD16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2),
161                      "add.w\t{$src2, $dst|$dst, $src2}",
162                      [(set GR16:$dst, (add GR16:$src1, imm:$src2)),
163                       (implicit SRW)]>;
164
165 let Uses = [SRW] in {
166
167 let isCommutable = 1 in { // X = ADDC Y, Z  == X = ADDC Z, Y
168 def ADC8rr  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2),
169                      "addc.b\t{$src2, $dst|$dst, $src2}",
170                      [(set GR8:$dst, (adde GR8:$src1, GR8:$src2)),
171                       (implicit SRW)]>;
172 def ADC16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2),
173                      "addc.w\t{$src2, $dst|$dst, $src2}",
174                      [(set GR16:$dst, (adde GR16:$src1, GR16:$src2)),
175                       (implicit SRW)]>;
176 } // isCommutable
177
178 def ADC8ri  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2),
179                      "addc.b\t{$src2, $dst|$dst, $src2}",
180                      [(set GR8:$dst, (adde GR8:$src1, imm:$src2)),
181                       (implicit SRW)]>;
182 def ADC16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2),
183                      "addc.w\t{$src2, $dst|$dst, $src2}",
184                      [(set GR16:$dst, (adde GR16:$src1, imm:$src2)),
185                       (implicit SRW)]>;
186
187 def ADC8rm  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2),
188                      "addc.b\t{$src2, $dst|$dst, $src2}",
189                      [(set GR8:$dst, (adde GR8:$src1, (load addr:$src2))),
190                       (implicit SRW)]>;
191 def ADC16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2),
192                      "addc.w\t{$src2, $dst|$dst, $src2}",
193                      [(set GR16:$dst, (adde GR16:$src1, (load addr:$src2))),
194                       (implicit SRW)]>;
195 }
196
197 let isCommutable = 1 in { // X = AND Y, Z  == X = AND Z, Y
198 def AND8rr  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2),
199                      "and.b\t{$src2, $dst|$dst, $src2}",
200                      [(set GR8:$dst, (and GR8:$src1, GR8:$src2)),
201                       (implicit SRW)]>;
202 def AND16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2),
203                      "and.w\t{$src2, $dst|$dst, $src2}",
204                      [(set GR16:$dst, (and GR16:$src1, GR16:$src2)),
205                       (implicit SRW)]>;
206 }
207
208 def AND8ri  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2),
209                      "and.b\t{$src2, $dst|$dst, $src2}",
210                      [(set GR8:$dst, (and GR8:$src1, imm:$src2)),
211                       (implicit SRW)]>;
212 def AND16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2),
213                      "and.w\t{$src2, $dst|$dst, $src2}",
214                      [(set GR16:$dst, (and GR16:$src1, imm:$src2)),
215                       (implicit SRW)]>;
216
217 def AND8rm  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2),
218                      "and.b\t{$src2, $dst|$dst, $src2}",
219                      [(set GR8:$dst, (and GR8:$src1, (load addr:$src2))),
220                       (implicit SRW)]>;
221 def AND16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2),
222                      "and.w\t{$src2, $dst|$dst, $src2}",
223                      [(set GR16:$dst, (and GR16:$src1, (load addr:$src2))),
224                       (implicit SRW)]>;
225
226 let isCommutable = 1 in { // X = XOR Y, Z  == X = XOR Z, Y
227 def XOR8rr  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2),
228                      "xor.b\t{$src2, $dst|$dst, $src2}",
229                      [(set GR8:$dst, (xor GR8:$src1, GR8:$src2)),
230                       (implicit SRW)]>;
231 def XOR16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2),
232                      "xor.w\t{$src2, $dst|$dst, $src2}",
233                      [(set GR16:$dst, (xor GR16:$src1, GR16:$src2)),
234                       (implicit SRW)]>;
235 }
236
237 def XOR8ri  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2),
238                      "xor.b\t{$src2, $dst|$dst, $src2}",
239                      [(set GR8:$dst, (xor GR8:$src1, imm:$src2)),
240                       (implicit SRW)]>;
241 def XOR16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2),
242                      "xor.w\t{$src2, $dst|$dst, $src2}",
243                      [(set GR16:$dst, (xor GR16:$src1, imm:$src2)),
244                       (implicit SRW)]>;
245
246 def XOR8rm  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2),
247                      "xor.b\t{$src2, $dst|$dst, $src2}",
248                      [(set GR8:$dst, (xor GR8:$src1, (load addr:$src2))),
249                       (implicit SRW)]>;
250 def XOR16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2),
251                      "xor.w\t{$src2, $dst|$dst, $src2}",
252                      [(set GR16:$dst, (xor GR16:$src1, (load addr:$src2))),
253                       (implicit SRW)]>;
254
255 def SUB8rr  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2),
256                      "sub.b\t{$src2, $dst|$dst, $src2}",
257                      [(set GR8:$dst, (sub GR8:$src1, GR8:$src2)),
258                       (implicit SRW)]>;
259 def SUB16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2),
260                      "sub.w\t{$src2, $dst|$dst, $src2}",
261                      [(set GR16:$dst, (sub GR16:$src1, GR16:$src2)),
262                       (implicit SRW)]>;
263
264 def SUB8ri  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2),
265                      "sub.b\t{$src2, $dst|$dst, $src2}",
266                      [(set GR8:$dst, (sub GR8:$src1, imm:$src2)),
267                       (implicit SRW)]>;
268 def SUB16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2),
269                      "sub.w\t{$src2, $dst|$dst, $src2}",
270                      [(set GR16:$dst, (sub GR16:$src1, imm:$src2)),
271                       (implicit SRW)]>;
272
273 def SUB8rm  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2),
274                      "sub.b\t{$src2, $dst|$dst, $src2}",
275                      [(set GR8:$dst, (sub GR8:$src1, (load addr:$src2))),
276                       (implicit SRW)]>;
277 def SUB16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2),
278                      "sub.w\t{$src2, $dst|$dst, $src2}",
279                      [(set GR16:$dst, (sub GR16:$src1, (load addr:$src2))),
280                       (implicit SRW)]>;
281
282 let Uses = [SRW] in {
283 def SBC8rr  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2),
284                      "subc.b\t{$src2, $dst|$dst, $src2}",
285                      [(set GR8:$dst, (sube GR8:$src1, GR8:$src2)),
286                       (implicit SRW)]>;
287 def SBC16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2),
288                      "subc.w\t{$src2, $dst|$dst, $src2}",
289                      [(set GR16:$dst, (sube GR16:$src1, GR16:$src2)),
290                       (implicit SRW)]>;
291
292 def SBC8ri  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2),
293                      "subc.b\t{$src2, $dst|$dst, $src2}",
294                      [(set GR8:$dst, (sube GR8:$src1, imm:$src2)),
295                       (implicit SRW)]>;
296 def SBC16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2),
297                      "subc.w\t{$src2, $dst|$dst, $src2}",
298                      [(set GR16:$dst, (sube GR16:$src1, imm:$src2)),
299                       (implicit SRW)]>;
300
301 def SBC8rm  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2),
302                      "subc.b\t{$src2, $dst|$dst, $src2}",
303                      [(set GR8:$dst, (sube GR8:$src1, (load addr:$src2))),
304                       (implicit SRW)]>;
305 def SBC16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2),
306                      "subc.w\t{$src2, $dst|$dst, $src2}",
307                      [(set GR16:$dst, (sube GR16:$src1, (load addr:$src2))),
308                       (implicit SRW)]>;
309 }
310
311 // FIXME: Provide proper encoding!
312 def SAR16r1 : Pseudo<(outs GR16:$dst), (ins GR16:$src),
313                      "rra.w\t$dst",
314                      [(set GR16:$dst, (MSP430rra GR16:$src)),
315                       (implicit SRW)]>;
316
317 def SEXT16r : Pseudo<(outs GR16:$dst), (ins GR16:$src),
318                      "sxt\t$dst",
319                      [(set GR16:$dst, (sext_inreg GR16:$src, i8)),
320                       (implicit SRW)]>;
321
322 } // Defs = [SRW]
323
324 let isCommutable = 1 in { // X = OR Y, Z  == X = OR Z, Y
325 def OR8rr  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, GR8:$src2),
326                     "bis.b\t{$src2, $dst|$dst, $src2}",
327                     [(set GR8:$dst, (or GR8:$src1, GR8:$src2))]>;
328 def OR16rr : Pseudo<(outs GR16:$dst), (ins GR16:$src1, GR16:$src2),
329                     "bis.w\t{$src2, $dst|$dst, $src2}",
330                     [(set GR16:$dst, (or GR16:$src1, GR16:$src2))]>;
331 }
332
333 def OR8ri  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, i8imm:$src2),
334                     "bis.b\t{$src2, $dst|$dst, $src2}",
335                     [(set GR8:$dst, (or GR8:$src1, imm:$src2))]>;
336 def OR16ri : Pseudo<(outs GR16:$dst), (ins GR16:$src1, i16imm:$src2),
337                     "bis.w\t{$src2, $dst|$dst, $src2}",
338                     [(set GR16:$dst, (or GR16:$src1, imm:$src2))]>;
339
340 def OR8rm  : Pseudo<(outs GR8:$dst), (ins GR8:$src1, memsrc:$src2),
341                     "bis.b\t{$src2, $dst|$dst, $src2}",
342                     [(set GR8:$dst, (or GR8:$src1, (load addr:$src2)))]>;
343 def OR16rm : Pseudo<(outs GR16:$dst), (ins GR16:$src1, memsrc:$src2),
344                     "bis.w\t{$src2, $dst|$dst, $src2}",
345                     [(set GR16:$dst, (or GR16:$src1, (load addr:$src2)))]>;
346 } // isTwoAddress = 1
347
348 //===----------------------------------------------------------------------===//
349 // Non-Instruction Patterns
350
351 // extload
352 def : Pat<(extloadi16i8 addr:$src), (MOVZX16rm8 addr:$src)>;
353
354 // truncs
355 def : Pat<(i8 (trunc GR16:$src)),
356           (EXTRACT_SUBREG GR16:$src, subreg_8bit)>;