提交 93eb7d33 编写于 作者: A Allen

Merge branch 'master' of github.com:RISCVERS/XiangShan into debian-gogogo

[submodule "chisel3"]
path = chisel3
url = https://github.com/ucb-bar/chisel3
[submodule "firrtl"]
path = firrtl
url = https://github.com/ucb-bar/firrtl
[submodule "treadle"]
path = treadle
url = https://github.com/ucb-bar/treadle
[submodule "hardfloat"]
path = hardfloat
url = https://github.com/ucb-bar/berkeley-hardfloat
[submodule "rocket-chip"]
path = rocket-chip
url = https://github.com/chipsalliance/rocket-chip.git
......
Subproject commit c5619b4cc11858377de2329d74adc2ec148b6367
Subproject commit 3d6bdf10d7b740588130e3056c8fd29f4175cadb
import os.Path
import mill._
import mill.modules.Util
import scalalib._
import $ivy.`com.lihaoyi::mill-contrib-buildinfo:$MILL_VERSION`
import $ivy.`com.lihaoyi::mill-contrib-bsp:$MILL_VERSION`
import mill.contrib.buildinfo.BuildInfo
import $file.chisel3.build
import $file.firrtl.build
import $file.treadle.build
import $file.chiseltest.build
import $file.`berkeley-hardfloat`.build
import $file.`rocket-chip`.common
import $file.`api-config-chipsalliance`.`build-rules`.mill.build
val sv = "2.12.12"
object myfirrtl extends firrtl.build.firrtlCrossModule(sv) {
override def millSourcePath = os.pwd / "firrtl"
import scalalib._
import coursier.maven.MavenRepository
object CustomZincWorkerModule extends ZincWorkerModule {
def repositories() = super.repositories ++ Seq(
MavenRepository("https://maven.aliyun.com/repository/public"),
MavenRepository("https://maven.aliyun.com/repository/apache-snapshots")
)
}
object mychisel3 extends chisel3.build.chisel3CrossModule(sv) {
override def millSourcePath = os.pwd / "chisel3"
trait CommonModule extends ScalaModule {
override def scalaVersion = "2.12.10"
def firrtlModule: Option[PublishModule] = Some(myfirrtl)
override def scalacOptions = Seq("-Xsource:2.11")
def treadleModule: Option[PublishModule] = Some(mytreadle)
}
override def zincWorker = CustomZincWorkerModule
object mytreadle extends treadle.build.treadleCrossModule(sv) {
override def millSourcePath = os.pwd / "treadle"
private val macroParadise = ivy"org.scalamacros:::paradise:2.1.0"
def firrtlModule: Option[PublishModule] = Some(myfirrtl)
}
override def compileIvyDeps = Agg(macroParadise)
object mychiseltest extends chiseltest.build.chiseltestCrossModule(sv) {
override def scalaVersion = sv
override def millSourcePath = os.pwd / "chiseltest"
def chisel3Module: Option[PublishModule] = Some(mychisel3)
def treadleModule: Option[PublishModule] = Some(mytreadle)
override def scalacPluginIvyDeps = Agg(macroParadise)
}
object myhardfloat extends `berkeley-hardfloat`.build.hardfloat {
override def scalaVersion = sv
val chisel = Agg(
ivy"edu.berkeley.cs::chisel3:3.4.0"
)
def chisel3Module: Option[PublishModule] = Some(mychisel3)
object `api-config-chipsalliance` extends CommonModule {
override def millSourcePath = super.millSourcePath / "design" / "craft"
}
object myconfig extends `api-config-chipsalliance`.`build-rules`.mill.build.config with PublishModule {
override def scalaVersion = sv
override def millSourcePath = os.pwd / "api-config-chipsalliance" / "design" / "craft"
override def pomSettings = T {
myrocketchip.pomSettings()
}
override def publishVersion = T {
myrocketchip.publishVersion()
}
object hardfloat extends SbtModule with CommonModule {
override def millSourcePath = os.pwd / "berkeley-hardfloat"
override def ivyDeps = super.ivyDeps() ++ chisel
}
object myrocketchip extends `rocket-chip`.common.CommonRocketChip {
override def scalaVersion = sv
object `rocket-chip` extends SbtModule with CommonModule {
override def millSourcePath = os.pwd / "rocket-chip"
override def ivyDeps = super.ivyDeps() ++ Agg(
ivy"${scalaOrganization()}:scala-reflect:${scalaVersion()}",
ivy"org.json4s::json4s-jackson:3.6.1"
) ++ chisel
def chisel3Module: Option[PublishModule] = Some(mychisel3)
object macros extends SbtModule with CommonModule
def hardfloatModule: PublishModule = myhardfloat
override def moduleDeps = super.moduleDeps ++ Seq(
`api-config-chipsalliance`, macros, hardfloat
)
def configModule: PublishModule = myconfig
}
object `block-inclusivecache-sifive` extends CommonModule {
override def ivyDeps = super.ivyDeps() ++ chisel
trait CommonModule extends ScalaModule {
override def scalaVersion = sv
override def scalacOptions = Seq("-Xsource:2.11")
override def moduleDeps: Seq[ScalaModule] = Seq(mychisel3)
override def millSourcePath = super.millSourcePath / 'design / 'craft / 'inclusivecache
private val macroParadise = ivy"org.scalamacros:::paradise:2.1.1"
override def compileIvyDeps = Agg(macroParadise)
override def scalacPluginIvyDeps = Agg(macroParadise)
override def moduleDeps = super.moduleDeps ++ Seq(`rocket-chip`)
}
object myinclusivecache extends CommonModule {
override def millSourcePath = os.pwd / "block-inclusivecache-sifive" / "design" / "craft" / "inclusivecache"
override def moduleDeps = super.moduleDeps ++ Seq(myrocketchip)
object chiseltest extends CommonModule with SbtModule {
override def ivyDeps = super.ivyDeps() ++ Agg(
ivy"edu.berkeley.cs::treadle:1.3.0",
ivy"org.scalatest::scalatest:3.2.0",
ivy"com.lihaoyi::utest:0.7.4"
) ++ chisel
object test extends Tests {
def ivyDeps = Agg(ivy"org.scalacheck::scalacheck:1.14.3")
def testFrameworks = Seq("org.scalatest.tools.Framework")
}
}
object myblocks extends CommonModule with SbtModule {
override def moduleDeps = super.moduleDeps ++ Seq(myrocketchip)
}
object XiangShan extends CommonModule with SbtModule {
override def millSourcePath = millOuterCtx.millSourcePath
override def forkArgs = Seq("-Xmx10G")
override def ivyDeps = super.ivyDeps() ++ chisel
override def moduleDeps = super.moduleDeps ++ Seq(
myrocketchip,
myinclusivecache,
`rocket-chip`,
`block-inclusivecache-sifive`,
chiseltest
)
object test extends Tests {
override def ivyDeps = Agg(
ivy"org.scalatest::scalatest:3.2.0",
)
override def moduleDeps = super.moduleDeps ++ Seq(
mychiseltest
override def ivyDeps = super.ivyDeps() ++ Agg(
ivy"org.scalatest::scalatest:3.2.0"
)
def testFrameworks = Seq(
"org.scalatest.tools.Framework"
)
def testOnly(args: String*) = T.command {
super.runMain("org.scalatest.tools.Runner", args: _*)
}
}
}
}
\ No newline at end of file
Subproject commit 87916d55490ff04691bc59454086c82ed09646b2
Subproject commit cd845bdbfea0c09e9edbf61e651ede5197d8a084
......@@ -170,35 +170,30 @@ class SbufferLRU(n_ways: Int) {
private val state_reg = RegInit(0.U(nBits.W))
def state_read = WireDefault(state_reg)
def get_next_state(state: UInt, touch_way: UInt): UInt = {
// set the row touched with 1, column with 0
def get_next_state(state: UInt, touch_ways: Seq[Valid[UInt]]): UInt = {
val nextState = Wire(Vec(n_ways, UInt(n_ways.W)))
val moreRecentVec = state.asTypeOf(Vec(n_ways, UInt(n_ways.W)))
val wayDec = UIntToOH(touch_way, n_ways)
val wayDecs = touch_ways.map( w => Mux(w.valid, UIntToOH(w.bits, n_ways), 0.U) )
val wayDec = ParallelOR(wayDecs)
val wayUpd = (~wayDec).asUInt()
nextState.zipWithIndex.foreach { case (e, i) =>
e := Mux(i.U === touch_way,
wayUpd,
moreRecentVec(i) & wayUpd
)
e := Mux(wayDec(i), wayUpd, moreRecentVec(i) & wayUpd )
}
nextState.asUInt()
}
def get_next_state(state: UInt, touch_ways: Seq[Valid[UInt]]): UInt = {
touch_ways.foldLeft(state)((prev, touch_way) => Mux(touch_way.valid, get_next_state(prev, touch_way.bits), prev))
}
def access(touch_way: UInt) {
state_reg := get_next_state(state_reg, touch_way)
}
// update the stateRect
def access(touch_ways: Seq[Valid[UInt]]) {
when (ParallelOR(touch_ways.map(_.valid))) {
state_reg := get_next_state(state_reg, touch_ways)
}
}
// get the index of the smallest value from a set of numbers
def get_min_value(xs: Seq[(UInt,UInt)]): (UInt,UInt)= {
xs match {
case Seq(a) => a
......@@ -208,6 +203,7 @@ class SbufferLRU(n_ways: Int) {
}
}
// get the way which is valid and has the least 1
def get_replace_way(state: UInt, sbufferState:Seq[Bool]): UInt = {
val moreRecentVec = state.asTypeOf(Vec(n_ways, UInt(n_ways.W)))
val count = Wire(Vec(n_ways, UInt(log2Up(n_ways).W)))
......@@ -218,11 +214,7 @@ class SbufferLRU(n_ways: Int) {
get_min_value(count.zip((0 until n_ways).map(_.U)))._2
}
def way(sbufferState:Seq[Bool]) = get_replace_way(state_reg,sbufferState)
//def miss = access(way)
def way(sbufferState:Seq[Bool]) = get_replace_way(state_reg, sbufferState)
def hit = {}
def flush() = { state_reg := 0.U(nBits.W) }
//@deprecated("replace 'replace' with 'way' from abstract class ReplacementPolicy","Rocket Chip 2020.05")
//def replace: UInt = way
}
\ No newline at end of file
......@@ -2,7 +2,7 @@ package xiangshan.cache
import chisel3._
import chisel3.util._
import utils.{Code, RandomReplacement, HasTLDump, XSDebug}
import utils.{Code, RandomReplacement, HasTLDump, XSDebug, SRAMTemplate}
import xiangshan.{HasXSLog}
import chipsalliance.rocketchip.config.Parameters
......@@ -105,24 +105,33 @@ class L1plusCacheDataArray extends L1plusCacheModule {
val resp = Output(Vec(nWays, Vec(blockRows, Bits(encRowBits.W))))
})
val singlePort = true
// write is always ready
io.write.ready := true.B
val waddr = (io.write.bits.addr >> blockOffBits).asUInt()
val raddr = (io.read.bits.addr >> blockOffBits).asUInt()
// raddr === waddr is undefined behavior!
// block read in this case
io.read.ready := !io.write.valid || raddr =/= waddr
// for single port SRAM, do not allow read and write in the same cycle
// for dual port SRAM, raddr === waddr is undefined behavior
val rwhazard = if(singlePort) io.write.valid else io.write.valid && waddr === raddr
io.read.ready := !rwhazard
for (w <- 0 until nWays) {
for (r <- 0 until blockRows) {
val array = SyncReadMem(nSets, Bits(encRowBits.W))
val array = Module(new SRAMTemplate(Bits(encRowBits.W), set=nSets, way=1,
shouldReset=false, holdRead=false, singlePort=singlePort))
// data write
when (io.write.bits.way_en(w) && io.write.bits.wmask(r).asBool && io.write.valid) {
val data = io.write.bits.data(r)
array.write(waddr, data)
}
array.io.w.req.valid := io.write.bits.way_en(w) && io.write.bits.wmask(r).asBool && io.write.valid
array.io.w.req.bits.apply(
setIdx=waddr,
data=io.write.bits.data(r),
waymask=1.U)
// data read
io.resp(w)(r) := RegNext(array.read(raddr, io.read.bits.way_en(w)
&& io.read.bits.rmask(r) && io.read.valid).asUInt)
array.io.r.req.valid := io.read.bits.way_en(w) && io.read.bits.rmask(r) && io.read.valid
array.io.r.req.bits.apply(setIdx=raddr)
io.resp(w)(r) := RegNext(array.io.r.resp.data(0))
}
}
......@@ -176,7 +185,8 @@ class L1plusCacheMetadataArray extends L1plusCacheModule {
val rmask = Mux((nWays == 1).B, (-1).asSInt, io.read.bits.way_en.asSInt).asBools
def encTagBits = cacheParams.tagCode.width(tagBits)
val tag_array = SyncReadMem(nSets, Vec(nWays, UInt(encTagBits.W)))
val tag_array = Module(new SRAMTemplate(UInt(encTagBits.W), set=nSets, way=nWays,
shouldReset=false, holdRead=false, singlePort=true))
val valid_array = Reg(Vec(nSets, UInt(nWays.W)))
when (reset.toBool || io.flush) {
for (i <- 0 until nSets) {
......@@ -185,24 +195,37 @@ class L1plusCacheMetadataArray extends L1plusCacheModule {
}
XSDebug("valid_array:%x flush:%d\n",valid_array.asUInt,io.flush)
// tag write
val wen = io.write.valid && !reset.toBool && !io.flush
tag_array.io.w.req.valid := wen
tag_array.io.w.req.bits.apply(
setIdx=waddr,
data=cacheParams.tagCode.encode(wtag),
waymask=VecInit(wmask).asUInt)
when (wen) {
tag_array.write(waddr, VecInit(Array.fill(nWays)(cacheParams.tagCode.encode(wtag))), wmask)
when (wvalid) {
valid_array(waddr) := valid_array(waddr) | io.write.bits.way_en
} .otherwise {
valid_array(waddr) := valid_array(waddr) & ~io.write.bits.way_en
}
}
val rtags = tag_array.read(io.read.bits.idx, io.read.fire()).map(rdata =>
// tag read
tag_array.io.r.req.valid := io.read.fire()
tag_array.io.r.req.bits.apply(setIdx=io.read.bits.idx)
val rtags = tag_array.io.r.resp.data.map(rdata =>
cacheParams.tagCode.decode(rdata).corrected)
for (i <- 0 until nWays) {
io.resp(i).valid := RegNext(valid_array(io.read.bits.idx)(i))
io.resp(i).tag := rtags(i)
}
io.read.ready := !io.write.valid && !reset.toBool && !io.flush
io.write.ready := !reset.toBool && !io.flush
// we use single port SRAM
// do not allow read and write in the same cycle
io.read.ready := !io.write.valid && !reset.toBool && !io.flush && tag_array.io.r.req.ready
io.write.ready := !reset.toBool && !io.flush && tag_array.io.w.req.ready
def dumpRead() = {
when (io.read.fire()) {
......
......@@ -3,7 +3,7 @@ package xiangshan.cache
import chisel3._
import chisel3.util._
import freechips.rocketchip.tilelink.{ClientMetadata, TLClientParameters, TLEdgeOut}
import utils.{Code, RandomReplacement, XSDebug}
import utils.{Code, RandomReplacement, XSDebug, SRAMTemplate}
import scala.math.max
......@@ -178,25 +178,40 @@ abstract class AbstractDataArray extends DCacheModule {
class DuplicatedDataArray extends AbstractDataArray
{
val singlePort = true
// write is always ready
io.write.ready := true.B
val waddr = (io.write.bits.addr >> blockOffBits).asUInt()
for (j <- 0 until LoadPipelineWidth) {
val raddr = (io.read(j).bits.addr >> blockOffBits).asUInt()
// raddr === waddr is undefined behavior!
// block read in this case
io.read(j).ready := !io.write.valid || raddr =/= waddr
// for single port SRAM, do not allow read and write in the same cycle
// for dual port SRAM, raddr === waddr is undefined behavior
val rwhazard = if(singlePort) io.write.valid else io.write.valid && waddr === raddr
io.read(j).ready := !rwhazard
for (w <- 0 until nWays) {
for (r <- 0 until blockRows) {
val array = SyncReadMem(nSets, Vec(rowWords, Bits(encWordBits.W)))
// data write
when (io.write.bits.way_en(w) && io.write.valid) {
val data = VecInit((0 until rowWords) map (i => io.write.bits.data(r)(encWordBits*(i+1)-1,encWordBits*i)))
array.write(waddr, data, io.write.bits.wmask(r).asBools)
val resp = Seq.fill(rowWords)(Wire(Bits(encWordBits.W)))
io.resp(j)(w)(r) := Cat((0 until rowWords).reverse map (k => resp(k)))
for (k <- 0 until rowWords) {
val array = Module(new SRAMTemplate(Bits(encWordBits.W), set=nSets, way=1,
shouldReset=false, holdRead=false, singlePort=singlePort))
// data write
val wen = io.write.valid && io.write.bits.way_en(w) && io.write.bits.wmask(r)(k)
array.io.w.req.valid := wen
array.io.w.req.bits.apply(
setIdx=waddr,
data=io.write.bits.data(r)(encWordBits*(k+1)-1,encWordBits*k),
waymask=1.U)
// data read
val ren = io.read(j).valid && io.read(j).bits.way_en(w) && io.read(j).bits.rmask(r)
array.io.r.req.valid := ren
array.io.r.req.bits.apply(setIdx=raddr)
resp(k) := RegNext(array.io.r.resp.data(0))
}
// data read
io.resp(j)(w)(r) := RegNext(array.read(raddr, io.read(j).bits.way_en(w)
&& io.read(j).bits.rmask(r) && io.read(j).valid).asUInt)
}
}
io.nacks(j) := false.B
......@@ -221,12 +236,21 @@ class L1MetadataArray(onReset: () => L1Metadata) extends DCacheModule {
val metaBits = rstVal.getWidth
val encMetaBits = cacheParams.tagCode.width(metaBits)
val tag_array = SyncReadMem(nSets, Vec(nWays, UInt(encMetaBits.W)))
val tag_array = Module(new SRAMTemplate(UInt(encMetaBits.W), set=nSets, way=nWays,
shouldReset=false, holdRead=false, singlePort=true))
// tag write
val wen = rst || io.write.valid
when (wen) {
tag_array.write(waddr, VecInit(Array.fill(nWays)(cacheParams.tagCode.encode(wdata))), wmask)
}
io.resp := tag_array.read(io.read.bits.idx, io.read.fire()).map(rdata =>
tag_array.io.w.req.valid := wen
tag_array.io.w.req.bits.apply(
setIdx=waddr,
data=cacheParams.tagCode.encode(wdata),
waymask=VecInit(wmask).asUInt)
// tag read
tag_array.io.r.req.valid := io.read.fire()
tag_array.io.r.req.bits.apply(setIdx=io.read.bits.idx)
io.resp := tag_array.io.r.resp.data.map(rdata =>
cacheParams.tagCode.decode(rdata).corrected.asTypeOf(rstVal))
io.read.ready := !wen
......
Subproject commit 0368d83ba472e8fb90057ace0389ff65d96b667a
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册