1//===-- RISCVInstrInfoZb.td - RISC-V Bitmanip 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 Bitmanip 10// extensions, versions: 11// Zba - 1.0 12// Zbb - 1.0 13// Zbc - 1.0 14// Zbs - 1.0 15// Zbe - 0.93 *experimental 16// Zbf - 0.93 *experimental 17// Zbm - 0.93 *experimental 18// Zbp - 0.93 *experimental 19// Zbr - 0.93 *experimental 20// Zbt - 0.93 *experimental 21// 22// The experimental extensions appeared in an earlier draft of the Bitmanip 23// extensions. They are not ratified and subject to change. 24// 25// This file also describes RISC-V instructions from the Zbk* extensions in 26// Cryptography Extensions Volume I: Scalar & Entropy Source Instructions, 27// versions: 28// Zbkb - 1.0 29// Zbkc - 1.0 30// Zbkx - 1.0 31// 32//===----------------------------------------------------------------------===// 33 34//===----------------------------------------------------------------------===// 35// Operand and SDNode transformation definitions. 36//===----------------------------------------------------------------------===// 37 38def riscv_clzw : SDNode<"RISCVISD::CLZW", SDT_RISCVIntUnaryOpW>; 39def riscv_ctzw : SDNode<"RISCVISD::CTZW", SDT_RISCVIntUnaryOpW>; 40def riscv_rolw : SDNode<"RISCVISD::ROLW", SDT_RISCVIntBinOpW>; 41def riscv_rorw : SDNode<"RISCVISD::RORW", SDT_RISCVIntBinOpW>; 42def riscv_fslw : SDNode<"RISCVISD::FSLW", SDT_RISCVIntShiftDOpW>; 43def riscv_fsrw : SDNode<"RISCVISD::FSRW", SDT_RISCVIntShiftDOpW>; 44def riscv_fsl : SDNode<"RISCVISD::FSL", SDTIntShiftDOp>; 45def riscv_fsr : SDNode<"RISCVISD::FSR", SDTIntShiftDOp>; 46def riscv_grev : SDNode<"RISCVISD::GREV", SDTIntBinOp>; 47def riscv_grevw : SDNode<"RISCVISD::GREVW", SDT_RISCVIntBinOpW>; 48def riscv_gorc : SDNode<"RISCVISD::GORC", SDTIntBinOp>; 49def riscv_gorcw : SDNode<"RISCVISD::GORCW", SDT_RISCVIntBinOpW>; 50def riscv_shfl : SDNode<"RISCVISD::SHFL", SDTIntBinOp>; 51def riscv_shflw : SDNode<"RISCVISD::SHFLW", SDT_RISCVIntBinOpW>; 52def riscv_unshfl : SDNode<"RISCVISD::UNSHFL", SDTIntBinOp>; 53def riscv_unshflw: SDNode<"RISCVISD::UNSHFLW",SDT_RISCVIntBinOpW>; 54def riscv_bfp : SDNode<"RISCVISD::BFP", SDTIntBinOp>; 55def riscv_bfpw : SDNode<"RISCVISD::BFPW", SDT_RISCVIntBinOpW>; 56def riscv_bcompress : SDNode<"RISCVISD::BCOMPRESS", SDTIntBinOp>; 57def riscv_bcompressw : SDNode<"RISCVISD::BCOMPRESSW", SDT_RISCVIntBinOpW>; 58def riscv_bdecompress : SDNode<"RISCVISD::BDECOMPRESS", SDTIntBinOp>; 59def riscv_bdecompressw : SDNode<"RISCVISD::BDECOMPRESSW",SDT_RISCVIntBinOpW>; 60 61def UImmLog2XLenHalfAsmOperand : AsmOperandClass { 62 let Name = "UImmLog2XLenHalf"; 63 let RenderMethod = "addImmOperands"; 64 let DiagnosticType = "InvalidUImmLog2XLenHalf"; 65} 66 67def shfl_uimm : Operand<XLenVT>, ImmLeaf<XLenVT, [{ 68 if (Subtarget->is64Bit()) 69 return isUInt<5>(Imm); 70 return isUInt<4>(Imm); 71}]> { 72 let ParserMatchClass = UImmLog2XLenHalfAsmOperand; 73 let DecoderMethod = "decodeUImmOperand<5>"; 74 let MCOperandPredicate = [{ 75 int64_t Imm; 76 if (!MCOp.evaluateAsConstantImm(Imm)) 77 return false; 78 if (STI.getTargetTriple().isArch64Bit()) 79 return isUInt<5>(Imm); 80 return isUInt<4>(Imm); 81 }]; 82} 83 84def BCLRXForm : SDNodeXForm<imm, [{ 85 // Find the lowest 0. 86 return CurDAG->getTargetConstant(N->getAPIntValue().countTrailingOnes(), 87 SDLoc(N), N->getValueType(0)); 88}]>; 89 90def BSETINVXForm : SDNodeXForm<imm, [{ 91 // Find the lowest 1. 92 return CurDAG->getTargetConstant(N->getAPIntValue().countTrailingZeros(), 93 SDLoc(N), N->getValueType(0)); 94}]>; 95 96// Checks if this mask has a single 0 bit and cannot be used with ANDI. 97def BCLRMask : ImmLeaf<XLenVT, [{ 98 if (Subtarget->is64Bit()) 99 return !isInt<12>(Imm) && isPowerOf2_64(~Imm); 100 return !isInt<12>(Imm) && isPowerOf2_32(~Imm); 101}], BCLRXForm>; 102 103// Checks if this mask has a single 1 bit and cannot be used with ORI/XORI. 104def BSETINVMask : ImmLeaf<XLenVT, [{ 105 if (Subtarget->is64Bit()) 106 return !isInt<12>(Imm) && isPowerOf2_64(Imm); 107 return !isInt<12>(Imm) && isPowerOf2_32(Imm); 108}], BSETINVXForm>; 109 110// Check if (or r, i) can be optimized to (BSETI (BSETI r, i0), i1), 111// in which i = (1 << i0) | (1 << i1). 112def BSETINVTwoBitsMask : PatLeaf<(imm), [{ 113 if (!N->hasOneUse()) 114 return false; 115 // The immediate should not be a simm12. 116 if (isInt<12>(N->getSExtValue())) 117 return false; 118 // The immediate must have exactly two bits set. 119 return countPopulation(N->getZExtValue()) == 2; 120}]>; 121 122def TrailingZerosXForm : SDNodeXForm<imm, [{ 123 uint64_t I = N->getZExtValue(); 124 return CurDAG->getTargetConstant(countTrailingZeros(I), SDLoc(N), 125 N->getValueType(0)); 126}]>; 127 128def BSETINVTwoBitsMaskHigh : SDNodeXForm<imm, [{ 129 uint64_t I = N->getZExtValue(); 130 return CurDAG->getTargetConstant(63 - countLeadingZeros(I), SDLoc(N), 131 N->getValueType(0)); 132}]>; 133 134// Check if (or r, imm) can be optimized to (BSETI (ORI r, i0), i1), 135// in which imm = i0 | (1 << i1). 136def BSETINVORIMask : PatLeaf<(imm), [{ 137 if (!N->hasOneUse()) 138 return false; 139 // The immediate should not be a simm12. 140 if (isInt<12>(N->getSExtValue())) 141 return false; 142 // There should be only one set bit from bit 11 to the top. 143 return isPowerOf2_64(N->getZExtValue() & ~0x7ff); 144}]>; 145 146def BSETINVORIMaskLow : SDNodeXForm<imm, [{ 147 return CurDAG->getTargetConstant(N->getZExtValue() & 0x7ff, 148 SDLoc(N), N->getValueType(0)); 149}]>; 150 151// Check if (and r, i) can be optimized to (BCLRI (BCLRI r, i0), i1), 152// in which i = ~((1<<i0) | (1<<i1)). 153def BCLRITwoBitsMask : PatLeaf<(imm), [{ 154 if (!N->hasOneUse()) 155 return false; 156 // The immediate should not be a simm12. 157 if (isInt<12>(N->getSExtValue())) 158 return false; 159 // The immediate must have exactly two bits clear. 160 return countPopulation(N->getZExtValue()) == Subtarget->getXLen() - 2; 161}]>; 162 163def BCLRITwoBitsMaskLow : SDNodeXForm<imm, [{ 164 return CurDAG->getTargetConstant(countTrailingZeros(~N->getZExtValue()), 165 SDLoc(N), N->getValueType(0)); 166}]>; 167 168def BCLRITwoBitsMaskHigh : SDNodeXForm<imm, [{ 169 uint64_t I = N->getSExtValue(); 170 if (!Subtarget->is64Bit()) 171 I |= 0xffffffffull << 32; 172 return CurDAG->getTargetConstant(63 - countLeadingZeros(~I), SDLoc(N), 173 N->getValueType(0)); 174}]>; 175 176// Check if (and r, i) can be optimized to (BCLRI (ANDI r, i0), i1), 177// in which i = i0 & ~(1<<i1). 178def BCLRIANDIMask : PatLeaf<(imm), [{ 179 if (!N->hasOneUse()) 180 return false; 181 // The immediate should not be a simm12. 182 if (isInt<12>(N->getSExtValue())) 183 return false; 184 // There should be only one clear bit from bit 11 to the top. 185 uint64_t I = N->getZExtValue() | 0x7ff; 186 return Subtarget->is64Bit() ? isPowerOf2_64(~I) : isPowerOf2_32(~I); 187}]>; 188 189def BCLRIANDIMaskLow : SDNodeXForm<imm, [{ 190 return CurDAG->getTargetConstant((N->getZExtValue() & 0x7ff) | ~0x7ffull, 191 SDLoc(N), N->getValueType(0)); 192}]>; 193 194def C3LeftShift : PatLeaf<(imm), [{ 195 uint64_t C = N->getZExtValue(); 196 return C > 3 && ((C % 3) == 0) && isPowerOf2_64(C / 3); 197}]>; 198 199def C5LeftShift : PatLeaf<(imm), [{ 200 uint64_t C = N->getZExtValue(); 201 return C > 5 && ((C % 5) == 0) && isPowerOf2_64(C / 5); 202}]>; 203 204def C9LeftShift : PatLeaf<(imm), [{ 205 uint64_t C = N->getZExtValue(); 206 return C > 9 && ((C % 9) == 0) && isPowerOf2_64(C / 9); 207}]>; 208 209def CSImm12MulBy4 : PatLeaf<(imm), [{ 210 if (!N->hasOneUse()) 211 return false; 212 int64_t C = N->getSExtValue(); 213 // Skip if C is simm12 or can be optimized by the PatLeaf AddiPair. 214 return !isInt<13>(C) && isInt<14>(C) && (C & 3) == 0; 215}]>; 216 217def CSImm12MulBy8 : PatLeaf<(imm), [{ 218 if (!N->hasOneUse()) 219 return false; 220 int64_t C = N->getSExtValue(); 221 // Skip if C is simm12 or can be optimized by the PatLeaf AddiPair. 222 return !isInt<13>(C) && isInt<15>(C) && (C & 7) == 0; 223}]>; 224 225def SimmShiftRightBy2XForm : SDNodeXForm<imm, [{ 226 return CurDAG->getTargetConstant(N->getSExtValue() >> 2, SDLoc(N), 227 N->getValueType(0)); 228}]>; 229 230def SimmShiftRightBy3XForm : SDNodeXForm<imm, [{ 231 return CurDAG->getTargetConstant(N->getSExtValue() >> 3, SDLoc(N), 232 N->getValueType(0)); 233}]>; 234 235//===----------------------------------------------------------------------===// 236// Instruction class templates 237//===----------------------------------------------------------------------===// 238 239// Some of these templates should be moved to RISCVInstrFormats.td once the B 240// extension has been ratified. 241 242let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 243class RVBUnary<bits<7> funct7, bits<5> funct5, bits<3> funct3, 244 RISCVOpcode opcode, string opcodestr> 245 : RVInstR<funct7, funct3, opcode, (outs GPR:$rd), (ins GPR:$rs1), 246 opcodestr, "$rd, $rs1"> { 247 let rs2 = funct5; 248} 249 250let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 251class RVBShift_ri<bits<5> imm11_7, bits<3> funct3, RISCVOpcode opcode, 252 string opcodestr> 253 : RVInstIShift<imm11_7, funct3, opcode, (outs GPR:$rd), 254 (ins GPR:$rs1, uimmlog2xlen:$shamt), opcodestr, 255 "$rd, $rs1, $shamt">; 256 257let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 258class RVBShiftW_ri<bits<7> imm11_5, bits<3> funct3, RISCVOpcode opcode, 259 string opcodestr> 260 : RVInstIShiftW<imm11_5, funct3, opcode, (outs GPR:$rd), 261 (ins GPR:$rs1, uimm5:$shamt), opcodestr, 262 "$rd, $rs1, $shamt">; 263 264// Using RVInstIShiftW since it allocates 5 bits instead of 6 to shamt. 265let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 266class RVBShfl_ri<bits<7> imm11_5, bits<3> funct3, RISCVOpcode opcode, 267 string opcodestr> 268 : RVInstIShiftW<imm11_5, funct3, opcode, (outs GPR:$rd), 269 (ins GPR:$rs1, shfl_uimm:$shamt), opcodestr, 270 "$rd, $rs1, $shamt">; 271 272let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 273class RVBTernaryR<bits<2> funct2, bits<3> funct3, RISCVOpcode opcode, 274 string opcodestr, string argstr> 275 : RVInstR4<funct2, funct3, opcode, (outs GPR:$rd), 276 (ins GPR:$rs1, GPR:$rs2, GPR:$rs3), opcodestr, argstr>; 277 278// Currently used by FSRI only 279let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 280class RVBTernaryImm6<bits<3> funct3, RISCVOpcode opcode, 281 string opcodestr, string argstr> 282 : RVInst<(outs GPR:$rd), (ins GPR:$rs1, GPR:$rs3, uimmlog2xlen:$shamt), 283 opcodestr, argstr, [], InstFormatR4> { 284 bits<5> rs3; 285 bits<6> shamt; 286 bits<5> rs1; 287 bits<5> rd; 288 289 let Inst{31-27} = rs3; 290 let Inst{26} = 1; 291 let Inst{25-20} = shamt; 292 let Inst{19-15} = rs1; 293 let Inst{14-12} = funct3; 294 let Inst{11-7} = rd; 295 let Opcode = opcode.Value; 296} 297 298// Currently used by FSRIW only 299let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 300class RVBTernaryImm5<bits<2> funct2, bits<3> funct3, RISCVOpcode opcode, 301 string opcodestr, string argstr> 302 : RVInst<(outs GPR:$rd), (ins GPR:$rs1, GPR:$rs3, uimm5:$shamt), 303 opcodestr, argstr, [], InstFormatR4> { 304 bits<5> rs3; 305 bits<5> shamt; 306 bits<5> rs1; 307 bits<5> rd; 308 309 let Inst{31-27} = rs3; 310 let Inst{26-25} = funct2; 311 let Inst{24-20} = shamt; 312 let Inst{19-15} = rs1; 313 let Inst{14-12} = funct3; 314 let Inst{11-7} = rd; 315 let Opcode = opcode.Value; 316} 317 318//===----------------------------------------------------------------------===// 319// Instructions 320//===----------------------------------------------------------------------===// 321 322let Predicates = [HasStdExtZbbOrZbpOrZbkb] in { 323def ANDN : ALU_rr<0b0100000, 0b111, "andn">, 324 Sched<[WriteIALU, ReadIALU, ReadIALU]>; 325def ORN : ALU_rr<0b0100000, 0b110, "orn">, 326 Sched<[WriteIALU, ReadIALU, ReadIALU]>; 327def XNOR : ALU_rr<0b0100000, 0b100, "xnor">, 328 Sched<[WriteIALU, ReadIALU, ReadIALU]>; 329} // Predicates = [HasStdExtZbbOrZbpOrZbkb] 330 331let Predicates = [HasStdExtZba] in { 332def SH1ADD : ALU_rr<0b0010000, 0b010, "sh1add">, 333 Sched<[WriteSHXADD, ReadSHXADD, ReadSHXADD]>; 334def SH2ADD : ALU_rr<0b0010000, 0b100, "sh2add">, 335 Sched<[WriteSHXADD, ReadSHXADD, ReadSHXADD]>; 336def SH3ADD : ALU_rr<0b0010000, 0b110, "sh3add">, 337 Sched<[WriteSHXADD, ReadSHXADD, ReadSHXADD]>; 338} // Predicates = [HasStdExtZba] 339 340let Predicates = [HasStdExtZba, IsRV64] in { 341def SLLI_UW : RVBShift_ri<0b00001, 0b001, OPC_OP_IMM_32, "slli.uw">, 342 Sched<[WriteShiftImm32, ReadShiftImm32]>; 343def ADD_UW : ALUW_rr<0b0000100, 0b000, "add.uw">, 344 Sched<[WriteIALU32, ReadIALU32, ReadIALU32]>; 345def SH1ADD_UW : ALUW_rr<0b0010000, 0b010, "sh1add.uw">, 346 Sched<[WriteSHXADD32, ReadSHXADD32, ReadSHXADD32]>; 347def SH2ADD_UW : ALUW_rr<0b0010000, 0b100, "sh2add.uw">, 348 Sched<[WriteSHXADD32, ReadSHXADD32, ReadSHXADD32]>; 349def SH3ADD_UW : ALUW_rr<0b0010000, 0b110, "sh3add.uw">, 350 Sched<[WriteSHXADD32, ReadSHXADD32, ReadSHXADD32]>; 351} // Predicates = [HasStdExtZbb, IsRV64] 352 353let Predicates = [HasStdExtZbbOrZbpOrZbkb] in { 354def ROL : ALU_rr<0b0110000, 0b001, "rol">, 355 Sched<[WriteRotateReg, ReadRotateReg, ReadRotateReg]>; 356def ROR : ALU_rr<0b0110000, 0b101, "ror">, 357 Sched<[WriteRotateReg, ReadRotateReg, ReadRotateReg]>; 358 359def RORI : RVBShift_ri<0b01100, 0b101, OPC_OP_IMM, "rori">, 360 Sched<[WriteRotateImm, ReadRotateImm]>; 361} // Predicates = [HasStdExtZbbOrZbpOrZbkb] 362 363let Predicates = [HasStdExtZbbOrZbpOrZbkb, IsRV64] in { 364def ROLW : ALUW_rr<0b0110000, 0b001, "rolw">, 365 Sched<[WriteRotateReg32, ReadRotateReg32, ReadRotateReg32]>; 366def RORW : ALUW_rr<0b0110000, 0b101, "rorw">, 367 Sched<[WriteRotateReg32, ReadRotateReg32, ReadRotateReg32]>; 368 369def RORIW : RVBShiftW_ri<0b0110000, 0b101, OPC_OP_IMM_32, "roriw">, 370 Sched<[WriteRotateImm32, ReadRotateImm32]>; 371} // Predicates = [HasStdExtZbbOrZbp, IsRV64] 372 373let Predicates = [HasStdExtZbs] in { 374def BCLR : ALU_rr<0b0100100, 0b001, "bclr">, 375 Sched<[WriteSingleBit, ReadSingleBit, ReadSingleBit]>; 376def BSET : ALU_rr<0b0010100, 0b001, "bset">, 377 Sched<[WriteSingleBit, ReadSingleBit, ReadSingleBit]>; 378def BINV : ALU_rr<0b0110100, 0b001, "binv">, 379 Sched<[WriteSingleBit, ReadSingleBit, ReadSingleBit]>; 380def BEXT : ALU_rr<0b0100100, 0b101, "bext">, 381 Sched<[WriteSingleBit, ReadSingleBit, ReadSingleBit]>; 382 383def BCLRI : RVBShift_ri<0b01001, 0b001, OPC_OP_IMM, "bclri">, 384 Sched<[WriteSingleBitImm, ReadSingleBitImm]>; 385def BSETI : RVBShift_ri<0b00101, 0b001, OPC_OP_IMM, "bseti">, 386 Sched<[WriteSingleBitImm, ReadSingleBitImm]>; 387def BINVI : RVBShift_ri<0b01101, 0b001, OPC_OP_IMM, "binvi">, 388 Sched<[WriteSingleBitImm, ReadSingleBitImm]>; 389def BEXTI : RVBShift_ri<0b01001, 0b101, OPC_OP_IMM, "bexti">, 390 Sched<[WriteSingleBitImm, ReadSingleBitImm]>; 391} // Predicates = [HasStdExtZbs] 392 393let Predicates = [HasStdExtZbp] in { 394def GORC : ALU_rr<0b0010100, 0b101, "gorc">, Sched<[]>; 395def GREV : ALU_rr<0b0110100, 0b101, "grev">, Sched<[]>; 396 397def GREVI : RVBShift_ri<0b01101, 0b101, OPC_OP_IMM, "grevi">, Sched<[]>; 398def GORCI : RVBShift_ri<0b00101, 0b101, OPC_OP_IMM, "gorci">, Sched<[]>; 399 400def SHFL : ALU_rr<0b0000100, 0b001, "shfl">, Sched<[]>; 401def UNSHFL : ALU_rr<0b0000100, 0b101, "unshfl">, Sched<[]>; 402 403def SHFLI : RVBShfl_ri<0b0000100, 0b001, OPC_OP_IMM, "shfli">, Sched<[]>; 404def UNSHFLI : RVBShfl_ri<0b0000100, 0b101, OPC_OP_IMM, "unshfli">, Sched<[]>; 405 406def XPERM_H : ALU_rr<0b0010100, 0b110, "xperm.h">, Sched<[]>; 407} // Predicates = [HasStdExtZbp] 408 409let Predicates = [HasStdExtZbp, IsRV64] in { 410def GORCW : ALUW_rr<0b0010100, 0b101, "gorcw">, Sched<[]>; 411def GREVW : ALUW_rr<0b0110100, 0b101, "grevw">, Sched<[]>; 412 413def GORCIW : RVBShiftW_ri<0b0010100, 0b101, OPC_OP_IMM_32, "gorciw">, Sched<[]>; 414def GREVIW : RVBShiftW_ri<0b0110100, 0b101, OPC_OP_IMM_32, "greviw">, Sched<[]>; 415 416def SHFLW : ALUW_rr<0b0000100, 0b001, "shflw">, Sched<[]>; 417def UNSHFLW : ALUW_rr<0b0000100, 0b101, "unshflw">, Sched<[]>; 418 419def XPERM_W : ALU_rr<0b0010100, 0b000, "xperm.w">, Sched<[]>; 420} // Predicates = [HasStdExtZbp, IsRV64] 421 422// These instructions were named xperm.n and xperm.b in the last version of 423// the draft bit manipulation specification they were included in. However, we 424// use the mnemonics given to them in the ratified Zbkx extension. 425let Predicates = [HasStdExtZbpOrZbkx] in { 426def XPERM4 : ALU_rr<0b0010100, 0b010, "xperm4">, Sched<[]>; 427def XPERM8 : ALU_rr<0b0010100, 0b100, "xperm8">, Sched<[]>; 428} // Predicates = [HasStdExtZbpOrZbkx] 429 430let Predicates = [HasStdExtZbt] in { 431def CMIX : RVBTernaryR<0b11, 0b001, OPC_OP, "cmix", "$rd, $rs2, $rs1, $rs3">, 432 Sched<[]>; 433def CMOV : RVBTernaryR<0b11, 0b101, OPC_OP, "cmov", "$rd, $rs2, $rs1, $rs3">, 434 Sched<[]>; 435def FSL : RVBTernaryR<0b10, 0b001, OPC_OP, "fsl", "$rd, $rs1, $rs3, $rs2">, 436 Sched<[]>; 437def FSR : RVBTernaryR<0b10, 0b101, OPC_OP, "fsr", "$rd, $rs1, $rs3, $rs2">, 438 Sched<[]>; 439def FSRI : RVBTernaryImm6<0b101, OPC_OP_IMM, "fsri", 440 "$rd, $rs1, $rs3, $shamt">, Sched<[]>; 441} // Predicates = [HasStdExtZbt] 442 443let Predicates = [HasStdExtZbt, IsRV64] in { 444def FSLW : RVBTernaryR<0b10, 0b001, OPC_OP_32, 445 "fslw", "$rd, $rs1, $rs3, $rs2">, Sched<[]>; 446def FSRW : RVBTernaryR<0b10, 0b101, OPC_OP_32, "fsrw", 447 "$rd, $rs1, $rs3, $rs2">, Sched<[]>; 448def FSRIW : RVBTernaryImm5<0b10, 0b101, OPC_OP_IMM_32, 449 "fsriw", "$rd, $rs1, $rs3, $shamt">, Sched<[]>; 450} // Predicates = [HasStdExtZbt, IsRV64] 451 452let Predicates = [HasStdExtZbb] in { 453def CLZ : RVBUnary<0b0110000, 0b00000, 0b001, OPC_OP_IMM, "clz">, 454 Sched<[WriteCLZ, ReadCLZ]>; 455def CTZ : RVBUnary<0b0110000, 0b00001, 0b001, OPC_OP_IMM, "ctz">, 456 Sched<[WriteCTZ, ReadCTZ]>; 457def CPOP : RVBUnary<0b0110000, 0b00010, 0b001, OPC_OP_IMM, "cpop">, 458 Sched<[WriteCPOP, ReadCPOP]>; 459} // Predicates = [HasStdExtZbb] 460 461let Predicates = [HasStdExtZbb, IsRV64] in { 462def CLZW : RVBUnary<0b0110000, 0b00000, 0b001, OPC_OP_IMM_32, "clzw">, 463 Sched<[WriteCLZ32, ReadCLZ32]>; 464def CTZW : RVBUnary<0b0110000, 0b00001, 0b001, OPC_OP_IMM_32, "ctzw">, 465 Sched<[WriteCTZ32, ReadCTZ32]>; 466def CPOPW : RVBUnary<0b0110000, 0b00010, 0b001, OPC_OP_IMM_32, "cpopw">, 467 Sched<[WriteCPOP32, ReadCPOP32]>; 468} // Predicates = [HasStdExtZbb, IsRV64] 469 470let Predicates = [HasStdExtZbb] in { 471def SEXT_B : RVBUnary<0b0110000, 0b00100, 0b001, OPC_OP_IMM, "sext.b">, 472 Sched<[WriteIALU, ReadIALU]>; 473def SEXT_H : RVBUnary<0b0110000, 0b00101, 0b001, OPC_OP_IMM, "sext.h">, 474 Sched<[WriteIALU, ReadIALU]>; 475} // Predicates = [HasStdExtZbb] 476 477let Predicates = [HasStdExtZbr] in { 478def CRC32_B : RVBUnary<0b0110000, 0b10000, 0b001, OPC_OP_IMM, "crc32.b">, 479 Sched<[]>; 480def CRC32_H : RVBUnary<0b0110000, 0b10001, 0b001, OPC_OP_IMM, "crc32.h">, 481 Sched<[]>; 482def CRC32_W : RVBUnary<0b0110000, 0b10010, 0b001, OPC_OP_IMM, "crc32.w">, 483 Sched<[]>; 484 485def CRC32C_B : RVBUnary<0b0110000, 0b11000, 0b001, OPC_OP_IMM, "crc32c.b">, 486 Sched<[]>; 487def CRC32C_H : RVBUnary<0b0110000, 0b11001, 0b001, OPC_OP_IMM, "crc32c.h">, 488 Sched<[]>; 489def CRC32C_W : RVBUnary<0b0110000, 0b11010, 0b001, OPC_OP_IMM, "crc32c.w">, 490 Sched<[]>; 491} // Predicates = [HasStdExtZbr] 492 493let Predicates = [HasStdExtZbr, IsRV64] in { 494def CRC32_D : RVBUnary<0b0110000, 0b10011, 0b001, OPC_OP_IMM, "crc32.d">, 495 Sched<[]>; 496 497def CRC32C_D : RVBUnary<0b0110000, 0b11011, 0b001, OPC_OP_IMM, "crc32c.d">, 498 Sched<[]>; 499} // Predicates = [HasStdExtZbr, IsRV64] 500 501let Predicates = [HasStdExtZbc] in { 502def CLMULR : ALU_rr<0b0000101, 0b010, "clmulr">, 503 Sched<[WriteCLMUL, ReadCLMUL, ReadCLMUL]>; 504} // Predicates = [HasStdExtZbc] 505 506let Predicates = [HasStdExtZbcOrZbkc] in { 507def CLMUL : ALU_rr<0b0000101, 0b001, "clmul">, 508 Sched<[WriteCLMUL, ReadCLMUL, ReadCLMUL]>; 509def CLMULH : ALU_rr<0b0000101, 0b011, "clmulh">, 510 Sched<[WriteCLMUL, ReadCLMUL, ReadCLMUL]>; 511} // Predicates = [HasStdExtZbcOrZbkc] 512 513let Predicates = [HasStdExtZbb] in { 514def MIN : ALU_rr<0b0000101, 0b100, "min">, 515 Sched<[WriteIALU, ReadIALU, ReadIALU]>; 516def MINU : ALU_rr<0b0000101, 0b101, "minu">, 517 Sched<[WriteIALU, ReadIALU, ReadIALU]>; 518def MAX : ALU_rr<0b0000101, 0b110, "max">, 519 Sched<[WriteIALU, ReadIALU, ReadIALU]>; 520def MAXU : ALU_rr<0b0000101, 0b111, "maxu">, 521 Sched<[WriteIALU, ReadIALU, ReadIALU]>; 522} // Predicates = [HasStdExtZbb] 523 524let Predicates = [HasStdExtZbp] in { 525} // Predicates = [HasStdExtZbp] 526 527let Predicates = [HasStdExtZbe] in { 528// NOTE: These mnemonics are from the 0.94 spec. There is a name conflict with 529// bext in the 0.93 spec. 530def BDECOMPRESS : ALU_rr<0b0100100, 0b110, "bdecompress">, Sched<[]>; 531def BCOMPRESS : ALU_rr<0b0000100, 0b110, "bcompress">, Sched<[]>; 532} // Predicates = [HasStdExtZbe] 533 534let Predicates = [HasStdExtZbe, IsRV64] in { 535// NOTE: These mnemonics are from the 0.94 spec. There is a name conflict with 536// bextw in the 0.93 spec. 537def BDECOMPRESSW : ALUW_rr<0b0100100, 0b110, "bdecompressw">, Sched<[]>; 538def BCOMPRESSW : ALUW_rr<0b0000100, 0b110, "bcompressw">, Sched<[]>; 539} // Predicates = [HasStdExtZbe, IsRV64] 540 541let Predicates = [HasStdExtZbpOrZbkb] in { 542def PACK : ALU_rr<0b0000100, 0b100, "pack">, Sched<[]>; 543def PACKH : ALU_rr<0b0000100, 0b111, "packh">, Sched<[]>; 544} // Predicates = [HasStdExtZbpOrZbkb] 545 546let Predicates = [HasStdExtZbpOrZbkb, IsRV64] in 547def PACKW : ALUW_rr<0b0000100, 0b100, "packw">, Sched<[]>; 548 549let Predicates = [HasStdExtZbp] in 550def PACKU : ALU_rr<0b0100100, 0b100, "packu">, Sched<[]>; 551 552let Predicates = [HasStdExtZbp, IsRV64] in 553def PACKUW : ALUW_rr<0b0100100, 0b100, "packuw">, Sched<[]>; 554 555let Predicates = [HasStdExtZbm, IsRV64] in { 556def BMATFLIP : RVBUnary<0b0110000, 0b00011, 0b001, OPC_OP_IMM, "bmatflip">, 557 Sched<[]>; 558 559def BMATOR : ALU_rr<0b0000100, 0b011, "bmator">, Sched<[]>; 560def BMATXOR : ALU_rr<0b0100100, 0b011, "bmatxor">, Sched<[]>; 561} // Predicates = [HasStdExtZbm, IsRV64] 562 563let Predicates = [HasStdExtZbf] in 564def BFP : ALU_rr<0b0100100, 0b111, "bfp">, 565 Sched<[WriteBFP, ReadBFP, ReadBFP]>; 566 567let Predicates = [HasStdExtZbf, IsRV64] in 568def BFPW : ALUW_rr<0b0100100, 0b111, "bfpw">, 569 Sched<[WriteBFP32, ReadBFP32, ReadBFP32]>; 570 571let Predicates = [HasStdExtZbbOrZbp, IsRV32] in { 572def ZEXT_H_RV32 : RVBUnary<0b0000100, 0b00000, 0b100, OPC_OP, "zext.h">, 573 Sched<[WriteIALU, ReadIALU]>; 574} // Predicates = [HasStdExtZbbOrZbp, IsRV32] 575 576let Predicates = [HasStdExtZbbOrZbp, IsRV64] in { 577def ZEXT_H_RV64 : RVBUnary<0b0000100, 0b00000, 0b100, OPC_OP_32, "zext.h">, 578 Sched<[WriteIALU, ReadIALU]>; 579} // Predicates = [HasStdExtZbbOrZbp, IsRV64] 580 581// We treat rev8 and orc.b as standalone instructions even though they use a 582// portion of the encodings for grevi and gorci. This allows us to support only 583// those encodings when only Zbb is enabled. We do this even when grevi and 584// gorci are available with Zbp. Trying to use 'HasStdExtZbb, NotHasStdExtZbp' 585// causes diagnostics to suggest that Zbp rather than Zbb is required for rev8 586// or gorci. Since Zbb is closer to being finalized than Zbp this will be 587// misleading to users. 588let Predicates = [HasStdExtZbbOrZbpOrZbkb, IsRV32] in { 589def REV8_RV32 : RVBUnary<0b0110100, 0b11000, 0b101, OPC_OP_IMM, "rev8">, 590 Sched<[WriteREV8, ReadREV8]>; 591} // Predicates = [HasStdExtZbbOrZbpOrZbkb, IsRV32] 592 593let Predicates = [HasStdExtZbbOrZbpOrZbkb, IsRV64] in { 594def REV8_RV64 : RVBUnary<0b0110101, 0b11000, 0b101, OPC_OP_IMM, "rev8">, 595 Sched<[WriteREV8, ReadREV8]>; 596} // Predicates = [HasStdExtZbbOrZbpOrZbkb, IsRV64] 597 598let Predicates = [HasStdExtZbbOrZbp] in { 599def ORC_B : RVBUnary<0b0010100, 0b00111, 0b101, OPC_OP_IMM, "orc.b">, 600 Sched<[WriteORCB, ReadORCB]>; 601} // Predicates = [HasStdExtZbbOrZbp] 602 603let Predicates = [HasStdExtZbpOrZbkb] in 604def BREV8 : RVBUnary<0b0110100, 0b00111, 0b101, OPC_OP_IMM, "brev8">; 605 606let Predicates = [HasStdExtZbpOrZbkb, IsRV32] in { 607def ZIP_RV32 : RVBUnary<0b0000100, 0b01111, 0b001, OPC_OP_IMM, "zip">; 608def UNZIP_RV32 : RVBUnary<0b0000100, 0b01111, 0b101, OPC_OP_IMM, "unzip">; 609} // Predicates = [HasStdExtZbkb, IsRV32] 610 611 612//===----------------------------------------------------------------------===// 613// Pseudo Instructions 614//===----------------------------------------------------------------------===// 615 616let Predicates = [HasStdExtZba, IsRV64] in { 617def : InstAlias<"zext.w $rd, $rs", (ADD_UW GPR:$rd, GPR:$rs, X0)>; 618} 619 620let Predicates = [HasStdExtZbp] in { 621def : InstAlias<"rev.p $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b00001)>; 622def : InstAlias<"rev2.n $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b00010)>; 623def : InstAlias<"rev.n $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b00011)>; 624def : InstAlias<"rev4.b $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b00100)>; 625def : InstAlias<"rev2.b $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b00110)>; 626def : InstAlias<"rev8.h $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b01000)>; 627def : InstAlias<"rev4.h $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b01100)>; 628def : InstAlias<"rev2.h $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b01110)>; 629def : InstAlias<"rev.h $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b01111)>; 630def : InstAlias<"rev.b $rd, $rs", (BREV8 GPR:$rd, GPR:$rs)>; 631 632def : InstAlias<"zip.n $rd, $rs", (SHFLI GPR:$rd, GPR:$rs, 0b0001)>; 633def : InstAlias<"unzip.n $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b0001)>; 634def : InstAlias<"zip2.b $rd, $rs", (SHFLI GPR:$rd, GPR:$rs, 0b0010)>; 635def : InstAlias<"unzip2.b $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b0010)>; 636def : InstAlias<"zip.b $rd, $rs", (SHFLI GPR:$rd, GPR:$rs, 0b0011)>; 637def : InstAlias<"unzip.b $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b0011)>; 638def : InstAlias<"zip4.h $rd, $rs", (SHFLI GPR:$rd, GPR:$rs, 0b0100)>; 639def : InstAlias<"unzip4.h $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b0100)>; 640def : InstAlias<"zip2.h $rd, $rs", (SHFLI GPR:$rd, GPR:$rs, 0b0110)>; 641def : InstAlias<"unzip2.h $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b0110)>; 642def : InstAlias<"zip.h $rd, $rs", (SHFLI GPR:$rd, GPR:$rs, 0b0111)>; 643def : InstAlias<"unzip.h $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b0111)>; 644 645def : InstAlias<"orc.p $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b00001)>; 646def : InstAlias<"orc2.n $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b00010)>; 647def : InstAlias<"orc.n $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b00011)>; 648def : InstAlias<"orc4.b $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b00100)>; 649def : InstAlias<"orc2.b $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b00110)>; 650// orc.b is considered an instruction rather than an alias. 651def : InstAlias<"orc8.h $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b01000)>; 652def : InstAlias<"orc4.h $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b01100)>; 653def : InstAlias<"orc2.h $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b01110)>; 654def : InstAlias<"orc.h $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b01111)>; 655} // Predicates = [HasStdExtZbp] 656 657let Predicates = [HasStdExtZbp, IsRV32] in { 658def : InstAlias<"rev16 $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b10000)>; 659// rev8 is considered an instruction rather than an alias. 660def : InstAlias<"rev4 $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b11100)>; 661def : InstAlias<"rev2 $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b11110)>; 662def : InstAlias<"rev $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b11111)>; 663 664def : InstAlias<"zip8 $rd, $rs", (SHFLI GPR:$rd, GPR:$rs, 0b1000)>; 665def : InstAlias<"unzip8 $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b1000)>; 666def : InstAlias<"zip4 $rd, $rs", (SHFLI GPR:$rd, GPR:$rs, 0b1100)>; 667def : InstAlias<"unzip4 $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b1100)>; 668def : InstAlias<"zip2 $rd, $rs", (SHFLI GPR:$rd, GPR:$rs, 0b1110)>; 669def : InstAlias<"unzip2 $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b1110)>; 670// zip and unzip are considered instructions rather than an alias. 671 672def : InstAlias<"orc16 $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b10000)>; 673def : InstAlias<"orc8 $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b11000)>; 674def : InstAlias<"orc4 $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b11100)>; 675def : InstAlias<"orc2 $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b11110)>; 676def : InstAlias<"orc $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b11111)>; 677} // Predicates = [HasStdExtZbp, IsRV32] 678 679let Predicates = [HasStdExtZbp, IsRV64] in { 680def : InstAlias<"rev16.w $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b010000)>; 681def : InstAlias<"rev8.w $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b011000)>; 682def : InstAlias<"rev4.w $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b011100)>; 683def : InstAlias<"rev2.w $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b011110)>; 684def : InstAlias<"rev.w $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b011111)>; 685def : InstAlias<"rev32 $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b100000)>; 686def : InstAlias<"rev16 $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b110000)>; 687// rev8 is considered an instruction rather than an alias. 688def : InstAlias<"rev4 $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b111100)>; 689def : InstAlias<"rev2 $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b111110)>; 690def : InstAlias<"rev $rd, $rs", (GREVI GPR:$rd, GPR:$rs, 0b111111)>; 691 692def : InstAlias<"zip8.w $rd, $rs", (SHFLI GPR:$rd, GPR:$rs, 0b01000)>; 693def : InstAlias<"unzip8.w $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b01000)>; 694def : InstAlias<"zip4.w $rd, $rs", (SHFLI GPR:$rd, GPR:$rs, 0b01100)>; 695def : InstAlias<"unzip4.w $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b01100)>; 696def : InstAlias<"zip2.w $rd, $rs", (SHFLI GPR:$rd, GPR:$rs, 0b01110)>; 697def : InstAlias<"unzip2.w $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b01110)>; 698def : InstAlias<"zip.w $rd, $rs", (SHFLI GPR:$rd, GPR:$rs, 0b01111)>; 699def : InstAlias<"unzip.w $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b01111)>; 700def : InstAlias<"zip16 $rd, $rs", (SHFLI GPR:$rd, GPR:$rs, 0b10000)>; 701def : InstAlias<"unzip16 $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b10000)>; 702def : InstAlias<"zip8 $rd, $rs", (SHFLI GPR:$rd, GPR:$rs, 0b11000)>; 703def : InstAlias<"unzip8 $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b11000)>; 704def : InstAlias<"zip4 $rd, $rs", (SHFLI GPR:$rd, GPR:$rs, 0b11100)>; 705def : InstAlias<"unzip4 $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b11100)>; 706def : InstAlias<"zip2 $rd, $rs", (SHFLI GPR:$rd, GPR:$rs, 0b11110)>; 707def : InstAlias<"unzip2 $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b11110)>; 708def : InstAlias<"zip $rd, $rs", (SHFLI GPR:$rd, GPR:$rs, 0b11111)>; 709def : InstAlias<"unzip $rd, $rs", (UNSHFLI GPR:$rd, GPR:$rs, 0b11111)>; 710 711def : InstAlias<"orc16.w $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b010000)>; 712def : InstAlias<"orc8.w $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b011000)>; 713def : InstAlias<"orc4.w $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b011100)>; 714def : InstAlias<"orc2.w $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b011110)>; 715def : InstAlias<"orc.w $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b011111)>; 716def : InstAlias<"orc32 $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b100000)>; 717def : InstAlias<"orc16 $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b110000)>; 718def : InstAlias<"orc8 $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b111000)>; 719def : InstAlias<"orc4 $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b111100)>; 720def : InstAlias<"orc2 $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b111110)>; 721def : InstAlias<"orc $rd, $rs", (GORCI GPR:$rd, GPR:$rs, 0b111111)>; 722} // Predicates = [HasStdExtZbp, IsRV64] 723 724let Predicates = [HasStdExtZbbOrZbp] in { 725def : InstAlias<"ror $rd, $rs1, $shamt", 726 (RORI GPR:$rd, GPR:$rs1, uimmlog2xlen:$shamt), 0>; 727} // Predicates = [HasStdExtZbbOrZbp] 728 729let Predicates = [HasStdExtZbbOrZbp, IsRV64] in { 730def : InstAlias<"rorw $rd, $rs1, $shamt", 731 (RORIW GPR:$rd, GPR:$rs1, uimm5:$shamt), 0>; 732} // Predicates = [HasStdExtZbbOrZbp, IsRV64] 733 734let Predicates = [HasStdExtZbp] in { 735def : InstAlias<"grev $rd, $rs1, $shamt", 736 (GREVI GPR:$rd, GPR:$rs1, uimmlog2xlen:$shamt), 0>; 737def : InstAlias<"gorc $rd, $rs1, $shamt", 738 (GORCI GPR:$rd, GPR:$rs1, uimmlog2xlen:$shamt), 0>; 739def : InstAlias<"shfl $rd, $rs1, $shamt", 740 (SHFLI GPR:$rd, GPR:$rs1, shfl_uimm:$shamt), 0>; 741def : InstAlias<"unshfl $rd, $rs1, $shamt", 742 (UNSHFLI GPR:$rd, GPR:$rs1, shfl_uimm:$shamt), 0>; 743} // Predicates = [HasStdExtZbp] 744 745let Predicates = [HasStdExtZbp, IsRV64] in { 746def : InstAlias<"grevw $rd, $rs1, $shamt", 747 (GREVIW GPR:$rd, GPR:$rs1, uimm5:$shamt), 0>; 748def : InstAlias<"gorcw $rd, $rs1, $shamt", 749 (GORCIW GPR:$rd, GPR:$rs1, uimm5:$shamt), 0>; 750} // Predicates = [HasStdExtZbp, IsRV64] 751 752// Zbp is unratified and that it would likely adopt the already ratified Zbkx names. 753// Thus current Zbp instructions are defined as aliases for Zbkx instructions. 754let Predicates = [HasStdExtZbp] in { 755 def : InstAlias<"xperm.b $rd, $rs1, $rs2", 756 (XPERM8 GPR:$rd, GPR:$rs1, GPR:$rs2)>; 757 def : InstAlias<"xperm.n $rd, $rs1, $rs2", 758 (XPERM4 GPR:$rd, GPR:$rs1, GPR:$rs2)>; 759} // Predicates = [HasStdExtZbp] 760 761let Predicates = [HasStdExtZbs] in { 762def : InstAlias<"bset $rd, $rs1, $shamt", 763 (BSETI GPR:$rd, GPR:$rs1, uimmlog2xlen:$shamt), 0>; 764def : InstAlias<"bclr $rd, $rs1, $shamt", 765 (BCLRI GPR:$rd, GPR:$rs1, uimmlog2xlen:$shamt), 0>; 766def : InstAlias<"binv $rd, $rs1, $shamt", 767 (BINVI GPR:$rd, GPR:$rs1, uimmlog2xlen:$shamt), 0>; 768def : InstAlias<"bext $rd, $rs1, $shamt", 769 (BEXTI GPR:$rd, GPR:$rs1, uimmlog2xlen:$shamt), 0>; 770} // Predicates = [HasStdExtZbs] 771 772//===----------------------------------------------------------------------===// 773// Codegen patterns 774//===----------------------------------------------------------------------===// 775 776let Predicates = [HasStdExtZbbOrZbpOrZbkb] in { 777def : Pat<(and GPR:$rs1, (not GPR:$rs2)), (ANDN GPR:$rs1, GPR:$rs2)>; 778def : Pat<(or GPR:$rs1, (not GPR:$rs2)), (ORN GPR:$rs1, GPR:$rs2)>; 779def : Pat<(xor GPR:$rs1, (not GPR:$rs2)), (XNOR GPR:$rs1, GPR:$rs2)>; 780} // Predicates = [HasStdExtZbbOrZbpOrZbkb] 781 782let Predicates = [HasStdExtZbbOrZbpOrZbkb] in { 783def : PatGprGpr<rotl, ROL>; 784def : PatGprGpr<rotr, ROR>; 785 786def : PatGprImm<rotr, RORI, uimmlog2xlen>; 787// There's no encoding for roli in the the 'B' extension as it can be 788// implemented with rori by negating the immediate. 789def : Pat<(rotl GPR:$rs1, uimmlog2xlen:$shamt), 790 (RORI GPR:$rs1, (ImmSubFromXLen uimmlog2xlen:$shamt))>; 791} // Predicates = [HasStdExtZbbOrZbpOrZbkb] 792 793let Predicates = [HasStdExtZbbOrZbpOrZbkb, IsRV64] in { 794def : PatGprGpr<riscv_rolw, ROLW>; 795def : PatGprGpr<riscv_rorw, RORW>; 796def : PatGprImm<riscv_rorw, RORIW, uimm5>; 797def : Pat<(riscv_rolw GPR:$rs1, uimm5:$rs2), 798 (RORIW GPR:$rs1, (ImmSubFrom32 uimm5:$rs2))>; 799} // Predicates = [HasStdExtZbbOrZbpOrZbkb, IsRV64] 800 801let Predicates = [HasStdExtZbs] in { 802def : Pat<(and (not (shiftop<shl> 1, GPR:$rs2)), GPR:$rs1), 803 (BCLR GPR:$rs1, GPR:$rs2)>; 804def : Pat<(and (rotl -2, GPR:$rs2), GPR:$rs1), (BCLR GPR:$rs1, GPR:$rs2)>; 805def : Pat<(or (shiftop<shl> 1, GPR:$rs2), GPR:$rs1), 806 (BSET GPR:$rs1, GPR:$rs2)>; 807def : Pat<(xor (shiftop<shl> 1, GPR:$rs2), GPR:$rs1), 808 (BINV GPR:$rs1, GPR:$rs2)>; 809def : Pat<(and (shiftop<srl> GPR:$rs1, GPR:$rs2), 1), 810 (BEXT GPR:$rs1, GPR:$rs2)>; 811 812def : Pat<(shiftop<shl> 1, GPR:$rs2), 813 (BSET X0, GPR:$rs2)>; 814 815def : Pat<(and GPR:$rs1, BCLRMask:$mask), 816 (BCLRI GPR:$rs1, BCLRMask:$mask)>; 817def : Pat<(or GPR:$rs1, BSETINVMask:$mask), 818 (BSETI GPR:$rs1, BSETINVMask:$mask)>; 819def : Pat<(xor GPR:$rs1, BSETINVMask:$mask), 820 (BINVI GPR:$rs1, BSETINVMask:$mask)>; 821 822def : Pat<(and (srl GPR:$rs1, uimmlog2xlen:$shamt), (XLenVT 1)), 823 (BEXTI GPR:$rs1, uimmlog2xlen:$shamt)>; 824 825def : Pat<(and (not (srl GPR:$rs1, uimmlog2xlen:$shamt)), (XLenVT 1)), 826 (XORI (BEXTI GPR:$rs1, uimmlog2xlen:$shamt), (XLenVT 1))>; 827 828def : Pat<(or GPR:$r, BSETINVTwoBitsMask:$i), 829 (BSETI (BSETI GPR:$r, (TrailingZerosXForm BSETINVTwoBitsMask:$i)), 830 (BSETINVTwoBitsMaskHigh BSETINVTwoBitsMask:$i))>; 831def : Pat<(xor GPR:$r, BSETINVTwoBitsMask:$i), 832 (BINVI (BINVI GPR:$r, (TrailingZerosXForm BSETINVTwoBitsMask:$i)), 833 (BSETINVTwoBitsMaskHigh BSETINVTwoBitsMask:$i))>; 834def : Pat<(or GPR:$r, BSETINVORIMask:$i), 835 (BSETI (ORI GPR:$r, (BSETINVORIMaskLow BSETINVORIMask:$i)), 836 (BSETINVTwoBitsMaskHigh BSETINVORIMask:$i))>; 837def : Pat<(xor GPR:$r, BSETINVORIMask:$i), 838 (BINVI (XORI GPR:$r, (BSETINVORIMaskLow BSETINVORIMask:$i)), 839 (BSETINVTwoBitsMaskHigh BSETINVORIMask:$i))>; 840def : Pat<(and GPR:$r, BCLRITwoBitsMask:$i), 841 (BCLRI (BCLRI GPR:$r, (BCLRITwoBitsMaskLow BCLRITwoBitsMask:$i)), 842 (BCLRITwoBitsMaskHigh BCLRITwoBitsMask:$i))>; 843def : Pat<(and GPR:$r, BCLRIANDIMask:$i), 844 (BCLRI (ANDI GPR:$r, (BCLRIANDIMaskLow BCLRIANDIMask:$i)), 845 (BCLRITwoBitsMaskHigh BCLRIANDIMask:$i))>; 846} 847 848let Predicates = [HasStdExtZbbOrZbp] in { 849// We treat orc.b as a separate instruction, so match it directly. We also 850// lower the Zbb orc.b intrinsic to this. 851def : Pat<(riscv_gorc GPR:$rs1, 7), (ORC_B GPR:$rs1)>; 852} 853 854let Predicates = [HasStdExtZbpOrZbkb] in { 855// We treat brev8 as a separate instruction, so match it directly. We also 856// use this for brev8 when lowering bitreverse with Zbkb. 857def : Pat<(riscv_grev GPR:$rs1, 7), (BREV8 GPR:$rs1)>; 858 859// We treat zip and unzip as separate instructions, so match it directly. 860def : Pat<(i32 (riscv_shfl GPR:$rs1, 15)), (ZIP_RV32 GPR:$rs1)>; 861def : Pat<(i32 (riscv_unshfl GPR:$rs1, 15)), (UNZIP_RV32 GPR:$rs1)>; 862} 863 864let Predicates = [HasStdExtZbp] in { 865def : PatGprGpr<riscv_grev, GREV>; 866def : PatGprGpr<riscv_gorc, GORC>; 867def : PatGprImm<riscv_grev, GREVI, uimmlog2xlen>; 868def : PatGprImm<riscv_gorc, GORCI, uimmlog2xlen>; 869 870def : PatGprGpr<riscv_shfl, SHFL>; 871def : PatGprGpr<riscv_unshfl, UNSHFL>; 872def : PatGprImm<riscv_shfl, SHFLI, shfl_uimm>; 873def : PatGprImm<riscv_unshfl, UNSHFLI, shfl_uimm>; 874 875def : PatGprGpr<int_riscv_xperm_n, XPERM4>; 876def : PatGprGpr<int_riscv_xperm_b, XPERM8>; 877def : PatGprGpr<int_riscv_xperm_h, XPERM_H>; 878} // Predicates = [HasStdExtZbp] 879 880let Predicates = [HasStdExtZbp, IsRV64] in { 881def : PatGprGpr<riscv_grevw, GREVW>; 882def : PatGprGpr<riscv_gorcw, GORCW>; 883def : PatGprImm<riscv_grevw, GREVIW, uimm5>; 884def : PatGprImm<riscv_gorcw, GORCIW, uimm5>; 885 886// FIXME: Move to DAG combine. 887def : Pat<(riscv_rorw (riscv_grevw GPR:$rs1, 24), 16), (GREVIW GPR:$rs1, 8)>; 888def : Pat<(riscv_rolw (riscv_grevw GPR:$rs1, 24), 16), (GREVIW GPR:$rs1, 8)>; 889 890def : PatGprGpr<riscv_shflw, SHFLW>; 891def : PatGprGpr<riscv_unshflw, UNSHFLW>; 892} // Predicates = [HasStdExtZbp, IsRV64] 893 894let Predicates = [HasStdExtZbp, IsRV64] in 895def : PatGprGpr<int_riscv_xperm_w, XPERM_W>; 896 897let Predicates = [HasStdExtZbp, IsRV32] in { 898// FIXME : Move to DAG combine. 899def : Pat<(i32 (rotr (riscv_grev GPR:$rs1, 24), (i32 16))), (GREVI GPR:$rs1, 8)>; 900def : Pat<(i32 (rotl (riscv_grev GPR:$rs1, 24), (i32 16))), (GREVI GPR:$rs1, 8)>; 901 902// We treat rev8 as a separate instruction, so match it directly. 903def : Pat<(i32 (riscv_grev GPR:$rs1, 24)), (REV8_RV32 GPR:$rs1)>; 904} // Predicates = [HasStdExtZbp, IsRV32] 905 906let Predicates = [HasStdExtZbp, IsRV64] in { 907// We treat rev8 as a separate instruction, so match it directly. 908def : Pat<(i64 (riscv_grev GPR:$rs1, 56)), (REV8_RV64 GPR:$rs1)>; 909} // Predicates = [HasStdExtZbp, IsRV64] 910 911let Predicates = [HasStdExtZbt] in { 912def : Pat<(or (and (not GPR:$rs2), GPR:$rs3), (and GPR:$rs2, GPR:$rs1)), 913 (CMIX GPR:$rs1, GPR:$rs2, GPR:$rs3)>; 914 915def : Pat<(select (XLenVT (setne GPR:$rs2, 0)), GPR:$rs1, GPR:$rs3), 916 (CMOV GPR:$rs1, GPR:$rs2, GPR:$rs3)>; 917def : Pat<(select (XLenVT (seteq GPR:$rs2, 0)), GPR:$rs3, GPR:$rs1), 918 (CMOV GPR:$rs1, GPR:$rs2, GPR:$rs3)>; 919def : Pat<(select (XLenVT (setne GPR:$x, simm12_plus1:$y)), GPR:$rs1, GPR:$rs3), 920 (CMOV GPR:$rs1, (ADDI GPR:$x, (NegImm simm12_plus1:$y)), GPR:$rs3)>; 921def : Pat<(select (XLenVT (seteq GPR:$x, simm12_plus1:$y)), GPR:$rs3, GPR:$rs1), 922 (CMOV GPR:$rs1, (ADDI GPR:$x, (NegImm simm12_plus1:$y)), GPR:$rs3)>; 923def : Pat<(select (XLenVT (setne GPR:$x, GPR:$y)), GPR:$rs1, GPR:$rs3), 924 (CMOV GPR:$rs1, (XOR GPR:$x, GPR:$y), GPR:$rs3)>; 925def : Pat<(select (XLenVT (seteq GPR:$x, GPR:$y)), GPR:$rs3, GPR:$rs1), 926 (CMOV GPR:$rs1, (XOR GPR:$x, GPR:$y), GPR:$rs3)>; 927def : Pat<(select (XLenVT (setuge GPR:$x, GPR:$y)), GPR:$rs3, GPR:$rs1), 928 (CMOV GPR:$rs1, (SLTU GPR:$x, GPR:$y), GPR:$rs3)>; 929def : Pat<(select (XLenVT (setule GPR:$y, GPR:$x)), GPR:$rs3, GPR:$rs1), 930 (CMOV GPR:$rs1, (SLTU GPR:$x, GPR:$y), GPR:$rs3)>; 931def : Pat<(select (XLenVT (setge GPR:$x, GPR:$y)), GPR:$rs3, GPR:$rs1), 932 (CMOV GPR:$rs1, (SLT GPR:$x, GPR:$y), GPR:$rs3)>; 933def : Pat<(select (XLenVT (setle GPR:$y, GPR:$x)), GPR:$rs3, GPR:$rs1), 934 (CMOV GPR:$rs1, (SLT GPR:$x, GPR:$y), GPR:$rs3)>; 935def : Pat<(select GPR:$rs2, GPR:$rs1, GPR:$rs3), 936 (CMOV GPR:$rs1, GPR:$rs2, GPR:$rs3)>; 937} // Predicates = [HasStdExtZbt] 938 939let Predicates = [HasStdExtZbt] in { 940def : Pat<(riscv_fsl GPR:$rs1, GPR:$rs3, GPR:$rs2), 941 (FSL GPR:$rs1, GPR:$rs2, GPR:$rs3)>; 942def : Pat<(riscv_fsr GPR:$rs1, GPR:$rs3, GPR:$rs2), 943 (FSR GPR:$rs1, GPR:$rs2, GPR:$rs3)>; 944def : Pat<(riscv_fsr GPR:$rs1, GPR:$rs3, uimmlog2xlen:$shamt), 945 (FSRI GPR:$rs1, GPR:$rs3, uimmlog2xlen:$shamt)>; 946// We can use FSRI for FSL by immediate if we subtract the immediate from 947// XLen and swap the operands. 948def : Pat<(riscv_fsl GPR:$rs3, GPR:$rs1, uimmlog2xlen:$shamt), 949 (FSRI GPR:$rs1, GPR:$rs3, (ImmSubFromXLen uimmlog2xlen:$shamt))>; 950} // Predicates = [HasStdExtZbt] 951 952let Predicates = [HasStdExtZbt, IsRV64] in { 953def : Pat<(riscv_fslw GPR:$rs1, GPR:$rs3, GPR:$rs2), 954 (FSLW GPR:$rs1, GPR:$rs2, GPR:$rs3)>; 955def : Pat<(riscv_fsrw GPR:$rs1, GPR:$rs3, GPR:$rs2), 956 (FSRW GPR:$rs1, GPR:$rs2, GPR:$rs3)>; 957def : Pat<(riscv_fsrw GPR:$rs1, GPR:$rs3, uimm5:$shamt), 958 (FSRIW GPR:$rs1, GPR:$rs3, uimm5:$shamt)>; 959// We can use FSRIW for FSLW by immediate if we subtract the immediate from 960// 32 and swap the operands. 961def : Pat<(riscv_fslw GPR:$rs3, GPR:$rs1, uimm5:$shamt), 962 (FSRIW GPR:$rs1, GPR:$rs3, (ImmSubFrom32 uimm5:$shamt))>; 963} // Predicates = [HasStdExtZbt, IsRV64] 964 965let Predicates = [HasStdExtZbb] in { 966def : PatGpr<ctlz, CLZ>; 967def : PatGpr<cttz, CTZ>; 968def : PatGpr<ctpop, CPOP>; 969} // Predicates = [HasStdExtZbb] 970 971let Predicates = [HasStdExtZbb, IsRV64] in { 972def : PatGpr<riscv_clzw, CLZW>; 973def : PatGpr<riscv_ctzw, CTZW>; 974def : Pat<(i64 (ctpop (i64 (zexti32 (i64 GPR:$rs1))))), (CPOPW GPR:$rs1)>; 975} // Predicates = [HasStdExtZbb, IsRV64] 976 977let Predicates = [HasStdExtZbb] in { 978def : Pat<(sext_inreg GPR:$rs1, i8), (SEXT_B GPR:$rs1)>; 979def : Pat<(sext_inreg GPR:$rs1, i16), (SEXT_H GPR:$rs1)>; 980} 981 982let Predicates = [HasStdExtZbb] in { 983def : PatGprGpr<smin, MIN>; 984def : PatGprGpr<smax, MAX>; 985def : PatGprGpr<umin, MINU>; 986def : PatGprGpr<umax, MAXU>; 987} // Predicates = [HasStdExtZbb] 988 989let Predicates = [HasStdExtZbbOrZbkb, IsRV32] in { 990def : Pat<(i32 (bswap GPR:$rs1)), (REV8_RV32 GPR:$rs1)>; 991} // Predicates = [HasStdExtZbbOrZbkb, IsRV32] 992 993let Predicates = [HasStdExtZbbOrZbkb, IsRV64] in { 994def : Pat<(i64 (bswap GPR:$rs1)), (REV8_RV64 GPR:$rs1)>; 995} // Predicates = [HasStdExtZbbOrZbkb, IsRV64] 996 997let Predicates = [HasStdExtZbpOrZbkb] in { 998def : Pat<(or (and (shl GPR:$rs2, (XLenVT 8)), 0xFFFF), 999 (and GPR:$rs1, 0x00FF)), 1000 (PACKH GPR:$rs1, GPR:$rs2)>; 1001def : Pat<(or (shl (and GPR:$rs2, 0x00FF), (XLenVT 8)), 1002 (and GPR:$rs1, 0x00FF)), 1003 (PACKH GPR:$rs1, GPR:$rs2)>; 1004} // Predicates = [HasStdExtZbpOrZbkb] 1005 1006let Predicates = [HasStdExtZbpOrZbkb, IsRV32] in 1007def : Pat<(i32 (or (and GPR:$rs1, 0x0000FFFF), (shl GPR:$rs2, (i32 16)))), 1008 (PACK GPR:$rs1, GPR:$rs2)>; 1009 1010let Predicates = [HasStdExtZbpOrZbkb, IsRV64] in { 1011def : Pat<(i64 (or (and GPR:$rs1, 0x00000000FFFFFFFF), (shl GPR:$rs2, (i64 32)))), 1012 (PACK GPR:$rs1, GPR:$rs2)>; 1013 1014def : Pat<(i64 (sext_inreg (or (shl GPR:$rs2, (i64 16)), 1015 (and GPR:$rs1, 0x000000000000FFFF)), 1016 i32)), 1017 (PACKW GPR:$rs1, GPR:$rs2)>; 1018def : Pat<(i64 (or (sext_inreg (shl GPR:$rs2, (i64 16)), i32), 1019 (and GPR:$rs1, 0x000000000000FFFF))), 1020 (PACKW GPR:$rs1, GPR:$rs2)>; 1021} 1022 1023let Predicates = [HasStdExtZbp, IsRV32] in 1024def : Pat<(i32 (or (and GPR:$rs2, 0xFFFF0000), (srl GPR:$rs1, (i32 16)))), 1025 (PACKU GPR:$rs1, GPR:$rs2)>; 1026 1027let Predicates = [HasStdExtZbp, IsRV64] in { 1028def : Pat<(i64 (or (and GPR:$rs2, 0xFFFFFFFF00000000), (srl GPR:$rs1, (i64 32)))), 1029 (PACKU GPR:$rs1, GPR:$rs2)>; 1030 1031def : Pat<(i64 (or (and (assertsexti32 GPR:$rs2), 0xFFFFFFFFFFFF0000), 1032 (srl (and GPR:$rs1, 0xFFFFFFFF), (i64 16)))), 1033 (PACKUW GPR:$rs1, GPR:$rs2)>; 1034} 1035 1036let Predicates = [HasStdExtZbbOrZbp, IsRV32] in 1037def : Pat<(i32 (and GPR:$rs, 0xFFFF)), (ZEXT_H_RV32 GPR:$rs)>; 1038let Predicates = [HasStdExtZbbOrZbp, IsRV64] in 1039def : Pat<(i64 (and GPR:$rs, 0xFFFF)), (ZEXT_H_RV64 GPR:$rs)>; 1040 1041// Pattern to exclude simm12 immediates from matching. 1042def non_imm12 : PatLeaf<(XLenVT GPR:$a), [{ 1043 auto *C = dyn_cast<ConstantSDNode>(N); 1044 return !C || !isInt<12>(C->getSExtValue()); 1045}]>; 1046 1047let Predicates = [HasStdExtZba] in { 1048def : Pat<(add (shl GPR:$rs1, (XLenVT 1)), non_imm12:$rs2), 1049 (SH1ADD GPR:$rs1, GPR:$rs2)>; 1050def : Pat<(add (shl GPR:$rs1, (XLenVT 2)), non_imm12:$rs2), 1051 (SH2ADD GPR:$rs1, GPR:$rs2)>; 1052def : Pat<(add (shl GPR:$rs1, (XLenVT 3)), non_imm12:$rs2), 1053 (SH3ADD GPR:$rs1, GPR:$rs2)>; 1054 1055def : Pat<(add (mul_oneuse GPR:$rs1, (XLenVT 6)), GPR:$rs2), 1056 (SH1ADD (SH1ADD GPR:$rs1, GPR:$rs1), GPR:$rs2)>; 1057def : Pat<(add (mul_oneuse GPR:$rs1, (XLenVT 10)), GPR:$rs2), 1058 (SH1ADD (SH2ADD GPR:$rs1, GPR:$rs1), GPR:$rs2)>; 1059def : Pat<(add (mul_oneuse GPR:$rs1, (XLenVT 18)), GPR:$rs2), 1060 (SH1ADD (SH3ADD GPR:$rs1, GPR:$rs1), GPR:$rs2)>; 1061def : Pat<(add (mul_oneuse GPR:$rs1, (XLenVT 12)), GPR:$rs2), 1062 (SH2ADD (SH1ADD GPR:$rs1, GPR:$rs1), GPR:$rs2)>; 1063def : Pat<(add (mul_oneuse GPR:$rs1, (XLenVT 20)), GPR:$rs2), 1064 (SH2ADD (SH2ADD GPR:$rs1, GPR:$rs1), GPR:$rs2)>; 1065def : Pat<(add (mul_oneuse GPR:$rs1, (XLenVT 36)), GPR:$rs2), 1066 (SH2ADD (SH3ADD GPR:$rs1, GPR:$rs1), GPR:$rs2)>; 1067def : Pat<(add (mul_oneuse GPR:$rs1, (XLenVT 24)), GPR:$rs2), 1068 (SH3ADD (SH1ADD GPR:$rs1, GPR:$rs1), GPR:$rs2)>; 1069def : Pat<(add (mul_oneuse GPR:$rs1, (XLenVT 40)), GPR:$rs2), 1070 (SH3ADD (SH2ADD GPR:$rs1, GPR:$rs1), GPR:$rs2)>; 1071def : Pat<(add (mul_oneuse GPR:$rs1, (XLenVT 72)), GPR:$rs2), 1072 (SH3ADD (SH3ADD GPR:$rs1, GPR:$rs1), GPR:$rs2)>; 1073 1074def : Pat<(add GPR:$r, CSImm12MulBy4:$i), 1075 (SH2ADD (ADDI X0, (SimmShiftRightBy2XForm CSImm12MulBy4:$i)), 1076 GPR:$r)>; 1077def : Pat<(add GPR:$r, CSImm12MulBy8:$i), 1078 (SH3ADD (ADDI X0, (SimmShiftRightBy3XForm CSImm12MulBy8:$i)), 1079 GPR:$r)>; 1080 1081def : Pat<(mul GPR:$r, C3LeftShift:$i), 1082 (SLLI (SH1ADD GPR:$r, GPR:$r), 1083 (TrailingZerosXForm C3LeftShift:$i))>; 1084def : Pat<(mul GPR:$r, C5LeftShift:$i), 1085 (SLLI (SH2ADD GPR:$r, GPR:$r), 1086 (TrailingZerosXForm C5LeftShift:$i))>; 1087def : Pat<(mul GPR:$r, C9LeftShift:$i), 1088 (SLLI (SH3ADD GPR:$r, GPR:$r), 1089 (TrailingZerosXForm C9LeftShift:$i))>; 1090 1091def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 11)), 1092 (SH1ADD (SH2ADD GPR:$r, GPR:$r), GPR:$r)>; 1093def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 19)), 1094 (SH1ADD (SH3ADD GPR:$r, GPR:$r), GPR:$r)>; 1095def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 13)), 1096 (SH2ADD (SH1ADD GPR:$r, GPR:$r), GPR:$r)>; 1097def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 21)), 1098 (SH2ADD (SH2ADD GPR:$r, GPR:$r), GPR:$r)>; 1099def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 37)), 1100 (SH2ADD (SH3ADD GPR:$r, GPR:$r), GPR:$r)>; 1101def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 25)), 1102 (SH3ADD (SH1ADD GPR:$r, GPR:$r), GPR:$r)>; 1103def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 41)), 1104 (SH3ADD (SH2ADD GPR:$r, GPR:$r), GPR:$r)>; 1105def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 73)), 1106 (SH3ADD (SH3ADD GPR:$r, GPR:$r), GPR:$r)>; 1107def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 27)), 1108 (SH1ADD (SH3ADD GPR:$r, GPR:$r), (SH3ADD GPR:$r, GPR:$r))>; 1109def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 45)), 1110 (SH2ADD (SH3ADD GPR:$r, GPR:$r), (SH3ADD GPR:$r, GPR:$r))>; 1111def : Pat<(mul_const_oneuse GPR:$r, (XLenVT 81)), 1112 (SH3ADD (SH3ADD GPR:$r, GPR:$r), (SH3ADD GPR:$r, GPR:$r))>; 1113} // Predicates = [HasStdExtZba] 1114 1115let Predicates = [HasStdExtZba, IsRV64] in { 1116def : Pat<(i64 (shl (and GPR:$rs1, 0xFFFFFFFF), uimm5:$shamt)), 1117 (SLLI_UW GPR:$rs1, uimm5:$shamt)>; 1118def : Pat<(i64 (add (and GPR:$rs1, 0xFFFFFFFF), non_imm12:$rs2)), 1119 (ADD_UW GPR:$rs1, GPR:$rs2)>; 1120def : Pat<(i64 (and GPR:$rs, 0xFFFFFFFF)), (ADD_UW GPR:$rs, X0)>; 1121 1122def : Pat<(i64 (add (shl (and GPR:$rs1, 0xFFFFFFFF), (i64 1)), non_imm12:$rs2)), 1123 (SH1ADD_UW GPR:$rs1, GPR:$rs2)>; 1124def : Pat<(i64 (add (shl (and GPR:$rs1, 0xFFFFFFFF), (i64 2)), non_imm12:$rs2)), 1125 (SH2ADD_UW GPR:$rs1, GPR:$rs2)>; 1126def : Pat<(i64 (add (shl (and GPR:$rs1, 0xFFFFFFFF), (i64 3)), non_imm12:$rs2)), 1127 (SH3ADD_UW GPR:$rs1, GPR:$rs2)>; 1128 1129def : Pat<(i64 (add (and (shl GPR:$rs1, (i64 1)), 0x1FFFFFFFF), non_imm12:$rs2)), 1130 (SH1ADD_UW GPR:$rs1, GPR:$rs2)>; 1131def : Pat<(i64 (add (and (shl GPR:$rs1, (i64 2)), 0x3FFFFFFFF), non_imm12:$rs2)), 1132 (SH2ADD_UW GPR:$rs1, GPR:$rs2)>; 1133def : Pat<(i64 (add (and (shl GPR:$rs1, (i64 3)), 0x7FFFFFFFF), non_imm12:$rs2)), 1134 (SH3ADD_UW GPR:$rs1, GPR:$rs2)>; 1135} // Predicates = [HasStdExtZba, IsRV64] 1136 1137let Predicates = [HasStdExtZbcOrZbkc] in { 1138def : PatGprGpr<int_riscv_clmul, CLMUL>; 1139def : PatGprGpr<int_riscv_clmulh, CLMULH>; 1140} // Predicates = [HasStdExtZbcOrZbkc] 1141 1142let Predicates = [HasStdExtZbc] in 1143def : PatGprGpr<int_riscv_clmulr, CLMULR>; 1144 1145let Predicates = [HasStdExtZbe] in { 1146def : PatGprGpr<riscv_bcompress, BCOMPRESS>; 1147def : PatGprGpr<riscv_bdecompress, BDECOMPRESS>; 1148} // Predicates = [HasStdExtZbe] 1149 1150let Predicates = [HasStdExtZbe, IsRV64] in { 1151def : PatGprGpr<riscv_bcompressw, BCOMPRESSW>; 1152def : PatGprGpr<riscv_bdecompressw, BDECOMPRESSW>; 1153} // Predicates = [HasStdExtZbe, IsRV64] 1154 1155let Predicates = [HasStdExtZbr] in { 1156def : PatGpr<int_riscv_crc32_b, CRC32_B>; 1157def : PatGpr<int_riscv_crc32_h, CRC32_H>; 1158def : PatGpr<int_riscv_crc32_w, CRC32_W>; 1159def : PatGpr<int_riscv_crc32c_b, CRC32C_B>; 1160def : PatGpr<int_riscv_crc32c_h, CRC32C_H>; 1161def : PatGpr<int_riscv_crc32c_w, CRC32C_W>; 1162} // Predicates = [HasStdExtZbr] 1163 1164let Predicates = [HasStdExtZbr, IsRV64] in { 1165def : PatGpr<int_riscv_crc32_d, CRC32_D>; 1166def : PatGpr<int_riscv_crc32c_d, CRC32C_D>; 1167} // Predicates = [HasStdExtZbr, IsRV64] 1168 1169let Predicates = [HasStdExtZbf] in 1170def : PatGprGpr<riscv_bfp, BFP>; 1171 1172let Predicates = [HasStdExtZbf, IsRV64] in 1173def : PatGprGpr<riscv_bfpw, BFPW>; 1174 1175let Predicates = [HasStdExtZbkx] in { 1176def : PatGprGpr<int_riscv_xperm4, XPERM4>; 1177def : PatGprGpr<int_riscv_xperm8, XPERM8>; 1178} 1179