• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1//===- ARCInstrFormats.td - ARC Instruction Formats --------*- tablegen -*-===//
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//===----------------------------------------------------------------------===//
11// Instruction format superclass
12//===----------------------------------------------------------------------===//
13
14class Encoding64 {
15  field bits<64> Inst;
16  field bits<64> SoftFail = 0;
17}
18
19// Address operands
20
21class immU<int BSz> : Operand<i32>, PatLeaf<(imm),
22    "\n    return isUInt<"#BSz#">(N->getSExtValue());"> {
23}
24
25def immU6 : immU<6>;
26
27class immS<int BSz> : Operand<i32>, PatLeaf<(imm),
28    "\n    return isInt<"#BSz#">(N->getSExtValue());"> {
29  let DecoderMethod = "DecodeSignedOperand<"#BSz#">";
30}
31
32// e.g. s3 field may encode the signed integers values -1 .. 6
33// using binary codes 111, 000, 001, 010, 011, 100, 101, and 110, respectively
34class immC<int BSz> : Operand<i32>, PatLeaf<(imm),
35    "\n    return isInt<"#BSz#">(N->getSExtValue());"> {
36  let DecoderMethod = "DecodeFromCyclicRange<"#BSz#">";
37}
38
39def MEMii : Operand<i32> {
40  let MIOperandInfo = (ops i32imm, i32imm);
41}
42
43def MEMrs9 : Operand<iAny> {
44  let MIOperandInfo = (ops GPR32:$B, immS<9>:$S9);
45  let PrintMethod = "printMemOperandRI";
46  let DecoderMethod = "DecodeMEMrs9";
47}
48
49def MEMrlimm : Operand<iAny> {
50  let MIOperandInfo = (ops GPR32:$B, i32imm:$LImm);
51  let PrintMethod = "printMemOperandRI";
52  let DecoderMethod = "DecodeMEMrlimm";
53}
54
55def GPR32Reduced : Operand<iAny> {
56  let DecoderMethod = "DecodeGBR32ShortRegister";
57}
58
59class InstARC<int sz, dag outs, dag ins, string asmstr, list<dag> pattern>
60    : Instruction, Encoding64 {
61
62  let Namespace = "ARC";
63  dag OutOperandList = outs;
64  dag InOperandList = ins;
65  let AsmString = asmstr;
66  let Pattern = pattern;
67  let Size = sz;
68}
69
70// ARC pseudo instructions format
71class PseudoInstARC<dag outs, dag ins, string asmstr, list<dag> pattern>
72   : InstARC<0, outs, ins, asmstr, pattern> {
73  let isPseudo = 1;
74}
75
76//===----------------------------------------------------------------------===//
77// Instruction formats
78//===----------------------------------------------------------------------===//
79
80// All 32-bit ARC instructions have a 5-bit "major" opcode class designator
81// in bits 27-31.
82//
83// Some general naming conventions:
84// N  - Delay Slot bit.  ARC v2 branch instructions have an optional delay slot
85//      which is encoded with this bit.  When set, a delay slot exists.
86// cc - Condition code.
87// SX - Signed X-bit immediate.
88// UX - Unsigned X-bit immediate.
89//
90// [ABC] - 32-bit register operand.  These are 6-bit fields.  This encodes the
91//         standard 32 general purpose registers, and allows use of additional
92//         (extension) registers.  This also encodes an instruction that uses
93//         a 32-bit Long Immediate (LImm), using 0x3e==62 as the field value.
94//         This makes 32-bit format instructions with Long Immediates
95//         64-bit instructions, with the Long Immediate in bits 32-63.
96// A - Inst[5-0] = A[5-0], when the format has A.  A is always a register.
97// B - Inst[14-12] = B[5-3], Inst[26-24] = B[2-0], when the format has B.
98//     B is always a register.
99// C - Inst[11-6] = C[5-0], when the format has C.  C can either be a register,
100//     or a 6-bit unsigned immediate (immU6), depending on the format.
101// F - Many instructions specify a flag bit. When set, the result of these
102//     instructions will set the ZNCV flags of the STATUS32 register
103//     (Zero/Negative/Carry/oVerflow).
104
105// Branch Instructions.
106class F32_BR<bits<5> major, dag outs, dag ins, bit b16, string asmstr,
107             list<dag> pattern> :
108  InstARC<4, outs, ins, asmstr, pattern> {
109  bit N;
110
111  let Inst{31-27} = major;
112  let Inst{16} = b16;
113  let Inst{5} = N;
114}
115
116class F32_BR_COND<bits<5> major, dag outs, dag ins, bit b16, string asmstr,
117                  list<dag> pattern> :
118  F32_BR<major, outs, ins, b16, asmstr, pattern> {
119  bits<21> S21; // 2-byte aligned 21-bit byte-offset.
120  bits<5> cc;
121  let Inst{26-18} = S21{10-2};
122  let Inst{15-6} = S21{20-11};
123  let Inst{4-0} = cc;
124}
125
126class F32_BR_UCOND_FAR<bits<5> major, dag outs, dag ins, bit b16, string asmstr,
127                       list<dag> pattern> :
128  F32_BR<major, outs, ins, b16, asmstr, pattern> {
129  bits<25> S25; // 2-byte aligned 25-bit byte-offset.
130  let Inst{26-18} = S25{10-2};
131  let Inst{15-6} = S25{20-11};
132  let Inst{4} = 0;
133  let Inst{3-0} = S25{24-21};
134}
135
136class F32_BR0_COND<dag outs, dag ins, string asmstr, list<dag> pat> :
137  F32_BR_COND<0b00000, outs, ins, 0, asmstr, pat> {
138  let Inst{17} = S21{1};
139}
140
141// Branch targets are 2-byte aligned, so S25[0] is implied 0.
142// |26|25|24|23|22|21|20|19|18|17|16|15|14|13|12|11|10|9|8|7|6|5|4|3|2|1|0   |
143// |S25[10-1]                    | 1|S25[20-11]               |N|0|S25[24-21]|
144class F32_BR0_UCOND_FAR<dag outs, dag ins, string asmstr, list<dag> pat> :
145  F32_BR_UCOND_FAR<0b00000, outs, ins, 1, asmstr, pat> {
146  let Inst{17} = S25{1};
147}
148
149// BL targets (functions) are 4-byte aligned, so S25[1-0] = 0b00
150// |26|25|24|23|22|21|20|19|18|17|16|15|14|13|12|11|10|9|8|7|6|5|4|3|2|1|0   |
151// |S25[10-2]                 | 1| 0|S25[20-11]               |N|0|S25[24-21]|
152class F32_BR1_BL_UCOND_FAR<dag outs, dag ins, string asmstr, list<dag> pat> :
153  F32_BR_UCOND_FAR<0b00001, outs, ins, 0, asmstr, pat> {
154  let Inst{17} = 1;
155}
156
157// BLcc targets have 21 bit range, and are 4-byte aligned.
158// |26|25|24|23|22|21|20|19|18|17|16|15|14|13|12|11|10|9|8|7|6|5|4|3|2|1|0|
159// |S25[10-2]                 | 0| 0|S25[20-11]               |N|0|cc     |
160class F32_BR1_BL_COND<dag outs, dag ins, string asmstr, list<dag> pat> :
161  F32_BR_COND<0b00001, outs, ins, 0, asmstr, pat> {
162  let Inst{17} = 0;
163}
164
165// BRcc targets have limited 9-bit range.  These are for compare and branch
166// in single instruction.  Their targets are 2-byte aligned.  They also use
167// a different (3-bit) set of condition codes.
168// |26|25|24|23|22|21|20|19|18|17|16|15   |14|13|12|11|10|9|8|7|6|5|4|3|2|1|0|
169// |B[2-0]  |S9[7-1]             | 1|S9[8]|B[5-3]  |C            |N|u|0|cc   |
170class F32_BR1_BCC<dag outs, dag ins, string asmstr, bit IsU6,
171                  list<dag> pattern> :
172  InstARC<4, outs, ins, asmstr, pattern> {
173
174  bits<3> cc;
175  bits<6> B;
176  bits<6> C;
177  bit N;
178  bits<9> S9; // 2-byte aligned 9-bit byte-offset.
179
180  let Inst{31-27} = 0b00001;
181  let Inst{26-24} = B{2-0};
182  let Inst{23-17} = S9{7-1};
183  let Inst{16} = 1;
184  let Inst{15} = S9{8};
185  let Inst{14-12} = B{5-3};
186  let Inst{11-6} = C;
187  let Inst{5} = N;
188  let Inst{4} = IsU6;
189  let Inst{3} = 0;
190  let Inst{2-0} = cc;
191}
192
193// General operations instructions.
194// Single Operand Instructions.  Inst[5-0] specifies the specific operation
195// for this format.
196// |26|25|24|23|22|21|20|19|18|17|16|15|14|13|12|11|10|9|8|7|6|5|4|3|2|1|0|
197// |B[2-0]  | 0| 0| 1| 0| 1| 1| 1| 1| F|B[5-3]  |C            |subop      |
198class F32_SOP_RR<bits<5> major, bits<6> subop, bit F, dag outs, dag ins,
199                 string asmstr, list<dag> pattern> :
200  InstARC<4, outs, ins, asmstr, pattern> {
201
202  bits<6> C;
203  bits<6> B;
204
205  let Inst{31-27} = major;
206  let Inst{26-24} = B{2-0};
207  let Inst{23-22} = 0b00;
208  let Inst{21-16} = 0b101111;
209  let Inst{15} = F;
210  let Inst{14-12} = B{5-3};
211  let Inst{11-6} = C;
212  let Inst{5-0} = subop;
213}
214
215// Dual Operand Instructions.  Inst[21-16] specifies the specific operation
216// for this format.
217
218// 3-register Dual Operand instruction.
219// |26|25|24|23|22|21|20|19|18|17|16|15|14|13|12|11|10|9|8|7|6|5|4|3|2|1|0|
220// |B[2-0]  | 0| 0|            subop| F|B[5-3]  |C            |A          |
221class F32_DOP_RR<bits<5> major, bits<6> subop, bit F, dag outs, dag ins,
222                 string asmstr, list<dag> pattern> :
223  InstARC<4, outs, ins, asmstr, pattern> {
224  bits<6> C;
225  bits<6> B;
226  bits<6> A;
227
228  let Inst{31-27} = major;
229  let Inst{26-24} = B{2-0};
230  let Inst{23-22} = 0b00;
231  let Inst{21-16} = subop;
232  let Inst{15} = F;
233  let Inst{14-12} = B{5-3};
234  let Inst{11-6} = C;
235  let Inst{5-0} = A;
236}
237
238// Conditional Dual Operand instruction.  This instruction uses B as the
239// first 2 operands (i.e, add.cc B, B, C).
240// |26|25|24|23|22|21|20|19|18|17|16|15|14|13|12|11|10|9|8|7|6|5|4|3|2|1|0|
241// |B[2-0]  | 1| 1|            subop| F|B[5-3]  |C            |A          |
242class F32_DOP_CC_RR<bits<5> major, bits<6> subop, bit F, dag outs, dag ins,
243                    string asmstr, list<dag> pattern> :
244  InstARC<4, outs, ins, asmstr, pattern> {
245  bits<5> cc;
246  bits<6> C;
247  bits<6> B;
248
249  let Inst{31-27} = major;
250  let Inst{26-24} = B{2-0};
251  let Inst{23-22} = 0b11;
252  let Inst{21-16} = subop;
253  let Inst{15} = F;
254  let Inst{14-12} = B{5-3};
255  let Inst{11-6} = C;
256  let Inst{5} = 0;
257  let Inst{4-0} = cc;
258}
259
260
261// 2-register, unsigned 6-bit immediate Dual Operand instruction.
262// |26|25|24|23|22|21|20|19|18|17|16|15|14|13|12|11|10|9|8|7|6|5|4|3|2|1|0|
263// |B[2-0]  | 0| 1|            subop| F|B[5-3]  |U6           |A          |
264class F32_DOP_RU6<bits<5> major, bits<6> subop, bit F, dag outs, dag ins,
265                  string asmstr, list<dag> pattern> :
266  InstARC<4, outs, ins, asmstr, pattern> {
267  bits<6> U6;
268  bits<6> B;
269  bits<6> A;
270
271  let Inst{31-27} = major;
272  let Inst{26-24} = B{2-0};
273  let Inst{23-22} = 0b01;
274  let Inst{21-16} = subop;
275  let Inst{15} = F;
276  let Inst{14-12} = B{5-3};
277  let Inst{11-6} = U6;
278  let Inst{5-0} = A;
279}
280
281// 2-register, signed 12-bit immediate Dual Operand instruction.
282// This instruction uses B as the first 2 operands (i.e., add B, B, -128).
283// |26|25|24|23|22|21|20|19|18|17|16|15|14|13|12|11|10|9|8|7|6|5|4|3|2|1|0|
284// |B[2-0]  | 1| 0|            subop| F|B[5-3]  |S12[5-0]     |S12[11-6]  |
285class F32_DOP_RS12<bits<5> major, bits<6> subop, bit F, dag outs, dag ins,
286                   string asmstr, list<dag> pattern> :
287  InstARC<4, outs, ins, asmstr, pattern> {
288  bits<6> B;
289  bits<12> S12;
290
291  let Inst{31-27} = major;
292  let Inst{26-24} = B{2-0};
293  let Inst{23-22} = 0b10;
294  let Inst{21-16} = subop;
295  let Inst{15} = F;
296  let Inst{14-12} = B{5-3};
297  let Inst{11-6} = S12{5-0};
298  let Inst{5-0} = S12{11-6};
299}
300
301// 2-register, 32-bit immediate (LImm) Dual Operand instruction.
302// This instruction has the 32-bit immediate in bits 32-63, and
303// 62 in the C register operand slot, but is otherwise F32_DOP_RR.
304class F32_DOP_RLIMM<bits<5> major, bits<6> subop, bit F, dag outs, dag ins,
305                    string asmstr, list<dag> pattern> :
306  InstARC<8, outs, ins, asmstr, pattern> {
307  bits<6> B;
308  bits<6> A;
309  bits<32> LImm;
310
311  let Inst{63-32} = LImm;
312  let Inst{31-27} = major;
313  let Inst{26-24} = B{2-0};
314  let Inst{23-22} = 0b00;
315  let Inst{21-16} = subop;
316  let Inst{15} = F;
317  let Inst{14-12} = B{5-3};
318  let Inst{11-6} = 0b111110;
319  let Inst{5-0} = A;
320}
321
322
323// Load and store instructions.
324// In addition to the previous naming conventions, load and store instructions
325// have:
326// di - Uncached bit.  When set, loads/stores bypass the cache and access
327//      memory directly.
328// aa - Incrementing mode.  Loads and stores can write-back address pre- or
329//      post- memory operation.
330// zz - Memory size (can be 8/16/32 bit load/store).
331//  x - Sign-extending.  When set, short loads can be sign-extended to 32-bits.
332// Loads and Stores support different memory addressing modes:
333// Base Register + Signed 9-bit Immediate: Both Load/Store.
334// LImm: Both Load/Store (Load/Store from a fixed 32-bit address).
335// Register + Register: Load Only.
336// Register + LImm: Load Only.
337
338// Register + S9 Load. (B + S9)
339// |26|25|24|23|22|21|20|19|18|17|16|15   |14|13|12|11|10|9|8|7|6|5|4|3|2|1|0|
340// |B[2-0]  |S9[7-0]                |S9[8]|B[5-3]  |di|aa  |zz |x|A          |
341class F32_LD_RS9<bit x, bits<2> aa, bit di, bits<2> zz, dag outs, dag ins,
342                 string asmstr, list<dag> pattern> :
343  InstARC<4, outs, ins, asmstr, pattern> {
344  bits<6> B;
345  bits<6> A;
346  bits<9> S9;
347
348  let Inst{31-27} = 0b00010;
349  let Inst{26-24} = B{2-0};
350  let Inst{23-16} = S9{7-0};
351  let Inst{15} = S9{8};
352  let Inst{14-12} = B{5-3};
353  let Inst{11} = di;
354  let Inst{10-9} = aa;
355  let Inst{8-7} = zz;
356  let Inst{6} = x;
357  let Inst{5-0} = A;
358}
359
360class F32_LD_ADDR<bit x, bits<2> aa, bit di, bits<2> zz, dag outs, dag ins,
361                  string asmstr, list<dag> pattern> :
362  F32_LD_RS9<x, aa, di, zz, outs, ins, asmstr, pattern> {
363  bits<15> addr;
364
365  let B = addr{14-9};
366  let S9 = addr{8-0};
367}
368
369
370// LImm Load.  The 32-bit immediate address is in Inst[63-32].
371// |26|25|24|23|22|21|20|19|18|17|16|15|14|13|12|11|10|9|8|7|6|5|4|3|2|1|0|
372// | 1| 1| 0| 0                        | 1| 1| 1|di| 0|0|zz |x|A          |
373class F32_LD_LIMM<bit x, bit di, bits<2> zz, dag outs, dag ins,
374                  string asmstr, list<dag> pattern> :
375  InstARC<8, outs, ins, asmstr, pattern> {
376  bits<6> LImmReg = 0b111110;
377  bits<6> A;
378  bits<32> LImm;
379
380  let Inst{63-32} = LImm;
381  let Inst{31-27} = 0b00010;
382  let Inst{26-24} = LImmReg{2-0};
383  let Inst{23-15} = 0;
384  let Inst{14-12} = LImmReg{5-3};
385  let Inst{11} = di;
386  let Inst{10-9} = 0;
387  let Inst{8-7} = zz;
388  let Inst{6} = x;
389  let Inst{5-0} = A;
390  let DecoderMethod = "DecodeLdLImmInstruction";
391}
392
393// Register + LImm load.  The 32-bit immediate address is in Inst[63-32].
394// |26|25|24|23|22|21|20|19|18|17|16|15|14|13|12|11|10|9|8|7|6|5|4|3|2|1|0|
395// |B[2-0]  |aa   | 1| 1| 0|zz   | x|di|B[5-3]  | 1| 1|1|1|1|0|A          |
396class F32_LD_RLIMM<bit x, bits<2> aa, bit di, bits<2> zz, dag outs, dag ins,
397                   string asmstr, list<dag> pattern> :
398  InstARC<8, outs, ins, asmstr, pattern> {
399  bits<6> LImmReg = 0b111110;
400  bits<32> LImm;
401  bits<6> B;
402  bits<6> A;
403  bits<38> addr;
404  let B = addr{37-32};
405  let LImm = addr{31-0};
406
407  let Inst{63-32} = LImm;
408  let Inst{31-27} = 0b00100;
409  let Inst{26-24} = B{2-0};
410  let Inst{23-22} = aa;
411  let Inst{21-19} = 0b110;
412  let Inst{18-17} = zz;
413  let Inst{16} = x;
414  let Inst{15} = di;
415  let Inst{14-12} = B{5-3};
416  let Inst{11-6} = LImmReg;
417  let Inst{5-0} = A;
418  let DecoderMethod = "DecodeLdRLImmInstruction";
419}
420
421// Register + S9 Store. (B + S9)
422// |26|25|24|23|22|21|20|19|18|17|16|15   |14|13|12|11|10|9|8|7|6|5 |4|3|2|1|0|
423// |B[2-0]  |S9[7-0]                |S9[8]|B[5-3]  |C            |di|aa |zz |0|
424class F32_ST_RS9<bits<2> aa, bit di, bits<2> zz, dag outs, dag ins,
425                 string asmstr, list<dag> pattern> :
426  InstARC<4, outs, ins, asmstr, pattern> {
427  bits<6> B;
428  bits<6> C;
429  bits<9> S9;
430
431  let Inst{31-27} = 0b00011;
432  let Inst{26-24} = B{2-0};
433  let Inst{23-16} = S9{7-0};
434  let Inst{15} = S9{8};
435  let Inst{14-12} = B{5-3};
436  let Inst{11-6} = C;
437  let Inst{5} = di;
438  let Inst{4-3} = aa;
439  let Inst{2-1} = zz;
440  let Inst{0} = 0;
441}
442
443class F32_ST_ADDR<bits<2> aa, bit di, bits<2> zz, dag outs, dag ins,
444                  string asmstr, list<dag> pattern> :
445  F32_ST_RS9<aa, di, zz, outs, ins, asmstr, pattern> {
446  bits<15> addr;
447
448  let B = addr{14-9};
449  let S9 = addr{8-0};
450}
451
452// LImm Store.
453// |26|25|24|23|22|21|20|19|18|17|16|15|14|13|12|11|10|9|8|7|6|5 |4|3|2|1|0|
454// | 1| 1| 0| 0                        | 1| 1| 1|C            |di|0|0|zz |0|
455class F32_ST_LIMM<bit di, bits<2> zz, dag outs, dag ins,
456                  string asmstr, list<dag> pattern> :
457  InstARC<8, outs, ins, asmstr, pattern> {
458  bits<6> LImmReg = 0b111110;
459  bits<6> C;
460  bits<32> LImm;
461
462  let Inst{63-32} = LImm;
463  let Inst{31-27} = 0b00011;
464  let Inst{26-24} = LImmReg{2-0};
465  let Inst{23-15} = 0;
466  let Inst{14-12} = LImmReg{5-3};
467  let Inst{11-6} = C;
468  let Inst{5} = di;
469  let Inst{4-3} = 0;
470  let Inst{2-1} = zz;
471  let Inst{0} = 0;
472  let DecoderMethod = "DecodeStLImmInstruction";
473}
474
475// Compact Move/Load.
476// |10|9|8|7|6|5|4|3|2|1|0|
477// |      |h    |   |i|H  |
478class F16_COMPACT<bits<1> i, dag outs, dag ins,
479                 string asmstr> :
480  InstARC<2, outs, ins, asmstr, []> {
481
482  bits<5> h;
483
484  let Inst{15-11} = 0b01000;
485  let Inst{7-5} = h{2-0};
486  let Inst{2} = i;
487  let Inst{1-0} = h{4-3};
488}
489
490// Compact Load/Add/Sub.
491class F16_LD_ADD_SUB<dag outs, dag ins, string asmstr> :
492  InstARC<2, outs, ins, asmstr, []> {
493
494  bits<3> b;
495  let Inst{15-11} = 0b01001;
496  let Inst{10-8} = b;
497}
498
499class F16_LD_SUB<bit i, string asmstr> :
500  F16_LD_ADD_SUB<(outs GPR32:$a), (ins GPR32:$b, GPR32:$c),
501  asmstr> {
502
503  bits<3> a;
504  bits<3> c;
505
506  let Inst{7-5} = c;
507  let Inst{4} = i;
508  let Inst{3} = 0;
509  let Inst{2-0} = a;
510}
511
512class F16_ADD :
513  F16_LD_ADD_SUB<(outs GPR32:$r), (ins GPR32:$b, immU<6>:$u6),
514  "add_s\t$r, $b, $u6"> {
515
516  bit r;
517  bits<6> u6;
518
519  let Inst{7} = r;
520  let Inst{6-4} = u6{5-3};
521  let Inst{3} = 1;
522  let Inst{2-0} = u6{2-0};
523}
524
525// Compact Load/Store.
526class F16_LD_ST_1<dag outs, dag ins, string asmstr> :
527  InstARC<2, outs, ins, asmstr, []> {
528
529  let Inst{15-11} = 0b01010;
530}
531
532class F16_LD_ST_s11<bit i, string asmstr> :
533  F16_LD_ST_1<(outs), (ins immS<11>:$s11), asmstr> {
534
535  bits<11> s11;
536
537  let Inst{10-5} = s11{10-5};
538  let Inst{4} = i;
539  let Inst{3} = 0;
540  let Inst{2-0} = s11{4-2};
541  let s11{1-0} = 0b00;
542}
543
544class F16_LDI_u7 :
545  F16_LD_ST_1<(outs GPR32:$b), (ins immU<7>:$u7),
546  "ldi_s\t$b, [$u7]"> {
547
548  bits<3> b;
549  bits<7> u7;
550
551  let Inst{10-8} = b;
552  let Inst{7-4} = u7{6-3};
553  let Inst{3} = 1;
554  let Inst{2-0} = u7{2-0};
555}
556
557// Indexed Jump or Execute.
558class F16_JLI_EI<bit i, string asmstr> :
559  InstARC<2, (outs), (ins immU<10>:$u10),
560  !strconcat(asmstr, "\t$u10"), []> {
561
562  bits<10> u10;
563
564  let Inst{15-11} = 0b01011;
565  let Inst{10} = i;
566  let Inst{9-0} = u10;
567}
568
569// Load/Add Register-Register.
570class F16_LD_ADD_RR<bits<2> i, string asmstr> :
571  InstARC<2, (outs GPR32:$a), (ins GPR32:$b, GPR32:$c),
572  asmstr, []> {
573
574  bits<3> a;
575  bits<3> b;
576  bits<3> c;
577
578  let Inst{15-11} = 0b01100;
579  let Inst{10-8} = b;
580  let Inst{7-5} = c;
581  let Inst{4-3} = i;
582  let Inst{2-0} = a;
583}
584
585// Load/Add GP-Relative.
586class F16_GP_LD_ADD<bits<2> i, dag ins, string asmstr> :
587  InstARC<2, (outs), ins, asmstr, []> {
588
589  let Inst{15-11} = 0b11001;
590  let Inst{10-9} = i;
591}
592
593// Add/Sub/Shift Register-Immediate.
594// |10|9|8|7|6|5|4|3|2|1|0|
595// |b     |c    |i  |u    |
596class F16_ADD_IMM<bits<2> i, string asmstr> :
597  InstARC<2, (outs GPR32:$c), (ins GPR32:$b, immU<3>:$u3),
598  !strconcat(asmstr, "\t$c, $b, $u3"), []> {
599
600  bits<3> b;
601  bits<3> c;
602  bits<3> u3;
603
604  let Inst{15-11} = 0b01101;
605  let Inst{10-8} = b;
606  let Inst{7-5} = c;
607  let Inst{4-3} = i;
608  let Inst{2-0} = u3;
609}
610
611// Dual Register Operations.
612// |10|9|8|7|6|5|4|3|2|1|0|
613// |b/s   |h    |i    |H  |
614class F16_OP_HREG<bits<3> i, dag outs, dag ins, string asmstr> :
615  InstARC<2, outs, ins, asmstr, []> {
616
617  bits<3> b_s3;
618  bits<5> h;
619
620  let Inst{15-11} = 0b01110;
621  let Inst{10-8} = b_s3;
622  let Inst{7-5} = h{2-0};
623  let Inst{4-2} = i;
624  let Inst{1-0} = h{4-3};
625}
626
627class F16_OP_HREG30<bits<3> i, dag outs, dag ins, string asmstr> :
628  F16_OP_HREG<i, outs, ins, asmstr> {
629
630  bits<5> LImmReg = 0b11110;
631  let Inst{7-5} = LImmReg{2-0};
632  let Inst{1-0} = LImmReg{4-3};
633}
634
635class F16_OP_HREG_LIMM<bits<3> i, dag outs, dag ins, string asmstr> :
636  F16_OP_HREG30<i, outs, ins, asmstr> {
637
638  bits<32> LImm;
639  let Inst{47-16} = LImm;
640  let Size = 6;
641}
642
643// General compact DOP format.
644class F16_GEN_DOP_BASE<bits<5> i, dag outs, dag ins, string asmstr> :
645  InstARC<2, outs, ins, asmstr, []> {
646
647  bits<3> b;
648  bits<3> c;
649  let Inst{15-11} = 0b01111;
650  let Inst{10-8} = b;
651  let Inst{7-5} = c;
652  let Inst{4-0} = i;
653}
654
655class F16_GEN_DOP<bits<5> i, string asmstr> :
656  F16_GEN_DOP_BASE<i, (outs GPR32:$b), (ins GPR32:$c),
657  !strconcat(asmstr, "\t$b, $b, $c")>;
658
659class F16_GEN_DOP_NODST<bits<5> i, string asmstr> :
660  F16_GEN_DOP_BASE<i, (outs), (ins GPR32:$b, GPR32:$c),
661  !strconcat(asmstr, "\t$b, $c")>;
662
663class F16_GEN_DOP_SINGLESRC<bits<5> i, string asmstr> :
664  F16_GEN_DOP_BASE<i, (outs GPR32:$b), (ins GPR32:$c),
665  !strconcat(asmstr, "\t$b, $c")>;
666
667class F16_GEN_SOP_BASE<bits<3> i, dag outs, dag ins, string asmstr> :
668  F16_GEN_DOP_BASE<0b00000, outs, ins, asmstr> {
669
670  let c = i;
671}
672
673class F16_GEN_SOP<bits<3> i, string asmstr> :
674  F16_GEN_SOP_BASE<i, (outs), (ins GPR32:$b), asmstr>;
675
676class F16_GEN_ZOP<bits<3> i, string asmstr> :
677  F16_GEN_SOP_BASE<0b111, (outs), (ins), asmstr> {
678
679  let b = i;
680}
681
682// Compact Load/Store with Offset Format.
683class F16_LD_ST_OFF<bits<5> opc, dag outs, dag ins, string asmstr> :
684  InstARC<2, outs, ins, !strconcat(asmstr, "\t$c, [$b, $off]"), []> {
685
686  bits<3> b;
687  bits<3> c;
688  let Inst{15-11} = opc;
689  let Inst{10-8} = b;
690  let Inst{7-5} = c;
691}
692
693class F16_LD_ST_WORD_OFF<bits<5> opc, dag outs, dag ins, string asmstr> :
694  F16_LD_ST_OFF<opc, outs, ins, asmstr> {
695
696  bits<7> off;
697  let Inst{4-0} = off{6-2};
698  let off{1-0} = 0b00;
699}
700
701class F16_LD_ST_HALF_OFF<bits<5> opc, dag outs, dag ins, string asmstr> :
702  F16_LD_ST_OFF<opc, outs, ins, asmstr> {
703
704  bits<6> off;
705  let Inst{4-0} = off{5-1};
706  let off{0} = 0b0;
707}
708
709class F16_LD_ST_BYTE_OFF<bits<5> opc, dag outs, dag ins, string asmstr> :
710  F16_LD_ST_OFF<opc, outs, ins, asmstr> {
711
712  bits<5> off;
713  let Inst{4-0} = off;
714}
715
716// Shift/Subtract/Bit Immediate.
717// |10|9|8|7|6|5|4|3|2|1|0|
718// |b     |i    |u        |
719class F16_SH_SUB_BIT<bits<3> i, string asmstr> :
720  InstARC<2, (outs), (ins GPR32:$b, immU<5>:$u5), asmstr, []> {
721
722  bits<3> b;
723  bits<5> u5;
724
725  let Inst{15-11} = 0b10111;
726  let Inst{10-8} = b;
727  let Inst{7-5} = i;
728  let Inst{4-0} = u5;
729}
730
731class F16_SH_SUB_BIT_DST<bits<3> i, string asmstr> :
732  F16_SH_SUB_BIT<i, !strconcat(asmstr, "\t$b, $b, $u5")>;
733
734// 16-bit stack-based operations.
735// |10|9|8|7|6|5|4|3|2|1|0|
736// |b     |i    |u        |
737class F16_SP_OPS<bits<3> i,
738  dag outs, dag ins, string asmstr> :
739  InstARC<2, outs, ins, asmstr, []> {
740
741  bits<3> fieldB;
742  bits<5> fieldU;
743
744  let Inst{15-11} = 0b11000;
745  let Inst{10-8} = fieldB;
746  let Inst{7-5} = i;
747  let Inst{4-0} = fieldU;
748}
749
750class F16_SP_OPS_u7_aligned<bits<3> i,
751  dag outs, dag ins, string asmstr> :
752  F16_SP_OPS<i, outs, ins, asmstr> {
753
754  bits<3> b3;
755  bits<7> u7;
756
757  let fieldB = b3;
758  let fieldU = u7{6-2};
759  let u7{1-0} = 0b00;
760}
761
762class F16_SP_OPS_bconst<bits<3> b, string asmop> :
763  F16_SP_OPS_u7_aligned<0b101,
764  (outs), (ins immU<7>:$u7),
765  !strconcat(asmop, "\t%sp, %sp, $u7")> {
766
767  let fieldB = b;
768}
769
770class F16_SP_OPS_uconst<bits<3> i,
771  dag outs, dag ins, string asmop> :
772  F16_SP_OPS_u7_aligned<i, outs, ins,
773  !strconcat(asmop, "\t$b3")> {
774
775  let fieldU = 0b00001;
776}
777
778class F16_SP_OPS_buconst<bits<3> i, string asmop> :
779  F16_SP_OPS_u7_aligned<i, (outs), (ins),
780    !strconcat(asmop, "\t%blink")> {
781
782  let fieldB = 0x000;
783  let fieldU = 0b10001;
784}
785
786class F16_SP_LD<bits<3> i, string asmop> : F16_SP_OPS_u7_aligned<i,
787                         (outs GPR32Reduced:$b3), (ins immU<7>:$u7),
788                         !strconcat(asmop, "\t$b3, [%sp, $u7]")>;
789
790class F16_SP_ST<bits<3> i, string asmop> : F16_SP_OPS_u7_aligned<i,
791                         (outs), (ins GPR32Reduced:$b3, immU<7>:$u7),
792                         !strconcat(asmop, "\t$b3, [%sp, $u7]")>;
793
794// Compact MOV/ADD/CMP Immediate Format.
795class F16_OP_IMM<bits<5> opc, dag outs, dag ins, string asmstr> :
796  InstARC<2, outs, ins, asmstr, []> {
797
798  bits<3> b;
799  let Inst{15-11} = opc;
800  let Inst{10-8} = b;
801}
802
803class F16_OP_U7<bit i, string asmstr> :
804  F16_OP_IMM<0b11100, (outs GPR32:$b), (ins immU<7>:$u7), asmstr> {
805
806  bits<7> u7;
807  let Inst{7} = i;
808  let Inst{6-0} = u7;
809}
810
811// Special types for different instruction operands.
812def cmovpred : Operand<i32>, PredicateOp,
813               ComplexPattern<i32, 2, "SelectCMOVPred"> {
814  let MIOperandInfo = (ops i32imm, i32imm);
815  let PrintMethod = "printPredicateOperand";
816}
817
818def ccond : Operand<i32> {
819  let MIOperandInfo = (ops i32imm);
820  let PrintMethod = "printPredicateOperand";
821}
822
823def brccond : Operand<i32> {
824  let MIOperandInfo = (ops i32imm);
825  let PrintMethod = "printBRCCPredicateOperand";
826}
827
828// Branch/call targets of different offset sizes.
829class BCTarget<ValueType vt> : Operand<vt> {
830  let OperandType = "OPERAND_PCREL";
831}
832
833def btarget : BCTarget<OtherVT>;
834
835class BCTargetSigned<ValueType vt, int BSz> : BCTarget<vt> {
836  let DecoderMethod = "DecodeBranchTargetS<"#BSz#">";
837}
838
839class BranchTargetS<int BSz> : BCTargetSigned<OtherVT, BSz>;
840def btargetS7 : BranchTargetS<7>;
841def btargetS8 : BranchTargetS<8>;
842def btargetS9 : BranchTargetS<9>;
843def btargetS10 : BranchTargetS<10>;
844def btargetS13 : BranchTargetS<13>;
845def btargetS21 : BranchTargetS<21>;
846def btargetS25 : BranchTargetS<25>;
847
848class CallTargetS<int BSz> : BCTargetSigned<i32, BSz>;
849def calltargetS25: CallTargetS<25>;
850
851// Compact Branch on Compare Register with Zero.
852class F16_BCC_REG<bit i, string asmstr> :
853  InstARC<2, (outs), (ins GPR32:$b, btargetS8:$s8),
854  !strconcat(asmstr, "\t$b, 0, $s8"), []> {
855
856  bits<3> b;
857  bits<8> s8;
858
859  let Inst{15-11} = 0b11101;
860  let Inst{10-8} = b;
861  let Inst{7} = i;
862  let Inst{6-0} = s8{7-1};
863  let s8{0} = 0b0;
864}
865
866// Compact Branch Conditionally Format.
867class F16_BCC<bits<2> i, dag ins, string asmstr> :
868  InstARC<2, (outs), ins, asmstr, []> {
869
870  let Inst{15-11} = 0b11110;
871  let Inst{10-9} = i;
872}
873
874class F16_BCC_s10<bits<2> i, string asmstr> :
875  F16_BCC<i, (ins btargetS10:$s),
876  !strconcat(asmstr, "\t$s")> {
877
878  bits<10> s;
879  let Inst{8-0} = s{9-1};
880  let s{0} = 0b0;
881}
882
883class F16_BCC_s7<bits<3> i, string asmstr> :
884  F16_BCC<0b11, (ins btargetS7:$s),
885  !strconcat(asmstr, "\t$s")> {
886
887  bits<7> s;
888  let Inst{8-6} = i;
889  let Inst{5-0} = s{6-1};
890  let s{0} = 0b0;
891}
892