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