xref: /XiangShan/src/main/scala/xiangshan/backend/fu/NewCSR/CSRPermitModule.scala (revision 40ac5bb1842d44eb247ef164881a9d06c158a05a)
1package xiangshan.backend.fu.NewCSR
2
3import chisel3._
4import chisel3.util._
5import chisel3.util.experimental.decode.TruthTable
6import xiangshan.backend.fu.NewCSR.CSRBundles.PrivState
7
8class CSRPermitModule extends Module {
9  val io = IO(new CSRPermitIO)
10
11  private val (ren, wen, addr, privState) = (
12    io.in.csrAccess.ren,
13    io.in.csrAccess.wen,
14    io.in.csrAccess.addr,
15    io.in.privState
16  )
17
18  private val csrAccess = WireInit(ren || wen)
19
20  private val (mret, sret) = (
21    io.in.mret,
22    io.in.sret,
23  )
24
25  private val (tsr, vtsr) = (
26    io.in.status.tsr,
27    io.in.status.vtsr,
28  )
29
30  private val csrIsRO = addr(11, 10) === "b11".U
31
32  private val accessTable = TruthTable(Seq(
33    //       V PRVM ADDR
34    BitPat("b?__00___00") -> BitPat.Y(), // HU/VU access U
35    BitPat("b?__00___??") -> BitPat.N(), // HU/VU access the others
36    BitPat("b1__01___00") -> BitPat.Y(), // VS access U
37    BitPat("b1__01___01") -> BitPat.Y(), // VS access S
38    BitPat("b1__01___??") -> BitPat.N(), // VS access the others
39    BitPat("b0__01___11") -> BitPat.N(), // HS access M
40    BitPat("b0__01___??") -> BitPat.Y(), // HS access the others
41    BitPat("b0__11___??") -> BitPat.Y(), // M  access any
42  ), BitPat.N())
43
44  private val privilegeLegal = chisel3.util.experimental.decode.decoder(
45    privState.V.asUInt ## privState.PRVM.asUInt ## addr(9, 8),
46    accessTable
47  ).asBool
48
49  private val rwIllegal = csrIsRO && wen
50
51  private val csrAccessIllegal = (!privilegeLegal || rwIllegal)
52
53  private val mretIllegal = !privState.isModeM
54
55  private val sretIllegal = sret && (
56    privState.isModeHS && tsr || privState.isModeVS && vtsr || privState.isModeHUorVU
57  )
58
59  io.out.illegal := csrAccess && csrAccessIllegal || mret && mretIllegal || sret && sretIllegal
60
61  // Todo: check correct
62  io.out.EX_II := io.out.illegal && !privState.isVirtual
63  io.out.EX_VI := io.out.illegal && privState.isVirtual
64
65  io.out.hasLegalWen := io.in.csrAccess.wen && !csrAccessIllegal
66  io.out.hasLegalMret := mret && !mretIllegal
67  io.out.hasLegalSret := sret && !sretIllegal
68}
69
70class CSRPermitIO extends Bundle {
71  val in = Input(new Bundle {
72    val csrAccess = new Bundle {
73      val ren = Bool()
74      val wen = Bool()
75      val addr = UInt(12.W)
76    }
77    val privState = new PrivState
78    val mret = Bool()
79    val sret = Bool()
80    val status = new Bundle {
81      // Trap SRET
82      val tsr = Bool()
83      // Virtual Trap SRET
84      val vtsr = Bool()
85    }
86  })
87
88  val out = Output(new Bundle {
89    val hasLegalWen = Bool()
90    val hasLegalMret = Bool()
91    val hasLegalSret = Bool()
92    // Todo: split illegal into EX_II and EX_VI
93    val illegal = Bool()
94    val EX_II = Bool()
95    val EX_VI = Bool()
96  })
97}
98