1//===-- RISCVInstrInfoXCV.td - CORE-V instructions ---------*- tablegen -*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// This file describes the vendor extensions defined by Core-V extensions.
10//
11//===----------------------------------------------------------------------===//
12
13let DecoderNamespace = "XCVbitmanip" in {
14  class CVInstBitManipRII<bits<2> funct2, bits<3> funct3, dag outs, dag ins,
15                      string opcodestr, string argstr>
16      : RVInstIBase<funct3, OPC_CUSTOM_2, outs, ins, opcodestr, argstr> {
17    bits<5> is3;
18    bits<5> is2;
19    let Inst{31-30} = funct2;
20    let Inst{29-25} = is3;
21    let Inst{24-20} = is2;
22  }
23
24  class CVBitManipRII<bits<2> funct2, bits<3> funct3, string opcodestr,
25                      Operand i3type = uimm5>
26      : CVInstBitManipRII<funct2, funct3, (outs GPR:$rd),
27                          (ins GPR:$rs1, i3type:$is3, uimm5:$is2),
28                          opcodestr, "$rd, $rs1, $is3, $is2">;
29
30  class CVBitManipRR<bits<7> funct7, string opcodestr>
31      : RVInstR<funct7, 0b011, OPC_CUSTOM_1, (outs GPR:$rd),
32                (ins GPR:$rs1, GPR:$rs2), opcodestr, "$rd, $rs1, $rs2">;
33
34  class CVBitManipR<bits<7> funct7, string opcodestr>
35      : RVInstR<funct7, 0b011, OPC_CUSTOM_1, (outs GPR:$rd),
36                (ins GPR:$rs1), opcodestr, "$rd, $rs1"> {
37    let rs2 = 0b00000;
38  }
39}
40
41let Predicates = [HasVendorXCVbitmanip, IsRV32],
42    hasSideEffects = 0, mayLoad = 0, mayStore = 0 in {
43  def CV_EXTRACT : CVBitManipRII<0b00, 0b000, "cv.extract">;
44  def CV_EXTRACTU : CVBitManipRII<0b01, 0b000, "cv.extractu">;
45
46  def CV_BCLR : CVBitManipRII<0b00, 0b001, "cv.bclr">;
47  def CV_BSET : CVBitManipRII<0b01, 0b001, "cv.bset">;
48  def CV_BITREV : CVBitManipRII<0b11, 0b001, "cv.bitrev", uimm2>;
49
50  def CV_EXTRACTR : CVBitManipRR<0b0011000, "cv.extractr">;
51  def CV_EXTRACTUR : CVBitManipRR<0b0011001, "cv.extractur">;
52
53  let Constraints = "$rd = $rd_wb" in {
54    def CV_INSERT : CVInstBitManipRII<0b10, 0b000, (outs GPR:$rd_wb),
55                             (ins GPR:$rd, GPR:$rs1, uimm5:$is3, uimm5:$is2),
56                             "cv.insert", "$rd, $rs1, $is3, $is2">;
57    def CV_INSERTR : RVInstR<0b0011010, 0b011, OPC_CUSTOM_1, (outs GPR:$rd_wb),
58                             (ins GPR:$rd, GPR:$rs1, GPR:$rs2),
59                             "cv.insertr", "$rd, $rs1, $rs2">;
60  }
61
62  def CV_BCLRR : CVBitManipRR<0b0011100, "cv.bclrr">;
63  def CV_BSETR : CVBitManipRR<0b0011101, "cv.bsetr">;
64
65  def CV_ROR : CVBitManipRR<0b0100000, "cv.ror">;
66  def CV_FF1 : CVBitManipR<0b0100001, "cv.ff1">;
67  def CV_FL1 : CVBitManipR<0b0100010, "cv.fl1">;
68  def CV_CLB : CVBitManipR<0b0100011, "cv.clb">;
69  def CV_CNT : CVBitManipR<0b0100100, "cv.cnt">;
70}
71
72class CVInstMac<bits<7> funct7, bits<3> funct3, string opcodestr>
73    : RVInstR<funct7, funct3, OPC_CUSTOM_1,
74              (outs GPR:$rd_wb), (ins GPR:$rd, GPR:$rs1, GPR:$rs2),
75              opcodestr, "$rd, $rs1, $rs2"> {
76  let DecoderNamespace = "XCVmac";
77}
78
79class CVInstMacMulN<bits<2> funct2, bits<3> funct3, dag outs, dag ins,
80                    string opcodestr>
81    : RVInstRBase<funct3, OPC_CUSTOM_2, outs, ins, opcodestr,
82                  "$rd, $rs1, $rs2, $imm5"> {
83  bits<5> imm5;
84
85  let Inst{31-30} = funct2;
86  let Inst{29-25} = imm5;
87  let DecoderNamespace = "XCVmac";
88}
89
90class CVInstMacN<bits<2> funct2, bits<3> funct3, string opcodestr>
91    : CVInstMacMulN<funct2, funct3, (outs GPR:$rd_wb),
92                    (ins GPR:$rd, GPR:$rs1, GPR:$rs2, uimm5:$imm5), opcodestr>;
93
94class CVInstMulN<bits<2> funct2, bits<3> funct3, string opcodestr>
95    : CVInstMacMulN<funct2, funct3, (outs GPR:$rd),
96                    (ins GPR:$rs1, GPR:$rs2, uimm5:$imm5), opcodestr>;
97
98let Predicates = [HasVendorXCVmac, IsRV32], hasSideEffects = 0, mayLoad = 0,
99    mayStore = 0, Constraints = "$rd = $rd_wb" in {
100  // 32x32 bit macs
101  def CV_MAC      : CVInstMac<0b1001000, 0b011, "cv.mac">,
102                    Sched<[]>;
103  def CV_MSU      : CVInstMac<0b1001001, 0b011, "cv.msu">,
104                    Sched<[]>;
105
106  // Signed 16x16 bit macs with imm
107  def CV_MACSN    : CVInstMacN<0b00, 0b110, "cv.macsn">,
108                    Sched<[]>;
109  def CV_MACHHSN  : CVInstMacN<0b01, 0b110, "cv.machhsn">,
110                    Sched<[]>;
111  def CV_MACSRN   : CVInstMacN<0b10, 0b110, "cv.macsrn">,
112                    Sched<[]>;
113  def CV_MACHHSRN : CVInstMacN<0b11, 0b110, "cv.machhsrn">,
114                    Sched<[]>;
115
116  // Unsigned 16x16 bit macs with imm
117  def CV_MACUN    : CVInstMacN<0b00, 0b111, "cv.macun">,
118                    Sched<[]>;
119  def CV_MACHHUN  : CVInstMacN<0b01, 0b111, "cv.machhun">,
120                    Sched<[]>;
121  def CV_MACURN   : CVInstMacN<0b10, 0b111, "cv.macurn">,
122                    Sched<[]>;
123  def CV_MACHHURN : CVInstMacN<0b11, 0b111, "cv.machhurn">,
124                    Sched<[]>;
125} // Predicates = [HasVendorXCVmac, IsRV32], hasSideEffects = 0, mayLoad = 0...
126
127let Predicates = [HasVendorXCVmac, IsRV32], hasSideEffects = 0, mayLoad = 0, mayStore = 0 in {
128  // Signed 16x16 bit muls with imm
129  def CV_MULSN    : CVInstMulN<0b00, 0b100, "cv.mulsn">,
130                    Sched<[]>;
131  def CV_MULHHSN  : CVInstMulN<0b01, 0b100, "cv.mulhhsn">,
132                    Sched<[]>;
133  def CV_MULSRN   : CVInstMulN<0b10, 0b100, "cv.mulsrn">,
134                    Sched<[]>;
135  def CV_MULHHSRN : CVInstMulN<0b11, 0b100, "cv.mulhhsrn">,
136                    Sched<[]>;
137
138  // Unsigned 16x16 bit muls with imm
139  def CV_MULUN    : CVInstMulN<0b00, 0b101, "cv.mulun">,
140                    Sched<[]>;
141  def CV_MULHHUN  : CVInstMulN<0b01, 0b101, "cv.mulhhun">,
142                    Sched<[]>;
143  def CV_MULURN   : CVInstMulN<0b10, 0b101, "cv.mulurn">,
144                    Sched<[]>;
145  def CV_MULHHURN : CVInstMulN<0b11, 0b101, "cv.mulhhurn">,
146                    Sched<[]>;
147} // Predicates = [HasVendorXCVmac, IsRV32], hasSideEffects = 0, mayLoad = 0...
148
149let Predicates = [HasVendorXCVmac, IsRV32] in {
150  // Xcvmac Pseudo Instructions
151  // Signed 16x16 bit muls
152  def : InstAlias<"cv.muls $rd1, $rs1, $rs2",
153                  (CV_MULSN GPR:$rd1,   GPR:$rs1, GPR:$rs2, 0)>;
154  def : InstAlias<"cv.mulhhs $rd1, $rs1, $rs2",
155                  (CV_MULHHSN GPR:$rd1, GPR:$rs1, GPR:$rs2, 0)>;
156
157  // Unsigned 16x16 bit muls
158  def : InstAlias<"cv.mulu $rd1, $rs1, $rs2",
159                  (CV_MULUN GPR:$rd1,   GPR:$rs1, GPR:$rs2, 0)>;
160  def : InstAlias<"cv.mulhhu $rd1, $rs1, $rs2",
161                  (CV_MULHHUN GPR:$rd1, GPR:$rs1, GPR:$rs2, 0)>;
162} // Predicates = [HasVendorXCVmac, IsRV32]
163
164let DecoderNamespace = "XCValu" in {
165  class CVInstAluRRI<bits<2> funct2, bits<3> funct3, string opcodestr>
166      : RVInstRBase<funct3, OPC_CUSTOM_2, (outs GPR:$rd),
167                    (ins GPR:$rs1, GPR:$rs2, uimm5:$imm5), opcodestr,
168                    "$rd, $rs1, $rs2, $imm5"> {
169    bits<5> imm5;
170
171    let Inst{31-30} = funct2;
172    let Inst{29-25} = imm5;
173  }
174
175  class CVInstAluRR<bits<7> funct7, bits<3> funct3, string opcodestr>
176    : RVInstR<funct7, funct3, OPC_CUSTOM_1, (outs GPR:$rd),
177              (ins GPR:$rs1, GPR:$rs2), opcodestr, "$rd, $rs1, $rs2">;
178
179  class CVInstAluRRNR<bits<7> funct7, bits<3> funct3, string opcodestr>
180    : RVInstR<funct7, funct3, OPC_CUSTOM_1, (outs GPR:$rd_wb),
181              (ins GPR:$rd, GPR:$rs1, GPR:$rs2), opcodestr, "$rd, $rs1, $rs2">;
182
183  class CVInstAluRI<bits<7> funct7, bits<3> funct3, string opcodestr>
184      : RVInstIBase<funct3, OPC_CUSTOM_1, (outs GPR:$rd),
185                    (ins GPR:$rs1, uimm5:$imm5), opcodestr,
186                    "$rd, $rs1, $imm5"> {
187    bits<5> imm5;
188
189    let Inst{31-25} = funct7;
190    let Inst{24-20} = imm5;
191  }
192
193  class CVInstAluR<bits<7> funct7, bits<3> funct3, string opcodestr>
194    : RVInstR<funct7, funct3, OPC_CUSTOM_1, (outs GPR:$rd), (ins GPR:$rs1),
195              opcodestr, "$rd, $rs1"> {
196     let rs2 = 0b00000;
197  }
198
199} // DecoderNamespace = "XCValu"
200
201let Predicates = [HasVendorXCValu],
202  hasSideEffects = 0, mayLoad = 0, mayStore = 0 in {
203  // General ALU Operations
204  def CV_ABS    : CVInstAluR<0b0101000, 0b011, "cv.abs">,
205                  Sched<[]>;
206  def CV_SLET   : CVInstAluRR<0b0101001, 0b011, "cv.slet">,
207                  Sched<[]>;
208  def CV_SLETU  : CVInstAluRR<0b0101010, 0b011, "cv.sletu">,
209                  Sched<[]>;
210  def CV_MIN    : CVInstAluRR<0b0101011, 0b011, "cv.min">,
211                  Sched<[]>;
212  def CV_MINU   : CVInstAluRR<0b0101100, 0b011, "cv.minu">,
213                  Sched<[]>;
214  def CV_MAX    : CVInstAluRR<0b0101101, 0b011, "cv.max">,
215                  Sched<[]>;
216  def CV_MAXU   : CVInstAluRR<0b0101110, 0b011, "cv.maxu">,
217                  Sched<[]>;
218  def CV_EXTHS  : CVInstAluR<0b0110000, 0b011, "cv.exths">,
219                  Sched<[]>;
220  def CV_EXTHZ  : CVInstAluR<0b0110001, 0b011, "cv.exthz">,
221                  Sched<[]>;
222  def CV_EXTBS  : CVInstAluR<0b0110010, 0b011, "cv.extbs">,
223                  Sched<[]>;
224  def CV_EXTBZ  : CVInstAluR<0b0110011, 0b011, "cv.extbz">,
225                  Sched<[]>;
226
227  def CV_CLIP   : CVInstAluRI<0b0111000, 0b011, "cv.clip">,
228                  Sched<[]>;
229  def CV_CLIPU  : CVInstAluRI<0b0111001, 0b011, "cv.clipu">,
230                  Sched<[]>;
231  def CV_CLIPR  : CVInstAluRR<0b0111010, 0b011, "cv.clipr">,
232                  Sched<[]>;
233  def CV_CLIPUR : CVInstAluRR<0b0111011, 0b011, "cv.clipur">,
234                  Sched<[]>;
235
236  def CV_ADDN   : CVInstAluRRI<0b00, 0b010, "cv.addn">,
237                  Sched<[]>;
238  def CV_ADDUN  : CVInstAluRRI<0b01, 0b010, "cv.addun">,
239                  Sched<[]>;
240  def CV_ADDRN  : CVInstAluRRI<0b10, 0b010, "cv.addrn">,
241                  Sched<[]>;
242  def CV_ADDURN : CVInstAluRRI<0b11, 0b010, "cv.addurn">,
243                  Sched<[]>;
244  def CV_SUBN   : CVInstAluRRI<0b00, 0b011, "cv.subn">,
245                  Sched<[]>;
246  def CV_SUBUN  : CVInstAluRRI<0b01, 0b011, "cv.subun">,
247                  Sched<[]>;
248  def CV_SUBRN  : CVInstAluRRI<0b10, 0b011, "cv.subrn">,
249                  Sched<[]>;
250  def CV_SUBURN : CVInstAluRRI<0b11, 0b011, "cv.suburn">,
251                  Sched<[]>;
252} // Predicates = [HasVendorXCValu],
253  //   hasSideEffects = 0, mayLoad = 0, mayStore = 0
254
255let Predicates = [HasVendorXCValu],
256  hasSideEffects = 0, mayLoad = 0, mayStore = 0,
257  Constraints = "$rd = $rd_wb" in {
258  def CV_ADDNR   : CVInstAluRRNR<0b1000000, 0b011, "cv.addnr">,
259                   Sched<[]>;
260  def CV_ADDUNR  : CVInstAluRRNR<0b1000001, 0b011, "cv.addunr">,
261                   Sched<[]>;
262  def CV_ADDRNR  : CVInstAluRRNR<0b1000010, 0b011, "cv.addrnr">,
263                   Sched<[]>;
264  def CV_ADDURNR : CVInstAluRRNR<0b1000011, 0b011, "cv.addurnr">,
265                   Sched<[]>;
266  def CV_SUBNR   : CVInstAluRRNR<0b1000100, 0b011, "cv.subnr">,
267                   Sched<[]>;
268  def CV_SUBUNR  : CVInstAluRRNR<0b1000101, 0b011, "cv.subunr">,
269                   Sched<[]>;
270  def CV_SUBRNR  : CVInstAluRRNR<0b1000110, 0b011, "cv.subrnr">,
271                   Sched<[]>;
272  def CV_SUBURNR : CVInstAluRRNR<0b1000111, 0b011, "cv.suburnr">,
273                   Sched<[]>;
274
275} // Predicates = [HasVendorXCValu],
276  //   hasSideEffects = 0, mayLoad = 0, mayStore = 0,
277  //   Constraints = "$rd = $rd_wb"
278
279
280class CVInstSIMDRR<bits<5> funct5, bit F, bit funct1, bits<3> funct3,
281                   RISCVOpcode opcode, dag outs,
282                   dag ins, string opcodestr, string argstr>
283    : RVInstRBase<funct3, opcode, outs, ins, opcodestr, argstr> {
284  let Inst{31-27} = funct5;
285  let Inst{26} = F;
286  let Inst{25} = funct1;
287  let DecoderNamespace = "XCVsimd";
288}
289
290class CVInstSIMDRI<bits<5> funct5, bit F, bits<3> funct3, RISCVOpcode opcode,
291                   dag outs, dag ins, string opcodestr, string argstr>
292    : RVInstIBase<funct3, opcode, outs, ins, opcodestr, argstr> {
293  bits<6> imm6;
294
295  let Inst{31-27} = funct5;
296  let Inst{26} = F;
297  let Inst{25} = imm6{0}; // funct1 unused
298  let Inst{24-20} = imm6{5-1};
299  let DecoderNamespace = "XCVsimd";
300}
301
302class CVSIMDRR<bits<5> funct5, bit F, bit funct1, bits<3> funct3,
303               string opcodestr>
304    : CVInstSIMDRR<funct5, F, funct1, funct3, OPC_CUSTOM_3, (outs GPR:$rd),
305              (ins GPR:$rs1, GPR:$rs2), opcodestr, "$rd, $rs1, $rs2">;
306
307class CVSIMDRRWb<bits<5> funct5, bit F, bit funct1, bits<3> funct3,
308                 string opcodestr>
309    : CVInstSIMDRR<funct5, F, funct1, funct3, OPC_CUSTOM_3, (outs GPR:$rd_wb),
310              (ins GPR:$rd, GPR:$rs1, GPR:$rs2), opcodestr, "$rd, $rs1, $rs2"> {
311  let Constraints = "$rd = $rd_wb";
312}
313
314class CVSIMDRI<bits<5> funct5, bit F, bits<3> funct3, string opcodestr>
315    : CVInstSIMDRI<funct5, F, funct3, OPC_CUSTOM_3, (outs GPR:$rd),
316              (ins GPR:$rs1, simm6:$imm6), opcodestr, "$rd, $rs1, $imm6">;
317
318class CVSIMDRIWb<bits<5> funct5, bit F, bits<3> funct3, string opcodestr>
319    : CVInstSIMDRI<funct5, F, funct3, OPC_CUSTOM_3,
320                   (outs GPR:$rd_wb), (ins GPR:$rd, GPR:$rs1, simm6:$imm6),
321                   opcodestr, "$rd, $rs1, $imm6"> {
322  let Constraints = "$rd = $rd_wb";
323}
324
325class CVSIMDRU<bits<5> funct5, bit F, bits<3> funct3, string opcodestr,
326               Operand immtype = uimm6>
327    : CVInstSIMDRI<funct5, F, funct3, OPC_CUSTOM_3,
328                   (outs GPR:$rd), (ins GPR:$rs1, immtype:$imm6),
329                   opcodestr, "$rd, $rs1, $imm6">;
330
331class CVSIMDRUWb<bits<5> funct5, bit F, bits<3> funct3, string opcodestr>
332    : CVInstSIMDRI<funct5, F, funct3, OPC_CUSTOM_3,
333                   (outs GPR:$rd_wb),
334                   (ins GPR:$rd, GPR:$rs1, uimm6:$imm6),
335                   opcodestr, "$rd, $rs1, $imm6"> {
336  let Constraints = "$rd = $rd_wb";
337}
338
339class CVSIMDR<bits<5> funct5, bit F, bit funct1, bits<3> funct3,
340              string opcodestr>
341    : CVInstSIMDRR<funct5, F, funct1, funct3, OPC_CUSTOM_3, (outs GPR:$rd),
342                  (ins GPR:$rs1), opcodestr, "$rd, $rs1"> {
343  let rs2 = 0b00000;
344}
345
346multiclass CVSIMDBinarySigned<bits<5> funct5, bit F, bit funct1, string mnemonic> {
347  def CV_ # NAME # _H : CVSIMDRR<funct5, F, funct1, 0b000, "cv." # mnemonic # ".h">;
348  def CV_ # NAME # _B : CVSIMDRR<funct5, F, funct1, 0b001, "cv." # mnemonic # ".b">;
349  def CV_ # NAME # _SC_H : CVSIMDRR<funct5, F, funct1, 0b100, "cv." # mnemonic # ".sc.h">;
350  def CV_ # NAME # _SC_B : CVSIMDRR<funct5, F, funct1, 0b101, "cv." # mnemonic # ".sc.b">;
351  def CV_ # NAME # _SCI_H : CVSIMDRI<funct5, F, 0b110, "cv." # mnemonic # ".sci.h">;
352  def CV_ # NAME # _SCI_B : CVSIMDRI<funct5, F, 0b111, "cv." # mnemonic # ".sci.b">;
353}
354
355multiclass CVSIMDBinaryUnsigned<bits<5> funct5, bit F, bit funct1, string mnemonic> {
356  def CV_ # NAME # _H : CVSIMDRR<funct5, F, funct1, 0b000, "cv." # mnemonic # ".h">;
357  def CV_ # NAME # _B : CVSIMDRR<funct5, F, funct1, 0b001, "cv." # mnemonic # ".b">;
358  def CV_ # NAME # _SC_H : CVSIMDRR<funct5, F, funct1, 0b100, "cv." # mnemonic # ".sc.h">;
359  def CV_ # NAME # _SC_B : CVSIMDRR<funct5, F, funct1, 0b101, "cv." # mnemonic # ".sc.b">;
360  def CV_ # NAME # _SCI_H : CVSIMDRU<funct5, F, 0b110, "cv." # mnemonic # ".sci.h">;
361  def CV_ # NAME # _SCI_B : CVSIMDRU<funct5, F, 0b111, "cv." # mnemonic # ".sci.b">;
362}
363
364multiclass CVSIMDShift<bits<5> funct5, bit F, bit funct1, string mnemonic> {
365  def CV_ # NAME # _H : CVSIMDRR<funct5, F, funct1, 0b000, "cv." # mnemonic # ".h">;
366  def CV_ # NAME # _B : CVSIMDRR<funct5, F, funct1, 0b001, "cv." # mnemonic # ".b">;
367  def CV_ # NAME # _SC_H : CVSIMDRR<funct5, F, funct1, 0b100, "cv." # mnemonic # ".sc.h">;
368  def CV_ # NAME # _SC_B : CVSIMDRR<funct5, F, funct1, 0b101, "cv." # mnemonic # ".sc.b">;
369  def CV_ # NAME # _SCI_H : CVSIMDRU<funct5, F, 0b110, "cv." # mnemonic # ".sci.h", uimm4>;
370  def CV_ # NAME # _SCI_B : CVSIMDRU<funct5, F, 0b111, "cv." # mnemonic # ".sci.b", uimm3>;
371}
372
373multiclass CVSIMDBinarySignedWb<bits<5> funct5, bit F, bit funct1, string mnemonic> {
374  def CV_ # NAME # _H : CVSIMDRRWb<funct5, F, funct1, 0b000, "cv." # mnemonic # ".h">;
375  def CV_ # NAME # _B : CVSIMDRRWb<funct5, F, funct1, 0b001, "cv." # mnemonic # ".b">;
376  def CV_ # NAME # _SC_H : CVSIMDRRWb<funct5, F, funct1, 0b100, "cv." # mnemonic # ".sc.h">;
377  def CV_ # NAME # _SC_B : CVSIMDRRWb<funct5, F, funct1, 0b101, "cv." # mnemonic # ".sc.b">;
378  def CV_ # NAME # _SCI_H : CVSIMDRIWb<funct5, F, 0b110, "cv." # mnemonic # ".sci.h">;
379  def CV_ # NAME # _SCI_B : CVSIMDRIWb<funct5, F, 0b111, "cv." # mnemonic # ".sci.b">;
380}
381
382multiclass CVSIMDBinaryUnsignedWb<bits<5> funct5, bit F, bit funct1, string mnemonic> {
383  def CV_ # NAME # _H : CVSIMDRRWb<funct5, F, funct1, 0b000, "cv." # mnemonic # ".h">;
384  def CV_ # NAME # _B : CVSIMDRRWb<funct5, F, funct1, 0b001, "cv." # mnemonic # ".b">;
385  def CV_ # NAME # _SC_H : CVSIMDRRWb<funct5, F, funct1, 0b100, "cv." # mnemonic # ".sc.h">;
386  def CV_ # NAME # _SC_B : CVSIMDRRWb<funct5, F, funct1, 0b101, "cv." # mnemonic # ".sc.b">;
387  def CV_ # NAME # _SCI_H : CVSIMDRUWb<funct5, F, 0b110, "cv." # mnemonic # ".sci.h">;
388  def CV_ # NAME # _SCI_B : CVSIMDRUWb<funct5, F, 0b111, "cv." # mnemonic # ".sci.b">;
389}
390
391
392let Predicates = [HasVendorXCVsimd, IsRV32],
393    hasSideEffects = 0, mayLoad = 0, mayStore = 0 in {
394  defm ADD :    CVSIMDBinarySigned<0b00000, 0, 0, "add">;
395  defm SUB :    CVSIMDBinarySigned<0b00001, 0, 0, "sub">;
396  defm AVG :    CVSIMDBinarySigned<0b00010, 0, 0, "avg">;
397  defm AVGU : CVSIMDBinaryUnsigned<0b00011, 0, 0, "avgu">;
398  defm MIN :    CVSIMDBinarySigned<0b00100, 0, 0, "min">;
399  defm MINU : CVSIMDBinaryUnsigned<0b00101, 0, 0, "minu">;
400  defm MAX :    CVSIMDBinarySigned<0b00110, 0, 0, "max">;
401  defm MAXU : CVSIMDBinaryUnsigned<0b00111, 0, 0, "maxu">;
402  defm SRL :           CVSIMDShift<0b01000, 0, 0, "srl">;
403  defm SRA :           CVSIMDShift<0b01001, 0, 0, "sra">;
404  defm SLL :           CVSIMDShift<0b01010, 0, 0, "sll">;
405  defm OR :     CVSIMDBinarySigned<0b01011, 0, 0, "or">;
406  defm XOR :    CVSIMDBinarySigned<0b01100, 0, 0, "xor">;
407  defm AND :    CVSIMDBinarySigned<0b01101, 0, 0, "and">;
408
409  def CV_ABS_H :    CVSIMDR<0b01110, 0, 0, 0b000, "cv.abs.h">;
410  def CV_ABS_B :    CVSIMDR<0b01110, 0, 0, 0b001, "cv.abs.b">;
411
412  // 0b01111xx: UNDEF
413
414  defm DOTUP :   CVSIMDBinaryUnsigned<0b10000, 0, 0, "dotup">;
415  defm DOTUSP :  CVSIMDBinarySigned<0b10001, 0, 0, "dotusp">;
416  defm DOTSP :   CVSIMDBinarySigned<0b10010, 0, 0, "dotsp">;
417  defm SDOTUP :  CVSIMDBinaryUnsignedWb<0b10011, 0, 0, "sdotup">;
418  defm SDOTUSP : CVSIMDBinarySignedWb<0b10100, 0, 0, "sdotusp">;
419  defm SDOTSP :  CVSIMDBinarySignedWb<0b10101, 0, 0, "sdotsp">;
420
421  // 0b10110xx: UNDEF
422
423  def CV_EXTRACT_H :    CVSIMDRU<0b10111, 0, 0b000, "cv.extract.h">;
424  def CV_EXTRACT_B :    CVSIMDRU<0b10111, 0, 0b001, "cv.extract.b">;
425  def CV_EXTRACTU_H :   CVSIMDRU<0b10111, 0, 0b010, "cv.extractu.h">;
426  def CV_EXTRACTU_B :   CVSIMDRU<0b10111, 0, 0b011, "cv.extractu.b">;
427  def CV_INSERT_H :     CVSIMDRUWb<0b10111, 0, 0b100, "cv.insert.h">;
428  def CV_INSERT_B :     CVSIMDRUWb<0b10111, 0, 0b101, "cv.insert.b">;
429
430  def CV_SHUFFLE_H :    CVSIMDRR<0b11000, 0, 0, 0b000, "cv.shuffle.h">;
431  def CV_SHUFFLE_B :    CVSIMDRR<0b11000, 0, 0, 0b001, "cv.shuffle.b">;
432  def CV_SHUFFLE_SCI_H :   CVSIMDRU<0b11000, 0, 0b110, "cv.shuffle.sci.h">;
433  def CV_SHUFFLEI0_SCI_B : CVSIMDRU<0b11000, 0, 0b111, "cv.shufflei0.sci.b">;
434
435  def CV_SHUFFLEI1_SCI_B : CVSIMDRU<0b11001, 0, 0b111, "cv.shufflei1.sci.b">;
436
437  def CV_SHUFFLEI2_SCI_B : CVSIMDRU<0b11010, 0, 0b111, "cv.shufflei2.sci.b">;
438
439  def CV_SHUFFLEI3_SCI_B : CVSIMDRU<0b11011, 0, 0b111, "cv.shufflei3.sci.b">;
440
441  def CV_SHUFFLE2_H :    CVSIMDRRWb<0b11100, 0, 0, 0b000, "cv.shuffle2.h">;
442  def CV_SHUFFLE2_B :    CVSIMDRRWb<0b11100, 0, 0, 0b001, "cv.shuffle2.b">;
443
444  // 0b11101xx: UNDEF
445
446  def CV_PACK :      CVSIMDRR<0b11110, 0, 0, 0b000, "cv.pack">;
447  def CV_PACK_H :    CVSIMDRR<0b11110, 0, 1, 0b000, "cv.pack.h">;
448
449  def CV_PACKHI_B : CVSIMDRRWb<0b11111, 0, 1, 0b001, "cv.packhi.b">;
450  def CV_PACKLO_B : CVSIMDRRWb<0b11111, 0, 0, 0b001, "cv.packlo.b">;
451
452  defm CMPEQ :  CVSIMDBinarySigned<0b00000, 1, 0, "cmpeq">;
453  defm CMPNE :  CVSIMDBinarySigned<0b00001, 1, 0, "cmpne">;
454  defm CMPGT :  CVSIMDBinarySigned<0b00010, 1, 0, "cmpgt">;
455  defm CMPGE :  CVSIMDBinarySigned<0b00011, 1, 0, "cmpge">;
456  defm CMPLT :  CVSIMDBinarySigned<0b00100, 1, 0, "cmplt">;
457  defm CMPLE :  CVSIMDBinarySigned<0b00101, 1, 0, "cmple">;
458  defm CMPGTU : CVSIMDBinaryUnsigned<0b00110, 1, 0, "cmpgtu">;
459  defm CMPGEU : CVSIMDBinaryUnsigned<0b00111, 1, 0, "cmpgeu">;
460  defm CMPLTU : CVSIMDBinaryUnsigned<0b01000, 1, 0, "cmpltu">;
461  defm CMPLEU : CVSIMDBinaryUnsigned<0b01001, 1, 0, "cmpleu">;
462
463  def CV_CPLXMUL_R :      CVSIMDRRWb<0b01010, 1, 0, 0b000, "cv.cplxmul.r">;
464  def CV_CPLXMUL_I :      CVSIMDRRWb<0b01010, 1, 1, 0b000, "cv.cplxmul.i">;
465  def CV_CPLXMUL_R_DIV2 : CVSIMDRRWb<0b01010, 1, 0, 0b010, "cv.cplxmul.r.div2">;
466  def CV_CPLXMUL_I_DIV2 : CVSIMDRRWb<0b01010, 1, 1, 0b010, "cv.cplxmul.i.div2">;
467  def CV_CPLXMUL_R_DIV4 : CVSIMDRRWb<0b01010, 1, 0, 0b100, "cv.cplxmul.r.div4">;
468  def CV_CPLXMUL_I_DIV4 : CVSIMDRRWb<0b01010, 1, 1, 0b100, "cv.cplxmul.i.div4">;
469  def CV_CPLXMUL_R_DIV8 : CVSIMDRRWb<0b01010, 1, 0, 0b110, "cv.cplxmul.r.div8">;
470  def CV_CPLXMUL_I_DIV8 : CVSIMDRRWb<0b01010, 1, 1, 0b110, "cv.cplxmul.i.div8">;
471
472  def CV_CPLXCONJ :    CVSIMDR<0b01011, 1, 0, 0b000, "cv.cplxconj">;
473
474  // 0b01011xx: UNDEF
475
476  def CV_SUBROTMJ :      CVSIMDRR<0b01100, 1, 0, 0b000, "cv.subrotmj">;
477  def CV_SUBROTMJ_DIV2 : CVSIMDRR<0b01100, 1, 0, 0b010, "cv.subrotmj.div2">;
478  def CV_SUBROTMJ_DIV4 : CVSIMDRR<0b01100, 1, 0, 0b100, "cv.subrotmj.div4">;
479  def CV_SUBROTMJ_DIV8 : CVSIMDRR<0b01100, 1, 0, 0b110, "cv.subrotmj.div8">;
480
481  def CV_ADD_DIV2 :    CVSIMDRR<0b01101, 1, 0, 0b010, "cv.add.div2">;
482  def CV_ADD_DIV4 :    CVSIMDRR<0b01101, 1, 0, 0b100, "cv.add.div4">;
483  def CV_ADD_DIV8 :    CVSIMDRR<0b01101, 1, 0, 0b110, "cv.add.div8">;
484
485  def CV_SUB_DIV2 :    CVSIMDRR<0b01110, 1, 0, 0b010, "cv.sub.div2">;
486  def CV_SUB_DIV4 :    CVSIMDRR<0b01110, 1, 0, 0b100, "cv.sub.div4">;
487  def CV_SUB_DIV8 :    CVSIMDRR<0b01110, 1, 0, 0b110, "cv.sub.div8">;
488}
489
490class CVInstImmBranch<bits<3> funct3, dag outs, dag ins,
491                      string opcodestr, string argstr>
492    : RVInstB<funct3, OPC_CUSTOM_0, outs, ins, opcodestr, argstr> {
493  bits<5> imm5;
494  let rs2 = imm5;
495  let DecoderNamespace = "XCVbi";
496}
497
498let Predicates = [HasVendorXCVbi, IsRV32], hasSideEffects = 0, mayLoad = 0,
499    mayStore = 0, isBranch = 1, isTerminator = 1 in {
500  // Immediate branching operations
501  def CV_BEQIMM : CVInstImmBranch<0b110, (outs),
502        (ins GPR:$rs1, simm5:$imm5, simm13_lsb0:$imm12),
503        "cv.beqimm", "$rs1, $imm5, $imm12">, Sched<[]>;
504  def CV_BNEIMM : CVInstImmBranch<0b111, (outs),
505        (ins GPR:$rs1, simm5:$imm5, simm13_lsb0:$imm12),
506        "cv.bneimm", "$rs1, $imm5, $imm12">, Sched<[]>;
507}
508
509def CVrrAsmOperand : AsmOperandClass {
510  let Name = "RegReg";
511  let ParserMethod = "parseRegReg";
512  let DiagnosticType = "InvalidRegReg";
513}
514
515def CVrr : Operand<OtherVT> {
516   let ParserMatchClass = CVrrAsmOperand;
517   let EncoderMethod =  "getRegReg";
518   let DecoderMethod = "decodeRegReg";
519   let PrintMethod = "printRegReg";
520}
521
522class CVLoad_ri_inc<bits<3> funct3, string opcodestr>
523    : RVInstI<funct3, OPC_CUSTOM_0, (outs GPR:$rd, GPR:$rs1_wb), (ins GPRMem:$rs1, simm12:$imm12),
524              opcodestr, "$rd, (${rs1}), ${imm12}"> {
525  let Constraints = "$rs1_wb = $rs1";
526  let DecoderNamespace = "XCVmem";
527}
528
529class CVLoad_rr_inc<bits<7> funct7, bits<3> funct3, string opcodestr>
530    : RVInstR<funct7, funct3, OPC_CUSTOM_1, (outs GPR:$rd, GPR:$rs1_wb), (ins GPRMem:$rs1, GPR:$rs2),
531              opcodestr, "$rd, (${rs1}), ${rs2}"> {
532  let Constraints = "$rs1_wb = $rs1";
533  let DecoderNamespace = "XCVmem";
534}
535
536class CVLoad_rr<bits<7> funct7, bits<3> funct3, string opcodestr>
537    : RVInstR<funct7, funct3, OPC_CUSTOM_1, (outs GPR:$rd), (ins CVrr:$cvrr),
538              opcodestr, "$rd, $cvrr"> {
539  bits<5> rd;
540  bits<10> cvrr;
541
542  let Inst{31-25} = funct7;
543  let Inst{24-20} = cvrr{4-0};
544  let Inst{19-15} = cvrr{9-5};
545  let Inst{14-12} = funct3;
546  let Inst{11-7} = rd;
547  let DecoderNamespace = "XCVmem";
548}
549
550let Predicates = [HasVendorXCVmem, IsRV32], hasSideEffects = 0,
551                 mayLoad = 1, mayStore = 0, Constraints = "$rs1_wb = $rs1" in {
552  // Register-Immediate load with post-increment
553  def CV_LB_ri_inc  : CVLoad_ri_inc<0b000, "cv.lb">;
554  def CV_LBU_ri_inc : CVLoad_ri_inc<0b100, "cv.lbu">;
555  def CV_LH_ri_inc  : CVLoad_ri_inc<0b001, "cv.lh">;
556  def CV_LHU_ri_inc : CVLoad_ri_inc<0b101, "cv.lhu">;
557  def CV_LW_ri_inc  : CVLoad_ri_inc<0b010, "cv.lw">;
558
559  // Register-Register load with post-increment
560  def CV_LB_rr_inc  : CVLoad_rr_inc<0b0000000, 0b011, "cv.lb">;
561  def CV_LBU_rr_inc : CVLoad_rr_inc<0b0001000, 0b011, "cv.lbu">;
562  def CV_LH_rr_inc  : CVLoad_rr_inc<0b0000001, 0b011, "cv.lh">;
563  def CV_LHU_rr_inc : CVLoad_rr_inc<0b0001001, 0b011, "cv.lhu">;
564  def CV_LW_rr_inc  : CVLoad_rr_inc<0b0000010, 0b011, "cv.lw">;
565}
566
567let Predicates = [HasVendorXCVmem, IsRV32], hasSideEffects = 0,
568                 mayLoad = 1, mayStore = 0 in {
569  // Register-Register load
570  def CV_LB_rr  : CVLoad_rr<0b0000100, 0b011, "cv.lb">;
571  def CV_LBU_rr : CVLoad_rr<0b0001100, 0b011, "cv.lbu">;
572  def CV_LH_rr  : CVLoad_rr<0b0000101, 0b011, "cv.lh">;
573  def CV_LHU_rr : CVLoad_rr<0b0001101, 0b011, "cv.lhu">;
574  def CV_LW_rr  : CVLoad_rr<0b0000110, 0b011, "cv.lw">;
575}
576
577class CVStore_ri_inc<bits<3> funct3, string opcodestr>
578    : RVInstS<funct3, OPC_CUSTOM_1, (outs GPR:$rs1_wb),
579              (ins GPR:$rs2, GPR:$rs1, simm12:$imm12),
580              opcodestr, "$rs2, (${rs1}), ${imm12}"> {
581  let Constraints = "$rs1_wb = $rs1";
582  let DecoderNamespace = "XCVmem";
583}
584
585class CVStore_rr_inc<bits<3> funct3, bits<7> funct7, dag outs, dag ins,
586                     string opcodestr, string argstr>
587    : RVInst<outs, ins, opcodestr, argstr, [], InstFormatOther> {
588  bits<5> rs3;
589  bits<5> rs2;
590  bits<5> rs1;
591
592  let Inst{31-25} = funct7;
593  let Inst{24-20} = rs2;
594  let Inst{19-15} = rs1;
595  let Inst{14-12} = funct3;
596  let Inst{11-7} = rs3;
597  let Inst{6-0} = OPC_CUSTOM_1.Value;
598  let DecoderNamespace = "XCVmem";
599}
600
601
602class CVStore_rr<bits<3> funct3, bits<7> funct7, dag outs, dag ins,
603                     string opcodestr, string argstr>
604    : RVInst<outs, ins, opcodestr, argstr, [], InstFormatOther> {
605  bits<5> rs2;
606  bits<10> cvrr;
607
608  let Inst{31-25} = funct7;
609  let Inst{24-20} = rs2;
610  let Inst{19-15} = cvrr{9-5};
611  let Inst{14-12} = funct3;
612  let Inst{11-7} = cvrr{4-0};
613  let Inst{6-0} = OPC_CUSTOM_1.Value;
614  let DecoderNamespace = "XCVmem";
615}
616
617let Predicates = [HasVendorXCVmem, IsRV32], hasSideEffects = 0,
618                 mayLoad = 0, mayStore = 1, Constraints = "$rs1_wb = $rs1" in {
619  // Register-Immediate store with post-increment
620  def CV_SB_ri_inc : CVStore_ri_inc<0b000, "cv.sb">;
621  def CV_SH_ri_inc : CVStore_ri_inc<0b001, "cv.sh">;
622  def CV_SW_ri_inc : CVStore_ri_inc<0b010, "cv.sw">;
623
624  // Register-Register store with post-increment
625  def CV_SB_rr_inc : CVStore_rr_inc<0b011, 0b0010000,
626                     (outs GPR:$rs1_wb), (ins GPR:$rs2, GPR:$rs1, GPR:$rs3),
627                      "cv.sb", "$rs2, (${rs1}), ${rs3}">;
628  def CV_SH_rr_inc : CVStore_rr_inc<0b011, 0b0010001,
629                     (outs GPR:$rs1_wb), (ins GPR:$rs2, GPR:$rs1, GPR:$rs3),
630                      "cv.sh", "$rs2, (${rs1}), ${rs3}">;
631  def CV_SW_rr_inc : CVStore_rr_inc<0b011, 0b0010010,
632                     (outs GPR:$rs1_wb), (ins GPR:$rs2, GPR:$rs1, GPR:$rs3),
633                      "cv.sw", "$rs2, (${rs1}), ${rs3}">;
634}
635
636
637let Predicates = [HasVendorXCVmem, IsRV32], hasSideEffects = 0,
638                  mayLoad = 0, mayStore = 1 in {
639  // Register-Register store
640  def CV_SB_rr : CVStore_rr<0b011, 0b0010100,
641                 (outs), (ins GPR:$rs2, CVrr:$cvrr),
642                 "cv.sb", "$rs2, $cvrr">;
643  def CV_SH_rr : CVStore_rr<0b011, 0b0010101,
644                 (outs), (ins GPR:$rs2, CVrr:$cvrr),
645                 "cv.sh", "$rs2, $cvrr">;
646  def CV_SW_rr : CVStore_rr<0b011, 0b0010110,
647                 (outs), (ins GPR:$rs2, CVrr:$cvrr),
648                 "cv.sw", "$rs2, $cvrr">;
649}
650
651let DecoderNamespace = "XCVelw" in
652class CVLoad_ri<bits<3> funct3, string opcodestr>
653    : RVInstI<funct3, OPC_CUSTOM_0, (outs GPR:$rd),
654      (ins GPRMem:$rs1, simm12:$imm12), opcodestr, "$rd, ${imm12}(${rs1})">;
655
656let Predicates = [HasVendorXCVelw, IsRV32], hasSideEffects = 0,
657    mayLoad = 1, mayStore = 0 in {
658  // Event load
659  def CV_ELW : CVLoad_ri<0b011, "cv.elw">;
660}
661
662def cv_tuimm2 : TImmLeaf<XLenVT, [{return isUInt<2>(Imm);}]>;
663def cv_tuimm5 : TImmLeaf<XLenVT, [{return isUInt<5>(Imm);}]>;
664def cv_uimm10 : ImmLeaf<XLenVT, [{return isUInt<10>(Imm);}]>;
665
666def CV_LO5: SDNodeXForm<imm, [{
667  return CurDAG->getTargetConstant(N->getZExtValue() & 0x1f, SDLoc(N),
668                                   N->getValueType(0));
669}]>;
670
671def CV_HI5: SDNodeXForm<imm, [{
672  return CurDAG->getTargetConstant(N->getZExtValue() >> 5, SDLoc(N),
673                                   N->getValueType(0));
674}]>;
675
676multiclass PatCoreVBitManip<Intrinsic intr> {
677  def : PatGprGpr<intr, !cast<RVInst>("CV_" # NAME # "R")>;
678  def : Pat<(intr GPR:$rs1, cv_uimm10:$imm),
679            (!cast<RVInst>("CV_" # NAME)
680             GPR:$rs1, (CV_HI5 cv_uimm10:$imm), (CV_LO5 cv_uimm10:$imm))>;
681}
682
683let Predicates = [HasVendorXCVbitmanip, IsRV32] in {
684  defm EXTRACT : PatCoreVBitManip<int_riscv_cv_bitmanip_extract>;
685  defm EXTRACTU : PatCoreVBitManip<int_riscv_cv_bitmanip_extractu>;
686  defm BCLR : PatCoreVBitManip<int_riscv_cv_bitmanip_bclr>;
687  defm BSET : PatCoreVBitManip<int_riscv_cv_bitmanip_bset>;
688
689  def : Pat<(int_riscv_cv_bitmanip_insert GPR:$rs1, GPR:$rs2, GPR:$rd),
690            (CV_INSERTR GPR:$rd, GPR:$rs1, GPR:$rs2)>;
691  def : Pat<(int_riscv_cv_bitmanip_insert GPR:$rs1, cv_uimm10:$imm, GPR:$rd),
692            (CV_INSERT GPR:$rd, GPR:$rs1, (CV_HI5 cv_uimm10:$imm),
693                                          (CV_LO5 cv_uimm10:$imm))>;
694
695  def : PatGpr<cttz, CV_FF1>;
696  def : PatGpr<ctlz, CV_FL1>;
697  def : PatGpr<int_riscv_cv_bitmanip_clb, CV_CLB>;
698  def : PatGpr<ctpop, CV_CNT>;
699
700  def : PatGprGpr<rotr, CV_ROR>;
701
702  def : Pat<(int_riscv_cv_bitmanip_bitrev GPR:$rs1, cv_tuimm5:$pts,
703             cv_tuimm2:$radix),
704            (CV_BITREV GPR:$rs1, cv_tuimm2:$radix, cv_tuimm5:$pts)>;
705  def : Pat<(bitreverse (XLenVT GPR:$rs)), (CV_BITREV GPR:$rs, 0, 0)>;
706}
707