1926 lines · plain
1//===---------------- RISCVInstrInfoXQci.td ----------------*- 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-exception6//7//===----------------------------------------------------------------------===//8//9// This file describes the vendor extensions defined by QUALCOMM.10//11//===----------------------------------------------------------------------===//12 13//===----------------------------------------------------------------------===//14// Operand and SDNode transformation definitions.15//===----------------------------------------------------------------------===//16 17def SDT_SetMultiple : SDTypeProfile<0, 4, [SDTCisSameAs<0, 1>,18 SDTCisSameAs<1, 3>,19 SDTCisPtrTy<2>,20 SDTCisVT<3, XLenVT>]>;21 22def qc_setwmi : RVSDNode<"QC_SETWMI", SDT_SetMultiple,23 [SDNPHasChain, SDNPMayStore, SDNPMemOperand]>;24 25def qc_insb : RVSDNode<"QC_INSB", SDTypeProfile<1, 4, [SDTCisSameAs<0, 1>,26 SDTCisSameAs<0, 2>,27 SDTCisVT<0, i32>,28 SDTCisInt<3>,29 SDTCisInt<4>]>,30 []>;31 32def qc_e_li : RVSDNode<"QC_E_LI", SDTIntUnaryOp>;33 34def uimm5nonzero : RISCVOp<XLenVT>,35 ImmLeaf<XLenVT, [{return (Imm != 0) && isUInt<5>(Imm);}]> {36 let ParserMatchClass = UImmAsmOperand<5, "NonZero">;37 let DecoderMethod = "decodeUImmNonZeroOperand<5>";38 let OperandType = "OPERAND_UIMM5_NONZERO";39 let MCOperandPredicate = [{40 int64_t Imm;41 if (!MCOp.evaluateAsConstantImm(Imm))42 return false;43 return (Imm != 0) && isUInt<5>(Imm);;44 }];45}46 47def tuimm5nonzero : TImmLeaf<XLenVT, [{return (Imm != 0) && isUInt<5>(Imm);}]>;48 49def uimm5gt3 : RISCVOp<XLenVT>, ImmLeaf<XLenVT,50 [{return (Imm > 3) && isUInt<5>(Imm);}]> {51 let ParserMatchClass = UImmAsmOperand<5, "GT3">;52 let DecoderMethod = "decodeUImmOperandGE<5, 4>";53 let OperandType = "OPERAND_UIMM5_GT3";54}55 56def tuimm5gt3 : TImmLeaf<XLenVT, [{return (Imm > 3) && isUInt<5>(Imm);}]>;57 58def UImm5Plus1AsmOperand : AsmOperandClass {59 let Name = "UImm5Plus1";60 let RenderMethod = "addImmOperands";61 let DiagnosticType = "InvalidUImm5Plus1";62}63 64def uimm5_plus1 : RISCVOp, ImmLeaf<XLenVT,65 [{return (isUInt<5>(Imm) && (Imm != 0)) || (Imm == 32);}]> {66 let ParserMatchClass = UImm5Plus1AsmOperand;67 let EncoderMethod = "getImmOpValueMinus1";68 let DecoderMethod = "decodeUImmPlus1Operand<5>";69 let OperandType = "OPERAND_UIMM5_PLUS1";70 let MCOperandPredicate = [{71 int64_t Imm;72 if (!MCOp.evaluateAsConstantImm(Imm))73 return false;74 return (isUInt<5>(Imm) && (Imm != 0)) || (Imm == 32);75 }];76}77 78def uimm5ge6_plus1 : RISCVOp<XLenVT>, ImmLeaf<XLenVT,79 [{return (Imm >= 6) && (isUInt<5>(Imm) || (Imm == 32));}]> {80 let ParserMatchClass = UImmAsmOperand<5, "GE6Plus1">;81 let EncoderMethod = "getImmOpValueMinus1";82 let DecoderMethod = "decodeUImmPlus1OperandGE<5,6>";83 let OperandType = "OPERAND_UIMM5_GE6_PLUS1";84 let MCOperandPredicate = [{85 int64_t Imm;86 if (!MCOp.evaluateAsConstantImm(Imm))87 return false;88 return (Imm >= 6) && (isUInt<5>(Imm) || (Imm == 32));89 }];90}91 92def uimm5slist : RISCVOp<XLenVT>, ImmLeaf<XLenVT,93 [{return ((Imm == 0) ||94 (Imm == 1) ||95 (Imm == 2) ||96 (Imm == 4) ||97 (Imm == 8) ||98 (Imm == 16) ||99 (Imm == 15) ||100 (Imm == 31));}]> {101 let ParserMatchClass = UImmAsmOperand<5, "Slist">;102 let EncoderMethod = "getImmOpValueSlist";103 let DecoderMethod = "decodeUImmSlistOperand";104 let OperandType = "OPERAND_UIMM5_SLIST";105 let MCOperandPredicate = [{106 int64_t Imm;107 if (!MCOp.evaluateAsConstantImm(Imm))108 return false;109 return ((Imm == 0) || (Imm == 1) ||110 (Imm == 2) || (Imm == 4) ||111 (Imm == 8) || (Imm == 16) ||112 (Imm == 15) || (Imm == 31));113 }];114}115 116def tuimm7_lsb00 : TImmLeaf<XLenVT,[{return isShiftedUInt<5, 2>(Imm);}]>;117 118def uimm10 : RISCVUImmLeafOp<10>;119 120def uimm11 : RISCVUImmLeafOp<11>;121 122// A 14-bit unsigned immediate where the least significant two bits are zero.123def uimm14lsb00 : RISCVOp,124 ImmLeaf<XLenVT, [{return isShiftedUInt<12, 2>(Imm);}]> {125 let ParserMatchClass = UImmAsmOperand<14, "Lsb00">;126 let EncoderMethod = "getImmOpValue";127 let DecoderMethod = "decodeUImmOperand<14>";128 let OperandType = "OPERAND_UIMM14_LSB00";129}130 131def uimm16nonzero : RISCVOp<XLenVT>,132 ImmLeaf<XLenVT, [{return (Imm != 0) && isUInt<16>(Imm);}]> {133 let ParserMatchClass = UImmAsmOperand<16, "NonZero">;134 let DecoderMethod = "decodeUImmNonZeroOperand<16>";135 let OperandType = "OPERAND_UIMM16_NONZERO";136}137 138def simm5nonzero : RISCVOp<XLenVT>,139 ImmLeaf<XLenVT, [{return (Imm != 0) && isInt<5>(Imm);}]> {140 let ParserMatchClass = SImmAsmOperand<5, "NonZero">;141 let DecoderMethod = "decodeSImmNonZeroOperand<5>";142 let OperandType = "OPERAND_SIMM5_NONZERO";143 let MCOperandPredicate = [{144 int64_t Imm;145 if (!MCOp.evaluateAsConstantImm(Imm))146 return false;147 return (Imm != 0) && isInt<5>(Imm);148 }];149}150 151def simm11 : RISCVSImmLeafOp<11>;152 153def simm16 : RISCVSImmOp<16>;154 155def simm16nonzero : RISCVOp<XLenVT>,156 ImmLeaf<XLenVT, [{return (Imm != 0) && isInt<16>(Imm);}]> {157 let ParserMatchClass = SImmAsmOperand<16, "NonZero">;158 let DecoderMethod = "decodeSImmNonZeroOperand<16>";159 let OperandType = "OPERAND_SIMM16_NONZERO";160}161 162def simm20_li : RISCVOp<XLenVT>,163 ImmLeaf<XLenVT, [{return isInt<20>(Imm);}]>{164 let ParserMatchClass = SImmAsmOperand<20, "LI">;165 let EncoderMethod = "getImmOpValue";166 let DecoderMethod = "decodeSImmOperand<20>";167 let OperandType = "OPERAND_SIMM20_LI";168 let MCOperandPredicate = [{169 int64_t Imm;170 if (MCOp.evaluateAsConstantImm(Imm))171 return isInt<20>(Imm);172 return MCOp.isBareSymbolRef();173 }];174}175 176def simm26 : RISCVSImmLeafOp<26>;177 178def simm26_nosimm12 : ImmLeaf<XLenVT, [{179 return isInt<26>(Imm) && !isInt<12>(Imm);}]>;180 181def simm32_nosimm26 : ImmLeaf<XLenVT, [{182 return isInt<32>(Imm) && !isInt<26>(Imm);}]>;183 184class BareSImmNAsmOperand<int width>185 : ImmAsmOperand<"BareS", width, ""> {186 let PredicateMethod = "isBareSimmN<" # width # ">";187}188 189// 32-bit Immediate, used by RV32 Instructions in 32-bit operations, so no190// sign-/zero-extension. This is represented internally as a signed 32-bit value.191def bare_simm32 : RISCVOp<XLenVT> {192 let ParserMatchClass = BareSImmNAsmOperand<32>;193 let EncoderMethod = "getImmOpValue";194 let DecoderMethod = "decodeSImmOperand<32>";195 let OperandType = "OPERAND_BARE_SIMM32";196 let MCOperandPredicate = [{197 int64_t Imm;198 if (MCOp.evaluateAsConstantImm(Imm))199 return isInt<32>(Imm);200 return MCOp.isBareSymbolRef();201 }];202}203 204// A 32-bit signed immediate where the least significant bit is zero.205def bare_simm32_lsb0 : Operand<OtherVT> {206 let ParserMatchClass = BareSImmNLsb0AsmOperand<32>;207 let PrintMethod = "printBranchOperand";208 let EncoderMethod = "getImmOpValueAsrN<1>";209 let DecoderMethod = "decodeSImmOperandAndLslN<32, 1>";210 let MCOperandPredicate = [{211 int64_t Imm;212 if (MCOp.evaluateAsConstantImm(Imm))213 return isShiftedInt<31, 1>(Imm);214 return MCOp.isBareSymbolRef();215 }];216 let OperandType = "OPERAND_PCREL";217}218 219def AddLike: PatFrags<(ops node:$A, node:$B),220 [(add node:$A, node:$B), (or node:$A, node:$B)], [{221 return CurDAG->isBaseWithConstantOffset(SDValue(N, 0));222}]>;223 224//===----------------------------------------------------------------------===//225// Instruction Formats226//===----------------------------------------------------------------------===//227 228 229class DirectiveInsnQC_EAI<dag outs, dag ins, string argstr>230 : RVInst48<outs, ins, "", "", [], InstFormatQC_EAI> {231 bits<7> opcode;232 bits<3> func3;233 bits<1> func1;234 235 bits<5> rd;236 bits<32> imm32;237 238 let Inst{47-16} = imm32;239 let Inst{15} = func1;240 let Inst{14-12} = func3;241 let Inst{11-7} = rd;242 let Inst{6-0} = opcode;243 244 let AsmString = ".insn qc.eai " # argstr;245}246 247class DirectiveInsnQC_EI<dag outs, dag ins, string argstr>248 : RVInst48<outs, ins, "", "", [], InstFormatQC_EI> {249 bits<7> opcode;250 bits<3> func3;251 bits<2> func2;252 253 bits<5> rd;254 bits<5> rs1;255 bits<26> imm26;256 257 let Inst{47-32} = imm26{25-10};258 let Inst{31-30} = func2;259 let Inst{29-20} = imm26{9-0};260 let Inst{19-15} = rs1;261 let Inst{14-12} = func3;262 let Inst{11-7} = rd;263 let Inst{6-0} = opcode;264 265 let AsmString = ".insn qc.ei " # argstr;266}267 268class DirectiveInsnQC_EB<dag outs, dag ins, string argstr>269 : RVInst48<outs, ins, "", "", [], InstFormatQC_EB> {270 bits<7> opcode;271 bits<3> func3;272 bits<5> func5;273 274 bits<5> rs1;275 bits<12> imm12; // This one is the PC-relative offset276 bits<16> imm16;277 278 let Inst{47-32} = imm16;279 let Inst{31} = imm12{11};280 let Inst{30-25} = imm12{9-4};281 let Inst{24-20} = func5;282 let Inst{19-15} = rs1;283 let Inst{14-12} = func3;284 let Inst{11-8} = imm12{3-0};285 let Inst{7} = imm12{10};286 let Inst{6-0} = opcode;287 288 let AsmString = ".insn qc.eb " # argstr;289}290 291class DirectiveInsnQC_EJ<dag outs, dag ins, string argstr>292 : RVInst48<outs, ins, "", "", [], InstFormatQC_EJ> {293 bits<7> opcode;294 bits<3> func3;295 bits<2> func2;296 bits<5> func5;297 298 bits<31> imm31;299 300 let Inst{47-32} = imm31{30-15};301 let Inst{31} = imm31{11};302 let Inst{30-25} = imm31{9-4};303 let Inst{24-20} = func5;304 let Inst{19-17} = imm31{14-12};305 let Inst{16-15} = func2;306 let Inst{14-12} = func3;307 let Inst{11-8} = imm31{3-0};308 let Inst{7} = imm31{10};309 let Inst{6-0} = opcode;310 311 let AsmString = ".insn qc.ej " # argstr;312}313 314class DirectiveInsnQC_ES<dag outs, dag ins, string argstr>315 : RVInst48<outs, ins, "", "", [], InstFormatQC_ES> {316 bits<7> opcode;317 bits<3> func3;318 bits<2> func2;319 320 bits<5> rs1;321 bits<5> rs2;322 bits<26> imm26;323 324 let Inst{47-32} = imm26{25-10};325 let Inst{31-30} = func2;326 let Inst{29-25} = imm26{9-5};327 let Inst{24-20} = rs2;328 let Inst{19-15} = rs1;329 let Inst{14-12} = func3;330 let Inst{11-7} = imm26{4-0};331 let Inst{6-0} = opcode;332 333 let AsmString = ".insn qc.es " # argstr;334}335 336 337let isCodeGenOnly = true, hasSideEffects = true, mayLoad = true,338 mayStore = true, hasNoSchedulingInfo = true, Predicates=[IsRV32] in {339def InsnQC_EAI : DirectiveInsnQC_EAI<(outs AnyReg:$rd),340 (ins uimm7_opcode:$opcode,341 uimm3:$func3,342 uimm1:$func1,343 bare_simm32:$imm32),344 "$opcode, $func3, $func1, $rd, $imm32">;345def InsnQC_EI : DirectiveInsnQC_EI<(outs AnyReg:$rd),346 (ins uimm7_opcode:$opcode,347 uimm3:$func3,348 uimm2:$func2,349 AnyReg:$rs1,350 simm26:$imm26),351 "$opcode, $func3, $func2, $rd, $rs1, $imm26">;352def InsnQC_EI_Mem : DirectiveInsnQC_EI<(outs AnyReg:$rd),353 (ins uimm7_opcode:$opcode,354 uimm3:$func3,355 uimm2:$func2,356 AnyReg:$rs1,357 simm26:$imm26),358 "$opcode, $func3, $func2, $rd, ${imm26}(${rs1})">;359def InsnQC_EB : DirectiveInsnQC_EB<(outs),360 (ins uimm7_opcode:$opcode,361 uimm3:$func3,362 uimm5:$func5,363 AnyReg:$rs1,364 simm16:$imm16,365 bare_simm13_lsb0:$imm12),366 "$opcode, $func3, $func5, $rs1, $imm16, $imm12">;367def InsnQC_EJ : DirectiveInsnQC_EJ<(outs),368 (ins uimm7_opcode:$opcode,369 uimm3:$func3,370 uimm2:$func2,371 uimm5:$func5,372 bare_simm32_lsb0:$imm31),373 "$opcode, $func3, $func2, $func5, $imm31">;374def InsnQC_ES : DirectiveInsnQC_ES<(outs),375 (ins uimm7_opcode:$opcode,376 uimm3:$func3,377 uimm2:$func2,378 AnyReg:$rs2,379 AnyReg:$rs1,380 simm26:$imm26),381 "$opcode, $func3, $func2, $rs2, ${imm26}(${rs1})">;382} // isCodeGenOnly, hasSideEffects, mayLoad, mayStore, hasNoSchedulingInfo, Predicates383 384let EmitPriority = 0, Predicates = [IsRV32] in {385def : InstAlias<".insn_qc.eai $opcode, $func3, $func1, $rd, $imm32",386 (InsnQC_EAI AnyReg:$rd,387 uimm7_opcode:$opcode,388 uimm3:$func3,389 uimm1:$func1,390 bare_simm32:$imm32)>;391def : InstAlias<".insn_qc.ei $opcode, $func3, $func2, $rd, $rs1, $imm26",392 (InsnQC_EI AnyReg:$rd,393 uimm7_opcode:$opcode,394 uimm3:$func3,395 uimm2:$func2,396 AnyReg:$rs1,397 simm26:$imm26)>;398def : InstAlias<".insn_qc.ei $opcode, $func3, $func2, $rd, ${imm26}(${rs1})",399 (InsnQC_EI_Mem AnyReg:$rd,400 uimm7_opcode:$opcode,401 uimm3:$func3,402 uimm2:$func2,403 AnyReg:$rs1,404 simm26:$imm26)>;405def : InstAlias<".insn_qc.ei $opcode, $func3, $func2, $rd, (${rs1})",406 (InsnQC_EI_Mem AnyReg:$rd,407 uimm7_opcode:$opcode,408 uimm3:$func3,409 uimm2:$func2,410 AnyReg:$rs1,411 0)>;412def : InstAlias<".insn_qc.eb $opcode, $func3, $func5, $rs1, $imm16, $imm12",413 (InsnQC_EB uimm7_opcode:$opcode,414 uimm3:$func3,415 uimm5:$func5,416 AnyReg:$rs1,417 simm16:$imm16,418 bare_simm13_lsb0:$imm12)>;419def : InstAlias<".insn_qc.ej $opcode, $func3, $func2, $func5, $imm31",420 (InsnQC_EJ uimm7_opcode:$opcode,421 uimm3:$func3,422 uimm2:$func2,423 uimm5:$func5,424 bare_simm32_lsb0:$imm31)>;425def : InstAlias<".insn_qc.es $opcode, $func3, $func2, $rs2, ${imm26}(${rs1})",426 (InsnQC_ES uimm7_opcode:$opcode,427 uimm3:$func3,428 uimm2:$func2,429 AnyReg:$rs2,430 AnyReg:$rs1,431 simm26:$imm26)>;432def : InstAlias<".insn_qc.es $opcode, $func3, $func2, $rs2, (${rs1})",433 (InsnQC_ES uimm7_opcode:$opcode,434 uimm3:$func3,435 uimm2:$func2,436 AnyReg:$rs2,437 AnyReg:$rs1,438 0)>;439} // EmitPriority = 0, Predicates = [IsRV32]440 441//===----------------------------------------------------------------------===//442// Instruction Class Templates443//===----------------------------------------------------------------------===//444 445let hasSideEffects = 0, mayLoad = 1, mayStore = 0 in {446class QCILoad_ScaleIdx<bits<4> funct4, string opcodestr>447 : RVInstRBase<0b111, OPC_CUSTOM_0,448 (outs GPR:$rd), (ins GPRMem:$rs1, GPRNoX0:$rs2, uimm3:$shamt),449 opcodestr, "$rd, $rs1, $rs2, $shamt"> {450 bits<3> shamt;451 let Inst{31-28} = funct4;452 let Inst{27-25} = shamt;453}454}455 456let hasSideEffects = 0, mayLoad = 0, mayStore = 1 in {457// rd corresponds to the source for the store 'rs3' described in the spec.458class QCIStore_ScaleIdx<bits<4> funct4, string opcodestr>459 : RVInstRBase<0b110, OPC_CUSTOM_1, (outs),460 (ins GPR:$rd, GPRMem:$rs1, GPRNoX0:$rs2, uimm3:$shamt),461 opcodestr, "$rd, $rs1, $rs2, $shamt"> {462 bits<3> shamt;463 let Inst{31-28} = funct4;464 let Inst{27-25} = shamt;465}466}467 468class QCIRVInstI<bits<4> funct4, string opcodestr>469 : RVInstIUnary<{0b000, funct4, 0b00000}, 0b011, OPC_CUSTOM_0,470 (outs GPRNoX0:$rd), (ins GPRNoX0:$rs1), opcodestr,471 "$rd, $rs1">;472 473class QCIRVInstR<bits<4> funct4, string opcodestr>474 : RVInstR<{0b000, funct4}, 0b011, OPC_CUSTOM_0, (outs GPRNoX0:$rd),475 (ins GPRNoX0:$rs1), opcodestr, "$rd, $rs1"> {476 let rs2 = 0;477}478 479class QCIRVInstRR<bits<5> funct5, DAGOperand InTyRs1, string opcodestr>480 : RVInstR<{0b00, funct5}, 0b011, OPC_CUSTOM_0, (outs GPRNoX0:$rd),481 (ins InTyRs1:$rs1, GPRNoX0:$rs2), opcodestr, "$rd, $rs1, $rs2">;482 483class QCIRVInstRRTied<bits<5> funct5, DAGOperand InTyRs1, string opcodestr>484 : RVInstR<{0b00, funct5}, 0b011, OPC_CUSTOM_0, (outs GPRNoX0:$rd_wb),485 (ins GPRNoX0:$rd, InTyRs1:$rs1, GPRNoX0:$rs2), opcodestr,486 "$rd, $rs1, $rs2"> {487 let Constraints = "$rd = $rd_wb";488}489 490class QCIBitManipRII<bits<3> funct3, bits<2> funct2,491 DAGOperand InTyRs1, string opcodestr>492 : RVInstIBase<funct3, OPC_CUSTOM_0, (outs GPRNoX0:$rd),493 (ins InTyRs1:$rs1, uimm5_plus1:$width, uimm5:$shamt),494 opcodestr, "$rd, $rs1, $width, $shamt"> {495 bits<5> shamt;496 bits<5> width;497 498 let Inst{31-30} = funct2;499 let Inst{29-25} = width;500 let Inst{24-20} = shamt;501}502 503class QCIBitManipRIITied<bits<3> funct3, bits<2> funct2,504 DAGOperand InTyRs1, string opcodestr>505 : RVInstIBase<funct3, OPC_CUSTOM_0, (outs GPRNoX0:$rd_wb), (ins GPRNoX0:$rd,506 InTyRs1:$rs1, uimm5_plus1:$width, uimm5:$shamt),507 opcodestr, "$rd, $rs1, $width, $shamt"> {508 let Constraints = "$rd = $rd_wb";509 bits<5> shamt;510 bits<5> width;511 512 let Inst{31-30} = funct2;513 let Inst{29-25} = width;514 let Inst{24-20} = shamt;515}516 517class QCIRVInstRI<bits<1> funct1, DAGOperand InTyImm11,518 string opcodestr>519 : RVInstIBase<0b000, OPC_CUSTOM_0, (outs GPRNoX0:$rd_wb),520 (ins GPRNoX0:$rd, GPRNoX0:$rs1, InTyImm11:$imm11), opcodestr,521 "$rd, $rs1, $imm11"> {522 let Constraints = "$rd = $rd_wb";523 bits<11> imm11;524 525 let Inst{31-31} = funct1;526 let Inst{30-20} = imm11;527}528 529let hasSideEffects = 0, mayLoad = 0, mayStore = 0, isCommutable = 1 in530class QCISELECTIICC<bits<3> funct3, string opcodestr>531 : RVInstR4<0b00, funct3, OPC_CUSTOM_2, (outs GPRNoX0:$rd_wb),532 (ins GPRNoX0:$rd, GPRNoX0:$rs1, simm5:$simm1, simm5:$simm2),533 opcodestr, "$rd, $rs1, $simm1, $simm2"> {534 let Constraints = "$rd = $rd_wb";535 bits<5> simm1;536 bits<5> simm2;537 538 let rs3 = simm2;539 let rs2 = simm1;540}541 542let hasSideEffects = 0, mayLoad = 0, mayStore = 0, isCommutable = 1 in543class QCISELECTICC<bits<3> funct3, string opcodestr>544 : RVInstR4<0b01, funct3, OPC_CUSTOM_2, (outs GPRNoX0:$rd_wb),545 (ins GPRNoX0:$rd, GPRNoX0:$rs1, GPRNoX0:$rs2, simm5:$simm2),546 opcodestr, "$rd, $rs1, $rs2, $simm2"> {547 let Constraints = "$rd = $rd_wb";548 bits<5> simm2;549 550 let rs3 = simm2;551}552 553let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in554class QCISELECTCCI<bits<3> funct3, string opcodestr>555 : RVInstR4<0b10, funct3, OPC_CUSTOM_2, (outs GPRNoX0:$rd_wb),556 (ins GPRNoX0:$rd, simm5:$imm, GPRNoX0:$rs2, GPRNoX0:$rs3),557 opcodestr, "$rd, $imm, $rs2, $rs3"> {558 let Constraints = "$rd = $rd_wb";559 bits<5> imm;560 561 let rs1 = imm;562}563 564let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in565class QCISELECTICCI<bits<3> funct3, string opcodestr>566 : RVInstR4<0b11, funct3, OPC_CUSTOM_2, (outs GPRNoX0:$rd_wb),567 (ins GPRNoX0:$rd, simm5:$imm, GPRNoX0:$rs2, simm5:$simm2),568 opcodestr, "$rd, $imm, $rs2, $simm2"> {569 let Constraints = "$rd = $rd_wb";570 bits<5> imm;571 bits<5> simm2;572 573 let rs3 = simm2;574 let rs1 = imm;575}576 577let hasSideEffects = 0, mayLoad = 1, mayStore = 0 in578class QCILoadMultiple<bits<2> funct2, DAGOperand InTyRs2, string opcodestr>579 : RVInstRBase<0b111, OPC_CUSTOM_0, (outs GPRNoX0:$rd),580 (ins GPR:$rs1, InTyRs2:$rs2, uimm7_lsb00:$imm),581 opcodestr, "$rd, $rs2, ${imm}(${rs1})"> {582 bits<7> imm;583 let Inst{31-25} = {funct2, imm{6-2}};584}585 586 587// rd corresponds to the source for the store 'rs3' described in the spec.588let hasSideEffects = 0, mayLoad = 0, mayStore = 1 in589class QCIStoreMultiple<bits<2> funct2, DAGOperand InTyRd, DAGOperand InTyRs2,590 string opcodestr>591 : RVInstRBase<0b111, OPC_CUSTOM_1, (outs),592 (ins InTyRd:$rd, GPR:$rs1, InTyRs2:$rs2, uimm7_lsb00:$imm),593 opcodestr, "$rd, $rs2, ${imm}(${rs1})"> {594 bits<7> imm;595 let Inst{31-25} = {funct2, imm{6-2}};596}597 598let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in599class QCILICC<bits<3> funct3, bits<2> funct2, DAGOperand InTyRs2, string opcodestr>600 : RVInstRBase<funct3, OPC_CUSTOM_2, (outs GPRNoX0:$rd_wb),601 (ins GPRNoX0:$rd, GPRNoX0:$rs1, InTyRs2:$rs2, simm5:$simm),602 opcodestr, "$rd, $rs1, $rs2, $simm"> {603 let Constraints = "$rd = $rd_wb";604 bits<5> simm;605 606 let Inst{31-25} = {simm, funct2};607}608 609let hasSideEffects = 0, mayLoad = 0, mayStore = 0, isCommutable = 1 in610class QCIMVCC<bits<3> funct3, string opcodestr>611 : RVInstR4<0b00, funct3, OPC_CUSTOM_2, (outs GPRNoX0:$rd_wb),612 (ins GPRNoX0:$rd, GPRNoX0:$rs1, GPRNoX0:$rs2, GPRNoX0:$rs3),613 opcodestr, "$rd, $rs1, $rs2, $rs3"> {614 let Constraints = "$rd = $rd_wb";615}616 617let hasSideEffects = 0, mayLoad = 0, mayStore = 0, isCommutable = 1 in618class QCIMVCCI<bits<3> funct3, string opcodestr, DAGOperand immType>619 : RVInstR4<0b10, funct3, OPC_CUSTOM_2, (outs GPRNoX0:$rd_wb),620 (ins GPRNoX0:$rd, GPRNoX0:$rs1, immType:$imm, GPRNoX0:$rs3),621 opcodestr, "$rd, $rs1, $imm, $rs3"> {622 bits<5> imm;623 624 let Constraints = "$rd = $rd_wb";625 let rs2 = imm;626}627 628class QCI_RVInst16CB_BM<bits<2> funct2, string opcodestr>629 : RVInst16CB<0b100, 0b01, (outs GPRC:$rd),630 (ins GPRC:$rs1, uimmlog2xlennonzero:$shamt),631 opcodestr, "$rs1, $shamt"> {632 bits<5> shamt;633 let Constraints = "$rs1 = $rd";634 let Inst{12} = 0b1;635 let Inst{11-10} = funct2;636 let Inst{6-2} = shamt{4-0};637}638 639let hasSideEffects = 1, mayLoad = 0, mayStore = 0 in640class QCIRVInst16CI_RS1<bits<5> funct5, string OpcodeStr>641 : RVInst16CI<0b000, 0b10, (outs), (ins GPRNoX0:$rs1), OpcodeStr, "$rs1"> {642 bits<5> rs1;643 644 let Inst{12} = 0b1;645 let Inst{11-7} = rs1;646 let Inst{6-2} = funct5{4-0};647}648 649class QCIBranchInst_rii<bits<3> funct3, DAGOperand InTyImm5, string opcodestr>650 : RVInstB<funct3, OPC_CUSTOM_3, (outs),651 (ins GPRNoX0:$rs1, InTyImm5:$rs2, bare_simm13_lsb0:$imm12),652 opcodestr, "$rs1, $rs2, $imm12"> {653 let isBranch = 1;654 let isTerminator = 1;655 let hasSideEffects = 0;656 let mayLoad = 0;657 let mayStore = 0;658}659 660class QCIBranchInst48_rii<bits<5> funct5, DAGOperand InTyImm16, string opcodestr>661 : RVInst48<(outs),662 (ins GPRNoX0:$rs1, InTyImm16:$imm16, bare_simm13_lsb0:$imm12),663 opcodestr, "$rs1, $imm16, $imm12", [], InstFormatQC_EB> {664 bits<5> rs1;665 bits<16> imm16;666 bits<12> imm12;667 668 let Inst{47-32} = imm16;669 let Inst{31} = imm12{11};670 let Inst{30-25} = imm12{9-4};671 let Inst{24-20} = funct5;672 let Inst{19-15} = rs1;673 let Inst{14-12} = 0b100;674 let Inst{11-8} = imm12{3-0};675 let Inst{7} = imm12{10};676 let Inst{6-0} = 0b0011111;677 let isBranch = 1;678 let isTerminator = 1;679 let hasSideEffects = 0;680 let mayLoad = 0;681 let mayStore = 0;682}683 684let hasSideEffects = 1 in685class QCIRVInst16CI_NONE<bits<5> funct5, string OpcodeStr>686 : RVInst16CI<0b000, 0b10, (outs), (ins), OpcodeStr, ""> {687 let Inst{12} = 0b1;688 let Inst{11-7} = funct5;689 let Inst{6-2} = 0b00100;690}691 692let hasSideEffects = 1, mayLoad = 0, mayStore = 0 in693class QCIInt_IMM<bits<1> funct1, string opcodestr>694 : RVInstIBase<0b000, OPC_SYSTEM, (outs), (ins uimm10:$imm10), opcodestr,695 "$imm10"> {696 bits<10> imm10;697 698 let rd = 0;699 let rs1 = imm10{4-0};700 let Inst{31-25} = {0b110011, funct1};701 let Inst{24-20} = imm10{9-5};702}703 704class QCISim_NONE<bits<4> imm11_8, string opcodestr>705 : RVInstI<0b010, OPC_OP_IMM, (outs), (ins), opcodestr, ""> {706 let rs1 = 0;707 let rd = 0;708 let imm12 = {imm11_8, 0b00000000};709}710 711class QCISim_RS1<bits<4> imm11_8, string opcodestr>712 : RVInstI<0b010, OPC_OP_IMM, (outs), (ins GPR:$rs1), opcodestr, "$rs1"> {713 let rd = 0;714 let imm12 = {imm11_8, 0b00000000};715}716 717let mayLoad = 0, mayStore = 0, hasSideEffects = 1 in718class QCISync_UIMM5<bits<4> imm11_8, string opcodestr>719 : RVInstI<0b011, OPC_OP_IMM, (outs), (ins uimm5:$imm5), opcodestr, "$imm5">720{721 bits<5> imm5;722 723 let rs1 = 0;724 let rd = 0;725 let imm12 = {imm11_8, 0b000, imm5};726}727 728let mayLoad = 0, mayStore = 0, hasSideEffects = 1 in729class QCIRVInst16CBSYNC<bits<3> imm5_func2, string OpcodeStr>730 : RVInst16CB<0b100, 0b01, (outs), (ins uimm5slist:$slist), OpcodeStr, "$slist"> {731 bits<3> slist;732 733 let Inst{6-2} = 0;734 let Inst{9-7} = slist;735 let Inst{12-10} = imm5_func2;736}737 738class QCIRVInstEIBase<bits<3> funct3, bits<2> funct2, dag outs,739 dag ins, string opcodestr, string argstr>740 : RVInst48<outs, ins, opcodestr, argstr, [], InstFormatOther> {741 bits<5> rd;742 bits<5> rs1;743 bits<26> imm;744 745 let Inst{47-32} = imm{25-10};746 let Inst{31-30} = funct2;747 let Inst{29-20} = imm{9-0};748 let Inst{19-15} = rs1;749 let Inst{14-12} = funct3;750 let Inst{11-7} = rd;751 let Inst{6-0} = 0b0011111;752}753 754let hasSideEffects = 0, mayLoad = 1, mayStore = 0 in755class QCIRVInstEILoad<bits<3> funct3, bits<2> funct2, string opcodestr>756 : QCIRVInstEIBase<funct3, funct2, (outs GPR:$rd),757 (ins GPRMem:$rs1, simm26:$imm), opcodestr,758 "$rd, ${imm}(${rs1})">;759 760class QCIRVInstESBase<bits<3> funct3, bits<2> funct2, dag outs,761 dag ins, string opcodestr, string argstr>762 : RVInst48<outs, ins, opcodestr, argstr, [], InstFormatOther> {763 bits<5> rs1;764 bits<5> rs2;765 bits<26> imm;766 767 let Inst{47-32} = imm{25-10};768 let Inst{31-30} = funct2;769 let Inst{29-25} = imm{9-5};770 let Inst{24-20} = rs2;771 let Inst{19-15} = rs1;772 let Inst{14-12} = funct3;773 let Inst{11-7} = imm{4-0};774 let Inst{6-0} = 0b0011111;775}776 777let hasSideEffects = 0, mayLoad = 0, mayStore = 1 in778class QCIRVInstESStore<bits<3> funct3, bits<2> funct2, string opcodestr>779 : QCIRVInstESBase<funct3, funct2, (outs),780 (ins GPR:$rs2, GPRMem:$rs1, simm26:$imm),781 opcodestr, "$rs2, ${imm}(${rs1})">;782 783class QCIRVInstEAI<bits<3> funct3, bits<1> funct1, string opcodestr>784 : RVInst48<(outs GPRNoX0:$rd_wb), (ins GPRNoX0:$rd, bare_simm32:$imm),785 opcodestr, "$rd, $imm", [], InstFormatOther> {786 bits<5> rd;787 bits<32> imm;788 789 let Constraints = "$rd = $rd_wb";790 let Inst{47-16} = imm{31-0};791 let Inst{15} = funct1;792 let Inst{14-12} = funct3;793 let Inst{11-7} = rd;794 let Inst{6-0} = 0b0011111;795}796 797class QCIRVInstEI<bits<3> funct3, bits<2> funct2, string opcodestr>798 : QCIRVInstEIBase<funct3, funct2, (outs GPRNoX0:$rd),799 (ins GPRNoX0:$rs1, simm26:$imm), opcodestr,800 "$rd, $rs1, $imm">;801 802let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in803class QCIRVInst48EJ<bits<2> func2, string opcodestr>804 : RVInst48<(outs), (ins bare_simm32_lsb0:$imm31),805 opcodestr, "$imm31", [], InstFormatQC_EJ> {806 bits<31> imm31;807 808 let Inst{47-32} = imm31{30-15};809 let Inst{31} = imm31{11};810 let Inst{30-25} = imm31{9-4};811 let Inst{24-20} = 0b00000;812 let Inst{19-17} = imm31{14-12};813 let Inst{16-15} = func2;814 let Inst{14-12} = 0b100;815 let Inst{11-8} = imm31{3-0};816 let Inst{7} = imm31{10};817 let Inst{6-0} = 0b0011111;818}819 820class SFBQC_LI821 : Pseudo<(outs GPR:$dst),822 (ins GPR:$lhs, GPR:$rhs, cond_code:$cc, GPR:$falsev,823 simm20_li:$imm), []> {824 let hasSideEffects = 0;825 let mayLoad = 0;826 let mayStore = 0;827 let Size = 8;828 let Constraints = "$dst = $falsev";829}830 831class SFBQC_E_LI832 : Pseudo<(outs GPR:$dst),833 (ins GPR:$lhs, GPR:$rhs, cond_code:$cc, GPR:$falsev,834 bare_simm32:$imm), []> {835 let hasSideEffects = 0;836 let mayLoad = 0;837 let mayStore = 0;838 let Size = 10;839 let Constraints = "$dst = $falsev";840}841 842//===----------------------------------------------------------------------===//843// Instructions844//===----------------------------------------------------------------------===//845 846let DecoderNamespace = "Xqci" in {847 848let Predicates = [HasVendorXqcicsr, IsRV32] in {849let hasSideEffects = 1, mayLoad = 0, mayStore = 0 in {850 def QC_CSRRWR : RVInstR<0b1000110, 0b000, OPC_SYSTEM, (outs GPR:$rd),851 (ins GPR:$rs1, GPRNoX0:$rs2), "qc.csrrwr",852 "$rd, $rs1, $rs2">;853 854 def QC_CSRRWRI : RVInstR<0b1000111, 0b000, OPC_SYSTEM, (outs GPR:$rd),855 (ins uimm5:$rs1, GPRNoX0:$rs2), "qc.csrrwri",856 "$rd, $rs1, $rs2">;857} // hasSideEffects = 1, mayLoad = 0, mayStore = 0858} // Predicates = [HasVendorXqcicsr, IsRV32]859 860let Predicates = [HasVendorXqcisls, IsRV32] in {861 def QC_LRB : QCILoad_ScaleIdx<0b1000, "qc.lrb">;862 def QC_LRH : QCILoad_ScaleIdx<0b1001, "qc.lrh">;863 def QC_LRW : QCILoad_ScaleIdx<0b1010, "qc.lrw">;864 def QC_LRBU : QCILoad_ScaleIdx<0b1011, "qc.lrbu">;865 def QC_LRHU : QCILoad_ScaleIdx<0b1100, "qc.lrhu">;866 867 def QC_SRB : QCIStore_ScaleIdx<0b1101, "qc.srb">;868 def QC_SRH : QCIStore_ScaleIdx<0b1110, "qc.srh">;869 def QC_SRW : QCIStore_ScaleIdx<0b1111, "qc.srw">;870} // Predicates = [HasVendorXqcisls, IsRV32]871 872let Predicates = [HasVendorXqcia, IsRV32] in {873let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in {874 def QC_SHLSAT : QCIRVInstRR<0b01010, GPRNoX0, "qc.shlsat">;875 def QC_SHLUSAT : QCIRVInstRR<0b01100, GPRNoX0, "qc.shlusat">;876 def QC_ADDSAT : QCIRVInstRR<0b01110, GPRNoX0, "qc.addsat">;877 def QC_ADDUSAT : QCIRVInstRR<0b01111, GPRNoX0, "qc.addusat">;878 def QC_SUBSAT : QCIRVInstRR<0b10000, GPRNoX0, "qc.subsat">;879 def QC_SUBUSAT : QCIRVInstRR<0b10001, GPRNoX0, "qc.subusat">;880 881 def QC_WRAP : QCIRVInstRR<0b10010, GPR, "qc.wrap">;882 def QC_WRAPI : RVInstI<0b000, OPC_CUSTOM_0, (outs GPRNoX0:$rd),883 (ins GPRNoX0:$rs1, uimm11:$imm11), "qc.wrapi",884 "$rd, $rs1, $imm11"> {885 bits<11> imm11;886 887 let imm12 = {0b0, imm11};888 }889 890 def QC_NORM : QCIRVInstR<0b0111, "qc.norm">;891 def QC_NORMU : QCIRVInstR<0b1000, "qc.normu">;892 def QC_NORMEU : QCIRVInstR<0b1001, "qc.normeu">;893} // hasSideEffects = 0, mayLoad = 0, mayStore = 0894} // Predicates = [HasVendorXqcia, IsRV32]895 896let Predicates = [HasVendorXqcibi, IsRV32] in {897 def QC_BEQI : QCIBranchInst_rii<0b000, simm5nonzero, "qc.beqi">;898 def QC_BNEI : QCIBranchInst_rii<0b001, simm5nonzero, "qc.bnei">;899 def QC_BLTI : QCIBranchInst_rii<0b100, simm5nonzero, "qc.blti">;900 def QC_BGEI : QCIBranchInst_rii<0b101, simm5nonzero, "qc.bgei">;901 def QC_BLTUI : QCIBranchInst_rii<0b110, uimm5nonzero, "qc.bltui">;902 def QC_BGEUI : QCIBranchInst_rii<0b111, uimm5nonzero, "qc.bgeui">;903 904 def QC_E_BEQI : QCIBranchInst48_rii<0b11000, simm16nonzero, "qc.e.beqi">;905 def QC_E_BNEI : QCIBranchInst48_rii<0b11001, simm16nonzero, "qc.e.bnei">;906 def QC_E_BLTI : QCIBranchInst48_rii<0b11100, simm16nonzero, "qc.e.blti">;907 def QC_E_BGEI : QCIBranchInst48_rii<0b11101, simm16nonzero, "qc.e.bgei">;908 def QC_E_BLTUI : QCIBranchInst48_rii<0b11110, uimm16nonzero, "qc.e.bltui">;909 def QC_E_BGEUI : QCIBranchInst48_rii<0b11111, uimm16nonzero, "qc.e.bgeui">;910} // Predicates = [HasVendorXqcibi, IsRV32]911 912let Predicates = [HasVendorXqcibm, IsRV32] in {913let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in {914 def QC_INSBRI : QCIRVInstRI<0b1, simm11, "qc.insbri">;915 def QC_INSBI : RVInstIBase<0b001, OPC_CUSTOM_0, (outs GPRNoX0:$rd_wb),916 (ins GPRNoX0:$rd, simm5:$imm5, uimm5_plus1:$width,917 uimm5:$shamt), "qc.insbi",918 "$rd, $imm5, $width, $shamt"> {919 let Constraints = "$rd = $rd_wb";920 bits<5> imm5;921 bits<5> shamt;922 bits<5> width;923 let rs1 = imm5;924 let Inst{31-30} = 0b00;925 let Inst{29-25} = width;926 let Inst{24-20} = shamt;927 }928 def QC_INSB : QCIBitManipRIITied<0b001, 0b01, GPR, "qc.insb">;929 def QC_INSBH : QCIBitManipRIITied<0b001, 0b10, GPR, "qc.insbh">;930 def QC_INSBR : QCIRVInstRRTied<0b00000, GPR, "qc.insbr">;931 def QC_INSBHR : QCIRVInstRRTied<0b00001, GPR, "qc.insbhr">;932 def QC_INSBPR : QCIRVInstRRTied<0b00010, GPR, "qc.insbpr">;933 def QC_INSBPRH : QCIRVInstRRTied<0b00011, GPR, "qc.insbprh">;934 def QC_EXTU : QCIBitManipRII<0b010, 0b00, GPRNoX0, "qc.extu">;935 def QC_EXTDU : QCIBitManipRII<0b010, 0b10, GPRNoX31, "qc.extdu">;936 def QC_EXTDUR : QCIRVInstRR<0b00100, GPRNoX31, "qc.extdur">;937 def QC_EXTDUPR : QCIRVInstRR<0b00110, GPRNoX31, "qc.extdupr">;938 def QC_EXTDUPRH : QCIRVInstRR<0b00111, GPRNoX31, "qc.extduprh">;939 def QC_EXT : QCIBitManipRII<0b010, 0b01, GPRNoX0, "qc.ext">;940 def QC_EXTD : QCIBitManipRII<0b010, 0b11, GPRNoX31, "qc.extd">;941 def QC_EXTDR : QCIRVInstRR<0b00101, GPRNoX31, "qc.extdr">;942 def QC_EXTDPR : QCIRVInstRR<0b01000, GPRNoX31, "qc.extdpr">;943 def QC_EXTDPRH : QCIRVInstRR<0b01001, GPRNoX31, "qc.extdprh">;944 def QC_COMPRESS2 : QCIRVInstI<0b0000, "qc.compress2">;945 def QC_COMPRESS3 : QCIRVInstI<0b0001, "qc.compress3">;946 def QC_EXPAND2 : QCIRVInstI<0b0010, "qc.expand2">;947 def QC_EXPAND3 : QCIRVInstI<0b0011, "qc.expand3">;948 def QC_CLO : QCIRVInstI<0b0100, "qc.clo">;949 def QC_CTO : QCIRVInstI<0b0101, "qc.cto">;950 def QC_BREV32 : QCIRVInstI<0b0110, "qc.brev32">;951 def QC_C_BEXTI : QCI_RVInst16CB_BM<0b00, "qc.c.bexti">;952 def QC_C_BSETI : QCI_RVInst16CB_BM<0b01, "qc.c.bseti">;953 def QC_C_EXTU : RVInst16CI<0b000, 0b10, (outs GPRNoX0:$rd_wb),954 (ins GPRNoX0:$rd, uimm5ge6_plus1:$width),955 "qc.c.extu", "$rd, $width"> {956 bits<5> rd;957 bits<5> width;958 let Constraints = "$rd = $rd_wb";959 let Inst{6-2} = width;960 let Inst{11-7} = rd;961 let Inst{12} = 0b1;962 }963} // hasSideEffects = 0, mayLoad = 0, mayStore = 0964} // Predicates = [HasVendorXqcibm, IsRV32]965 966let Predicates = [HasVendorXqciac, IsRV32] in {967let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in {968 def QC_C_MULIADD : RVInst16CL<0b001, 0b10, (outs GPRC:$rd_wb),969 (ins GPRC:$rd, GPRC:$rs1, uimm5:$uimm),970 "qc.c.muliadd", "$rd, $rs1, $uimm"> {971 let Constraints = "$rd = $rd_wb";972 bits<5> uimm;973 974 let Inst{12-10} = uimm{3-1};975 let Inst{6} = uimm{0};976 let Inst{5} = uimm{4};977 }978 979 def QC_MULIADD : RVInstI<0b110, OPC_CUSTOM_0, (outs GPRNoX0:$rd_wb),980 (ins GPRNoX0:$rd, GPRNoX0:$rs1, simm12_lo:$imm12),981 "qc.muliadd", "$rd, $rs1, $imm12"> {982 let Constraints = "$rd = $rd_wb";983 }984 985 def QC_SHLADD : RVInstRBase<0b011, OPC_CUSTOM_0, (outs GPRNoX0:$rd),986 (ins GPRNoX0:$rs1, GPRNoX0:$rs2, uimm5gt3:$shamt),987 "qc.shladd", "$rd, $rs1, $rs2, $shamt"> {988 bits<5> shamt;989 990 let Inst{31-30} = 0b01;991 let Inst{29-25} = shamt;992 }993 994} // hasSideEffects = 0, mayLoad = 0, mayStore = 0995} // Predicates = [HasVendorXqciac, IsRV32]996 997let Predicates = [HasVendorXqcics, IsRV32] in {998 def QC_SELECTIIEQ : QCISELECTIICC <0b010, "qc.selectiieq">;999 def QC_SELECTIINE : QCISELECTIICC <0b011, "qc.selectiine">;1000 def QC_SELECTIEQ : QCISELECTICC <0b010, "qc.selectieq">;1001 def QC_SELECTINE : QCISELECTICC <0b011, "qc.selectine">;1002 def QC_SELECTEQI : QCISELECTCCI <0b010, "qc.selecteqi">;1003 def QC_SELECTNEI : QCISELECTCCI <0b011, "qc.selectnei">;1004 def QC_SELECTIEQI : QCISELECTICCI <0b010, "qc.selectieqi">;1005 def QC_SELECTINEI : QCISELECTICCI <0b011, "qc.selectinei">;1006} // Predicates = [HasVendorXqcics, IsRV32]1007 1008let Predicates = [HasVendorXqcilsm, IsRV32] in {1009 def QC_SWM : QCIStoreMultiple<0b00, GPRNoX0, GPRNoX0, "qc.swm">;1010 def QC_SWMI : QCIStoreMultiple<0b01, GPRNoX0, uimm5nonzero, "qc.swmi">;1011 def QC_SETWM : QCIStoreMultiple<0b10, GPR, GPRNoX0, "qc.setwm">;1012 def QC_SETWMI : QCIStoreMultiple<0b11, GPR, uimm5nonzero, "qc.setwmi">;1013 1014 def QC_LWM : QCILoadMultiple<0b00, GPRNoX0, "qc.lwm">;1015 def QC_LWMI : QCILoadMultiple<0b01, uimm5nonzero, "qc.lwmi">;1016} // Predicates = [HasVendorXqcilsm, IsRV32]1017 1018let Predicates = [HasVendorXqcicli, IsRV32] in {1019 def QC_LIEQ : QCILICC<0b000, 0b01, GPRNoX0, "qc.lieq">;1020 def QC_LINE : QCILICC<0b001, 0b01, GPRNoX0, "qc.line">;1021 def QC_LILT : QCILICC<0b100, 0b01, GPRNoX0, "qc.lilt">;1022 def QC_LIGE : QCILICC<0b101, 0b01, GPRNoX0, "qc.lige">;1023 def QC_LILTU : QCILICC<0b110, 0b01, GPRNoX0, "qc.liltu">;1024 def QC_LIGEU : QCILICC<0b111, 0b01, GPRNoX0, "qc.ligeu">;1025 1026 def QC_LIEQI : QCILICC<0b000, 0b11, simm5, "qc.lieqi">;1027 def QC_LINEI : QCILICC<0b001, 0b11, simm5, "qc.linei">;1028 def QC_LILTI : QCILICC<0b100, 0b11, simm5, "qc.lilti">;1029 def QC_LIGEI : QCILICC<0b101, 0b11, simm5, "qc.ligei">;1030 def QC_LILTUI : QCILICC<0b110, 0b11, uimm5, "qc.liltui">;1031 def QC_LIGEUI : QCILICC<0b111, 0b11, uimm5, "qc.ligeui">;1032} // Predicates = [HasVendorXqcicli, IsRV32]1033 1034let Predicates = [HasVendorXqcicm, IsRV32] in {1035let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in1036 def QC_C_MVEQZ : RVInst16CL<0b101, 0b10, (outs GPRC:$rd_wb),1037 (ins GPRC:$rd, GPRC:$rs1),1038 "qc.c.mveqz", "$rd, $rs1"> {1039 let Constraints = "$rd = $rd_wb";1040 1041 let Inst{12-10} = 0b011;1042 let Inst{6-5} = 0b00;1043 }1044 1045 def QC_MVEQ : QCIMVCC<0b000, "qc.mveq">;1046 def QC_MVNE : QCIMVCC<0b001, "qc.mvne">;1047 def QC_MVLT : QCIMVCC<0b100, "qc.mvlt">;1048 def QC_MVGE : QCIMVCC<0b101, "qc.mvge">;1049 def QC_MVLTU : QCIMVCC<0b110, "qc.mvltu">;1050 def QC_MVGEU : QCIMVCC<0b111, "qc.mvgeu">;1051 1052 def QC_MVEQI : QCIMVCCI<0b000, "qc.mveqi", simm5>;1053 def QC_MVNEI : QCIMVCCI<0b001, "qc.mvnei", simm5>;1054 def QC_MVLTI : QCIMVCCI<0b100, "qc.mvlti", simm5>;1055 def QC_MVGEI : QCIMVCCI<0b101, "qc.mvgei", simm5>;1056 def QC_MVLTUI : QCIMVCCI<0b110, "qc.mvltui", uimm5>;1057 def QC_MVGEUI : QCIMVCCI<0b111, "qc.mvgeui", uimm5>;1058} // Predicates = [HasVendorXqcicm, IsRV32]1059 1060let Predicates = [HasVendorXqciint, IsRV32], hasSideEffects = 1 in {1061 1062let mayLoad = 0, mayStore = 0 in {1063def QC_C_DIR : RVInst16CI<0b000, 0b10, (outs GPRNoX0:$rd), (ins),1064 "qc.c.dir", "$rd"> {1065 bits<5> rd;1066 1067 let Inst{12} = 0b1;1068 let Inst{11-7} = rd;1069 let Inst{6-2} = 0b00000;1070}1071 1072def QC_SETINTI : QCIInt_IMM<0b0, "qc.setinti">;1073def QC_CLRINTI : QCIInt_IMM<0b1, "qc.clrinti">;1074 1075def QC_C_EIR : QCIRVInst16CI_RS1<0b00001, "qc.c.eir">;1076def QC_C_SETINT : QCIRVInst16CI_RS1<0b00010, "qc.c.setint">;1077def QC_C_CLRINT : QCIRVInst16CI_RS1<0b00011, "qc.c.clrint">;1078 1079def QC_C_DI : QCIRVInst16CI_NONE<0b10110, "qc.c.di">;1080def QC_C_EI : QCIRVInst16CI_NONE<0b10111, "qc.c.ei">;1081 1082let isBarrier = 1, isReturn = 1, isTerminator = 1 in {1083def QC_C_MRET : QCIRVInst16CI_NONE<0b10010, "qc.c.mret">;1084def QC_C_MNRET : QCIRVInst16CI_NONE<0b10011, "qc.c.mnret">;1085} // isBarrier = 1, isReturn = 1, isTerminator = 11086} // mayLoad = 0, mayStore = 01087 1088let mayLoad = 0, mayStore = 1,1089 Uses = [X1, X2, X5, X6, X7, X8, X10, X11, X12, X13, X14, X15, X16, X17, X28, X29, X30, X31],1090 Defs = [X2, X8] in {1091def QC_C_MIENTER : QCIRVInst16CI_NONE<0b10000, "qc.c.mienter">;1092def QC_C_MIENTER_NEST : QCIRVInst16CI_NONE<0b10001, "qc.c.mienter.nest">;1093} // mayLoad = 1, mayStore = 1, Uses = [...], Defs = [...]1094 1095let mayLoad = 1, mayStore = 0, isBarrier = 1, isReturn = 1, isTerminator = 1,1096 Uses = [X2],1097 Defs = [X1, X2, X5, X6, X7, X8, X10, X11, X12, X13, X14, X15, X16, X17, X28, X29, X30, X31] in1098def QC_C_MILEAVERET : QCIRVInst16CI_NONE<0b10100, "qc.c.mileaveret">;1099 1100} // Predicates = [HasVendorXqciint, IsRV32], hasSideEffects = 11101 1102let Predicates = [HasVendorXqciio, IsRV32] in {1103let hasSideEffects = 1, mayLoad = 0, mayStore = 0 in {1104 def QC_OUTW : RVInstI<0b100, OPC_CUSTOM_0, (outs),1105 (ins GPR:$rs2, GPR:$rs1, uimm14lsb00:$imm14),1106 "qc.outw", "$rs2, ${imm14}(${rs1})"> {1107 bits<5> rs2;1108 bits<14> imm14;1109 1110 let rd = rs2;1111 let imm12 = imm14{13-2};1112 }1113 1114 def QC_INW : RVInstI<0b101, OPC_CUSTOM_0, (outs GPRNoX0:$rd),1115 (ins GPR:$rs1, uimm14lsb00:$imm14),1116 "qc.inw", "$rd, ${imm14}(${rs1})"> {1117 bits<14> imm14;1118 1119 let imm12 = imm14{13-2};1120 }1121} // hasSideEffects = 1, mayLoad = 0, mayStore = 01122} // Predicates = [HasVendorXqciio, IsRV32]1123 1124let Predicates = [HasVendorXqcilo, IsRV32] in {1125 def QC_E_LB : QCIRVInstEILoad<0b101, 0b00, "qc.e.lb">;1126 def QC_E_LBU : QCIRVInstEILoad<0b101, 0b01, "qc.e.lbu">;1127 def QC_E_LH : QCIRVInstEILoad<0b101, 0b10, "qc.e.lh">;1128 def QC_E_LHU : QCIRVInstEILoad<0b101, 0b11, "qc.e.lhu">;1129 def QC_E_LW : QCIRVInstEILoad<0b110, 0b00, "qc.e.lw">;1130 1131 def QC_E_SB : QCIRVInstESStore<0b110, 0b01, "qc.e.sb">;1132 def QC_E_SH : QCIRVInstESStore<0b110, 0b10, "qc.e.sh">;1133 def QC_E_SW : QCIRVInstESStore<0b110, 0b11, "qc.e.sw">;1134} // Predicates = [HasVendorXqcilo, IsRV32]1135 1136let Predicates = [HasVendorXqcilb, IsRV32] in {1137 let isCall = 1, Defs = [X1] in1138 def QC_E_JAL : QCIRVInst48EJ<0b01, "qc.e.jal">;1139 let isBranch = 1, isTerminator = 1, isBarrier = 1 in1140 def QC_E_J : QCIRVInst48EJ<0b00, "qc.e.j">;1141} // Predicates = [HasVendorXqcilb, IsRV32]1142 1143let Predicates = [HasVendorXqcili, IsRV32] in {1144let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in {1145 def QC_LI : RVInstU<OPC_OP_IMM_32, (outs GPRNoX0:$rd), (ins simm20_li:$imm20),1146 "qc.li", "$rd, $imm20"> {1147 let Inst{31} = imm20{19};1148 let Inst{30-16} = imm20{14-0};1149 let Inst{15-12} = imm20{18-15};1150 }1151 1152 def QC_E_LI : RVInst48<(outs GPRNoX0:$rd), (ins bare_simm32:$imm),1153 "qc.e.li", "$rd, $imm", [], InstFormatQC_EAI> {1154 bits<5> rd;1155 bits<32> imm;1156 1157 let Inst{47-16} = imm;1158 let Inst{15-12} = 0b0000;1159 let Inst{11-7} = rd;1160 let Inst{6-0} = 0b0011111;1161 }1162} // hasSideEffects = 0, mayLoad = 0, mayStore = 01163} // Predicates = [HasVendorXqcili, IsRV32]1164 1165let Predicates = [HasVendorXqcilia, IsRV32] in {1166let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in {1167 def QC_E_XORAI : QCIRVInstEAI<0b001, 0b0, "qc.e.xorai">;1168 def QC_E_ORAI : QCIRVInstEAI<0b001, 0b1, "qc.e.orai" >;1169 def QC_E_ADDAI : QCIRVInstEAI<0b010, 0b0, "qc.e.addai">;1170 def QC_E_ANDAI : QCIRVInstEAI<0b010, 0b1, "qc.e.andai">;1171 1172 def QC_E_XORI : QCIRVInstEI<0b011, 0b00, "qc.e.xori">;1173 def QC_E_ORI : QCIRVInstEI<0b011, 0b01, "qc.e.ori" >;1174 def QC_E_ADDI : QCIRVInstEI<0b011, 0b10, "qc.e.addi">;1175 def QC_E_ANDI : QCIRVInstEI<0b011, 0b11, "qc.e.andi">;1176} // hasSideEffects = 0, mayLoad = 0, mayStore = 01177} // Predicates = [HasVendorXqcilia, IsRV32]1178 1179let Predicates = [HasVendorXqcisync, IsRV32] in {1180 def QC_SYNC : QCISync_UIMM5<0b0001, "qc.sync">;1181 def QC_SYNCR : QCISync_UIMM5<0b0010, "qc.syncr">;1182 def QC_SYNCWF : QCISync_UIMM5<0b0100, "qc.syncwf">;1183 def QC_SYNCWL : QCISync_UIMM5<0b1000, "qc.syncwl">;1184 1185 def QC_C_SYNC : QCIRVInst16CBSYNC<0b000, "qc.c.sync">;1186 def QC_C_SYNCR : QCIRVInst16CBSYNC<0b001, "qc.c.syncr">;1187 def QC_C_SYNCWF : QCIRVInst16CBSYNC<0b100, "qc.c.syncwf">;1188 def QC_C_SYNCWL : QCIRVInst16CBSYNC<0b101, "qc.c.syncwl">;1189 1190 // qc.c.delay implemented as an alias, below1191} // Predicates = [HasVendorXqcisync, IsRV32]1192 1193let Predicates = [HasVendorXqcisim, IsRV32] in {1194let mayLoad = 0, mayStore = 0, hasSideEffects = 1 in {1195 def QC_PPUTCI : RVInstI<0b010, OPC_OP_IMM, (outs), (ins uimm8:$imm8),1196 "qc.pputci", "$imm8"> {1197 bits<8> imm8;1198 1199 let rs1 = 0;1200 let rd = 0;1201 let imm12 = {0b0100, imm8};1202 }1203 1204 // The other instructions are all implemented as aliases, below1205} // mayLoad = 0, mayStore = 0, hasSideEffects = 11206} // Predicates = [HasVendorXqcisim, IsRV32]1207 1208} // DecoderNamespace = "Xqci"1209 1210//===----------------------------------------------------------------------===//1211// Aliases1212//===----------------------------------------------------------------------===//1213 1214let Predicates = [HasVendorXqciio, IsRV32] in {1215let EmitPriority = 0 in {1216 def : InstAlias<"qc.outw $rs2, (${rs1})",1217 (QC_OUTW GPR:$rs2, GPR:$rs1, 0)>;1218 def : InstAlias<"qc.inw $rd, (${rs1})",1219 (QC_INW GPRNoX0:$rd, GPR:$rs1, 0)>;1220} // EmitPriority = 01221} // Predicates = [HasVendorXqciio, IsRV32]1222 1223let Predicates = [HasVendorXqcilsm, IsRV32] in {1224let EmitPriority = 0 in {1225 def : InstAlias<"qc.swm $rs3, $rs2, (${rs1})",1226 (QC_SWM GPRNoX0:$rs3, GPR:$rs1, GPRNoX0:$rs2, 0)>;1227 def : InstAlias<"qc.swmi $rs3, $length, (${rs1})",1228 (QC_SWMI GPRNoX0:$rs3, GPR:$rs1, uimm5nonzero:$length, 0)>;1229 def : InstAlias<"qc.setwm $rs3, $rs2, (${rs1})",1230 (QC_SETWM GPR:$rs3, GPR:$rs1, GPRNoX0:$rs2, 0)>;1231 def : InstAlias<"qc.setwmi $rs3, $length, (${rs1})",1232 (QC_SETWMI GPR:$rs3, GPR:$rs1, uimm5nonzero:$length, 0)>;1233 def : InstAlias<"qc.lwm $rd, $rs2, (${rs1})",1234 (QC_LWM GPRNoX0:$rd, GPR:$rs1, GPRNoX0:$rs2, 0)>;1235 def : InstAlias<"qc.lwmi $rd, $length, (${rs1})",1236 (QC_LWMI GPRNoX0:$rd, GPR:$rs1, uimm5nonzero:$length, 0)>;1237} // EmitPriority = 01238} // Predicates = [HasVendorXqcilsm, IsRV32]1239 1240let Predicates = [HasVendorXqcilo, IsRV32] in {1241let EmitPriority = 0 in {1242 def : InstAlias<"qc.e.lb $rd, (${rs1})",1243 (QC_E_LB GPR:$rd, GPR:$rs1, 0)>;1244 def : InstAlias<"qc.e.lbu $rd, (${rs1})",1245 (QC_E_LBU GPR:$rd, GPR:$rs1, 0)>;1246 def : InstAlias<"qc.e.lh $rd, (${rs1})",1247 (QC_E_LH GPR:$rd, GPR:$rs1, 0)>;1248 def : InstAlias<"qc.e.lhu $rd, (${rs1})",1249 (QC_E_LHU GPR:$rd, GPR:$rs1, 0)>;1250 def : InstAlias<"qc.e.lw $rd, (${rs1})",1251 (QC_E_LW GPR:$rd, GPR:$rs1, 0)>;1252 def : InstAlias<"qc.e.sb $rs2, (${rs1})",1253 (QC_E_SB GPR:$rs2, GPR:$rs1, 0)>;1254 def : InstAlias<"qc.e.sh $rs2, (${rs1})",1255 (QC_E_SH GPR:$rs2, GPR:$rs1, 0)>;1256 def : InstAlias<"qc.e.sw $rs2, (${rs1})",1257 (QC_E_SW GPR:$rs2, GPR:$rs1, 0)>;1258} // EmitPriority = 01259} // Predicates = [HasVendorXqcilo, IsRV32]1260 1261let Predicates = [HasVendorXqcisim, IsRV32] in {1262let EmitPriority = 1 in {1263 def : InstAlias<"qc.c.ptrace", (C_SLLI X0, 0)>;1264 1265 def : InstAlias<"qc.psyscalli $imm", (SLTI X0, X0, uimm10:$imm)>;1266 def : InstAlias<"qc.pcoredump", (SLTI X0, X0, 1536)>;1267 def : InstAlias<"qc.ppregs", (SLTI X0, X0, 1792)>;1268 def : InstAlias<"qc.ppreg $rs1", (SLTI X0, GPR:$rs1, -2048)>;1269 def : InstAlias<"qc.pputc $rs1", (SLTI X0, GPR:$rs1, -1792)>;1270 def : InstAlias<"qc.pputs $rs1", (SLTI X0, GPR:$rs1, -1536)>;1271 def : InstAlias<"qc.pexit $rs1", (SLTI X0, GPR:$rs1, -1280)>;1272 def : InstAlias<"qc.psyscall $rs1", (SLTI X0, GPR:$rs1, -1024)>;1273} // EmitPriority = 11274} // Predicates = [HasVendorXqcisim, IsRV32]1275 1276let Predicates = [HasVendorXqcisync, IsRV32] in {1277let EmitPriority = 1 in {1278 def : InstAlias<"qc.c.delay $imm", (C_SLLI X0, uimm5nonzero:$imm)>;1279}1280} // Predicates = [HasVendorXqcisync, IsRV32]1281 1282//===----------------------------------------------------------------------===//1283// Pseudo-instructions1284//===----------------------------------------------------------------------===//1285 1286class LongBcciPseudo<DAGOperand InTyImm, int size>1287 : Pseudo<(outs), (ins GPR:$rs1, InTyImm:$imm, simm21_lsb0_jal:$imm20), []>1288{1289 let Size = size;1290 let isBarrier = 1;1291 let isBranch = 1;1292 let hasSideEffects = 0;1293 let mayStore = 0;1294 let mayLoad = 0;1295 let isAsmParserOnly = 1;1296 let hasNoSchedulingInfo = 1;1297}1298 1299// This will be expanded into either:1300// QC.BXXX(4 bytes) + JAL(4 bytes)1301// or1302// QC.E.BXXX(6 bytes) + JAL(4 bytes)1303def PseudoLongQC_BEQI : LongBcciPseudo<simm5nonzero, 8>;1304def PseudoLongQC_BNEI : LongBcciPseudo<simm5nonzero, 8>;1305def PseudoLongQC_BLTI : LongBcciPseudo<simm5nonzero, 8>;1306def PseudoLongQC_BGEI : LongBcciPseudo<simm5nonzero, 8>;1307def PseudoLongQC_BLTUI : LongBcciPseudo<uimm5nonzero, 8>;1308def PseudoLongQC_BGEUI : LongBcciPseudo<uimm5nonzero, 8>;1309def PseudoLongQC_E_BEQI : LongBcciPseudo<simm16nonzero, 10>;1310def PseudoLongQC_E_BNEI : LongBcciPseudo<simm16nonzero, 10>;1311def PseudoLongQC_E_BLTI : LongBcciPseudo<simm16nonzero, 10>;1312def PseudoLongQC_E_BGEI : LongBcciPseudo<simm16nonzero, 10>;1313def PseudoLongQC_E_BLTUI : LongBcciPseudo<uimm16nonzero, 10>;1314def PseudoLongQC_E_BGEUI : LongBcciPseudo<uimm16nonzero, 10>;1315 1316// Load/Store pseudos with QC.E.* Mnemonics. These expand to an AUIPC +1317// (Standard) Load/Store sequence, as this can materialize all 32-bit addresses,1318// and is shorter than e.g. an AUIPC + Xqcilo Load/Store sequence. These1319// sequences can be turned back into a single Xqcilo instruction using linker1320// relaxation.1321let Predicates = [HasVendorXqcilo, IsRV32] in {1322def PseudoQC_E_LB : PseudoLoad<"qc.e.lb">;1323def PseudoQC_E_LBU : PseudoLoad<"qc.e.lbu">;1324def PseudoQC_E_LH : PseudoLoad<"qc.e.lh">;1325def PseudoQC_E_LHU : PseudoLoad<"qc.e.lhu">;1326def PseudoQC_E_LW : PseudoLoad<"qc.e.lw">;1327 1328def PseudoQC_E_SB : PseudoStore<"qc.e.sb">;1329def PseudoQC_E_SH : PseudoStore<"qc.e.sh">;1330def PseudoQC_E_SW : PseudoStore<"qc.e.sw">;1331} // Predicates = [HasVendorXqcilo, IsRV32]1332 1333let Predicates = [HasShortForwardBranchIALU] in {1334def PseudoCCQC_LI : SFBQC_LI;1335def PseudoCCQC_E_LI : SFBQC_E_LI;1336}1337 1338//===----------------------------------------------------------------------===//1339// Code Gen Patterns1340//===----------------------------------------------------------------------===//1341 1342/// Generic pattern classes1343 1344class PatGprNoX0Simm26NoSimm12<SDPatternOperator OpNode, RVInst48 Inst>1345 : Pat<(i32 (OpNode (i32 GPRNoX0:$rs1), simm26_nosimm12:$imm)),1346 (Inst GPRNoX0:$rs1, simm26_nosimm12:$imm)>;1347 1348class PatGprNoX0Simm32NoSimm26<SDPatternOperator OpNode, RVInst48 Inst>1349 : Pat<(i32 (OpNode (i32 GPRNoX0:$rs1), simm32_nosimm26:$imm)),1350 (Inst GPRNoX0:$rs1, simm32_nosimm26:$imm)>;1351 1352class PatGprNoX0GprNoX0<SDPatternOperator OpNode, RVInstR Inst>1353 : Pat<(i32 (OpNode (i32 GPRNoX0:$rs1), (i32 GPRNoX0:$rs2))),1354 (Inst GPRNoX0:$rs1, GPRNoX0:$rs2)>;1355 1356class QC48LdPat<PatFrag LoadOp, RVInst48 Inst>1357 : Pat<(i32 (LoadOp (AddLike (i32 GPR:$rs1), simm26_nosimm12:$imm26))),1358 (Inst GPR:$rs1, simm26_nosimm12:$imm26)>;1359 1360class QC48StPat<PatFrag StoreOp, RVInst48 Inst>1361 : Pat<(StoreOp (i32 GPR:$rs2), (AddLike (i32 GPR:$rs1), simm26_nosimm12:$imm26)),1362 (Inst GPR:$rs2, GPR:$rs1, simm26_nosimm12:$imm26)>;1363 1364def AddrRegRegScale7 : AddrRegRegScale<7>;1365 1366class QCScaledLdPat<PatFrag LoadOp, RVInst Inst>1367 : Pat<(i32 (LoadOp (AddrRegRegScale7 (i32 GPRMem:$rs1), (i32 GPRNoX0:$rs2), uimm3:$shamt))),1368 (Inst GPRMem:$rs1, GPRNoX0:$rs2, uimm3:$shamt)>;1369 1370class QCScaledStPat<PatFrag StoreOp, RVInst Inst>1371 : Pat<(StoreOp (i32 GPR:$rd), (AddrRegRegScale7 (i32 GPRMem:$rs1), (i32 GPRNoX0:$rs2), uimm3:$shamt)),1372 (Inst GPR:$rd, GPRMem:$rs1, GPRNoX0:$rs2, uimm3:$shamt)>;1373 1374class QCIMVCCPat<CondCode Cond, QCIMVCC Inst>1375 : Pat<(i32 (riscv_selectcc (i32 GPRNoX0:$rs1), (i32 GPRNoX0:$rs2), Cond, (i32 GPRNoX0:$rs3), (i32 GPRNoX0:$rd))),1376 (Inst GPRNoX0:$rd, GPRNoX0:$rs1, GPRNoX0:$rs2, GPRNoX0:$rs3)>;1377 1378class QCIMVCCIPat<CondCode Cond, QCIMVCCI Inst, DAGOperand InTyImm>1379 : Pat<(i32 (riscv_selectcc (i32 GPRNoX0:$rs1), InTyImm:$imm, Cond, (i32 GPRNoX0:$rs3), (i32 GPRNoX0:$rd))),1380 (Inst GPRNoX0:$rd, GPRNoX0:$rs1, InTyImm:$imm, GPRNoX0:$rs3)>;1381 1382class QCIMVCCIZeroPat<CondCode Cond, QCIMVCCI Inst>1383 : Pat<(i32 (riscv_selectcc (i32 GPRNoX0:$rs1), (i32 0), Cond, (i32 GPRNoX0:$rs3), (i32 GPRNoX0:$rd))),1384 (Inst GPRNoX0:$rd, GPRNoX0:$rs1, 0, GPRNoX0:$rs3)>;1385 1386class QCISELECTCCIPat<CondCode Cond, QCISELECTCCI Inst>1387 : Pat<(i32 (riscv_selectcc (i32 GPRNoX0:$rd), simm5:$imm, Cond, (i32 GPRNoX0:$rs2), (i32 GPRNoX0:$rs3))),1388 (Inst GPRNoX0:$rd, simm5:$imm, GPRNoX0:$rs2, GPRNoX0:$rs3)>;1389 1390class QCISELECTICCIPat<CondCode Cond, QCISELECTICCI Inst>1391 : Pat<(i32 (riscv_selectcc (i32 GPRNoX0:$rd), simm5:$imm, Cond, (i32 GPRNoX0:$rs2), simm5:$simm2)),1392 (Inst GPRNoX0:$rd, simm5:$imm, GPRNoX0:$rs2, simm5:$simm2)>;1393 1394class QCISELECTICCIPatInv<CondCode Cond, QCISELECTICCI Inst>1395 : Pat<(i32 (riscv_selectcc (i32 GPRNoX0:$rd), simm5:$imm, Cond, simm5:$simm2, (i32 GPRNoX0:$rs2))),1396 (Inst GPRNoX0:$rd, simm5:$imm, GPRNoX0:$rs2, simm5:$simm2)>;1397 1398class QCISELECTICCPat<CondCode Cond, QCISELECTICC Inst>1399 : Pat<(i32 (riscv_selectcc (i32 GPRNoX0:$rd), (i32 GPRNoX0:$rs1), Cond, (i32 GPRNoX0:$rs2), simm5:$simm2)),1400 (Inst GPRNoX0:$rd, GPRNoX0:$rs1, GPRNoX0:$rs2, simm5:$simm2)>;1401 1402class QCISELECTICCPatInv<CondCode Cond, QCISELECTICC Inst>1403 : Pat<(i32 (riscv_selectcc (i32 GPRNoX0:$rd), (i32 GPRNoX0:$rs1), Cond, simm5:$simm2, (i32 GPRNoX0:$rs2))),1404 (Inst GPRNoX0:$rd, GPRNoX0:$rs1, GPRNoX0:$rs2, simm5:$simm2)>;1405 1406class QCISELECTIICCPat<CondCode Cond, QCISELECTIICC Inst>1407 : Pat<(i32 (riscv_selectcc (i32 GPRNoX0:$rd), (i32 GPRNoX0:$rs1), Cond, simm5:$simm1, simm5:$simm2)),1408 (Inst GPRNoX0:$rd, GPRNoX0:$rs1, simm5:$simm1, simm5:$simm2)>;1409 1410class QCILICCPat<CondCode Cond, QCILICC Inst>1411 : Pat<(i32 (riscv_selectcc (i32 GPRNoX0:$rs1), (i32 GPRNoX0:$rs2), Cond, simm5:$simm, (i32 GPRNoX0:$rd))),1412 (Inst GPRNoX0:$rd, GPRNoX0:$rs1, GPRNoX0:$rs2, simm5:$simm)>;1413 1414class QCILICCPatInv<CondCode Cond, QCILICC Inst>1415 : Pat<(i32 (riscv_selectcc (i32 GPRNoX0:$rs1), (i32 GPRNoX0:$rs2), Cond, (i32 GPRNoX0:$rd), simm5:$simm)),1416 (Inst GPRNoX0:$rd, GPRNoX0:$rs1, GPRNoX0:$rs2, simm5:$simm)>;1417 1418class QCILICCIPat<CondCode Cond, QCILICC Inst, DAGOperand InTyImm>1419 : Pat<(i32 (riscv_selectcc (i32 GPRNoX0:$rs1), InTyImm:$imm, Cond, simm5:$simm, (i32 GPRNoX0:$rd))),1420 (Inst GPRNoX0:$rd, GPRNoX0:$rs1, InTyImm:$imm, simm5:$simm)>;1421 1422class QCILICCIPatInv<CondCode Cond, QCILICC Inst, DAGOperand InTyImm>1423 : Pat<(i32 (riscv_selectcc (i32 GPRNoX0:$rs1), InTyImm:$imm, Cond, (i32 GPRNoX0:$rd), simm5:$simm)),1424 (Inst GPRNoX0:$rd, GPRNoX0:$rs1, InTyImm:$imm, simm5:$simm)>;1425 1426// Match `riscv_brcc` and lower to the appropriate XQCIBI branch instruction.1427class BcciPat<CondCode Cond, QCIBranchInst_rii Inst, DAGOperand InTyImm>1428 : Pat<(riscv_brcc (i32 GPRNoX0:$rs1), InTyImm:$rs2, Cond, bb:$imm12),1429 (Inst GPRNoX0:$rs1, InTyImm:$rs2, bare_simm13_lsb0_bb:$imm12)>;1430 1431class Bcci48Pat<CondCode Cond, QCIBranchInst48_rii Inst, DAGOperand InTyImm>1432 : Pat<(riscv_brcc (i32 GPRNoX0:$rs1), InTyImm:$rs2, Cond, bb:$imm12),1433 (Inst GPRNoX0:$rs1, InTyImm:$rs2, bare_simm13_lsb0_bb:$imm12)>;1434 1435defm CC_SImm5NonZero_QC : SelectCC_GPR_riirr<GPRNoX0, simm5nonzero>;1436defm CC_UImm5NonZero_QC : SelectCC_GPR_riirr<GPRNoX0, uimm5nonzero>;1437defm CC_SImm16NonZero_QC : SelectCC_GPR_riirr<GPRNoX0, simm16nonzero>;1438defm CC_UImm16NonZero_QC : SelectCC_GPR_riirr<GPRNoX0, uimm16nonzero>;1439 1440class SelectQCbi<CondCode Cond, DAGOperand InTyImm, Pseudo OpNode >1441 : Pat<(riscv_selectcc_frag:$cc (i32 GPRNoX0:$lhs), InTyImm:$Constant, Cond,1442 (i32 GPRNoX0:$truev), GPRNoX0:$falsev),1443 (OpNode GPRNoX0:$lhs, InTyImm:$Constant,1444 (IntCCtoRISCVCC $cc), GPRNoX0:$truev, GPRNoX0:$falsev)>;1445 1446let Predicates = [HasVendorXqciac, IsRV32] in {1447def : Pat<(i32 (add GPRNoX0:$rd, (mul GPRNoX0:$rs1, simm12_lo:$imm12))),1448 (QC_MULIADD GPRNoX0:$rd, GPRNoX0:$rs1, simm12_lo:$imm12)>;1449def : Pat<(i32 (add_like_non_imm12 (shl GPRNoX0:$rs1, (i32 uimm5gt3:$imm)), GPRNoX0:$rs2)),1450 (QC_SHLADD GPRNoX0:$rs1, GPRNoX0:$rs2, uimm5gt3:$imm)>;1451def : Pat<(i32 (riscv_shl_add GPRNoX0:$rs1, (i32 tuimm5gt3:$imm), GPRNoX0:$rs2)),1452 (QC_SHLADD GPRNoX0:$rs1, GPRNoX0:$rs2, tuimm5gt3:$imm)>;1453} // Predicates = [HasVendorXqciac, IsRV32]1454 1455/// Simple arithmetic operations1456 1457let Predicates = [HasVendorXqcilia, IsRV32] in {1458def : PatGprNoX0Simm32NoSimm26<add, QC_E_ADDAI>;1459def : PatGprNoX0Simm32NoSimm26<and, QC_E_ANDAI>;1460def : PatGprNoX0Simm32NoSimm26<or, QC_E_ORAI>;1461def : PatGprNoX0Simm32NoSimm26<xor, QC_E_XORAI>;1462 1463def : PatGprNoX0Simm26NoSimm12<add, QC_E_ADDI>;1464def : PatGprNoX0Simm26NoSimm12<and, QC_E_ANDI>;1465def : PatGprNoX0Simm26NoSimm12<or, QC_E_ORI>;1466def : PatGprNoX0Simm26NoSimm12<xor, QC_E_XORI>;1467} // Predicates = [HasVendorXqcilia, IsRV32]1468 1469/// Load/Store operations1470 1471let Predicates = [HasVendorXqcilo, IsRV32], AddedComplexity = 2 in {1472 def : QC48LdPat<sextloadi8, QC_E_LB>;1473 def : QC48LdPat<extloadi8, QC_E_LBU>; // Prefer unsigned due to no c.lb in Zcb.1474 def : QC48LdPat<sextloadi16, QC_E_LH>;1475 def : QC48LdPat<extloadi16, QC_E_LH>;1476 def : QC48LdPat<load, QC_E_LW>;1477 def : QC48LdPat<zextloadi8, QC_E_LBU>;1478 def : QC48LdPat<zextloadi16, QC_E_LHU>;1479 1480 def : QC48StPat<truncstorei8, QC_E_SB>;1481 def : QC48StPat<truncstorei16, QC_E_SH>;1482 def : QC48StPat<store, QC_E_SW>;1483} // Predicates = [HasVendorXqcilo, IsRV32], AddedComplexity = 21484 1485 1486let Predicates = [HasVendorXqcisls, IsRV32], AddedComplexity = 1 in {1487 def : QCScaledLdPat<sextloadi8, QC_LRB>;1488 def : QCScaledLdPat<extloadi8, QC_LRBU>;1489 def : QCScaledLdPat<sextloadi16, QC_LRH>;1490 def : QCScaledLdPat<extloadi16, QC_LRH>;1491 def : QCScaledLdPat<load, QC_LRW>;1492 def : QCScaledLdPat<zextloadi8, QC_LRBU>;1493 def : QCScaledLdPat<zextloadi16, QC_LRHU>;1494 1495 def : QCScaledStPat<truncstorei8, QC_SRB>;1496 def : QCScaledStPat<truncstorei16, QC_SRH>;1497 def : QCScaledStPat<store, QC_SRW>;1498} // Predicates = [HasVendorXqcisls, IsRV32], AddedComplexity = 11499 1500let Predicates = [HasVendorXqcia, IsRV32] in {1501def : PatGprNoX0GprNoX0<saddsat, QC_ADDSAT>;1502def : PatGprNoX0GprNoX0<uaddsat, QC_ADDUSAT>;1503def : PatGprNoX0GprNoX0<ssubsat, QC_SUBSAT>;1504def : PatGprNoX0GprNoX0<usubsat, QC_SUBUSAT>;1505def : PatGprNoX0GprNoX0<ushlsat, QC_SHLUSAT>;1506def : PatGprNoX0GprNoX0<sshlsat, QC_SHLSAT>;1507} // Predicates = [HasVendorXqcia, IsRV32]1508 1509/// Branches1510 1511let Predicates = [HasVendorXqcibi, IsRV32] in {1512def : BcciPat<SETEQ, QC_BEQI, simm5nonzero>;1513def : BcciPat<SETNE, QC_BNEI, simm5nonzero>;1514def : BcciPat<SETLT, QC_BLTI, simm5nonzero>;1515def : BcciPat<SETGE, QC_BGEI, simm5nonzero>;1516def : BcciPat<SETULT, QC_BLTUI, uimm5nonzero>;1517def : BcciPat<SETUGE, QC_BGEUI, uimm5nonzero>;1518 1519def : Bcci48Pat<SETEQ, QC_E_BEQI, simm16nonzero>;1520def : Bcci48Pat<SETNE, QC_E_BNEI, simm16nonzero>;1521def : Bcci48Pat<SETLT, QC_E_BLTI, simm16nonzero>;1522def : Bcci48Pat<SETGE, QC_E_BGEI, simm16nonzero>;1523def : Bcci48Pat<SETULT, QC_E_BLTUI, uimm16nonzero>;1524def : Bcci48Pat<SETUGE, QC_E_BGEUI, uimm16nonzero>;1525 1526def : SelectQCbi<SETEQ, simm5nonzero, Select_GPRNoX0_Using_CC_SImm5NonZero_QC>;1527def : SelectQCbi<SETNE, simm5nonzero, Select_GPRNoX0_Using_CC_SImm5NonZero_QC>;1528def : SelectQCbi<SETLT, simm5nonzero, Select_GPRNoX0_Using_CC_SImm5NonZero_QC>;1529def : SelectQCbi<SETGE, simm5nonzero, Select_GPRNoX0_Using_CC_SImm5NonZero_QC>;1530def : SelectQCbi<SETULT, uimm5nonzero, Select_GPRNoX0_Using_CC_UImm5NonZero_QC>;1531def : SelectQCbi<SETUGE, uimm5nonzero, Select_GPRNoX0_Using_CC_UImm5NonZero_QC>;1532 1533def : SelectQCbi<SETEQ, simm16nonzero, Select_GPRNoX0_Using_CC_SImm16NonZero_QC>;1534def : SelectQCbi<SETNE, simm16nonzero, Select_GPRNoX0_Using_CC_SImm16NonZero_QC>;1535def : SelectQCbi<SETLT, simm16nonzero, Select_GPRNoX0_Using_CC_SImm16NonZero_QC>;1536def : SelectQCbi<SETGE, simm16nonzero, Select_GPRNoX0_Using_CC_SImm16NonZero_QC>;1537def : SelectQCbi<SETULT, uimm16nonzero, Select_GPRNoX0_Using_CC_UImm16NonZero_QC>;1538def : SelectQCbi<SETUGE, uimm16nonzero, Select_GPRNoX0_Using_CC_UImm16NonZero_QC>;1539} // let Predicates = [HasVendorXqcibi, IsRV32]1540 1541let Predicates = [HasVendorXqcibm, IsRV32] in {1542def : Pat<(sext_inreg (i32 GPR:$rs1), i1), (QC_EXT GPR:$rs1, 1, 0)>;1543 1544// Prefer qc.extu to andi for the following cases since the former can be compressed1545def : Pat<(i32 (and GPRNoX0:$rs, 63)), (QC_EXTU GPRNoX0:$rs, 6, 0)>;1546def : Pat<(i32 (and GPRNoX0:$rs, 127)), (QC_EXTU GPRNoX0:$rs, 7, 0)>;1547def : Pat<(i32 (and GPRNoX0:$rs, 255)), (QC_EXTU GPRNoX0:$rs, 8, 0)>;1548def : Pat<(i32 (and GPRNoX0:$rs, 511)), (QC_EXTU GPRNoX0:$rs, 9, 0)>;1549def : Pat<(i32 (and GPRNoX0:$rs, 1023)), (QC_EXTU GPRNoX0:$rs, 10, 0)>;1550def : Pat<(i32 (and GPRNoX0:$rs, 2047)), (QC_EXTU GPRNoX0:$rs, 11, 0)>;1551 1552def : Pat<(i32 (bitreverse GPRNoX0:$rs1)), (QC_BREV32 GPRNoX0:$rs1)>;1553 1554def : Pat<(qc_insb GPRNoX0:$rd, simm5:$imm5, uimm5_plus1:$width, uimm5:$shamt),1555 (QC_INSBI GPRNoX0:$rd, simm5:$imm5, uimm5_plus1:$width, uimm5:$shamt)>;1556def : Pat<(qc_insb GPRNoX0:$rd, GPR:$rs1, uimm5_plus1:$width, uimm5:$shamt),1557 (QC_INSB GPRNoX0:$rd, GPR:$rs1, uimm5_plus1:$width, uimm5:$shamt)>;1558} // Predicates = [HasVendorXqcibm, IsRV32]1559 1560// If Zbb is enabled sext.b/h is preferred since they are compressible1561let Predicates = [HasVendorXqcibm, NoStdExtZbb, IsRV32] in {1562def : Pat<(sext_inreg (i32 GPR:$rs1), i16), (QC_EXT GPR:$rs1, 16, 0)>;1563def : Pat<(sext_inreg (i32 GPR:$rs1), i8), (QC_EXT GPR:$rs1, 8, 0)>;1564} // Predicates = [HasVendorXqcibm, NoStdExtZbb, IsRV32]1565 1566let Predicates = [HasVendorXqcibm, HasStdExtZbb, IsRV32] in {1567def: Pat<(i32 (cttz (not (i32 GPR:$rs1)))), (QC_CTO GPR:$rs1)>;1568def: Pat<(i32 (ctlz (not (i32 GPR:$rs1)))), (QC_CLO GPR:$rs1)>;1569} // Predicates = [HasVendorXqcibm, HasStdExtZbb, IsRV32]1570 1571let Predicates = [HasVendorXqciint, IsRV32] in1572def : Pat<(riscv_mileaveret_glue), (QC_C_MILEAVERET)>;1573 1574let Predicates = [HasVendorXqcicm, NoShortForwardBranch, IsRV32] in {1575def : QCIMVCCPat<SETEQ, QC_MVEQ>;1576def : QCIMVCCPat<SETNE, QC_MVNE>;1577def : QCIMVCCPat<SETLT, QC_MVLT>;1578def : QCIMVCCPat<SETULT, QC_MVLTU>;1579def : QCIMVCCPat<SETGE, QC_MVGE>;1580def : QCIMVCCPat<SETUGE, QC_MVGEU>;1581 1582// These exist to prioritise over the `Select_GPR_Using_CC_GPR` pattern for X0.1583def : QCIMVCCIZeroPat<SETEQ, QC_MVEQI>;1584def : QCIMVCCIZeroPat<SETNE, QC_MVNEI>;1585def : QCIMVCCIZeroPat<SETLT, QC_MVLTI>;1586def : QCIMVCCIZeroPat<SETULT, QC_MVLTUI>;1587def : QCIMVCCIZeroPat<SETGE, QC_MVGEI>;1588def : QCIMVCCIZeroPat<SETUGE, QC_MVGEUI>;1589}1590 1591let Predicates = [HasVendorXqcicm, IsRV32] in {1592// These all use *imm5nonzero because we want to use PseudoCCMOVGPR with X0 when SFB is enabled.1593// When SFB is not enabled, the `QCIMVCCIZeroPat`s above will be used if RHS=0.1594def : QCIMVCCIPat<SETEQ, QC_MVEQI, simm5nonzero>;1595def : QCIMVCCIPat<SETNE, QC_MVNEI, simm5nonzero>;1596def : QCIMVCCIPat<SETLT, QC_MVLTI, simm5nonzero>;1597def : QCIMVCCIPat<SETULT, QC_MVLTUI, uimm5nonzero>;1598def : QCIMVCCIPat<SETGE, QC_MVGEI, simm5nonzero>;1599def : QCIMVCCIPat<SETUGE, QC_MVGEUI, uimm5nonzero>;1600}1601 1602let Predicates = [HasVendorXqcicli, IsRV32] in {1603def : QCILICCPat<SETLT, QC_LILT>;1604def : QCILICCPat<SETGE, QC_LIGE>;1605def : QCILICCPat<SETULT, QC_LILTU>;1606def : QCILICCPat<SETUGE, QC_LIGEU>;1607 1608def : QCILICCIPat<SETLT, QC_LILTI, simm5>;1609def : QCILICCIPat<SETGE, QC_LIGEI, simm5>;1610def : QCILICCIPat<SETULT, QC_LILTUI, uimm5>;1611def : QCILICCIPat<SETUGE, QC_LIGEUI, uimm5>;1612 1613def : QCILICCPatInv<SETGE, QC_LILT>;1614def : QCILICCPatInv<SETLT, QC_LIGE>;1615def : QCILICCPatInv<SETUGE, QC_LILTU>;1616def : QCILICCPatInv<SETULT, QC_LIGEU>;1617 1618def : QCILICCIPatInv<SETGE, QC_LILTI, simm5>;1619def : QCILICCIPatInv<SETLT, QC_LIGEI, simm5>;1620def : QCILICCIPatInv<SETUGE, QC_LILTUI, uimm5>;1621def : QCILICCIPatInv<SETULT, QC_LIGEUI, uimm5>;1622} // Predicates = [HasVendorXqcicli, IsRV32]1623 1624// Prioritize Xqcics over these patterns.1625let Predicates = [HasVendorXqcicli, NoVendorXqcics, IsRV32] in {1626def : QCILICCPat<SETEQ, QC_LIEQ>;1627def : QCILICCPat<SETNE, QC_LINE>;1628 1629def : QCILICCIPat<SETEQ, QC_LIEQI, simm5>;1630def : QCILICCIPat<SETNE, QC_LINEI, simm5>;1631 1632def : QCILICCPatInv<SETNE, QC_LIEQ>;1633def : QCILICCPatInv<SETEQ, QC_LINE>;1634 1635def : QCILICCIPatInv<SETNE, QC_LIEQI, simm5>;1636def : QCILICCIPatInv<SETEQ, QC_LINEI, simm5>;1637} // Predicates = [HasVendorXqcicli, NoVendorXqcics, IsRV32]1638 1639let Predicates = [HasVendorXqcics, IsRV32] in {1640// (SELECT X, Y, Z) is canonicalised to `(riscv_selectcc x, 0, NE, y, z)`.1641// These exist to prioritise over the `Select_GPR_Using_CC_GPR` pattern.1642def : Pat<(i32 (riscv_selectcc (i32 GPRNoX0:$rd), (i32 0), SETNE, (i32 GPRNoX0:$rs2), simm5:$simm2)),1643 (QC_SELECTINEI GPRNoX0:$rd, (i32 0), GPRNoX0:$rs2, simm5:$simm2)>;1644def : Pat<(i32 (riscv_selectcc (i32 GPRNoX0:$rd), (i32 0), SETNE, simm5:$simm2, (i32 GPRNoX0:$rs2))),1645 (QC_SELECTIEQI GPRNoX0:$rd, (i32 0), GPRNoX0:$rs2, simm5:$simm2)>;1646 1647def : QCISELECTICCIPat<SETEQ, QC_SELECTIEQI>;1648def : QCISELECTICCIPat<SETNE, QC_SELECTINEI>;1649 1650def : QCISELECTICCIPatInv<SETEQ, QC_SELECTINEI>;1651def : QCISELECTICCIPatInv<SETNE, QC_SELECTIEQI>;1652 1653def : QCISELECTICCPat<SETEQ, QC_SELECTIEQ>;1654def : QCISELECTICCPat<SETNE, QC_SELECTINE>;1655 1656def : QCISELECTICCPatInv<SETEQ, QC_SELECTINE>;1657def : QCISELECTICCPatInv<SETNE, QC_SELECTIEQ>;1658 1659def : QCISELECTIICCPat<SETEQ, QC_SELECTIIEQ>;1660def : QCISELECTIICCPat<SETNE, QC_SELECTIINE>;1661} // Predicates = [HasVendorXqcics, IsRV32]1662 1663// Prioritize Xqcicm over these patterns, because Xqcicm is compressible.1664let Predicates = [HasVendorXqcics, NoVendorXqcicm, IsRV32] in {1665def : Pat<(i32 (riscv_selectcc (i32 GPRNoX0:$rd), (i32 0), SETNE, (i32 GPRNoX0:$rs2), (i32 GPRNoX0:$rs3))),1666 (QC_SELECTNEI GPRNoX0:$rd, (i32 0), GPRNoX0:$rs2, GPRNoX0:$rs3)>;1667def : Pat<(i32 (riscv_selectcc (i32 GPRNoX0:$rd), (i32 0), SETEQ, (i32 GPRNoX0:$rs2), (i32 GPRNoX0:$rs3))),1668 (QC_SELECTEQI GPRNoX0:$rd, (i32 0), GPRNoX0:$rs2, GPRNoX0:$rs3)>;1669 1670def : QCISELECTCCIPat<SETEQ, QC_SELECTEQI>;1671def : QCISELECTCCIPat<SETNE, QC_SELECTNEI>;1672}1673 1674let Predicates = [HasVendorXqcilsm, IsRV32] in {1675def : Pat<(qc_setwmi (i32 GPR:$rs3), GPR:$rs1, tuimm5nonzero:$uimm5, tuimm7_lsb00:$uimm7),1676 (QC_SETWMI GPR:$rs3, GPR:$rs1, tuimm5nonzero:$uimm5, tuimm7_lsb00:$uimm7)>;1677} // Predicates = [HasVendorXqcilsm, IsRV32]1678 1679let Predicates = [HasVendorXqcili, IsRV32] in {1680def: Pat<(i32 (qc_e_li tglobaladdr:$A)), (QC_E_LI bare_simm32:$A)>;1681def: Pat<(i32 (qc_e_li tblockaddress:$A)), (QC_E_LI bare_simm32:$A)>;1682def: Pat<(i32 (qc_e_li tjumptable:$A)), (QC_E_LI bare_simm32:$A)>;1683def: Pat<(i32 (qc_e_li tconstpool:$A)), (QC_E_LI bare_simm32:$A)>;1684} // Predicates = [HasVendorXqcili, IsRV32]1685 1686//===----------------------------------------------------------------------===/i1687// Compress Instruction tablegen backend.1688//===----------------------------------------------------------------------===//1689 1690let Predicates = [HasVendorXqcisync, IsRV32] in {1691def : CompressPat<(QC_SYNC uimm5slist:$imm5), (QC_C_SYNC uimm5slist:$imm5)>;1692def : CompressPat<(QC_SYNCR uimm5slist:$imm5), (QC_C_SYNCR uimm5slist:$imm5)>;1693def : CompressPat<(QC_SYNCWL uimm5slist:$imm5), (QC_C_SYNCWL uimm5slist:$imm5)>;1694def : CompressPat<(QC_SYNCWF uimm5slist:$imm5), (QC_C_SYNCWF uimm5slist:$imm5)>;1695} // Predicates = [HasVendorXqcisync, IsRV32]1696 1697let isCompressOnly = true, Predicates = [HasVendorXqcilo, HasStdExtZcb, IsRV32] in {1698def : CompressPat<(QC_E_LBU GPRC:$rd, GPRCMem:$rs1, uimm2:$imm),1699 (C_LBU GPRC:$rd, GPRCMem:$rs1, uimm2:$imm)>;1700def : CompressPat<(QC_E_LHU GPRC:$rd, GPRCMem:$rs1, uimm2_lsb0:$imm),1701 (C_LHU GPRC:$rd, GPRCMem:$rs1, uimm2_lsb0:$imm)>;1702def : CompressPat<(QC_E_LH GPRC:$rd, GPRCMem:$rs1, uimm2_lsb0:$imm),1703 (C_LH GPRC:$rd, GPRCMem:$rs1, uimm2_lsb0:$imm)>;1704def : CompressPat<(QC_E_SB GPRC:$rs2, GPRCMem:$rs1, uimm2:$imm),1705 (C_SB GPRC:$rs2, GPRCMem:$rs1, uimm2:$imm)>;1706def : CompressPat<(QC_E_SH GPRC:$rs2, GPRCMem:$rs1, uimm2_lsb0:$imm),1707 (C_SH GPRC:$rs2, GPRCMem:$rs1, uimm2_lsb0:$imm)>;1708} // isCompressOnly = true, Predicates = [HasVendorXqcilo, HasStdExtZcb, IsRV32]1709 1710let isCompressOnly = true, Predicates = [HasVendorXqcilo, IsRV32] in {1711def : CompressPat<(QC_E_LW GPRC:$rd, GPRCMem:$rs1, uimm7_lsb00:$imm),1712 (C_LW GPRC:$rd, GPRCMem:$rs1, uimm7_lsb00:$imm)>;1713def : CompressPat<(QC_E_LW GPRNoX0:$rd, SPMem:$rs1, uimm8_lsb00:$imm),1714 (C_LWSP GPRNoX0:$rd, SPMem:$rs1, uimm8_lsb00:$imm)>;1715def : CompressPat<(QC_E_LB GPR:$rd, GPRMem:$rs1, simm12_lo:$imm12),1716 (LB GPR:$rd, GPRMem:$rs1, simm12_lo:$imm12)>;1717def : CompressPat<(QC_E_LBU GPR:$rd, GPRMem:$rs1, simm12_lo:$imm12),1718 (LBU GPR:$rd, GPRMem:$rs1, simm12_lo:$imm12)>;1719def : CompressPat<(QC_E_LH GPR:$rd, GPRMem:$rs1, simm12_lo:$imm12),1720 (LH GPR:$rd, GPRMem:$rs1, simm12_lo:$imm12)>;1721def : CompressPat<(QC_E_LHU GPR:$rd, GPRMem:$rs1, simm12_lo:$imm12),1722 (LHU GPR:$rd, GPRMem:$rs1, simm12_lo:$imm12)>;1723def : CompressPat<(QC_E_LW GPR:$rd, GPRMem:$rs1, simm12_lo:$imm12),1724 (LW GPR:$rd, GPRMem:$rs1, simm12_lo:$imm12)>;1725 1726def : CompressPat<(QC_E_SW GPRC:$rs2, GPRCMem:$rs1, uimm7_lsb00:$imm),1727 (C_SW GPRC:$rs2, GPRCMem:$rs1, uimm7_lsb00:$imm)>;1728def : CompressPat<(QC_E_SW GPR:$rs2, SPMem:$rs1, uimm8_lsb00:$imm),1729 (C_SWSP GPR:$rs2, SPMem:$rs1, uimm8_lsb00:$imm)>;1730def : CompressPat<(QC_E_SB GPR:$rs2, GPRMem:$rs1, simm12_lo:$imm12),1731 (SB GPR:$rs2, GPRMem:$rs1, simm12_lo:$imm12)>;1732def : CompressPat<(QC_E_SH GPR:$rs2, GPRMem:$rs1, simm12_lo:$imm12),1733 (SH GPR:$rs2, GPRMem:$rs1, simm12_lo:$imm12)>;1734def : CompressPat<(QC_E_SW GPR:$rs2, GPRMem:$rs1, simm12_lo:$imm12),1735 (SW GPR:$rs2, GPRMem:$rs1, simm12_lo:$imm12)>;1736} // isCompressOnly = true, Predicates = [HasVendorXqcilo, IsRV32]1737 1738let Predicates = [HasVendorXqcicm, IsRV32] in {1739def : CompressPat<(QC_MVEQI GPRC:$rd, GPRC:$rd, 0, GPRC:$rs1),1740 (QC_C_MVEQZ GPRC:$rd, GPRC:$rs1)>;1741let isCompressOnly = true in1742def : CompressPat<(QC_MVLTUI GPRC:$rd, GPRC:$rd, 1, GPRC:$rs1),1743 (QC_C_MVEQZ GPRC:$rd, GPRC:$rs1)>;1744}1745 1746let Predicates = [HasVendorXqcibm, IsRV32] in {1747def : CompressPat<(QC_EXTU GPRNoX0:$rd, GPRNoX0:$rd, uimm5ge6_plus1:$width, 0),1748 (QC_C_EXTU GPRNoX0:$rd, uimm5ge6_plus1:$width)>;1749}1750 1751let Predicates = [HasVendorXqcibm, HasStdExtZbs, IsRV32] in {1752def : CompressPat<(BSETI GPRC:$rs1, GPRC:$rs1, uimmlog2xlennonzero:$shamt),1753 (QC_C_BSETI GPRC:$rs1, uimmlog2xlennonzero:$shamt)>;1754def : CompressPat<(BEXTI GPRC:$rs1, GPRC:$rs1, uimmlog2xlennonzero:$shamt),1755 (QC_C_BEXTI GPRC:$rs1, uimmlog2xlennonzero:$shamt)>;1756let isCompressOnly = true in1757def : CompressPat<(QC_EXTU GPRC:$rd, GPRC:$rd, 1, uimmlog2xlennonzero:$shamt),1758 (QC_C_BEXTI GPRC:$rd, uimmlog2xlennonzero:$shamt)>;1759} // Predicates = [HasVendorXqcibm, HasStdExtZbs, IsRV32]1760 1761let isCompressOnly = true, Predicates = [HasVendorXqcilb, IsRV32] in {1762def : CompressPat<(QC_E_J bare_simm12_lsb0:$offset),1763 (C_J bare_simm12_lsb0:$offset)>;1764def : CompressPat<(QC_E_JAL bare_simm12_lsb0:$offset),1765 (C_JAL bare_simm12_lsb0:$offset)>;1766def : CompressPat<(QC_E_JAL simm21_lsb0_jal:$offset),1767 (JAL X1, simm21_lsb0_jal:$offset)>;1768def : CompressPat<(QC_E_J simm21_lsb0_jal:$offset),1769 (JAL X0, simm21_lsb0_jal:$offset)>;1770} // isCompressOnly = true, Predicates = [HasVendorXqcilb, IsRV32]1771 1772let Predicates = [HasVendorXqcili, IsRV32] in {1773def : CompressPat<(QC_LI GPRNoX0:$rd, simm6:$imm),1774 (C_LI GPRNoX0:$rd, simm6:$imm)>;1775 1776let isCompressOnly = true in {1777def : CompressPat<(QC_E_LI GPRNoX0:$rd, simm6:$imm),1778 (C_LI GPRNoX0:$rd, simm6:$imm)>;1779def : CompressPat<(QC_E_LI GPRNoX0:$rd, simm20_li:$imm),1780 (QC_LI GPRNoX0:$rd, simm20_li:$imm)>;1781} // isCompressOnly = true1782} // Predicates = [HasVendorXqcili, IsRV32]1783 1784let isCompressOnly = true, Predicates = [HasVendorXqcilia, IsRV32] in {1785def : CompressPat<(QC_E_ADDAI GPRNoX0:$rd, simm6nonzero:$imm),1786 (C_ADDI GPRNoX0:$rd, simm6nonzero:$imm)>;1787def : CompressPat<(QC_E_ADDI GPRNoX0:$rs1, GPRNoX0:$rs1, simm6nonzero:$imm),1788 (C_ADDI GPRNoX0:$rs1, simm6nonzero:$imm)>;1789def : CompressPat<(QC_E_ANDAI GPRC:$rd, simm6:$imm),1790 (C_ANDI GPRC:$rd, simm6:$imm)>;1791def : CompressPat<(QC_E_ANDI GPRC:$rs1, GPRC:$rs1, simm6:$imm),1792 (C_ANDI GPRC:$rs1, simm6:$imm)>;1793def : CompressPat<(QC_E_ADDI GPRNoX0:$rs1, GPRNoX0:$rs2, 0),1794 (C_MV GPRNoX0:$rs1, GPRNoX0:$rs2)>;1795def : CompressPat<(QC_E_ADDAI X2, simm10_lsb0000nonzero:$imm),1796 (C_ADDI16SP X2, simm10_lsb0000nonzero:$imm)>;1797def : CompressPat<(QC_E_ADDI X2, X2, simm10_lsb0000nonzero:$imm),1798 (C_ADDI16SP X2, simm10_lsb0000nonzero:$imm)>;1799 1800def : CompressPat<(QC_E_ADDI GPRNoX0:$rs1, GPRNoX0:$rs2, simm12_lo:$imm),1801 (ADDI GPRNoX0:$rs1, GPRNoX0:$rs2, simm12_lo:$imm)>;1802def : CompressPat<(QC_E_ANDI GPRNoX0:$rs1, GPRNoX0:$rs2, simm12_lo:$imm),1803 (ANDI GPRNoX0:$rs1, GPRNoX0:$rs2, simm12_lo:$imm)>;1804def : CompressPat<(QC_E_ORI GPRNoX0:$rs1, GPRNoX0:$rs2, simm12_lo:$imm),1805 (ORI GPRNoX0:$rs1, GPRNoX0:$rs2, simm12_lo:$imm)>;1806def : CompressPat<(QC_E_XORI GPRNoX0:$rs1, GPRNoX0:$rs2, simm12_lo:$imm),1807 (XORI GPRNoX0:$rs1, GPRNoX0:$rs2, simm12_lo:$imm)>;1808 1809def : CompressPat<(QC_E_ADDAI GPRNoX0:$rd, simm12_lo:$imm),1810 (ADDI GPRNoX0:$rd, GPRNoX0:$rd, simm12_lo:$imm)>;1811def : CompressPat<(QC_E_ANDAI GPRNoX0:$rd, simm12_lo:$imm),1812 (ANDI GPRNoX0:$rd, GPRNoX0:$rd, simm12_lo:$imm)>;1813def : CompressPat<(QC_E_ORAI GPRNoX0:$rd, simm12_lo:$imm),1814 (ORI GPRNoX0:$rd, GPRNoX0:$rd, simm12_lo:$imm)>;1815def : CompressPat<(QC_E_XORAI GPRNoX0:$rd, simm12_lo:$imm),1816 (XORI GPRNoX0:$rd, GPRNoX0:$rd, simm12_lo:$imm)>;1817} // let isCompressOnly = true, Predicates = [HasVendorXqcilia, IsRV32]1818 1819let isCompressOnly = true, Predicates = [HasVendorXqciac, IsRV32] in {1820def : CompressPat<(QC_MULIADD GPRC:$rd, GPRC:$rs1, uimm5:$imm5),1821 (QC_C_MULIADD GPRC:$rd, GPRC:$rs1, uimm5:$imm5)>;1822} // isCompressOnly = true, Predicates = [HasVendorXqciac, IsRV32]1823 1824let isCompressOnly = true, Predicates = [HasVendorXqciac, HasStdExtZba, IsRV32] in {1825def : CompressPat<(SH1ADD GPRC:$rd, GPRC:$rs1, GPRC:$rd),1826 (QC_C_MULIADD GPRC:$rd, GPRC:$rs1, 2)>;1827def : CompressPat<(SH2ADD GPRC:$rd, GPRC:$rs1, GPRC:$rd),1828 (QC_C_MULIADD GPRC:$rd, GPRC:$rs1, 4)>;1829def : CompressPat<(SH3ADD GPRC:$rd, GPRC:$rs1, GPRC:$rd),1830 (QC_C_MULIADD GPRC:$rd, GPRC:$rs1, 8)>;1831} // isCompressOnly = true, Predicates = [HasVendorXqciac, HasStdExtZba, IsRV32]1832 1833let isCompressOnly = true, Predicates = [HasVendorXqcibi, IsRV32] in {1834def : CompressPat<(QC_E_BEQI GPRNoX0:$rs1, simm5nonzero:$imm5, bare_simm13_lsb0:$imm12),1835 (QC_BEQI GPRNoX0:$rs1, simm5nonzero:$imm5, bare_simm13_lsb0:$imm12)>;1836def : CompressPat<(QC_E_BNEI GPRNoX0:$rs1, simm5nonzero:$imm5, bare_simm13_lsb0:$imm12),1837 (QC_BNEI GPRNoX0:$rs1, simm5nonzero:$imm5, bare_simm13_lsb0:$imm12)>;1838def : CompressPat<(QC_E_BGEI GPRNoX0:$rs1, simm5nonzero:$imm5, bare_simm13_lsb0:$imm12),1839 (QC_BGEI GPRNoX0:$rs1, simm5nonzero:$imm5, bare_simm13_lsb0:$imm12)>;1840def : CompressPat<(QC_E_BLTI GPRNoX0:$rs1, simm5nonzero:$imm5, bare_simm13_lsb0:$imm12),1841 (QC_BLTI GPRNoX0:$rs1, simm5nonzero:$imm5, bare_simm13_lsb0:$imm12)>;1842def : CompressPat<(QC_E_BGEUI GPRNoX0:$rs1, uimm5nonzero:$imm5, bare_simm13_lsb0:$imm12),1843 (QC_BGEUI GPRNoX0:$rs1, uimm5nonzero:$imm5, bare_simm13_lsb0:$imm12)>;1844def : CompressPat<(QC_E_BLTUI GPRNoX0:$rs1, uimm5nonzero:$imm5, bare_simm13_lsb0:$imm12),1845 (QC_BLTUI GPRNoX0:$rs1, uimm5nonzero:$imm5, bare_simm13_lsb0:$imm12)>;1846} // let isCompressOnly = true, Predicates = [HasVendorXqcibi, IsRV32]1847 1848// HACKS1849// -----1850// The reasons for needing the definitions below are long and quite annoying. I'm writing1851// this so they are explained in-line, rather than anywhere else.1852//1853// Emitting an instruction to an object proceeds as:1854// - Compression (in emitInstruction)1855// - Emit to Binary Code + Fixups1856// - Assembler Relaxation1857// - Fixup evaluation/application1858// - If relaxed, re-emitted to Binary + Fixups1859// - Relocation generation from Fixups1860//1861// Unfortunately, the `QC.E.LI` -> `C.LI` compression pattern has an edge case that has1862// caused crashes in the past.1863//1864// How the bug happens is:1865// - QC.E.LI is parsed with a bare symbol, which is valid + expected, and can1866// be handled by fixups/relocations.1867// - Compression turns this into a `C.LI` because the `simm6` 1868// MCOperandPredicate accepts bare symbols.1869// - Binary Code emission didn't know how to create a fixup for a CI-type1870// instruction containing a bare symbol.1871//1872// The solution to the last bullet is that we added the `fixup_riscv_rvc_imm`,1873// so that we could proceed past the last error, and then use Assembler Relaxation1874// to turn the `C.LI` with a bare symbol back into a `QC.E.LI`.1875//1876// This is good enough for emitting objects, but doesn't work for emitting1877// assembly. Emitting assembly is why we need the following Hacks.1878// 1879// Emitting an instruction to assembly proceeds as:1880// - Compression (in emitInstruction)1881// - Decompression (in RISCVInstPrinter::printInst)1882// - InstAliases are applied1883//1884// So in the case of `QC.E.LI` with a bare symbol, first it is compressed to1885// `C.LI` with a bare symbol, and then it is decompressed to `ADDI` with a bare1886// symbol for printing, which is printed via an alias as `li <reg>, <symbol>`.1887// Both the decompression and the alias use the MCOperandPredicate from 1888// `simm12`, which accepts bare symbols.1889//1890// The problem here is that `li <reg>, <symbol>` fails to parse, because the1891// parsers do not accept bare symbols, they only accept symbols with specifiers1892// or immediates.1893//1894// Our solution is to add another alias, which will be prioritised above the1895// `li` alias, but only when `qc.e.li` is available. We originally intended to1896// use the `bare_symbol` Operand type, but this had no MCOperandPredicate, and1897// adding one changed the error messages when parsing `qc.e.li` with a1898// too-large constant. So instead, we add a new `AsmOperand` and `Operand` type,1899// just for the alias, which parse just like a BareSymbol, but they1900// have both an MCOperandPredicate, and the error message that corresponds to1901// the existing one on `qc.e.li` for too-large immediates (which fail to parse1902// as both an immediate, and a bare symbol).1903//1904// This is fairly unpleasant, but it's the least disruptive thing we can do1905// and keeps all the hacks confined to the RISC-V backend code.1906 1907def BareSymbolQC_E_LI : AsmOperandClass {1908 let Name = "BareSymbolQC_E_LI";1909 let PredicateMethod = "isBareSymbol";1910 let RenderMethod = "addImmOperands";1911 let DiagnosticType = "InvalidBareSymbolQC_E_LI";1912 let ParserMethod = "parseBareSymbol";1913}1914 1915def hack_bare_symbol_qc_e_li : Operand<XLenVT> {1916 let ParserMatchClass = BareSymbolQC_E_LI;1917 let MCOperandPredicate = [{1918 return MCOp.isExpr() && MCOp.isBareSymbolRef();1919 }];1920}1921 1922let Predicates = [HasVendorXqcili, IsRV32] in {1923def : InstAlias<"qc.e.li $rd, $sym", (ADDI GPR:$rd, X0, hack_bare_symbol_qc_e_li:$sym), 3>;1924} // Predicates = [HasVendorXqcili, IsRV32]1925// END HACKS1926