提交 73faecdc 编写于 作者: X Xuan Hu

RegFile: add vector regfile

上级 912e2179
......@@ -129,6 +129,8 @@ case class XSCoreParameters
EnableLoadFastWakeUp: Boolean = true, // NOTE: not supported now, make it false
IssQueSize: Int = 16,
NRPhyRegs: Int = 192,
IntPhyRegs: Int = 192,
VfPhyRegs: Int = 192,
LoadQueueSize: Int = 80,
LoadQueueNWriteBanks: Int = 8,
StoreQueueSize: Int = 64,
......@@ -373,6 +375,10 @@ trait HasXSParameter {
val EnableLoadFastWakeUp = coreParams.EnableLoadFastWakeUp
val NRPhyRegs = coreParams.NRPhyRegs
val PhyRegIdxWidth = log2Up(NRPhyRegs)
val IntPhyRegs = coreParams.IntPhyRegs
val VfPhyRegs = coreParams.VfPhyRegs
val IntPregIdxWidth = log2Up(IntPhyRegs)
val VfPregIdxWidth = log2Up(VfPhyRegs)
val RobSize = coreParams.RobSize
val IntRefCounterWidth = log2Ceil(RobSize)
val LoadQueueSize = coreParams.LoadQueueSize
......
......@@ -27,7 +27,7 @@ import xiangshan.backend.dispatch.Dispatch2Rs
import xiangshan.backend.exu.ExuConfig
import xiangshan.backend.fu.FuConfig
import xiangshan.backend.issue.{BaseReservationStationWrapper, RSParams, RSMod}
import xiangshan.backend.regfile.{Regfile, RfReadPort}
import xiangshan.backend.regfile.{IntRegFile, VfRegFile, RfReadPort}
import xiangshan.backend.rename.{BusyTable, BusyTableReadIO}
import xiangshan.mem.{LsqEnqCtrl, LsqEnqIO, MemWaitUpdateReq, SqPtr}
import chisel3.ExcitingUtils
......@@ -272,11 +272,11 @@ class SchedulerImp(outer: Scheduler) extends LazyModuleImp(outer) with HasXSPara
// special ports for RS that needs to read from other schedulers
// In: read response from other schedulers
// Out: read request to other schedulers
val intRfReadIn = if (!outer.hasIntRf && outer.numIntRfReadPorts > 0) Some(Vec(outer.numIntRfReadPorts, Flipped(new RfReadPort(XLEN)))) else None
val intRfReadOut = if (outer.outIntRfReadPorts > 0) Some(Vec(outer.outIntRfReadPorts, new RfReadPort(XLEN))) else None
val fpRfReadIn = if (!outer.hasFpRf && outer.numFpRfReadPorts > 0) Some(Vec(outer.numFpRfReadPorts, Flipped(new RfReadPort(XLEN)))) else None
val intRfReadIn = if (!outer.hasIntRf && outer.numIntRfReadPorts > 0) Some(Vec(outer.numIntRfReadPorts, Flipped(new RfReadPort(XLEN, IntPregIdxWidth)))) else None
val intRfReadOut = if (outer.outIntRfReadPorts > 0) Some(Vec(outer.outIntRfReadPorts, new RfReadPort(XLEN, IntPregIdxWidth))) else None
val fpRfReadIn = if (!outer.hasFpRf && outer.numFpRfReadPorts > 0) Some(Vec(outer.numFpRfReadPorts, Flipped(new RfReadPort(VLEN, VfPregIdxWidth)))) else None
val fpStateReadIn = if (!outer.hasFpRf && outer.numFpRfReadPorts > 0) Some(Vec(outer.numFpRfReadPorts, Flipped(new BusyTableReadIO))) else None
val fpRfReadOut = if (outer.outFpRfReadPorts > 0) Some(Vec(outer.outFpRfReadPorts, new RfReadPort(XLEN))) else None
val fpRfReadOut = if (outer.outFpRfReadPorts > 0) Some(Vec(outer.outFpRfReadPorts, new RfReadPort(VLEN, VfPregIdxWidth))) else None
val fpStateReadOut = if (outer.outFpRfReadPorts > 0) Some(Vec(outer.outFpRfReadPorts, new BusyTableReadIO)) else None
val loadFastMatch = if (numLoadPorts > 0) Some(Vec(numLoadPorts, Output(UInt(exuParameters.LduCnt.W)))) else None
val loadFastImm = if (numLoadPorts > 0) Some(Vec(numLoadPorts, Output(UInt(12.W)))) else None
......@@ -396,12 +396,14 @@ class SchedulerImp(outer: Scheduler) extends LazyModuleImp(outer) with HasXSPara
val debugRead = if (isInt) io.extra.debug_int_rat else io.extra.debug_fp_rat
if (isInt) {
val wen = wbPorts.map(wb =>wb.valid && wb.bits.uop.ctrl.rfWen)
Regfile(NRPhyRegs, readIntRf, wen, waddr, wdata, true, debugRead = Some(debugRead))
IntRegFile(IntPhyRegs, readIntRf, wen, waddr, wdata, debugReadAddr = Some(debugRead))
}
else {
// For floating-point function units, every instruction writes either int or fp regfile.
val wen = wbPorts.map(_.valid)
Regfile(NRPhyRegs, readFpRf, wen, waddr, wdata, false, debugRead = Some(debugRead))
// Multi-wen for each regfile
val wen = Seq.fill(VLEN/XLEN)(wbPorts.map(_.valid))
val widenWdata = wdata.map(ZeroExt(_, VLEN))
VfRegFile(VfPhyRegs, VLEN/XLEN, readFpRf, wen, waddr, widenWdata, debugReadAddr = Some(debugRead))
}
}
......
......@@ -22,14 +22,14 @@ import chisel3.experimental.ExtModule
import chisel3.util._
import xiangshan._
class RfReadPort(len: Int)(implicit p: Parameters) extends XSBundle {
val addr = Input(UInt(PhyRegIdxWidth.W))
class RfReadPort(len: Int, width: Int)(implicit p: Parameters) extends XSBundle {
val addr = Input(UInt(width.W))
val data = Output(UInt(len.W))
}
class RfWritePort(len: Int)(implicit p: Parameters) extends XSBundle {
class RfWritePort(len: Int, width: Int)(implicit p: Parameters) extends XSBundle {
val wen = Input(Bool())
val addr = Input(UInt(PhyRegIdxWidth.W))
val addr = Input(UInt(width.W))
val data = Input(UInt(len.W))
}
......@@ -38,12 +38,13 @@ class Regfile
numReadPorts: Int,
numWritePorts: Int,
hasZero: Boolean,
len: Int
len: Int,
width: Int,
)(implicit p: Parameters) extends XSModule {
val io = IO(new Bundle() {
val readPorts = Vec(numReadPorts, new RfReadPort(len))
val writePorts = Vec(numWritePorts, new RfWritePort(len))
val debug_rports = Vec(32, new RfReadPort(len))
val readPorts = Vec(numReadPorts, new RfReadPort(len, width))
val writePorts = Vec(numWritePorts, new RfWritePort(len, width))
val debug_rports = Vec(32, new RfReadPort(len, width))
})
println("Regfile: size:" + NRPhyRegs + " read: " + numReadPorts + " write: " + numWritePorts)
......@@ -67,14 +68,14 @@ class Regfile
object Regfile {
def apply(
numEntries: Int,
raddr: Seq[UInt],
wen: Seq[Bool],
waddr: Seq[UInt],
wdata: Seq[UInt],
hasZero: Boolean,
withReset: Boolean = false,
debugRead: Option[Seq[UInt]] = None
numEntries : Int,
raddr : Seq[UInt],
wen : Seq[Bool],
waddr : Seq[UInt],
wdata : Seq[UInt],
hasZero : Boolean,
withReset : Boolean = false,
debugReadAddr: Option[Seq[UInt]] = None,
)(implicit p: Parameters): Seq[UInt] = {
val numReadPorts = raddr.length
val numWritePorts = wen.length
......@@ -82,11 +83,15 @@ object Regfile {
require(wen.length == wdata.length)
val dataBits = wdata.map(_.getWidth).min
require(wdata.map(_.getWidth).min == wdata.map(_.getWidth).max, s"dataBits != $dataBits")
val regfile = Module(new Regfile(numReadPorts, numWritePorts, hasZero, dataBits))
val addrBits = waddr.map(_.getWidth).min
require(waddr.map(_.getWidth).min == waddr.map(_.getWidth).max, s"addrBits != $addrBits")
val regfile = Module(new Regfile(numReadPorts, numWritePorts, hasZero, dataBits, addrBits))
val rdata = regfile.io.readPorts.zip(raddr).map { case (rport, addr) =>
rport.addr := addr
rport.data
}
regfile.io.writePorts.zip(wen).zip(waddr).zip(wdata).foreach{ case (((wport, en), addr), data) =>
wport.wen := en
wport.addr := addr
......@@ -111,10 +116,76 @@ object Regfile {
}
}
regfile.io.debug_rports := DontCare
val debug_rdata = regfile.io.debug_rports.zip(debugRead.getOrElse(Seq())).map { case (rport, addr) =>
val debug_rdata = regfile.io.debug_rports.zip(debugReadAddr.getOrElse(Seq())).map { case (rport, addr) =>
rport.addr := addr
rport.data
}
rdata ++ debug_rdata
}
}
object IntRegFile {
def apply(
numEntries : Int,
raddr : Seq[UInt],
wen : Seq[Bool],
waddr : Seq[UInt],
wdata : Seq[UInt],
withReset : Boolean = false,
debugReadAddr: Option[Seq[UInt]] = None,
)(implicit p: Parameters): Seq[UInt] = {
Regfile(
numEntries, raddr, wen, waddr, wdata,
hasZero = true, withReset, debugReadAddr)
}
}
object VfRegFile {
def apply(
numEntries : Int,
splitNum : Int,
raddr : Seq[UInt],
wen : Seq[Seq[Bool]],
waddr : Seq[UInt],
wdata : Seq[UInt],
withReset : Boolean = false,
debugReadAddr: Option[Seq[UInt]] = None,
)(implicit p: Parameters) : Seq[UInt] = {
require(splitNum >= 1, "splitNum should be no less than 1")
require(splitNum == wen.length, "splitNum should be equal to length of wen vec")
if (splitNum == 1) {
Regfile(numEntries, raddr, wen.head, waddr, wdata,
hasZero = false, withReset, debugReadAddr)
}
val dataWidth = 64
val numReadPorts = raddr.length + debugReadAddr.getOrElse(Seq()).length
require(splitNum > 1 && wdata.head.getWidth == dataWidth * splitNum)
val wdataVec = Wire(Vec(splitNum, Vec(wdata.length, UInt(dataWidth.W))))
var rdataVec = Wire(Vec(splitNum, Vec(numReadPorts, UInt(dataWidth.W))))
for (i <- 0 until splitNum) {
wdataVec(i) := wdata.map(_((i + 1) * dataWidth - 1, i * dataWidth))
rdataVec(i) := Regfile(numEntries, raddr, wen(i), waddr, wdataVec(i),
hasZero = false, withReset, debugReadAddr)
}
val rdata = Wire(Vec(numReadPorts, UInt(wdata.head.getWidth.W)))
for (i <- 0 until rdata.length) {
rdata(i) := Cat(rdataVec.map(_(i)))
}
rdata
}
// // for dummy usage
// def apply(
// numEntries : Int,
// raddr : Vec[UInt],
// wen : Vec[Bool],
// waddr : Vec[UInt],
// wdata : Vec[UInt],
// withReset : Boolean = false,
// debugReadAddr: Option[Vec[UInt]] = None,
// )(implicit p: Parameters) : Unit = {
// Regfile(numEntries, raddr, wen, waddr, wdata,
// hasZero = false, withReset, debugReadAddr)
// }
}
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册