1/*************************************************************************************** 2* Copyright (c) 2020-2021 Institute of Computing Technology, Chinese Academy of Sciences 3* Copyright (c) 2020-2021 Peng Cheng Laboratory 4* 5* XiangShan is licensed under Mulan PSL v2. 6* You can use this software according to the terms and conditions of the Mulan PSL v2. 7* You may obtain a copy of Mulan PSL v2 at: 8* http://license.coscl.org.cn/MulanPSL2 9* 10* THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, 11* EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, 12* MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE. 13* 14* See the Mulan PSL v2 for more details. 15***************************************************************************************/ 16 17package xiangshan.backend.decode 18 19import org.chipsalliance.cde.config.Parameters 20import chisel3._ 21import chisel3.util._ 22import freechips.rocketchip.rocket.CSRs 23import freechips.rocketchip.rocket.Instructions._ 24import freechips.rocketchip.util.uintToBitPat 25import utility._ 26import utils._ 27import xiangshan.ExceptionNO.{EX_II, breakPoint, illegalInstr, virtualInstr} 28import xiangshan._ 29import xiangshan.backend.fu.FuType 30import xiangshan.backend.Bundles.{DecodedInst, DynInst, StaticInst} 31import xiangshan.backend.decode.isa.PseudoInstructions 32import xiangshan.backend.decode.isa.bitfield.{InstVType, OPCODE5Bit, XSInstBitFields} 33import xiangshan.backend.fu.vector.Bundles.{VType, Vl} 34import xiangshan.backend.fu.wrapper.CSRToDecode 35import xiangshan.backend.decode.Zimop._ 36 37/** 38 * Abstract trait giving defaults and other relevant values to different Decode constants/ 39 */ 40abstract trait DecodeConstants { 41 // This X should be used only in 1-bit signal. Otherwise, use BitPat("b???") to align with the width of UInt. 42 def X = BitPat("b0") 43 def N = BitPat("b0") 44 def Y = BitPat("b1") 45 def T = true 46 def F = false 47 48 def decodeDefault: List[BitPat] = // illegal instruction 49 // srcType(0) srcType(1) srcType(2) fuType fuOpType rfWen 50 // | | | | | | fpWen 51 // | | | | | | | vecWen 52 // | | | | | | | | isXSTrap 53 // | | | | | | | | | noSpecExec 54 // | | | | | | | | | | blockBackward 55 // | | | | | | | | | | | flushPipe 56 // | | | | | | | | | | | | canRobCompress 57 // | | | | | | | | | | | | | uopSplitType 58 // | | | | | | | | | | | | | | selImm 59 List(SrcType.X, SrcType.X, SrcType.X, FuType.X, FuOpType.X, N, N, N, N, N, N, N, N, UopSplitType.X, SelImm.INVALID_INSTR) // Use SelImm to indicate invalid instr 60 61 val decodeArray: Array[(BitPat, XSDecodeBase)] 62 final def table: Array[(BitPat, List[BitPat])] = decodeArray.map(x => (x._1, x._2.generate())) 63} 64 65trait DecodeUnitConstants 66{ 67 // abstract out instruction decode magic numbers 68 val RD_MSB = 11 69 val RD_LSB = 7 70 val RS1_MSB = 19 71 val RS1_LSB = 15 72 val RS2_MSB = 24 73 val RS2_LSB = 20 74 val RS3_MSB = 31 75 val RS3_LSB = 27 76} 77 78/** 79 * Decoded control signals 80 * See xiangshan/package.scala, xiangshan/backend/package.scala, Bundle.scala 81 */ 82 83abstract class XSDecodeBase { 84 def X = BitPat("b?") 85 def N = BitPat("b0") 86 def Y = BitPat("b1") 87 def T = true 88 def F = false 89 def generate() : List[BitPat] 90} 91 92case class XSDecode( 93 src1: BitPat, src2: BitPat, src3: BitPat, 94 fu: FuType.OHType, fuOp: BitPat, selImm: BitPat, 95 uopSplitType: BitPat = UopSplitType.X, 96 xWen: Boolean = false, 97 fWen: Boolean = false, 98 vWen: Boolean = false, 99 mWen: Boolean = false, 100 xsTrap: Boolean = false, 101 noSpec: Boolean = false, 102 blockBack: Boolean = false, 103 flushPipe: Boolean = false, 104 canRobCompress: Boolean = false, 105) extends XSDecodeBase { 106 def generate() : List[BitPat] = { 107 List (src1, src2, src3, BitPat(fu.U(FuType.num.W)), fuOp, xWen.B, fWen.B, (vWen || mWen).B, xsTrap.B, noSpec.B, blockBack.B, flushPipe.B, canRobCompress.B, uopSplitType, selImm) 108 } 109} 110 111case class FDecode( 112 src1: BitPat, src2: BitPat, src3: BitPat, 113 fu: FuType.OHType, fuOp: BitPat, selImm: BitPat = SelImm.X, 114 uopSplitType: BitPat = UopSplitType.X, 115 xWen: Boolean = false, 116 fWen: Boolean = false, 117 vWen: Boolean = false, 118 mWen: Boolean = false, 119 xsTrap: Boolean = false, 120 noSpec: Boolean = false, 121 blockBack: Boolean = false, 122 flushPipe: Boolean = false, 123 canRobCompress: Boolean = false, 124) extends XSDecodeBase { 125 def generate() : List[BitPat] = { 126 XSDecode(src1, src2, src3, fu, fuOp, selImm, uopSplitType, xWen, fWen, vWen, mWen, xsTrap, noSpec, blockBack, flushPipe, canRobCompress).generate() 127 } 128} 129 130/** 131 * Overall Decode constants 132 */ 133object XDecode extends DecodeConstants { 134 val decodeArray: Array[(BitPat, XSDecodeBase)] = Array( 135 // RV32I 136 LW -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.ldu, LSUOpType.lw , SelImm.IMM_I, xWen = T), 137 LH -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.ldu, LSUOpType.lh , SelImm.IMM_I, xWen = T), 138 LHU -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.ldu, LSUOpType.lhu , SelImm.IMM_I, xWen = T), 139 LB -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.ldu, LSUOpType.lb , SelImm.IMM_I, xWen = T), 140 LBU -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.ldu, LSUOpType.lbu , SelImm.IMM_I, xWen = T), 141 SW -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.stu, LSUOpType.sw , SelImm.IMM_S ), 142 SH -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.stu, LSUOpType.sh , SelImm.IMM_S ), 143 SB -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.stu, LSUOpType.sb , SelImm.IMM_S ), 144 LUI -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.add , SelImm.IMM_U, xWen = T, canRobCompress = T), 145 ADDI -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.add , SelImm.IMM_I, xWen = T, canRobCompress = T), 146 ANDI -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.and , SelImm.IMM_I, xWen = T, canRobCompress = T), 147 ORI -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.or , SelImm.IMM_I, xWen = T, canRobCompress = T), 148 XORI -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.xor , SelImm.IMM_I, xWen = T, canRobCompress = T), 149 SLTI -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.slt , SelImm.IMM_I, xWen = T, canRobCompress = T), 150 SLTIU -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.sltu, SelImm.IMM_I, xWen = T, canRobCompress = T), 151 SLL -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.sll , SelImm.X , xWen = T, canRobCompress = T), 152 ADD -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.add , SelImm.X , xWen = T, canRobCompress = T), 153 SUB -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.sub , SelImm.X , xWen = T, canRobCompress = T), 154 SLT -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.slt , SelImm.X , xWen = T, canRobCompress = T), 155 SLTU -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.sltu, SelImm.X , xWen = T, canRobCompress = T), 156 AND -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.and , SelImm.X , xWen = T, canRobCompress = T), 157 OR -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.or , SelImm.X , xWen = T, canRobCompress = T), 158 XOR -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.xor , SelImm.X , xWen = T, canRobCompress = T), 159 SRA -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.sra , SelImm.X , xWen = T, canRobCompress = T), 160 SRL -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.srl , SelImm.X , xWen = T, canRobCompress = T), 161 162 // RV64I (extend from RV32I) 163 LD -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.ldu, LSUOpType.ld , SelImm.IMM_I, xWen = T), 164 LWU -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.ldu, LSUOpType.lwu , SelImm.IMM_I, xWen = T), 165 SD -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.stu, LSUOpType.sd , SelImm.IMM_S ), 166 167 SLLI -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.sll , SelImm.IMM_I, xWen = T, canRobCompress = T), 168 SRLI -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.srl , SelImm.IMM_I, xWen = T, canRobCompress = T), 169 SRAI -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.sra , SelImm.IMM_I, xWen = T, canRobCompress = T), 170 171 ADDIW -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.addw, SelImm.IMM_I, xWen = T, canRobCompress = T), 172 SLLIW -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.sllw, SelImm.IMM_I, xWen = T, canRobCompress = T), 173 SRAIW -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.sraw, SelImm.IMM_I, xWen = T, canRobCompress = T), 174 SRLIW -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.srlw, SelImm.IMM_I, xWen = T, canRobCompress = T), 175 176 ADDW -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.addw, SelImm.X , xWen = T, canRobCompress = T), 177 SUBW -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.subw, SelImm.X , xWen = T, canRobCompress = T), 178 SLLW -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.sllw, SelImm.X , xWen = T, canRobCompress = T), 179 SRAW -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.sraw, SelImm.X , xWen = T, canRobCompress = T), 180 SRLW -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.srlw, SelImm.X , xWen = T, canRobCompress = T), 181 182 // RV64M 183 MUL -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mul, MDUOpType.mul , SelImm.X, xWen = T, canRobCompress = T), 184 MULH -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mul, MDUOpType.mulh , SelImm.X, xWen = T, canRobCompress = T), 185 MULHU -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mul, MDUOpType.mulhu , SelImm.X, xWen = T, canRobCompress = T), 186 MULHSU -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mul, MDUOpType.mulhsu, SelImm.X, xWen = T, canRobCompress = T), 187 MULW -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mul, MDUOpType.mulw , SelImm.X, xWen = T, canRobCompress = T), 188 189 DIV -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.div, MDUOpType.div , SelImm.X, xWen = T, canRobCompress = T), 190 DIVU -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.div, MDUOpType.divu , SelImm.X, xWen = T, canRobCompress = T), 191 REM -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.div, MDUOpType.rem , SelImm.X, xWen = T, canRobCompress = T), 192 REMU -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.div, MDUOpType.remu , SelImm.X, xWen = T, canRobCompress = T), 193 DIVW -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.div, MDUOpType.divw , SelImm.X, xWen = T, canRobCompress = T), 194 DIVUW -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.div, MDUOpType.divuw , SelImm.X, xWen = T, canRobCompress = T), 195 REMW -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.div, MDUOpType.remw , SelImm.X, xWen = T, canRobCompress = T), 196 REMUW -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.div, MDUOpType.remuw , SelImm.X, xWen = T, canRobCompress = T), 197 198 AUIPC -> XSDecode(SrcType.pc , SrcType.imm, SrcType.X, FuType.jmp, JumpOpType.auipc, SelImm.IMM_U , xWen = T), 199 JAL -> XSDecode(SrcType.pc , SrcType.imm, SrcType.X, FuType.jmp, JumpOpType.jal , SelImm.IMM_UJ, xWen = T), 200 JALR -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.jmp, JumpOpType.jalr , SelImm.IMM_I , xWen = T), 201 BEQ -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.brh, BRUOpType.beq , SelImm.IMM_SB ), 202 BNE -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.brh, BRUOpType.bne , SelImm.IMM_SB ), 203 BGE -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.brh, BRUOpType.bge , SelImm.IMM_SB ), 204 BGEU -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.brh, BRUOpType.bgeu , SelImm.IMM_SB ), 205 BLT -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.brh, BRUOpType.blt , SelImm.IMM_SB ), 206 BLTU -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.brh, BRUOpType.bltu , SelImm.IMM_SB ), 207 208 // System, the immediate12 holds the CSR register. 209 210 CSRRW -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.csr, CSROpType.wrt , SelImm.IMM_Z, xWen = T, noSpec = T, blockBack = T), 211 CSRRS -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.csr, CSROpType.set , SelImm.IMM_Z, xWen = T, noSpec = T, blockBack = T), 212 CSRRC -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.csr, CSROpType.clr , SelImm.IMM_Z, xWen = T, noSpec = T, blockBack = T), 213 214 CSRRWI -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.csr, CSROpType.wrti, SelImm.IMM_Z, xWen = T, noSpec = T, blockBack = T), 215 CSRRSI -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.csr, CSROpType.seti, SelImm.IMM_Z, xWen = T, noSpec = T, blockBack = T), 216 CSRRCI -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.csr, CSROpType.clri, SelImm.IMM_Z, xWen = T, noSpec = T, blockBack = T), 217 218 EBREAK -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.csr, CSROpType.jmp, SelImm.IMM_I, xWen = T, noSpec = T, blockBack = T), 219 ECALL -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.csr, CSROpType.jmp, SelImm.IMM_I, xWen = T, noSpec = T, blockBack = T), 220 SRET -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.csr, CSROpType.jmp, SelImm.IMM_I, xWen = T, noSpec = T, blockBack = T), 221 MRET -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.csr, CSROpType.jmp, SelImm.IMM_I, xWen = T, noSpec = T, blockBack = T), 222 DRET -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.csr, CSROpType.jmp, SelImm.IMM_I, xWen = T, noSpec = T, blockBack = T), 223 WFI -> XSDecode(SrcType.pc , SrcType.imm, SrcType.X, FuType.csr, CSROpType.wfi, SelImm.X , xWen = T, noSpec = T, blockBack = T), 224 225 SFENCE_VMA -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.fence, FenceOpType.sfence, SelImm.X, noSpec = T, blockBack = T, flushPipe = T), 226 FENCE_I -> XSDecode(SrcType.pc , SrcType.imm, SrcType.X, FuType.fence, FenceOpType.fencei, SelImm.X, noSpec = T, blockBack = T, flushPipe = T), 227 FENCE -> XSDecode(SrcType.pc , SrcType.imm, SrcType.X, FuType.fence, FenceOpType.fence , SelImm.X, noSpec = T, blockBack = T, flushPipe = T), 228 229 // RV64A 230 AMOADD_W -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.amoadd_w , SelImm.X, xWen = T, noSpec = T, blockBack = T), 231 AMOXOR_W -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.amoxor_w , SelImm.X, xWen = T, noSpec = T, blockBack = T), 232 AMOSWAP_W -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.amoswap_w, SelImm.X, xWen = T, noSpec = T, blockBack = T), 233 AMOAND_W -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.amoand_w , SelImm.X, xWen = T, noSpec = T, blockBack = T), 234 AMOOR_W -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.amoor_w , SelImm.X, xWen = T, noSpec = T, blockBack = T), 235 AMOMIN_W -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.amomin_w , SelImm.X, xWen = T, noSpec = T, blockBack = T), 236 AMOMINU_W -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.amominu_w, SelImm.X, xWen = T, noSpec = T, blockBack = T), 237 AMOMAX_W -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.amomax_w , SelImm.X, xWen = T, noSpec = T, blockBack = T), 238 AMOMAXU_W -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.amomaxu_w, SelImm.X, xWen = T, noSpec = T, blockBack = T), 239 240 AMOADD_D -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.amoadd_d , SelImm.X, xWen = T, noSpec = T, blockBack = T), 241 AMOXOR_D -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.amoxor_d , SelImm.X, xWen = T, noSpec = T, blockBack = T), 242 AMOSWAP_D -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.amoswap_d, SelImm.X, xWen = T, noSpec = T, blockBack = T), 243 AMOAND_D -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.amoand_d , SelImm.X, xWen = T, noSpec = T, blockBack = T), 244 AMOOR_D -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.amoor_d , SelImm.X, xWen = T, noSpec = T, blockBack = T), 245 AMOMIN_D -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.amomin_d , SelImm.X, xWen = T, noSpec = T, blockBack = T), 246 AMOMINU_D -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.amominu_d, SelImm.X, xWen = T, noSpec = T, blockBack = T), 247 AMOMAX_D -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.amomax_d , SelImm.X, xWen = T, noSpec = T, blockBack = T), 248 AMOMAXU_D -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.amomaxu_d, SelImm.X, xWen = T, noSpec = T, blockBack = T), 249 250 LR_W -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.mou, LSUOpType.lr_w, SelImm.X, xWen = T, noSpec = T, blockBack = T), 251 LR_D -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.mou, LSUOpType.lr_d, SelImm.X, xWen = T, noSpec = T, blockBack = T), 252 SC_W -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.sc_w, SelImm.X, xWen = T, noSpec = T, blockBack = T), 253 SC_D -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.mou, LSUOpType.sc_d, SelImm.X, xWen = T, noSpec = T, blockBack = T), 254 ) 255} 256 257object BitmanipDecode extends DecodeConstants{ 258 /* 259 Note: Some Bitmanip instruction may have different OP code between rv32 and rv64. 260 Including pseudo instruction like zext.h, and different funct12 like rev8. 261 If some day we need to support change XLEN via CSR, we should care about this. 262 */ 263 val decodeArray: Array[(BitPat, XSDecodeBase)] = Array( 264 // Zba 265 ADD_UW -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.adduw , SelImm.X , xWen = T, canRobCompress = T), 266 SH1ADD -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.sh1add , SelImm.X , xWen = T, canRobCompress = T), 267 SH1ADD_UW -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.sh1adduw, SelImm.X , xWen = T, canRobCompress = T), 268 SH2ADD -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.sh2add , SelImm.X , xWen = T, canRobCompress = T), 269 SH2ADD_UW -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.sh2adduw, SelImm.X , xWen = T, canRobCompress = T), 270 SH3ADD -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.sh3add , SelImm.X , xWen = T, canRobCompress = T), 271 SH3ADD_UW -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.sh3adduw, SelImm.X , xWen = T, canRobCompress = T), 272 SLLI_UW -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.slliuw , SelImm.IMM_I, xWen = T, canRobCompress = T), 273 274 // Zbb 275 ANDN -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.andn , SelImm.X , xWen = T, canRobCompress = T), 276 ORN -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.orn , SelImm.X , xWen = T, canRobCompress = T), 277 XNOR -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.xnor , SelImm.X , xWen = T, canRobCompress = T), 278 279 CLZ -> XSDecode(SrcType.reg, SrcType.DC , SrcType.X, FuType.bku, BKUOpType.clz , SelImm.X , xWen = T, canRobCompress = T), 280 CLZW -> XSDecode(SrcType.reg, SrcType.DC , SrcType.X, FuType.bku, BKUOpType.clzw , SelImm.X , xWen = T, canRobCompress = T), 281 CTZ -> XSDecode(SrcType.reg, SrcType.DC , SrcType.X, FuType.bku, BKUOpType.ctz , SelImm.X , xWen = T, canRobCompress = T), 282 CTZW -> XSDecode(SrcType.reg, SrcType.DC , SrcType.X, FuType.bku, BKUOpType.ctzw , SelImm.X , xWen = T, canRobCompress = T), 283 284 CPOP -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.bku, BKUOpType.cpop , SelImm.X , xWen = T, canRobCompress = T), 285 CPOPW -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.bku, BKUOpType.cpopw , SelImm.X , xWen = T, canRobCompress = T), 286 287 MAX -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.max , SelImm.X , xWen = T, canRobCompress = T), 288 MAXU -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.maxu , SelImm.X , xWen = T, canRobCompress = T), 289 MIN -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.min , SelImm.X , xWen = T, canRobCompress = T), 290 MINU -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.minu , SelImm.X , xWen = T, canRobCompress = T), 291 292 SEXT_B -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.alu, ALUOpType.sextb , SelImm.X , xWen = T, canRobCompress = T), 293 SEXT_H -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.alu, ALUOpType.sexth , SelImm.X , xWen = T, canRobCompress = T), 294 // zext.h in rv64 is shared with packw in Zbkb with rs2 = $0. 295 // If we configured to have no Zbkb, we should add zext.h here. 296 297 ROL -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.rol , SelImm.X , xWen = T, canRobCompress = T), 298 ROLW -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.rolw , SelImm.X , xWen = T, canRobCompress = T), 299 ROR -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.ror , SelImm.X , xWen = T, canRobCompress = T), 300 RORI -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.ror , SelImm.IMM_I, xWen = T, canRobCompress = T), 301 RORIW -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.rorw , SelImm.IMM_I, xWen = T, canRobCompress = T), 302 RORW -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.rorw , SelImm.X , xWen = T, canRobCompress = T), 303 304 ORC_B -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.alu, ALUOpType.orcb , SelImm.X , xWen = T, canRobCompress = T), 305 306 REV8 -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.alu, ALUOpType.rev8 , SelImm.X , xWen = T, canRobCompress = T), 307 308 // Zbc 309 CLMUL -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.bku, BKUOpType.clmul , SelImm.X , xWen = T, canRobCompress = T), 310 CLMULH -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.bku, BKUOpType.clmulh , SelImm.X , xWen = T, canRobCompress = T), 311 CLMULR -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.bku, BKUOpType.clmulr , SelImm.X , xWen = T, canRobCompress = T), 312 313 // Zbs 314 BCLR -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.bclr , SelImm.X , xWen = T, canRobCompress = T), 315 BCLRI -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.bclr , SelImm.IMM_I, xWen = T, canRobCompress = T), 316 BEXT -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.bext , SelImm.X , xWen = T, canRobCompress = T), 317 BEXTI -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.bext , SelImm.IMM_I, xWen = T, canRobCompress = T), 318 BINV -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.binv , SelImm.X , xWen = T, canRobCompress = T), 319 BINVI -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.binv , SelImm.IMM_I, xWen = T, canRobCompress = T), 320 BSET -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.bset , SelImm.X , xWen = T, canRobCompress = T), 321 BSETI -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.bset , SelImm.IMM_I, xWen = T, canRobCompress = T), 322 323 // Zbkb 324 // rol, rolw, ror,rori, roriw, rorw, andn, orn, xnor, rev8 is in Zbb 325 PACK -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.pack , SelImm.X , xWen = T, canRobCompress = T), 326 PACKH -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.packh , SelImm.X , xWen = T, canRobCompress = T), 327 PACKW -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.packw , SelImm.X , xWen = T, canRobCompress = T), 328 BREV8 -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.alu, ALUOpType.revb , SelImm.X , xWen = T, canRobCompress = T), 329 // If configured to RV32, we should add zip and unzip. 330 331 // Zbkc 332 // clmul, clmulh is in Zbc 333 334 // Zbkx 335 XPERM4 -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.bku, BKUOpType.xpermn , SelImm.X , xWen = T, canRobCompress = T), 336 XPERM8 -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.bku, BKUOpType.xpermb , SelImm.X , xWen = T, canRobCompress = T), 337 ) 338} 339 340object ScalarCryptoDecode extends DecodeConstants { 341 val decodeArray: Array[(BitPat, XSDecodeBase)] = Array( 342 // Zknd: NIST Suite: AES Decryption 343 AES64DS -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.bku, BKUOpType.aes64ds , SelImm.X , xWen = T, canRobCompress = T), 344 AES64DSM -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.bku, BKUOpType.aes64dsm , SelImm.X , xWen = T, canRobCompress = T), 345 AES64IM -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.bku, BKUOpType.aes64im , SelImm.X , xWen = T, canRobCompress = T), 346 AES64KS1I -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.bku, BKUOpType.aes64ks1i , SelImm.IMM_I, xWen = T, canRobCompress = T), 347 AES64KS2 -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.bku, BKUOpType.aes64ks2 , SelImm.X , xWen = T, canRobCompress = T), 348 349 // Zkne: NIST Suite: AES Encryption 350 // aes64ks1i, aes64ks2 is in Zknd 351 AES64ES -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.bku, BKUOpType.aes64es , SelImm.X , xWen = T, canRobCompress = T), 352 AES64ESM -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.bku, BKUOpType.aes64esm , SelImm.X , xWen = T, canRobCompress = T), 353 354 // Zknh: NIST Suite: Hash Function Instructions 355 SHA256SIG0 -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.bku, BKUOpType.sha256sig0, SelImm.X , xWen = T, canRobCompress = T), 356 SHA256SIG1 -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.bku, BKUOpType.sha256sig1, SelImm.X , xWen = T, canRobCompress = T), 357 SHA256SUM0 -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.bku, BKUOpType.sha256sum0, SelImm.X , xWen = T, canRobCompress = T), 358 SHA256SUM1 -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.bku, BKUOpType.sha256sum1, SelImm.X , xWen = T, canRobCompress = T), 359 SHA512SIG0 -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.bku, BKUOpType.sha512sig0, SelImm.X , xWen = T, canRobCompress = T), 360 SHA512SIG1 -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.bku, BKUOpType.sha512sig1, SelImm.X , xWen = T, canRobCompress = T), 361 SHA512SUM0 -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.bku, BKUOpType.sha512sum0, SelImm.X , xWen = T, canRobCompress = T), 362 SHA512SUM1 -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.bku, BKUOpType.sha512sum1, SelImm.X , xWen = T, canRobCompress = T), 363 364 // Zksed: ShangMi Suite: SM4 Block Cipher Instructions 365 SM4ED0 -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.bku, BKUOpType.sm4ed0 , SelImm.X , xWen = T, canRobCompress = T), 366 SM4ED1 -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.bku, BKUOpType.sm4ed1 , SelImm.X , xWen = T, canRobCompress = T), 367 SM4ED2 -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.bku, BKUOpType.sm4ed2 , SelImm.X , xWen = T, canRobCompress = T), 368 SM4ED3 -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.bku, BKUOpType.sm4ed3 , SelImm.X , xWen = T, canRobCompress = T), 369 SM4KS0 -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.bku, BKUOpType.sm4ks0 , SelImm.X , xWen = T, canRobCompress = T), 370 SM4KS1 -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.bku, BKUOpType.sm4ks1 , SelImm.X , xWen = T, canRobCompress = T), 371 SM4KS2 -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.bku, BKUOpType.sm4ks2 , SelImm.X , xWen = T, canRobCompress = T), 372 SM4KS3 -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.bku, BKUOpType.sm4ks3 , SelImm.X , xWen = T, canRobCompress = T), 373 374 // Zksh: ShangMi Suite: SM3 Hash Function Instructions 375 SM3P0 -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.bku, BKUOpType.sm3p0 , SelImm.X , xWen = T, canRobCompress = T), 376 SM3P1 -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.bku, BKUOpType.sm3p1 , SelImm.X , xWen = T, canRobCompress = T), 377 ) 378} 379 380/** 381 * FP Decode constants 382 */ 383object FpDecode extends DecodeConstants{ 384 val decodeArray: Array[(BitPat, XSDecodeBase)] = Array( 385 FLH -> FDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.ldu, LSUOpType.lh, selImm = SelImm.IMM_I, fWen = T), 386 FLW -> FDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.ldu, LSUOpType.lw, selImm = SelImm.IMM_I, fWen = T), 387 FLD -> FDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.ldu, LSUOpType.ld, selImm = SelImm.IMM_I, fWen = T), 388 FSH -> FDecode(SrcType.reg, SrcType.fp, SrcType.X, FuType.stu, LSUOpType.sh, selImm = SelImm.IMM_S ), 389 FSW -> FDecode(SrcType.reg, SrcType.fp, SrcType.X, FuType.stu, LSUOpType.sw, selImm = SelImm.IMM_S ), 390 FSD -> FDecode(SrcType.reg, SrcType.fp, SrcType.X, FuType.stu, LSUOpType.sd, selImm = SelImm.IMM_S ), 391 392 FMV_D_X -> FDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.i2v, IF2VectorType.FMX_D_X, fWen = T, canRobCompress = T), 393 FMV_W_X -> FDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.i2v, IF2VectorType.FMX_W_X, fWen = T, canRobCompress = T), 394 FMV_H_X -> FDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.i2v, IF2VectorType.FMX_H_X, fWen = T, canRobCompress = T), 395 396 // Int to FP 397 FCVT_S_W -> FDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.i2f, FuOpType.X, fWen = T, canRobCompress = T), 398 FCVT_S_WU -> FDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.i2f, FuOpType.X, fWen = T, canRobCompress = T), 399 FCVT_S_L -> FDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.i2f, FuOpType.X, fWen = T, canRobCompress = T), 400 FCVT_S_LU -> FDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.i2f, FuOpType.X, fWen = T, canRobCompress = T), 401 402 FCVT_D_W -> FDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.i2f, FuOpType.X, fWen = T, canRobCompress = T), 403 FCVT_D_WU -> FDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.i2f, FuOpType.X, fWen = T, canRobCompress = T), 404 FCVT_D_L -> FDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.i2f, FuOpType.X, fWen = T, canRobCompress = T), 405 FCVT_D_LU -> FDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.i2f, FuOpType.X, fWen = T, canRobCompress = T), 406 407 ) 408} 409 410/** 411 * FP Divide SquareRoot Constants 412 */ 413object FDivSqrtDecode extends DecodeConstants { 414 val decodeArray: Array[(BitPat, XSDecodeBase)] = Array( 415 FDIV_S -> FDecode(SrcType.fp, SrcType.fp, SrcType.X, FuType.fDivSqrt, FuOpType.X, fWen = T, canRobCompress = T), 416 FDIV_D -> FDecode(SrcType.fp, SrcType.fp, SrcType.X, FuType.fDivSqrt, FuOpType.X, fWen = T, canRobCompress = T), 417 FSQRT_S -> FDecode(SrcType.fp, SrcType.imm, SrcType.X, FuType.fDivSqrt, FuOpType.X, fWen = T, canRobCompress = T), 418 FSQRT_D -> FDecode(SrcType.fp, SrcType.imm, SrcType.X, FuType.fDivSqrt, FuOpType.X, fWen = T, canRobCompress = T), 419 ) 420} 421 422/** 423 * Svinval extension Constants 424 */ 425object SvinvalDecode extends DecodeConstants { 426 val decodeArray: Array[(BitPat, XSDecodeBase)] = Array( 427 /* sinval_vma is like sfence.vma , but sinval_vma can be dispatched and issued like normal instructions while sfence.vma 428 * must assure it is the ONLY instrucion executing in backend. 429 */ 430 SINVAL_VMA -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.fence, FenceOpType.sfence, SelImm.X), 431 /* sfecne.w.inval is the begin instrucion of a TLB flush which set *noSpecExec* and *blockBackward* signals 432 * so when it comes to dispatch , it will block all instruction after itself until all instrucions ahead of it in rob commit 433 * then dispatch and issue this instrucion to flush sbuffer to dcache 434 * after this instrucion commits , issue following sinval_vma instructions (out of order) to flush TLB 435 */ 436 SFENCE_W_INVAL -> XSDecode(SrcType.DC, SrcType.DC, SrcType.X, FuType.fence, FenceOpType.nofence, SelImm.X, noSpec = T, blockBack = T), 437 /* sfecne.inval.ir is the end instrucion of a TLB flush which set *noSpecExec* *blockBackward* and *flushPipe* signals 438 * so when it comes to dispatch , it will wait until all sinval_vma ahead of it in rob commit 439 * then dispatch and issue this instrucion 440 * when it commit at the head of rob , flush the pipeline since some instrucions have been fetched to ibuffer using old TLB map 441 */ 442 SFENCE_INVAL_IR -> XSDecode(SrcType.DC, SrcType.DC, SrcType.X, FuType.fence, FenceOpType.nofence, SelImm.X, noSpec = T, blockBack = T, flushPipe = T) 443 /* what is Svinval extension ? 444 * -----> sfecne.w.inval 445 * sfence.vma vpn1 -----> sinval_vma vpn1 446 * sfence.vma vpn2 -----> sinval_vma vpn2 447 * -----> sfecne.inval.ir 448 * 449 * sfence.vma should be executed in-order and it flushes the pipeline after committing 450 * we can parallel sfence instrucions with this extension 451 */ 452 ) 453} 454 455/* 456 * CBO decode 457 */ 458object CBODecode extends DecodeConstants { 459 val decodeArray: Array[(BitPat, XSDecodeBase)] = Array( 460 CBO_ZERO -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.stu, LSUOpType.cbo_zero , SelImm.IMM_S), 461 CBO_CLEAN -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.stu, LSUOpType.cbo_clean, SelImm.IMM_S), 462 CBO_FLUSH -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.stu, LSUOpType.cbo_flush, SelImm.IMM_S), 463 CBO_INVAL -> XSDecode(SrcType.reg, SrcType.DC, SrcType.X, FuType.stu, LSUOpType.cbo_inval, SelImm.IMM_S) 464 ) 465} 466 467/* 468 * Hypervisor decode 469 */ 470object HypervisorDecode extends DecodeConstants { 471 override val decodeArray: Array[(BitPat, XSDecodeBase)] = Array( 472 HFENCE_GVMA -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.fence, FenceOpType.hfence_g, SelImm.X, noSpec = T, blockBack = T, flushPipe = T), 473 HFENCE_VVMA -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.fence, FenceOpType.hfence_v, SelImm.X, noSpec = T, blockBack = T, flushPipe = T), 474 HINVAL_GVMA -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.fence, FenceOpType.hfence_g, SelImm.X), 475 HINVAL_VVMA -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.fence, FenceOpType.hfence_v, SelImm.X), 476 HLV_B -> XSDecode(SrcType.reg, SrcType.X, SrcType.X, FuType.ldu, LSUOpType.hlvb, SelImm.X, xWen = T), 477 HLV_BU -> XSDecode(SrcType.reg, SrcType.X, SrcType.X, FuType.ldu, LSUOpType.hlvbu, SelImm.X, xWen = T), 478 HLV_D -> XSDecode(SrcType.reg, SrcType.X, SrcType.X, FuType.ldu, LSUOpType.hlvd, SelImm.X, xWen = T), 479 HLV_H -> XSDecode(SrcType.reg, SrcType.X, SrcType.X, FuType.ldu, LSUOpType.hlvh, SelImm.X, xWen = T), 480 HLV_HU -> XSDecode(SrcType.reg, SrcType.X, SrcType.X, FuType.ldu, LSUOpType.hlvhu, SelImm.X, xWen = T), 481 HLV_W -> XSDecode(SrcType.reg, SrcType.X, SrcType.X, FuType.ldu, LSUOpType.hlvw, SelImm.X, xWen = T), 482 HLV_WU -> XSDecode(SrcType.reg, SrcType.X, SrcType.X, FuType.ldu, LSUOpType.hlvwu, SelImm.X, xWen = T), 483 HLVX_HU -> XSDecode(SrcType.reg, SrcType.X, SrcType.X, FuType.ldu, LSUOpType.hlvxhu, SelImm.X, xWen = T), 484 HLVX_WU -> XSDecode(SrcType.reg, SrcType.X, SrcType.X, FuType.ldu, LSUOpType.hlvxwu, SelImm.X, xWen = T), 485 HSV_B -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.stu, LSUOpType.hsvb, SelImm.X), 486 HSV_D -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.stu, LSUOpType.hsvd, SelImm.X), 487 HSV_H -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.stu, LSUOpType.hsvh, SelImm.X), 488 HSV_W -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.stu, LSUOpType.hsvw, SelImm.X), 489 ) 490} 491 492object ZicondDecode extends DecodeConstants { 493 override val decodeArray: Array[(BitPat, XSDecodeBase)] = Array( 494 CZERO_EQZ -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.czero_eqz, SelImm.X, xWen = T, canRobCompress = T), 495 CZERO_NEZ -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.czero_nez, SelImm.X, xWen = T, canRobCompress = T), 496 ) 497} 498 499/** 500 * "Zimop" Extension for May-Be-Operations 501 */ 502object ZimopDecode extends DecodeConstants { 503 override val decodeArray: Array[(BitPat, XSDecodeBase)] = Array( 504 // temp use addi to decode MOP_R and MOP_RR 505 MOP_R -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.add, SelImm.IMM_I, xWen = T, canRobCompress = T), 506 MOP_RR -> XSDecode(SrcType.reg, SrcType.reg, SrcType.X, FuType.alu, ALUOpType.add, SelImm.IMM_I, xWen = T, canRobCompress = T), 507 ) 508} 509 510/** 511 * XiangShan Trap Decode constants 512 */ 513object XSTrapDecode extends DecodeConstants { 514 def TRAP = BitPat("b000000000000?????000000001101011") 515 val decodeArray: Array[(BitPat, XSDecodeBase)] = Array( 516 TRAP -> XSDecode(SrcType.reg, SrcType.imm, SrcType.X, FuType.alu, ALUOpType.add, SelImm.IMM_I, xWen = T, xsTrap = T, noSpec = T, blockBack = T) 517 ) 518} 519 520abstract class Imm(val len: Int) { 521 def toImm32(minBits: UInt): UInt = do_toImm32(minBits(len - 1, 0)) 522 def do_toImm32(minBits: UInt): UInt 523 def minBitsFromInstr(instr: UInt): UInt 524} 525 526case class Imm_I() extends Imm(12) { 527 override def do_toImm32(minBits: UInt): UInt = SignExt(minBits(len - 1, 0), 32) 528 529 override def minBitsFromInstr(instr: UInt): UInt = 530 Cat(instr(31, 20)) 531} 532 533case class Imm_S() extends Imm(12) { 534 override def do_toImm32(minBits: UInt): UInt = SignExt(minBits, 32) 535 536 override def minBitsFromInstr(instr: UInt): UInt = 537 Cat(instr(31, 25), instr(11, 7)) 538} 539 540case class Imm_B() extends Imm(12) { 541 override def do_toImm32(minBits: UInt): UInt = SignExt(Cat(minBits, 0.U(1.W)), 32) 542 543 override def minBitsFromInstr(instr: UInt): UInt = 544 Cat(instr(31), instr(7), instr(30, 25), instr(11, 8)) 545} 546 547case class Imm_U() extends Imm(20){ 548 override def do_toImm32(minBits: UInt): UInt = Cat(minBits(len - 1, 0), 0.U(12.W)) 549 550 override def minBitsFromInstr(instr: UInt): UInt = { 551 instr(31, 12) 552 } 553} 554 555case class Imm_J() extends Imm(20){ 556 override def do_toImm32(minBits: UInt): UInt = SignExt(Cat(minBits, 0.U(1.W)), 32) 557 558 override def minBitsFromInstr(instr: UInt): UInt = { 559 Cat(instr(31), instr(19, 12), instr(20), instr(30, 25), instr(24, 21)) 560 } 561} 562 563case class Imm_Z() extends Imm(12 + 5 + 5){ 564 override def do_toImm32(minBits: UInt): UInt = minBits 565 566 override def minBitsFromInstr(instr: UInt): UInt = { 567 Cat(instr(11, 7), instr(19, 15), instr(31, 20)) 568 } 569 570 def getCSRAddr(imm: UInt): UInt = { 571 require(imm.getWidth == this.len) 572 imm(11, 0) 573 } 574 575 def getRS1(imm: UInt): UInt = { 576 require(imm.getWidth == this.len) 577 imm(16, 12) 578 } 579 580 def getRD(imm: UInt): UInt = { 581 require(imm.getWidth == this.len) 582 imm(21, 17) 583 } 584 585 def getImm5(imm: UInt): UInt = { 586 require(imm.getWidth == this.len) 587 imm(16, 12) 588 } 589} 590 591case class Imm_B6() extends Imm(6){ 592 override def do_toImm32(minBits: UInt): UInt = ZeroExt(minBits, 32) 593 594 override def minBitsFromInstr(instr: UInt): UInt = { 595 instr(25, 20) 596 } 597} 598 599case class Imm_OPIVIS() extends Imm(5){ 600 override def do_toImm32(minBits: UInt): UInt = SignExt(minBits, 32) 601 602 override def minBitsFromInstr(instr: UInt): UInt = { 603 instr(19, 15) 604 } 605} 606 607case class Imm_OPIVIU() extends Imm(5){ 608 override def do_toImm32(minBits: UInt): UInt = ZeroExt(minBits, 32) 609 610 override def minBitsFromInstr(instr: UInt): UInt = { 611 instr(19, 15) 612 } 613} 614 615case class Imm_VSETVLI() extends Imm(11){ 616 override def do_toImm32(minBits: UInt): UInt = SignExt(minBits, 32) 617 618 override def minBitsFromInstr(instr: UInt): UInt = { 619 instr(30, 20) 620 } 621 /** 622 * get VType from extended imm 623 * @param extedImm 624 * @return VType 625 */ 626 def getVType(extedImm: UInt): InstVType = { 627 val vtype = Wire(new InstVType) 628 vtype := extedImm(10, 0).asTypeOf(new InstVType) 629 vtype 630 } 631} 632 633case class Imm_VSETIVLI() extends Imm(15){ 634 override def do_toImm32(minBits: UInt): UInt = SignExt(minBits, 32) 635 636 override def minBitsFromInstr(instr: UInt): UInt = { 637 val rvInst: XSInstBitFields = instr.asTypeOf(new XSInstBitFields) 638 val uimm5 = rvInst.UIMM_VSETIVLI 639 val vtype8 = rvInst.ZIMM_VSETIVLI 640 Cat(uimm5, vtype8) 641 } 642 /** 643 * get VType from extended imm 644 * @param extedImm 645 * @return VType 646 */ 647 def getVType(extedImm: UInt): InstVType = { 648 val vtype = Wire(new InstVType) 649 vtype := extedImm(9, 0).asTypeOf(new InstVType) 650 vtype 651 } 652 653 def getAvl(extedImm: UInt): UInt = { 654 extedImm(14, 10) 655 } 656} 657 658case class Imm_LUI32() extends Imm(32){ 659 override def do_toImm32(minBits: UInt): UInt = minBits(31, 0) 660 661 override def minBitsFromInstr(instr: UInt): UInt = { 662 instr(31, 0) 663 } 664} 665 666case class Imm_VRORVI() extends Imm(6){ 667 override def do_toImm32(minBits: UInt): UInt = ZeroExt(minBits, 32) 668 669 override def minBitsFromInstr(instr: UInt): UInt = { 670 Cat(instr(26), instr(19, 15)) 671 } 672} 673 674object ImmUnion { 675 val I = Imm_I() 676 val S = Imm_S() 677 val B = Imm_B() 678 val U = Imm_U() 679 val J = Imm_J() 680 val Z = Imm_Z() 681 val B6 = Imm_B6() 682 val OPIVIS = Imm_OPIVIS() 683 val OPIVIU = Imm_OPIVIU() 684 val VSETVLI = Imm_VSETVLI() 685 val VSETIVLI = Imm_VSETIVLI() 686 val LUI32 = Imm_LUI32() 687 val VRORVI = Imm_VRORVI() 688 689 // do not add special type lui32 to this, keep ImmUnion max len being 20. 690 val imms = Seq(I, S, B, U, J, Z, B6, OPIVIS, OPIVIU, VSETVLI, VSETIVLI, VRORVI) 691 val maxLen = imms.maxBy(_.len).len 692 val immSelMap = Seq( 693 SelImm.IMM_I, 694 SelImm.IMM_S, 695 SelImm.IMM_SB, 696 SelImm.IMM_U, 697 SelImm.IMM_UJ, 698 SelImm.IMM_Z, 699 SelImm.IMM_B6, 700 SelImm.IMM_OPIVIS, 701 SelImm.IMM_OPIVIU, 702 SelImm.IMM_VSETVLI, 703 SelImm.IMM_VSETIVLI, 704 SelImm.IMM_VRORVI, 705 ).zip(imms) 706 println(s"ImmUnion max len: $maxLen") 707} 708 709case class Imm_LUI_LOAD() { 710 def immFromLuiLoad(lui_imm: UInt, load_imm: UInt): UInt = { 711 val loadImm = load_imm(Imm_I().len - 1, 0) 712 Cat(lui_imm(ImmUnion.maxLen - loadImm.getWidth - 1, 0), loadImm) 713 } 714 def getLuiImm(uop: DynInst): UInt = { 715 val loadImmLen = Imm_I().len 716 val imm_u = Cat(uop.psrc(1), uop.psrc(0), uop.imm(ImmUnion.maxLen - 1, loadImmLen)) 717 Cat(Imm_U().toImm32(imm_u)(31, loadImmLen), uop.imm(loadImmLen - 1, 0)) 718 } 719} 720 721/** 722 * IO bundle for the Decode unit 723 */ 724class DecodeUnitDeqIO(implicit p: Parameters) extends XSBundle { 725 val decodedInst = Output(new DecodedInst) 726 val isComplex = Output(Bool()) 727 val uopInfo = Output(new UopInfo) 728} 729class DecodeUnitIO(implicit p: Parameters) extends XSBundle { 730 val enq = new Bundle { 731 val ctrlFlow = Input(new StaticInst) 732 val vtype = Input(new VType) 733 val vstart = Input(Vl()) 734 } 735// val vconfig = Input(UInt(XLEN.W)) 736 val deq = new DecodeUnitDeqIO 737 val csrCtrl = Input(new CustomCSRCtrlIO) 738 val fromCSR = Input(new CSRToDecode) 739} 740 741/** 742 * Decode unit that takes in a single CtrlFlow and generates a CfCtrl. 743 */ 744class DecodeUnit(implicit p: Parameters) extends XSModule with DecodeUnitConstants { 745 val io = IO(new DecodeUnitIO) 746 747 val ctrl_flow = io.enq.ctrlFlow // input with RVC Expanded 748 749 private val inst: XSInstBitFields = io.enq.ctrlFlow.instr.asTypeOf(new XSInstBitFields) 750 751 val decode_table: Array[(BitPat, List[BitPat])] = XDecode.table ++ 752 FpDecode.table ++ 753// FDivSqrtDecode.table ++ 754 BitmanipDecode.table ++ 755 ScalarCryptoDecode.table ++ 756 XSTrapDecode.table ++ 757 CBODecode.table ++ 758 SvinvalDecode.table ++ 759 HypervisorDecode.table ++ 760 VecDecoder.table ++ 761 ZicondDecode.table ++ 762 ZimopDecode.table 763 764 require(decode_table.map(_._2.length == 15).reduce(_ && _), "Decode tables have different column size") 765 // assertion for LUI: only LUI should be assigned `selImm === SelImm.IMM_U && fuType === FuType.alu` 766 val luiMatch = (t: Seq[BitPat]) => t(3).value == FuType.alu.ohid && t.reverse.head.value == SelImm.IMM_U.litValue 767 val luiTable = decode_table.filter(t => luiMatch(t._2)).map(_._1).distinct 768 assert(luiTable.length == 1 && luiTable.head == LUI, "Conflicts: LUI is determined by FuType and SelImm in Dispatch") 769 770 // output 771 val decodedInst: DecodedInst = Wire(new DecodedInst()).decode(ctrl_flow.instr, decode_table) 772 773 val fpDecoder = Module(new FPDecoder) 774 fpDecoder.io.instr := ctrl_flow.instr 775 decodedInst.fpu := fpDecoder.io.fpCtrl 776 decodedInst.fpu.wflags := fpDecoder.io.fpCtrl.wflags || decodedInst.wfflags 777 778 decodedInst.connectStaticInst(io.enq.ctrlFlow) 779 780 decodedInst.uopIdx := 0.U 781 decodedInst.firstUop := true.B 782 decodedInst.lastUop := true.B 783 decodedInst.numUops := 1.U 784 decodedInst.numWB := 1.U 785 786 val isZimop = (BitPat("b1?00??0111??_?????_100_?????_1110011") === ctrl_flow.instr) || 787 (BitPat("b1?00??1?????_?????_100_?????_1110011") === ctrl_flow.instr) 788 789 val isMove = BitPat("b000000000000_?????_000_?????_0010011") === ctrl_flow.instr 790 // temp decode zimop as move 791 decodedInst.isMove := (isMove || isZimop) && ctrl_flow.instr(RD_MSB, RD_LSB) =/= 0.U && !io.csrCtrl.singlestep 792 793 // fmadd - b1000011 794 // fmsub - b1000111 795 // fnmsub- b1001011 796 // fnmadd- b1001111 797 private val isFMA = inst.OPCODE === BitPat("b100??11") 798 private val isVppu = FuType.isVppu(decodedInst.fuType) 799 private val isVecOPF = FuType.isVecOPF(decodedInst.fuType) 800 801 // read src1~3 location 802 decodedInst.lsrc(0) := inst.RS1 803 decodedInst.lsrc(1) := inst.RS2 804 // src(2) of fma is fs3, src(2) of vector inst is old vd 805 decodedInst.lsrc(2) := Mux(isFMA, inst.FS3, inst.VD) 806 decodedInst.lsrc(3) := V0_IDX.U 807 decodedInst.lsrc(4) := Vl_IDX.U 808 809 // read dest location 810 decodedInst.ldest := inst.RD 811 812 // init v0Wen vlWen 813 decodedInst.v0Wen := false.B 814 decodedInst.vlWen := false.B 815 816 // fill in exception vector 817 val vecException = Module(new VecExceptionGen) 818 vecException.io.inst := io.enq.ctrlFlow.instr 819 vecException.io.decodedInst := decodedInst 820 vecException.io.vtype := decodedInst.vpu.vtype 821 vecException.io.vstart := decodedInst.vpu.vstart 822 823 private val exceptionII = 824 decodedInst.selImm === SelImm.INVALID_INSTR || 825 vecException.io.illegalInst || 826 io.fromCSR.illegalInst.sfenceVMA && FuType.FuTypeOrR(decodedInst.fuType, FuType.fence) && decodedInst.fuOpType === FenceOpType.sfence || 827 io.fromCSR.illegalInst.sfencePart && FuType.FuTypeOrR(decodedInst.fuType, FuType.fence) && decodedInst.fuOpType === FenceOpType.nofence || 828 io.fromCSR.illegalInst.hfenceGVMA && FuType.FuTypeOrR(decodedInst.fuType, FuType.fence) && decodedInst.fuOpType === FenceOpType.hfence_g || 829 io.fromCSR.illegalInst.hfenceVVMA && FuType.FuTypeOrR(decodedInst.fuType, FuType.fence) && decodedInst.fuOpType === FenceOpType.hfence_v || 830 io.fromCSR.illegalInst.hlsv && FuType.FuTypeOrR(decodedInst.fuType, FuType.ldu) && (LSUOpType.isHlv(decodedInst.fuOpType) || LSUOpType.isHlvx(decodedInst.fuOpType)) || 831 io.fromCSR.illegalInst.hlsv && FuType.FuTypeOrR(decodedInst.fuType, FuType.stu) && LSUOpType.isHsv(decodedInst.fuOpType) || 832 io.fromCSR.illegalInst.fsIsOff && (FuType.FuTypeOrR(decodedInst.fuType, FuType.fpOP ++ Seq(FuType.f2v)) || 833 (FuType.FuTypeOrR(decodedInst.fuType, FuType.ldu) && (decodedInst.fuOpType === LSUOpType.lw || decodedInst.fuOpType === LSUOpType.ld) || 834 FuType.FuTypeOrR(decodedInst.fuType, FuType.stu) && (decodedInst.fuOpType === LSUOpType.sw || decodedInst.fuOpType === LSUOpType.sd)) && decodedInst.instr(2) || 835 isVecOPF) || 836 io.fromCSR.illegalInst.vsIsOff && FuType.FuTypeOrR(decodedInst.fuType, FuType.vecAll) || 837 io.fromCSR.illegalInst.wfi && FuType.FuTypeOrR(decodedInst.fuType, FuType.csr) && CSROpType.isWfi(decodedInst.fuOpType) || 838 (decodedInst.needFrm.scalaNeedFrm || FuType.isScalaNeedFrm(decodedInst.fuType)) && (((decodedInst.fpu.rm === 5.U) || (decodedInst.fpu.rm === 6.U)) || ((decodedInst.fpu.rm === 7.U) && io.fromCSR.illegalInst.frm)) || 839 (decodedInst.needFrm.vectorNeedFrm || FuType.isVectorNeedFrm(decodedInst.fuType)) && io.fromCSR.illegalInst.frm 840 841 private val exceptionVI = 842 io.fromCSR.virtualInst.sfenceVMA && FuType.FuTypeOrR(decodedInst.fuType, FuType.fence) && decodedInst.fuOpType === FenceOpType.sfence || 843 io.fromCSR.virtualInst.sfencePart && FuType.FuTypeOrR(decodedInst.fuType, FuType.fence) && decodedInst.fuOpType === FenceOpType.nofence || 844 io.fromCSR.virtualInst.hfence && FuType.FuTypeOrR(decodedInst.fuType, FuType.fence) && (decodedInst.fuOpType === FenceOpType.hfence_g || decodedInst.fuOpType === FenceOpType.hfence_v) || 845 io.fromCSR.virtualInst.hlsv && FuType.FuTypeOrR(decodedInst.fuType, FuType.ldu) && (LSUOpType.isHlv(decodedInst.fuOpType) || LSUOpType.isHlvx(decodedInst.fuOpType)) || 846 io.fromCSR.virtualInst.hlsv && FuType.FuTypeOrR(decodedInst.fuType, FuType.stu) && LSUOpType.isHsv(decodedInst.fuOpType) || 847 io.fromCSR.virtualInst.wfi && FuType.FuTypeOrR(decodedInst.fuType, FuType.csr) && CSROpType.isWfi(decodedInst.fuOpType) 848 849 decodedInst.exceptionVec(illegalInstr) := exceptionII || io.enq.ctrlFlow.exceptionVec(EX_II) 850 decodedInst.exceptionVec(virtualInstr) := exceptionVI 851 852 //update exceptionVec: from frontend trigger's breakpoint exception. To reduce 1 bit of overhead in ibuffer entry. 853 decodedInst.exceptionVec(breakPoint) := TriggerAction.isExp(ctrl_flow.trigger) 854 855 decodedInst.imm := LookupTree(decodedInst.selImm, ImmUnion.immSelMap.map( 856 x => { 857 val minBits = x._2.minBitsFromInstr(ctrl_flow.instr) 858 require(minBits.getWidth == x._2.len) 859 x._1 -> minBits 860 } 861 )) 862 863 private val isLs = FuType.isLoadStore(decodedInst.fuType) 864 private val isVls = FuType.isVls(decodedInst.fuType) 865 private val isStore = FuType.isStore(decodedInst.fuType) 866 private val isAMO = FuType.isAMO(decodedInst.fuType) 867 private val isVStore = FuType.isVStore(decodedInst.fuType) 868 private val isBranch = !decodedInst.preDecodeInfo.notCFI || FuType.isJump(decodedInst.fuType) 869 870 decodedInst.commitType := Cat(isLs | isVls, (isStore && !isAMO) | isVStore | isBranch) 871 872 decodedInst.isVset := FuType.isVset(decodedInst.fuType) 873 874 private val needReverseInsts = Seq(VRSUB_VI, VRSUB_VX, VFRDIV_VF, VFRSUB_VF, VFMV_F_S) 875 private val vextInsts = Seq(VZEXT_VF2, VZEXT_VF4, VZEXT_VF8, VSEXT_VF2, VSEXT_VF4, VSEXT_VF8) 876 private val narrowInsts = Seq( 877 VNSRA_WV, VNSRA_WX, VNSRA_WI, VNSRL_WV, VNSRL_WX, VNSRL_WI, 878 VNCLIP_WV, VNCLIP_WX, VNCLIP_WI, VNCLIPU_WV, VNCLIPU_WX, VNCLIPU_WI, 879 ) 880 private val maskDstInsts = Seq( 881 VMADC_VV, VMADC_VX, VMADC_VI, VMADC_VVM, VMADC_VXM, VMADC_VIM, 882 VMSBC_VV, VMSBC_VX, VMSBC_VVM, VMSBC_VXM, 883 VMAND_MM, VMNAND_MM, VMANDN_MM, VMXOR_MM, VMOR_MM, VMNOR_MM, VMORN_MM, VMXNOR_MM, 884 VMSEQ_VV, VMSEQ_VX, VMSEQ_VI, VMSNE_VV, VMSNE_VX, VMSNE_VI, 885 VMSLE_VV, VMSLE_VX, VMSLE_VI, VMSLEU_VV, VMSLEU_VX, VMSLEU_VI, 886 VMSLT_VV, VMSLT_VX, VMSLTU_VV, VMSLTU_VX, 887 VMSGT_VX, VMSGT_VI, VMSGTU_VX, VMSGTU_VI, 888 VMFEQ_VV, VMFEQ_VF, VMFNE_VV, VMFNE_VF, VMFLT_VV, VMFLT_VF, VMFLE_VV, VMFLE_VF, VMFGT_VF, VMFGE_VF, 889 ) 890 private val maskOpInsts = Seq( 891 VMAND_MM, VMNAND_MM, VMANDN_MM, VMXOR_MM, VMOR_MM, VMNOR_MM, VMORN_MM, VMXNOR_MM, 892 ) 893 private val vmaInsts = Seq( 894 VMACC_VV, VMACC_VX, VNMSAC_VV, VNMSAC_VX, VMADD_VV, VMADD_VX, VNMSUB_VV, VNMSUB_VX, 895 VWMACCU_VV, VWMACCU_VX, VWMACC_VV, VWMACC_VX, VWMACCSU_VV, VWMACCSU_VX, VWMACCUS_VX, 896 ) 897 private val wfflagsInsts = Seq( 898 // opfff 899 FADD_S, FSUB_S, FADD_D, FSUB_D, 900 FEQ_S, FLT_S, FLE_S, FEQ_D, FLT_D, FLE_D, 901 FMIN_S, FMAX_S, FMIN_D, FMAX_D, 902 FMUL_S, FMUL_D, 903 FDIV_S, FDIV_D, FSQRT_S, FSQRT_D, 904 FMADD_S, FMSUB_S, FNMADD_S, FNMSUB_S, FMADD_D, FMSUB_D, FNMADD_D, FNMSUB_D, 905 FSGNJ_S, FSGNJN_S, FSGNJX_S, 906 // opfvv 907 VFADD_VV, VFSUB_VV, VFWADD_VV, VFWSUB_VV, VFWADD_WV, VFWSUB_WV, 908 VFMUL_VV, VFDIV_VV, VFWMUL_VV, 909 VFMACC_VV, VFNMACC_VV, VFMSAC_VV, VFNMSAC_VV, VFMADD_VV, VFNMADD_VV, VFMSUB_VV, VFNMSUB_VV, 910 VFWMACC_VV, VFWNMACC_VV, VFWMSAC_VV, VFWNMSAC_VV, 911 VFSQRT_V, 912 VFMIN_VV, VFMAX_VV, 913 VMFEQ_VV, VMFNE_VV, VMFLT_VV, VMFLE_VV, 914 VFSGNJ_VV, VFSGNJN_VV, VFSGNJX_VV, 915 // opfvf 916 VFADD_VF, VFSUB_VF, VFRSUB_VF, VFWADD_VF, VFWSUB_VF, VFWADD_WF, VFWSUB_WF, 917 VFMUL_VF, VFDIV_VF, VFRDIV_VF, VFWMUL_VF, 918 VFMACC_VF, VFNMACC_VF, VFMSAC_VF, VFNMSAC_VF, VFMADD_VF, VFNMADD_VF, VFMSUB_VF, VFNMSUB_VF, 919 VFWMACC_VF, VFWNMACC_VF, VFWMSAC_VF, VFWNMSAC_VF, 920 VFMIN_VF, VFMAX_VF, 921 VMFEQ_VF, VMFNE_VF, VMFLT_VF, VMFLE_VF, VMFGT_VF, VMFGE_VF, 922 VFSGNJ_VF, VFSGNJN_VF, VFSGNJX_VF, 923 // vfred 924 VFREDOSUM_VS, VFREDUSUM_VS, VFREDMAX_VS, VFREDMIN_VS, VFWREDOSUM_VS, VFWREDUSUM_VS, 925 // fcvt & vfcvt 926 FCVT_S_W, FCVT_S_WU, FCVT_S_L, FCVT_S_LU, 927 FCVT_W_S, FCVT_WU_S, FCVT_L_S, FCVT_LU_S, 928 FCVT_D_W, FCVT_D_WU, FCVT_D_L, FCVT_D_LU, 929 FCVT_W_D, FCVT_WU_D, FCVT_L_D, FCVT_LU_D, FCVT_S_D, FCVT_D_S, 930 FCVT_S_H, FCVT_H_S, FCVT_H_D, FCVT_D_H, 931 VFCVT_XU_F_V, VFCVT_X_F_V, VFCVT_RTZ_XU_F_V, VFCVT_RTZ_X_F_V, VFCVT_F_XU_V, VFCVT_F_X_V, 932 VFWCVT_XU_F_V, VFWCVT_X_F_V, VFWCVT_RTZ_XU_F_V, VFWCVT_RTZ_X_F_V, VFWCVT_F_XU_V, VFWCVT_F_X_V, VFWCVT_F_F_V, 933 VFNCVT_XU_F_W, VFNCVT_X_F_W, VFNCVT_RTZ_XU_F_W, VFNCVT_RTZ_X_F_W, VFNCVT_F_XU_W, VFNCVT_F_X_W, VFNCVT_F_F_W, 934 VFNCVT_ROD_F_F_W, VFRSQRT7_V, VFREC7_V, 935 ) 936 937 private val scalaNeedFrmInsts = Seq( 938 FADD_S, FSUB_S, FADD_D, FSUB_D, 939 FCVT_W_S, FCVT_WU_S, FCVT_L_S, FCVT_LU_S, 940 FCVT_W_D, FCVT_WU_D, FCVT_L_D, FCVT_LU_D, FCVT_S_D, FCVT_D_S, 941 ) 942 943 private val vectorNeedFrmInsts = Seq ( 944 VFSLIDE1UP_VF, VFSLIDE1DOWN_VF, 945 ) 946 947 decodedInst.wfflags := wfflagsInsts.map(_ === inst.ALL).reduce(_ || _) 948 decodedInst.needFrm.scalaNeedFrm := scalaNeedFrmInsts.map(_ === inst.ALL).reduce(_ || _) 949 decodedInst.needFrm.vectorNeedFrm := vectorNeedFrmInsts.map(_ === inst.ALL).reduce(_ || _) 950 val fpToVecDecoder = Module(new FPToVecDecoder()) 951 fpToVecDecoder.io.instr := inst.asUInt 952 val isFpToVecInst = fpToVecDecoder.io.vpuCtrl.fpu.isFpToVecInst 953 decodedInst.vpu := 0.U.asTypeOf(decodedInst.vpu) // Todo: Connect vpu decoder 954 when(isFpToVecInst){ 955 decodedInst.vpu := fpToVecDecoder.io.vpuCtrl 956 }.otherwise{ 957 decodedInst.vpu.vill := io.enq.vtype.illegal 958 decodedInst.vpu.vma := io.enq.vtype.vma 959 decodedInst.vpu.vta := io.enq.vtype.vta 960 decodedInst.vpu.vsew := io.enq.vtype.vsew 961 decodedInst.vpu.vlmul := io.enq.vtype.vlmul 962 decodedInst.vpu.vm := inst.VM 963 decodedInst.vpu.nf := inst.NF 964 decodedInst.vpu.veew := inst.WIDTH 965 decodedInst.vpu.isReverse := needReverseInsts.map(_ === inst.ALL).reduce(_ || _) 966 decodedInst.vpu.isExt := vextInsts.map(_ === inst.ALL).reduce(_ || _) 967 val isNarrow = narrowInsts.map(_ === inst.ALL).reduce(_ || _) 968 val isDstMask = maskDstInsts.map(_ === inst.ALL).reduce(_ || _) 969 val isOpMask = maskOpInsts.map(_ === inst.ALL).reduce(_ || _) 970 val isVlx = decodedInst.fuOpType === VlduType.vloxe || decodedInst.fuOpType === VlduType.vluxe 971 val isVle = decodedInst.fuOpType === VlduType.vle || decodedInst.fuOpType === VlduType.vleff || decodedInst.fuOpType === VlduType.vlse 972 val isVlm = decodedInst.fuOpType === VlduType.vlm 973 val isWritePartVd = decodedInst.uopSplitType === UopSplitType.VEC_VRED || decodedInst.uopSplitType === UopSplitType.VEC_0XV 974 val isVma = vmaInsts.map(_ === inst.ALL).reduce(_ || _) 975 val emulIsFrac = Cat(~decodedInst.vpu.vlmul(2), decodedInst.vpu.vlmul(1, 0)) +& decodedInst.vpu.veew < 4.U +& decodedInst.vpu.vsew 976 decodedInst.vpu.isNarrow := isNarrow 977 decodedInst.vpu.isDstMask := isDstMask 978 decodedInst.vpu.isOpMask := isOpMask 979 decodedInst.vpu.isDependOldvd := isVppu || isVecOPF || isVStore || (isDstMask && !isOpMask) || isNarrow || isVlx || isVma 980 decodedInst.vpu.isWritePartVd := isWritePartVd || isVlm || isVle && emulIsFrac 981 decodedInst.vpu.vstart := io.enq.vstart 982 } 983 decodedInst.vpu.specVill := io.enq.vtype.illegal 984 decodedInst.vpu.specVma := io.enq.vtype.vma 985 decodedInst.vpu.specVta := io.enq.vtype.vta 986 decodedInst.vpu.specVsew := io.enq.vtype.vsew 987 decodedInst.vpu.specVlmul := io.enq.vtype.vlmul 988 989 decodedInst.vlsInstr := isVls 990 991 decodedInst.srcType(3) := Mux(inst.VM === 0.U && !isFpToVecInst, SrcType.vp, SrcType.DC) // mask src 992 decodedInst.srcType(4) := Mux(!isFpToVecInst, SrcType.vp, SrcType.DC) // vconfig 993 994 val uopInfoGen = Module(new UopInfoGen) 995 uopInfoGen.io.in.preInfo.typeOfSplit := decodedInst.uopSplitType 996 uopInfoGen.io.in.preInfo.vsew := decodedInst.vpu.vsew 997 uopInfoGen.io.in.preInfo.vlmul := decodedInst.vpu.vlmul 998 uopInfoGen.io.in.preInfo.vwidth := inst.RM 999 uopInfoGen.io.in.preInfo.vmvn := inst.IMM5_OPIVI(2, 0) 1000 uopInfoGen.io.in.preInfo.nf := inst.NF 1001 uopInfoGen.io.in.preInfo.isVlsr := decodedInst.fuOpType === VlduType.vlr || decodedInst.fuOpType === VstuType.vsr 1002 uopInfoGen.io.in.preInfo.isVlsm := decodedInst.fuOpType === VlduType.vlm || decodedInst.fuOpType === VstuType.vsm 1003 io.deq.isComplex := uopInfoGen.io.out.isComplex 1004 // numOfUop should be 1 when vector instruction is illegalInst 1005 io.deq.uopInfo.numOfUop := Mux(vecException.io.illegalInst, 1.U, uopInfoGen.io.out.uopInfo.numOfUop) 1006 io.deq.uopInfo.numOfWB := uopInfoGen.io.out.uopInfo.numOfWB 1007 io.deq.uopInfo.lmul := uopInfoGen.io.out.uopInfo.lmul 1008 1009 val isCSR = inst.OPCODE5Bit === OPCODE5Bit.SYSTEM && inst.FUNCT3(1, 0) =/= 0.U 1010 val isCSRR = isCSR && inst.FUNCT3 === BitPat("b?1?") && inst.RS1 === 0.U 1011 val isCSRW = isCSR && inst.FUNCT3 === BitPat("b?10") && inst.RD === 0.U 1012 dontTouch(isCSRR) 1013 dontTouch(isCSRW) 1014 1015 // for csrr vl instruction, convert to vsetvl 1016 val isCsrrVlenb = isCSRR && inst.CSRIDX === CSRs.vlenb.U 1017 val isCsrrVl = isCSRR && inst.CSRIDX === CSRs.vl.U 1018 1019 // decode for SoftPrefetch instructions (prefetch.w / prefetch.r / prefetch.i) 1020 val isSoftPrefetch = inst.OPCODE === BitPat("b0010011") && inst.FUNCT3 === BitPat("b110") && inst.RD === 0.U 1021 val isPreW = isSoftPrefetch && inst.RS2 === 3.U(5.W) 1022 val isPreR = isSoftPrefetch && inst.RS2 === 1.U(5.W) 1023 val isPreI = isSoftPrefetch && inst.RS2 === 0.U(5.W) 1024 1025 when (isCsrrVl) { 1026 // convert to vsetvl instruction 1027 decodedInst.srcType(0) := SrcType.no 1028 decodedInst.srcType(1) := SrcType.no 1029 decodedInst.srcType(2) := SrcType.no 1030 decodedInst.srcType(3) := SrcType.no 1031 decodedInst.srcType(4) := SrcType.vp 1032 decodedInst.lsrc(4) := Vl_IDX.U 1033 decodedInst.waitForward := false.B 1034 decodedInst.blockBackward := false.B 1035 decodedInst.exceptionVec(illegalInstr) := io.fromCSR.illegalInst.vsIsOff 1036 }.elsewhen (isCsrrVlenb) { 1037 // convert to addi instruction 1038 decodedInst.srcType(0) := SrcType.reg 1039 decodedInst.srcType(1) := SrcType.imm 1040 decodedInst.srcType(2) := SrcType.no 1041 decodedInst.srcType(3) := SrcType.no 1042 decodedInst.srcType(4) := SrcType.no 1043 decodedInst.selImm := SelImm.IMM_I 1044 decodedInst.waitForward := false.B 1045 decodedInst.blockBackward := false.B 1046 decodedInst.canRobCompress := true.B 1047 decodedInst.exceptionVec(illegalInstr) := io.fromCSR.illegalInst.vsIsOff 1048 }.elsewhen (isPreW || isPreR || isPreI) { 1049 decodedInst.selImm := SelImm.IMM_S 1050 decodedInst.fuType := FuType.ldu.U 1051 decodedInst.canRobCompress := false.B 1052 decodedInst.fuOpType := Mux1H(Seq( 1053 isPreW -> LSUOpType.prefetch_w, 1054 isPreR -> LSUOpType.prefetch_r, 1055 isPreI -> LSUOpType.prefetch_i, 1056 )) 1057 }.elsewhen (isZimop) { 1058 // set srcType for zimop 1059 decodedInst.srcType(0) := SrcType.reg 1060 decodedInst.srcType(1) := SrcType.imm 1061 // use x0 as src1 1062 decodedInst.lsrc(0) := 0.U 1063 } 1064 1065 io.deq.decodedInst := decodedInst 1066 io.deq.decodedInst.rfWen := (decodedInst.ldest =/= 0.U) && decodedInst.rfWen 1067 io.deq.decodedInst.fuType := Mux1H(Seq( 1068 // keep condition 1069 (!FuType.FuTypeOrR(decodedInst.fuType, FuType.vldu, FuType.vstu) && !isCsrrVl && !isCsrrVlenb) -> decodedInst.fuType, 1070 (isCsrrVl) -> FuType.vsetfwf.U, 1071 (isCsrrVlenb) -> FuType.alu.U, 1072 1073 // change vlsu to vseglsu when NF =/= 0.U 1074 ( FuType.FuTypeOrR(decodedInst.fuType, FuType.vldu, FuType.vstu) && inst.NF === 0.U || (inst.NF =/= 0.U && (inst.MOP === "b00".U && inst.SUMOP === "b01000".U))) -> decodedInst.fuType, 1075 // MOP === b00 && SUMOP === b01000: unit-stride whole register store 1076 // MOP =/= b00 : strided and indexed store 1077 ( FuType.FuTypeOrR(decodedInst.fuType, FuType.vstu) && inst.NF =/= 0.U && ((inst.MOP === "b00".U && inst.SUMOP =/= "b01000".U) || inst.MOP =/= "b00".U)) -> FuType.vsegstu.U, 1078 // MOP === b00 && LUMOP === b01000: unit-stride whole register load 1079 // MOP =/= b00 : strided and indexed load 1080 ( FuType.FuTypeOrR(decodedInst.fuType, FuType.vldu) && inst.NF =/= 0.U && ((inst.MOP === "b00".U && inst.LUMOP =/= "b01000".U) || inst.MOP =/= "b00".U)) -> FuType.vsegldu.U, 1081 )) 1082 io.deq.decodedInst.imm := MuxCase(decodedInst.imm, Seq( 1083 isCsrrVlenb -> (VLEN / 8).U, 1084 isZimop -> 0.U, 1085 )) 1086 1087 io.deq.decodedInst.fuOpType := MuxCase(decodedInst.fuOpType, Seq( 1088 isCsrrVl -> VSETOpType.csrrvl, 1089 isCsrrVlenb -> ALUOpType.add, 1090 )) 1091 1092 io.deq.decodedInst.blockBackward := MuxCase(decodedInst.blockBackward, Seq( 1093 isCSRR -> false.B, 1094 )) 1095 //------------------------------------------------------------- 1096 // Debug Info 1097// XSDebug("in: instr=%x pc=%x excepVec=%b crossPageIPFFix=%d\n", 1098// io.enq.ctrl_flow.instr, io.enq.ctrl_flow.pc, io.enq.ctrl_flow.exceptionVec.asUInt, 1099// io.enq.ctrl_flow.crossPageIPFFix) 1100// XSDebug("out: srcType(0)=%b srcType(1)=%b srcType(2)=%b lsrc(0)=%d lsrc(1)=%d lsrc(2)=%d ldest=%d fuType=%b fuOpType=%b\n", 1101// io.deq.cf_ctrl.ctrl.srcType(0), io.deq.cf_ctrl.ctrl.srcType(1), io.deq.cf_ctrl.ctrl.srcType(2), 1102// io.deq.cf_ctrl.ctrl.lsrc(0), io.deq.cf_ctrl.ctrl.lsrc(1), io.deq.cf_ctrl.ctrl.lsrc(2), 1103// io.deq.cf_ctrl.ctrl.ldest, io.deq.cf_ctrl.ctrl.fuType, io.deq.cf_ctrl.ctrl.fuOpType) 1104// XSDebug("out: rfWen=%d fpWen=%d isXSTrap=%d noSpecExec=%d isBlocked=%d flushPipe=%d imm=%x\n", 1105// io.deq.cf_ctrl.ctrl.rfWen, io.deq.cf_ctrl.ctrl.fpWen, io.deq.cf_ctrl.ctrl.isXSTrap, 1106// io.deq.cf_ctrl.ctrl.noSpecExec, io.deq.cf_ctrl.ctrl.blockBackward, io.deq.cf_ctrl.ctrl.flushPipe, 1107// io.deq.cf_ctrl.ctrl.imm) 1108// XSDebug("out: excepVec=%b\n", io.deq.cf_ctrl.cf.exceptionVec.asUInt) 1109} 1110