diff --git a/src/main/scala/rocketchip/Configs.scala b/src/main/scala/rocketchip/Configs.scala index 29437d44..f70ded99 100644 --- a/src/main/scala/rocketchip/Configs.scala +++ b/src/main/scala/rocketchip/Configs.scala @@ -115,7 +115,10 @@ class BasePlatformConfig extends Config ( idBits = Dump("MEM_ID_BITS", site(MIFTagBits))) } case BuildCoreplex => (p: Parameters) => Module(new DefaultCoreplex(p)) - case NExtInterrupts => 2 + case NExtTopInterrupts => 2 + case NExtPeripheryInterrupts => 0 + // Note that PLIC asserts that this is > 0. + case NExtInterrupts => site(NExtTopInterrupts) + site(NExtPeripheryInterrupts) case AsyncDebugBus => false case IncludeJtagDTM => false case AsyncMMIOChannels => false @@ -260,11 +263,13 @@ class WithTestRAM extends Config( def addrMapEntries = Seq( AddrMapEntry("testram", MemSize(ramSize, MemAttr(AddrMapProt.RW)))) def builder( - mmioPorts: HashMap[String, ClientUncachedTileLinkIO], - clientPorts: Seq[ClientUncachedTileLinkIO], - extra: Bundle, p: Parameters) { + mmioPorts: HashMap[String, ClientUncachedTileLinkIO], + clientPorts: Seq[ClientUncachedTileLinkIO], + interrupts: Seq[Bool], + extra: Bundle, p: Parameters) { val testram = Module(new TileLinkTestRAM(ramSize)(p)) testram.io <> mmioPorts("testram") + interrupts.foreach(x => x := Bool(false)) } } new TestRAMDevice diff --git a/src/main/scala/rocketchip/Devices.scala b/src/main/scala/rocketchip/Devices.scala index d79b4ac4..3151de70 100644 --- a/src/main/scala/rocketchip/Devices.scala +++ b/src/main/scala/rocketchip/Devices.scala @@ -23,12 +23,14 @@ abstract class DeviceBlock { * Use the names specified in addrMapEntries to get * the mmio port for each device. * @param clientPorts All the client ports available for the devices + * @param interrupts External interrupts from Periphery to Coreplex * @param extra The extra top-level IO bundle * @param p The CDE parameters for the devices */ def builder( mmioPorts: HashMap[String, ClientUncachedTileLinkIO], clientPorts: Seq[ClientUncachedTileLinkIO], + interrupts : Seq[Bool], extra: Bundle, p: Parameters): Unit /** @@ -53,7 +55,8 @@ class EmptyDeviceBlock extends DeviceBlock { def addrMapEntries = Seq.empty def builder( - mmioPorts: HashMap[String, ClientUncachedTileLinkIO], - clientPorts: Seq[ClientUncachedTileLinkIO], - extra: Bundle, p: Parameters) {} + mmioPorts: HashMap[String, ClientUncachedTileLinkIO], + clientPorts: Seq[ClientUncachedTileLinkIO], + interrupts : Seq[Bool], + extra: Bundle, p: Parameters) {} } diff --git a/src/main/scala/rocketchip/RocketChip.scala b/src/main/scala/rocketchip/RocketChip.scala index 2ddabbbf..6f0ae1eb 100644 --- a/src/main/scala/rocketchip/RocketChip.scala +++ b/src/main/scala/rocketchip/RocketChip.scala @@ -47,6 +47,11 @@ case object BuildCoreplex extends Field[Parameters => Coreplex] case object ConnectExtraPorts extends Field[(Bundle, Bundle, Parameters) => Unit] /** Specifies the size of external memory */ case object ExtMemSize extends Field[Long] +/** Specifies the actual sorce of External Interrupts as Top and Periphery. + * NExtInterrupts = NExtTopInterrupts + NExtPeripheryInterrupts + **/ +case object NExtTopInterrupts extends Field[Int] +case object NExtPeripheryInterrupts extends Field[Int] /** Utility trait for quick access to some relevant parameters */ trait HasTopLevelParameters { @@ -79,7 +84,7 @@ class TopIO(implicit p: Parameters) extends BasicTopIO()(p) { val mem_axi = Vec(nMemAXIChannels, new NastiIO) val mem_ahb = Vec(nMemAHBChannels, new HastiMasterIO) val mem_tl = Vec(nMemTLChannels, new ClientUncachedTileLinkIO()(outermostParams)) - val interrupts = Vec(p(NExtInterrupts), Bool()).asInput + val interrupts = Vec(p(NExtTopInterrupts), Bool()).asInput val bus_clk = if (p(AsyncBusChannels)) Some(Vec(p(NExtBusAXIChannels), Clock(INPUT))) else None val bus_rst = if (p(AsyncBusChannels)) Some(Vec(p(NExtBusAXIChannels), Bool (INPUT))) else None val bus_axi = Vec(p(NExtBusAXIChannels), new NastiIO).flip @@ -181,7 +186,11 @@ class Top(topParams: Parameters) extends Module with HasTopLevelParameters { asyncAxiFrom(io.bus_clk.get, io.bus_rst.get, io.bus_axi) else io.bus_axi) - coreplex.io.interrupts <> io.interrupts + // This places the Periphery Interrupts at Bits [0...] + // Top-level interrupts are at the higher Bits. + // This may have some implications for prioritization of the interrupts, + // but PLIC could do some internal swizzling in the future. + coreplex.io.interrupts <> (periphery.io.interrupts ++ io.interrupts) io.extra <> periphery.io.extra p(ConnectExtraPorts)(io.extra, coreplex.io.extra, p) @@ -200,6 +209,7 @@ class Periphery(implicit val p: Parameters) extends Module val mmio_axi = Vec(p(NExtMMIOAXIChannels), new NastiIO) val mmio_ahb = Vec(p(NExtMMIOAHBChannels), new HastiMasterIO) val mmio_tl = Vec(p(NExtMMIOTLChannels), new ClientUncachedTileLinkIO()(outermostMMIOParams)) + val interrupts = Vec(p(NExtPeripheryInterrupts), Bool()).asOutput val extra = p(ExtraTopPorts)(p) } @@ -255,7 +265,8 @@ class Periphery(implicit val p: Parameters) extends Module case OuterTLId => "L1toL2" // Device client port }) - extraDevices.builder(deviceMMIO.result(), deviceClients, io.extra, buildParams) + extraDevices.builder(deviceMMIO.result(), deviceClients, + io.interrupts, io.extra, buildParams) val ext = p(ExtMMIOPorts).map( port => TileLinkWidthAdapter(mmioNetwork.port(port.name), "MMIO_Outermost")) diff --git a/src/main/scala/rocketchip/TestConfigs.scala b/src/main/scala/rocketchip/TestConfigs.scala index 359d9628..1d64e7ce 100644 --- a/src/main/scala/rocketchip/TestConfigs.scala +++ b/src/main/scala/rocketchip/TestConfigs.scala @@ -189,12 +189,14 @@ class WithBusMasterTest extends Config( def addrMapEntries = Seq( AddrMapEntry("busmaster", MemSize(4096, MemAttr(AddrMapProt.RW)))) def builder( - mmioPorts: HashMap[String, ClientUncachedTileLinkIO], - clientPorts: Seq[ClientUncachedTileLinkIO], - extra: Bundle, p: Parameters) { + mmioPorts: HashMap[String, ClientUncachedTileLinkIO], + clientPorts: Seq[ClientUncachedTileLinkIO], + interrupts : Seq[Bool], + extra: Bundle, p: Parameters) { val busmaster = Module(new ExampleBusMaster()(p)) busmaster.io.mmio <> mmioPorts("busmaster") clientPorts.head <> busmaster.io.mem + interrupts.foreach(x => x := Bool(false)) } } new BusMasterDevice