1//===- RISCVInstrInfoC.td - Compressed RISC-V instructions -*- tblgen-*----===// 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 9include "RISCVInstrFormatsC.td" 10 11//===----------------------------------------------------------------------===// 12// Operand definitions. 13//===----------------------------------------------------------------------===// 14 15def UImmLog2XLenNonZeroAsmOperand : AsmOperandClass { 16 let Name = "UImmLog2XLenNonZero"; 17 let RenderMethod = "addImmOperands"; 18 let DiagnosticType = "InvalidUImmLog2XLenNonZero"; 19} 20 21def uimmlog2xlennonzero : RISCVOp, ImmLeaf<XLenVT, [{ 22 if (Subtarget->is64Bit()) 23 return isUInt<6>(Imm) && (Imm != 0); 24 return isUInt<5>(Imm) && (Imm != 0); 25}]> { 26 let ParserMatchClass = UImmLog2XLenNonZeroAsmOperand; 27 // TODO: should ensure invalid shamt is rejected when decoding. 28 let DecoderMethod = "decodeUImmNonZeroOperand<6>"; 29 let OperandType = "OPERAND_UIMMLOG2XLEN_NONZERO"; 30 let MCOperandPredicate = [{ 31 int64_t Imm; 32 if (!MCOp.evaluateAsConstantImm(Imm)) 33 return false; 34 if (STI.getTargetTriple().isArch64Bit()) 35 return isUInt<6>(Imm) && (Imm != 0); 36 return isUInt<5>(Imm) && (Imm != 0); 37 }]; 38} 39 40def simm6 : RISCVSImmLeafOp<6> { 41 let MCOperandPredicate = [{ 42 int64_t Imm; 43 if (MCOp.evaluateAsConstantImm(Imm)) 44 return isInt<6>(Imm); 45 return MCOp.isBareSymbolRef(); 46 }]; 47} 48 49def simm6nonzero : RISCVOp, 50 ImmLeaf<XLenVT, [{return (Imm != 0) && isInt<6>(Imm);}]> { 51 let ParserMatchClass = SImmAsmOperand<6, "NonZero">; 52 let EncoderMethod = "getImmOpValue"; 53 let DecoderMethod = "decodeSImmNonZeroOperand<6>"; 54 let OperandType = "OPERAND_SIMM6_NONZERO"; 55 let MCOperandPredicate = [{ 56 int64_t Imm; 57 if (MCOp.evaluateAsConstantImm(Imm)) 58 return (Imm != 0) && isInt<6>(Imm); 59 return MCOp.isBareSymbolRef(); 60 }]; 61} 62 63def immzero : RISCVOp, 64 ImmLeaf<XLenVT, [{return (Imm == 0);}]> { 65 let ParserMatchClass = ImmZeroAsmOperand; 66 let OperandType = "OPERAND_ZERO"; 67} 68 69def CLUIImmAsmOperand : AsmOperandClass { 70 let Name = "CLUIImm"; 71 let RenderMethod = "addImmOperands"; 72 let DiagnosticType = !strconcat("Invalid", Name); 73} 74 75 76// c_lui_imm checks the immediate range is in [1, 31] or [0xfffe0, 0xfffff]. 77// The RISC-V ISA describes the constraint as [1, 63], with that value being 78// loaded in to bits 17-12 of the destination register and sign extended from 79// bit 17. Therefore, this 6-bit immediate can represent values in the ranges 80// [1, 31] and [0xfffe0, 0xfffff]. 81def c_lui_imm : RISCVOp, 82 ImmLeaf<XLenVT, [{return (Imm != 0) && 83 (isUInt<5>(Imm) || 84 (Imm >= 0xfffe0 && Imm <= 0xfffff));}]> { 85 let ParserMatchClass = CLUIImmAsmOperand; 86 let EncoderMethod = "getImmOpValue"; 87 let DecoderMethod = "decodeCLUIImmOperand"; 88 let OperandType = "OPERAND_CLUI_IMM"; 89 let MCOperandPredicate = [{ 90 int64_t Imm; 91 if (MCOp.evaluateAsConstantImm(Imm)) 92 return (Imm != 0) && (isUInt<5>(Imm) || 93 (Imm >= 0xfffe0 && Imm <= 0xfffff)); 94 return MCOp.isBareSymbolRef(); 95 }]; 96} 97 98// A 7-bit unsigned immediate where the least significant two bits are zero. 99def uimm7_lsb00 : RISCVOp, 100 ImmLeaf<XLenVT, [{return isShiftedUInt<5, 2>(Imm);}]> { 101 let ParserMatchClass = UImmAsmOperand<7, "Lsb00">; 102 let EncoderMethod = "getImmOpValue"; 103 let DecoderMethod = "decodeUImmOperand<7>"; 104 let OperandType = "OPERAND_UIMM7_LSB00"; 105 let MCOperandPredicate = [{ 106 int64_t Imm; 107 if (!MCOp.evaluateAsConstantImm(Imm)) 108 return false; 109 return isShiftedUInt<5, 2>(Imm); 110 }]; 111} 112 113// A 8-bit unsigned immediate where the least significant two bits are zero. 114def uimm8_lsb00 : RISCVOp, 115 ImmLeaf<XLenVT, [{return isShiftedUInt<6, 2>(Imm);}]> { 116 let ParserMatchClass = UImmAsmOperand<8, "Lsb00">; 117 let EncoderMethod = "getImmOpValue"; 118 let DecoderMethod = "decodeUImmOperand<8>"; 119 let OperandType = "OPERAND_UIMM8_LSB00"; 120 let MCOperandPredicate = [{ 121 int64_t Imm; 122 if (!MCOp.evaluateAsConstantImm(Imm)) 123 return false; 124 return isShiftedUInt<6, 2>(Imm); 125 }]; 126} 127 128// A 8-bit unsigned immediate where the least significant three bits are zero. 129def uimm8_lsb000 : RISCVOp, 130 ImmLeaf<XLenVT, [{return isShiftedUInt<5, 3>(Imm);}]> { 131 let ParserMatchClass = UImmAsmOperand<8, "Lsb000">; 132 let EncoderMethod = "getImmOpValue"; 133 let DecoderMethod = "decodeUImmOperand<8>"; 134 let OperandType = "OPERAND_UIMM8_LSB000"; 135 let MCOperandPredicate = [{ 136 int64_t Imm; 137 if (!MCOp.evaluateAsConstantImm(Imm)) 138 return false; 139 return isShiftedUInt<5, 3>(Imm); 140 }]; 141} 142 143// A 9-bit signed immediate where the least significant bit is zero. 144def simm9_lsb0 : Operand<OtherVT>, 145 ImmLeaf<XLenVT, [{return isShiftedInt<8, 1>(Imm);}]> { 146 let ParserMatchClass = SImmAsmOperand<9, "Lsb0">; 147 let PrintMethod = "printBranchOperand"; 148 let EncoderMethod = "getImmOpValueAsr1"; 149 let DecoderMethod = "decodeSImmOperandAndLsl1<9>"; 150 let MCOperandPredicate = [{ 151 int64_t Imm; 152 if (MCOp.evaluateAsConstantImm(Imm)) 153 return isShiftedInt<8, 1>(Imm); 154 return MCOp.isBareSymbolRef(); 155 156 }]; 157 let OperandType = "OPERAND_PCREL"; 158} 159 160// A 9-bit unsigned immediate where the least significant three bits are zero. 161def uimm9_lsb000 : RISCVOp, 162 ImmLeaf<XLenVT, [{return isShiftedUInt<6, 3>(Imm);}]> { 163 let ParserMatchClass = UImmAsmOperand<9, "Lsb000">; 164 let EncoderMethod = "getImmOpValue"; 165 let DecoderMethod = "decodeUImmOperand<9>"; 166 let OperandType = "OPERAND_UIMM9_LSB000"; 167 let MCOperandPredicate = [{ 168 int64_t Imm; 169 if (!MCOp.evaluateAsConstantImm(Imm)) 170 return false; 171 return isShiftedUInt<6, 3>(Imm); 172 }]; 173} 174 175// A 10-bit unsigned immediate where the least significant two bits are zero 176// and the immediate can't be zero. 177def uimm10_lsb00nonzero : RISCVOp, 178 ImmLeaf<XLenVT, 179 [{return isShiftedUInt<8, 2>(Imm) && (Imm != 0);}]> { 180 let ParserMatchClass = UImmAsmOperand<10, "Lsb00NonZero">; 181 let EncoderMethod = "getImmOpValue"; 182 let DecoderMethod = "decodeUImmNonZeroOperand<10>"; 183 let OperandType = "OPERAND_UIMM10_LSB00_NONZERO"; 184 let MCOperandPredicate = [{ 185 int64_t Imm; 186 if (!MCOp.evaluateAsConstantImm(Imm)) 187 return false; 188 return isShiftedUInt<8, 2>(Imm) && (Imm != 0); 189 }]; 190} 191 192// A 10-bit signed immediate where the least significant four bits are zero. 193def simm10_lsb0000nonzero : RISCVOp, 194 ImmLeaf<XLenVT, 195 [{return (Imm != 0) && isShiftedInt<6, 4>(Imm);}]> { 196 let ParserMatchClass = SImmAsmOperand<10, "Lsb0000NonZero">; 197 let EncoderMethod = "getImmOpValue"; 198 let DecoderMethod = "decodeSImmNonZeroOperand<10>"; 199 let OperandType = "OPERAND_SIMM10_LSB0000_NONZERO"; 200 let MCOperandPredicate = [{ 201 int64_t Imm; 202 if (!MCOp.evaluateAsConstantImm(Imm)) 203 return false; 204 return isShiftedInt<6, 4>(Imm) && (Imm != 0); 205 }]; 206} 207 208// A 12-bit signed immediate where the least significant bit is zero. 209def simm12_lsb0 : Operand<XLenVT>, 210 ImmLeaf<XLenVT, [{return isShiftedInt<11, 1>(Imm);}]> { 211 let ParserMatchClass = SImmAsmOperand<12, "Lsb0">; 212 let PrintMethod = "printBranchOperand"; 213 let EncoderMethod = "getImmOpValueAsr1"; 214 let DecoderMethod = "decodeSImmOperandAndLsl1<12>"; 215 let MCOperandPredicate = [{ 216 int64_t Imm; 217 if (MCOp.evaluateAsConstantImm(Imm)) 218 return isShiftedInt<11, 1>(Imm); 219 return MCOp.isBareSymbolRef(); 220 }]; 221 let OperandType = "OPERAND_PCREL"; 222} 223 224def InsnCDirectiveOpcode : AsmOperandClass { 225 let Name = "InsnCDirectiveOpcode"; 226 let ParserMethod = "parseInsnCDirectiveOpcode"; 227 let RenderMethod = "addImmOperands"; 228 let PredicateMethod = "isImm"; 229} 230 231def uimm2_opcode : RISCVOp { 232 let ParserMatchClass = InsnCDirectiveOpcode; 233 let DecoderMethod = "decodeUImmOperand<2>"; 234 let OperandType = "OPERAND_UIMM2"; 235} 236 237//===----------------------------------------------------------------------===// 238// Instruction Class Templates 239//===----------------------------------------------------------------------===// 240 241let hasSideEffects = 0, mayLoad = 1, mayStore = 0 in 242class CStackLoad<bits<3> funct3, string OpcodeStr, 243 RegisterClass cls, DAGOperand opnd> 244 : RVInst16CI<funct3, 0b10, (outs cls:$rd), (ins SPMem:$rs1, opnd:$imm), 245 OpcodeStr, "$rd, ${imm}(${rs1})">; 246 247let hasSideEffects = 0, mayLoad = 0, mayStore = 1 in 248class CStackStore<bits<3> funct3, string OpcodeStr, 249 RegisterClass cls, DAGOperand opnd> 250 : RVInst16CSS<funct3, 0b10, (outs), (ins cls:$rs2, SPMem:$rs1, opnd:$imm), 251 OpcodeStr, "$rs2, ${imm}(${rs1})">; 252 253let hasSideEffects = 0, mayLoad = 1, mayStore = 0 in 254class CLoad_ri<bits<3> funct3, string OpcodeStr, 255 RegisterClass cls, DAGOperand opnd> 256 : RVInst16CL<funct3, 0b00, (outs cls:$rd), (ins GPRCMem:$rs1, opnd:$imm), 257 OpcodeStr, "$rd, ${imm}(${rs1})">; 258 259let hasSideEffects = 0, mayLoad = 0, mayStore = 1 in 260class CStore_rri<bits<3> funct3, string OpcodeStr, 261 RegisterClass cls, DAGOperand opnd> 262 : RVInst16CS<funct3, 0b00, (outs), (ins cls:$rs2,GPRCMem:$rs1, opnd:$imm), 263 OpcodeStr, "$rs2, ${imm}(${rs1})">; 264 265let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 266class Bcz<bits<3> funct3, string OpcodeStr, 267 RegisterClass cls> 268 : RVInst16CB<funct3, 0b01, (outs), (ins cls:$rs1, simm9_lsb0:$imm), 269 OpcodeStr, "$rs1, $imm"> { 270 let isBranch = 1; 271 let isTerminator = 1; 272 let Inst{12} = imm{7}; 273 let Inst{11-10} = imm{3-2}; 274 let Inst{6-5} = imm{6-5}; 275 let Inst{4-3} = imm{1-0}; 276 let Inst{2} = imm{4}; 277} 278 279let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 280class Shift_right<bits<2> funct2, string OpcodeStr, RegisterClass cls, 281 Operand ImmOpnd> 282 : RVInst16CB<0b100, 0b01, (outs cls:$rs1_wb), (ins cls:$rs1, ImmOpnd:$imm), 283 OpcodeStr, "$rs1, $imm"> { 284 let Constraints = "$rs1 = $rs1_wb"; 285 let Inst{12} = imm{5}; 286 let Inst{11-10} = funct2; 287 let Inst{6-2} = imm{4-0}; 288} 289 290let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 291class CA_ALU<bits<6> funct6, bits<2> funct2, string OpcodeStr, 292 RegisterClass cls> 293 : RVInst16CA<funct6, funct2, 0b01, (outs cls:$rd_wb), (ins cls:$rd, cls:$rs2), 294 OpcodeStr, "$rd, $rs2"> { 295 bits<3> rd; 296 let Constraints = "$rd = $rd_wb"; 297 let Inst{9-7} = rd; 298} 299 300//===----------------------------------------------------------------------===// 301// Instructions 302//===----------------------------------------------------------------------===// 303 304let Predicates = [HasStdExtCOrZca] in { 305 306let hasSideEffects = 0, mayLoad = 0, mayStore = 0, Uses = [X2] in 307def C_ADDI4SPN : RVInst16CIW<0b000, 0b00, (outs GPRC:$rd), 308 (ins SP:$rs1, uimm10_lsb00nonzero:$imm), 309 "c.addi4spn", "$rd, $rs1, $imm">, 310 Sched<[WriteIALU, ReadIALU]> { 311 bits<5> rs1; 312 let Inst{12-11} = imm{5-4}; 313 let Inst{10-7} = imm{9-6}; 314 let Inst{6} = imm{2}; 315 let Inst{5} = imm{3}; 316} 317 318let Predicates = [HasStdExtCOrZcd, HasStdExtD] in 319def C_FLD : CLoad_ri<0b001, "c.fld", FPR64C, uimm8_lsb000>, 320 Sched<[WriteFLD64, ReadMemBase]> { 321 bits<8> imm; 322 let Inst{12-10} = imm{5-3}; 323 let Inst{6-5} = imm{7-6}; 324} 325 326def C_LW : CLoad_ri<0b010, "c.lw", GPRC, uimm7_lsb00>, 327 Sched<[WriteLDW, ReadMemBase]> { 328 bits<7> imm; 329 let Inst{12-10} = imm{5-3}; 330 let Inst{6} = imm{2}; 331 let Inst{5} = imm{6}; 332} 333 334let DecoderNamespace = "RISCV32Only_", 335 Predicates = [HasStdExtCOrZcfOrZce, HasStdExtF, IsRV32] in 336def C_FLW : CLoad_ri<0b011, "c.flw", FPR32C, uimm7_lsb00>, 337 Sched<[WriteFLD32, ReadMemBase]> { 338 bits<7> imm; 339 let Inst{12-10} = imm{5-3}; 340 let Inst{6} = imm{2}; 341 let Inst{5} = imm{6}; 342} 343 344let Predicates = [HasStdExtCOrZca, IsRV64] in 345def C_LD : CLoad_ri<0b011, "c.ld", GPRC, uimm8_lsb000>, 346 Sched<[WriteLDD, ReadMemBase]> { 347 bits<8> imm; 348 let Inst{12-10} = imm{5-3}; 349 let Inst{6-5} = imm{7-6}; 350} 351 352let Predicates = [HasStdExtCOrZcd, HasStdExtD] in 353def C_FSD : CStore_rri<0b101, "c.fsd", FPR64C, uimm8_lsb000>, 354 Sched<[WriteFST64, ReadStoreData, ReadMemBase]> { 355 bits<8> imm; 356 let Inst{12-10} = imm{5-3}; 357 let Inst{6-5} = imm{7-6}; 358} 359 360def C_SW : CStore_rri<0b110, "c.sw", GPRC, uimm7_lsb00>, 361 Sched<[WriteSTW, ReadStoreData, ReadMemBase]> { 362 bits<7> imm; 363 let Inst{12-10} = imm{5-3}; 364 let Inst{6} = imm{2}; 365 let Inst{5} = imm{6}; 366} 367 368let DecoderNamespace = "RISCV32Only_", 369 Predicates = [HasStdExtCOrZcfOrZce, HasStdExtF, IsRV32] in 370def C_FSW : CStore_rri<0b111, "c.fsw", FPR32C, uimm7_lsb00>, 371 Sched<[WriteFST32, ReadStoreData, ReadMemBase]> { 372 bits<7> imm; 373 let Inst{12-10} = imm{5-3}; 374 let Inst{6} = imm{2}; 375 let Inst{5} = imm{6}; 376} 377 378let Predicates = [HasStdExtCOrZca, IsRV64] in 379def C_SD : CStore_rri<0b111, "c.sd", GPRC, uimm8_lsb000>, 380 Sched<[WriteSTD, ReadStoreData, ReadMemBase]> { 381 bits<8> imm; 382 let Inst{12-10} = imm{5-3}; 383 let Inst{6-5} = imm{7-6}; 384} 385 386let rd = 0, imm = 0, hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 387def C_NOP : RVInst16CI<0b000, 0b01, (outs), (ins), "c.nop", "">, 388 Sched<[WriteNop]> { 389 let Inst{6-2} = 0; 390} 391 392let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 393def C_ADDI : RVInst16CI<0b000, 0b01, (outs GPRNoX0:$rd_wb), 394 (ins GPRNoX0:$rd, simm6nonzero:$imm), 395 "c.addi", "$rd, $imm">, 396 Sched<[WriteIALU, ReadIALU]> { 397 let Constraints = "$rd = $rd_wb"; 398 let Inst{6-2} = imm{4-0}; 399} 400 401let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 402def C_ADDI_NOP : RVInst16CI<0b000, 0b01, (outs GPRX0:$rd_wb), 403 (ins GPRX0:$rd, immzero:$imm), 404 "c.addi", "$rd, $imm">, 405 Sched<[WriteIALU, ReadIALU]> { 406 let Constraints = "$rd = $rd_wb"; 407 let Inst{6-2} = 0; 408 let isAsmParserOnly = 1; 409} 410 411let hasSideEffects = 0, mayLoad = 0, mayStore = 0, isCall = 1, 412 DecoderNamespace = "RISCV32Only_", Defs = [X1], 413 Predicates = [HasStdExtCOrZca, IsRV32] in 414def C_JAL : RVInst16CJ<0b001, 0b01, (outs), (ins simm12_lsb0:$offset), 415 "c.jal", "$offset">, Sched<[WriteJal]>; 416 417let hasSideEffects = 0, mayLoad = 0, mayStore = 0, 418 Predicates = [HasStdExtCOrZca, IsRV64] in 419def C_ADDIW : RVInst16CI<0b001, 0b01, (outs GPRNoX0:$rd_wb), 420 (ins GPRNoX0:$rd, simm6:$imm), 421 "c.addiw", "$rd, $imm">, 422 Sched<[WriteIALU32, ReadIALU32]> { 423 let Constraints = "$rd = $rd_wb"; 424 let Inst{6-2} = imm{4-0}; 425} 426 427let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 428def C_LI : RVInst16CI<0b010, 0b01, (outs GPRNoX0:$rd), (ins simm6:$imm), 429 "c.li", "$rd, $imm">, 430 Sched<[WriteIALU]> { 431 let Inst{6-2} = imm{4-0}; 432} 433 434let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 435def C_ADDI16SP : RVInst16CI<0b011, 0b01, (outs SP:$rd_wb), 436 (ins SP:$rd, simm10_lsb0000nonzero:$imm), 437 "c.addi16sp", "$rd, $imm">, 438 Sched<[WriteIALU, ReadIALU]> { 439 let Constraints = "$rd = $rd_wb"; 440 let Inst{12} = imm{9}; 441 let Inst{11-7} = 2; 442 let Inst{6} = imm{4}; 443 let Inst{5} = imm{6}; 444 let Inst{4-3} = imm{8-7}; 445 let Inst{2} = imm{5}; 446} 447 448let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 449def C_LUI : RVInst16CI<0b011, 0b01, (outs GPRNoX0X2:$rd), 450 (ins c_lui_imm:$imm), 451 "c.lui", "$rd, $imm">, 452 Sched<[WriteIALU]> { 453 let Inst{6-2} = imm{4-0}; 454} 455 456def C_SRLI : Shift_right<0b00, "c.srli", GPRC, uimmlog2xlennonzero>, 457 Sched<[WriteShiftImm, ReadShiftImm]>; 458def C_SRAI : Shift_right<0b01, "c.srai", GPRC, uimmlog2xlennonzero>, 459 Sched<[WriteShiftImm, ReadShiftImm]>; 460 461let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 462def C_ANDI : RVInst16CB<0b100, 0b01, (outs GPRC:$rs1_wb), (ins GPRC:$rs1, simm6:$imm), 463 "c.andi", "$rs1, $imm">, 464 Sched<[WriteIALU, ReadIALU]> { 465 let Constraints = "$rs1 = $rs1_wb"; 466 let Inst{12} = imm{5}; 467 let Inst{11-10} = 0b10; 468 let Inst{6-2} = imm{4-0}; 469} 470 471def C_SUB : CA_ALU<0b100011, 0b00, "c.sub", GPRC>, 472 Sched<[WriteIALU, ReadIALU, ReadIALU]>; 473def C_XOR : CA_ALU<0b100011, 0b01, "c.xor", GPRC>, 474 Sched<[WriteIALU, ReadIALU, ReadIALU]>; 475def C_OR : CA_ALU<0b100011, 0b10, "c.or" , GPRC>, 476 Sched<[WriteIALU, ReadIALU, ReadIALU]>; 477def C_AND : CA_ALU<0b100011, 0b11, "c.and", GPRC>, 478 Sched<[WriteIALU, ReadIALU, ReadIALU]>; 479 480let Predicates = [HasStdExtCOrZca, IsRV64] in { 481def C_SUBW : CA_ALU<0b100111, 0b00, "c.subw", GPRC>, 482 Sched<[WriteIALU32, ReadIALU32, ReadIALU32]>; 483def C_ADDW : CA_ALU<0b100111, 0b01, "c.addw", GPRC>, 484 Sched<[WriteIALU32, ReadIALU32, ReadIALU32]>; 485} 486 487let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 488def C_J : RVInst16CJ<0b101, 0b01, (outs), (ins simm12_lsb0:$offset), 489 "c.j", "$offset">, Sched<[WriteJmp]> { 490 let isBranch = 1; 491 let isTerminator=1; 492 let isBarrier=1; 493} 494 495def C_BEQZ : Bcz<0b110, "c.beqz", GPRC>, Sched<[WriteJmp, ReadJmp]>; 496def C_BNEZ : Bcz<0b111, "c.bnez", GPRC>, Sched<[WriteJmp, ReadJmp]>; 497 498let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 499def C_SLLI : RVInst16CI<0b000, 0b10, (outs GPRNoX0:$rd_wb), 500 (ins GPRNoX0:$rd, uimmlog2xlennonzero:$imm), 501 "c.slli", "$rd, $imm">, 502 Sched<[WriteShiftImm, ReadShiftImm]> { 503 let Constraints = "$rd = $rd_wb"; 504 let Inst{6-2} = imm{4-0}; 505} 506 507let Predicates = [HasStdExtCOrZcd, HasStdExtD] in 508def C_FLDSP : CStackLoad<0b001, "c.fldsp", FPR64, uimm9_lsb000>, 509 Sched<[WriteFLD64, ReadMemBase]> { 510 let Inst{6-5} = imm{4-3}; 511 let Inst{4-2} = imm{8-6}; 512} 513 514def C_LWSP : CStackLoad<0b010, "c.lwsp", GPRNoX0, uimm8_lsb00>, 515 Sched<[WriteLDW, ReadMemBase]> { 516 let Inst{6-4} = imm{4-2}; 517 let Inst{3-2} = imm{7-6}; 518} 519 520let DecoderNamespace = "RISCV32Only_", 521 Predicates = [HasStdExtCOrZcfOrZce, HasStdExtF, IsRV32] in 522def C_FLWSP : CStackLoad<0b011, "c.flwsp", FPR32, uimm8_lsb00>, 523 Sched<[WriteFLD32, ReadMemBase]> { 524 let Inst{6-4} = imm{4-2}; 525 let Inst{3-2} = imm{7-6}; 526} 527 528let Predicates = [HasStdExtCOrZca, IsRV64] in 529def C_LDSP : CStackLoad<0b011, "c.ldsp", GPRNoX0, uimm9_lsb000>, 530 Sched<[WriteLDD, ReadMemBase]> { 531 let Inst{6-5} = imm{4-3}; 532 let Inst{4-2} = imm{8-6}; 533} 534 535let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 536def C_JR : RVInst16CR<0b1000, 0b10, (outs), (ins GPRNoX0:$rs1), 537 "c.jr", "$rs1">, Sched<[WriteJalr, ReadJalr]> { 538 let isBarrier = 1; 539 let isTerminator = 1; 540 let rs2 = 0; 541} 542 543let hasSideEffects = 0, mayLoad = 0, mayStore = 0, isMoveReg = 1, 544 isAsCheapAsAMove = 1 in 545def C_MV : RVInst16CR<0b1000, 0b10, (outs GPRNoX0:$rs1), (ins GPRNoX0:$rs2), 546 "c.mv", "$rs1, $rs2">, 547 Sched<[WriteIALU, ReadIALU]>; 548 549let rs1 = 0, rs2 = 0, hasSideEffects = 1, mayLoad = 0, mayStore = 0 in 550def C_EBREAK : RVInst16CR<0b1001, 0b10, (outs), (ins), "c.ebreak", "">, Sched<[]>; 551 552let hasSideEffects = 0, mayLoad = 0, mayStore = 0, 553 isCall=1, Defs=[X1], rs2 = 0 in 554def C_JALR : RVInst16CR<0b1001, 0b10, (outs), (ins GPRNoX0:$rs1), 555 "c.jalr", "$rs1">, Sched<[WriteJalr, ReadJalr]>; 556 557let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in 558def C_ADD : RVInst16CR<0b1001, 0b10, (outs GPRNoX0:$rs1_wb), 559 (ins GPRNoX0:$rs1, GPRNoX0:$rs2), 560 "c.add", "$rs1, $rs2">, 561 Sched<[WriteIALU, ReadIALU, ReadIALU]> { 562 let Constraints = "$rs1 = $rs1_wb"; 563} 564 565let Predicates = [HasStdExtCOrZcd, HasStdExtD] in 566def C_FSDSP : CStackStore<0b101, "c.fsdsp", FPR64, uimm9_lsb000>, 567 Sched<[WriteFST64, ReadStoreData, ReadMemBase]> { 568 let Inst{12-10} = imm{5-3}; 569 let Inst{9-7} = imm{8-6}; 570} 571 572def C_SWSP : CStackStore<0b110, "c.swsp", GPR, uimm8_lsb00>, 573 Sched<[WriteSTW, ReadStoreData, ReadMemBase]> { 574 let Inst{12-9} = imm{5-2}; 575 let Inst{8-7} = imm{7-6}; 576} 577 578let DecoderNamespace = "RISCV32Only_", 579 Predicates = [HasStdExtCOrZcfOrZce, HasStdExtF, IsRV32] in 580def C_FSWSP : CStackStore<0b111, "c.fswsp", FPR32, uimm8_lsb00>, 581 Sched<[WriteFST32, ReadStoreData, ReadMemBase]> { 582 let Inst{12-9} = imm{5-2}; 583 let Inst{8-7} = imm{7-6}; 584} 585 586let Predicates = [HasStdExtCOrZca, IsRV64] in 587def C_SDSP : CStackStore<0b111, "c.sdsp", GPR, uimm9_lsb000>, 588 Sched<[WriteSTD, ReadStoreData, ReadMemBase]> { 589 let Inst{12-10} = imm{5-3}; 590 let Inst{9-7} = imm{8-6}; 591} 592 593// The all zeros pattern isn't a valid RISC-V instruction. It's used by GNU 594// binutils as 16-bit instruction known to be unimplemented (i.e., trapping). 595let hasSideEffects = 1, mayLoad = 0, mayStore = 0 in 596def C_UNIMP : RVInst16<(outs), (ins), "c.unimp", "", [], InstFormatOther>, 597 Sched<[]> { 598 let Inst{15-0} = 0; 599} 600 601} // Predicates = [HasStdExtCOrZca] 602 603//===----------------------------------------------------------------------===// 604// HINT Instructions 605//===----------------------------------------------------------------------===// 606 607let Predicates = [HasStdExtCOrZca, HasRVCHints], hasSideEffects = 0, mayLoad = 0, 608 mayStore = 0 in { 609 610let rd = 0 in 611def C_NOP_HINT : RVInst16CI<0b000, 0b01, (outs), (ins simm6nonzero:$imm), 612 "c.nop", "$imm">, Sched<[WriteNop]> { 613 let Inst{6-2} = imm{4-0}; 614} 615 616def C_ADDI_HINT_IMM_ZERO : RVInst16CI<0b000, 0b01, (outs GPRNoX0:$rd_wb), 617 (ins GPRNoX0:$rd, immzero:$imm), 618 "c.addi", "$rd, $imm">, 619 Sched<[WriteIALU, ReadIALU]> { 620 let Constraints = "$rd = $rd_wb"; 621 let Inst{12} = 0; 622 let Inst{6-2} = 0; 623 let DecoderMethod = "decodeRVCInstrRdRs1ImmZero"; 624} 625 626def C_LI_HINT : RVInst16CI<0b010, 0b01, (outs GPRX0:$rd), (ins simm6:$imm), 627 "c.li", "$rd, $imm">, 628 Sched<[WriteIALU]> { 629 let Inst{6-2} = imm{4-0}; 630 let Inst{11-7} = 0; 631 let DecoderMethod = "decodeRVCInstrRdSImm"; 632} 633 634def C_LUI_HINT : RVInst16CI<0b011, 0b01, (outs GPRX0:$rd), 635 (ins c_lui_imm:$imm), 636 "c.lui", "$rd, $imm">, 637 Sched<[WriteIALU]> { 638 let Inst{6-2} = imm{4-0}; 639 let Inst{11-7} = 0; 640 let DecoderMethod = "decodeRVCInstrRdSImm"; 641} 642 643def C_MV_HINT : RVInst16CR<0b1000, 0b10, (outs GPRX0:$rs1), (ins GPRNoX0:$rs2), 644 "c.mv", "$rs1, $rs2">, Sched<[WriteIALU, ReadIALU]> { 645 let Inst{11-7} = 0; 646 let DecoderMethod = "decodeRVCInstrRdRs2"; 647} 648 649def C_ADD_HINT : RVInst16CR<0b1001, 0b10, (outs GPRX0:$rs1_wb), 650 (ins GPRX0:$rs1, GPRNoX0:$rs2), 651 "c.add", "$rs1, $rs2">, 652 Sched<[WriteIALU, ReadIALU, ReadIALU]> { 653 let Constraints = "$rs1 = $rs1_wb"; 654 let Inst{11-7} = 0; 655 let DecoderMethod = "decodeRVCInstrRdRs1Rs2"; 656} 657 658def C_SLLI_HINT : RVInst16CI<0b000, 0b10, (outs GPRX0:$rd_wb), 659 (ins GPRX0:$rd, uimmlog2xlennonzero:$imm), 660 "c.slli", "$rd, $imm">, 661 Sched<[WriteShiftImm, ReadShiftImm]> { 662 let Constraints = "$rd = $rd_wb"; 663 let Inst{6-2} = imm{4-0}; 664 let Inst{11-7} = 0; 665 let DecoderMethod = "decodeRVCInstrRdRs1UImm"; 666} 667 668def C_SLLI64_HINT : RVInst16CI<0b000, 0b10, (outs GPR:$rd_wb), (ins GPR:$rd), 669 "c.slli64", "$rd">, 670 Sched<[WriteShiftImm, ReadShiftImm]> { 671 let Constraints = "$rd = $rd_wb"; 672 let Inst{6-2} = 0; 673 let Inst{12} = 0; 674} 675 676def C_SRLI64_HINT : RVInst16CI<0b100, 0b01, (outs GPRC:$rd_wb), 677 (ins GPRC:$rd), 678 "c.srli64", "$rd">, 679 Sched<[WriteShiftImm, ReadShiftImm]> { 680 let Constraints = "$rd = $rd_wb"; 681 let Inst{6-2} = 0; 682 let Inst{11-10} = 0; 683 let Inst{12} = 0; 684} 685 686def C_SRAI64_HINT : RVInst16CI<0b100, 0b01, (outs GPRC:$rd_wb), 687 (ins GPRC:$rd), 688 "c.srai64", "$rd">, 689 Sched<[WriteShiftImm, ReadShiftImm]> { 690 let Constraints = "$rd = $rd_wb"; 691 let Inst{6-2} = 0; 692 let Inst{11-10} = 1; 693 let Inst{12} = 0; 694} 695 696} // Predicates = [HasStdExtCOrZca, HasRVCHints], hasSideEffects = 0, mayLoad = 0, 697 // mayStore = 0 698 699//===----------------------------------------------------------------------===// 700// Assembler Pseudo Instructions 701//===----------------------------------------------------------------------===// 702 703let Predicates = [HasStdExtCOrZca, HasRVCHints] in { 704// Just a different syntax for the c.nop hint: c.addi x0, simm6 vs c.nop simm6. 705def : InstAlias<"c.addi x0, $imm", (C_NOP_HINT simm6nonzero:$imm), 0>; 706} 707 708let Predicates = [HasStdExtC, HasRVCHints, HasStdExtZihintntl] in { 709def : InstAlias<"c.ntl.p1", (C_ADD_HINT X0, X2)>; 710def : InstAlias<"c.ntl.pall", (C_ADD_HINT X0, X3)>; 711def : InstAlias<"c.ntl.s1", (C_ADD_HINT X0, X4)>; 712def : InstAlias<"c.ntl.all", (C_ADD_HINT X0, X5)>; 713} // Predicates = [HasStdExtC, HasRVCHints, HasStdExtZihintntl] 714 715let EmitPriority = 0 in { 716let Predicates = [HasStdExtCOrZca] in { 717def : InstAlias<"c.lw $rd, (${rs1})", (C_LW GPRC:$rd, GPRCMem:$rs1, 0)>; 718def : InstAlias<"c.sw $rs2, (${rs1})", (C_SW GPRC:$rs2, GPRCMem:$rs1, 0)>; 719def : InstAlias<"c.lwsp $rd, (${rs1})", (C_LWSP GPRC:$rd, SPMem:$rs1, 0)>; 720def : InstAlias<"c.swsp $rs2, (${rs1})", (C_SWSP GPRC:$rs2, SPMem:$rs1, 0)>; 721} 722 723let Predicates = [HasStdExtCOrZca, IsRV64] in { 724def : InstAlias<"c.ld $rd, (${rs1})", (C_LD GPRC:$rd, GPRCMem:$rs1, 0)>; 725def : InstAlias<"c.sd $rs2, (${rs1})", (C_SD GPRC:$rs2, GPRCMem:$rs1, 0)>; 726def : InstAlias<"c.ldsp $rd, (${rs1})", (C_LDSP GPRC:$rd, SPMem:$rs1, 0)>; 727def : InstAlias<"c.sdsp $rs2, (${rs1})", (C_SDSP GPRC:$rs2, SPMem:$rs1, 0)>; 728} 729 730let Predicates = [HasStdExtCOrZcfOrZce, HasStdExtF, IsRV32] in { 731def : InstAlias<"c.flw $rd, (${rs1})", (C_FLW FPR32C:$rd, GPRCMem:$rs1, 0)>; 732def : InstAlias<"c.fsw $rs2, (${rs1})", (C_FSW FPR32C:$rs2, GPRCMem:$rs1, 0)>; 733def : InstAlias<"c.flwsp $rd, (${rs1})", (C_FLWSP FPR32C:$rd, SPMem:$rs1, 0)>; 734def : InstAlias<"c.fswsp $rs2, (${rs1})", (C_FSWSP FPR32C:$rs2, SPMem:$rs1, 0)>; 735} 736 737let Predicates = [HasStdExtCOrZcd, HasStdExtD] in { 738def : InstAlias<"c.fld $rd, (${rs1})", (C_FLD FPR64C:$rd, GPRCMem:$rs1, 0)>; 739def : InstAlias<"c.fsd $rs2, (${rs1})", (C_FSD FPR64C:$rs2, GPRCMem:$rs1, 0)>; 740def : InstAlias<"c.fldsp $rd, (${rs1})", (C_FLDSP FPR64C:$rd, SPMem:$rs1, 0)>; 741def : InstAlias<"c.fsdsp $rs2, (${rs1})", (C_FSDSP FPR64C:$rs2, SPMem:$rs1, 0)>; 742} 743} // EmitPriority = 0 744 745//===----------------------------------------------------------------------===// 746// .insn directive instructions 747//===----------------------------------------------------------------------===// 748 749def AnyRegCOperand : AsmOperandClass { 750 let Name = "AnyRegCOperand"; 751 let RenderMethod = "addRegOperands"; 752 let PredicateMethod = "isAnyRegC"; 753} 754 755def AnyRegC : Operand<XLenVT> { 756 let OperandType = "OPERAND_REGISTER"; 757 let ParserMatchClass = AnyRegCOperand; 758} 759 760// isCodeGenOnly = 1 to hide them from the tablegened assembly parser. 761let isCodeGenOnly = 1, hasSideEffects = 1, mayLoad = 1, mayStore = 1, 762 hasNoSchedulingInfo = 1, Predicates = [HasStdExtCOrZca] in { 763def InsnCR : DirectiveInsnCR<(outs AnyReg:$rd), (ins uimm2_opcode:$opcode, 764 uimm4:$funct4, 765 AnyReg:$rs2), 766 "$opcode, $funct4, $rd, $rs2">; 767def InsnCI : DirectiveInsnCI<(outs AnyRegC:$rd), (ins uimm2_opcode:$opcode, 768 uimm3:$funct3, 769 simm6:$imm6), 770 "$opcode, $funct3, $rd, $imm6">; 771def InsnCIW : DirectiveInsnCIW<(outs AnyRegC:$rd), (ins uimm2_opcode:$opcode, 772 uimm3:$funct3, 773 uimm8:$imm8), 774 "$opcode, $funct3, $rd, $imm8">; 775def InsnCSS : DirectiveInsnCSS<(outs), (ins uimm2_opcode:$opcode, 776 uimm3:$funct3, 777 AnyReg:$rs2, 778 uimm6:$imm6), 779 "$opcode, $funct3, $rs2, $imm6">; 780def InsnCL : DirectiveInsnCL<(outs AnyRegC:$rd), (ins uimm2_opcode:$opcode, 781 uimm3:$funct3, 782 AnyRegC:$rs1, 783 uimm5:$imm5), 784 "$opcode, $funct3, $rd, ${imm5}(${rs1})">; 785def InsnCS : DirectiveInsnCS<(outs), (ins uimm2_opcode:$opcode, 786 uimm3:$funct3, 787 AnyRegC:$rs2, 788 AnyRegC:$rs1, 789 uimm5:$imm5), 790 "$opcode, $funct3, $rs2, ${imm5}(${rs1})">; 791def InsnCA : DirectiveInsnCA<(outs AnyRegC:$rd), (ins uimm2_opcode:$opcode, 792 uimm6:$funct6, 793 uimm2:$funct2, 794 AnyRegC:$rs2), 795 "$opcode, $funct6, $funct2, $rd, $rs2">; 796def InsnCB : DirectiveInsnCB<(outs), (ins uimm2_opcode:$opcode, uimm3:$funct3, 797 AnyRegC:$rs1, 798 simm9_lsb0:$imm8), 799 "$opcode, $funct3, $rs1, $imm8">; 800def InsnCJ : DirectiveInsnCJ<(outs), (ins uimm2_opcode:$opcode, 801 uimm3:$funct3, 802 simm12_lsb0:$imm11), 803 "$opcode, $funct3, $imm11">; 804} 805 806// Use InstAliases to match these so that we can combine the insn and format 807// into a mnemonic to use as the key for the tablegened asm matcher table. The 808// parser will take care of creating these fake mnemonics and will only do it 809// for known formats. 810let EmitPriority = 0, Predicates = [HasStdExtCOrZca] in { 811def : InstAlias<".insn_cr $opcode, $funct4, $rd, $rs2", 812 (InsnCR AnyReg:$rd, uimm2_opcode:$opcode, uimm4:$funct4, 813 AnyReg:$rs2)>; 814def : InstAlias<".insn_ci $opcode, $funct3, $rd, $imm6", 815 (InsnCI AnyRegC:$rd, uimm2_opcode:$opcode, uimm3:$funct3, 816 simm6:$imm6)>; 817def : InstAlias<".insn_ciw $opcode, $funct3, $rd, $imm8", 818 (InsnCIW AnyRegC:$rd, uimm2_opcode:$opcode, uimm3:$funct3, 819 uimm8:$imm8)>; 820def : InstAlias<".insn_css $opcode, $funct3, $rs2, $imm6", 821 (InsnCSS uimm2_opcode:$opcode, uimm3:$funct3, AnyReg:$rs2, 822 uimm6:$imm6)>; 823def : InstAlias<".insn_cl $opcode, $funct3, $rd, ${imm5}(${rs1})", 824 (InsnCL AnyRegC:$rd, uimm2_opcode:$opcode, uimm3:$funct3, 825 AnyRegC:$rs1, uimm5:$imm5)>; 826def : InstAlias<".insn_cs $opcode, $funct3, $rs2, ${imm5}(${rs1})", 827 (InsnCS uimm2_opcode:$opcode, uimm3:$funct3, AnyRegC:$rs2, 828 AnyRegC:$rs1, uimm5:$imm5)>; 829def : InstAlias<".insn_ca $opcode, $funct6, $funct2, $rd, $rs2", 830 (InsnCA AnyRegC:$rd, uimm2_opcode:$opcode, uimm6:$funct6, 831 uimm2:$funct2, AnyRegC:$rs2)>; 832def : InstAlias<".insn_cb $opcode, $funct3, $rs1, $imm8", 833 (InsnCB uimm2_opcode:$opcode, uimm3:$funct3, AnyRegC:$rs1, 834 simm9_lsb0:$imm8)>; 835def : InstAlias<".insn_cj $opcode, $funct3, $imm11", 836 (InsnCJ uimm2_opcode:$opcode, uimm3:$funct3, simm12_lsb0:$imm11)>; 837} 838 839//===----------------------------------------------------------------------===/i 840// Compress Instruction tablegen backend. 841//===----------------------------------------------------------------------===// 842 843// Patterns are defined in the same order the compressed instructions appear 844// on page 82 of the ISA manual. 845 846// Quadrant 0 847let Predicates = [HasStdExtCOrZca] in { 848def : CompressPat<(ADDI GPRC:$rd, SP:$rs1, uimm10_lsb00nonzero:$imm), 849 (C_ADDI4SPN GPRC:$rd, SP:$rs1, uimm10_lsb00nonzero:$imm)>; 850} // Predicates = [HasStdExtCOrZca] 851 852let Predicates = [HasStdExtCOrZcd, HasStdExtD] in { 853def : CompressPat<(FLD FPR64C:$rd, GPRCMem:$rs1, uimm8_lsb000:$imm), 854 (C_FLD FPR64C:$rd, GPRCMem:$rs1, uimm8_lsb000:$imm)>; 855} // Predicates = [HasStdExtCOrZcd, HasStdExtD] 856 857let Predicates = [HasStdExtCOrZca] in { 858def : CompressPat<(LW GPRC:$rd, GPRCMem:$rs1, uimm7_lsb00:$imm), 859 (C_LW GPRC:$rd, GPRCMem:$rs1, uimm7_lsb00:$imm)>; 860} // Predicates = [HasStdExtCOrZca] 861 862let Predicates = [HasStdExtCOrZcfOrZce, HasStdExtF, IsRV32] in { 863def : CompressPat<(FLW FPR32C:$rd, GPRCMem:$rs1, uimm7_lsb00:$imm), 864 (C_FLW FPR32C:$rd, GPRCMem:$rs1, uimm7_lsb00:$imm)>; 865} // Predicates = [HasStdExtC, HasStdExtF, IsRV32] 866 867let Predicates = [HasStdExtCOrZca, IsRV64] in { 868def : CompressPat<(LD GPRC:$rd, GPRCMem:$rs1, uimm8_lsb000:$imm), 869 (C_LD GPRC:$rd, GPRCMem:$rs1, uimm8_lsb000:$imm)>; 870} // Predicates = [HasStdExtCOrZca, IsRV64] 871 872let Predicates = [HasStdExtCOrZcd, HasStdExtD] in { 873def : CompressPat<(FSD FPR64C:$rs2, GPRCMem:$rs1, uimm8_lsb000:$imm), 874 (C_FSD FPR64C:$rs2, GPRCMem:$rs1, uimm8_lsb000:$imm)>; 875} // Predicates = [HasStdExtCOrZcd, HasStdExtD] 876 877let Predicates = [HasStdExtCOrZca] in { 878def : CompressPat<(SW GPRC:$rs2, GPRCMem:$rs1, uimm7_lsb00:$imm), 879 (C_SW GPRC:$rs2, GPRCMem:$rs1, uimm7_lsb00:$imm)>; 880} // Predicates = [HasStdExtCOrZca] 881 882let Predicates = [HasStdExtCOrZcfOrZce, HasStdExtF, IsRV32] in { 883def : CompressPat<(FSW FPR32C:$rs2, GPRCMem:$rs1, uimm7_lsb00:$imm), 884 (C_FSW FPR32C:$rs2, GPRCMem:$rs1, uimm7_lsb00:$imm)>; 885} // Predicates = [HasStdExtC, HasStdExtF, IsRV32] 886 887let Predicates = [HasStdExtCOrZca, IsRV64] in { 888def : CompressPat<(SD GPRC:$rs2, GPRCMem:$rs1, uimm8_lsb000:$imm), 889 (C_SD GPRC:$rs2, GPRCMem:$rs1, uimm8_lsb000:$imm)>; 890} // Predicates = [HasStdExtCOrZca, IsRV64] 891 892// Quadrant 1 893let Predicates = [HasStdExtCOrZca] in { 894def : CompressPat<(ADDI X0, X0, 0), (C_NOP)>; 895def : CompressPat<(ADDI GPRNoX0:$rs1, GPRNoX0:$rs1, simm6nonzero:$imm), 896 (C_ADDI GPRNoX0:$rs1, simm6nonzero:$imm)>; 897} // Predicates = [HasStdExtCOrZca] 898 899let Predicates = [HasStdExtCOrZca, IsRV32] in { 900def : CompressPat<(JAL X1, simm12_lsb0:$offset), 901 (C_JAL simm12_lsb0:$offset)>; 902} // Predicates = [HasStdExtCOrZca, IsRV32] 903 904let Predicates = [HasStdExtCOrZca, IsRV64] in { 905def : CompressPat<(ADDIW GPRNoX0:$rs1, GPRNoX0:$rs1, simm6:$imm), 906 (C_ADDIW GPRNoX0:$rs1, simm6:$imm)>; 907} // Predicates = [HasStdExtCOrZca, IsRV64] 908 909let Predicates = [HasStdExtCOrZca] in { 910def : CompressPat<(ADDI GPRNoX0:$rd, X0, simm6:$imm), 911 (C_LI GPRNoX0:$rd, simm6:$imm)>; 912def : CompressPat<(ADDI X2, X2, simm10_lsb0000nonzero:$imm), 913 (C_ADDI16SP X2, simm10_lsb0000nonzero:$imm)>; 914def : CompressPat<(LUI GPRNoX0X2:$rd, c_lui_imm:$imm), 915 (C_LUI GPRNoX0X2:$rd, c_lui_imm:$imm)>; 916def : CompressPat<(SRLI GPRC:$rs1, GPRC:$rs1, uimmlog2xlennonzero:$imm), 917 (C_SRLI GPRC:$rs1, uimmlog2xlennonzero:$imm)>; 918def : CompressPat<(SRAI GPRC:$rs1, GPRC:$rs1, uimmlog2xlennonzero:$imm), 919 (C_SRAI GPRC:$rs1, uimmlog2xlennonzero:$imm)>; 920def : CompressPat<(ANDI GPRC:$rs1, GPRC:$rs1, simm6:$imm), 921 (C_ANDI GPRC:$rs1, simm6:$imm)>; 922def : CompressPat<(SUB GPRC:$rs1, GPRC:$rs1, GPRC:$rs2), 923 (C_SUB GPRC:$rs1, GPRC:$rs2)>; 924def : CompressPat<(XOR GPRC:$rs1, GPRC:$rs1, GPRC:$rs2), 925 (C_XOR GPRC:$rs1, GPRC:$rs2)>; 926let isCompressOnly = true in 927def : CompressPat<(XOR GPRC:$rs1, GPRC:$rs2, GPRC:$rs1), 928 (C_XOR GPRC:$rs1, GPRC:$rs2)>; 929def : CompressPat<(OR GPRC:$rs1, GPRC:$rs1, GPRC:$rs2), 930 (C_OR GPRC:$rs1, GPRC:$rs2)>; 931let isCompressOnly = true in 932def : CompressPat<(OR GPRC:$rs1, GPRC:$rs2, GPRC:$rs1), 933 (C_OR GPRC:$rs1, GPRC:$rs2)>; 934def : CompressPat<(AND GPRC:$rs1, GPRC:$rs1, GPRC:$rs2), 935 (C_AND GPRC:$rs1, GPRC:$rs2)>; 936let isCompressOnly = true in 937def : CompressPat<(AND GPRC:$rs1, GPRC:$rs2, GPRC:$rs1), 938 (C_AND GPRC:$rs1, GPRC:$rs2)>; 939} // Predicates = [HasStdExtCOrZca] 940 941let Predicates = [HasStdExtCOrZca, IsRV64] in { 942let isCompressOnly = true in 943def : CompressPat<(ADDIW GPRNoX0:$rd, X0, simm6:$imm), 944 (C_LI GPRNoX0:$rd, simm6:$imm)>; 945def : CompressPat<(SUBW GPRC:$rs1, GPRC:$rs1, GPRC:$rs2), 946 (C_SUBW GPRC:$rs1, GPRC:$rs2)>; 947def : CompressPat<(ADDW GPRC:$rs1, GPRC:$rs1, GPRC:$rs2), 948 (C_ADDW GPRC:$rs1, GPRC:$rs2)>; 949let isCompressOnly = true in 950def : CompressPat<(ADDW GPRC:$rs1, GPRC:$rs2, GPRC:$rs1), 951 (C_ADDW GPRC:$rs1, GPRC:$rs2)>; 952} // Predicates = [HasStdExtCOrZca, IsRV64] 953 954let Predicates = [HasStdExtCOrZca] in { 955def : CompressPat<(JAL X0, simm12_lsb0:$offset), 956 (C_J simm12_lsb0:$offset)>; 957def : CompressPat<(BEQ GPRC:$rs1, X0, simm9_lsb0:$imm), 958 (C_BEQZ GPRC:$rs1, simm9_lsb0:$imm)>; 959let isCompressOnly = true in 960def : CompressPat<(BEQ X0, GPRC:$rs1, simm9_lsb0:$imm), 961 (C_BEQZ GPRC:$rs1, simm9_lsb0:$imm)>; 962def : CompressPat<(BNE GPRC:$rs1, X0, simm9_lsb0:$imm), 963 (C_BNEZ GPRC:$rs1, simm9_lsb0:$imm)>; 964let isCompressOnly = true in 965def : CompressPat<(BNE X0, GPRC:$rs1, simm9_lsb0:$imm), 966 (C_BNEZ GPRC:$rs1, simm9_lsb0:$imm)>; 967} // Predicates = [HasStdExtCOrZca] 968 969// Quadrant 2 970let Predicates = [HasStdExtCOrZca] in { 971def : CompressPat<(SLLI GPRNoX0:$rs1, GPRNoX0:$rs1, uimmlog2xlennonzero:$imm), 972 (C_SLLI GPRNoX0:$rs1, uimmlog2xlennonzero:$imm)>; 973} // Predicates = [HasStdExtCOrZca] 974 975let Predicates = [HasStdExtCOrZcd, HasStdExtD] in { 976def : CompressPat<(FLD FPR64:$rd, SPMem:$rs1, uimm9_lsb000:$imm), 977 (C_FLDSP FPR64:$rd, SPMem:$rs1, uimm9_lsb000:$imm)>; 978} // Predicates = [HasStdExtCOrZcd, HasStdExtD] 979 980let Predicates = [HasStdExtCOrZca] in { 981def : CompressPat<(LW GPRNoX0:$rd, SPMem:$rs1, uimm8_lsb00:$imm), 982 (C_LWSP GPRNoX0:$rd, SPMem:$rs1, uimm8_lsb00:$imm)>; 983} // Predicates = [HasStdExtCOrZca] 984 985let Predicates = [HasStdExtCOrZcfOrZce, HasStdExtF, IsRV32] in { 986def : CompressPat<(FLW FPR32:$rd, SPMem:$rs1, uimm8_lsb00:$imm), 987 (C_FLWSP FPR32:$rd, SPMem:$rs1, uimm8_lsb00:$imm)>; 988} // Predicates = [HasStdExtC, HasStdExtF, IsRV32] 989 990let Predicates = [HasStdExtCOrZca, IsRV64] in { 991def : CompressPat<(LD GPRNoX0:$rd, SPMem:$rs1, uimm9_lsb000:$imm), 992 (C_LDSP GPRNoX0:$rd, SPMem:$rs1, uimm9_lsb000:$imm)>; 993} // Predicates = [HasStdExtCOrZca, IsRV64] 994 995let Predicates = [HasStdExtCOrZca] in { 996def : CompressPat<(JALR X0, GPRNoX0:$rs1, 0), 997 (C_JR GPRNoX0:$rs1)>; 998let isCompressOnly = true in { 999def : CompressPat<(ADD GPRNoX0:$rs1, X0, GPRNoX0:$rs2), 1000 (C_MV GPRNoX0:$rs1, GPRNoX0:$rs2)>; 1001def : CompressPat<(ADD GPRNoX0:$rs1, GPRNoX0:$rs2, X0), 1002 (C_MV GPRNoX0:$rs1, GPRNoX0:$rs2)>; 1003} 1004def : CompressPat<(ADDI GPRNoX0:$rs1, GPRNoX0:$rs2, 0), 1005 (C_MV GPRNoX0:$rs1, GPRNoX0:$rs2)>; 1006def : CompressPat<(EBREAK), (C_EBREAK)>; 1007def : CompressPat<(UNIMP), (C_UNIMP)>; 1008def : CompressPat<(JALR X1, GPRNoX0:$rs1, 0), 1009 (C_JALR GPRNoX0:$rs1)>; 1010def : CompressPat<(ADD GPRNoX0:$rs1, GPRNoX0:$rs1, GPRNoX0:$rs2), 1011 (C_ADD GPRNoX0:$rs1, GPRNoX0:$rs2)>; 1012let isCompressOnly = true in 1013def : CompressPat<(ADD GPRNoX0:$rs1, GPRNoX0:$rs2, GPRNoX0:$rs1), 1014 (C_ADD GPRNoX0:$rs1, GPRNoX0:$rs2)>; 1015} // Predicates = [HasStdExtCOrZca] 1016 1017let Predicates = [HasStdExtCOrZcd, HasStdExtD] in { 1018def : CompressPat<(FSD FPR64:$rs2, SPMem:$rs1, uimm9_lsb000:$imm), 1019 (C_FSDSP FPR64:$rs2, SPMem:$rs1, uimm9_lsb000:$imm)>; 1020} // Predicates = [HasStdExtCOrZcd, HasStdExtD] 1021 1022let Predicates = [HasStdExtCOrZca] in { 1023def : CompressPat<(SW GPR:$rs2, SPMem:$rs1, uimm8_lsb00:$imm), 1024 (C_SWSP GPR:$rs2, SPMem:$rs1, uimm8_lsb00:$imm)>; 1025} // Predicates = [HasStdExtCOrZca] 1026 1027let Predicates = [HasStdExtCOrZcfOrZce, HasStdExtF, IsRV32] in { 1028def : CompressPat<(FSW FPR32:$rs2, SPMem:$rs1, uimm8_lsb00:$imm), 1029 (C_FSWSP FPR32:$rs2, SPMem:$rs1, uimm8_lsb00:$imm)>; 1030} // Predicates = [HasStdExtC, HasStdExtF, IsRV32] 1031 1032let Predicates = [HasStdExtCOrZca, IsRV64] in { 1033def : CompressPat<(SD GPR:$rs2, SPMem:$rs1, uimm9_lsb000:$imm), 1034 (C_SDSP GPR:$rs2, SPMem:$rs1, uimm9_lsb000:$imm)>; 1035} // Predicates = [HasStdExtCOrZca, IsRV64] 1036