diff --git a/src/main/scala/coreplex/BaseCoreplex.scala b/src/main/scala/coreplex/BaseCoreplex.scala index e0333128..4d2f0b59 100644 --- a/src/main/scala/coreplex/BaseCoreplex.scala +++ b/src/main/scala/coreplex/BaseCoreplex.scala @@ -49,7 +49,6 @@ trait HasCoreplexParameters { lazy val cbusConfig = p(CBusConfig) lazy val l1tol2Config = p(L1toL2Config) lazy val nTiles = tilesParams.size - lazy val hasSupervisor = tilesParams.exists(_.core.useVM) // TODO ask andrew about this lazy val l2Config = p(BankedL2Config) } diff --git a/src/main/scala/coreplex/RISCVPlatform.scala b/src/main/scala/coreplex/RISCVPlatform.scala index 87afaaa0..79a306e2 100644 --- a/src/main/scala/coreplex/RISCVPlatform.scala +++ b/src/main/scala/coreplex/RISCVPlatform.scala @@ -15,7 +15,7 @@ trait CoreplexRISCVPlatform extends CoreplexNetwork { val module: CoreplexRISCVPlatformModule val debug = LazyModule(new TLDebugModule()) - val plic = LazyModule(new TLPLIC(hasSupervisor, maxPriorities = 7)) + val plic = LazyModule(new TLPLIC(maxPriorities = 7)) val clint = LazyModule(new CoreplexLocalInterrupter) debug.node := TLFragmenter(cbus_beatBytes, cbus_lineBytes)(cbus.node) diff --git a/src/main/scala/coreplex/RocketTiles.scala b/src/main/scala/coreplex/RocketTiles.scala index 206098f0..d9d2e3bb 100644 --- a/src/main/scala/coreplex/RocketTiles.scala +++ b/src/main/scala/coreplex/RocketTiles.scala @@ -23,20 +23,6 @@ trait HasRocketTiles extends CoreplexRISCVPlatform { private val crossing = p(RocketCrossing) private val configs = p(RocketTilesKey) - private val rocketTileIntNodes = configs.map { _ => IntInternalOutputNode(IntSinkPortSimple(ports = 2)) } - rocketTileIntNodes.foreach { n => - n := plic.intnode - n := clint.intnode - } - - private def wireInterrupts(x: TileInterrupts, i: Int) { - x.debug := debug.module.io.debugInterrupts(i) - x.meip := rocketTileIntNodes(i).bundleOut(0)(0) - x.seip.foreach { _ := rocketTileIntNodes(i).bundleOut(0)(1) } // optional - x.msip := rocketTileIntNodes(i).bundleOut(1)(0) - x.mtip := rocketTileIntNodes(i).bundleOut(1)(1) - } - val rocketWires: Seq[HasRocketTilesBundle => Unit] = configs.zipWithIndex.map { case (c, i) => val pWithExtra = p.alterPartial { case TileKey => c @@ -45,6 +31,15 @@ trait HasRocketTiles extends CoreplexRISCVPlatform { case PAddrBits => l1tol2.node.edgesIn(0).bundle.addressBits } + // Hack debug interrupt into a node (future debug module should use diplomacy) + val debugNode = IntInternalInputNode(IntSourcePortSimple()) + + val intBar = LazyModule(new IntXbar) + intBar.intnode := debugNode + intBar.intnode := clint.intnode // msip+mtip + intBar.intnode := plic.intnode // meip + if (c.core.useVM) intBar.intnode := plic.intnode // seip + crossing match { case Synchronous => { val tile = LazyModule(new RocketTile(c, i)(pWithExtra)) @@ -52,21 +47,12 @@ trait HasRocketTiles extends CoreplexRISCVPlatform { buffer.node :=* tile.masterNode l1tol2.node :=* buffer.node tile.slaveNode :*= cbus.node - ResourceBinding { - rocketTileIntNodes(i).edgesIn(0).source.sources.flatMap(_.resources).foreach { r => - r.bind(tile.device, ResourceInt(11)) // meip - if (c.core.useVM) r.bind(tile.device, ResourceInt(9)) // seip - } - rocketTileIntNodes(i).edgesIn(1).source.sources.flatMap(_.resources).foreach { r => - r.bind(tile.device, ResourceInt(3)) // msip - r.bind(tile.device, ResourceInt(7)) // mtip - } - } + tile.intNode := intBar.intnode (io: HasRocketTilesBundle) => { // leave clock as default (simpler for hierarchical PnR) tile.module.io.hartid := UInt(i) tile.module.io.resetVector := io.resetVector - wireInterrupts(tile.module.io.interrupts, i) + debugNode.bundleOut(0)(0) := debug.module.io.debugInterrupts(i) } } case Asynchronous(depth, sync) => { @@ -76,23 +62,14 @@ trait HasRocketTiles extends CoreplexRISCVPlatform { sink.node :=* wrapper.masterNode l1tol2.node :=* sink.node wrapper.slaveNode :*= source.node + wrapper.intNode := intBar.intnode source.node :*= cbus.node - ResourceBinding { - rocketTileIntNodes(i).edgesIn(0).source.sources.flatMap(_.resources).foreach { r => - r.bind(wrapper.rocket.device, ResourceInt(11)) // meip - if (c.core.useVM) r.bind(wrapper.rocket.device, ResourceInt(9)) // seip - } - rocketTileIntNodes(i).edgesIn(1).source.sources.flatMap(_.resources).foreach { r => - r.bind(wrapper.rocket.device, ResourceInt(3)) // msip - r.bind(wrapper.rocket.device, ResourceInt(7)) // mtip - } - } (io: HasRocketTilesBundle) => { wrapper.module.clock := io.tcrs(i).clock wrapper.module.reset := io.tcrs(i).reset wrapper.module.io.hartid := UInt(i) wrapper.module.io.resetVector := io.resetVector - wireInterrupts(wrapper.module.io.interrupts, i) + debugNode.bundleOut(0)(0) := debug.module.io.debugInterrupts(i) } } case Rational => { @@ -102,23 +79,14 @@ trait HasRocketTiles extends CoreplexRISCVPlatform { sink.node :=* wrapper.masterNode l1tol2.node :=* sink.node wrapper.slaveNode :*= source.node + wrapper.intNode := intBar.intnode source.node :*= cbus.node - ResourceBinding { - rocketTileIntNodes(i).edgesIn(0).source.sources.flatMap(_.resources).foreach { r => - r.bind(wrapper.rocket.device, ResourceInt(11)) // meip - if (c.core.useVM) r.bind(wrapper.rocket.device, ResourceInt(9)) // seip - } - rocketTileIntNodes(i).edgesIn(1).source.sources.flatMap(_.resources).foreach { r => - r.bind(wrapper.rocket.device, ResourceInt(3)) // msip - r.bind(wrapper.rocket.device, ResourceInt(7)) // mtip - } - } (io: HasRocketTilesBundle) => { wrapper.module.clock := io.tcrs(i).clock wrapper.module.reset := io.tcrs(i).reset wrapper.module.io.hartid := UInt(i) wrapper.module.io.resetVector := io.resetVector - wireInterrupts(wrapper.module.io.interrupts, i) + debugNode.bundleOut(0)(0) := debug.module.io.debugInterrupts(i) } } } diff --git a/src/main/scala/rocket/Tile.scala b/src/main/scala/rocket/Tile.scala index 737536c1..04462028 100644 --- a/src/main/scala/rocket/Tile.scala +++ b/src/main/scala/rocket/Tile.scala @@ -87,6 +87,19 @@ class RocketTile(val rocketParams: RocketTileParams, val hartid: Int)(implicit p ResourceBinding { Resource(device, "reg").bind(ResourceInt(BigInt(hartid))) + + // debug, msip, mtip, meip, seip offsets in CSRs + val intMap = Seq(65535, 3, 7, 11, 9) + + intNode.edgesIn.flatMap(_.source.sources).map { case s => + for (i <- s.range.start until s.range.end) { + intMap.lift(i).foreach { j => + s.resources.foreach { r => + r.bind(device, ResourceInt(j)) + } + } + } + } } override lazy val module = new RocketTileModule(this) @@ -100,7 +113,6 @@ class RocketTileModule(outer: RocketTile) extends BaseTileModule(outer, () => ne with CanHaveScratchpadModule { val core = Module(p(BuildCore)(outer.p)) - core.io.interrupts := io.interrupts core.io.hartid := io.hartid outer.frontend.module.io.cpu <> core.io.imem outer.frontend.module.io.resetVector := io.resetVector @@ -115,6 +127,13 @@ class RocketTileModule(outer: RocketTile) extends BaseTileModule(outer, () => ne core.io.rocc.interrupt := lr.module.io.core.interrupt } + // Decode the interrupt vector + core.io.interrupts.debug := io.interrupts(0)(0) + core.io.interrupts.msip := io.interrupts(0)(1) + core.io.interrupts.mtip := io.interrupts(0)(2) + core.io.interrupts.meip := io.interrupts(0)(3) + core.io.interrupts.seip.foreach { _ := io.interrupts(0)(4) } + // TODO eliminate this redundancy val h = dcachePorts.size val c = core.dcacheArbPorts @@ -139,15 +158,19 @@ class AsyncRocketTile(rtp: RocketTileParams, hartid: Int)(implicit p: Parameters rocket.slaveNode :*= sink.node sink.node :*= slaveNode + val intNode = IntInputNode() + val xing = LazyModule(new IntXing(3)) + rocket.intNode := xing.intnode + xing.intnode := intNode + lazy val module = new LazyModuleImp(this) { val io = new Bundle { val master = masterNode.bundleOut val slave = slaveNode.bundleIn + val interrupts = intNode.bundleIn val hartid = UInt(INPUT, p(XLen)) - val interrupts = new TileInterrupts()(p).asInput val resetVector = UInt(INPUT, p(XLen)) } - rocket.module.io.interrupts := ShiftRegister(io.interrupts, 3) // signals that do not change: rocket.module.io.hartid := io.hartid rocket.module.io.resetVector := io.resetVector @@ -167,15 +190,19 @@ class RationalRocketTile(rtp: RocketTileParams, hartid: Int)(implicit p: Paramet rocket.slaveNode :*= sink.node sink.node :*= slaveNode + val intNode = IntInputNode() + val xing = LazyModule(new IntXing(1)) + rocket.intNode := xing.intnode + xing.intnode := intNode + lazy val module = new LazyModuleImp(this) { val io = new Bundle { val master = masterNode.bundleOut val slave = slaveNode.bundleIn + val interrupts = intNode.bundleIn val hartid = UInt(INPUT, p(XLen)) - val interrupts = new TileInterrupts()(p).asInput val resetVector = UInt(INPUT, p(XLen)) } - rocket.module.io.interrupts := ShiftRegister(io.interrupts, 1) // signals that do not change: rocket.module.io.hartid := io.hartid rocket.module.io.resetVector := io.resetVector diff --git a/src/main/scala/tile/BaseTile.scala b/src/main/scala/tile/BaseTile.scala index 1434697d..f39da677 100644 --- a/src/main/scala/tile/BaseTile.scala +++ b/src/main/scala/tile/BaseTile.scala @@ -53,11 +53,13 @@ trait HasTileLinkMasterPort extends HasTileParameters { implicit val p: Parameters val module: HasTileLinkMasterPortModule val masterNode = TLOutputNode() + val intNode = IntSinkNode(IntSinkPortSimple()) } trait HasTileLinkMasterPortBundle { val outer: HasTileLinkMasterPort val master = outer.masterNode.bundleOut + val interrupts = outer.intNode.bundleIn } trait HasTileLinkMasterPortModule { @@ -73,7 +75,6 @@ abstract class BaseTile(tileParams: TileParams)(implicit p: Parameters) extends class BaseTileBundle[+L <: BaseTile](_outer: L) extends BareTileBundle(_outer) with HasTileLinkMasterPortBundle { val hartid = UInt(INPUT, p(XLen)) - val interrupts = new TileInterrupts()(p).asInput val resetVector = UInt(INPUT, p(XLen)) } diff --git a/src/main/scala/uncore/devices/Plic.scala b/src/main/scala/uncore/devices/Plic.scala index adfc38ea..98e54f0c 100644 --- a/src/main/scala/uncore/devices/Plic.scala +++ b/src/main/scala/uncore/devices/Plic.scala @@ -53,9 +53,8 @@ object PLICConsts } /** Platform-Level Interrupt Controller */ -class TLPLIC(supervisor: Boolean, maxPriorities: Int, address: BigInt = 0xC000000)(implicit p: Parameters) extends LazyModule +class TLPLIC(maxPriorities: Int, address: BigInt = 0xC000000)(implicit p: Parameters) extends LazyModule { - val contextsPerHart = if (supervisor) 2 else 1 require (maxPriorities >= 0) // plic0 => max devices 1023 @@ -81,7 +80,7 @@ class TLPLIC(supervisor: Boolean, maxPriorities: Int, address: BigInt = 0xC00000 val intnode = IntNexusNode( numSourcePorts = 0 to 1024, numSinkPorts = 0 to 1024, - sourceFn = { _ => IntSourcePortParameters(Seq(IntSourceParameters(contextsPerHart, Seq(Resource(device, "int"))))) }, + sourceFn = { _ => IntSourcePortParameters(Seq(IntSourceParameters(1, Seq(Resource(device, "int"))))) }, sinkFn = { _ => IntSinkPortParameters(Seq(IntSinkParameters())) }) /* Negotiated sizes */