xref: /XiangShan/src/main/scala/xiangshan/backend/fu/NewCSR/CSRAIA.scala (revision 523f2fa2aaf74fc75721a4481c008da507a5cb75)
1package xiangshan.backend.fu.NewCSR
2
3import chisel3._
4import chisel3.util._
5import xiangshan.backend.fu.NewCSR.CSRDefines.{CSRROField => RO, CSRRWField => RW, CSRWARLField => WARL, CSRWLRLField => WLRL, _}
6import CSRConfig._
7import xiangshan.backend.fu.NewCSR.CSRBundles.PrivState
8
9import scala.collection.immutable.SeqMap
10
11trait CSRAIA { self: NewCSR with HypervisorLevel =>
12  val miselect = Module(new CSRModule("Miselevt", new MISelectBundle))
13    .setAddr(0x350)
14
15  val mireg = Module(new CSRModule("Mireg") with HasIregSink {
16    rdata := iregRead.mireg
17  })
18    .setAddr(0x351)
19
20  val mtopei = Module(new CSRModule("Mtopei", new CSRBundle {
21    val id   = RW(26, 16)
22    val prio = RW(10,  0)
23  }))
24    .setAddr(0x35C)
25
26  val mtopi = Module(new CSRModule("Mtopi", new TopIBundle) with HasInterruptFilterSink {
27    rdata.IID := topIR.mtopi.IID
28    rdata.IPRIO := topIR.mtopi.IPRIO
29  })
30    .setAddr(0xFB0)
31
32  val siselect = Module(new CSRModule("Siselect", new SISelectBundle))
33    .setAddr(0x150)
34
35  val sireg = Module(new CSRModule("Sireg") with HasIregSink {
36    rdata := iregRead.sireg
37  })
38    .setAddr(0x151)
39
40  val stopei = Module(new CSRModule("Stopei", new CSRBundle {
41    val id   = RW(26, 16)
42    val prio = RW(10,  0)
43  }))
44    .setAddr(0x15C)
45
46  val stopi = Module(new CSRModule("Stopi", new TopIBundle) with HasInterruptFilterSink {
47    rdata.IID := topIR.stopi.IID
48    rdata.IPRIO := topIR.stopi.IPRIO
49  })
50    .setAddr(0xDB0)
51
52  val vsiselect = Module(new CSRModule("VSiselect", new VSISelectBundle))
53    .setAddr(0x250)
54
55  val vsireg    = Module(new CSRModule("VSireg") with HasIregSink {
56    rdata := iregRead.sireg
57  })
58    .setAddr(0x251)
59
60  val vstopei   = Module(new CSRModule("VStopei", new CSRBundle {
61    val id   = RW(26, 16)
62    val prio = RW(10,  0)
63  }))
64    .setAddr(0x25C)
65
66  val vstopi = Module(new CSRModule("VStopi", new TopIBundle) with HasInterruptFilterSink {
67    rdata := topIR.vstopi
68  })
69    .setAddr(0xEB0)
70
71  val miregiprios: Seq[CSRModule[_]] = Range(0, 0xF, 2).map(num =>
72    Module(new CSRModule(s"Iprio$num"))
73      .setAddr(0x30 + num)
74  )
75
76  val siregiprios: Seq[CSRModule[_]] = Range(0, 0xF, 2).map(num =>
77    Module(new CSRModule(s"Iprio$num"))
78      .setAddr(0x30 + num)
79  )
80
81  val vsiregiprios: Seq[CSRModule[_]] = Range(0, 0xF, 2).map(num =>
82    Module(new CSRModule(s"Iprio$num"))
83      .setAddr(0x30 + num)
84  )
85
86  val aiaCSRMods = Seq(
87    miselect,
88    mireg,
89    mtopei,
90    mtopi,
91    siselect,
92    sireg,
93    stopei,
94    stopi,
95    vsiselect,
96    vsireg,
97    vstopi,
98    vstopei,
99  )
100
101  val aiaCSRMap = SeqMap.from(
102    aiaCSRMods.map(csr => (csr.addr -> (csr.w -> csr.rdata.asInstanceOf[CSRBundle].asUInt))).iterator
103  )
104
105  val aiaCSROutMap: SeqMap[Int, UInt] = SeqMap.from(
106    aiaCSRMods.map(csr => (csr.addr -> csr.regOut.asInstanceOf[CSRBundle].asUInt)).iterator
107  )
108
109  private val miregRead = Mux1H(
110    miregiprios.map(prio => (miselect.rdata.ALL.asUInt === prio.addr.U) -> prio.rdata.asInstanceOf[CSRBundle])
111  ).asUInt
112
113  private val siregRead = Mux1H(
114    siregiprios.map(prio => (siselect.rdata.ALL.asUInt === prio.addr.U) -> prio.rdata.asInstanceOf[CSRBundle])
115  ).asUInt
116
117  private val vsiregRead = Mux1H(
118    vsiregiprios.map(prio => (miselect.rdata.ALL.asUInt === prio.addr.U) -> prio.rdata.asInstanceOf[CSRBundle])
119  ).asUInt
120
121  aiaCSRMods.foreach { mod =>
122    mod match {
123      case m: HasIregSink =>
124        m.iregRead.mireg := miregRead
125        m.iregRead.sireg := siregRead
126        m.iregRead.vsireg := vsiregRead
127      case _ =>
128    }
129  }
130}
131
132class ISelectField(final val maxValue: Int, reserved: Seq[Range]) extends CSREnum with WARLApply {
133  override def isLegal(enum: CSREnumType): Bool = {
134    !reserved.map(range => enum.asUInt >= range.start.U && enum.asUInt <= range.end.U).reduce(_ || _)
135  }
136}
137
138object VSISelectField extends ISelectField(
139  0x1FF,
140  reserved = Seq(
141    Range.inclusive(0x000, 0x02F),
142    Range.inclusive(0x040, 0x06F),
143    Range.inclusive(0x100, 0x1FF),
144  ),
145)
146
147object MISelectField extends ISelectField(
148  maxValue = 0xFF,
149  reserved = Seq(
150    Range.inclusive(0x00, 0x2F),
151    Range.inclusive(0x40, 0x6F),
152  ),
153)
154
155object SISelectField extends ISelectField(
156  maxValue = 0xFF,
157  reserved = Seq(
158    Range.inclusive(0x00, 0x2F),
159    Range.inclusive(0x40, 0x6F),
160  ),
161)
162
163class VSISelectBundle extends CSRBundle {
164  val ALL = VSISelectField(log2Up(0x1FF), 0, null)
165}
166
167class MISelectBundle extends CSRBundle {
168  val ALL = MISelectField(log2Up(0xFF), 0, null)
169}
170
171class SISelectBundle extends CSRBundle {
172  val ALL = SISelectField(log2Up(0xFF), 0, null)
173}
174
175class TopIBundle extends CSRBundle {
176  val IID   = RO(27, 16)
177  val IPRIO = RO(7, 0)
178}
179
180class TopEIBundle extends CSRBundle {
181  val IID   = RW(26, 16)
182  val IPRIO = RW(10, 0)
183}
184
185class IprioBundle extends CSRBundle {
186  val ALL = RW(63, 0).withReset(0.U)
187}
188
189class CSRToAIABundle extends Bundle {
190  private final val AddrWidth = 12
191
192  val addr = ValidIO(new Bundle {
193    val addr = UInt(AddrWidth.W)
194    val v = VirtMode()
195    val prvm = PrivMode()
196  })
197
198  val vgein = UInt(VGEINWidth.W)
199
200  val wdata = ValidIO(new Bundle {
201    val data = UInt(XLEN.W)
202  })
203
204  val mClaim = Bool()
205  val sClaim = Bool()
206  val vsClaim = Bool()
207}
208
209class AIAToCSRBundle extends Bundle {
210  val rdata = ValidIO(new Bundle {
211    val data = UInt(XLEN.W)
212    val illegal = Bool()
213  })
214  val mtopei = ValidIO(new TopEIBundle)
215  val stopei = ValidIO(new TopEIBundle)
216  val vstopei = ValidIO(new TopEIBundle)
217}
218
219trait HasAIABundle { self: CSRModule[_] =>
220  val aiaToCSR = IO(Input(new AIAToCSRBundle))
221}
222
223trait HasInterruptFilterSink { self: CSRModule[_] =>
224  val topIR = IO(new Bundle {
225    val mtopi = Input(new TopIBundle)
226    val stopi = Input(new TopIBundle)
227    val vstopi = Input(new TopIBundle)
228  })
229}
230
231trait HasISelectBundle { self: CSRModule[_] =>
232  val privState = IO(Input(new PrivState))
233  val miselect = IO(Input(new MISelectBundle))
234  val siselect = IO(Input(new SISelectBundle))
235  val mireg = IO(Input(UInt(XLEN.W)))
236  val sireg = IO(Input(UInt(XLEN.W)))
237}
238
239trait HasIregSink { self: CSRModule[_] =>
240  val iregRead = IO(Input(new Bundle {
241    val mireg = UInt(XLEN.W) // Todo: check if use ireg bundle, and shrink the width
242    val sireg = UInt(XLEN.W)
243    val vsireg = UInt(XLEN.W)
244  }))
245}