From 35d02c5096f9f722feb1994c74bacd8176e60f5c Mon Sep 17 00:00:00 2001 From: Henry Cook Date: Fri, 1 Apr 2016 15:38:31 -0700 Subject: [PATCH] LRSC fix. RocketChipNetwork moved to uncore. --- src/main/scala/Network.scala | 180 -------------------------------- src/main/scala/RocketChip.scala | 9 +- 2 files changed, 3 insertions(+), 186 deletions(-) delete mode 100644 src/main/scala/Network.scala diff --git a/src/main/scala/Network.scala b/src/main/scala/Network.scala deleted file mode 100644 index 92a32f5f..00000000 --- a/src/main/scala/Network.scala +++ /dev/null @@ -1,180 +0,0 @@ -// See LICENSE for license details. - -package rocketchip - -import Chisel._ -import uncore._ -import cde.Parameters - -/** RocketChipNetworks combine a TileLink protocol with a particular physical - * network implementation and chip layout. - * - * Specifically, they provide mappings between ClientTileLinkIO/ - * ManagerTileLinkIO channels and LogicalNetwork ports (i.e. generic - * TileLinkIO with networking headers). Channels coming into the network have - * appropriate networking headers appended and outgoing channels have their - * headers stripped. - * - * @constructor base class constructor for Rocket NoC - * @param addrToManagerId a mapping from a physical address to the network - * id of a coherence manager - * @param sharerToClientId a mapping from the id of a particular coherent - * client (as determined by e.g. the directory) and the network id - * of that client - * @param clientDepths the depths of the queue that should be used to buffer - * each channel on the client side of the network - * @param managerDepths the depths of the queue that should be used to buffer - * each channel on the manager side of the network - */ -abstract class RocketChipNetwork( - addrToManagerId: UInt => UInt, - sharerToClientId: UInt => UInt, - clientDepths: TileLinkDepths, - managerDepths: TileLinkDepths) - (implicit p: Parameters) extends TLModule()(p) { - val nClients = tlNClients - val nManagers = tlNManagers - val io = new Bundle { - val clients = Vec(nClients, new ClientTileLinkIO).flip - val managers = Vec(nManagers, new ManagerTileLinkIO).flip - } - - val clients = io.clients.zipWithIndex.map { - case (c, i) => { - val port = Module(new ClientTileLinkNetworkPort(i, addrToManagerId)) - val qs = Module(new TileLinkEnqueuer(clientDepths)) - port.io.client <> c - qs.io.client <> port.io.network - qs.io.manager - } - } - - val managers = io.managers.zipWithIndex.map { - case (m, i) => { - val port = Module(new ManagerTileLinkNetworkPort(i, sharerToClientId)) - val qs = Module(new TileLinkEnqueuer(managerDepths)) - port.io.manager <> m - port.io.network <> qs.io.manager - qs.io.client - } - } -} - -/** A simple arbiter for each channel that also deals with header-based routing. - * Assumes a single manager agent. */ -class RocketChipTileLinkArbiter( - sharerToClientId: UInt => UInt = (u: UInt) => u, - clientDepths: TileLinkDepths = TileLinkDepths(0,0,0,0,0), - managerDepths: TileLinkDepths = TileLinkDepths(0,0,0,0,0)) - (implicit p: Parameters) - extends RocketChipNetwork(u => UInt(0), sharerToClientId, clientDepths, managerDepths)(p) - with TileLinkArbiterLike - with PassesId { - val arbN = nClients - require(nManagers == 1) - if(arbN > 1) { - hookupClientSource(clients.map(_.acquire), managers.head.acquire) - hookupClientSource(clients.map(_.release), managers.head.release) - hookupFinish(clients.map(_.finish), managers.head.finish) - hookupManagerSourceWithHeader(clients.map(_.probe), managers.head.probe) - hookupManagerSourceWithHeader(clients.map(_.grant), managers.head.grant) - } else { - managers.head <> clients.head - } -} - -/** Provides a separate physical crossbar for each channel. Assumes multiple manager - * agents. Managers are assigned to higher physical network port ids than - * clients, and translations between logical network id and physical crossbar - * port id are done automatically. - */ -class RocketChipTileLinkCrossbar( - addrToManagerId: UInt => UInt = u => UInt(0), - sharerToClientId: UInt => UInt = u => u, - clientDepths: TileLinkDepths = TileLinkDepths(0,0,0,0,0), - managerDepths: TileLinkDepths = TileLinkDepths(0,0,0,0,0)) - (implicit p: Parameters) - extends RocketChipNetwork(addrToManagerId, sharerToClientId, clientDepths, managerDepths)(p) { - val n = p(LNEndpoints) - val count = tlDataBeats - // Actually instantiate the particular networks required for TileLink - val acqNet = Module(new BasicCrossbar(n, new Acquire, count, Some((a: PhysicalNetworkIO[Acquire]) => a.payload.hasMultibeatData()))) - val relNet = Module(new BasicCrossbar(n, new Release, count, Some((r: PhysicalNetworkIO[Release]) => r.payload.hasMultibeatData()))) - val prbNet = Module(new BasicCrossbar(n, new Probe)) - val gntNet = Module(new BasicCrossbar(n, new Grant, count, Some((g: PhysicalNetworkIO[Grant]) => g.payload.hasMultibeatData()))) - val ackNet = Module(new BasicCrossbar(n, new Finish)) - - // Aliases for the various network IO bundle types - type PNIO[T <: Data] = DecoupledIO[PhysicalNetworkIO[T]] - type LNIO[T <: Data] = DecoupledIO[LogicalNetworkIO[T]] - type FromCrossbar[T <: Data] = PNIO[T] => LNIO[T] - type ToCrossbar[T <: Data] = LNIO[T] => PNIO[T] - - // Shims for converting between logical network IOs and physical network IOs - def crossbarToManagerShim[T <: Data](in: PNIO[T]): LNIO[T] = { - val out = DefaultFromPhysicalShim(in) - out.bits.header.src := in.bits.header.src - UInt(nManagers) - out - } - def crossbarToClientShim[T <: Data](in: PNIO[T]): LNIO[T] = { - val out = DefaultFromPhysicalShim(in) - out.bits.header.dst := in.bits.header.dst - UInt(nManagers) - out - } - def managerToCrossbarShim[T <: Data](in: LNIO[T]): PNIO[T] = { - val out = DefaultToPhysicalShim(n, in) - out.bits.header.dst := in.bits.header.dst + UInt(nManagers) - out - } - def clientToCrossbarShim[T <: Data](in: LNIO[T]): PNIO[T] = { - val out = DefaultToPhysicalShim(n, in) - out.bits.header.src := in.bits.header.src + UInt(nManagers) - out - } - - // Make an individual connection between virtual and physical ports using - // a particular shim. Also pin the unused Decoupled control signal low. - def doDecoupledInputHookup[T <: Data](phys_in: PNIO[T], phys_out: PNIO[T], log_io: LNIO[T], shim: ToCrossbar[T]) = { - val s = shim(log_io) - phys_in.valid := s.valid - phys_in.bits := s.bits - s.ready := phys_in.ready - phys_out.ready := Bool(false) - } - - def doDecoupledOutputHookup[T <: Data](phys_in: PNIO[T], phys_out: PNIO[T], log_io: LNIO[T], shim: FromCrossbar[T]) = { - val s = shim(phys_out) - log_io.valid := s.valid - log_io.bits := s.bits - s.ready := log_io.ready - phys_in.valid := Bool(false) - } - - //Hookup all instances of a particular subbundle of TileLink - def doDecoupledHookups[T <: Data](physIO: BasicCrossbarIO[T], getLogIO: TileLinkIO => LNIO[T]) = { - physIO.in.head.bits.payload match { - case c: ClientToManagerChannel => { - managers.zipWithIndex.map { case (i, id) => - doDecoupledOutputHookup(physIO.in(id), physIO.out(id), getLogIO(i), crossbarToManagerShim[T]) - } - clients.zipWithIndex.map { case (i, id) => - doDecoupledInputHookup(physIO.in(id+nManagers), physIO.out(id+nManagers), getLogIO(i), clientToCrossbarShim[T]) - } - } - case m: ManagerToClientChannel => { - managers.zipWithIndex.map { case (i, id) => - doDecoupledInputHookup(physIO.in(id), physIO.out(id), getLogIO(i), managerToCrossbarShim[T]) - } - clients.zipWithIndex.map { case (i, id) => - doDecoupledOutputHookup(physIO.in(id+nManagers), physIO.out(id+nManagers), getLogIO(i), crossbarToClientShim[T]) - } - } - } - } - - doDecoupledHookups(acqNet.io, (tl: TileLinkIO) => tl.acquire) - doDecoupledHookups(relNet.io, (tl: TileLinkIO) => tl.release) - doDecoupledHookups(prbNet.io, (tl: TileLinkIO) => tl.probe) - doDecoupledHookups(gntNet.io, (tl: TileLinkIO) => tl.grant) - doDecoupledHookups(ackNet.io, (tl: TileLinkIO) => tl.finish) -} diff --git a/src/main/scala/RocketChip.scala b/src/main/scala/RocketChip.scala index dd143165..ac9e8d70 100644 --- a/src/main/scala/RocketChip.scala +++ b/src/main/scala/RocketChip.scala @@ -228,9 +228,6 @@ class OuterMemorySystem(implicit val p: Parameters) extends Module with HasTopLe // Create a simple L1toL2 NoC between the tiles+htif and the banks of outer memory // Cached ports are first in client list, making sharerToClientId just an indentity function // addrToBank is sed to hash physical addresses (of cache blocks) to banks (and thereby memory channels) - val ordered_clients = (io.tiles_cached ++ - (io.tiles_uncached ++ Seq(rtc.io, io.htif_uncached)) - .map(TileLinkIOWrapper(_))) def sharerToClientId(sharerId: UInt) = sharerId def addrToBank(addr: Bits): UInt = { Mux(addr.toUInt < UInt(mmioBase >> log2Up(p(CacheBlockBytes))), @@ -238,8 +235,7 @@ class OuterMemorySystem(implicit val p: Parameters) extends Module with HasTopLe UInt(nBanks)) } val preBuffering = TileLinkDepths(2,2,2,2,2) - val postBuffering = TileLinkDepths(0,0,1,0,0) //TODO: had EOS24 crit path on inner.release - val l1tol2net = Module(new RocketChipTileLinkCrossbar(addrToBank, sharerToClientId, preBuffering, postBuffering)) + val l1tol2net = Module(new PortedTileLinkCrossbar(addrToBank, sharerToClientId, preBuffering)) // Create point(s) of coherence serialization val managerEndpoints = List.tabulate(nBanks){id => p(BuildL2CoherenceManager)(id, p)} @@ -253,7 +249,8 @@ class OuterMemorySystem(implicit val p: Parameters) extends Module with HasTopLe // Wire the tiles and htif to the TileLink client ports of the L1toL2 network, // and coherence manager(s) to the other side - l1tol2net.io.clients <> ordered_clients + l1tol2net.io.clients_cached <> io.tiles_cached + l1tol2net.io.clients_uncached <> io.tiles_uncached ++ Seq(rtc.io, io.htif_uncached) l1tol2net.io.managers <> managerEndpoints.map(_.innerTL) :+ mmioManager.io.inner // Create a converter between TileLinkIO and MemIO for each channel