1package xiangshan.backend.fu.NewCSR 2 3import chisel3._ 4import chisel3.util._ 5import difftest._ 6import freechips.rocketchip.rocket.CSRs 7import org.chipsalliance.cde.config.Parameters 8import top.{ArgParser, Generator} 9import utility.{DataHoldBypass, DelayN, GatedValidRegNext, RegNextWithEnable, SignExt, ZeroExt} 10import utils.{HPerfMonitor, OptionWrapper, PerfEvent} 11import xiangshan.backend.fu.NewCSR.CSRBundles.{CSRCustomState, PrivState, RobCommitCSR} 12import xiangshan.backend.fu.NewCSR.CSRDefines.{ContextStatus, HgatpMode, PrivMode, SatpMode, VirtMode} 13import xiangshan.backend.fu.NewCSR.CSREnumTypeImplicitCast._ 14import xiangshan.backend.fu.NewCSR.CSREvents.{CSREvents, DretEventSinkBundle, EventUpdatePrivStateOutput, MNretEventSinkBundle, MretEventSinkBundle, SretEventSinkBundle, TargetPCBundle, TrapEntryDEventSinkBundle, TrapEntryEventInput, TrapEntryHSEventSinkBundle, TrapEntryMEventSinkBundle, TrapEntryMNEventSinkBundle, TrapEntryVSEventSinkBundle} 15import xiangshan.backend.fu.fpu.Bundles.Frm 16import xiangshan.backend.fu.util.CSRConst 17import xiangshan.backend.fu.vector.Bundles.{Vl, Vstart, Vxrm, Vxsat} 18import xiangshan.backend.fu.wrapper.CSRToDecode 19import xiangshan.backend.rob.RobPtr 20import xiangshan._ 21import xiangshan.backend.fu.PerfCounterIO 22import xiangshan.ExceptionNO._ 23 24import scala.collection.immutable.SeqMap 25 26object CSRConfig { 27 final val GEILEN = 63 28 29 final val ASIDLEN = 16 // the length of ASID of XS implementation 30 31 final val ASIDMAX = 16 // the max value of ASIDLEN defined by spec 32 33 final val HIIDWidth = 12 // support Hvictl[27:16](IID) 34 35 final val VMIDLEN = 14 // the length of VMID of XS implementation 36 37 final val VMIDMAX = 14 // the max value of VMIDLEN defined by spec 38 39 // the width of VGEIN 40 final val VGEINWidth = 6 41 42 final val VaddrMaxWidth = 48 + 2 // support Sv39/Sv48/Sv39x4/Sv48x4 43 44 final val InstWidth = 32 45 46 final val XLEN = 64 // Todo: use XSParams 47 48 final val VLEN = 128 49 50 // Since we need macro to compute the width of CSR field, the input of macro should be the value that can be computed 51 // at compile time. The log2Up function cannot be used as meta-programming function, so we use litral value here 52 // log2Up(128 + 1), hold 0~128 53 final val VlWidth = 8 54 55 final val PAddrWidth = 48 56 57 final val AddrWidthInPage = 12 58 59 final val PMPAddrWidth = 48 60 61 final val PMPOffBits = 2 62 63 final val PMPAddrBits = PMPAddrWidth - PMPOffBits 64 65 // perf 66 final val perfCntNum = 29 // in Spec 67 68 final val EXT_SSTC = true 69 70 final val PPNLength = 44 71} 72 73class NewCSR(implicit val p: Parameters) extends Module 74 with HasXSParameter 75 with MachineLevel 76 with SupervisorLevel 77 with HypervisorLevel 78 with VirtualSupervisorLevel 79 with Unprivileged 80 with CSRAIA 81 with HasExternalInterruptBundle 82 with HasNonMaskableIRPBundle 83 with CSREvents 84 with DebugLevel 85 with CSRCustom 86 with CSRPMP 87 with IpIeAliasConnect 88{ 89 90 import CSRConfig._ 91 92 val io = IO(new Bundle { 93 val fromTop = Input(new Bundle { 94 val hartId = UInt(hartIdLen.W) 95 val clintTime = Input(ValidIO(UInt(64.W))) 96 }) 97 val in = Input(ValidIO(new Bundle { 98 val wen = Bool() 99 val ren = Bool() 100 val op = UInt(2.W) 101 val addr = UInt(12.W) 102 val src = UInt(64.W) 103 val wdata = UInt(64.W) 104 val mnret = Input(Bool()) 105 val mret = Input(Bool()) 106 val sret = Input(Bool()) 107 val dret = Input(Bool()) 108 })) 109 val trapInst = Input(ValidIO(UInt(InstWidth.W))) 110 val fromMem = Input(new Bundle { 111 val excpVA = UInt(VaddrMaxWidth.W) 112 val excpGPA = UInt(VaddrMaxWidth.W) // Todo: use guest physical address width 113 }) 114 val fromRob = Input(new Bundle { 115 val trap = ValidIO(new Bundle { 116 val pc = UInt(VaddrMaxWidth.W) 117 val pcGPA = UInt(VaddrMaxWidth.W) 118 val instr = UInt(InstWidth.W) 119 val trapVec = UInt(64.W) 120 val singleStep = Bool() 121 val trigger = TriggerAction() 122 val crossPageIPFFix = Bool() 123 val isInterrupt = Bool() 124 val isHls = Bool() 125 val isFetchMalAddr = Bool() 126 }) 127 val commit = Input(new RobCommitCSR) 128 val robDeqPtr = Input(new RobPtr) 129 }) 130 131 val perf = Input(new PerfCounterIO) 132 133 val out = Output(ValidIO(new Bundle { 134 val EX_II = Bool() 135 val EX_VI = Bool() 136 val flushPipe = Bool() 137 val rData = UInt(64.W) 138 val targetPcUpdate = Bool() 139 val targetPc = new TargetPCBundle 140 val regOut = UInt(64.W) 141 // perf 142 val isPerfCnt = Bool() 143 })) 144 val status = Output(new Bundle { 145 val privState = new PrivState 146 val interrupt = Bool() 147 val wfiEvent = Bool() 148 // fp 149 val fpState = new Bundle { 150 val off = Bool() 151 val frm = Frm() 152 } 153 // vec 154 val vecState = new Bundle { 155 val vstart = Vstart() 156 val vxsat = Vxsat() 157 val vxrm = Vxrm() 158 val vcsr = UInt(XLEN.W) 159 val vl = Vl() 160 val vtype = UInt(XLEN.W) 161 val vlenb = UInt(XLEN.W) 162 val off = Bool() 163 } 164 // debug 165 val debugMode = Bool() 166 val singleStepFlag = Bool() 167 // trigger 168 val frontendTrigger = new FrontendTdataDistributeIO() 169 val memTrigger = new MemTdataDistributeIO() 170 // Instruction fetch address translation type 171 val instrAddrTransType = new AddrTransType 172 // custom 173 val custom = new CSRCustomState 174 }) 175 // tlb 176 val tlb = Output(new Bundle { 177 val satpASIDChanged = Bool() 178 val vsatpASIDChanged = Bool() 179 val hgatpVMIDChanged = Bool() 180 val satp = new SatpBundle 181 val vsatp = new SatpBundle 182 val hgatp = new HgatpBundle 183 val mxr = Bool() 184 val sum = Bool() 185 val vmxr = Bool() 186 val vsum = Bool() 187 val spvp = Bool() 188 val imode = UInt(2.W) 189 val dmode = UInt(2.W) 190 val dvirt = Bool() 191 val mPBMTE = Bool() 192 val hPBMTE = Bool() 193 }) 194 195 val toDecode = new CSRToDecode 196 197 val fetchMalTval = Input(UInt(XLEN.W)) 198 }) 199 200 val toAIA = IO(Output(new CSRToAIABundle)) 201 val fromAIA = IO(Flipped(Output(new AIAToCSRBundle))) 202 203 dontTouch(toAIA) 204 dontTouch(fromAIA) 205 dontTouch(io.fromTop.clintTime) 206 207 val valid = io.in.valid 208 209 val wen = io.in.bits.wen && valid 210 val addr = io.in.bits.addr 211 val wdata = io.in.bits.wdata 212 213 val ren = io.in.bits.ren && valid 214 val raddr = io.in.bits.addr 215 216 val hasTrap = io.fromRob.trap.valid 217 val trapVec = io.fromRob.trap.bits.trapVec 218 val trapPC = io.fromRob.trap.bits.pc 219 val trapPCGPA = io.fromRob.trap.bits.pcGPA 220 val trapIsInterrupt = io.fromRob.trap.bits.isInterrupt 221 val trapIsCrossPageIPF = io.fromRob.trap.bits.crossPageIPFFix 222 val trigger = io.fromRob.trap.bits.trigger 223 val singleStep = io.fromRob.trap.bits.singleStep 224 val trapIsHls = io.fromRob.trap.bits.isHls 225 val trapIsFetchMalAddr = io.fromRob.trap.bits.isFetchMalAddr 226 227 // debug_intrrupt 228 val debugIntrEnable = RegInit(true.B) // debug interrupt will be handle only when debugIntrEnable 229 val debugIntr = platformIRP.debugIP && debugIntrEnable 230 231 // CSR Privilege State 232 val PRVM = RegInit(PrivMode(1, 0), PrivMode.M) 233 val V = RegInit(VirtMode(0), VirtMode.Off) 234 val debugMode = RegInit(false.B) 235 236 private val privState = Wire(new PrivState) 237 privState.PRVM := PRVM 238 privState.V := V 239 240 private val isModeM = privState.isModeM 241 private val (isModeHS, isModeHU) = (privState.isModeHS, privState.isModeHU) 242 private val (isModeVS, isModeVU) = (privState.isModeVS, privState.isModeVU) 243 244 val permitMod = Module(new CSRPermitModule) 245 val sstcIRGen = Module(new SstcInterruptGen) 246 247 private val wenLegal = permitMod.io.out.hasLegalWen 248 249 val legalSret = permitMod.io.out.hasLegalSret 250 val legalMret = permitMod.io.out.hasLegalMret 251 val legalMNret = permitMod.io.out.hasLegalMNret 252 val legalDret = permitMod.io.out.hasLegalDret 253 254 var csrRwMap: SeqMap[Int, (CSRAddrWriteBundle[_], UInt)] = 255 machineLevelCSRMap ++ 256 supervisorLevelCSRMap ++ 257 hypervisorCSRMap ++ 258 virtualSupervisorCSRMap ++ 259 unprivilegedCSRMap ++ 260 debugCSRMap ++ 261 aiaCSRMap ++ 262 customCSRMap ++ 263 pmpCSRMap 264 265 val csrMods: Seq[CSRModule[_]] = 266 machineLevelCSRMods ++ 267 supervisorLevelCSRMods ++ 268 hypervisorCSRMods ++ 269 virtualSupervisorCSRMods ++ 270 unprivilegedCSRMods ++ 271 debugCSRMods ++ 272 aiaCSRMods ++ 273 customCSRMods ++ 274 pmpCSRMods 275 276 var csrOutMap: SeqMap[Int, UInt] = 277 machineLevelCSROutMap ++ 278 supervisorLevelCSROutMap ++ 279 hypervisorCSROutMap ++ 280 virtualSupervisorCSROutMap ++ 281 unprivilegedCSROutMap ++ 282 debugCSROutMap ++ 283 aiaCSROutMap ++ 284 customCSROutMap ++ 285 pmpCSROutMap 286 287 // interrupt 288 val intrMod = Module(new InterruptFilter) 289 intrMod.io.in.privState := privState 290 intrMod.io.in.mstatusMIE := mstatus.regOut.MIE.asBool 291 intrMod.io.in.sstatusSIE := mstatus.regOut.SIE.asBool 292 intrMod.io.in.vsstatusSIE := vsstatus.regOut.SIE.asBool 293 intrMod.io.in.mip := mip.rdata.asUInt 294 intrMod.io.in.mie := mie.rdata.asUInt 295 intrMod.io.in.mideleg := mideleg.rdata.asUInt 296 intrMod.io.in.sip := sip.rdata.asUInt 297 intrMod.io.in.sie := sie.rdata.asUInt 298 intrMod.io.in.hip := hip.rdata.asUInt 299 intrMod.io.in.hie := hie.rdata.asUInt 300 intrMod.io.in.hideleg := hideleg.rdata.asUInt 301 intrMod.io.in.vsip := vsip.rdata.asUInt 302 intrMod.io.in.vsie := vsie.rdata.asUInt 303 intrMod.io.in.hvictl := hvictl.rdata.asUInt 304 intrMod.io.in.hstatus := hstatus.rdata.asUInt 305 intrMod.io.in.mtopei := mtopei.rdata.asUInt 306 intrMod.io.in.stopei := stopei.rdata.asUInt 307 intrMod.io.in.vstopei := vstopei.rdata.asUInt 308 intrMod.io.in.hviprio1 := hviprio1.rdata.asUInt 309 intrMod.io.in.hviprio2 := hviprio2.rdata.asUInt 310 intrMod.io.in.miprios := Cat(miregiprios.map(_.rdata).reverse) 311 intrMod.io.in.hsiprios := Cat(siregiprios.map(_.rdata).reverse) 312 intrMod.io.in.mnstatusNMIE := mnstatus.regOut.NMIE.asBool 313 314 val nmip = RegInit(new NonMaskableIRPendingBundle, (new NonMaskableIRPendingBundle).init) 315 when(nonMaskableIRP.NMI) { 316 nmip.NMI := true.B 317 } 318 319 intrMod.io.in.nmi := nmip.asUInt.orR 320 intrMod.io.in.nmiVec := nmip.asUInt 321 322 when(intrMod.io.out.nmi && intrMod.io.out.interruptVec.valid) { 323 nmip.NMI := false.B 324 } 325 val intrVec = RegEnable(intrMod.io.out.interruptVec.bits, 0.U, intrMod.io.out.interruptVec.valid) 326 val nmi = RegEnable(intrMod.io.out.nmi, false.B, intrMod.io.out.interruptVec.valid) 327 val virtualInterruptIsHvictlInject = RegEnable(intrMod.io.out.virtualInterruptIsHvictlInject, false.B, intrMod.io.out.interruptVec.valid) 328 329 val trapHandleMod = Module(new TrapHandleModule) 330 331 trapHandleMod.io.in.trapInfo.valid := hasTrap 332 trapHandleMod.io.in.trapInfo.bits.trapVec := trapVec.asUInt 333 trapHandleMod.io.in.trapInfo.bits.nmi := nmi 334 trapHandleMod.io.in.trapInfo.bits.intrVec := intrVec 335 trapHandleMod.io.in.trapInfo.bits.isInterrupt := trapIsInterrupt 336 trapHandleMod.io.in.privState := privState 337 trapHandleMod.io.in.mideleg := mideleg.regOut 338 trapHandleMod.io.in.medeleg := medeleg.regOut 339 trapHandleMod.io.in.hideleg := hideleg.regOut 340 trapHandleMod.io.in.hedeleg := hedeleg.regOut 341 trapHandleMod.io.in.mvien := mvien.regOut 342 trapHandleMod.io.in.hvien := hvien.regOut 343 trapHandleMod.io.in.mtvec := mtvec.regOut 344 trapHandleMod.io.in.stvec := stvec.regOut 345 trapHandleMod.io.in.vstvec := vstvec.regOut 346 trapHandleMod.io.in.virtualInterruptIsHvictlInject := virtualInterruptIsHvictlInject 347 348 val entryPrivState = trapHandleMod.io.out.entryPrivState 349 val entryDebugMode = WireInit(false.B) 350 351 // PMP 352 val pmpEntryMod = Module(new PMPEntryHandleModule) 353 pmpEntryMod.io.in.pmpCfg := cfgs.map(_.regOut.asInstanceOf[PMPCfgBundle]) 354 pmpEntryMod.io.in.pmpAddr := pmpaddr.map(_.regOut.asInstanceOf[PMPAddrBundle]) 355 pmpEntryMod.io.in.ren := ren 356 pmpEntryMod.io.in.wen := wen 357 pmpEntryMod.io.in.addr := addr 358 pmpEntryMod.io.in.wdata := wdata 359 360 for ((id, (wBundle, _)) <- csrRwMap) { 361 if (vsMapS.contains(id)) { 362 // VS access CSR by S: privState.isModeVS && addrMappedToVS === sMapVS(id).U 363 wBundle.wen := wenLegal && ((isModeVS && addr === vsMapS(id).U) || (!isModeVS && addr === id.U)) 364 wBundle.wdata := wdata 365 } else if (sMapVS.contains(id)) { 366 wBundle.wen := wenLegal && !isModeVS && addr === id.U 367 wBundle.wdata := wdata 368 } else { 369 wBundle.wen := wenLegal && addr === id.U 370 wBundle.wdata := wdata 371 } 372 } 373 374 private val writeFpLegal = permitMod.io.out.hasLegalWriteFcsr 375 private val writeVecLegal = permitMod.io.out.hasLegalWriteVcsr 376 377 permitMod.io.in.csrAccess.ren := ren && valid 378 permitMod.io.in.csrAccess.wen := wen 379 permitMod.io.in.csrAccess.addr := addr 380 381 permitMod.io.in.privState := privState 382 permitMod.io.in.debugMode := debugMode 383 384 permitMod.io.in.mnret := io.in.bits.mnret && valid 385 permitMod.io.in.mret := io.in.bits.mret && valid 386 permitMod.io.in.sret := io.in.bits.sret && valid 387 permitMod.io.in.dret := io.in.bits.dret && valid 388 permitMod.io.in.csrIsCustom := customCSRMods.map(_.addr.U === addr).reduce(_ || _).orR 389 390 permitMod.io.in.status.tsr := mstatus.regOut.TSR.asBool 391 permitMod.io.in.status.vtsr := hstatus.regOut.VTSR.asBool 392 393 permitMod.io.in.status.tvm := mstatus.regOut.TVM.asBool 394 permitMod.io.in.status.vtvm := hstatus.regOut.VTVM.asBool 395 396 permitMod.io.in.status.mcounteren := mcounteren.rdata 397 permitMod.io.in.status.hcounteren := hcounteren.rdata 398 permitMod.io.in.status.scounteren := scounteren.rdata 399 400 permitMod.io.in.status.mstateen0 := mstateen0.rdata 401 permitMod.io.in.status.hstateen0 := hstateen0.rdata 402 permitMod.io.in.status.sstateen0 := sstateen0.rdata 403 404 permitMod.io.in.status.menvcfg := menvcfg.rdata 405 permitMod.io.in.status.henvcfg := henvcfg.rdata 406 407 permitMod.io.in.status.mstatusFSOff := mstatus.regOut.FS === ContextStatus.Off 408 permitMod.io.in.status.mstatusVSOff := mstatus.regOut.VS === ContextStatus.Off 409 permitMod.io.in.status.vsstatusFSOff := vsstatus.regOut.FS === ContextStatus.Off 410 permitMod.io.in.status.vsstatusVSOff := vsstatus.regOut.VS === ContextStatus.Off 411 412 permitMod.io.in.aia.miselectIsIllegal := miselect.isIllegal 413 permitMod.io.in.aia.siselectIsIllegal := siselect.isIllegal 414 permitMod.io.in.aia.vsiselectIsIllegal := vsiselect.isIllegal 415 permitMod.io.in.aia.siselect := siselect.rdata 416 permitMod.io.in.aia.vsiselect := vsiselect.rdata 417 permitMod.io.in.aia.mvienSEIE := mvien.regOut.SEIE.asBool 418 permitMod.io.in.aia.hvictlVTI := hvictl.regOut.VTI.asBool 419 420 sstcIRGen.i.stime.valid := time.updated 421 sstcIRGen.i.stime.bits := time.stime 422 sstcIRGen.i.vstime.valid := time.updated 423 sstcIRGen.i.vstime.bits := time.vstime 424 sstcIRGen.i.stimecmp := stimecmp.rdata 425 sstcIRGen.i.vstimecmp := vstimecmp.rdata 426 sstcIRGen.i.menvcfgSTCE := menvcfg.regOut.STCE.asBool 427 sstcIRGen.i.henvcfgSTCE := henvcfg.regOut.STCE.asBool 428 429 miregiprios.foreach { mod => 430 mod.w.wen := (addr === mireg.addr.U) && (miselect.regOut.ALL.asUInt === mod.addr.U) 431 mod.w.wdata := wdata 432 } 433 434 siregiprios.foreach { mod => 435 mod.w.wen := (addr === sireg.addr.U) && (siselect.regOut.ALL.asUInt === mod.addr.U) 436 mod.w.wdata := wdata 437 } 438 439 mhartid.hartid := this.io.fromTop.hartId 440 441 cfgs.zipWithIndex.foreach { case (mod, i) => 442 mod.w.wen := wen && (addr === (0x3A0 + i / 8 * 2).U) 443 mod.w.wdata := pmpEntryMod.io.out.pmpCfgWData(8*((i%8)+1)-1,8*(i%8)) 444 } 445 446 pmpaddr.zipWithIndex.foreach{ case(mod, i) => 447 mod.w.wen := wen && (addr === (0x3B0 + i).U) 448 mod.w.wdata := pmpEntryMod.io.out.pmpAddrWData(i) 449 } 450 451 csrMods.foreach { mod => 452 mod match { 453 case m: HypervisorBundle => 454 m.hstatus := hstatus.regOut 455 case _ => 456 } 457 mod match { 458 case m: VirtualSupervisorBundle => 459 m.v := V.asUInt.asBool 460 m.hgatp := hgatp.regOut 461 case _ => 462 } 463 mod match { 464 case m: HasMachineDelegBundle => 465 m.mideleg := mideleg.regOut 466 m.medeleg := medeleg.regOut 467 case _ => 468 } 469 mod match { 470 case m: HasMachineCounterControlBundle => 471 m.mcountinhibit := mcountinhibit.regOut 472 case _ => 473 } 474 mod match { 475 case m: HasExternalInterruptBundle => 476 m.platformIRP := this.platformIRP 477 m.platformIRP.STIP := sstcIRGen.o.STIP 478 m.platformIRP.VSTIP := sstcIRGen.o.VSTIP 479 case _ => 480 } 481 mod match { 482 case m: HasRobCommitBundle => 483 // Todo: move RegNext from ROB to CSR 484 m.robCommit.instNum := io.fromRob.commit.instNum 485 m.robCommit.fflags := RegNextWithEnable(io.fromRob.commit.fflags) 486 m.robCommit.fsDirty := GatedValidRegNext(io.fromRob.commit.fsDirty) 487 m.robCommit.vsDirty := GatedValidRegNext(io.fromRob.commit.vsDirty) 488 m.robCommit.vxsat := RegNextWithEnable(io.fromRob.commit.vxsat) 489 m.robCommit.vtype := RegNextWithEnable(io.fromRob.commit.vtype) 490 m.robCommit.vl := RegNext (io.fromRob.commit.vl) 491 m.robCommit.vstart := RegNextWithEnable(io.fromRob.commit.vstart) 492 m.writeFCSR := writeFpLegal 493 m.writeVCSR := writeVecLegal 494 m.isVirtMode := V.asUInt.asBool 495 case _ => 496 } 497 mod match { 498 case m: TrapEntryDEventSinkBundle => 499 m.trapToD := trapEntryDEvent.out 500 case _ => 501 } 502 mod match { 503 case m: TrapEntryMEventSinkBundle => 504 m.trapToM := trapEntryMEvent.out 505 case _ => 506 } 507 mod match { 508 case m: TrapEntryMNEventSinkBundle => 509 m.trapToMN := trapEntryMNEvent.out 510 case _ => 511 } 512 mod match { 513 case m: TrapEntryHSEventSinkBundle => 514 m.trapToHS := trapEntryHSEvent.out 515 case _ => 516 } 517 mod match { 518 case m: TrapEntryVSEventSinkBundle => 519 m.trapToVS := trapEntryVSEvent.out 520 case _ => 521 } 522 mod match { 523 case m: MretEventSinkBundle => 524 m.retFromM := mretEvent.out 525 case _ => 526 } 527 mod match { 528 case m: MNretEventSinkBundle => 529 m.retFromMN := mnretEvent.out 530 case _ => 531 } 532 mod match { 533 case m: SretEventSinkBundle => 534 m.retFromS := sretEvent.out 535 case _ => 536 } 537 mod match { 538 case m: DretEventSinkBundle => 539 m.retFromD := dretEvent.out 540 case _ => 541 } 542 mod match { 543 case m: HasAIABundle => 544 m.aiaToCSR.rdata.valid := fromAIA.rdata.valid 545 m.aiaToCSR.rdata.bits.data := fromAIA.rdata.bits.data 546 m.aiaToCSR.rdata.bits.illegal := fromAIA.rdata.bits.illegal 547 m.aiaToCSR.meip := fromAIA.meip 548 m.aiaToCSR.seip := fromAIA.seip 549 m.aiaToCSR.vseip := fromAIA.vseip 550 m.aiaToCSR.mtopei := fromAIA.mtopei 551 m.aiaToCSR.stopei := fromAIA.stopei 552 m.aiaToCSR.vstopei := fromAIA.vstopei 553 case _ => 554 } 555 mod match { 556 case m: HasInterruptFilterSink => 557 m.topIR.mtopi := intrMod.io.out.mtopi 558 m.topIR.stopi := intrMod.io.out.stopi 559 m.topIR.vstopi := intrMod.io.out.vstopi 560 case _ => 561 } 562 mod match { 563 case m: HasPMPAddrSink => 564 m.addrRData := pmpEntryMod.io.out.pmpAddrRData 565 case _ => 566 } 567 mod match { 568 case m: HasMHPMSink => 569 // cycle from mcycle 570 m.mHPM.cycle := mcycle.rdata 571 // time from clint 572 m.mHPM.time := io.fromTop.clintTime 573 // instret from minstret 574 m.mHPM.instret := minstret.rdata 575 // VS-Mode or VU-Mode 576 m.v := privState.isVirtual 577 m.htimedelta := htimedelta.rdata 578 m.mHPM.hpmcounters.zip(mhpmcounters).map{ 579 case(counter, mcounter) => counter := mcounter.rdata 580 } 581 case _ => 582 } 583 mod match { 584 case m: HasMachineEnvBundle => 585 m.menvcfg := menvcfg.regOut 586 case _ => 587 } 588 mod match { 589 case m: HasHypervisorEnvBundle => 590 m.menvcfg := menvcfg.regOut 591 m.privState := privState 592 m.accessStimecmp := (ren || wen) && (addr === CSRs.stimecmp.U || addr === CSRs.vstimecmp.U) 593 case _ => 594 } 595 mod match { 596 case m: HasIpIeBundle => 597 m.mideleg := mideleg.regOut 598 m.mip := mip.rdata 599 m.mie := mie.regOut 600 m.mvip := mvip.regOut 601 m.mvien := mvien.regOut 602 m.hideleg := hideleg.regOut 603 m.hip := hip.regOut 604 m.hie := hie.regOut 605 m.hvien := hvien.regOut 606 m.hvip := hvip.regOut 607 m.sip := sip.regOut 608 m.sie := sie.regOut 609 m.vsip := vsip.regOut 610 m.vsie := vsie.regOut 611 m.hgeip := hgeip.regOut 612 m.hgeie := hgeie.regOut 613 m.hstatusVGEIN := hstatus.regOut.VGEIN 614 case _ => 615 } 616 mod match { 617 case m: HasMhpmeventOfBundle => 618 m.ofVec := VecInit(mhpmevents.map(event => event.rdata.head(1).asBool)).asUInt //todo:fix 619 m.privState := privState 620 m.mcounteren := mcounteren.rdata 621 m.hcounteren := hcounteren.rdata 622 case _ => 623 } 624 mod match { 625 case m: HasStateen0Bundle => 626 m.fromMstateen0 := mstateen0.regOut 627 m.fromHstateen0 := hstateen0.regOut 628 m.privState := privState 629 case _ => 630 } 631 } 632 633 csrMods.foreach { mod => 634 println(s"${mod.modName}: ") 635 println(mod.dumpFields) 636 } 637 638 trapEntryMEvent.valid := hasTrap && entryPrivState.isModeM && !entryDebugMode && !debugMode && !nmi 639 trapEntryMNEvent.valid := hasTrap && nmi && !debugMode 640 trapEntryHSEvent.valid := hasTrap && entryPrivState.isModeHS && !entryDebugMode && !debugMode 641 trapEntryVSEvent.valid := hasTrap && entryPrivState.isModeVS && !entryDebugMode && !debugMode 642 643 Seq(trapEntryMEvent, trapEntryMNEvent, trapEntryHSEvent, trapEntryVSEvent, trapEntryDEvent).foreach { eMod => 644 eMod.in match { 645 case in: TrapEntryEventInput => 646 in.causeNO := trapHandleMod.io.out.causeNO 647 in.trapPc := trapPC 648 in.trapPcGPA := trapPCGPA // only used by trapEntryMEvent & trapEntryHSEvent 649 in.trapInst := io.trapInst 650 in.fetchMalTval := io.fetchMalTval 651 in.isCrossPageIPF := trapIsCrossPageIPF 652 in.isHls := trapIsHls 653 in.isFetchMalAddr := trapIsFetchMalAddr 654 655 in.iMode.PRVM := PRVM 656 in.iMode.V := V 657 // when NMIE is zero, force to behave as MPRV is zero 658 in.dMode.PRVM := Mux(mstatus.regOut.MPRV.asBool && mnstatus.regOut.NMIE.asBool, mstatus.regOut.MPP, PRVM) 659 in.dMode.V := V.asUInt.asBool || mstatus.regOut.MPRV && mnstatus.regOut.NMIE.asBool && (mstatus.regOut.MPP =/= PrivMode.M) && mstatus.regOut.MPV 660 661 in.privState := privState 662 in.mstatus := mstatus.regOut 663 in.hstatus := hstatus.regOut 664 in.sstatus := mstatus.sstatus 665 in.vsstatus := vsstatus.regOut 666 in.pcFromXtvec := trapHandleMod.io.out.pcFromXtvec 667 in.tcontrol := tcontrol.regOut 668 669 in.satp := satp.regOut 670 in.vsatp := vsatp.regOut 671 in.hgatp := hgatp.regOut 672 673 in.memExceptionVAddr := io.fromMem.excpVA 674 in.memExceptionGPAddr := io.fromMem.excpGPA 675 676 in.virtualInterruptIsHvictlInject := virtualInterruptIsHvictlInject 677 in.hvictlIID := hvictl.regOut.IID.asUInt 678 } 679 } 680 681 mnretEvent.valid := legalMNret 682 mnretEvent.in match { 683 case in => 684 in.mstatus := mstatus.regOut 685 in.mnepc := mnepc.regOut 686 in.mnstatus:= mnstatus.regOut 687 in.satp := satp.regOut 688 in.vsatp := vsatp.regOut 689 in.hgatp := hgatp.regOut 690 } 691 692 mretEvent.valid := legalMret 693 mretEvent.in match { 694 case in => 695 in.mstatus := mstatus.regOut 696 in.mepc := mepc.regOut 697 in.tcontrol := tcontrol.regOut 698 in.satp := satp.regOut 699 in.vsatp := vsatp.regOut 700 in.hgatp := hgatp.regOut 701 } 702 703 sretEvent.valid := legalSret 704 sretEvent.in match { 705 case in => 706 in.privState := privState 707 in.sstatus := mstatus.sstatus 708 in.hstatus := hstatus.regOut 709 in.vsstatus := vsstatus.regOut 710 in.sepc := sepc.regOut 711 in.vsepc := vsepc.regOut 712 in.satp := satp.regOut 713 in.vsatp := vsatp.regOut 714 in.hgatp := hgatp.regOut 715 } 716 717 dretEvent.valid := legalDret 718 dretEvent.in match { 719 case in => 720 in.dcsr := dcsr.regOut 721 in.dpc := dpc.regOut 722 in.mstatus := mstatus.regOut 723 in.satp := satp.regOut 724 in.vsatp := vsatp.regOut 725 in.hgatp := hgatp.regOut 726 } 727 728 PRVM := MuxCase( 729 PRVM, 730 events.filter(_.out.isInstanceOf[EventUpdatePrivStateOutput]).map { 731 x => x.out match { 732 case xx: EventUpdatePrivStateOutput => (xx.privState.valid -> xx.privState.bits.PRVM) 733 } 734 } 735 ) 736 737 V := MuxCase( 738 V, 739 events.filter(_.out.isInstanceOf[EventUpdatePrivStateOutput]).map { 740 x => x.out match { 741 case xx: EventUpdatePrivStateOutput => (xx.privState.valid -> xx.privState.bits.V) 742 } 743 } 744 ) 745 746 debugMode := MuxCase( 747 debugMode, 748 Seq( 749 dretEvent.out.debugMode.valid -> dretEvent.out.debugMode.bits, 750 trapEntryDEvent.out.debugMode.valid -> trapEntryDEvent.out.debugMode.bits 751 ) 752 ) 753 754 debugIntrEnable := MuxCase( 755 debugIntrEnable, 756 Seq( 757 dretEvent.out.debugIntrEnable.valid -> dretEvent.out.debugIntrEnable.bits, 758 trapEntryDEvent.out.debugIntrEnable.valid -> trapEntryDEvent.out.debugIntrEnable.bits 759 ) 760 ) 761 762 // perf 763 val addrInPerfCnt = (wen || ren) && ( 764 (addr >= CSRs.mcycle.U) && (addr <= CSRs.mhpmcounter31.U) || 765 (addr === mcountinhibit.addr.U) || 766 (addr >= CSRs.cycle.U) && (addr <= CSRs.hpmcounter31.U) || 767 (addr === CSRs.mip.U) || (addr === CSRs.sip.U) || (addr === CSRs.vsip.U) || 768 (addr === CSRs.hip.U) || (addr === CSRs.mvip.U) || (addr === CSRs.hvip.U) || 769 Cat(aiaSkipCSRs.map(_.addr.U === addr)).orR || 770 (addr === CSRs.menvcfg.U) || 771 (addr === CSRs.henvcfg.U) || 772 (addr === CSRs.stimecmp.U) 773 ) 774 775 // flush 776 val resetSatp = Cat(Seq(satp, vsatp, hgatp).map(_.addr.U === addr)).orR && wenLegal // write to satp will cause the pipeline be flushed 777 778 val floatStatusOnOff = mstatus.w.wen && ( 779 mstatus.w.wdataFields.FS === ContextStatus.Off && mstatus.regOut.FS =/= ContextStatus.Off || 780 mstatus.w.wdataFields.FS =/= ContextStatus.Off && mstatus.regOut.FS === ContextStatus.Off 781 ) || mstatus.wAliasSstatus.wen && ( 782 mstatus.wAliasSstatus.wdataFields.FS === ContextStatus.Off && mstatus.regOut.FS =/= ContextStatus.Off || 783 mstatus.wAliasSstatus.wdataFields.FS =/= ContextStatus.Off && mstatus.regOut.FS === ContextStatus.Off 784 ) || vsstatus.w.wen && ( 785 vsstatus.w.wdataFields.FS === ContextStatus.Off && vsstatus.regOut.FS =/= ContextStatus.Off || 786 vsstatus.w.wdataFields.FS =/= ContextStatus.Off && vsstatus.regOut.FS === ContextStatus.Off 787 ) 788 789 val vectorStatusOnOff = mstatus.w.wen && ( 790 mstatus.w.wdataFields.VS === ContextStatus.Off && mstatus.regOut.VS =/= ContextStatus.Off || 791 mstatus.w.wdataFields.VS =/= ContextStatus.Off && mstatus.regOut.VS === ContextStatus.Off 792 ) || mstatus.wAliasSstatus.wen && ( 793 mstatus.wAliasSstatus.wdataFields.VS === ContextStatus.Off && mstatus.regOut.VS =/= ContextStatus.Off || 794 mstatus.wAliasSstatus.wdataFields.VS =/= ContextStatus.Off && mstatus.regOut.VS === ContextStatus.Off 795 ) || vsstatus.w.wen && ( 796 vsstatus.w.wdataFields.VS === ContextStatus.Off && vsstatus.regOut.VS =/= ContextStatus.Off || 797 vsstatus.w.wdataFields.VS =/= ContextStatus.Off && vsstatus.regOut.VS === ContextStatus.Off 798 ) 799 800 val triggerFrontendChange = Wire(Bool()) 801 802 val vstartChange = vstart.w.wen && ( 803 vstart.w.wdata === 0.U && vstart.regOut.vstart.asUInt =/= 0.U || 804 vstart.w.wdata =/= 0.U && vstart.regOut.vstart.asUInt === 0.U 805 ) 806 807 // flush pipe when write frm and data > 4 or write fcsr and data[7:5] > 4 or write frm/fcsr and frm is reserved 808 val frmIsReserved = fcsr.frm(2) && fcsr.frm(1, 0).orR 809 val frmWdataReserved = fcsr.wAliasFfm.wdata(2) && fcsr.wAliasFfm.wdata(1, 0).orR 810 val fcsrWdataReserved = fcsr.w.wdata(7) && fcsr.w.wdata(6, 5).orR 811 val frmChange = fcsr.wAliasFfm.wen && (!frmIsReserved && frmWdataReserved || frmIsReserved && !frmWdataReserved) || 812 fcsr.w.wen && (!frmIsReserved && fcsrWdataReserved || frmIsReserved && !fcsrWdataReserved) 813 814 val flushPipe = resetSatp || 815 triggerFrontendChange || floatStatusOnOff || vectorStatusOnOff || 816 vstartChange || frmChange 817 818 private val rdata = Mux1H(csrRwMap.map { case (id, (_, rdata)) => 819 if (vsMapS.contains(id)) { 820 ((isModeVS && addr === vsMapS(id).U) || !isModeVS && addr === id.U) -> rdata 821 } else if (sMapVS.contains(id)) { 822 (!isModeVS && addr === id.U) -> rdata 823 } else { 824 (raddr === id.U) -> rdata 825 } 826 }) 827 828 private val regOut = Mux1H(csrOutMap.map { case (id, regOut) => 829 if (vsMapS.contains(id)) { 830 ((isModeVS && addr === vsMapS(id).U) || !isModeVS && addr === id.U) -> regOut 831 } else if (sMapVS.contains(id)) { 832 (!isModeVS && addr === id.U) -> regOut 833 } else { 834 (raddr === id.U) -> regOut 835 } 836 }) 837 838 private val needTargetUpdate = mnretEvent.out.targetPc.valid || mretEvent.out.targetPc.valid || sretEvent.out.targetPc.valid || dretEvent.out.targetPc.valid || 839 trapEntryMEvent.out.targetPc.valid || trapEntryMNEvent.out.targetPc.valid || trapEntryHSEvent.out.targetPc.valid || trapEntryVSEvent.out.targetPc.valid || trapEntryDEvent.out.targetPc.valid 840 841 private val noCSRIllegal = (ren || wen) && Cat(csrRwMap.keys.toSeq.sorted.map(csrAddr => !(addr === csrAddr.U))).andR 842 843 private val s_idle :: s_waitIMSIC :: Nil = Enum(2) 844 845 private val state = RegInit(s_idle) 846 private val stateNext = WireInit(state) 847 state := stateNext 848 849 private val asyncRead = ren && ( 850 mireg.addr.U === addr && miselect.inIMSICRange || 851 sireg.addr.U === addr && siselect.inIMSICRange || 852 vsireg.addr.U === addr && vsiselect.inIMSICRange 853 ) 854 855 switch(state) { 856 is(s_idle) { 857 when(asyncRead) { 858 stateNext := s_waitIMSIC 859 } 860 } 861 is(s_waitIMSIC) { 862 when(fromAIA.rdata.valid) { 863 stateNext := s_idle 864 } 865 } 866 } 867 868 // Todo: check IMSIC EX_II and EX_VI 869 private val imsicIllegal = fromAIA.rdata.valid && fromAIA.rdata.bits.illegal 870 private val imsic_EX_II = imsicIllegal && !V.asUInt.asBool 871 private val imsic_EX_VI = imsicIllegal && V.asUInt.asBool 872 873 io.out.valid := 874 io.in.valid && stateNext === s_idle || 875 state === s_waitIMSIC && stateNext === s_idle 876 io.out.bits.EX_II := permitMod.io.out.EX_II || imsic_EX_II || noCSRIllegal 877 io.out.bits.EX_VI := permitMod.io.out.EX_VI || imsic_EX_VI 878 879 io.out.bits.flushPipe := flushPipe 880 881 io.out.bits.rData := MuxCase(0.U, Seq( 882 (state === s_waitIMSIC && stateNext === s_idle) -> fromAIA.rdata.bits.data, 883 ren -> rdata, 884 )) 885 io.out.bits.regOut := regOut 886 io.out.bits.targetPc := DataHoldBypass( 887 Mux(trapEntryDEvent.out.targetPc.valid, 888 trapEntryDEvent.out.targetPc.bits, 889 Mux1H(Seq( 890 mnretEvent.out.targetPc.valid -> mnretEvent.out.targetPc.bits, 891 mretEvent.out.targetPc.valid -> mretEvent.out.targetPc.bits, 892 sretEvent.out.targetPc.valid -> sretEvent.out.targetPc.bits, 893 dretEvent.out.targetPc.valid -> dretEvent.out.targetPc.bits, 894 trapEntryMEvent.out.targetPc.valid -> trapEntryMEvent.out.targetPc.bits, 895 trapEntryMNEvent.out.targetPc.valid -> trapEntryMNEvent.out.targetPc.bits, 896 trapEntryHSEvent.out.targetPc.valid -> trapEntryHSEvent.out.targetPc.bits, 897 trapEntryVSEvent.out.targetPc.valid -> trapEntryVSEvent.out.targetPc.bits) 898 ) 899 ), 900 needTargetUpdate) 901 io.out.bits.targetPcUpdate := needTargetUpdate 902 io.out.bits.isPerfCnt := addrInPerfCnt 903 904 io.status.privState := privState 905 io.status.fpState.frm := fcsr.frm 906 io.status.fpState.off := mstatus.regOut.FS === ContextStatus.Off 907 io.status.vecState.vstart := vstart.rdata.asUInt 908 io.status.vecState.vxsat := vcsr.vxsat 909 io.status.vecState.vxrm := vcsr.vxrm 910 io.status.vecState.vcsr := vcsr.rdata.asUInt 911 io.status.vecState.vl := vl.rdata.asUInt 912 io.status.vecState.vtype := vtype.rdata.asUInt // Todo: check correct 913 io.status.vecState.vlenb := vlenb.rdata.asUInt 914 io.status.vecState.off := mstatus.regOut.VS === ContextStatus.Off 915 io.status.interrupt := intrMod.io.out.interruptVec.valid 916 io.status.wfiEvent := debugIntr || (mie.rdata.asUInt & mip.rdata.asUInt).orR 917 io.status.debugMode := debugMode 918 io.status.singleStepFlag := !debugMode && dcsr.regOut.STEP 919 920 /** 921 * debug_begin 922 */ 923 val tdata1Selected = Wire(new Tdata1Bundle) 924 tdata1Selected := tdata1.rdata 925 val dmodeInSelectedTrigger = tdata1Selected.DMODE.asBool 926 val triggerCanWrite = dmodeInSelectedTrigger && debugMode || !dmodeInSelectedTrigger 927 val tdata1Update = tdata1.w.wen && triggerCanWrite 928 val tdata2Update = tdata2.w.wen && triggerCanWrite 929 val tdata1Vec = tdata1RegVec.map{ mod => { 930 val tdata1Wire = Wire(new Tdata1Bundle) 931 tdata1Wire := mod.rdata 932 tdata1Wire 933 }} 934 935 val debugMod = Module(new Debug) 936 debugMod.io.in.trapInfo.valid := hasTrap 937 debugMod.io.in.trapInfo.bits.trapVec := trapVec.asUInt 938 debugMod.io.in.trapInfo.bits.intrVec := intrVec 939 debugMod.io.in.trapInfo.bits.isInterrupt := trapIsInterrupt 940 debugMod.io.in.trapInfo.bits.trigger := trigger 941 debugMod.io.in.trapInfo.bits.singleStep := singleStep 942 debugMod.io.in.privState := privState 943 debugMod.io.in.debugMode := debugMode 944 debugMod.io.in.dcsr := dcsr.regOut 945 debugMod.io.in.tcontrol := tcontrol.regOut 946 debugMod.io.in.tselect := tselect.regOut 947 debugMod.io.in.tdata1Vec := tdata1Vec 948 debugMod.io.in.tdata1Selected := tdata1.rdata 949 debugMod.io.in.tdata2Selected := tdata2.rdata 950 debugMod.io.in.tdata1Update := tdata1Update 951 debugMod.io.in.tdata2Update := tdata2Update 952 debugMod.io.in.tdata1Wdata := wdata 953 954 entryDebugMode := debugMod.io.out.hasDebugTrap && !debugMode 955 956 trapEntryDEvent.valid := entryDebugMode 957 trapEntryDEvent.in.hasDebugIntr := debugMod.io.out.hasDebugIntr 958 trapEntryDEvent.in.debugMode := debugMode 959 trapEntryDEvent.in.hasTrap := hasTrap 960 trapEntryDEvent.in.hasSingleStep := debugMod.io.out.hasSingleStep 961 trapEntryDEvent.in.triggerEnterDebugMode := debugMod.io.out.triggerEnterDebugMode 962 trapEntryDEvent.in.hasDebugEbreakException := debugMod.io.out.hasDebugEbreakException 963 trapEntryDEvent.in.breakPoint := debugMod.io.out.breakPoint 964 965 trapHandleMod.io.in.trapInfo.bits.singleStep := debugMod.io.out.hasSingleStep 966 967 intrMod.io.in.debugMode := debugMode 968 intrMod.io.in.debugIntr := debugIntr 969 intrMod.io.in.dcsr := dcsr.regOut 970 971 tdata1RegVec.foreach { mod => 972 mod match { 973 case m: HasdebugModeBundle => 974 m.debugMode := debugMode 975 m.chainable := debugMod.io.out.newTriggerChainIsLegal 976 case _ => 977 } 978 } 979 tdata1RegVec.zip(tdata2RegVec).zipWithIndex.map { case ((mod1, mod2), idx) => { 980 mod1.w.wen := tdata1Update && (tselect.rdata === idx.U) 981 mod1.w.wdata := wdata 982 mod2.w.wen := tdata2Update && (tselect.rdata === idx.U) 983 mod2.w.wdata := wdata 984 }} 985 986 triggerFrontendChange := debugMod.io.out.triggerFrontendChange 987 988 io.status.frontendTrigger := debugMod.io.out.frontendTrigger 989 io.status.memTrigger := debugMod.io.out.memTrigger 990 /** 991 * debug_end 992 */ 993 994 /** 995 * perf_begin 996 * perf number: 29 (frontend 8, ctrlblock 8, memblock 8, huancun 5) 997 */ 998 // tmp: mhpmevents is wrapper of perfEvents, read/write/update mhpmevents -> read/write/update perfEvents 999 val csrevents = perfEvents.slice(24, 29) 1000 1001 val hcEvents = Wire(Vec(numPCntHc * coreParams.L2NBanks, new PerfEvent)) 1002 for (i <- 0 until numPCntHc * coreParams.L2NBanks) { 1003 hcEvents(i) := io.perf.perfEventsHc(i) 1004 } 1005 1006 val allHcPerfEvents = hcEvents.map(x => (s"Hc", x.value)) 1007 if (printEventCoding) { 1008 for (((name, inc), i) <- allHcPerfEvents.zipWithIndex) { 1009 println("HuanCun perfEvents Set", name, inc, i) 1010 } 1011 } 1012 1013 val hpmHc = HPerfMonitor(csrevents, hcEvents) 1014 1015 val privState1H = Cat(privState.isModeM, privState.isModeHS, privState.isModeHU, privState.isModeVS, privState.isModeVU) 1016 val countingEn = RegInit(0.U.asTypeOf(Vec(perfCntNum, Bool()))) 1017 for (i <-0 until perfCntNum) { 1018 countingEn(i) := ((~mhpmevents(i).rdata(62, 58)).asUInt & privState1H).orR 1019 } 1020 val allPerfEvents = io.perf.perfEventsFrontend ++ 1021 io.perf.perfEventsBackend ++ 1022 io.perf.perfEventsLsu ++ 1023 hpmHc.getPerf 1024 1025 val ofFromPerfCntVec = Wire(Vec(perfCntNum, Bool())) 1026 val lcofiReqVec = Wire(Vec(perfCntNum, Bool())) 1027 for(i <- 0 until perfCntNum) { 1028 mhpmcounters(i) match { 1029 case m: HasPerfCounterBundle => 1030 m.countingEn := countingEn(i) 1031 m.perf := allPerfEvents(i) 1032 ofFromPerfCntVec(i) := m.toMhpmeventOF 1033 case _ => 1034 } 1035 perfEvents(i) := Mux(mhpmevents(i).w.wen, wdata, (perfEvents(i).head(1).asBool || ofFromPerfCntVec(i)) ## perfEvents(i).tail(1)) 1036 lcofiReqVec(i) := ofFromPerfCntVec(i) && !mhpmevents(i).rdata.head(1) 1037 } 1038 1039 val lcofiReq = lcofiReqVec.asUInt.orR 1040 mip match { 1041 case m: HasLocalInterruptReqBundle => 1042 m.lcofiReq := lcofiReq 1043 case _ => 1044 } 1045 /** 1046 * perf_end 1047 */ 1048 1049 /** 1050 * [[io.status.custom]] connection 1051 */ 1052 io.status.custom.l1I_pf_enable := spfctl.regOut.L1I_PF_ENABLE.asBool 1053 io.status.custom.l2_pf_enable := spfctl.regOut.L2_PF_ENABLE.asBool 1054 io.status.custom.l1D_pf_enable := spfctl.regOut.L1D_PF_ENABLE.asBool 1055 io.status.custom.l1D_pf_train_on_hit := spfctl.regOut.L1D_PF_TRAIN_ON_HIT.asBool 1056 io.status.custom.l1D_pf_enable_agt := spfctl.regOut.L1D_PF_ENABLE_AGT.asBool 1057 io.status.custom.l1D_pf_enable_pht := spfctl.regOut.L1D_PF_ENABLE_PHT.asBool 1058 io.status.custom.l1D_pf_active_threshold := spfctl.regOut.L1D_PF_ACTIVE_THRESHOLD.asUInt 1059 io.status.custom.l1D_pf_active_stride := spfctl.regOut.L1D_PF_ACTIVE_STRIDE.asUInt 1060 io.status.custom.l1D_pf_enable_stride := spfctl.regOut.L1D_PF_ENABLE_STRIDE.asBool 1061 io.status.custom.l2_pf_store_only := spfctl.regOut.L2_PF_STORE_ONLY.asBool 1062 1063 io.status.custom.icache_parity_enable := sfetchctl.regOut.ICACHE_PARITY_ENABLE.asBool 1064 1065 io.status.custom.lvpred_disable := slvpredctl.regOut.LVPRED_DISABLE.asBool 1066 io.status.custom.no_spec_load := slvpredctl.regOut.NO_SPEC_LOAD.asBool 1067 io.status.custom.storeset_wait_store := slvpredctl.regOut.STORESET_WAIT_STORE.asBool 1068 io.status.custom.storeset_no_fast_wakeup := slvpredctl.regOut.STORESET_NO_FAST_WAKEUP.asBool 1069 io.status.custom.lvpred_timeout := slvpredctl.regOut.LVPRED_TIMEOUT.asUInt 1070 1071 io.status.custom.bp_ctrl.ubtb_enable := sbpctl.regOut.UBTB_ENABLE .asBool 1072 io.status.custom.bp_ctrl.btb_enable := sbpctl.regOut.BTB_ENABLE .asBool 1073 io.status.custom.bp_ctrl.bim_enable := sbpctl.regOut.BIM_ENABLE .asBool 1074 io.status.custom.bp_ctrl.tage_enable := sbpctl.regOut.TAGE_ENABLE .asBool 1075 io.status.custom.bp_ctrl.sc_enable := sbpctl.regOut.SC_ENABLE .asBool 1076 io.status.custom.bp_ctrl.ras_enable := sbpctl.regOut.RAS_ENABLE .asBool 1077 io.status.custom.bp_ctrl.loop_enable := sbpctl.regOut.LOOP_ENABLE .asBool 1078 1079 io.status.custom.sbuffer_threshold := smblockctl.regOut.SBUFFER_THRESHOLD.asUInt 1080 io.status.custom.ldld_vio_check_enable := smblockctl.regOut.LDLD_VIO_CHECK_ENABLE.asBool 1081 io.status.custom.soft_prefetch_enable := smblockctl.regOut.SOFT_PREFETCH_ENABLE.asBool 1082 io.status.custom.cache_error_enable := smblockctl.regOut.CACHE_ERROR_ENABLE.asBool 1083 io.status.custom.uncache_write_outstanding_enable := smblockctl.regOut.UNCACHE_WRITE_OUTSTANDING_ENABLE.asBool 1084 io.status.custom.hd_misalign_st_enable := smblockctl.regOut.HD_MISALIGN_ST_ENABLE.asBool 1085 io.status.custom.hd_misalign_ld_enable := smblockctl.regOut.HD_MISALIGN_LD_ENABLE.asBool 1086 1087 io.status.custom.fusion_enable := srnctl.regOut.FUSION_ENABLE.asBool 1088 io.status.custom.wfi_enable := srnctl.regOut.WFI_ENABLE.asBool 1089 1090 io.status.instrAddrTransType.bare := privState.isModeM || 1091 (!privState.isVirtual && satp.regOut.MODE === SatpMode.Bare) || 1092 (privState.isVirtual && vsatp.regOut.MODE === SatpMode.Bare && hgatp.regOut.MODE === HgatpMode.Bare) 1093 io.status.instrAddrTransType.sv39 := !privState.isModeM && !privState.isVirtual && satp.regOut.MODE === SatpMode.Sv39 || 1094 privState.isVirtual && vsatp.regOut.MODE === SatpMode.Sv39 1095 io.status.instrAddrTransType.sv48 := !privState.isModeM && !privState.isVirtual && satp.regOut.MODE === SatpMode.Sv48 || 1096 privState.isVirtual && vsatp.regOut.MODE === SatpMode.Sv48 1097 io.status.instrAddrTransType.sv39x4 := privState.isVirtual && vsatp.regOut.MODE === SatpMode.Bare && hgatp.regOut.MODE === HgatpMode.Sv39x4 1098 io.status.instrAddrTransType.sv48x4 := privState.isVirtual && vsatp.regOut.MODE === SatpMode.Bare && hgatp.regOut.MODE === HgatpMode.Sv48x4 1099 assert(PopCount(io.status.instrAddrTransType.asUInt) === 1.U, "Exactly one inst trans type should be asserted") 1100 1101 private val csrAccess = wen || ren 1102 1103 private val imsicAddrValid = 1104 csrAccess && addr === CSRs.mireg.U && miselect.inIMSICRange || 1105 csrAccess && addr === CSRs.sireg.U && !isModeVS && siselect.inIMSICRange || 1106 csrAccess && (addr === CSRs.sireg.U && isModeVS || addr === CSRs.vsireg.U) && vsiselect.inIMSICRange 1107 1108 private val imsicAddr = Mux1H(Seq( 1109 (csrAccess && addr === CSRs.mireg.U) -> miselect.rdata, 1110 (csrAccess && addr === CSRs.sireg.U && !isModeVS) -> siselect.rdata, 1111 (csrAccess && (addr === CSRs.sireg.U && isModeVS || addr === CSRs.vsireg.U)) -> vsiselect.rdata, 1112 )) 1113 1114 private val imsicAddrPrivState = Mux1H(Seq( 1115 (csrAccess && addr === CSRs.mireg.U) -> PrivState.ModeM, 1116 (csrAccess && addr === CSRs.sireg.U && !isModeVS) -> PrivState.ModeHS, 1117 (csrAccess && (addr === CSRs.sireg.U && isModeVS || addr === CSRs.vsireg.U)) -> PrivState.ModeVS, 1118 )) 1119 1120 private val imsicWdataValid = 1121 mireg.w.wen && miselect.inIMSICRange || 1122 sireg.w.wen && siselect.inIMSICRange || 1123 vsireg.w.wen && vsiselect.inIMSICRange 1124 1125 toAIA.addr.valid := imsicAddrValid 1126 toAIA.addr.bits.addr := imsicAddr 1127 toAIA.addr.bits.prvm := imsicAddrPrivState.PRVM 1128 toAIA.addr.bits.v := imsicAddrPrivState.V 1129 1130 toAIA.wdata.valid := imsicWdataValid 1131 toAIA.wdata.bits.op := io.in.bits.op 1132 toAIA.wdata.bits.data := io.in.bits.src 1133 toAIA.vgein := hstatus.regOut.VGEIN.asUInt 1134 toAIA.mClaim := mtopei.w.wen 1135 toAIA.sClaim := stopei.w.wen 1136 toAIA.vsClaim := vstopei.w.wen 1137 1138 // tlb 1139 io.tlb.satpASIDChanged := GatedValidRegNext(wenLegal && addr === CSRs. satp.U && satp .regOut.ASID =/= satp.w.wdataFields.ASID) 1140 io.tlb.vsatpASIDChanged := GatedValidRegNext(wenLegal && addr === CSRs.vsatp.U && vsatp.regOut.ASID =/= vsatp.w.wdataFields.ASID) 1141 io.tlb.hgatpVMIDChanged := GatedValidRegNext(wenLegal && addr === CSRs.hgatp.U && hgatp.regOut.VMID =/= hgatp.w.wdataFields.VMID) 1142 io.tlb.satp := satp.rdata 1143 io.tlb.vsatp := vsatp.rdata 1144 io.tlb.hgatp := hgatp.rdata 1145 io.tlb.mxr := mstatus.regOut.MXR.asBool 1146 io.tlb.sum := mstatus.regOut.SUM.asBool 1147 io.tlb.vmxr := vsstatus.regOut.MXR.asBool 1148 io.tlb.vsum := vsstatus.regOut.SUM.asBool 1149 io.tlb.spvp := hstatus.regOut.SPVP.asBool 1150 1151 io.tlb.imode := PRVM.asUInt 1152 // when NMIE is zero, force to behave as MPRV is zero 1153 io.tlb.dmode := Mux( 1154 (debugMode && dcsr.regOut.MPRVEN || !debugMode) && mstatus.regOut.MPRV && mnstatus.regOut.NMIE, 1155 mstatus.regOut.MPP.asUInt, 1156 PRVM.asUInt 1157 ) 1158 io.tlb.dvirt := Mux( 1159 (debugMode && dcsr.regOut.MPRVEN || !debugMode) && mstatus.regOut.MPRV && mnstatus.regOut.NMIE && mstatus.regOut.MPP =/= PrivMode.M, 1160 mstatus.regOut.MPV.asUInt, 1161 V.asUInt 1162 ) 1163 io.tlb.mPBMTE := menvcfg.regOut.PBMTE.asBool 1164 io.tlb.hPBMTE := henvcfg.regOut.PBMTE.asBool 1165 1166 io.toDecode.illegalInst.sfenceVMA := isModeHS && mstatus.regOut.TVM || isModeHU 1167 io.toDecode.virtualInst.sfenceVMA := isModeVS && hstatus.regOut.VTVM || isModeVU 1168 io.toDecode.illegalInst.sfencePart := isModeHU 1169 io.toDecode.virtualInst.sfencePart := isModeVU 1170 io.toDecode.illegalInst.hfenceGVMA := isModeHS && mstatus.regOut.TVM || isModeHU 1171 io.toDecode.illegalInst.hfenceVVMA := isModeHU 1172 io.toDecode.virtualInst.hfence := isModeVS || isModeVU 1173 io.toDecode.illegalInst.hlsv := isModeHU && !hstatus.regOut.HU 1174 io.toDecode.virtualInst.hlsv := isModeVS || isModeVU 1175 io.toDecode.illegalInst.fsIsOff := mstatus.regOut.FS === ContextStatus.Off || (isModeVS || isModeVU) && vsstatus.regOut.FS === ContextStatus.Off 1176 io.toDecode.illegalInst.vsIsOff := mstatus.regOut.VS === ContextStatus.Off || (isModeVS || isModeVU) && vsstatus.regOut.VS === ContextStatus.Off 1177 io.toDecode.illegalInst.wfi := isModeHU || !isModeM && mstatus.regOut.TW 1178 io.toDecode.virtualInst.wfi := isModeVS && !mstatus.regOut.TW && hstatus.regOut.VTW || isModeVU && !mstatus.regOut.TW 1179 io.toDecode.illegalInst.frm := frmIsReserved 1180 1181 // Always instantiate basic difftest modules. 1182 if (env.AlwaysBasicDiff || env.EnableDifftest) { 1183 val hartId = io.fromTop.hartId 1184 val trapValid = io.fromRob.trap.valid 1185 val trapNO = Mux(virtualInterruptIsHvictlInject && hasTrap, hvictl.regOut.IID.asUInt, trapHandleMod.io.out.causeNO.ExceptionCode.asUInt) 1186 val interrupt = trapHandleMod.io.out.causeNO.Interrupt.asBool 1187 val hasNMI = nmi && hasTrap 1188 val interruptNO = Mux(interrupt, trapNO, 0.U) 1189 val exceptionNO = Mux(!interrupt, trapNO, 0.U) 1190 val isSv39: Bool = 1191 (isModeHS || isModeHU) && satp.regOut.MODE === SatpMode.Sv39 || 1192 (isModeVS || isModeVU) && vsatp.regOut.MODE === SatpMode.Sv39 1193 val isSv48: Bool = 1194 (isModeHS || isModeHU) && satp.regOut.MODE === SatpMode.Sv48 || 1195 (isModeVS || isModeVU) && vsatp.regOut.MODE === SatpMode.Sv48 1196 val isBare = !isSv39 && !isSv48 1197 val sv39PC = SignExt(trapPC.take(39), XLEN) 1198 val sv48PC = SignExt(trapPC.take(48), XLEN) 1199 val barePC = ZeroExt(trapPC.take(PAddrBits), XLEN) 1200 // When enable virtual memory, the higher bit should fill with the msb of address of Sv39/Sv48/Sv57 1201 val exceptionPC = Mux1H(Seq( 1202 isSv39 -> sv39PC, 1203 isSv48 -> sv48PC, 1204 isBare -> barePC, 1205 )) 1206 1207 val diffArchEvent = DifftestModule(new DiffArchEvent, delay = 3, dontCare = true) 1208 diffArchEvent.coreid := hartId 1209 diffArchEvent.valid := trapValid 1210 diffArchEvent.interrupt := interruptNO 1211 diffArchEvent.exception := exceptionNO 1212 diffArchEvent.exceptionPC := exceptionPC 1213 diffArchEvent.hasNMI := hasNMI 1214 diffArchEvent.virtualInterruptIsHvictlInject := virtualInterruptIsHvictlInject && hasTrap 1215 if (env.EnableDifftest) { 1216 diffArchEvent.exceptionInst := io.fromRob.trap.bits.instr 1217 } 1218 1219 val diffCSRState = DifftestModule(new DiffCSRState) 1220 diffCSRState.coreid := hartId 1221 diffCSRState.privilegeMode := privState.PRVM.asUInt 1222 diffCSRState.mstatus := mstatus.rdata.asUInt 1223 diffCSRState.sstatus := mstatus.sstatus.asUInt 1224 diffCSRState.mepc := mepc.rdata.asUInt 1225 diffCSRState.sepc := sepc.rdata.asUInt 1226 diffCSRState.mtval := mtval.rdata.asUInt 1227 diffCSRState.stval := stval.rdata.asUInt 1228 diffCSRState.mtvec := mtvec.rdata.asUInt 1229 diffCSRState.stvec := stvec.rdata.asUInt 1230 diffCSRState.mcause := mcause.rdata.asUInt 1231 diffCSRState.scause := scause.rdata.asUInt 1232 diffCSRState.satp := satp.rdata.asUInt 1233 diffCSRState.mip := mip.regOut.asUInt 1234 diffCSRState.mie := mie.rdata.asUInt 1235 diffCSRState.mscratch := mscratch.rdata.asUInt 1236 diffCSRState.sscratch := sscratch.rdata.asUInt 1237 diffCSRState.mideleg := mideleg.rdata.asUInt 1238 diffCSRState.medeleg := medeleg.rdata.asUInt 1239 1240 val diffDebugMode = DifftestModule(new DiffDebugMode) 1241 diffDebugMode.coreid := hartId 1242 diffDebugMode.debugMode := debugMode 1243 diffDebugMode.dcsr := dcsr.rdata.asUInt 1244 diffDebugMode.dpc := dpc.rdata.asUInt 1245 diffDebugMode.dscratch0 := dscratch0.rdata.asUInt 1246 diffDebugMode.dscratch1 := dscratch1.rdata.asUInt 1247 1248 val diffTriggerCSRState = DifftestModule(new DiffTriggerCSRState) 1249 diffTriggerCSRState.coreid := hartId 1250 diffTriggerCSRState.tselect := tselect.rdata 1251 diffTriggerCSRState.tdata1 := tdata1.rdata 1252 diffTriggerCSRState.tinfo := tinfo.rdata 1253 diffTriggerCSRState.tcontrol := tcontrol.rdata 1254 1255 val diffVecCSRState = DifftestModule(new DiffVecCSRState) 1256 diffVecCSRState.coreid := hartId 1257 diffVecCSRState.vstart := vstart.rdata.asUInt 1258 diffVecCSRState.vxsat := vcsr.vxsat.asUInt 1259 diffVecCSRState.vxrm := vcsr.vxrm.asUInt 1260 diffVecCSRState.vcsr := vcsr.rdata.asUInt 1261 diffVecCSRState.vl := RegNext(io.fromRob.commit.vl) 1262 diffVecCSRState.vtype := vtype.rdata.asUInt 1263 diffVecCSRState.vlenb := vlenb.rdata.asUInt 1264 1265 val diffFpCSRState = DifftestModule(new DiffFpCSRState) 1266 diffFpCSRState.coreid := hartId 1267 diffFpCSRState.fcsr := fcsr.rdata.asUInt 1268 1269 val diffHCSRState = DifftestModule(new DiffHCSRState) 1270 diffHCSRState.coreid := hartId 1271 diffHCSRState.virtMode := privState.V.asBool 1272 diffHCSRState.mtval2 := mtval2.rdata.asUInt 1273 diffHCSRState.mtinst := mtinst.rdata.asUInt 1274 diffHCSRState.hstatus := hstatus.rdata.asUInt 1275 diffHCSRState.hideleg := hideleg.rdata.asUInt 1276 diffHCSRState.hedeleg := hedeleg.rdata.asUInt 1277 diffHCSRState.hcounteren := hcounteren.rdata.asUInt 1278 diffHCSRState.htval := htval.rdata.asUInt 1279 diffHCSRState.htinst := htinst.rdata.asUInt 1280 diffHCSRState.hgatp := hgatp.rdata.asUInt 1281 diffHCSRState.vsstatus := vsstatus.rdata.asUInt 1282 diffHCSRState.vstvec := vstvec.rdata.asUInt 1283 diffHCSRState.vsepc := vsepc.rdata.asUInt 1284 diffHCSRState.vscause := vscause.rdata.asUInt 1285 diffHCSRState.vstval := vstval.rdata.asUInt 1286 diffHCSRState.vsatp := vsatp.rdata.asUInt 1287 diffHCSRState.vsscratch := vsscratch.rdata.asUInt 1288 1289 } 1290} 1291 1292trait IpIeAliasConnect { 1293 self: NewCSR with MachineLevel with SupervisorLevel with VirtualSupervisorLevel with HypervisorLevel => 1294 1295 mip.fromMvip := mvip.toMip 1296 mip.fromSip := sip.toMip 1297 mip.fromVSip := vsip.toMip 1298 mvip.fromMip := mip.toMvip 1299 mvip.fromSip := sip.toMvip 1300 mvip.fromVSip := vsip.toMvip 1301 hvip.fromMip := mip.toHvip 1302 hvip.fromHip := hip.toHvip 1303 hvip.fromVSip := vsip.toHvip 1304 1305 mie.fromHie := hie.toMie 1306 mie.fromSie := sie.toMie 1307 mie.fromVSie := vsie.toMie 1308 sie.fromVSie := vsie.toSie 1309} 1310 1311object NewCSRMain extends App { 1312 val (config, firrtlOpts, firtoolOpts) = ArgParser.parse( 1313 args :+ "--disable-always-basic-diff" :+ "--dump-fir" :+ "--fpga-platform" :+ "--target" :+ "verilog") 1314 1315 val defaultConfig = config.alterPartial({ 1316 // Get XSCoreParams and pass it to the "small module" 1317 case XSCoreParamsKey => config(XSTileKey).head 1318 }) 1319 1320 Generator.execute( 1321 firrtlOpts :+ "--full-stacktrace" :+ "--target-dir" :+ "backend", 1322 new NewCSR()(defaultConfig), 1323 firtoolOpts 1324 ) 1325 1326 println("done") 1327}