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