rocket: change connection between rocketchip and coreplex
* rtc and dtm are now crossed half-and-half on the two sides * groundtest no longer uses riscv platform traits
This commit is contained in:
@ -35,7 +35,6 @@ trait HasCoreplexParameters {
|
||||
lazy val outerMMIOParams = p.alterPartial({ case TLId => "L2toMMIO" })
|
||||
lazy val globalAddrMap = p(rocketchip.GlobalAddrMap)
|
||||
lazy val nTiles = p(uncore.devices.NTiles)
|
||||
lazy val nSlaves = p(rocketchip.NCoreplexExtClients)
|
||||
lazy val nMemChannels = p(NMemoryChannels)
|
||||
lazy val hasSupervisor = p(rocket.UseVM)
|
||||
lazy val nTrackersPerBank = p(NTrackersPerBank)
|
||||
@ -53,7 +52,7 @@ abstract class BareCoreplexModule[+L <: BareCoreplex, +B <: BareCoreplexBundle[L
|
||||
}
|
||||
|
||||
trait CoreplexNetwork extends HasCoreplexParameters {
|
||||
this: BareCoreplex =>
|
||||
val module: CoreplexNetworkModule
|
||||
|
||||
val l1tol2 = LazyModule(new TLXbar)
|
||||
val l1tol2_beatBytes = p(TLKey("L2toMMIO")).dataBitsPerBeat/8
|
||||
@ -79,9 +78,7 @@ trait CoreplexNetwork extends HasCoreplexParameters {
|
||||
}
|
||||
|
||||
trait CoreplexNetworkBundle extends HasCoreplexParameters {
|
||||
this: {
|
||||
val outer: CoreplexNetwork
|
||||
} =>
|
||||
val outer: CoreplexNetwork
|
||||
|
||||
implicit val p = outer.p
|
||||
val mmio = outer.mmio.bundleOut
|
||||
@ -89,12 +86,15 @@ trait CoreplexNetworkBundle extends HasCoreplexParameters {
|
||||
}
|
||||
|
||||
trait CoreplexNetworkModule extends HasCoreplexParameters {
|
||||
this: BareCoreplexModule[BareCoreplex, BareCoreplexBundle[BareCoreplex]] =>
|
||||
val outer: CoreplexNetwork
|
||||
val io: CoreplexNetworkBundle
|
||||
|
||||
implicit val p = outer.p
|
||||
}
|
||||
|
||||
trait BankedL2CoherenceManagers {
|
||||
this: CoreplexNetwork =>
|
||||
trait BankedL2CoherenceManagers extends CoreplexNetwork {
|
||||
val module: BankedL2CoherenceManagersModule
|
||||
|
||||
require (isPow2(nBanksPerMemChannel))
|
||||
require (isPow2(l1tol2_lineBytes))
|
||||
|
||||
@ -116,100 +116,28 @@ trait BankedL2CoherenceManagers {
|
||||
}
|
||||
}
|
||||
|
||||
trait BankedL2CoherenceManagersBundle {
|
||||
this: CoreplexNetworkBundle {
|
||||
val outer: BankedL2CoherenceManagers
|
||||
} =>
|
||||
trait BankedL2CoherenceManagersBundle extends CoreplexNetworkBundle {
|
||||
val outer: BankedL2CoherenceManagers
|
||||
|
||||
require (nMemChannels <= 1, "Seq in Chisel Bundle needed to support > 1") // !!!
|
||||
val mem = outer.mem.map(_.bundleOut).toList.headOption // .headOption should be removed !!!
|
||||
}
|
||||
|
||||
trait BankedL2CoherenceManagersModule {
|
||||
this: CoreplexNetworkModule {
|
||||
val outer: BankedL2CoherenceManagers
|
||||
val io: BankedL2CoherenceManagersBundle
|
||||
} =>
|
||||
}
|
||||
|
||||
trait CoreplexRISCVPlatform {
|
||||
this: CoreplexNetwork =>
|
||||
|
||||
val lazyTiles = List.tabulate(p(NTiles)){ i => LazyModule(new RocketTile(i)) }
|
||||
val debug = LazyModule(new TLDebugModule())
|
||||
val plic = LazyModule(new TLPLIC(hasSupervisor, maxPriorities = 7))
|
||||
val clint = LazyModule(new CoreplexLocalInterrupter)
|
||||
val tileIntNodes = lazyTiles.map { _ => IntInternalOutputNode() } // this should be moved into the Tile...
|
||||
|
||||
debug.node := TLFragmenter(cbus_beatBytes, cbus_lineBytes)(cbus.node)
|
||||
plic.node := TLFragmenter(cbus_beatBytes, cbus_lineBytes)(cbus.node)
|
||||
clint.node := TLFragmenter(cbus_beatBytes, cbus_lineBytes)(cbus.node)
|
||||
|
||||
plic.intnode := mmioInt
|
||||
tileIntNodes.foreach { _ := plic.intnode }
|
||||
}
|
||||
|
||||
trait CoreplexRISCVPlatformBundle {
|
||||
this: CoreplexNetworkBundle {
|
||||
val outer: CoreplexRISCVPlatform
|
||||
} =>
|
||||
|
||||
val slave = Vec(nSlaves, new ClientUncachedTileLinkIO()(innerParams)).flip
|
||||
val debug = new DebugBusIO().flip
|
||||
val rtcTick = Bool(INPUT)
|
||||
val resetVector = UInt(INPUT, p(XLen))
|
||||
val success = Bool(OUTPUT) // used for testing
|
||||
}
|
||||
|
||||
trait CoreplexRISCVPlatformModule {
|
||||
this: CoreplexNetworkModule {
|
||||
val outer: CoreplexNetwork with CoreplexRISCVPlatform
|
||||
val io: CoreplexRISCVPlatformBundle
|
||||
} =>
|
||||
|
||||
val tiles = outer.lazyTiles.map(_.module)
|
||||
|
||||
// Remaining external coreplex signals
|
||||
outer.debug.module.io.db <> io.debug
|
||||
outer.clint.module.io.rtcTick := io.rtcTick
|
||||
io.success := Bool(false) // Coreplex doesn't know when to stop running
|
||||
|
||||
println("\nGenerated Address Map")
|
||||
for (entry <- p(rocketchip.GlobalAddrMap).flatten) {
|
||||
val name = entry.name
|
||||
val start = entry.region.start
|
||||
val end = entry.region.start + entry.region.size - 1
|
||||
val prot = entry.region.attr.prot
|
||||
val protStr = (if ((prot & AddrMapProt.R) > 0) "R" else "") +
|
||||
(if ((prot & AddrMapProt.W) > 0) "W" else "") +
|
||||
(if ((prot & AddrMapProt.X) > 0) "X" else "")
|
||||
val cacheable = if (entry.region.attr.cacheable) " [C]" else ""
|
||||
println(f"\t$name%s $start%x - $end%x, $protStr$cacheable")
|
||||
}
|
||||
|
||||
// Create and export the ConfigString
|
||||
val managers = outer.l1tol2.node.edgesIn(0).manager.managers
|
||||
val configString = rocketchip.GenerateConfigString(p, outer.clint, outer.plic, managers)
|
||||
// Allow something else to have override the config string
|
||||
if (!ConfigStringOutput.contents.isDefined) {
|
||||
ConfigStringOutput.contents = Some(configString)
|
||||
}
|
||||
println(s"\nGenerated Configuration String\n${ConfigStringOutput.contents.get}")
|
||||
trait BankedL2CoherenceManagersModule extends CoreplexNetworkModule {
|
||||
val outer: BankedL2CoherenceManagers
|
||||
val io: BankedL2CoherenceManagersBundle
|
||||
}
|
||||
|
||||
abstract class BaseCoreplex(implicit p: Parameters) extends BareCoreplex
|
||||
with CoreplexNetwork
|
||||
with BankedL2CoherenceManagers
|
||||
with CoreplexRISCVPlatform {
|
||||
with BankedL2CoherenceManagers {
|
||||
override lazy val module = new BaseCoreplexModule(this, () => new BaseCoreplexBundle(this))
|
||||
}
|
||||
|
||||
class BaseCoreplexBundle[+L <: BaseCoreplex](_outer: L) extends BareCoreplexBundle(_outer)
|
||||
with CoreplexNetworkBundle
|
||||
with BankedL2CoherenceManagersBundle
|
||||
with CoreplexRISCVPlatformBundle
|
||||
|
||||
class BaseCoreplexModule[+L <: BaseCoreplex, +B <: BaseCoreplexBundle[L]](_outer: L, _io: () => B) extends BareCoreplexModule(_outer, _io)
|
||||
with CoreplexNetworkModule
|
||||
with BankedL2CoherenceManagersModule
|
||||
with CoreplexRISCVPlatformModule
|
||||
|
@ -13,7 +13,7 @@ import uncore.converters._
|
||||
import rocket._
|
||||
import util._
|
||||
import util.ConfigUtils._
|
||||
import rocketchip.{GlobalAddrMap, NCoreplexExtClients}
|
||||
import rocketchip.{GlobalAddrMap}
|
||||
import cde.{Parameters, Config, Dump, Knob, CDEMatchError}
|
||||
|
||||
class BaseCoreplexConfig extends Config (
|
||||
@ -104,7 +104,7 @@ class BaseCoreplexConfig extends Config (
|
||||
else new MESICoherence(site(L2DirectoryRepresentation))),
|
||||
nManagers = site(NBanksPerMemoryChannel)*site(NMemoryChannels) + 1 /* MMIO */,
|
||||
nCachingClients = 1,
|
||||
nCachelessClients = site(NCoreplexExtClients) + 1,
|
||||
nCachelessClients = 1,
|
||||
maxClientXacts = max_int(
|
||||
// L1 cache
|
||||
site(DCacheKey).nMSHRs + 1 /* IOMSHR */,
|
||||
|
@ -10,8 +10,7 @@ import uncore.util._
|
||||
import util._
|
||||
import rocket._
|
||||
|
||||
trait BroadcastL2 {
|
||||
this: CoreplexNetwork =>
|
||||
trait BroadcastL2 extends BankedL2CoherenceManagers {
|
||||
def l2ManagerFactory() = {
|
||||
val bh = LazyModule(new TLBroadcast(l1tol2_lineBytes, nTrackersPerBank))
|
||||
(bh.node, bh.node)
|
||||
@ -20,45 +19,23 @@ trait BroadcastL2 {
|
||||
|
||||
/////
|
||||
|
||||
trait DirectConnection {
|
||||
this: CoreplexNetwork with CoreplexRISCVPlatform =>
|
||||
|
||||
lazyTiles foreach { t =>
|
||||
t.slaveNode.foreach { _ := cbus.node }
|
||||
l1tol2.node := TLBuffer(1,1,2,2,0)(TLHintHandler()(t.cachedOut))
|
||||
l1tol2.node := TLBuffer(1,0,0,2,0)(TLHintHandler()(t.uncachedOut))
|
||||
}
|
||||
}
|
||||
|
||||
trait DirectConnectionModule {
|
||||
this: CoreplexNetworkModule with CoreplexRISCVPlatformModule {
|
||||
val outer: CoreplexNetwork with CoreplexRISCVPlatform
|
||||
val io: CoreplexRISCVPlatformBundle
|
||||
} =>
|
||||
|
||||
// connect coreplex-internal interrupts to tiles
|
||||
tiles.zipWithIndex.foreach { case (tile, i) =>
|
||||
tile.io.hartid := UInt(i)
|
||||
tile.io.resetVector := io.resetVector
|
||||
tile.io.interrupts := outer.clint.module.io.tiles(i)
|
||||
tile.io.interrupts.debug := outer.debug.module.io.debugInterrupts(i)
|
||||
tile.io.interrupts.meip := outer.tileIntNodes(i).bundleOut(0)(0)
|
||||
tile.io.interrupts.seip.foreach(_ := outer.tileIntNodes(i).bundleOut(0)(1))
|
||||
}
|
||||
}
|
||||
|
||||
class DefaultCoreplex(implicit p: Parameters) extends BaseCoreplex
|
||||
with BroadcastL2
|
||||
with DirectConnection {
|
||||
with CoreplexRISCVPlatform
|
||||
with RocketPlex {
|
||||
override lazy val module = new DefaultCoreplexModule(this, () => new DefaultCoreplexBundle(this))
|
||||
}
|
||||
|
||||
class DefaultCoreplexBundle[+L <: DefaultCoreplex](_outer: L) extends BaseCoreplexBundle(_outer)
|
||||
with CoreplexRISCVPlatformBundle
|
||||
with RocketPlexBundle
|
||||
|
||||
class DefaultCoreplexModule[+L <: DefaultCoreplex, +B <: DefaultCoreplexBundle[L]](_outer: L, _io: () => B) extends BaseCoreplexModule(_outer, _io)
|
||||
with DirectConnectionModule
|
||||
with CoreplexRISCVPlatformModule
|
||||
with RocketPlexModule
|
||||
|
||||
/////
|
||||
/*
|
||||
|
||||
trait AsyncConnection {
|
||||
this: CoreplexNetwork with CoreplexRISCVPlatform =>
|
||||
@ -149,3 +126,4 @@ class MultiClockCoreplexBundle[+L <: MultiClockCoreplex](_outer: L) extends Base
|
||||
|
||||
class MultiClockCoreplexModule[+L <: MultiClockCoreplex, +B <: MultiClockCoreplexBundle[L]](_outer: L, _io: () => B) extends BaseCoreplexModule(_outer, _io)
|
||||
with AsyncConnectionModule
|
||||
*/
|
||||
|
73
src/main/scala/coreplex/RISCVPlatform.scala
Normal file
73
src/main/scala/coreplex/RISCVPlatform.scala
Normal file
@ -0,0 +1,73 @@
|
||||
package coreplex
|
||||
|
||||
import Chisel._
|
||||
import cde.{Parameters, Field}
|
||||
import junctions._
|
||||
import diplomacy._
|
||||
import uncore.tilelink._
|
||||
import uncore.tilelink2._
|
||||
import uncore.coherence._
|
||||
import uncore.agents._
|
||||
import uncore.devices._
|
||||
import uncore.util._
|
||||
import uncore.converters._
|
||||
import rocket._
|
||||
import util._
|
||||
|
||||
trait CoreplexRISCVPlatform extends CoreplexNetwork {
|
||||
val module: CoreplexRISCVPlatformModule
|
||||
|
||||
val debug = LazyModule(new TLDebugModule())
|
||||
val plic = LazyModule(new TLPLIC(hasSupervisor, maxPriorities = 7))
|
||||
val clint = LazyModule(new CoreplexLocalInterrupter)
|
||||
|
||||
debug.node := TLFragmenter(cbus_beatBytes, cbus_lineBytes)(cbus.node)
|
||||
plic.node := TLFragmenter(cbus_beatBytes, cbus_lineBytes)(cbus.node)
|
||||
clint.node := TLFragmenter(cbus_beatBytes, cbus_lineBytes)(cbus.node)
|
||||
|
||||
plic.intnode := mmioInt
|
||||
|
||||
}
|
||||
|
||||
trait CoreplexRISCVPlatformBundle extends CoreplexNetworkBundle {
|
||||
val outer: CoreplexRISCVPlatform
|
||||
|
||||
val debug = new AsyncDebugBusIO().flip
|
||||
val rtcToggle = Bool(INPUT)
|
||||
val resetVector = UInt(INPUT, p(XLen))
|
||||
}
|
||||
|
||||
trait CoreplexRISCVPlatformModule extends CoreplexNetworkModule {
|
||||
val outer: CoreplexRISCVPlatform
|
||||
val io: CoreplexRISCVPlatformBundle
|
||||
|
||||
// Synchronize the debug bus into the coreplex
|
||||
outer.debug.module.io.db <> FromAsyncDebugBus(io.debug)
|
||||
|
||||
// Synchronize the rtc into the coreplex
|
||||
val rtcSync = ShiftRegister(io.rtcToggle, 3)
|
||||
val rtcLast = Reg(init = Bool(false), next=rtcSync)
|
||||
outer.clint.module.io.rtcTick := Reg(init = Bool(false), next=(rtcSync & (~rtcLast)))
|
||||
|
||||
println("\nGenerated Address Map")
|
||||
for (entry <- p(rocketchip.GlobalAddrMap).flatten) {
|
||||
val name = entry.name
|
||||
val start = entry.region.start
|
||||
val end = entry.region.start + entry.region.size - 1
|
||||
val prot = entry.region.attr.prot
|
||||
val protStr = (if ((prot & AddrMapProt.R) > 0) "R" else "") +
|
||||
(if ((prot & AddrMapProt.W) > 0) "W" else "") +
|
||||
(if ((prot & AddrMapProt.X) > 0) "X" else "")
|
||||
val cacheable = if (entry.region.attr.cacheable) " [C]" else ""
|
||||
println(f"\t$name%s $start%x - $end%x, $protStr$cacheable")
|
||||
}
|
||||
|
||||
// Create and export the ConfigString
|
||||
val managers = outer.l1tol2.node.edgesIn(0).manager.managers
|
||||
val configString = rocketchip.GenerateConfigString(p, outer.clint, outer.plic, managers)
|
||||
// Allow something else to have override the config string
|
||||
if (!ConfigStringOutput.contents.isDefined) {
|
||||
ConfigStringOutput.contents = Some(configString)
|
||||
}
|
||||
println(s"\nGenerated Configuration String\n${ConfigStringOutput.contents.get}")
|
||||
}
|
41
src/main/scala/coreplex/RocketPlex.scala
Normal file
41
src/main/scala/coreplex/RocketPlex.scala
Normal file
@ -0,0 +1,41 @@
|
||||
package coreplex
|
||||
|
||||
import Chisel._
|
||||
import cde.{Parameters, Field}
|
||||
import diplomacy._
|
||||
import uncore.tilelink2._
|
||||
import uncore.coherence._
|
||||
import rocket._
|
||||
import uncore.devices.NTiles
|
||||
|
||||
trait RocketPlex extends CoreplexRISCVPlatform {
|
||||
val module: RocketPlexModule
|
||||
|
||||
val rocketTiles = List.tabulate(p(NTiles)) { i => LazyModule(new RocketTile(i)) }
|
||||
val tileIntNodes = rocketTiles.map { _ => IntInternalOutputNode() }
|
||||
|
||||
tileIntNodes.foreach { _ := plic.intnode }
|
||||
rocketTiles.foreach { r =>
|
||||
r.slaveNode.foreach { _ := cbus.node }
|
||||
l1tol2.node := r.cachedOut
|
||||
l1tol2.node := r.uncachedOut
|
||||
}
|
||||
}
|
||||
|
||||
trait RocketPlexBundle extends CoreplexRISCVPlatformBundle {
|
||||
val outer: CoreplexRISCVPlatform
|
||||
}
|
||||
|
||||
trait RocketPlexModule extends CoreplexRISCVPlatformModule {
|
||||
val outer: RocketPlex
|
||||
val io: RocketPlexBundle
|
||||
|
||||
outer.rocketTiles.map(_.module).zipWithIndex.foreach { case (tile, i) =>
|
||||
tile.io.hartid := UInt(i)
|
||||
tile.io.resetVector := io.resetVector
|
||||
tile.io.interrupts := outer.clint.module.io.tiles(i)
|
||||
tile.io.interrupts.debug := outer.debug.module.io.debugInterrupts(i)
|
||||
tile.io.interrupts.meip := outer.tileIntNodes(i).bundleOut(0)(0)
|
||||
tile.io.interrupts.seip.foreach(_ := outer.tileIntNodes(i).bundleOut(0)(1))
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user