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