]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - contrib/llvm-project/llvm/lib/Target/RISCV/RISCVInstrInfoB.td
Merge llvm, clang, compiler-rt, libc++, libunwind, lld, lldb and openmp
[FreeBSD/FreeBSD.git] / contrib / llvm-project / llvm / lib / Target / RISCV / RISCVInstrInfoB.td
1 //===-- RISCVInstrInfoB.td - RISC-V 'B' 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 RISC-V instructions from the standard 'B' Bitmanip
10 // extension, version 0.92.
11 // This version is still experimental as the 'B' extension hasn't been
12 // ratified yet.
13 //
14 //===----------------------------------------------------------------------===//
15
16 //===----------------------------------------------------------------------===//
17 // Operand definitions.
18 //===----------------------------------------------------------------------===//
19
20 def UImmLog2XLenHalfAsmOperand : AsmOperandClass {
21   let Name = "UImmLog2XLenHalf";
22   let RenderMethod = "addImmOperands";
23   let DiagnosticType = "InvalidUImmLog2XLenHalf";
24 }
25
26 def shfl_uimm : Operand<XLenVT>, ImmLeaf<XLenVT, [{
27   if (Subtarget->is64Bit())
28     return isUInt<5>(Imm);
29   return isUInt<4>(Imm);
30 }]> {
31   let ParserMatchClass = UImmLog2XLenHalfAsmOperand;
32   let DecoderMethod = "decodeUImmOperand<5>";
33   let MCOperandPredicate = [{
34     int64_t Imm;
35     if (!MCOp.evaluateAsConstantImm(Imm))
36       return false;
37     if (STI.getTargetTriple().isArch64Bit())
38       return  isUInt<5>(Imm);
39     return isUInt<4>(Imm);
40   }];
41 }
42
43 //===----------------------------------------------------------------------===//
44 // Instruction class templates
45 //===----------------------------------------------------------------------===//
46
47 // Some of these templates should be moved to RISCVInstrFormats.td once the B
48 // extension has been ratified.
49
50 let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in
51 class RVBUnary<bits<7> funct7, bits<5> funct5, bits<3> funct3,
52                RISCVOpcode opcode, string opcodestr>
53     : RVInstR<funct7, funct3, opcode, (outs GPR:$rd), (ins GPR:$rs1),
54               opcodestr, "$rd, $rs1"> {
55   let Inst{24-20} = funct5;
56 }
57
58 let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in
59 class RVBALUW_ri<bits<3> funct3, string opcodestr>
60     : RVInstI<funct3, OPC_OP_IMM_32, (outs GPR:$rd),
61               (ins GPR:$rs1, simm12:$imm12), opcodestr, "$rd, $rs1, $imm12">;
62
63 let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in
64 class RVBShift_ri<bits<5> funct5, bits<3> funct3, RISCVOpcode opcode,
65                   string opcodestr>
66     : RVInstI<funct3, opcode, (outs GPR:$rd),
67               (ins GPR:$rs1, uimmlog2xlen:$shamt), opcodestr,
68               "$rd, $rs1, $shamt"> {
69   bits<6> shamt;
70
71   let Inst{31-27} = funct5;
72   // NOTE: the bit op(26)=1 is used to select funnel shifts. All other
73   // shifts operations and operations that live in the encoding space
74   // of the shifts (single bit operations, grev, gorc) use op(26) = 0
75   let Inst{26} = 0;
76   let Inst{25-20} = shamt;
77 }
78
79 let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in
80 class RVBShiftW_ri<bits<7> funct7, bits<3> funct3, RISCVOpcode opcode,
81                    string opcodestr>
82     : RVInstI<funct3, opcode, (outs GPR:$rd), (ins GPR:$rs1, uimm5:$shamt),
83               opcodestr, "$rd, $rs1, $shamt"> {
84   bits<5> shamt;
85
86   let Inst{31-25} = funct7;
87   let Inst{24-20} = shamt;
88 }
89
90 let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in
91 class RVBShfl_ri<bits<6> funct6, bits<3> funct3, RISCVOpcode opcode,
92                  string opcodestr>
93     : RVInstI<funct3, opcode, (outs GPR:$rd), (ins GPR:$rs1, shfl_uimm:$shamt),
94               opcodestr, "$rd, $rs1, $shamt"> {
95   bits<6> shamt;
96
97   let Inst{31-26} = funct6;
98   let Inst{25-20} = shamt;
99 }
100
101 let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in
102 class RVBTernaryR<bits<2> funct2, bits<3> funct3_b, RISCVOpcode opcode,
103                   string opcodestr, string argstr>
104     : RVInstR4<funct2, opcode, (outs GPR:$rd),
105                (ins GPR:$rs1, GPR:$rs2, GPR:$rs3), opcodestr, argstr> {
106   let Inst{14-12} = funct3_b;
107 }
108
109 // Currently used by FSRI only
110 let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in
111 class RVBTernaryImm6<bits<3> funct3_b, RISCVOpcode opcode,
112                      string opcodestr, string argstr>
113     : RVInstR4<0b10, opcode, (outs GPR:$rd),
114                (ins GPR:$rs1, GPR:$rs3, uimmlog2xlen:$shamt),
115                opcodestr, argstr> {
116   bits<6> shamt;
117
118   // NOTE: the first argument of RVInstR4 is hardcoded to 0b10 like the other
119   // funnel shift instructions. The second bit of the argument though is
120   // overwritten by the shamt as the encoding of this particular instruction
121   // requires. This is to obtain op(26) = 1 as required by funnel shift
122   // instructions without the need of a confusing argument in the definition
123   // of the instruction.
124   let Inst{25-20} = shamt;
125   let Inst{14-12} = funct3_b;
126 }
127
128 // Currently used by FSRIW only
129 let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in
130 class RVBTernaryImm5<bits<2> funct2, bits<3> funct3_b, RISCVOpcode opcode,
131                      string opcodestr, string argstr>
132     : RVInstR4<funct2, opcode, (outs GPR:$rd),
133                (ins GPR:$rs1, GPR:$rs3, uimm5:$shamt), opcodestr, argstr> {
134   bits<5> shamt;
135
136   let Inst{24-20} = shamt;
137   let Inst{14-12} = funct3_b;
138 }
139
140 //===----------------------------------------------------------------------===//
141 // Instructions
142 //===----------------------------------------------------------------------===//
143
144 let Predicates = [HasStdExtZbbOrZbp] in {
145 def ANDN  : ALU_rr<0b0100000, 0b111, "andn">, Sched<[]>;
146 def ORN   : ALU_rr<0b0100000, 0b110, "orn">, Sched<[]>;
147 def XNOR  : ALU_rr<0b0100000, 0b100, "xnor">, Sched<[]>;
148 } // Predicates = [HasStdExtZbbOrZbp]
149
150 let Predicates = [HasStdExtZbb] in {
151 def SLO  : ALU_rr<0b0010000, 0b001, "slo">, Sched<[]>;
152 def SRO  : ALU_rr<0b0010000, 0b101, "sro">, Sched<[]>;
153 } // Predicates = [HasStdExtZbb]
154
155 let Predicates = [HasStdExtZbbOrZbp] in {
156 def ROL   : ALU_rr<0b0110000, 0b001, "rol">, Sched<[]>;
157 def ROR   : ALU_rr<0b0110000, 0b101, "ror">, Sched<[]>;
158 } // Predicates = [HasStdExtZbbOrZbp]
159
160 let Predicates = [HasStdExtZbs] in {
161 def SBCLR : ALU_rr<0b0100100, 0b001, "sbclr">, Sched<[]>;
162 def SBSET : ALU_rr<0b0010100, 0b001, "sbset">, Sched<[]>;
163 def SBINV : ALU_rr<0b0110100, 0b001, "sbinv">, Sched<[]>;
164 def SBEXT : ALU_rr<0b0100100, 0b101, "sbext">, Sched<[]>;
165 } // Predicates = [HasStdExtZbs]
166
167 let Predicates = [HasStdExtZbp] in {
168 def GORC : ALU_rr<0b0010100, 0b101, "gorc">, Sched<[]>;
169 def GREV : ALU_rr<0b0110100, 0b101, "grev">, Sched<[]>;
170 } // Predicates = [HasStdExtZbp]
171
172 let Predicates = [HasStdExtZbb] in {
173 def SLOI : RVBShift_ri<0b00100, 0b001, OPC_OP_IMM, "sloi">, Sched<[]>;
174 def SROI : RVBShift_ri<0b00100, 0b101, OPC_OP_IMM, "sroi">, Sched<[]>;
175 } // Predicates = [HasStdExtZbb]
176
177 let Predicates = [HasStdExtZbbOrZbp] in
178 def RORI  : RVBShift_ri<0b01100, 0b101, OPC_OP_IMM, "rori">, Sched<[]>;
179
180 let Predicates = [HasStdExtZbs] in {
181 def SBCLRI : RVBShift_ri<0b01001, 0b001, OPC_OP_IMM, "sbclri">, Sched<[]>;
182 def SBSETI : RVBShift_ri<0b00101, 0b001, OPC_OP_IMM, "sbseti">, Sched<[]>;
183 def SBINVI : RVBShift_ri<0b01101, 0b001, OPC_OP_IMM, "sbinvi">, Sched<[]>;
184 def SBEXTI : RVBShift_ri<0b01001, 0b101, OPC_OP_IMM, "sbexti">, Sched<[]>;
185 } // Predicates = [HasStdExtZbs]
186
187 let Predicates = [HasStdExtZbp] in {
188 def GREVI : RVBShift_ri<0b01101, 0b101, OPC_OP_IMM, "grevi">, Sched<[]>;
189 def GORCI : RVBShift_ri<0b00101, 0b101, OPC_OP_IMM, "gorci">, Sched<[]>;
190 } // Predicates = [HasStdExtZbp]
191
192 let Predicates = [HasStdExtZbt] in {
193 def CMIX : RVBTernaryR<0b11, 0b001, OPC_OP, "cmix", "$rd, $rs2, $rs1, $rs3">,
194            Sched<[]>;
195 def CMOV : RVBTernaryR<0b11, 0b101, OPC_OP, "cmov", "$rd, $rs2, $rs1, $rs3">,
196            Sched<[]>;
197 def FSL  : RVBTernaryR<0b10, 0b001, OPC_OP, "fsl", "$rd, $rs1, $rs3, $rs2">,
198            Sched<[]>;
199 def FSR  : RVBTernaryR<0b10, 0b101, OPC_OP, "fsr", "$rd, $rs1, $rs3, $rs2">,
200            Sched<[]>;
201 def FSRI : RVBTernaryImm6<0b101, OPC_OP_IMM, "fsri",
202                           "$rd, $rs1, $rs3, $shamt">, Sched<[]>;
203 } // Predicates = [HasStdExtZbt]
204
205 let Predicates = [HasStdExtZbb] in {
206 def CLZ  : RVBUnary<0b0110000, 0b00000, 0b001, RISCVOpcode<0b0010011>, "clz">,
207            Sched<[]>;
208 def CTZ  : RVBUnary<0b0110000, 0b00001, 0b001, RISCVOpcode<0b0010011>, "ctz">,
209            Sched<[]>;
210 def PCNT : RVBUnary<0b0110000, 0b00010, 0b001, RISCVOpcode<0b0010011>, "pcnt">,
211            Sched<[]>;
212 } // Predicates = [HasStdExtZbb]
213
214 let Predicates = [HasStdExtZbm, IsRV64] in
215 def BMATFLIP : RVBUnary<0b0110000, 0b00011, 0b001, RISCVOpcode<0b0010011>,
216                         "bmatflip">, Sched<[]>;
217
218 let Predicates = [HasStdExtZbb] in {
219 def SEXTB : RVBUnary<0b0110000, 0b00100, 0b001, RISCVOpcode<0b0010011>,
220                      "sext.b">, Sched<[]>;
221 def SEXTH : RVBUnary<0b0110000, 0b00101, 0b001, RISCVOpcode<0b0010011>,
222                      "sext.h">, Sched<[]>;
223 } // Predicates = [HasStdExtZbb]
224
225 let Predicates = [HasStdExtZbr] in {
226 def CRC32B : RVBUnary<0b0110000, 0b10000, 0b001, RISCVOpcode<0b0010011>,
227                       "crc32.b">, Sched<[]>;
228 def CRC32H : RVBUnary<0b0110000, 0b10001, 0b001, RISCVOpcode<0b0010011>,
229                       "crc32.h">, Sched<[]>;
230 def CRC32W : RVBUnary<0b0110000, 0b10010, 0b001, RISCVOpcode<0b0010011>,
231                       "crc32.w">, Sched<[]>;
232 } // Predicates = [HasStdExtZbr]
233
234 let Predicates = [HasStdExtZbr, IsRV64] in
235 def CRC32D  : RVBUnary<0b0110000, 0b10011, 0b001, RISCVOpcode<0b0010011>,
236                        "crc32.d">, Sched<[]>;
237
238 let Predicates = [HasStdExtZbr] in {
239 def CRC32CB : RVBUnary<0b0110000, 0b11000, 0b001, RISCVOpcode<0b0010011>,
240                        "crc32c.b">, Sched<[]>;
241 def CRC32CH : RVBUnary<0b0110000, 0b11001, 0b001, RISCVOpcode<0b0010011>,
242                        "crc32c.h">, Sched<[]>;
243 def CRC32CW : RVBUnary<0b0110000, 0b11010, 0b001, RISCVOpcode<0b0010011>,
244                        "crc32c.w">, Sched<[]>;
245 } // Predicates = [HasStdExtZbr]
246
247 let Predicates = [HasStdExtZbr, IsRV64] in
248 def CRC32CD : RVBUnary<0b0110000, 0b11011, 0b001, RISCVOpcode<0b0010011>,
249                        "crc32c.d">, Sched<[]>;
250
251 let Predicates = [HasStdExtZbc] in {
252 def CLMUL  : ALU_rr<0b0000101, 0b001, "clmul">, Sched<[]>;
253 def CLMULR : ALU_rr<0b0000101, 0b010, "clmulr">, Sched<[]>;
254 def CLMULH : ALU_rr<0b0000101, 0b011, "clmulh">, Sched<[]>;
255 } // Predicates = [HasStdExtZbc]
256
257 let Predicates = [HasStdExtZbb] in {
258 def MIN  : ALU_rr<0b0000101, 0b100, "min">, Sched<[]>;
259 def MAX  : ALU_rr<0b0000101, 0b101, "max">, Sched<[]>;
260 def MINU : ALU_rr<0b0000101, 0b110, "minu">, Sched<[]>;
261 def MAXU : ALU_rr<0b0000101, 0b111, "maxu">, Sched<[]>;
262 } // Predicates = [HasStdExtZbb]
263
264 let Predicates = [HasStdExtZbp] in {
265 def SHFL   : ALU_rr<0b0000100, 0b001, "shfl">, Sched<[]>;
266 def UNSHFL : ALU_rr<0b0000100, 0b101, "unshfl">, Sched<[]>;
267 } // Predicates = [HasStdExtZbp]
268
269 let Predicates = [HasStdExtZbe] in {
270 def BDEP : ALU_rr<0b0100100, 0b110, "bdep">, Sched<[]>;
271 def BEXT : ALU_rr<0b0000100, 0b110, "bext">, Sched<[]>;
272 } // Predicates = [HasStdExtZbe]
273
274 let Predicates = [HasStdExtZbbOrZbp] in {
275 def PACK  : ALU_rr<0b0000100, 0b100, "pack">, Sched<[]>;
276 def PACKU : ALU_rr<0b0100100, 0b100, "packu">, Sched<[]>;
277 } // Predicates = [HasStdExtZbbOrZbp]
278
279 let Predicates = [HasStdExtZbm, IsRV64] in {
280 def BMATOR   : ALU_rr<0b0000100, 0b011, "bmator">, Sched<[]>;
281 def BMATXOR  : ALU_rr<0b0100100, 0b011, "bmatxor">, Sched<[]>;
282 } // Predicates = [HasStdExtZbm, IsRV64]
283
284 let Predicates = [HasStdExtZbbOrZbp] in
285 def PACKH : ALU_rr<0b0000100, 0b111, "packh">, Sched<[]>;
286
287 let Predicates = [HasStdExtZbf] in
288 def BFP : ALU_rr<0b0100100, 0b111, "bfp">, Sched<[]>;
289
290 let Predicates = [HasStdExtZbp] in {
291 def SHFLI   : RVBShfl_ri<0b000010, 0b001, OPC_OP_IMM, "shfli">, Sched<[]>;
292 def UNSHFLI : RVBShfl_ri<0b000010, 0b101, OPC_OP_IMM, "unshfli">, Sched<[]>;
293 } // Predicates = [HasStdExtZbp]
294
295 let Predicates = [HasStdExtZbb, IsRV64] in {
296 def ADDIWU : RVBALUW_ri<0b100, "addiwu">, Sched<[]>;
297 def SLLIUW : RVBShift_ri<0b00001, 0b001, OPC_OP_IMM_32, "slliu.w">, Sched<[]>;
298 def ADDWU : ALUW_rr<0b0000101, 0b000, "addwu">, Sched<[]>;
299 def SUBWU : ALUW_rr<0b0100101, 0b000, "subwu">, Sched<[]>;
300 def ADDUW : ALUW_rr<0b0000100, 0b000, "addu.w">, Sched<[]>;
301 def SUBUW : ALUW_rr<0b0100100, 0b000, "subu.w">, Sched<[]>;
302 } // Predicates = [HasStdExtZbb, IsRV64]
303
304 let Predicates = [HasStdExtZbb, IsRV64] in {
305 def SLOW   : ALUW_rr<0b0010000, 0b001, "slow">, Sched<[]>;
306 def SROW   : ALUW_rr<0b0010000, 0b101, "srow">, Sched<[]>;
307 } // Predicates = [HasStdExtZbb, IsRV64]
308
309 let Predicates = [HasStdExtZbbOrZbp, IsRV64] in {
310 def ROLW  : ALUW_rr<0b0110000, 0b001, "rolw">, Sched<[]>;
311 def RORW  : ALUW_rr<0b0110000, 0b101, "rorw">, Sched<[]>;
312 } // Predicates = [HasStdExtZbbOrZbp, IsRV64]
313
314 let Predicates = [HasStdExtZbs, IsRV64] in {
315 def SBCLRW : ALUW_rr<0b0100100, 0b001, "sbclrw">, Sched<[]>;
316 def SBSETW : ALUW_rr<0b0010100, 0b001, "sbsetw">, Sched<[]>;
317 def SBINVW : ALUW_rr<0b0110100, 0b001, "sbinvw">, Sched<[]>;
318 def SBEXTW : ALUW_rr<0b0100100, 0b101, "sbextw">, Sched<[]>;
319 } // Predicates = [HasStdExtZbs, IsRV64]
320
321 let Predicates = [HasStdExtZbp, IsRV64] in {
322 def GORCW  : ALUW_rr<0b0010100, 0b101, "gorcw">, Sched<[]>;
323 def GREVW  : ALUW_rr<0b0110100, 0b101, "grevw">, Sched<[]>;
324 } // Predicates = [HasStdExtZbp, IsRV64]
325
326 let Predicates = [HasStdExtZbb, IsRV64] in {
327 def SLOIW  : RVBShiftW_ri<0b0010000, 0b001, OPC_OP_IMM_32, "sloiw">, Sched<[]>;
328 def SROIW  : RVBShiftW_ri<0b0010000, 0b101, OPC_OP_IMM_32, "sroiw">, Sched<[]>;
329 } // Predicates = [HasStdExtZbb, IsRV64]
330
331 let Predicates = [HasStdExtZbbOrZbp, IsRV64] in
332 def RORIW : RVBShiftW_ri<0b0110000, 0b101, OPC_OP_IMM_32, "roriw">, Sched<[]>;
333
334 let Predicates = [HasStdExtZbs, IsRV64] in {
335 def SBCLRIW : RVBShiftW_ri<0b0100100, 0b001, OPC_OP_IMM_32, "sbclriw">,
336               Sched<[]>;
337 def SBSETIW : RVBShiftW_ri<0b0010100, 0b001, OPC_OP_IMM_32, "sbsetiw">,
338               Sched<[]>;
339 def SBINVIW : RVBShiftW_ri<0b0110100, 0b001, OPC_OP_IMM_32, "sbinviw">,
340               Sched<[]>;
341 } // Predicates = [HasStdExtZbs, IsRV64]
342
343 let Predicates = [HasStdExtZbp, IsRV64] in {
344 def GORCIW : RVBShiftW_ri<0b0010100, 0b101, OPC_OP_IMM_32, "gorciw">, Sched<[]>;
345 def GREVIW : RVBShiftW_ri<0b0110100, 0b101, OPC_OP_IMM_32, "greviw">, Sched<[]>;
346 } // Predicates = [HasStdExtZbp, IsRV64]
347
348 let Predicates = [HasStdExtZbt, IsRV64] in {
349 def FSLW  : RVBTernaryR<0b10, 0b001, OPC_OP_32,
350                         "fslw", "$rd, $rs1, $rs3, $rs2">, Sched<[]>;
351 def FSRW  : RVBTernaryR<0b10, 0b101, OPC_OP_32, "fsrw",
352                         "$rd, $rs1, $rs3, $rs2">, Sched<[]>;
353 def FSRIW : RVBTernaryImm5<0b10, 0b101, OPC_OP_IMM_32,
354                            "fsriw", "$rd, $rs1, $rs3, $shamt">, Sched<[]>;
355 } // Predicates = [HasStdExtZbt, IsRV64]
356
357 let Predicates = [HasStdExtZbb, IsRV64] in {
358 def CLZW   : RVBUnary<0b0110000, 0b00000, 0b001, RISCVOpcode<0b0011011>,
359                       "clzw">, Sched<[]>;
360 def CTZW   : RVBUnary<0b0110000, 0b00001, 0b001, RISCVOpcode<0b0011011>,
361                       "ctzw">, Sched<[]>;
362 def PCNTW  : RVBUnary<0b0110000, 0b00010, 0b001, RISCVOpcode<0b0011011>,
363                       "pcntw">, Sched<[]>;
364 } // Predicates = [HasStdExtZbb, IsRV64]
365
366 let Predicates = [HasStdExtZbc, IsRV64] in {
367 def CLMULW  : ALUW_rr<0b0000101, 0b001, "clmulw">, Sched<[]>;
368 def CLMULRW : ALUW_rr<0b0000101, 0b010, "clmulrw">, Sched<[]>;
369 def CLMULHW : ALUW_rr<0b0000101, 0b011, "clmulhw">, Sched<[]>;
370 } // Predicates = [HasStdExtZbc, IsRV64]
371
372 let Predicates = [HasStdExtZbp, IsRV64] in {
373 def SHFLW   : ALUW_rr<0b0000100, 0b001, "shflw">, Sched<[]>;
374 def UNSHFLW : ALUW_rr<0b0000100, 0b101, "unshflw">, Sched<[]>;
375 } // Predicates = [HasStdExtZbp, IsRV64]
376
377 let Predicates = [HasStdExtZbe, IsRV64] in {
378 def BDEPW : ALUW_rr<0b0100100, 0b110, "bdepw">, Sched<[]>;
379 def BEXTW : ALUW_rr<0b0000100, 0b110, "bextw">, Sched<[]>;
380 } // Predicates = [HasStdExtZbe, IsRV64]
381
382 let Predicates = [HasStdExtZbbOrZbp, IsRV64] in {
383 def PACKW  : ALUW_rr<0b0000100, 0b100, "packw">, Sched<[]>;
384 def PACKUW : ALUW_rr<0b0100100, 0b100, "packuw">, Sched<[]>;
385 } // Predicates = [HasStdExtZbbOrZbp, IsRV64]
386
387 let Predicates = [HasStdExtZbf, IsRV64] in
388 def BFPW : ALUW_rr<0b0100100, 0b111, "bfpw">, Sched<[]>;
389
390 //===----------------------------------------------------------------------===//
391 // Future compressed instructions
392 //===----------------------------------------------------------------------===//
393
394 // The presence of these instructions in the B extension is purely experimental
395 // and they should be moved to the C extension as soon as they are ratified.
396
397 let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in
398 class RVBInstC<bits<2> funct2, string opcodestr>
399     : RVInst16<(outs GPRC:$rs_wb), (ins GPRC:$rs), opcodestr, "$rs", [],
400                InstFormatCR> {
401   bits<3> rs;
402   let Constraints = "$rs = $rs_wb";
403
404   let Inst{15-12} = 0b0110;
405   let Inst{11-10} = funct2;
406   let Inst{9-7} = rs;
407   let Inst{6-0} = 0b0000001;
408 }
409
410 // The namespace RVBC exists to avoid encoding conflicts with the compressed
411 // instructions c.addi16sp and c.lui already implemented in the C extension.
412
413 let DecoderNamespace = "RVBC", Predicates = [HasStdExtZbproposedc, HasStdExtC] in {
414 def C_NOT : RVBInstC<0b00, "c.not">, Sched<[]>;
415 def C_NEG : RVBInstC<0b01, "c.neg">, Sched<[]>;
416 } // DecoderNamespace = "RVBC", Predicates = [HasStdExtZbproposedc, HasStdExtC]
417
418 let DecoderNamespace = "RVBC", Predicates = [HasStdExtZbproposedc, HasStdExtZbbOrZbp, HasStdExtC, IsRV64] in
419 def C_ZEXTW : RVBInstC<0b10, "c.zext.w">, Sched<[]>;
420
421 //===----------------------------------------------------------------------===//
422 // Pseudo Instructions
423 //===----------------------------------------------------------------------===//
424
425 let Predicates = [HasStdExtZbb, IsRV32] in {
426 def : InstAlias<"zext.b $rd, $rs", (ANDI GPR:$rd, GPR:$rs, 0xFF)>;
427 def : InstAlias<"zext.h $rd, $rs", (PACK GPR:$rd, GPR:$rs, X0)>;
428 } // Predicates = [HasStdExtZbb, IsRV32]
429
430 let Predicates = [HasStdExtZbb, IsRV64] in {
431 def : InstAlias<"zext.b $rd, $rs", (ANDI GPR:$rd, GPR:$rs, 0xFF)>;
432 def : InstAlias<"zext.h $rd, $rs", (PACKW GPR:$rd, GPR:$rs, X0)>;
433 def : InstAlias<"zext.w $rd, $rs", (PACK GPR:$rd, GPR:$rs, X0)>;
434 } // Predicates = [HasStdExtZbb, IsRV64]
435
436 let Predicates = [HasStdExtZbbOrZbp] in {
437 def : InstAlias<"rev.p $rd, $rs",  (GREVI GPR:$rd, GPR:$rs, 0b00001)>,
438       Sched<[]>;
439 def : InstAlias<"rev2.n $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b00010)>,
440       Sched<[]>;
441 def : InstAlias<"rev.n $rd, $rs",  (GREVI GPR:$rd, GPR:$rs, 0b00011)>,
442       Sched<[]>;
443 def : InstAlias<"rev4.b $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b00100)>,
444       Sched<[]>;
445 def : InstAlias<"rev2.b $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b00110)>,
446       Sched<[]>;
447 def : InstAlias<"rev.b $rd, $rs",  (GREVI GPR:$rd, GPR:$rs, 0b00111)>,
448       Sched<[]>;
449 def : InstAlias<"rev8.h $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b01000)>,
450       Sched<[]>;
451 def : InstAlias<"rev4.h $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b01100)>,
452       Sched<[]>;
453 def : InstAlias<"rev2.h $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b01110)>,
454       Sched<[]>;
455 def : InstAlias<"rev.h $rd, $rs",  (GREVI GPR:$rd, GPR:$rs, 0b01111)>,
456       Sched<[]>;
457
458 def : InstAlias<"zip.n $rd, $rs",    (SHFLI   GPR:$rd, GPR:$rs, 0b0001)>,
459       Sched<[]>;
460 def : InstAlias<"unzip.n $rd, $rs",  (UNSHFLI GPR:$rd, GPR:$rs, 0b0001)>,
461       Sched<[]>;
462 def : InstAlias<"zip2.b $rd, $rs",   (SHFLI   GPR:$rd, GPR:$rs, 0b0010)>,
463       Sched<[]>;
464 def : InstAlias<"unzip2.b $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b0010)>,
465       Sched<[]>;
466 def : InstAlias<"zip.b $rd, $rs",    (SHFLI   GPR:$rd, GPR:$rs, 0b0011)>,
467       Sched<[]>;
468 def : InstAlias<"unzip.b $rd, $rs",  (UNSHFLI GPR:$rd, GPR:$rs, 0b0011)>,
469       Sched<[]>;
470 def : InstAlias<"zip4.h $rd, $rs",   (SHFLI   GPR:$rd, GPR:$rs, 0b0100)>,
471       Sched<[]>;
472 def : InstAlias<"unzip4.h $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b0100)>,
473       Sched<[]>;
474 def : InstAlias<"zip2.h $rd, $rs",   (SHFLI   GPR:$rd, GPR:$rs, 0b0110)>,
475       Sched<[]>;
476 def : InstAlias<"unzip2.h $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b0110)>,
477       Sched<[]>;
478 def : InstAlias<"zip.h $rd, $rs",    (SHFLI   GPR:$rd, GPR:$rs, 0b0111)>,
479       Sched<[]>;
480 def : InstAlias<"unzip.h $rd, $rs",  (UNSHFLI GPR:$rd, GPR:$rs, 0b0111)>,
481       Sched<[]>;
482
483 def : InstAlias<"orc.p $rd, $rs",  (GORCI GPR:$rd, GPR:$rs, 0b00001)>,
484       Sched<[]>;
485 def : InstAlias<"orc2.n $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b00010)>,
486       Sched<[]>;
487 def : InstAlias<"orc.n $rd, $rs",  (GORCI GPR:$rd, GPR:$rs, 0b00011)>,
488       Sched<[]>;
489 def : InstAlias<"orc4.b $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b00100)>,
490       Sched<[]>;
491 def : InstAlias<"orc2.b $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b00110)>,
492       Sched<[]>;
493 def : InstAlias<"orc.b $rd, $rs",  (GORCI GPR:$rd, GPR:$rs, 0b00111)>,
494       Sched<[]>;
495 def : InstAlias<"orc8.h $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b01000)>,
496       Sched<[]>;
497 def : InstAlias<"orc4.h $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b01100)>,
498       Sched<[]>;
499 def : InstAlias<"orc2.h $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b01110)>,
500       Sched<[]>;
501 def : InstAlias<"orc.h $rd, $rs",  (GORCI GPR:$rd, GPR:$rs, 0b01111)>,
502       Sched<[]>;
503 } // Predicates = [HasStdExtZbbOrZbp]
504
505 let Predicates = [HasStdExtZbbOrZbp, IsRV32] in {
506 def : InstAlias<"rev16 $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b10000)>, Sched<[]>;
507 def : InstAlias<"rev8 $rd, $rs",  (GREVI GPR:$rd, GPR:$rs, 0b11000)>, Sched<[]>;
508 def : InstAlias<"rev4 $rd, $rs",  (GREVI GPR:$rd, GPR:$rs, 0b11100)>, Sched<[]>;
509 def : InstAlias<"rev2 $rd, $rs",  (GREVI GPR:$rd, GPR:$rs, 0b11110)>, Sched<[]>;
510 def : InstAlias<"rev $rd, $rs",   (GREVI GPR:$rd, GPR:$rs, 0b11111)>, Sched<[]>;
511
512 def : InstAlias<"zip8 $rd, $rs",   (SHFLI   GPR:$rd, GPR:$rs, 0b1000)>,
513       Sched<[]>;
514 def : InstAlias<"unzip8 $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b1000)>,
515       Sched<[]>;
516 def : InstAlias<"zip4 $rd, $rs",   (SHFLI   GPR:$rd, GPR:$rs, 0b1100)>,
517       Sched<[]>;
518 def : InstAlias<"unzip4 $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b1100)>,
519       Sched<[]>;
520 def : InstAlias<"zip2 $rd, $rs",   (SHFLI   GPR:$rd, GPR:$rs, 0b1110)>,
521       Sched<[]>;
522 def : InstAlias<"unzip2 $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b1110)>,
523       Sched<[]>;
524 def : InstAlias<"zip $rd, $rs",    (SHFLI   GPR:$rd, GPR:$rs, 0b1111)>,
525       Sched<[]>;
526 def : InstAlias<"unzip $rd, $rs",  (UNSHFLI GPR:$rd, GPR:$rs, 0b1111)>,
527       Sched<[]>;
528
529 def : InstAlias<"orc16 $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b10000)>, Sched<[]>;
530 def : InstAlias<"orc8 $rd, $rs",  (GORCI GPR:$rd, GPR:$rs, 0b11000)>, Sched<[]>;
531 def : InstAlias<"orc4 $rd, $rs",  (GORCI GPR:$rd, GPR:$rs, 0b11100)>, Sched<[]>;
532 def : InstAlias<"orc2 $rd, $rs",  (GORCI GPR:$rd, GPR:$rs, 0b11110)>, Sched<[]>;
533 def : InstAlias<"orc $rd, $rs",   (GORCI GPR:$rd, GPR:$rs, 0b11111)>, Sched<[]>;
534 } // Predicates = [HasStdExtZbbOrZbp, IsRV32]
535
536 let Predicates = [HasStdExtZbbOrZbp, IsRV64] in {
537 def : InstAlias<"rev16.w $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b010000)>,
538       Sched<[]>;
539 def : InstAlias<"rev8.w $rd, $rs",  (GREVI GPR:$rd, GPR:$rs, 0b011000)>,
540       Sched<[]>;
541 def : InstAlias<"rev4.w $rd, $rs",  (GREVI GPR:$rd, GPR:$rs, 0b011100)>,
542       Sched<[]>;
543 def : InstAlias<"rev2.w $rd, $rs",  (GREVI GPR:$rd, GPR:$rs, 0b011110)>,
544       Sched<[]>;
545 def : InstAlias<"rev.w $rd, $rs",   (GREVI GPR:$rd, GPR:$rs, 0b011111)>,
546       Sched<[]>;
547 def : InstAlias<"rev32 $rd, $rs",   (GREVI GPR:$rd, GPR:$rs, 0b100000)>,
548       Sched<[]>;
549 def : InstAlias<"rev16 $rd, $rs",   (GREVI GPR:$rd, GPR:$rs, 0b110000)>,
550       Sched<[]>;
551 def : InstAlias<"rev8 $rd, $rs",    (GREVI GPR:$rd, GPR:$rs, 0b111000)>,
552       Sched<[]>;
553 def : InstAlias<"rev4 $rd, $rs",    (GREVI GPR:$rd, GPR:$rs, 0b111100)>,
554       Sched<[]>;
555 def : InstAlias<"rev2 $rd, $rs",    (GREVI GPR:$rd, GPR:$rs, 0b111110)>,
556       Sched<[]>;
557 def : InstAlias<"rev $rd, $rs",     (GREVI GPR:$rd, GPR:$rs, 0b111111)>,
558       Sched<[]>;
559
560 def : InstAlias<"zip8.w $rd, $rs",   (SHFLI   GPR:$rd, GPR:$rs, 0b01000)>,
561       Sched<[]>;
562 def : InstAlias<"unzip8.w $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b01000)>,
563       Sched<[]>;
564 def : InstAlias<"zip4.w $rd, $rs",   (SHFLI   GPR:$rd, GPR:$rs, 0b01100)>,
565       Sched<[]>;
566 def : InstAlias<"unzip4.w $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b01100)>,
567       Sched<[]>;
568 def : InstAlias<"zip2.w $rd, $rs",   (SHFLI   GPR:$rd, GPR:$rs, 0b01110)>,
569       Sched<[]>;
570 def : InstAlias<"unzip2.w $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b01110)>,
571       Sched<[]>;
572 def : InstAlias<"zip.w $rd, $rs",    (SHFLI   GPR:$rd, GPR:$rs, 0b01111)>,
573       Sched<[]>;
574 def : InstAlias<"unzip.w $rd, $rs",  (UNSHFLI GPR:$rd, GPR:$rs, 0b01111)>,
575       Sched<[]>;
576 def : InstAlias<"zip16 $rd, $rs",    (SHFLI   GPR:$rd, GPR:$rs, 0b10000)>,
577       Sched<[]>;
578 def : InstAlias<"unzip16 $rd, $rs",  (UNSHFLI GPR:$rd, GPR:$rs, 0b10000)>,
579       Sched<[]>;
580 def : InstAlias<"zip8 $rd, $rs",     (SHFLI   GPR:$rd, GPR:$rs, 0b11000)>,
581       Sched<[]>;
582 def : InstAlias<"unzip8 $rd, $rs",   (UNSHFLI GPR:$rd, GPR:$rs, 0b11000)>,
583       Sched<[]>;
584 def : InstAlias<"zip4 $rd, $rs",     (SHFLI   GPR:$rd, GPR:$rs, 0b11100)>,
585       Sched<[]>;
586 def : InstAlias<"unzip4 $rd, $rs",   (UNSHFLI GPR:$rd, GPR:$rs, 0b11100)>,
587       Sched<[]>;
588 def : InstAlias<"zip2 $rd, $rs",     (SHFLI   GPR:$rd, GPR:$rs, 0b11110)>,
589       Sched<[]>;
590 def : InstAlias<"unzip2 $rd, $rs",   (UNSHFLI GPR:$rd, GPR:$rs, 0b11110)>,
591       Sched<[]>;
592 def : InstAlias<"zip $rd, $rs",      (SHFLI   GPR:$rd, GPR:$rs, 0b11111)>,
593       Sched<[]>;
594 def : InstAlias<"unzip $rd, $rs",    (UNSHFLI GPR:$rd, GPR:$rs, 0b11111)>,
595       Sched<[]>;
596
597 def : InstAlias<"orc16.w $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b010000)>,
598       Sched<[]>;
599 def : InstAlias<"orc8.w $rd, $rs",  (GORCI GPR:$rd, GPR:$rs, 0b011000)>,
600       Sched<[]>;
601 def : InstAlias<"orc4.w $rd, $rs",  (GORCI GPR:$rd, GPR:$rs, 0b011100)>,
602       Sched<[]>;
603 def : InstAlias<"orc2.w $rd, $rs",  (GORCI GPR:$rd, GPR:$rs, 0b011110)>,
604       Sched<[]>;
605 def : InstAlias<"orc.w $rd, $rs",   (GORCI GPR:$rd, GPR:$rs, 0b011111)>,
606       Sched<[]>;
607 def : InstAlias<"orc32 $rd, $rs",   (GORCI GPR:$rd, GPR:$rs, 0b100000)>,
608       Sched<[]>;
609 def : InstAlias<"orc16 $rd, $rs",   (GORCI GPR:$rd, GPR:$rs, 0b110000)>,
610       Sched<[]>;
611 def : InstAlias<"orc8 $rd, $rs",    (GORCI GPR:$rd, GPR:$rs, 0b111000)>,
612       Sched<[]>;
613 def : InstAlias<"orc4 $rd, $rs",    (GORCI GPR:$rd, GPR:$rs, 0b111100)>,
614       Sched<[]>;
615 def : InstAlias<"orc2 $rd, $rs",    (GORCI GPR:$rd, GPR:$rs, 0b111110)>,
616       Sched<[]>;
617 def : InstAlias<"orc $rd, $rs",     (GORCI GPR:$rd, GPR:$rs, 0b111111)>,
618       Sched<[]>;
619 } // Predicates = [HasStdExtZbbOrZbp, IsRV64]
620
621 //===----------------------------------------------------------------------===//
622 // Compressed Instruction patterns
623 //===----------------------------------------------------------------------===//
624 let Predicates = [HasStdExtZbproposedc, HasStdExtC] in {
625 def : CompressPat<(XORI GPRC:$rs1, GPRC:$rs1, -1),
626                   (C_NOT GPRC:$rs1)>;
627 def : CompressPat<(SUB GPRC:$rs1, X0, GPRC:$rs1),
628                   (C_NEG GPRC:$rs1)>;
629 } // Predicates = [HasStdExtZbproposedc, HasStdExtC]
630
631 let Predicates = [HasStdExtZbproposedc, HasStdExtZbbOrZbp, HasStdExtC, IsRV64] in {
632 def : CompressPat<(PACK GPRC:$rs1, GPRC:$rs1, X0),
633                   (C_ZEXTW GPRC:$rs1)>;
634 } // Predicates = [HasStdExtZbproposedc, HasStdExtC, IsRV64]
635
636 //===----------------------------------------------------------------------===//
637 // Codegen patterns
638 //===----------------------------------------------------------------------===//
639 def SLOIPat   : ComplexPattern<XLenVT, 2, "SelectSLOI", [or]>;
640 def SROIPat   : ComplexPattern<XLenVT, 2, "SelectSROI", [or]>;
641 def RORIPat   : ComplexPattern<XLenVT, 2, "SelectRORI", [rotl]>;
642 def SLLIUWPat : ComplexPattern<i64, 2, "SelectSLLIUW", [and]>;
643 def SLOIWPat  : ComplexPattern<i64, 2, "SelectSLOIW", [sext_inreg]>;
644 def SROIWPat  : ComplexPattern<i64, 2, "SelectSROIW", [or]>;
645 def RORIWPat  : ComplexPattern<i64, 2, "SelectRORIW", [sext_inreg]>;
646 def FSRIWPat  : ComplexPattern<i64, 3, "SelectFSRIW", [sext_inreg]>;
647
648 let Predicates = [HasStdExtZbbOrZbp] in {
649 def : Pat<(and GPR:$rs1, (not GPR:$rs2)), (ANDN GPR:$rs1, GPR:$rs2)>;
650 def : Pat<(or  GPR:$rs1, (not GPR:$rs2)), (ORN  GPR:$rs1, GPR:$rs2)>;
651 def : Pat<(xor GPR:$rs1, (not GPR:$rs2)), (XNOR GPR:$rs1, GPR:$rs2)>;
652 } // Predicates = [HasStdExtZbbOrZbp]
653
654 let Predicates = [HasStdExtZbb] in {
655 def : Pat<(xor (shl (xor GPR:$rs1, -1), GPR:$rs2), -1),
656           (SLO GPR:$rs1, GPR:$rs2)>;
657 def : Pat<(xor (srl (xor GPR:$rs1, -1), GPR:$rs2), -1),
658           (SRO GPR:$rs1, GPR:$rs2)>;
659 } // Predicates = [HasStdExtZbb]
660
661 let Predicates = [HasStdExtZbbOrZbp] in {
662 def : Pat<(rotl GPR:$rs1, GPR:$rs2), (ROL GPR:$rs1, GPR:$rs2)>;
663 def : Pat<(fshl GPR:$rs1, GPR:$rs1, GPR:$rs2), (ROL GPR:$rs1, GPR:$rs2)>;
664 def : Pat<(rotr GPR:$rs1, GPR:$rs2), (ROR GPR:$rs1, GPR:$rs2)>;
665 def : Pat<(fshr GPR:$rs1, GPR:$rs1, GPR:$rs2), (ROR GPR:$rs1, GPR:$rs2)>;
666 } // Predicates = [HasStdExtZbbOrZbp]
667
668 let Predicates = [HasStdExtZbs, IsRV32] in
669 def : Pat<(and (xor (shl 1, (and GPR:$rs2, 31)), -1), GPR:$rs1),
670           (SBCLR GPR:$rs1, GPR:$rs2)>;
671 let Predicates = [HasStdExtZbs, IsRV64] in
672 def : Pat<(and (xor (shl 1, (and GPR:$rs2, 63)), -1), GPR:$rs1),
673           (SBCLR GPR:$rs1, GPR:$rs2)>;
674
675 let Predicates = [HasStdExtZbs] in
676 def : Pat<(and (rotl -2, GPR:$rs2), GPR:$rs1), (SBCLR GPR:$rs1, GPR:$rs2)>;
677
678 let Predicates = [HasStdExtZbs, IsRV32] in
679 def : Pat<(or (shl 1, (and GPR:$rs2, 31)), GPR:$rs1),
680           (SBSET GPR:$rs1, GPR:$rs2)>;
681 let Predicates = [HasStdExtZbs, IsRV64] in
682 def : Pat<(or (shl 1, (and GPR:$rs2, 63)), GPR:$rs1),
683           (SBSET GPR:$rs1, GPR:$rs2)>;
684
685 let Predicates = [HasStdExtZbs, IsRV32] in
686 def : Pat<(xor (shl 1, (and GPR:$rs2, 31)), GPR:$rs1),
687           (SBINV GPR:$rs1, GPR:$rs2)>;
688 let Predicates = [HasStdExtZbs, IsRV64] in
689 def : Pat<(xor (shl 1, (and GPR:$rs2, 63)), GPR:$rs1),
690           (SBINV GPR:$rs1, GPR:$rs2)>;
691
692 let Predicates = [HasStdExtZbs, IsRV32] in
693 def : Pat<(and (srl GPR:$rs1, (and GPR:$rs2, 31)), 1),
694           (SBEXT GPR:$rs1, GPR:$rs2)>;
695
696 let Predicates = [HasStdExtZbs, IsRV64] in
697 def : Pat<(and (srl GPR:$rs1, (and GPR:$rs2, 63)), 1),
698           (SBEXT GPR:$rs1, GPR:$rs2)>;
699
700 let Predicates = [HasStdExtZbb] in {
701 def : Pat<(SLOIPat GPR:$rs1, uimmlog2xlen:$shamt),
702           (SLOI GPR:$rs1, uimmlog2xlen:$shamt)>;
703 def : Pat<(SROIPat GPR:$rs1, uimmlog2xlen:$shamt),
704           (SROI GPR:$rs1, uimmlog2xlen:$shamt)>;
705 } // Predicates = [HasStdExtZbb]
706
707 // There's no encoding for roli in the current version of the 'B' extension
708 // (v0.92) as it can be implemented with rori by negating the immediate.
709 // For this reason we pattern-match only against rori[w].
710 let Predicates = [HasStdExtZbbOrZbp] in
711 def : Pat<(RORIPat GPR:$rs1, uimmlog2xlen:$shamt),
712           (RORI GPR:$rs1, uimmlog2xlen:$shamt)>;
713
714 // We don't pattern-match sbclri[w], sbseti[w], sbinvi[w] because they are
715 // pattern-matched by simple andi, ori, and xori.
716 let Predicates = [HasStdExtZbs] in
717 def : Pat<(and (srl GPR:$rs1, uimmlog2xlen:$shamt), (XLenVT 1)),
718           (SBEXTI GPR:$rs1, uimmlog2xlen:$shamt)>;
719
720 let Predicates = [HasStdExtZbp, IsRV32] in {
721 def : Pat<(or (or (and (srl GPR:$rs1, (i32 1)), (i32 0x55555555)), GPR:$rs1),
722               (and (shl GPR:$rs1, (i32 1)), (i32 0xAAAAAAAA))),
723           (GORCI GPR:$rs1, (i32 1))>;
724 def : Pat<(or (or (and (srl GPR:$rs1, (i32 2)), (i32 0x33333333)), GPR:$rs1),
725               (and (shl GPR:$rs1, (i32 2)), (i32 0xCCCCCCCC))),
726           (GORCI GPR:$rs1, (i32 2))>;
727 def : Pat<(or (or (and (srl GPR:$rs1, (i32 4)), (i32 0x0F0F0F0F)), GPR:$rs1),
728               (and (shl GPR:$rs1, (i32 4)), (i32 0xF0F0F0F0))),
729           (GORCI GPR:$rs1, (i32 4))>;
730 def : Pat<(or (or (and (srl GPR:$rs1, (i32 8)), (i32 0x00FF00FF)), GPR:$rs1),
731               (and (shl GPR:$rs1, (i32 8)), (i32 0xFF00FF00))),
732           (GORCI GPR:$rs1, (i32 8))>;
733 def : Pat<(or (or (srl GPR:$rs1, (i32 16)), GPR:$rs1),
734               (shl GPR:$rs1, (i32 16))),
735           (GORCI GPR:$rs1, (i32 16))>;
736 } // Predicates = [HasStdExtZbp, IsRV32]
737
738 let Predicates = [HasStdExtZbp, IsRV64] in {
739 def : Pat<(or (or (and (srl GPR:$rs1, (i64 1)), (i64 0x5555555555555555)),
740                    GPR:$rs1),
741               (and (shl GPR:$rs1, (i64 1)), (i64 0xAAAAAAAAAAAAAAAA))),
742           (GORCI GPR:$rs1, (i64 1))>;
743 def : Pat<(or (or (and (srl GPR:$rs1, (i64 2)), (i64 0x3333333333333333)),
744                    GPR:$rs1),
745               (and (shl GPR:$rs1, (i64 2)), (i64 0xCCCCCCCCCCCCCCCC))),
746           (GORCI GPR:$rs1, (i64 2))>;
747 def : Pat<(or (or (and (srl GPR:$rs1, (i64 4)), (i64 0x0F0F0F0F0F0F0F0F)),
748                    GPR:$rs1),
749               (and (shl GPR:$rs1, (i64 4)), (i64 0xF0F0F0F0F0F0F0F0))),
750           (GORCI GPR:$rs1, (i64 4))>;
751 def : Pat<(or (or (and (srl GPR:$rs1, (i64 8)), (i64 0x00FF00FF00FF00FF)),
752                    GPR:$rs1),
753               (and (shl GPR:$rs1, (i64 8)), (i64 0xFF00FF00FF00FF00))),
754           (GORCI GPR:$rs1, (i64 8))>;
755 def : Pat<(or (or (and (srl GPR:$rs1, (i64 16)), (i64 0x0000FFFF0000FFFF)),
756                    GPR:$rs1),
757               (and (shl GPR:$rs1, (i64 16)), (i64 0xFFFF0000FFFF0000))),
758           (GORCI GPR:$rs1, (i64 16))>;
759 def : Pat<(or (or (srl GPR:$rs1, (i64 32)), GPR:$rs1),
760               (shl GPR:$rs1, (i64 32))),
761           (GORCI GPR:$rs1, (i64 32))>;
762 } // Predicates = [HasStdExtZbp, IsRV64]
763
764 let Predicates = [HasStdExtZbp, IsRV32] in {
765 def : Pat<(or (and (shl GPR:$rs1, (i32 1)), (i32 0xAAAAAAAA)),
766               (and (srl GPR:$rs1, (i32 1)), (i32 0x55555555))),
767           (GREVI GPR:$rs1, (i32 1))>;
768 def : Pat<(or (and (shl GPR:$rs1, (i32 2)), (i32 0xCCCCCCCC)),
769               (and (srl GPR:$rs1, (i32 2)), (i32 0x33333333))),
770           (GREVI GPR:$rs1, (i32 2))>;
771 def : Pat<(or (and (shl GPR:$rs1, (i32 4)), (i32 0xF0F0F0F0)),
772               (and (srl GPR:$rs1, (i32 4)), (i32 0x0F0F0F0F))),
773           (GREVI GPR:$rs1, (i32 4))>;
774 def : Pat<(or (and (shl GPR:$rs1, (i32 8)), (i32 0xFF00FF00)),
775               (and (srl GPR:$rs1, (i32 8)), (i32 0x00FF00FF))),
776           (GREVI GPR:$rs1, (i32 8))>;
777 def : Pat<(rotr (bswap GPR:$rs1), (i32 16)), (GREVI GPR:$rs1, (i32 8))>;
778 def : Pat<(or (shl GPR:$rs1, (i32 16)), (srl GPR:$rs1, (i32 16))),
779           (GREVI GPR:$rs1, (i32 16))>;
780 def : Pat<(rotl GPR:$rs1, (i32 16)), (GREVI GPR:$rs1, (i32 16))>;
781 def : Pat<(bswap GPR:$rs1), (GREVI GPR:$rs1, (i32 24))>;
782 def : Pat<(bitreverse GPR:$rs1), (GREVI GPR:$rs1, (i32 31))>;
783 } // Predicates = [HasStdExtZbp, IsRV32]
784
785 let Predicates = [HasStdExtZbp, IsRV64] in {
786 def : Pat<(or (and (shl GPR:$rs1, (i64 1)), (i64 0xAAAAAAAAAAAAAAAA)),
787               (and (srl GPR:$rs1, (i64 1)), (i64 0x5555555555555555))),
788           (GREVI GPR:$rs1, (i64 1))>;
789 def : Pat<(or (and (shl GPR:$rs1, (i64 2)), (i64 0xCCCCCCCCCCCCCCCC)),
790               (and (srl GPR:$rs1, (i64 2)), (i64 0x3333333333333333))),
791           (GREVI GPR:$rs1, (i64 2))>;
792 def : Pat<(or (and (shl GPR:$rs1, (i64 4)), (i64 0xF0F0F0F0F0F0F0F0)),
793               (and (srl GPR:$rs1, (i64 4)), (i64 0x0F0F0F0F0F0F0F0F))),
794           (GREVI GPR:$rs1, (i64 4))>;
795 def : Pat<(or (and (shl GPR:$rs1, (i64 8)), (i64 0xFF00FF00FF00FF00)),
796               (and (srl GPR:$rs1, (i64 8)), (i64 0x00FF00FF00FF00FF))),
797           (GREVI GPR:$rs1, (i64 8))>;
798 def : Pat<(or (and (shl GPR:$rs1, (i64 16)), (i64 0xFFFF0000FFFF0000)),
799               (and (srl GPR:$rs1, (i64 16)), (i64 0x0000FFFF0000FFFF))),
800           (GREVI GPR:$rs1, (i64 16))>;
801 def : Pat<(or (shl GPR:$rs1, (i64 32)), (srl GPR:$rs1, (i64 32))),
802           (GREVI GPR:$rs1, (i64 32))>;
803 def : Pat<(rotl GPR:$rs1, (i64 32)), (GREVI GPR:$rs1, (i64 32))>;
804 def : Pat<(bswap GPR:$rs1), (GREVI GPR:$rs1, (i64 56))>;
805 def : Pat<(bitreverse GPR:$rs1), (GREVI GPR:$rs1, (i64 63))>;
806 } // Predicates = [HasStdExtZbp, IsRV64]
807
808 let Predicates = [HasStdExtZbt] in {
809 def : Pat<(or (and (xor GPR:$rs2, -1), GPR:$rs3), (and GPR:$rs2, GPR:$rs1)),
810           (CMIX GPR:$rs1, GPR:$rs2, GPR:$rs3)>;
811 def : Pat<(riscv_selectcc GPR:$rs2, (XLenVT 0), (XLenVT 17), GPR:$rs3, GPR:$rs1),
812           (CMOV GPR:$rs1, GPR:$rs2, GPR:$rs3)>;
813 def : Pat<(fshl GPR:$rs1, GPR:$rs2, GPR:$rs3),
814           (FSL GPR:$rs1, GPR:$rs2, GPR:$rs3)>;
815 def : Pat<(fshr GPR:$rs1, GPR:$rs2, GPR:$rs3),
816           (FSR GPR:$rs1, GPR:$rs2, GPR:$rs3)>;
817 def : Pat<(fshr GPR:$rs1, GPR:$rs2, uimmlog2xlen:$shamt),
818           (FSRI GPR:$rs1, GPR:$rs2, uimmlog2xlen:$shamt)>;
819 } // Predicates = [HasStdExtZbt]
820
821 let Predicates = [HasStdExtZbb] in {
822 def : Pat<(ctlz GPR:$rs1), (CLZ GPR:$rs1)>;
823 def : Pat<(cttz GPR:$rs1), (CTZ GPR:$rs1)>;
824 def : Pat<(ctpop GPR:$rs1), (PCNT GPR:$rs1)>;
825 } // Predicates = [HasStdExtZbb]
826
827 let Predicates = [HasStdExtZbb, IsRV32] in
828 def : Pat<(sra (shl GPR:$rs1, (i32 24)), (i32 24)), (SEXTB GPR:$rs1)>;
829 let Predicates = [HasStdExtZbb, IsRV64] in
830 def : Pat<(sra (shl GPR:$rs1, (i64 56)), (i64 56)), (SEXTB GPR:$rs1)>;
831
832 let Predicates = [HasStdExtZbb, IsRV32] in
833 def : Pat<(sra (shl GPR:$rs1, (i32 16)), (i32 16)), (SEXTH GPR:$rs1)>;
834 let Predicates = [HasStdExtZbb, IsRV64] in
835 def : Pat<(sra (shl GPR:$rs1, (i64 48)), (i64 48)), (SEXTH GPR:$rs1)>;
836
837 let Predicates = [HasStdExtZbb] in {
838 def : Pat<(smin GPR:$rs1, GPR:$rs2), (MIN  GPR:$rs1, GPR:$rs2)>;
839 def : Pat<(riscv_selectcc GPR:$rs1, GPR:$rs2, (XLenVT 20), GPR:$rs1, GPR:$rs2),
840           (MIN  GPR:$rs1, GPR:$rs2)>;
841 def : Pat<(smax GPR:$rs1, GPR:$rs2), (MAX  GPR:$rs1, GPR:$rs2)>;
842 def : Pat<(riscv_selectcc GPR:$rs2, GPR:$rs1, (XLenVT 20), GPR:$rs1, GPR:$rs2),
843           (MAX  GPR:$rs1, GPR:$rs2)>;
844 def : Pat<(umin GPR:$rs1, GPR:$rs2), (MINU GPR:$rs1, GPR:$rs2)>;
845 def : Pat<(riscv_selectcc GPR:$rs1, GPR:$rs2, (XLenVT 12), GPR:$rs1, GPR:$rs2),
846           (MINU  GPR:$rs1, GPR:$rs2)>;
847 def : Pat<(umax GPR:$rs1, GPR:$rs2), (MAXU GPR:$rs1, GPR:$rs2)>;
848 def : Pat<(riscv_selectcc GPR:$rs2, GPR:$rs1, (XLenVT 12), GPR:$rs1, GPR:$rs2),
849           (MAXU  GPR:$rs1, GPR:$rs2)>;
850 } // Predicates = [HasStdExtZbb]
851
852 let Predicates = [HasStdExtZbbOrZbp, IsRV32] in
853 def : Pat<(or (and GPR:$rs1, 0x0000FFFF), (shl GPR:$rs2, (i32 16))),
854           (PACK GPR:$rs1, GPR:$rs2)>;
855 let Predicates = [HasStdExtZbbOrZbp, IsRV64] in
856 def : Pat<(or (and GPR:$rs1, 0x00000000FFFFFFFF), (shl GPR:$rs2, (i64 32))),
857           (PACK GPR:$rs1, GPR:$rs2)>;
858 let Predicates = [HasStdExtZbbOrZbp, IsRV32] in
859 def : Pat<(or (and GPR:$rs2, 0xFFFF0000), (srl GPR:$rs1, (i32 16))),
860           (PACKU GPR:$rs1, GPR:$rs2)>;
861 let Predicates = [HasStdExtZbbOrZbp, IsRV64] in
862 def : Pat<(or (and GPR:$rs2, 0xFFFFFFFF00000000), (srl GPR:$rs1, (i64 32))),
863           (PACKU GPR:$rs1, GPR:$rs2)>;
864 let Predicates = [HasStdExtZbbOrZbp] in
865 def : Pat<(or (and (shl GPR:$rs2, (XLenVT 8)), 0xFF00),
866               (and GPR:$rs1, 0x00FF)),
867           (PACKH GPR:$rs1, GPR:$rs2)>;
868
869 let Predicates = [HasStdExtZbp, IsRV32] in {
870 def : Pat<(or (or (and (shl GPR:$rs1, (i32 8)), (i32 0x00FF0000)),
871                   (and GPR:$rs1, (i32 0xFF0000FF))),
872               (and (srl GPR:$rs1, (i32 8)), (i32 0x0000FF00))),
873           (SHFLI GPR:$rs1, (i32 8))>;
874 def : Pat<(or (or (and (shl GPR:$rs1, (i32 4)), (i32 0x0F000F00)),
875                   (and GPR:$rs1, (i32 0xF00FF00F))),
876               (and (srl GPR:$rs1, (i32 4)), (i32 0x00F000F0))),
877           (SHFLI GPR:$rs1, (i32 4))>;
878 def : Pat<(or (or (and (shl GPR:$rs1, (i32 2)), (i32 0x30303030)),
879                   (and GPR:$rs1, (i32 0xC3C3C3C3))),
880               (and (srl GPR:$rs1, (i32 2)), (i32 0x0C0C0C0C))),
881           (SHFLI GPR:$rs1, (i32 2))>;
882 def : Pat<(or (or (and (shl GPR:$rs1, (i32 1)), (i32 0x44444444)),
883                   (and GPR:$rs1, (i32 0x99999999))),
884               (and (srl GPR:$rs1, (i32 1)), (i32 0x22222222))),
885           (SHFLI GPR:$rs1, (i32 1))>;
886 } // Predicates = [HasStdExtZbp, IsRV32]
887
888 let Predicates = [HasStdExtZbp, IsRV64] in {
889 def : Pat<(or (or (and (shl GPR:$rs1, (i64 16)), (i64 0x0000FFFF00000000)),
890                   (and GPR:$rs1, (i64 0xFFFF00000000FFFF))),
891               (and (srl GPR:$rs1, (i64 16)), (i64 0x00000000FFFF0000))),
892           (SHFLI GPR:$rs1, (i64 16))>;
893 def : Pat<(or (or (and (shl GPR:$rs1, (i64 8)), (i64 0x00FF000000FF0000)),
894                   (and GPR:$rs1, (i64 0xFF0000FFFF0000FF))),
895               (and (srl GPR:$rs1, (i64 8)), (i64 0x0000FF000000FF00))),
896           (SHFLI GPR:$rs1, (i64 8))>;
897 def : Pat<(or (or (and (shl GPR:$rs1, (i64 4)), (i64 0x0F000F000F000F00)),
898                   (and GPR:$rs1, (i64 0xF00FF00FF00FF00F))),
899               (and (srl GPR:$rs1, (i64 4)), (i64 0x00F000F000F000F0))),
900           (SHFLI GPR:$rs1, (i64 4))>;
901 def : Pat<(or (or (and (shl GPR:$rs1, (i64 2)), (i64 0x3030303030303030)),
902                   (and GPR:$rs1, (i64 0xC3C3C3C3C3C3C3C3))),
903               (and (srl GPR:$rs1, (i64 2)), (i64 0x0C0C0C0C0C0C0C0C))),
904           (SHFLI GPR:$rs1, (i64 2))>;
905 def : Pat<(or (or (and (shl GPR:$rs1, (i64 1)), (i64 0x4444444444444444)),
906                   (and GPR:$rs1, (i64 0x9999999999999999))),
907               (and (srl GPR:$rs1, (i64 1)), (i64 0x2222222222222222))),
908           (SHFLI GPR:$rs1, (i64 1))>;
909 } // Predicates = [HasStdExtZbp, IsRV64]
910
911 let Predicates = [HasStdExtZbb, IsRV64] in {
912 def : Pat<(and (add GPR:$rs, simm12:$simm12), (i64 0xFFFFFFFF)),
913           (ADDIWU GPR:$rs, simm12:$simm12)>;
914 def : Pat<(SLLIUWPat GPR:$rs1, uimmlog2xlen:$shamt),
915           (SLLIUW GPR:$rs1, uimmlog2xlen:$shamt)>;
916 def : Pat<(and (add GPR:$rs1, GPR:$rs2), (i64 0xFFFFFFFF)),
917           (ADDWU GPR:$rs1, GPR:$rs2)>;
918 def : Pat<(and (sub GPR:$rs1, GPR:$rs2), (i64 0xFFFFFFFF)),
919           (SUBWU GPR:$rs1, GPR:$rs2)>;
920 def : Pat<(add GPR:$rs1, (and GPR:$rs2, (i64 0xFFFFFFFF))),
921           (ADDUW GPR:$rs1, GPR:$rs2)>;
922 def : Pat<(sub GPR:$rs1, (and GPR:$rs2, (i64 0xFFFFFFFF))),
923           (SUBUW GPR:$rs1, GPR:$rs2)>;
924 def : Pat<(xor (riscv_sllw (xor GPR:$rs1, -1), GPR:$rs2), -1),
925           (SLOW GPR:$rs1, GPR:$rs2)>;
926 def : Pat<(xor (riscv_srlw (xor GPR:$rs1, -1), GPR:$rs2), -1),
927           (SROW GPR:$rs1, GPR:$rs2)>;
928 } // Predicates = [HasStdExtZbb, IsRV64]
929
930 let Predicates = [HasStdExtZbbOrZbp, IsRV64] in {
931 def : Pat<(or (riscv_sllw (assertsexti32 GPR:$rs1), (assertsexti32 GPR:$rs2)),
932               (riscv_srlw (assertsexti32 GPR:$rs1),
933                           (sub (i64 0), (assertsexti32 GPR:$rs2)))),
934           (ROLW GPR:$rs1, GPR:$rs2)>;
935 def : Pat<(or (riscv_sllw (assertsexti32 GPR:$rs1),
936                           (sub (i64 0), (assertsexti32 GPR:$rs2))),
937               (riscv_srlw (assertsexti32 GPR:$rs1), (assertsexti32 GPR:$rs2))),
938           (RORW GPR:$rs1, GPR:$rs2)>;
939 } // Predicates = [HasStdExtZbbOrZbp, IsRV64]
940
941 let Predicates = [HasStdExtZbs, IsRV64] in {
942 def : Pat<(and (xor (riscv_sllw 1, (assertsexti32 GPR:$rs2)), -1),
943                (assertsexti32 GPR:$rs1)),
944           (SBCLRW GPR:$rs1, GPR:$rs2)>;
945 def : Pat<(or (riscv_sllw 1, (assertsexti32 GPR:$rs2)),
946               (assertsexti32 GPR:$rs1)),
947           (SBSETW GPR:$rs1, GPR:$rs2)>;
948 def : Pat<(xor (riscv_sllw 1, (assertsexti32 GPR:$rs2)),
949                (assertsexti32 GPR:$rs1)),
950           (SBINVW GPR:$rs1, GPR:$rs2)>;
951 def : Pat<(and (riscv_srlw (assertsexti32 GPR:$rs1), (assertsexti32 GPR:$rs2)),
952                1),
953           (SBEXTW GPR:$rs1, GPR:$rs2)>;
954 } // Predicates = [HasStdExtZbs, IsRV64]
955
956 let Predicates = [HasStdExtZbb, IsRV64] in {
957 def : Pat<(SLOIWPat GPR:$rs1, uimmlog2xlen:$shamt),
958           (SLOIW GPR:$rs1, uimmlog2xlen:$shamt)>;
959 def : Pat<(SROIWPat GPR:$rs1, uimmlog2xlen:$shamt),
960           (SROIW GPR:$rs1, uimmlog2xlen:$shamt)>;
961 } // Predicates = [HasStdExtZbb, IsRV64]
962
963 let Predicates = [HasStdExtZbbOrZbp, IsRV64] in
964 def : Pat<(RORIWPat GPR:$rs1, uimmlog2xlen:$shamt),
965           (RORIW GPR:$rs1, uimmlog2xlen:$shamt)>;
966
967 let Predicates = [HasStdExtZbp, IsRV64] in {
968 def : Pat<(sext_inreg (or (or (and (srl GPR:$rs1, (i64 1)), (i64 0x55555555)),
969                               GPR:$rs1),
970                           (and (shl GPR:$rs1, (i64 1)), (i64 0xAAAAAAAA))),
971                       i32),
972           (GORCIW GPR:$rs1, (i64 1))>;
973 def : Pat<(sext_inreg (or (or (and (srl GPR:$rs1, (i64 2)), (i64 0x33333333)),
974                               GPR:$rs1),
975                           (and (shl GPR:$rs1, (i64 2)), (i64 0xCCCCCCCC))),
976                       i32),
977           (GORCIW GPR:$rs1, (i64 2))>;
978 def : Pat<(sext_inreg (or (or (and (srl GPR:$rs1, (i64 4)), (i64 0x0F0F0F0F)),
979                               GPR:$rs1),
980                           (and (shl GPR:$rs1, (i64 4)), (i64 0xF0F0F0F0))),
981                       i32),
982           (GORCIW GPR:$rs1, (i64 4))>;
983 def : Pat<(sext_inreg (or (or (and (srl GPR:$rs1, (i64 8)), (i64 0x00FF00FF)),
984                               GPR:$rs1),
985                           (and (shl GPR:$rs1, (i64 8)), (i64 0xFF00FF00))),
986                       i32),
987           (GORCIW GPR:$rs1, (i64 8))>;
988 def : Pat<(sext_inreg (or (or (and (srl GPR:$rs1, (i64 16)), (i64 0x0000FFFF)),
989                               GPR:$rs1),
990                           (and (shl GPR:$rs1, (i64 16)), (i64 0xFFFF0000))),
991                       i32),
992           (GORCIW GPR:$rs1, (i64 16))>;
993 def : Pat<(sext_inreg (or (or (srl (and GPR:$rs1, (i64 0xFFFF0000)), (i64 16)),
994                               GPR:$rs1),
995                           (shl GPR:$rs1, (i64 16))), i32),
996           (GORCIW GPR:$rs1, (i64 16))>;
997
998 def : Pat<(sext_inreg (or (and (shl GPR:$rs1, (i64 1)), (i64 0xAAAAAAAA)),
999                           (and (srl GPR:$rs1, (i64 1)), (i64 0x55555555))),
1000                       i32),
1001           (GREVIW GPR:$rs1, (i64 1))>;
1002 def : Pat<(sext_inreg (or (and (shl GPR:$rs1, (i64 2)), (i64 0xCCCCCCCC)),
1003                           (and (srl GPR:$rs1, (i64 2)), (i64 0x33333333))),
1004                       i32),
1005           (GREVIW GPR:$rs1, (i64 2))>;
1006 def : Pat<(sext_inreg (or (and (shl GPR:$rs1, (i64 4)), (i64 0xF0F0F0F0)),
1007                           (and (srl GPR:$rs1, (i64 4)), (i64 0x0F0F0F0F))),
1008                       i32),
1009           (GREVIW GPR:$rs1, (i64 4))>;
1010 def : Pat<(sext_inreg (or (and (shl GPR:$rs1, (i64 8)), (i64 0xFF00FF00)),
1011                           (and (srl GPR:$rs1, (i64 8)), (i64 0x00FF00FF))),
1012                       i32),
1013           (GREVIW GPR:$rs1, (i64 8))>;
1014 def : Pat<(sext_inreg (or (shl GPR:$rs1, (i64 16)),
1015                           (srl (and GPR:$rs1, 0xFFFF0000), (i64 16))), i32),
1016           (GREVIW GPR:$rs1, (i64 16))>;
1017 def : Pat<(sra (bswap GPR:$rs1), (i64 32)), (GREVIW GPR:$rs1, (i64 24))>;
1018 def : Pat<(sra (bitreverse GPR:$rs1), (i64 32)), (GREVIW GPR:$rs1, (i64 31))>;
1019 } // Predicates = [HasStdExtZbp, IsRV64]
1020
1021 let Predicates = [HasStdExtZbt, IsRV64] in {
1022 def : Pat<(riscv_selectcc (and (assertsexti32 GPR:$rs3), 31),
1023                           (i64 0),
1024                           (i64 17),
1025                           (assertsexti32 GPR:$rs1),
1026                           (or (riscv_sllw (assertsexti32 GPR:$rs1),
1027                                           (and (assertsexti32 GPR:$rs3), 31)),
1028                               (riscv_srlw (assertsexti32 GPR:$rs2),
1029                                           (sub (i64 32),
1030                                                (assertsexti32 GPR:$rs3))))),
1031           (FSLW GPR:$rs1, GPR:$rs2, GPR:$rs3)>;
1032 def : Pat<(riscv_selectcc (and (assertsexti32 GPR:$rs3), 31),
1033                           (i64 0),
1034                           (i64 17),
1035                           (assertsexti32 GPR:$rs2),
1036                           (or (riscv_sllw (assertsexti32 GPR:$rs1),
1037                                           (sub (i64 32),
1038                                                (assertsexti32 GPR:$rs3))),
1039                               (riscv_srlw (assertsexti32 GPR:$rs2),
1040                                           (and (assertsexti32 GPR:$rs3), 31)))),
1041           (FSRW GPR:$rs1, GPR:$rs2, GPR:$rs3)>;
1042 def : Pat<(FSRIWPat GPR:$rs1, GPR:$rs2, uimmlog2xlen:$shamt),
1043           (FSRIW GPR:$rs1, GPR:$rs2, uimmlog2xlen:$shamt)>;
1044 } // Predicates = [HasStdExtZbt, IsRV64]
1045
1046 let Predicates = [HasStdExtZbb, IsRV64] in {
1047 def : Pat<(add (ctlz (and GPR:$rs1, (i64 0xFFFFFFFF))), (i64 -32)),
1048           (CLZW GPR:$rs1)>;
1049 // We don't pattern-match CTZW here as it has the same pattern and result as
1050 // RV64 CTZ
1051 def : Pat<(ctpop (and GPR:$rs1, (i64 0xFFFFFFFF))), (PCNTW GPR:$rs1)>;
1052 } // Predicates = [HasStdExtZbb, IsRV64]
1053
1054 let Predicates = [HasStdExtZbbOrZbp, IsRV64] in {
1055 def : Pat<(sext_inreg (or (shl (assertsexti32 GPR:$rs2), (i64 16)),
1056                           (and (assertsexti32 GPR:$rs1), 0x000000000000FFFF)),
1057                       i32),
1058           (PACKW GPR:$rs1, GPR:$rs2)>;
1059 def : Pat<(or (and (assertsexti32 GPR:$rs2), 0xFFFFFFFFFFFF0000),
1060               (srl (and (assertsexti32 GPR:$rs1), 0x00000000FFFF0000),
1061                    (i64 16))),
1062           (PACKUW GPR:$rs1, GPR:$rs2)>;
1063 } // Predicates = [HasStdExtZbbOrZbp, IsRV64]