108 lines
4.1 KiB
Scala
108 lines
4.1 KiB
Scala
//******************************************************************************
|
|
// Copyright (c) 2019 - 2019, The Regents of the University of California (Regents).
|
|
// All Rights Reserved. See LICENSE and LICENSE.SiFive for license details.
|
|
//------------------------------------------------------------------------------
|
|
|
|
package utilities
|
|
|
|
import chisel3._
|
|
import chisel3.internal.sourceinfo.{SourceInfo}
|
|
|
|
import freechips.rocketchip.config.{Field, Parameters}
|
|
import freechips.rocketchip.devices.tilelink._
|
|
import freechips.rocketchip.devices.debug.{HasPeripheryDebug, HasPeripheryDebugModuleImp}
|
|
import freechips.rocketchip.diplomacy._
|
|
import freechips.rocketchip.diplomaticobjectmodel.model.{OMInterrupt}
|
|
import freechips.rocketchip.diplomaticobjectmodel.logicaltree.{RocketTileLogicalTreeNode, LogicalModuleTree}
|
|
import freechips.rocketchip.tile._
|
|
import freechips.rocketchip.tilelink._
|
|
import freechips.rocketchip.interrupts._
|
|
import freechips.rocketchip.util._
|
|
import freechips.rocketchip.subsystem._
|
|
import freechips.rocketchip.amba.axi4._
|
|
|
|
import boom.common.{BoomTile, BoomTilesKey, BoomCrossingKey, BoomTileParams}
|
|
|
|
|
|
trait HasBoomAndRocketTiles extends HasTiles
|
|
with CanHavePeripheryPLIC
|
|
with CanHavePeripheryCLINT
|
|
with HasPeripheryDebug
|
|
{ this: BaseSubsystem =>
|
|
|
|
val module: HasBoomAndRocketTilesModuleImp
|
|
|
|
protected val rocketTileParams = p(RocketTilesKey)
|
|
protected val boomTileParams = p(BoomTilesKey)
|
|
|
|
// crossing can either be per tile or global (aka only 1 crossing specified)
|
|
private val rocketCrossings = perTileOrGlobalSetting(p(RocketCrossingKey), rocketTileParams.size)
|
|
private val boomCrossings = perTileOrGlobalSetting(p(BoomCrossingKey), boomTileParams.size)
|
|
|
|
val allTilesInfo = (rocketTileParams ++ boomTileParams) zip (rocketCrossings ++ boomCrossings)
|
|
|
|
// Make a tile and wire its nodes into the system,
|
|
// according to the specified type of clock crossing.
|
|
// Note that we also inject new nodes into the tile itself,
|
|
// also based on the crossing type.
|
|
// This MUST be performed in order of hartid
|
|
// There is something weird with registering tile-local interrupt controllers to the CLINT.
|
|
// TODO: investigate why
|
|
val tiles = allTilesInfo.sortWith(_._1.hartId < _._1.hartId).map {
|
|
case (param, crossing) => {
|
|
val (tile, rocketLogicalTree) = param match {
|
|
case r: RocketTileParams => {
|
|
val t = LazyModule(new RocketTile(r, crossing, PriorityMuxHartIdFromSeq(rocketTileParams), logicalTreeNode))
|
|
(t, t.rocketLogicalTree)
|
|
}
|
|
case b: BoomTileParams => {
|
|
val t = LazyModule(new BoomTile(b, crossing, PriorityMuxHartIdFromSeq(boomTileParams), logicalTreeNode))
|
|
(t, t.rocketLogicalTree) // TODO FIX rocketLogicalTree is not a member of the superclass, both child classes define it separately
|
|
}
|
|
}
|
|
connectMasterPortsToSBus(tile, crossing)
|
|
connectSlavePortsToCBus(tile, crossing)
|
|
|
|
def treeNode: RocketTileLogicalTreeNode = new RocketTileLogicalTreeNode(rocketLogicalTree.getOMInterruptTargets)
|
|
LogicalModuleTree.add(logicalTreeNode, rocketLogicalTree)
|
|
|
|
connectInterrupts(tile, Some(debug), clintOpt, plicOpt)
|
|
|
|
tile
|
|
}
|
|
}
|
|
|
|
|
|
def coreMonitorBundles = tiles.map {
|
|
case r: RocketTile => r.module.core.rocketImpl.coreMonitorBundle
|
|
case b: BoomTile => b.module.core.coreMonitorBundle
|
|
}.toList
|
|
}
|
|
|
|
trait HasBoomAndRocketTilesModuleImp extends HasTilesModuleImp
|
|
with HasPeripheryDebugModuleImp
|
|
{
|
|
val outer: HasBoomAndRocketTiles
|
|
}
|
|
|
|
class Subsystem(implicit p: Parameters) extends BaseSubsystem
|
|
with HasBoomAndRocketTiles
|
|
{
|
|
override lazy val module = new SubsystemModuleImp(this)
|
|
|
|
def getOMInterruptDevice(resourceBindingsMap: ResourceBindingsMap): Seq[OMInterrupt] = Nil
|
|
}
|
|
|
|
class SubsystemModuleImp[+L <: Subsystem](_outer: L) extends BaseSubsystemModuleImp(_outer)
|
|
with HasResetVectorWire
|
|
with HasBoomAndRocketTilesModuleImp
|
|
{
|
|
tile_inputs.zip(outer.hartIdList).foreach { case(wire, i) =>
|
|
wire.hartid := i.U
|
|
wire.reset_vector := global_reset_vector
|
|
}
|
|
|
|
// create file with boom params
|
|
ElaborationArtefacts.add("""core.config""", outer.tiles.map(x => x.module.toString).mkString("\n"))
|
|
}
|