353 lines · plain
1//===-- RISCVInstrInfoZc.td - RISC-V 'Zc*' instructions ----*- tablegen -*-===//2//3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.4// See https://llvm.org/LICENSE.txt for license information.5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception6//7//===----------------------------------------------------------------------===//8///9/// This file describes the RISC-V instructions from the 'Zc*' compressed10/// instruction extensions, version 1.0.3.11///12//===----------------------------------------------------------------------===//13 14//===----------------------------------------------------------------------===//15// Operand and SDNode transformation definitions.16//===----------------------------------------------------------------------===//17 18def uimm2_lsb0 : RISCVOp,19 ImmLeaf<XLenVT, [{return isShiftedUInt<1, 1>(Imm);}]> {20 let ParserMatchClass = UImmAsmOperand<2, "Lsb0">;21 let EncoderMethod = "getImmOpValue";22 let DecoderMethod = "decodeUImmOperand<2>";23 let OperandType = "OPERAND_UIMM2_LSB0";24 let MCOperandPredicate = [{25 int64_t Imm;26 if (!MCOp.evaluateAsConstantImm(Imm))27 return false;28 return isShiftedUInt<1, 1>(Imm);29 }];30}31 32def uimm8ge32 : RISCVOp {33 let ParserMatchClass = UImmAsmOperand<8, "GE32">;34 let DecoderMethod = "decodeUImmOperandGE<8, 32>";35 let OperandType = "OPERAND_UIMM8_GE32";36}37 38def RegListAsmOperand : AsmOperandClass {39 let Name = "RegList";40 let ParserMethod = "parseRegList";41 let DiagnosticType = "InvalidRegList";42 let DiagnosticString = "operand must be {ra [, s0[-sN]]} or {x1 [, x8[-x9][, x18[-xN]]]}";43}44 45def StackAdjAsmOperand : AsmOperandClass {46 let Name = "StackAdj";47 let ParserMethod = "parseZcmpStackAdj";48 let DiagnosticType = "InvalidStackAdj";49 let PredicateMethod = "isStackAdj";50 let RenderMethod = "addStackAdjOperands";51}52 53def NegStackAdjAsmOperand : AsmOperandClass {54 let Name = "NegStackAdj";55 let ParserMethod = "parseZcmpNegStackAdj";56 let DiagnosticType = "InvalidStackAdj";57 let PredicateMethod = "isStackAdj";58 let RenderMethod = "addStackAdjOperands";59}60 61def reglist : RISCVOp<OtherVT> {62 let ParserMatchClass = RegListAsmOperand;63 let PrintMethod = "printRegList";64 let DecoderMethod = "decodeZcmpRlist";65 let EncoderMethod = "getRlistOpValue";66 let MCOperandPredicate = [{67 int64_t Imm;68 if (!MCOp.evaluateAsConstantImm(Imm))69 return false;70 // 0~3 Reserved for EABI71 return isUInt<4>(Imm) && Imm >= RISCVZC::RA;72 }];73 74 let OperandType = "OPERAND_RLIST";75}76 77def stackadj : RISCVOp<OtherVT> {78 let ParserMatchClass = StackAdjAsmOperand;79 let PrintMethod = "printStackAdj";80 let OperandType = "OPERAND_STACKADJ";81 let MCOperandPredicate = [{82 int64_t Imm;83 if (!MCOp.evaluateAsConstantImm(Imm))84 return false;85 return isShiftedUInt<2, 4>(Imm);86 }];87}88 89def negstackadj : RISCVOp<OtherVT> {90 let ParserMatchClass = NegStackAdjAsmOperand;91 let PrintMethod = "printNegStackAdj";92 let OperandType = "OPERAND_STACKADJ";93 let MCOperandPredicate = [{94 int64_t Imm;95 if (!MCOp.evaluateAsConstantImm(Imm))96 return false;97 return isShiftedUInt<2, 4>(Imm);98 }];99}100 101//===----------------------------------------------------------------------===//102// Instruction Class Templates103//===----------------------------------------------------------------------===//104 105let hasSideEffects = 0, mayLoad = 1, mayStore = 0 in106class CLoadB_ri<bits<6> funct6, string OpcodeStr>107 : RVInst16CLB<funct6, 0b00, (outs GPRC:$rd),108 (ins GPRCMem:$rs1, uimm2:$imm),109 OpcodeStr, "$rd, ${imm}(${rs1})"> {110 bits<2> imm;111 112 let Inst{6-5} = imm{0,1};113}114 115let hasSideEffects = 0, mayLoad = 1, mayStore = 0 in116class CLoadH_ri<bits<6> funct6, bit funct1, string OpcodeStr,117 DAGOperand rty = GPRC>118 : RVInst16CLH<funct6, funct1, 0b00, (outs rty:$rd),119 (ins GPRCMem:$rs1, uimm2_lsb0:$imm),120 OpcodeStr, "$rd, ${imm}(${rs1})"> {121 bits<2> imm;122 123 let Inst{5} = imm{1};124}125 126let hasSideEffects = 0, mayLoad = 0, mayStore = 1 in127class CStoreB_rri<bits<6> funct6, string OpcodeStr>128 : RVInst16CSB<funct6, 0b00, (outs),129 (ins GPRC:$rs2, GPRCMem:$rs1, uimm2:$imm),130 OpcodeStr, "$rs2, ${imm}(${rs1})"> {131 bits<2> imm;132 133 let Inst{6-5} = imm{0,1};134}135 136let hasSideEffects = 0, mayLoad = 0, mayStore = 1 in137class CStoreH_rri<bits<6> funct6, bit funct1, string OpcodeStr,138 DAGOperand rty = GPRC>139 : RVInst16CSH<funct6, funct1, 0b00, (outs),140 (ins rty:$rs2, GPRCMem:$rs1, uimm2_lsb0:$imm),141 OpcodeStr, "$rs2, ${imm}(${rs1})"> {142 bits<2> imm;143 144 let Inst{5} = imm{1};145}146 147let hasSideEffects = 0, mayLoad = 0, mayStore = 0 in148class RVZcArith_r<bits<5> funct5, string OpcodeStr> :149 RVInst16CU<0b100111, funct5, 0b01, (outs GPRC:$rd_wb), (ins GPRC:$rd),150 OpcodeStr, "$rd"> {151 let Constraints = "$rd = $rd_wb";152}153 154class RVInstZcCPPP<bits<5> funct5, string opcodestr,155 DAGOperand immtype = stackadj>156 : RVInst16<(outs), (ins reglist:$rlist, immtype:$stackadj),157 opcodestr, "$rlist, $stackadj", [], InstFormatOther> {158 bits<4> rlist;159 bits<16> stackadj;160 161 let Inst{1-0} = 0b10;162 let Inst{3-2} = stackadj{5-4};163 let Inst{7-4} = rlist;164 let Inst{12-8} = funct5;165 let Inst{15-13} = 0b101;166}167 168//===----------------------------------------------------------------------===//169// Instructions170//===----------------------------------------------------------------------===//171 172let Predicates = [HasStdExtZcb, HasStdExtZba, IsRV64] in173def C_ZEXT_W : RVZcArith_r<0b11100 , "c.zext.w">,174 Sched<[WriteIALU32, ReadIALU32, ReadIALU32]>;175 176let Predicates = [HasStdExtZcb, HasStdExtZbb] in {177def C_ZEXT_H : RVZcArith_r<0b11010 , "c.zext.h">,178 Sched<[WriteIALU, ReadIALU]>;179def C_SEXT_B : RVZcArith_r<0b11001 , "c.sext.b">,180 Sched<[WriteIALU, ReadIALU]>;181def C_SEXT_H : RVZcArith_r<0b11011 , "c.sext.h">,182 Sched<[WriteIALU, ReadIALU]>;183}184 185let Predicates = [HasStdExtZcb] in186def C_ZEXT_B : RVZcArith_r<0b11000 , "c.zext.b">,187 Sched<[WriteIALU, ReadIALU]>;188 189let Predicates = [HasStdExtZcb, HasStdExtZmmul] in190def C_MUL : CA_ALU<0b100111, 0b10, "c.mul">,191 Sched<[WriteIMul, ReadIMul, ReadIMul]>;192 193let Predicates = [HasStdExtZcb] in {194def C_NOT : RVZcArith_r<0b11101 , "c.not">,195 Sched<[WriteIALU, ReadIALU]>;196 197def C_LBU : CLoadB_ri<0b100000, "c.lbu">,198 Sched<[WriteLDB, ReadMemBase]>;199def C_LHU : CLoadH_ri<0b100001, 0b0, "c.lhu">,200 Sched<[WriteLDH, ReadMemBase]>;201def C_LH : CLoadH_ri<0b100001, 0b1, "c.lh">,202 Sched<[WriteLDH, ReadMemBase]>;203 204def C_SB : CStoreB_rri<0b100010, "c.sb">,205 Sched<[WriteSTB, ReadStoreData, ReadMemBase]>;206def C_SH : CStoreH_rri<0b100011, 0b0, "c.sh">,207 Sched<[WriteSTH, ReadStoreData, ReadMemBase]>;208 209// Compressed versions of Zhinx load/store.210let isCodeGenOnly = 1 in {211def C_LH_INX : CLoadH_ri<0b100001, 0b1, "c.lh", GPRF16C>,212 Sched<[WriteLDH, ReadMemBase]>;213def C_SH_INX : CStoreH_rri<0b100011, 0b0, "c.sh", GPRF16C>,214 Sched<[WriteSTH, ReadStoreData, ReadMemBase]>;215}216} // Predicates = [HasStdExtZcb]217 218// Zcmp219let DecoderNamespace = "ZcOverlap", Predicates = [HasStdExtZcmp],220 hasSideEffects = 0, mayLoad = 0, mayStore = 0 in {221let Defs = [X10, X11] in222def CM_MVA01S : RVInst16CA<0b101011, 0b11, 0b10, (outs),223 (ins SR07:$rs1, SR07:$rs2), "cm.mva01s", "$rs1, $rs2">,224 Sched<[WriteIALU, WriteIALU, ReadIALU, ReadIALU]>;225 226let Uses = [X10, X11] in227def CM_MVSA01 : RVInst16CA<0b101011, 0b01, 0b10, (outs SR07:$rs1, SR07:$rs2),228 (ins), "cm.mvsa01", "$rs1, $rs2">,229 Sched<[WriteIALU, WriteIALU, ReadIALU, ReadIALU]>;230} // DecoderNamespace = "ZcOverlap", Predicates = [HasStdExtZcmp]...231 232let DecoderNamespace = "ZcOverlap", Predicates = [HasStdExtZcmp] in {233let hasSideEffects = 0, mayLoad = 0, mayStore = 1, Uses = [X2], Defs = [X2] in234def CM_PUSH : RVInstZcCPPP<0b11000, "cm.push", negstackadj>,235 Sched<[WriteIALU, ReadIALU, ReadStoreData, ReadStoreData,236 ReadStoreData, ReadStoreData, ReadStoreData, ReadStoreData,237 ReadStoreData, ReadStoreData, ReadStoreData, ReadStoreData,238 ReadStoreData, ReadStoreData, ReadStoreData]>;239 240let hasSideEffects = 0, mayLoad = 1, mayStore = 0, isReturn = 1,241 Uses = [X2], Defs = [X2] in242def CM_POPRET : RVInstZcCPPP<0b11110, "cm.popret">,243 Sched<[WriteIALU, WriteLDW, WriteLDW, WriteLDW, WriteLDW,244 WriteLDW, WriteLDW, WriteLDW, WriteLDW, WriteLDW,245 WriteLDW, WriteLDW, WriteLDW, WriteLDW, ReadIALU]>;246 247let hasSideEffects = 0, mayLoad = 1, mayStore = 0, isReturn = 1,248 Uses = [X2], Defs = [X2, X10] in249def CM_POPRETZ : RVInstZcCPPP<0b11100, "cm.popretz">,250 Sched<[WriteIALU, WriteIALU, WriteLDW, WriteLDW, WriteLDW,251 WriteLDW, WriteLDW, WriteLDW, WriteLDW, WriteLDW,252 WriteLDW, WriteLDW, WriteLDW, WriteLDW, WriteLDW,253 ReadIALU]>;254 255let hasSideEffects = 0, mayLoad = 1, mayStore = 0,256 Uses = [X2], Defs = [X2] in257def CM_POP : RVInstZcCPPP<0b11010, "cm.pop">,258 Sched<[WriteIALU, WriteLDW, WriteLDW, WriteLDW, WriteLDW,259 WriteLDW, WriteLDW, WriteLDW, WriteLDW, WriteLDW, WriteLDW,260 WriteLDW, WriteLDW, WriteLDW, ReadIALU]>;261} // DecoderNamespace = "ZcOverlap", Predicates = [HasStdExtZcmp]...262 263let DecoderNamespace = "ZcOverlap", Predicates = [HasStdExtZcmt],264 hasSideEffects = 0, mayLoad = 0, mayStore = 0 in {265def CM_JT : RVInst16CJ<0b101, 0b10, (outs), (ins uimm5:$index),266 "cm.jt", "$index">{267 bits<5> index;268 269 let Inst{12-7} = 0b000000;270 let Inst{6-2} = index;271}272 273let Defs = [X1] in274def CM_JALT : RVInst16CJ<0b101, 0b10, (outs), (ins uimm8ge32:$index),275 "cm.jalt", "$index">{276 bits<8> index;277 278 let Inst{12-10} = 0b000;279 let Inst{9-2} = index;280}281} // DecoderNamespace = "ZcOverlap", Predicates = [HasStdExtZcmt]...282 283 284let Predicates = [HasStdExtZcb, HasStdExtZmmul] in{285def : CompressPat<(MUL GPRC:$rs1, GPRC:$rs1, GPRC:$rs2),286 (C_MUL GPRC:$rs1, GPRC:$rs2)>;287let isCompressOnly = true in288def : CompressPat<(MUL GPRC:$rs1, GPRC:$rs2, GPRC:$rs1),289 (C_MUL GPRC:$rs1, GPRC:$rs2)>;290} // Predicates = [HasStdExtZcb, HasStdExtZmmul]291 292let Predicates = [HasStdExtZcb, HasStdExtZbb] in{293def : CompressPat<(SEXT_B GPRC:$rs1, GPRC:$rs1),294 (C_SEXT_B GPRC:$rs1)>;295def : CompressPat<(SEXT_H GPRC:$rs1, GPRC:$rs1),296 (C_SEXT_H GPRC:$rs1)>;297} // Predicates = [HasStdExtZcb, HasStdExtZbb]298 299let Predicates = [HasStdExtZcb, HasStdExtZbb] in{300def : CompressPat<(ZEXT_H_RV32 GPRC:$rs1, GPRC:$rs1),301 (C_ZEXT_H GPRC:$rs1)>;302def : CompressPat<(ZEXT_H_RV64 GPRC:$rs1, GPRC:$rs1),303 (C_ZEXT_H GPRC:$rs1)>;304} // Predicates = [HasStdExtZcb, HasStdExtZbb]305 306let Predicates = [HasStdExtZcb] in{307def : CompressPat<(ANDI GPRC:$rs1, GPRC:$rs1, 255),308 (C_ZEXT_B GPRC:$rs1)>;309} // Predicates = [HasStdExtZcb]310 311let Predicates = [HasStdExtZcb, HasStdExtZba, IsRV64] in{312def : CompressPat<(ADD_UW GPRC:$rs1, GPRC:$rs1, X0),313 (C_ZEXT_W GPRC:$rs1)>;314} // Predicates = [HasStdExtZcb, HasStdExtZba, IsRV64]315 316let Predicates = [HasStdExtZcb] in{317def : CompressPat<(XORI GPRC:$rs1, GPRC:$rs1, -1),318 (C_NOT GPRC:$rs1)>;319}320 321let Predicates = [HasStdExtZcb] in{322def : CompressPat<(LBU GPRC:$rd, GPRCMem:$rs1, uimm2:$imm),323 (C_LBU GPRC:$rd, GPRCMem:$rs1, uimm2:$imm)>;324def : CompressPat<(LHU GPRC:$rd, GPRCMem:$rs1, uimm2_lsb0:$imm),325 (C_LHU GPRC:$rd, GPRCMem:$rs1, uimm2_lsb0:$imm)>;326def : CompressPat<(LH GPRC:$rd, GPRCMem:$rs1, uimm2_lsb0:$imm),327 (C_LH GPRC:$rd, GPRCMem:$rs1, uimm2_lsb0:$imm)>;328def : CompressPat<(SB GPRC:$rs2, GPRCMem:$rs1, uimm2:$imm),329 (C_SB GPRC:$rs2, GPRCMem:$rs1, uimm2:$imm)>;330def : CompressPat<(SH GPRC:$rs2, GPRCMem:$rs1, uimm2_lsb0:$imm),331 (C_SH GPRC:$rs2, GPRCMem:$rs1, uimm2_lsb0:$imm)>;332 333let isCompressOnly = true in {334def : CompressPat<(LH_INX GPRF16C:$rd, GPRCMem:$rs1, uimm2_lsb0:$imm),335 (C_LH_INX GPRF16C:$rd, GPRCMem:$rs1, uimm2_lsb0:$imm)>;336def : CompressPat<(SH_INX GPRF16C:$rs2, GPRCMem:$rs1, uimm2_lsb0:$imm),337 (C_SH_INX GPRF16C:$rs2, GPRCMem:$rs1, uimm2_lsb0:$imm)>;338}339}// Predicates = [HasStdExtZcb]340 341 342//===----------------------------------------------------------------------===//343// Pseudo Instructions344//===----------------------------------------------------------------------===//345 346let Predicates = [HasStdExtZcb] in {347def : InstAlias<"c.lbu $rd, (${rs1})",(C_LBU GPRC:$rd, GPRC:$rs1, 0), 0>;348def : InstAlias<"c.lhu $rd, (${rs1})",(C_LHU GPRC:$rd, GPRC:$rs1, 0), 0>;349def : InstAlias<"c.lh $rd, (${rs1})", (C_LH GPRC:$rd, GPRC:$rs1, 0), 0>;350def : InstAlias<"c.sb $rd, (${rs1})", (C_SB GPRC:$rd, GPRC:$rs1, 0), 0>;351def : InstAlias<"c.sh $rd, (${rs1})", (C_SH GPRC:$rd, GPRC:$rs1, 0), 0>;352}353