SystemZInstrFormats.td revision ccdf5cc7bc443726425dd1ad498d44768332d49c
1//==- SystemZInstrFormats.td - SystemZ 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// Basic SystemZ instruction definition
12//===----------------------------------------------------------------------===//
13
14class InstSystemZ<int size, dag outs, dag ins, string asmstr,
15                  list<dag> pattern> : Instruction {
16  let Namespace = "SystemZ";
17
18  dag OutOperandList = outs;
19  dag InOperandList = ins;
20  let Size = size;
21  let Pattern = pattern;
22  let AsmString = asmstr;
23
24  // Some instructions come in pairs, one having a 12-bit displacement
25  // and the other having a 20-bit displacement.  Both instructions in
26  // the pair have the same DispKey and their DispSizes are "12" and "20"
27  // respectively.
28  string DispKey = "";
29  string DispSize = "none";
30
31  // Many register-based <INSN>R instructions have a memory-based <INSN>
32  // counterpart.  OpKey uniquely identifies <INSN>, while OpType is
33  // "reg" for <INSN>R and "mem" for <INSN>.
34  string OpKey = "";
35  string OpType = "none";
36
37  // Many distinct-operands instructions have older 2-operand equivalents.
38  // NumOpsKey uniquely identifies one of these 2-operand and 3-operand pairs,
39  // with NumOpsValue being "2" or "3" as appropriate.
40  string NumOpsKey = "";
41  string NumOpsValue = "none";
42
43  // True if this instruction is a simple D(X,B) load of a register
44  // (with no sign or zero extension).
45  bit SimpleBDXLoad = 0;
46
47  // True if this instruction is a simple D(X,B) store of a register
48  // (with no truncation).
49  bit SimpleBDXStore = 0;
50
51  // True if this instruction has a 20-bit displacement field.
52  bit Has20BitOffset = 0;
53
54  // True if addresses in this instruction have an index register.
55  bit HasIndex = 0;
56
57  // True if this is a 128-bit pseudo instruction that combines two 64-bit
58  // operations.
59  bit Is128Bit = 0;
60
61  // The access size of all memory operands in bytes, or 0 if not known.
62  bits<5> AccessBytes = 0;
63
64  // If the instruction sets CC to a useful value, this gives the mask
65  // of all possible CC results.  The mask has the same form as
66  // SystemZ::CCMASK_*.
67  bits<4> CCValues = 0;
68
69  // True if the instruction sets CC to 0 when the result is 0.
70  bit CCHasZero = 0;
71
72  // True if the instruction sets CC to 1 when the result is less than 0
73  // and to 2 when the result is greater than 0.
74  bit CCHasOrder = 0;
75
76  // True if the instruction is conditional and if the CC mask operand
77  // comes first (as for BRC, etc.).
78  bit CCMaskFirst = 0;
79
80  // Similar, but true if the CC mask operand comes last (as for LOC, etc.).
81  bit CCMaskLast = 0;
82
83  // True if the instruction is the "logical" rather than "arithmetic" form,
84  // in cases where a distinction exists.
85  bit IsLogical = 0;
86
87  let TSFlags{0}     = SimpleBDXLoad;
88  let TSFlags{1}     = SimpleBDXStore;
89  let TSFlags{2}     = Has20BitOffset;
90  let TSFlags{3}     = HasIndex;
91  let TSFlags{4}     = Is128Bit;
92  let TSFlags{9-5}   = AccessBytes;
93  let TSFlags{13-10} = CCValues;
94  let TSFlags{14}    = CCHasZero;
95  let TSFlags{15}    = CCHasOrder;
96  let TSFlags{16}    = CCMaskFirst;
97  let TSFlags{17}    = CCMaskLast;
98  let TSFlags{18}    = IsLogical;
99}
100
101//===----------------------------------------------------------------------===//
102// Mappings between instructions
103//===----------------------------------------------------------------------===//
104
105// Return the version of an instruction that has an unsigned 12-bit
106// displacement.
107def getDisp12Opcode : InstrMapping {
108  let FilterClass = "InstSystemZ";
109  let RowFields = ["DispKey"];
110  let ColFields = ["DispSize"];
111  let KeyCol = ["20"];
112  let ValueCols = [["12"]];
113}
114
115// Return the version of an instruction that has a signed 20-bit displacement.
116def getDisp20Opcode : InstrMapping {
117  let FilterClass = "InstSystemZ";
118  let RowFields = ["DispKey"];
119  let ColFields = ["DispSize"];
120  let KeyCol = ["12"];
121  let ValueCols = [["20"]];
122}
123
124// Return the memory form of a register instruction.
125def getMemOpcode : InstrMapping {
126  let FilterClass = "InstSystemZ";
127  let RowFields = ["OpKey"];
128  let ColFields = ["OpType"];
129  let KeyCol = ["reg"];
130  let ValueCols = [["mem"]];
131}
132
133// Return the 3-operand form of a 2-operand instruction.
134def getThreeOperandOpcode : InstrMapping {
135  let FilterClass = "InstSystemZ";
136  let RowFields = ["NumOpsKey"];
137  let ColFields = ["NumOpsValue"];
138  let KeyCol = ["2"];
139  let ValueCols = [["3"]];
140}
141
142//===----------------------------------------------------------------------===//
143// Instruction formats
144//===----------------------------------------------------------------------===//
145//
146// Formats are specified using operand field declarations of the form:
147//
148//   bits<4> Rn   : register input or output for operand n
149//   bits<m> In   : immediate value of width m for operand n
150//   bits<4> BDn  : address operand n, which has a base and a displacement
151//   bits<m> XBDn : address operand n, which has an index, a base and a
152//                  displacement
153//   bits<4> Xn   : index register for address operand n
154//   bits<4> Mn   : mode value for operand n
155//
156// The operand numbers ("n" in the list above) follow the architecture manual.
157// Assembly operands sometimes have a different order; in particular, R3 often
158// is often written between operands 1 and 2.
159//
160//===----------------------------------------------------------------------===//
161
162class InstRI<bits<12> op, dag outs, dag ins, string asmstr, list<dag> pattern>
163  : InstSystemZ<4, outs, ins, asmstr, pattern> {
164  field bits<32> Inst;
165  field bits<32> SoftFail = 0;
166
167  bits<4> R1;
168  bits<16> I2;
169
170  let Inst{31-24} = op{11-4};
171  let Inst{23-20} = R1;
172  let Inst{19-16} = op{3-0};
173  let Inst{15-0}  = I2;
174}
175
176class InstRIEb<bits<16> op, dag outs, dag ins, string asmstr, list<dag> pattern>
177  : InstSystemZ<6, outs, ins, asmstr, pattern> {
178  field bits<48> Inst;
179  field bits<48> SoftFail = 0;
180
181  bits<4> R1;
182  bits<4> R2;
183  bits<4> M3;
184  bits<16> RI4;
185
186  let Inst{47-40} = op{15-8};
187  let Inst{39-36} = R1;
188  let Inst{35-32} = R2;
189  let Inst{31-16} = RI4;
190  let Inst{15-12} = M3;
191  let Inst{11-8}  = 0;
192  let Inst{7-0}   = op{7-0};
193}
194
195class InstRIEc<bits<16> op, dag outs, dag ins, string asmstr, list<dag> pattern>
196  : InstSystemZ<6, outs, ins, asmstr, pattern> {
197  field bits<48> Inst;
198  field bits<48> SoftFail = 0;
199
200  bits<4> R1;
201  bits<8> I2;
202  bits<4> M3;
203  bits<16> RI4;
204
205  let Inst{47-40} = op{15-8};
206  let Inst{39-36} = R1;
207  let Inst{35-32} = M3;
208  let Inst{31-16} = RI4;
209  let Inst{15-8}  = I2;
210  let Inst{7-0}   = op{7-0};
211}
212
213class InstRIEd<bits<16> op, dag outs, dag ins, string asmstr, list<dag> pattern>
214  : InstSystemZ<6, outs, ins, asmstr, pattern> {
215  field bits<48> Inst;
216  field bits<48> SoftFail = 0;
217
218  bits<4> R1;
219  bits<4> R3;
220  bits<16> I2;
221
222  let Inst{47-40} = op{15-8};
223  let Inst{39-36} = R1;
224  let Inst{35-32} = R3;
225  let Inst{31-16} = I2;
226  let Inst{15-8}  = 0;
227  let Inst{7-0}   = op{7-0};
228}
229
230class InstRIEf<bits<16> op, dag outs, dag ins, string asmstr, list<dag> pattern>
231  : InstSystemZ<6, outs, ins, asmstr, pattern> {
232  field bits<48> Inst;
233  field bits<48> SoftFail = 0;
234
235  bits<4> R1;
236  bits<4> R2;
237  bits<8> I3;
238  bits<8> I4;
239  bits<8> I5;
240
241  let Inst{47-40} = op{15-8};
242  let Inst{39-36} = R1;
243  let Inst{35-32} = R2;
244  let Inst{31-24} = I3;
245  let Inst{23-16} = I4;
246  let Inst{15-8}  = I5;
247  let Inst{7-0}   = op{7-0};
248}
249
250class InstRIL<bits<12> op, dag outs, dag ins, string asmstr, list<dag> pattern>
251  : InstSystemZ<6, outs, ins, asmstr, pattern> {
252  field bits<48> Inst;
253  field bits<48> SoftFail = 0;
254
255  bits<4> R1;
256  bits<32> I2;
257
258  let Inst{47-40} = op{11-4};
259  let Inst{39-36} = R1;
260  let Inst{35-32} = op{3-0};
261  let Inst{31-0}  = I2;
262}
263
264class InstRR<bits<8> op, dag outs, dag ins, string asmstr, list<dag> pattern>
265  : InstSystemZ<2, outs, ins, asmstr, pattern> {
266  field bits<16> Inst;
267  field bits<16> SoftFail = 0;
268
269  bits<4> R1;
270  bits<4> R2;
271
272  let Inst{15-8} = op;
273  let Inst{7-4}  = R1;
274  let Inst{3-0}  = R2;
275}
276
277class InstRRD<bits<16> op, dag outs, dag ins, string asmstr, list<dag> pattern>
278  : InstSystemZ<4, outs, ins, asmstr, pattern> {
279  field bits<32> Inst;
280  field bits<32> SoftFail = 0;
281
282  bits<4> R1;
283  bits<4> R3;
284  bits<4> R2;
285
286  let Inst{31-16} = op;
287  let Inst{15-12} = R1;
288  let Inst{11-8}  = 0;
289  let Inst{7-4}   = R3;
290  let Inst{3-0}   = R2;
291}
292
293class InstRRE<bits<16> op, dag outs, dag ins, string asmstr, list<dag> pattern>
294  : InstSystemZ<4, outs, ins, asmstr, pattern> {
295  field bits<32> Inst;
296  field bits<32> SoftFail = 0;
297
298  bits<4> R1;
299  bits<4> R2;
300
301  let Inst{31-16} = op;
302  let Inst{15-8}  = 0;
303  let Inst{7-4}   = R1;
304  let Inst{3-0}   = R2;
305}
306
307class InstRRF<bits<16> op, dag outs, dag ins, string asmstr, list<dag> pattern>
308  : InstSystemZ<4, outs, ins, asmstr, pattern> {
309  field bits<32> Inst;
310  field bits<32> SoftFail = 0;
311
312  bits<4> R1;
313  bits<4> R2;
314  bits<4> R3;
315
316  let Inst{31-16} = op;
317  let Inst{15-12} = R3;
318  let Inst{11-8}  = 0;
319  let Inst{7-4}   = R1;
320  let Inst{3-0}   = R2;
321}
322
323class InstRX<bits<8> op, dag outs, dag ins, string asmstr, list<dag> pattern>
324  : InstSystemZ<4, outs, ins, asmstr, pattern> {
325  field bits<32> Inst;
326  field bits<32> SoftFail = 0;
327
328  bits<4> R1;
329  bits<20> XBD2;
330
331  let Inst{31-24} = op;
332  let Inst{23-20} = R1;
333  let Inst{19-0}  = XBD2;
334
335  let HasIndex = 1;
336}
337
338class InstRXE<bits<16> op, dag outs, dag ins, string asmstr, list<dag> pattern>
339  : InstSystemZ<6, outs, ins, asmstr, pattern> {
340  field bits<48> Inst;
341  field bits<48> SoftFail = 0;
342
343  bits<4> R1;
344  bits<20> XBD2;
345
346  let Inst{47-40} = op{15-8};
347  let Inst{39-36} = R1;
348  let Inst{35-16} = XBD2;
349  let Inst{15-8}  = 0;
350  let Inst{7-0}   = op{7-0};
351
352  let HasIndex = 1;
353}
354
355class InstRXF<bits<16> op, dag outs, dag ins, string asmstr, list<dag> pattern>
356  : InstSystemZ<6, outs, ins, asmstr, pattern> {
357  field bits<48> Inst;
358  field bits<48> SoftFail = 0;
359
360  bits<4> R1;
361  bits<4> R3;
362  bits<20> XBD2;
363
364  let Inst{47-40} = op{15-8};
365  let Inst{39-36} = R3;
366  let Inst{35-16} = XBD2;
367  let Inst{15-12} = R1;
368  let Inst{11-8}  = 0;
369  let Inst{7-0}   = op{7-0};
370
371  let HasIndex = 1;
372}
373
374class InstRXY<bits<16> op, dag outs, dag ins, string asmstr, list<dag> pattern>
375  : InstSystemZ<6, outs, ins, asmstr, pattern> {
376  field bits<48> Inst;
377  field bits<48> SoftFail = 0;
378
379  bits<4> R1;
380  bits<28> XBD2;
381
382  let Inst{47-40} = op{15-8};
383  let Inst{39-36} = R1;
384  let Inst{35-8}  = XBD2;
385  let Inst{7-0}   = op{7-0};
386
387  let Has20BitOffset = 1;
388  let HasIndex = 1;
389}
390
391class InstRS<bits<8> op, dag outs, dag ins, string asmstr, list<dag> pattern>
392  : InstSystemZ<4, outs, ins, asmstr, pattern> {
393  field bits<32> Inst;
394  field bits<32> SoftFail = 0;
395
396  bits<4> R1;
397  bits<4> R3;
398  bits<16> BD2;
399
400  let Inst{31-24} = op;
401  let Inst{23-20} = R1;
402  let Inst{19-16} = R3;
403  let Inst{15-0}  = BD2;
404}
405
406class InstRSY<bits<16> op, dag outs, dag ins, string asmstr, list<dag> pattern>
407  : InstSystemZ<6, outs, ins, asmstr, pattern> {
408  field bits<48> Inst;
409  field bits<48> SoftFail = 0;
410
411  bits<4> R1;
412  bits<4> R3;
413  bits<24> BD2;
414
415  let Inst{47-40} = op{15-8};
416  let Inst{39-36} = R1;
417  let Inst{35-32} = R3;
418  let Inst{31-8}  = BD2;
419  let Inst{7-0}   = op{7-0};
420
421  let Has20BitOffset = 1;
422}
423
424class InstSI<bits<8> op, dag outs, dag ins, string asmstr, list<dag> pattern>
425  : InstSystemZ<4, outs, ins, asmstr, pattern> {
426  field bits<32> Inst;
427  field bits<32> SoftFail = 0;
428
429  bits<16> BD1;
430  bits<8> I2;
431
432  let Inst{31-24} = op;
433  let Inst{23-16} = I2;
434  let Inst{15-0}  = BD1;
435}
436
437class InstSIL<bits<16> op, dag outs, dag ins, string asmstr, list<dag> pattern>
438  : InstSystemZ<6, outs, ins, asmstr, pattern> {
439  field bits<48> Inst;
440  field bits<48> SoftFail = 0;
441
442  bits<16> BD1;
443  bits<16> I2;
444
445  let Inst{47-32} = op;
446  let Inst{31-16} = BD1;
447  let Inst{15-0}  = I2;
448}
449
450class InstSIY<bits<16> op, dag outs, dag ins, string asmstr, list<dag> pattern>
451  : InstSystemZ<6, outs, ins, asmstr, pattern> {
452  field bits<48> Inst;
453  field bits<48> SoftFail = 0;
454
455  bits<24> BD1;
456  bits<8> I2;
457
458  let Inst{47-40} = op{15-8};
459  let Inst{39-32} = I2;
460  let Inst{31-8}  = BD1;
461  let Inst{7-0}   = op{7-0};
462
463  let Has20BitOffset = 1;
464}
465
466class InstSS<bits<8> op, dag outs, dag ins, string asmstr, list<dag> pattern>
467  : InstSystemZ<6, outs, ins, asmstr, pattern> {
468  field bits<48> Inst;
469  field bits<48> SoftFail = 0;
470
471  bits<24> BDL1;
472  bits<16> BD2;
473
474  let Inst{47-40} = op;
475  let Inst{39-16} = BDL1;
476  let Inst{15-0}  = BD2;
477}
478
479//===----------------------------------------------------------------------===//
480// Instruction definitions with semantics
481//===----------------------------------------------------------------------===//
482//
483// These classes have the form [Cond]<Category><Format>, where <Format> is one
484// of the formats defined above and where <Category> describes the inputs
485// and outputs.  "Cond" is used if the instruction is conditional,
486// in which case the 4-bit condition-code mask is added as a final operand.
487// <Category> can be one of:
488//
489//   Inherent:
490//     One register output operand and no input operands.
491//
492//   BranchUnary:
493//     One register output operand, one register input operand and
494//     one branch displacement.  The instructions stores a modified
495//     form of the source register in the destination register and
496//     branches on the result.
497//
498//   Store:
499//     One register or immediate input operand and one address input operand.
500//     The instruction stores the first operand to the address.
501//
502//     This category is used for both pure and truncating stores.
503//
504//   LoadMultiple:
505//     One address input operand and two explicit output operands.
506//     The instruction loads a range of registers from the address,
507//     with the explicit operands giving the first and last register
508//     to load.  Other loaded registers are added as implicit definitions.
509//
510//   StoreMultiple:
511//     Two explicit input register operands and an address operand.
512//     The instruction stores a range of registers to the address,
513//     with the explicit operands giving the first and last register
514//     to store.  Other stored registers are added as implicit uses.
515//
516//   Unary:
517//     One register output operand and one input operand.  The input
518//     operand may be a register, immediate or memory.
519//
520//   Binary:
521//     One register output operand and two input operands.  The first
522//     input operand is always a register and he second may be a register,
523//     immediate or memory.
524//
525//   Shift:
526//     One register output operand and two input operands.  The first
527//     input operand is a register and the second has the same form as
528//     an address (although it isn't actually used to address memory).
529//
530//   Compare:
531//     Two input operands.  The first operand is always a register,
532//     the second may be a register, immediate or memory.
533//
534//   Ternary:
535//     One register output operand and three register input operands.
536//
537//   CmpSwap:
538//     One output operand and three input operands.  The first two
539//     operands are registers and the third is an address.  The instruction
540//     both reads from and writes to the address.
541//
542//   RotateSelect:
543//     One output operand and five input operands.  The first two operands
544//     are registers and the other three are immediates.
545//
546// The format determines which input operands are tied to output operands,
547// and also determines the shape of any address operand.
548//
549// Multiclasses of the form <Category><Format>Pair define two instructions,
550// one with <Category><Format> and one with <Category><Format>Y.  The name
551// of the first instruction has no suffix, the name of the second has
552// an extra "y".
553//
554//===----------------------------------------------------------------------===//
555
556class InherentRRE<string mnemonic, bits<16> opcode, RegisterOperand cls,
557                  dag src>
558  : InstRRE<opcode, (outs cls:$R1), (ins),
559            mnemonic#"r\t$R1",
560            [(set cls:$R1, src)]> {
561  let R2 = 0;
562}
563
564class BranchUnaryRI<string mnemonic, bits<12> opcode, RegisterOperand cls>
565  : InstRI<opcode, (outs cls:$R1), (ins cls:$R1src, brtarget16:$I2),
566           mnemonic##"\t$R1, $I2", []> {
567  let isBranch = 1;
568  let isTerminator = 1;
569  let Constraints = "$R1 = $R1src";
570  let DisableEncoding = "$R1src";
571}
572
573class LoadMultipleRSY<string mnemonic, bits<16> opcode, RegisterOperand cls>
574  : InstRSY<opcode, (outs cls:$R1, cls:$R3), (ins bdaddr20only:$BD2),
575            mnemonic#"\t$R1, $R3, $BD2", []> {
576  let mayLoad = 1;
577}
578
579class StoreRILPC<string mnemonic, bits<12> opcode, SDPatternOperator operator,
580                 RegisterOperand cls>
581  : InstRIL<opcode, (outs), (ins cls:$R1, pcrel32:$I2),
582            mnemonic#"\t$R1, $I2",
583            [(operator cls:$R1, pcrel32:$I2)]> {
584  let mayStore = 1;
585  // We want PC-relative addresses to be tried ahead of BD and BDX addresses.
586  // However, BDXs have two extra operands and are therefore 6 units more
587  // complex.
588  let AddedComplexity = 7;
589}
590
591class StoreRX<string mnemonic, bits<8> opcode, SDPatternOperator operator,
592              RegisterOperand cls, bits<5> bytes,
593              AddressingMode mode = bdxaddr12only>
594  : InstRX<opcode, (outs), (ins cls:$R1, mode:$XBD2),
595           mnemonic#"\t$R1, $XBD2",
596           [(operator cls:$R1, mode:$XBD2)]> {
597  let OpKey = mnemonic ## cls;
598  let OpType = "mem";
599  let mayStore = 1;
600  let AccessBytes = bytes;
601}
602
603class StoreRXY<string mnemonic, bits<16> opcode, SDPatternOperator operator,
604               RegisterOperand cls, bits<5> bytes,
605               AddressingMode mode = bdxaddr20only>
606  : InstRXY<opcode, (outs), (ins cls:$R1, mode:$XBD2),
607            mnemonic#"\t$R1, $XBD2",
608            [(operator cls:$R1, mode:$XBD2)]> {
609  let OpKey = mnemonic ## cls;
610  let OpType = "mem";
611  let mayStore = 1;
612  let AccessBytes = bytes;
613}
614
615multiclass StoreRXPair<string mnemonic, bits<8> rxOpcode, bits<16> rxyOpcode,
616                       SDPatternOperator operator, RegisterOperand cls,
617                       bits<5> bytes> {
618  let DispKey = mnemonic ## #cls in {
619    let DispSize = "12" in
620      def "" : StoreRX<mnemonic, rxOpcode, operator, cls, bytes, bdxaddr12pair>;
621    let DispSize = "20" in
622      def Y  : StoreRXY<mnemonic#"y", rxyOpcode, operator, cls, bytes,
623                        bdxaddr20pair>;
624  }
625}
626
627class StoreMultipleRSY<string mnemonic, bits<16> opcode, RegisterOperand cls>
628  : InstRSY<opcode, (outs), (ins cls:$R1, cls:$R3, bdaddr20only:$BD2),
629            mnemonic#"\t$R1, $R3, $BD2", []> {
630  let mayStore = 1;
631}
632
633class StoreSI<string mnemonic, bits<8> opcode, SDPatternOperator operator,
634              Immediate imm, AddressingMode mode = bdaddr12only>
635  : InstSI<opcode, (outs), (ins mode:$BD1, imm:$I2),
636           mnemonic#"\t$BD1, $I2",
637           [(operator imm:$I2, mode:$BD1)]> {
638  let mayStore = 1;
639}
640
641class StoreSIY<string mnemonic, bits<16> opcode, SDPatternOperator operator,
642               Immediate imm, AddressingMode mode = bdaddr20only>
643  : InstSIY<opcode, (outs), (ins mode:$BD1, imm:$I2),
644            mnemonic#"\t$BD1, $I2",
645            [(operator imm:$I2, mode:$BD1)]> {
646  let mayStore = 1;
647}
648
649class StoreSIL<string mnemonic, bits<16> opcode, SDPatternOperator operator,
650               Immediate imm>
651  : InstSIL<opcode, (outs), (ins bdaddr12only:$BD1, imm:$I2),
652            mnemonic#"\t$BD1, $I2",
653            [(operator imm:$I2, bdaddr12only:$BD1)]> {
654  let mayStore = 1;
655}
656
657multiclass StoreSIPair<string mnemonic, bits<8> siOpcode, bits<16> siyOpcode,
658                       SDPatternOperator operator, Immediate imm> {
659  let DispKey = mnemonic in {
660    let DispSize = "12" in
661      def "" : StoreSI<mnemonic, siOpcode, operator, imm, bdaddr12pair>;
662    let DispSize = "20" in
663      def Y  : StoreSIY<mnemonic#"y", siyOpcode, operator, imm, bdaddr20pair>;
664  }
665}
666
667class CondStoreRSY<string mnemonic, bits<16> opcode,
668                   RegisterOperand cls, bits<5> bytes,
669                   AddressingMode mode = bdaddr20only>
670  : InstRSY<opcode, (outs), (ins cls:$R1, mode:$BD2, cond4:$valid, cond4:$R3),
671            mnemonic#"$R3\t$R1, $BD2", []>,
672    Requires<[FeatureLoadStoreOnCond]> {
673  let mayStore = 1;
674  let AccessBytes = bytes;
675  let CCMaskLast = 1;
676}
677
678// Like CondStoreRSY, but used for the raw assembly form.  The condition-code
679// mask is the third operand rather than being part of the mnemonic.
680class AsmCondStoreRSY<string mnemonic, bits<16> opcode,
681                      RegisterOperand cls, bits<5> bytes,
682                      AddressingMode mode = bdaddr20only>
683  : InstRSY<opcode, (outs), (ins cls:$R1, mode:$BD2, uimm8zx4:$R3),
684            mnemonic#"\t$R1, $BD2, $R3", []>,
685    Requires<[FeatureLoadStoreOnCond]> {
686  let mayStore = 1;
687  let AccessBytes = bytes;
688}
689
690// Like CondStoreRSY, but with a fixed CC mask.
691class FixedCondStoreRSY<string mnemonic, bits<16> opcode,
692                        RegisterOperand cls, bits<4> ccmask, bits<5> bytes,
693                        AddressingMode mode = bdaddr20only>
694  : InstRSY<opcode, (outs), (ins cls:$R1, mode:$BD2),
695            mnemonic#"\t$R1, $BD2", []>,
696    Requires<[FeatureLoadStoreOnCond]> {
697  let mayStore = 1;
698  let AccessBytes = bytes;
699  let R3 = ccmask;
700}
701
702class UnaryRR<string mnemonic, bits<8> opcode, SDPatternOperator operator,
703              RegisterOperand cls1, RegisterOperand cls2>
704  : InstRR<opcode, (outs cls1:$R1), (ins cls2:$R2),
705           mnemonic#"r\t$R1, $R2",
706           [(set cls1:$R1, (operator cls2:$R2))]> {
707  let OpKey = mnemonic ## cls1;
708  let OpType = "reg";
709}
710
711class UnaryRRE<string mnemonic, bits<16> opcode, SDPatternOperator operator,
712               RegisterOperand cls1, RegisterOperand cls2>
713  : InstRRE<opcode, (outs cls1:$R1), (ins cls2:$R2),
714            mnemonic#"r\t$R1, $R2",
715            [(set cls1:$R1, (operator cls2:$R2))]> {
716  let OpKey = mnemonic ## cls1;
717  let OpType = "reg";
718}
719
720class UnaryRRF<string mnemonic, bits<16> opcode, RegisterOperand cls1,
721               RegisterOperand cls2>
722  : InstRRF<opcode, (outs cls1:$R1), (ins uimm8zx4:$R3, cls2:$R2),
723            mnemonic#"r\t$R1, $R3, $R2", []> {
724  let OpKey = mnemonic ## cls1;
725  let OpType = "reg";
726}
727
728// These instructions are generated by if conversion.  The old value of R1
729// is added as an implicit use.
730class CondUnaryRRF<string mnemonic, bits<16> opcode, RegisterOperand cls1,
731                   RegisterOperand cls2>
732  : InstRRF<opcode, (outs cls1:$R1), (ins cls2:$R2, cond4:$valid, cond4:$R3),
733            mnemonic#"r$R3\t$R1, $R2", []>,
734    Requires<[FeatureLoadStoreOnCond]> {
735  let CCMaskLast = 1;
736}
737
738// Like CondUnaryRRF, but used for the raw assembly form.  The condition-code
739// mask is the third operand rather than being part of the mnemonic.
740class AsmCondUnaryRRF<string mnemonic, bits<16> opcode, RegisterOperand cls1,
741                      RegisterOperand cls2>
742  : InstRRF<opcode, (outs cls1:$R1), (ins cls1:$R1src, cls2:$R2, uimm8zx4:$R3),
743            mnemonic#"r\t$R1, $R2, $R3", []>,
744    Requires<[FeatureLoadStoreOnCond]> {
745  let Constraints = "$R1 = $R1src";
746  let DisableEncoding = "$R1src";
747}
748
749// Like CondUnaryRRF, but with a fixed CC mask.
750class FixedCondUnaryRRF<string mnemonic, bits<16> opcode, RegisterOperand cls1,
751                        RegisterOperand cls2, bits<4> ccmask>
752  : InstRRF<opcode, (outs cls1:$R1), (ins cls1:$R1src, cls2:$R2),
753            mnemonic#"\t$R1, $R2", []>,
754    Requires<[FeatureLoadStoreOnCond]> {
755  let Constraints = "$R1 = $R1src";
756  let DisableEncoding = "$R1src";
757  let R3 = ccmask;
758}
759
760class UnaryRI<string mnemonic, bits<12> opcode, SDPatternOperator operator,
761              RegisterOperand cls, Immediate imm>
762  : InstRI<opcode, (outs cls:$R1), (ins imm:$I2),
763           mnemonic#"\t$R1, $I2",
764           [(set cls:$R1, (operator imm:$I2))]>;
765
766class UnaryRIL<string mnemonic, bits<12> opcode, SDPatternOperator operator,
767               RegisterOperand cls, Immediate imm>
768  : InstRIL<opcode, (outs cls:$R1), (ins imm:$I2),
769            mnemonic#"\t$R1, $I2",
770            [(set cls:$R1, (operator imm:$I2))]>;
771
772class UnaryRILPC<string mnemonic, bits<12> opcode, SDPatternOperator operator,
773                 RegisterOperand cls>
774  : InstRIL<opcode, (outs cls:$R1), (ins pcrel32:$I2),
775            mnemonic#"\t$R1, $I2",
776            [(set cls:$R1, (operator pcrel32:$I2))]> {
777  let mayLoad = 1;
778  // We want PC-relative addresses to be tried ahead of BD and BDX addresses.
779  // However, BDXs have two extra operands and are therefore 6 units more
780  // complex.
781  let AddedComplexity = 7;
782}
783
784class CondUnaryRSY<string mnemonic, bits<16> opcode,
785                   SDPatternOperator operator, RegisterOperand cls,
786                   bits<5> bytes, AddressingMode mode = bdaddr20only>
787  : InstRSY<opcode, (outs cls:$R1),
788            (ins cls:$R1src, mode:$BD2, cond4:$valid, cond4:$R3),
789            mnemonic#"$R3\t$R1, $BD2",
790            [(set cls:$R1,
791                  (z_select_ccmask (load bdaddr20only:$BD2), cls:$R1src,
792                                   cond4:$valid, cond4:$R3))]>,
793    Requires<[FeatureLoadStoreOnCond]> {
794  let Constraints = "$R1 = $R1src";
795  let DisableEncoding = "$R1src";
796  let mayLoad = 1;
797  let AccessBytes = bytes;
798  let CCMaskLast = 1;
799}
800
801// Like CondUnaryRSY, but used for the raw assembly form.  The condition-code
802// mask is the third operand rather than being part of the mnemonic.
803class AsmCondUnaryRSY<string mnemonic, bits<16> opcode,
804                      RegisterOperand cls, bits<5> bytes,
805                      AddressingMode mode = bdaddr20only>
806  : InstRSY<opcode, (outs cls:$R1), (ins cls:$R1src, mode:$BD2, uimm8zx4:$R3),
807            mnemonic#"\t$R1, $BD2, $R3", []>,
808    Requires<[FeatureLoadStoreOnCond]> {
809  let mayLoad = 1;
810  let AccessBytes = bytes;
811  let Constraints = "$R1 = $R1src";
812  let DisableEncoding = "$R1src";
813}
814
815// Like CondUnaryRSY, but with a fixed CC mask.
816class FixedCondUnaryRSY<string mnemonic, bits<16> opcode,
817                        RegisterOperand cls, bits<4> ccmask, bits<5> bytes,
818                        AddressingMode mode = bdaddr20only>
819  : InstRSY<opcode, (outs cls:$R1), (ins cls:$R1src, mode:$BD2),
820            mnemonic#"\t$R1, $BD2", []>,
821    Requires<[FeatureLoadStoreOnCond]> {
822  let Constraints = "$R1 = $R1src";
823  let DisableEncoding = "$R1src";
824  let R3 = ccmask;
825  let mayLoad = 1;
826  let AccessBytes = bytes;
827}
828
829class UnaryRX<string mnemonic, bits<8> opcode, SDPatternOperator operator,
830              RegisterOperand cls, bits<5> bytes,
831              AddressingMode mode = bdxaddr12only>
832  : InstRX<opcode, (outs cls:$R1), (ins mode:$XBD2),
833           mnemonic#"\t$R1, $XBD2",
834           [(set cls:$R1, (operator mode:$XBD2))]> {
835  let OpKey = mnemonic ## cls;
836  let OpType = "mem";
837  let mayLoad = 1;
838  let AccessBytes = bytes;
839}
840
841class UnaryRXE<string mnemonic, bits<16> opcode, SDPatternOperator operator,
842               RegisterOperand cls, bits<5> bytes>
843  : InstRXE<opcode, (outs cls:$R1), (ins bdxaddr12only:$XBD2),
844            mnemonic#"\t$R1, $XBD2",
845            [(set cls:$R1, (operator bdxaddr12only:$XBD2))]> {
846  let OpKey = mnemonic ## cls;
847  let OpType = "mem";
848  let mayLoad = 1;
849  let AccessBytes = bytes;
850}
851
852class UnaryRXY<string mnemonic, bits<16> opcode, SDPatternOperator operator,
853               RegisterOperand cls, bits<5> bytes,
854               AddressingMode mode = bdxaddr20only>
855  : InstRXY<opcode, (outs cls:$R1), (ins mode:$XBD2),
856            mnemonic#"\t$R1, $XBD2",
857            [(set cls:$R1, (operator mode:$XBD2))]> {
858  let OpKey = mnemonic ## cls;
859  let OpType = "mem";
860  let mayLoad = 1;
861  let AccessBytes = bytes;
862}
863
864multiclass UnaryRXPair<string mnemonic, bits<8> rxOpcode, bits<16> rxyOpcode,
865                       SDPatternOperator operator, RegisterOperand cls,
866                       bits<5> bytes> {
867  let DispKey = mnemonic ## #cls in {
868    let DispSize = "12" in
869      def "" : UnaryRX<mnemonic, rxOpcode, operator, cls, bytes, bdxaddr12pair>;
870    let DispSize = "20" in
871      def Y  : UnaryRXY<mnemonic#"y", rxyOpcode, operator, cls, bytes,
872                        bdxaddr20pair>;
873  }
874}
875
876class BinaryRR<string mnemonic, bits<8> opcode, SDPatternOperator operator,
877               RegisterOperand cls1, RegisterOperand cls2>
878  : InstRR<opcode, (outs cls1:$R1), (ins cls1:$R1src, cls2:$R2),
879           mnemonic#"r\t$R1, $R2",
880           [(set cls1:$R1, (operator cls1:$R1src, cls2:$R2))]> {
881  let OpKey = mnemonic ## cls1;
882  let OpType = "reg";
883  let Constraints = "$R1 = $R1src";
884  let DisableEncoding = "$R1src";
885}
886
887class BinaryRRE<string mnemonic, bits<16> opcode, SDPatternOperator operator,
888                RegisterOperand cls1, RegisterOperand cls2>
889  : InstRRE<opcode, (outs cls1:$R1), (ins cls1:$R1src, cls2:$R2),
890            mnemonic#"r\t$R1, $R2",
891            [(set cls1:$R1, (operator cls1:$R1src, cls2:$R2))]> {
892  let OpKey = mnemonic ## cls1;
893  let OpType = "reg";
894  let Constraints = "$R1 = $R1src";
895  let DisableEncoding = "$R1src";
896}
897
898class BinaryRRF<string mnemonic, bits<16> opcode, SDPatternOperator operator,
899                RegisterOperand cls1, RegisterOperand cls2>
900  : InstRRF<opcode, (outs cls1:$R1), (ins cls1:$R3, cls2:$R2),
901            mnemonic#"r\t$R1, $R3, $R2",
902            [(set cls1:$R1, (operator cls1:$R3, cls2:$R2))]> {
903  let OpKey = mnemonic ## cls1;
904  let OpType = "reg";
905}
906
907class BinaryRRFK<string mnemonic, bits<16> opcode, SDPatternOperator operator,
908                 RegisterOperand cls1, RegisterOperand cls2>
909  : InstRRF<opcode, (outs cls1:$R1), (ins cls1:$R2, cls2:$R3),
910            mnemonic#"rk\t$R1, $R2, $R3",
911            [(set cls1:$R1, (operator cls1:$R2, cls2:$R3))]>;
912
913multiclass BinaryRRAndK<string mnemonic, bits<8> opcode1, bits<16> opcode2,
914                        SDPatternOperator operator, RegisterOperand cls1,
915                        RegisterOperand cls2> {
916  let NumOpsKey = mnemonic in {
917    let NumOpsValue = "3" in
918      def K : BinaryRRFK<mnemonic, opcode2, null_frag, cls1, cls2>,
919              Requires<[FeatureDistinctOps]>;
920    let NumOpsValue = "2", isConvertibleToThreeAddress = 1 in
921      def "" : BinaryRR<mnemonic, opcode1, operator, cls1, cls2>;
922  }
923}
924
925multiclass BinaryRREAndK<string mnemonic, bits<16> opcode1, bits<16> opcode2,
926                         SDPatternOperator operator, RegisterOperand cls1,
927                         RegisterOperand cls2> {
928  let NumOpsKey = mnemonic in {
929    let NumOpsValue = "3" in
930      def K : BinaryRRFK<mnemonic, opcode2, null_frag, cls1, cls2>,
931              Requires<[FeatureDistinctOps]>;
932    let NumOpsValue = "2", isConvertibleToThreeAddress = 1 in
933      def "" : BinaryRRE<mnemonic, opcode1, operator, cls1, cls2>;
934  }
935}
936
937class BinaryRI<string mnemonic, bits<12> opcode, SDPatternOperator operator,
938               RegisterOperand cls, Immediate imm>
939  : InstRI<opcode, (outs cls:$R1), (ins cls:$R1src, imm:$I2),
940           mnemonic#"\t$R1, $I2",
941           [(set cls:$R1, (operator cls:$R1src, imm:$I2))]> {
942  let Constraints = "$R1 = $R1src";
943  let DisableEncoding = "$R1src";
944}
945
946class BinaryRIE<string mnemonic, bits<16> opcode, SDPatternOperator operator,
947                RegisterOperand cls, Immediate imm>
948  : InstRIEd<opcode, (outs cls:$R1), (ins cls:$R3, imm:$I2),
949             mnemonic#"\t$R1, $R3, $I2",
950             [(set cls:$R1, (operator cls:$R3, imm:$I2))]>;
951
952multiclass BinaryRIAndK<string mnemonic, bits<12> opcode1, bits<16> opcode2,
953                        SDPatternOperator operator, RegisterOperand cls,
954                        Immediate imm> {
955  let NumOpsKey = mnemonic in {
956    let NumOpsValue = "3" in
957      def K : BinaryRIE<mnemonic##"k", opcode2, null_frag, cls, imm>,
958              Requires<[FeatureDistinctOps]>;
959    let NumOpsValue = "2", isConvertibleToThreeAddress = 1 in
960      def "" : BinaryRI<mnemonic, opcode1, operator, cls, imm>;
961  }
962}
963
964class BinaryRIL<string mnemonic, bits<12> opcode, SDPatternOperator operator,
965                RegisterOperand cls, Immediate imm>
966  : InstRIL<opcode, (outs cls:$R1), (ins cls:$R1src, imm:$I2),
967            mnemonic#"\t$R1, $I2",
968            [(set cls:$R1, (operator cls:$R1src, imm:$I2))]> {
969  let Constraints = "$R1 = $R1src";
970  let DisableEncoding = "$R1src";
971}
972
973class BinaryRX<string mnemonic, bits<8> opcode, SDPatternOperator operator,
974               RegisterOperand cls, SDPatternOperator load, bits<5> bytes,
975               AddressingMode mode = bdxaddr12only>
976  : InstRX<opcode, (outs cls:$R1), (ins cls:$R1src, mode:$XBD2),
977           mnemonic#"\t$R1, $XBD2",
978           [(set cls:$R1, (operator cls:$R1src, (load mode:$XBD2)))]> {
979  let OpKey = mnemonic ## cls;
980  let OpType = "mem";
981  let Constraints = "$R1 = $R1src";
982  let DisableEncoding = "$R1src";
983  let mayLoad = 1;
984  let AccessBytes = bytes;
985}
986
987class BinaryRXE<string mnemonic, bits<16> opcode, SDPatternOperator operator,
988                  RegisterOperand cls, SDPatternOperator load, bits<5> bytes>
989  : InstRXE<opcode, (outs cls:$R1), (ins cls:$R1src, bdxaddr12only:$XBD2),
990            mnemonic#"\t$R1, $XBD2",
991            [(set cls:$R1, (operator cls:$R1src,
992                                     (load bdxaddr12only:$XBD2)))]> {
993  let OpKey = mnemonic ## cls;
994  let OpType = "mem";
995  let Constraints = "$R1 = $R1src";
996  let DisableEncoding = "$R1src";
997  let mayLoad = 1;
998  let AccessBytes = bytes;
999}
1000
1001class BinaryRXY<string mnemonic, bits<16> opcode, SDPatternOperator operator,
1002                RegisterOperand cls, SDPatternOperator load, bits<5> bytes,
1003                AddressingMode mode = bdxaddr20only>
1004  : InstRXY<opcode, (outs cls:$R1), (ins cls:$R1src, mode:$XBD2),
1005            mnemonic#"\t$R1, $XBD2",
1006            [(set cls:$R1, (operator cls:$R1src, (load mode:$XBD2)))]> {
1007  let OpKey = mnemonic ## cls;
1008  let OpType = "mem";
1009  let Constraints = "$R1 = $R1src";
1010  let DisableEncoding = "$R1src";
1011  let mayLoad = 1;
1012  let AccessBytes = bytes;
1013}
1014
1015multiclass BinaryRXPair<string mnemonic, bits<8> rxOpcode, bits<16> rxyOpcode,
1016                        SDPatternOperator operator, RegisterOperand cls,
1017                        SDPatternOperator load, bits<5> bytes> {
1018  let DispKey = mnemonic ## #cls in {
1019    let DispSize = "12" in
1020      def "" : BinaryRX<mnemonic, rxOpcode, operator, cls, load, bytes,
1021                        bdxaddr12pair>;
1022    let DispSize = "20" in
1023      def Y  : BinaryRXY<mnemonic#"y", rxyOpcode, operator, cls, load, bytes,
1024                         bdxaddr20pair>;
1025  }
1026}
1027
1028class BinarySI<string mnemonic, bits<8> opcode, SDPatternOperator operator,
1029               Operand imm, AddressingMode mode = bdaddr12only>
1030  : InstSI<opcode, (outs), (ins mode:$BD1, imm:$I2),
1031           mnemonic#"\t$BD1, $I2",
1032           [(store (operator (load mode:$BD1), imm:$I2), mode:$BD1)]> {
1033  let mayLoad = 1;
1034  let mayStore = 1;
1035}
1036
1037class BinarySIY<string mnemonic, bits<16> opcode, SDPatternOperator operator,
1038                Operand imm, AddressingMode mode = bdaddr20only>
1039  : InstSIY<opcode, (outs), (ins mode:$BD1, imm:$I2),
1040            mnemonic#"\t$BD1, $I2",
1041            [(store (operator (load mode:$BD1), imm:$I2), mode:$BD1)]> {
1042  let mayLoad = 1;
1043  let mayStore = 1;
1044}
1045
1046multiclass BinarySIPair<string mnemonic, bits<8> siOpcode,
1047                        bits<16> siyOpcode, SDPatternOperator operator,
1048                        Operand imm> {
1049  let DispKey = mnemonic ## #cls in {
1050    let DispSize = "12" in
1051      def "" : BinarySI<mnemonic, siOpcode, operator, imm, bdaddr12pair>;
1052    let DispSize = "20" in
1053      def Y  : BinarySIY<mnemonic#"y", siyOpcode, operator, imm, bdaddr20pair>;
1054  }
1055}
1056
1057class ShiftRS<string mnemonic, bits<8> opcode, SDPatternOperator operator,
1058              RegisterOperand cls>
1059  : InstRS<opcode, (outs cls:$R1), (ins cls:$R1src, shift12only:$BD2),
1060           mnemonic#"\t$R1, $BD2",
1061           [(set cls:$R1, (operator cls:$R1src, shift12only:$BD2))]> {
1062  let R3 = 0;
1063  let Constraints = "$R1 = $R1src";
1064  let DisableEncoding = "$R1src";
1065}
1066
1067class ShiftRSY<string mnemonic, bits<16> opcode, SDPatternOperator operator,
1068               RegisterOperand cls>
1069  : InstRSY<opcode, (outs cls:$R1), (ins cls:$R3, shift20only:$BD2),
1070            mnemonic#"\t$R1, $R3, $BD2",
1071            [(set cls:$R1, (operator cls:$R3, shift20only:$BD2))]>;
1072
1073multiclass ShiftRSAndK<string mnemonic, bits<8> opcode1, bits<16> opcode2,
1074                       SDPatternOperator operator, RegisterOperand cls> {
1075  let NumOpsKey = mnemonic in {
1076    let NumOpsValue = "3" in
1077      def K  : ShiftRSY<mnemonic##"k", opcode2, null_frag, cls>,
1078               Requires<[FeatureDistinctOps]>;
1079    let NumOpsValue = "2", isConvertibleToThreeAddress = 1 in
1080      def "" : ShiftRS<mnemonic, opcode1, operator, cls>;
1081  }
1082}
1083
1084class CompareRR<string mnemonic, bits<8> opcode, SDPatternOperator operator,
1085                RegisterOperand cls1, RegisterOperand cls2>
1086  : InstRR<opcode, (outs), (ins cls1:$R1, cls2:$R2),
1087           mnemonic#"r\t$R1, $R2",
1088           [(operator cls1:$R1, cls2:$R2)]> {
1089  let OpKey = mnemonic ## cls1;
1090  let OpType = "reg";
1091  let isCompare = 1;
1092}
1093
1094class CompareRRE<string mnemonic, bits<16> opcode, SDPatternOperator operator,
1095                 RegisterOperand cls1, RegisterOperand cls2>
1096  : InstRRE<opcode, (outs), (ins cls1:$R1, cls2:$R2),
1097            mnemonic#"r\t$R1, $R2",
1098            [(operator cls1:$R1, cls2:$R2)]> {
1099  let OpKey = mnemonic ## cls1;
1100  let OpType = "reg";
1101  let isCompare = 1;
1102}
1103
1104class CompareRI<string mnemonic, bits<12> opcode, SDPatternOperator operator,
1105                RegisterOperand cls, Immediate imm>
1106  : InstRI<opcode, (outs), (ins cls:$R1, imm:$I2),
1107           mnemonic#"\t$R1, $I2",
1108           [(operator cls:$R1, imm:$I2)]> {
1109  let isCompare = 1;
1110}
1111
1112class CompareRIL<string mnemonic, bits<12> opcode, SDPatternOperator operator,
1113                 RegisterOperand cls, Immediate imm>
1114  : InstRIL<opcode, (outs), (ins cls:$R1, imm:$I2),
1115            mnemonic#"\t$R1, $I2",
1116            [(operator cls:$R1, imm:$I2)]> {
1117  let isCompare = 1;
1118}
1119
1120class CompareRILPC<string mnemonic, bits<12> opcode, SDPatternOperator operator,
1121                   RegisterOperand cls, SDPatternOperator load>
1122  : InstRIL<opcode, (outs), (ins cls:$R1, pcrel32:$I2),
1123            mnemonic#"\t$R1, $I2",
1124            [(operator cls:$R1, (load pcrel32:$I2))]> {
1125  let isCompare = 1;
1126  let mayLoad = 1;
1127  // We want PC-relative addresses to be tried ahead of BD and BDX addresses.
1128  // However, BDXs have two extra operands and are therefore 6 units more
1129  // complex.
1130  let AddedComplexity = 7;
1131}
1132
1133class CompareRX<string mnemonic, bits<8> opcode, SDPatternOperator operator,
1134                RegisterOperand cls, SDPatternOperator load, bits<5> bytes,
1135                AddressingMode mode = bdxaddr12only>
1136  : InstRX<opcode, (outs), (ins cls:$R1, mode:$XBD2),
1137           mnemonic#"\t$R1, $XBD2",
1138           [(operator cls:$R1, (load mode:$XBD2))]> {
1139  let OpKey = mnemonic ## cls;
1140  let OpType = "mem";
1141  let isCompare = 1;
1142  let mayLoad = 1;
1143  let AccessBytes = bytes;
1144}
1145
1146class CompareRXE<string mnemonic, bits<16> opcode, SDPatternOperator operator,
1147                 RegisterOperand cls, SDPatternOperator load, bits<5> bytes>
1148  : InstRXE<opcode, (outs), (ins cls:$R1, bdxaddr12only:$XBD2),
1149            mnemonic#"\t$R1, $XBD2",
1150            [(operator cls:$R1, (load bdxaddr12only:$XBD2))]> {
1151  let OpKey = mnemonic ## cls;
1152  let OpType = "mem";
1153  let isCompare = 1;
1154  let mayLoad = 1;
1155  let AccessBytes = bytes;
1156}
1157
1158class CompareRXY<string mnemonic, bits<16> opcode, SDPatternOperator operator,
1159                 RegisterOperand cls, SDPatternOperator load, bits<5> bytes,
1160                 AddressingMode mode = bdxaddr20only>
1161  : InstRXY<opcode, (outs), (ins cls:$R1, mode:$XBD2),
1162            mnemonic#"\t$R1, $XBD2",
1163            [(operator cls:$R1, (load mode:$XBD2))]> {
1164  let OpKey = mnemonic ## cls;
1165  let OpType = "mem";
1166  let isCompare = 1;
1167  let mayLoad = 1;
1168  let AccessBytes = bytes;
1169}
1170
1171multiclass CompareRXPair<string mnemonic, bits<8> rxOpcode, bits<16> rxyOpcode,
1172                         SDPatternOperator operator, RegisterOperand cls,
1173                         SDPatternOperator load, bits<5> bytes> {
1174  let DispKey = mnemonic ## #cls in {
1175    let DispSize = "12" in
1176      def "" : CompareRX<mnemonic, rxOpcode, operator, cls,
1177                         load, bytes, bdxaddr12pair>;
1178    let DispSize = "20" in
1179      def Y  : CompareRXY<mnemonic#"y", rxyOpcode, operator, cls,
1180                          load, bytes, bdxaddr20pair>;
1181  }
1182}
1183
1184class CompareSI<string mnemonic, bits<8> opcode, SDPatternOperator operator,
1185                SDPatternOperator load, Immediate imm,
1186                AddressingMode mode = bdaddr12only>
1187  : InstSI<opcode, (outs), (ins mode:$BD1, imm:$I2),
1188           mnemonic#"\t$BD1, $I2",
1189           [(operator (load mode:$BD1), imm:$I2)]> {
1190  let isCompare = 1;
1191  let mayLoad = 1;
1192}
1193
1194class CompareSIL<string mnemonic, bits<16> opcode, SDPatternOperator operator,
1195                 SDPatternOperator load, Immediate imm>
1196  : InstSIL<opcode, (outs), (ins bdaddr12only:$BD1, imm:$I2),
1197            mnemonic#"\t$BD1, $I2",
1198            [(operator (load bdaddr12only:$BD1), imm:$I2)]> {
1199  let isCompare = 1;
1200  let mayLoad = 1;
1201}
1202
1203class CompareSIY<string mnemonic, bits<16> opcode, SDPatternOperator operator,
1204                 SDPatternOperator load, Immediate imm,
1205                 AddressingMode mode = bdaddr20only>
1206  : InstSIY<opcode, (outs), (ins mode:$BD1, imm:$I2),
1207            mnemonic#"\t$BD1, $I2",
1208            [(operator (load mode:$BD1), imm:$I2)]> {
1209  let isCompare = 1;
1210  let mayLoad = 1;
1211}
1212
1213multiclass CompareSIPair<string mnemonic, bits<8> siOpcode, bits<16> siyOpcode,
1214                         SDPatternOperator operator, SDPatternOperator load,
1215                         Immediate imm> {
1216  let DispKey = mnemonic in {
1217    let DispSize = "12" in
1218      def "" : CompareSI<mnemonic, siOpcode, operator, load, imm, bdaddr12pair>;
1219    let DispSize = "20" in
1220      def Y  : CompareSIY<mnemonic#"y", siyOpcode, operator, load, imm,
1221                          bdaddr20pair>;
1222  }
1223}
1224
1225class TernaryRRD<string mnemonic, bits<16> opcode,
1226                 SDPatternOperator operator, RegisterOperand cls>
1227  : InstRRD<opcode, (outs cls:$R1), (ins cls:$R1src, cls:$R3, cls:$R2),
1228            mnemonic#"r\t$R1, $R3, $R2",
1229            [(set cls:$R1, (operator cls:$R1src, cls:$R3, cls:$R2))]> {
1230  let OpKey = mnemonic ## cls;
1231  let OpType = "reg";
1232  let Constraints = "$R1 = $R1src";
1233  let DisableEncoding = "$R1src";
1234}
1235
1236class TernaryRXF<string mnemonic, bits<16> opcode, SDPatternOperator operator,
1237                 RegisterOperand cls, SDPatternOperator load, bits<5> bytes>
1238  : InstRXF<opcode, (outs cls:$R1),
1239            (ins cls:$R1src, cls:$R3, bdxaddr12only:$XBD2),
1240            mnemonic#"\t$R1, $R3, $XBD2",
1241            [(set cls:$R1, (operator cls:$R1src, cls:$R3,
1242                                     (load bdxaddr12only:$XBD2)))]> {
1243  let OpKey = mnemonic ## cls;
1244  let OpType = "mem";
1245  let Constraints = "$R1 = $R1src";
1246  let DisableEncoding = "$R1src";
1247  let mayLoad = 1;
1248  let AccessBytes = bytes;
1249}
1250
1251class CmpSwapRS<string mnemonic, bits<8> opcode, SDPatternOperator operator,
1252                RegisterOperand cls, AddressingMode mode = bdaddr12only>
1253  : InstRS<opcode, (outs cls:$R1), (ins cls:$R1src, cls:$R3, mode:$BD2),
1254           mnemonic#"\t$R1, $R3, $BD2",
1255           [(set cls:$R1, (operator mode:$BD2, cls:$R1src, cls:$R3))]> {
1256  let Constraints = "$R1 = $R1src";
1257  let DisableEncoding = "$R1src";
1258  let mayLoad = 1;
1259  let mayStore = 1;
1260}
1261
1262class CmpSwapRSY<string mnemonic, bits<16> opcode, SDPatternOperator operator,
1263                 RegisterOperand cls, AddressingMode mode = bdaddr20only>
1264  : InstRSY<opcode, (outs cls:$R1), (ins cls:$R1src, cls:$R3, mode:$BD2),
1265            mnemonic#"\t$R1, $R3, $BD2",
1266            [(set cls:$R1, (operator mode:$BD2, cls:$R1src, cls:$R3))]> {
1267  let Constraints = "$R1 = $R1src";
1268  let DisableEncoding = "$R1src";
1269  let mayLoad = 1;
1270  let mayStore = 1;
1271}
1272
1273multiclass CmpSwapRSPair<string mnemonic, bits<8> rsOpcode, bits<16> rsyOpcode,
1274                         SDPatternOperator operator, RegisterOperand cls> {
1275  let DispKey = mnemonic ## #cls in {
1276    let DispSize = "12" in
1277      def "" : CmpSwapRS<mnemonic, rsOpcode, operator, cls, bdaddr12pair>;
1278    let DispSize = "20" in
1279      def Y  : CmpSwapRSY<mnemonic#"y", rsyOpcode, operator, cls, bdaddr20pair>;
1280  }
1281}
1282
1283class RotateSelectRIEf<string mnemonic, bits<16> opcode, RegisterOperand cls1,
1284                       RegisterOperand cls2>
1285  : InstRIEf<opcode, (outs cls1:$R1),
1286             (ins cls1:$R1src, cls2:$R2, uimm8:$I3, uimm8:$I4, uimm8zx6:$I5),
1287             mnemonic#"\t$R1, $R2, $I3, $I4, $I5", []> {
1288  let Constraints = "$R1 = $R1src";
1289  let DisableEncoding = "$R1src";
1290}
1291
1292//===----------------------------------------------------------------------===//
1293// Pseudo instructions
1294//===----------------------------------------------------------------------===//
1295//
1296// Convenience instructions that get lowered to real instructions
1297// by either SystemZTargetLowering::EmitInstrWithCustomInserter()
1298// or SystemZInstrInfo::expandPostRAPseudo().
1299//
1300//===----------------------------------------------------------------------===//
1301
1302class Pseudo<dag outs, dag ins, list<dag> pattern>
1303  : InstSystemZ<0, outs, ins, "", pattern> {
1304  let isPseudo = 1;
1305  let isCodeGenOnly = 1;
1306}
1307
1308// Implements "$dst = $cc & (8 >> CC) ? $src1 : $src2", where CC is
1309// the value of the PSW's 2-bit condition code field.
1310class SelectWrapper<RegisterOperand cls>
1311  : Pseudo<(outs cls:$dst),
1312           (ins cls:$src1, cls:$src2, uimm8zx4:$valid, uimm8zx4:$cc),
1313           [(set cls:$dst, (z_select_ccmask cls:$src1, cls:$src2,
1314                                            uimm8zx4:$valid, uimm8zx4:$cc))]> {
1315  let usesCustomInserter = 1;
1316  // Although the instructions used by these nodes do not in themselves
1317  // change CC, the insertion requires new blocks, and CC cannot be live
1318  // across them.
1319  let Defs = [CC];
1320  let Uses = [CC];
1321}
1322
1323// Stores $new to $addr if $cc is true ("" case) or false (Inv case).
1324multiclass CondStores<RegisterOperand cls, SDPatternOperator store,
1325                      SDPatternOperator load, AddressingMode mode> {
1326  let Defs = [CC], Uses = [CC], usesCustomInserter = 1 in {
1327    def "" : Pseudo<(outs),
1328                    (ins cls:$new, mode:$addr, uimm8zx4:$valid, uimm8zx4:$cc),
1329                    [(store (z_select_ccmask cls:$new, (load mode:$addr),
1330                                             uimm8zx4:$valid, uimm8zx4:$cc),
1331                            mode:$addr)]>;
1332    def Inv : Pseudo<(outs),
1333                     (ins cls:$new, mode:$addr, uimm8zx4:$valid, uimm8zx4:$cc),
1334                     [(store (z_select_ccmask (load mode:$addr), cls:$new,
1335                                              uimm8zx4:$valid, uimm8zx4:$cc),
1336                              mode:$addr)]>;
1337  }
1338}
1339
1340// OPERATOR is ATOMIC_SWAP or an ATOMIC_LOAD_* operation.  PAT and OPERAND
1341// describe the second (non-memory) operand.
1342class AtomicLoadBinary<SDPatternOperator operator, RegisterOperand cls,
1343                       dag pat, DAGOperand operand>
1344  : Pseudo<(outs cls:$dst), (ins bdaddr20only:$ptr, operand:$src2),
1345           [(set cls:$dst, (operator bdaddr20only:$ptr, pat))]> {
1346  let Defs = [CC];
1347  let Has20BitOffset = 1;
1348  let mayLoad = 1;
1349  let mayStore = 1;
1350  let usesCustomInserter = 1;
1351}
1352
1353// Specializations of AtomicLoadWBinary.
1354class AtomicLoadBinaryReg32<SDPatternOperator operator>
1355  : AtomicLoadBinary<operator, GR32, (i32 GR32:$src2), GR32>;
1356class AtomicLoadBinaryImm32<SDPatternOperator operator, Immediate imm>
1357  : AtomicLoadBinary<operator, GR32, (i32 imm:$src2), imm>;
1358class AtomicLoadBinaryReg64<SDPatternOperator operator>
1359  : AtomicLoadBinary<operator, GR64, (i64 GR64:$src2), GR64>;
1360class AtomicLoadBinaryImm64<SDPatternOperator operator, Immediate imm>
1361  : AtomicLoadBinary<operator, GR64, (i64 imm:$src2), imm>;
1362
1363// OPERATOR is ATOMIC_SWAPW or an ATOMIC_LOADW_* operation.  PAT and OPERAND
1364// describe the second (non-memory) operand.
1365class AtomicLoadWBinary<SDPatternOperator operator, dag pat,
1366                        DAGOperand operand>
1367  : Pseudo<(outs GR32:$dst),
1368           (ins bdaddr20only:$ptr, operand:$src2, ADDR32:$bitshift,
1369                ADDR32:$negbitshift, uimm32:$bitsize),
1370           [(set GR32:$dst, (operator bdaddr20only:$ptr, pat, ADDR32:$bitshift,
1371                                      ADDR32:$negbitshift, uimm32:$bitsize))]> {
1372  let Defs = [CC];
1373  let Has20BitOffset = 1;
1374  let mayLoad = 1;
1375  let mayStore = 1;
1376  let usesCustomInserter = 1;
1377}
1378
1379// Specializations of AtomicLoadWBinary.
1380class AtomicLoadWBinaryReg<SDPatternOperator operator>
1381  : AtomicLoadWBinary<operator, (i32 GR32:$src2), GR32>;
1382class AtomicLoadWBinaryImm<SDPatternOperator operator, Immediate imm>
1383  : AtomicLoadWBinary<operator, (i32 imm:$src2), imm>;
1384