restructure parameters into config object && cleanup

This commit is contained in:
Richard Yan
2023-04-23 03:09:20 -07:00
parent d28216182c
commit a84757f8f8
2 changed files with 141 additions and 109 deletions

View File

@@ -4,27 +4,64 @@ package freechips.rocketchip.tilelink
import chisel3._
import chisel3.util._
import chisel3.experimental.ChiselEnum
import freechips.rocketchip.config.Parameters
import freechips.rocketchip.diplomacy._
// import freechips.rocketchip.devices.tilelink.TLTestRAM
import freechips.rocketchip.util.MultiPortQueue
import freechips.rocketchip.unittest._
object CoalescerConsts {
val MAX_SIZE = 6 // maximum burst size (64 bytes)
val DEPTH = 1 // request window per lane
val WAIT_TIMEOUT = 8 // max cycles to wait before forced fifo dequeue, per lane
val ADDR_WIDTH = 32 // assume <= 32
val DATA_BUS_SIZE = 4 // 2^4=16 bytes, 128 bit bus
val NUM_LANES = 4
// val WATERMARK = 2 // minimum buffer occupancy to start coalescing
val WORD_SIZE = 4 // 32-bit system
val WORD_WIDTH = 2 // log(WORD_SIZE)
val NUM_OLD_IDS = 8 // num of outstanding requests per lane, from processor
val NUM_NEW_IDS = 4 // num of outstanding coalesced requests
object InFlightTableSizeEnum extends ChiselEnum {
val INVALID = Value(0.U)
val FOUR = Value(1.U)
def log2Enum(x: UInt): Type = {
MuxCase(INVALID, Seq(
(x === 2.U) -> FOUR
))
}
def enum2log(x: Type): UInt = {
MuxCase(0.U, Seq(
(x === FOUR) -> 2.U
))
}
}
class CoalescingUnit(numLanes: Int = CoalescerConsts.NUM_LANES)(implicit p: Parameters) extends LazyModule {
case class CoalescerConfig(
MAX_SIZE: Int, // maximum burst size (64 bytes)
DEPTH: Int, // request window per lane
WAIT_TIMEOUT: Int, // max cycles to wait before forced fifo dequeue, per lane
ADDR_WIDTH: Int, // assume <= 32
DATA_BUS_SIZE: Int, // 2^4=16 bytes, 128 bit bus
NUM_LANES: Int,
// WATERMARK = 2, // minimum buffer occupancy to start coalescing
WORD_SIZE: Int, // 32-bit system
WORD_WIDTH: Int, // log(WORD_SIZE)
NUM_OLD_IDS: Int, // num of outstanding requests per lane, from processor
NUM_NEW_IDS: Int, // num of outstanding coalesced requests
COAL_SIZES: Seq[Int],
SizeEnum: ChiselEnum
)
object defaultConfig extends CoalescerConfig(
// TODO: bigger size
MAX_SIZE = 3, // maximum burst size (64 bytes)
DEPTH = 1, // request window per lane
WAIT_TIMEOUT = 8, // max cycles to wait before forced fifo dequeue, per lane
ADDR_WIDTH = 24, // assume <= 32
DATA_BUS_SIZE = 4, // 2^4=16 bytes, 128 bit bus
NUM_LANES = 4,
// WATERMARK = 2, // minimum buffer occupancy to start coalescing
WORD_SIZE = 4, // 32-bit system
WORD_WIDTH = 2, // log(WORD_SIZE)
NUM_OLD_IDS = 16, // num of outstanding requests per lane, from processor
NUM_NEW_IDS = 4, // num of outstanding coalesced requests
COAL_SIZES = Seq(3),
SizeEnum = InFlightTableSizeEnum
)
class CoalescingUnit(config: CoalescerConfig)(implicit p: Parameters) extends LazyModule {
// Identity node that captures the incoming TL requests and passes them
// through the other end, dropping coalesced requests. This node is what
// will be visible to upstream and downstream nodes.
@@ -32,7 +69,7 @@ class CoalescingUnit(numLanes: Int = CoalescerConsts.NUM_LANES)(implicit p: Para
// Number of maximum in-flight coalesced requests. The upper bound of this
// value would be the sourceId range of a single lane.
val numInflightCoalRequests = CoalescerConsts.NUM_NEW_IDS
val numInflightCoalRequests = config.NUM_NEW_IDS
// Master node that actually generates coalesced requests.
protected val coalParam = Seq(
@@ -48,7 +85,7 @@ class CoalescingUnit(numLanes: Int = CoalescerConsts.NUM_LANES)(implicit p: Para
// Connect master node as the first inward edge of the IdentityNode
node :=* coalescerNode
lazy val module = new CoalescingUnitImp(this, numLanes)
lazy val module = new CoalescingUnitImp(this, config)
}
class ReqQueueEntry(sourceWidth: Int, sizeWidth: Int, addressWidth: Int, maxSize: Int) extends Bundle {
@@ -181,18 +218,19 @@ class CoalShiftQueue[T <: Data](
}
// Software model: coalescer.py
class MonoCoalescer[T <: Data](coalSize: Int, coalWindow: Seq[CoalShiftQueue[T]]) extends Module {
class MonoCoalescer[T <: Data](coalSize: Int, coalWindow: Seq[CoalShiftQueue[T]],
config: CoalescerConfig) extends Module {
val io = IO(new Bundle {
val leader_idx = Output(UInt(log2Ceil(CoalescerConsts.NUM_LANES).W))
val base_addr = Output(UInt(CoalescerConsts.ADDR_WIDTH.W))
val match_oh = Output(Vec(CoalescerConsts.NUM_LANES, UInt(CoalescerConsts.DEPTH.W)))
val coverage_hits = Output(UInt((1 << CoalescerConsts.MAX_SIZE).W))
val leader_idx = Output(UInt(log2Ceil(config.NUM_LANES).W))
val base_addr = Output(UInt(config.ADDR_WIDTH.W))
val match_oh = Output(Vec(config.NUM_LANES, UInt(config.DEPTH.W)))
val coverage_hits = Output(UInt((1 << config.MAX_SIZE).W))
})
io := DontCare
val size = coalSize
val mask = ((1 << CoalescerConsts.ADDR_WIDTH - 1) - (1 << size - 1)).U
val mask = ((1 << config.ADDR_WIDTH - 1) - (1 << size - 1)).U
val window = coalWindow
def can_match(req0: Valid[ReqQueueEntry], req1: Valid[ReqQueueEntry]): Bool = {
@@ -208,33 +246,36 @@ class MonoCoalescer[T <: Data](coalSize: Int, coalWindow: Seq[CoalShiftQueue[T]]
// Software model: coalescer.py
class MultiCoalescer[T <: Data]
(sizes: Seq[Int], window: Seq[CoalShiftQueue[T]], coalReqT: ReqQueueEntry) extends Module {
(sizes: Seq[Int], window: Seq[CoalShiftQueue[T]], coalReqT: ReqQueueEntry,
config: CoalescerConfig) extends Module {
val coalescers = sizes.map(size => Module(new MonoCoalescer(size, window)))
val coalescers = sizes.map(size => Module(new MonoCoalescer(size, window, config)))
val io = IO(new Bundle {
val out_req = Output(Valid(coalReqT.cloneType))
val invalidate = Output(Valid(Vec(CoalescerConsts.NUM_LANES, UInt(CoalescerConsts.DEPTH.W))))
val invalidate = Output(Valid(Vec(config.NUM_LANES, UInt(config.DEPTH.W))))
})
io := DontCare
}
class CoalescingUnitImp(outer: CoalescingUnit, numLanes: Int) extends LazyModuleImp(outer) {
class CoalescingUnitImp(outer: CoalescingUnit, config: CoalescerConfig) extends LazyModuleImp(outer) {
// Make sure IdentityNode is connected to an upstream node, not just the
// coalescer TL master node
assert(outer.node.in.length >= 2)
assert(outer.node.in(1)._1.params.sourceBits == log2Ceil(config.NUM_OLD_IDS),
s"old source id bits TL param (${outer.node.in(1)._1.params.sourceBits}) mismatch with config")
assert(outer.node.in(1)._1.params.addressBits == config.ADDR_WIDTH,
s"address width TL param (${outer.node.in(1)._1.params.addressBits}) mismatch with config")
val reqQueueDepth = CoalescerConsts.DEPTH
val sourceWidth = outer.node.in(1)._1.params.sourceBits
val addressWidth = outer.node.in(1)._1.params.addressBits
// note we are using word size. assuming all coalescer inputs are word sized
val reqQueueEntryT = new ReqQueueEntry(sourceWidth, log2Ceil(CoalescerConsts.WORD_SIZE), addressWidth, CoalescerConsts.WORD_SIZE)
val reqQueues = Seq.tabulate(numLanes) { _ =>
Module(new CoalShiftQueue(reqQueueEntryT, reqQueueDepth))
val reqQueueEntryT = new ReqQueueEntry(sourceWidth, config.WORD_WIDTH, config.ADDR_WIDTH, config.WORD_SIZE)
val reqQueues = Seq.tabulate(config.NUM_LANES) { _ =>
Module(new CoalShiftQueue(reqQueueEntryT, config.DEPTH))
}
val coalReqT = new ReqQueueEntry(sourceWidth, log2Ceil(CoalescerConsts.MAX_SIZE), addressWidth, CoalescerConsts.MAX_SIZE)
val coalescer = Module(new MultiCoalescer(Seq(4, 5, 6), reqQueues, coalReqT))
val coalReqT = new ReqQueueEntry(sourceWidth, log2Ceil(config.MAX_SIZE), config.ADDR_WIDTH, config.MAX_SIZE)
val coalescer = Module(new MultiCoalescer(config.COAL_SIZES, reqQueues, coalReqT, config))
// Per-lane request and response queues
//
@@ -251,9 +292,8 @@ class CoalescingUnitImp(outer: CoalescingUnit, numLanes: Int) extends LazyModule
// except for connecting the outgoing edge to the inflight table, which is done
// down below.
tlOut.a <> tlIn.a
case (((tlIn, edgeIn), (tlOut, edgeOut)), i) =>
case (((tlIn, _), (tlOut, edgeOut)), i) =>
// Request queue
//
val lane = i - 1
val reqQueue = reqQueues(lane)
val req = Wire(reqQueueEntryT)
@@ -293,13 +333,12 @@ class CoalescingUnitImp(outer: CoalescingUnit, numLanes: Int) extends LazyModule
// ******************************************************************
// ==================================================================
val respQueueDepth = CoalescerConsts.NUM_NEW_IDS
// The maximum number of requests from a single lane that can go into a
// coalesced request. Upper bound is min(DEPTH, 2**sourceWidth).
val numPerLaneReqs = CoalescerConsts.DEPTH
val numPerLaneReqs = config.DEPTH
val respQueueEntryT = new RespQueueEntry(sourceWidth, log2Ceil(CoalescerConsts.MAX_SIZE), CoalescerConsts.MAX_SIZE)
val respQueues = Seq.tabulate(numLanes) { _ =>
val respQueueEntryT = new RespQueueEntry(sourceWidth, log2Ceil(config.MAX_SIZE), config.MAX_SIZE)
val respQueues = Seq.tabulate(config.NUM_LANES) { _ =>
Module(
new MultiPortQueue(
respQueueEntryT,
@@ -318,7 +357,7 @@ class CoalescingUnitImp(outer: CoalescingUnit, numLanes: Int) extends LazyModule
// make queue block up in the middle of the simulation. Ideally there
// should be a more logical way to set this, or we should handle
// response queue blocking.
respQueueDepth
config.NUM_NEW_IDS
)
)
}
@@ -335,7 +374,7 @@ class CoalescingUnitImp(outer: CoalescingUnit, numLanes: Int) extends LazyModule
// except for connecting the outgoing edge to the inflight table, which is done
// down below.
tlIn.d <> tlOut.d
case (((tlIn, edgeIn), (tlOut, edgeOut)), i) =>
case (((tlIn, edgeIn), (tlOut, _)), i) =>
// Response queue
//
// This queue will serialize non-coalesced responses along with
@@ -396,25 +435,32 @@ class CoalescingUnitImp(outer: CoalescingUnit, numLanes: Int) extends LazyModule
// Construct new entry for the inflight table
// FIXME: don't instantiate inflight table entry type here. It leaks the table's impl
// detail to the coalescer
// richard: I think a good idea is to pass Valid[ReqQueueEntry] generated by
// the coalescer directly into the uncoalescer, so that we can offload the
// logic to generate the Inflight Entry into the uncoalescer, where it should be.
// this also reduces top level clutter.
val offsetBits = 4 // FIXME hardcoded
val sizeBits = 4 // FIXME hardcoded. This is should be not the TL size bits
val sizeBits = log2Ceil(config.MAX_SIZE) // FIXME This is should be not the TL size bits
// but the width of the size enum
val newEntry = Wire(
new InflightCoalReqTableEntry(numLanes, numPerLaneReqs, sourceWidth, offsetBits, sizeBits)
new InflightCoalReqTableEntry(config.NUM_LANES, numPerLaneReqs, sourceWidth, offsetBits, sizeBits)
)
println(s"=========== table sourceWidth: ${sourceWidth}")
println(s"=========== table sizeBits: ${sizeBits}")
newEntry.source := coalescer.io.out_req.bits.source
// TODO: richard to write table fill logic
assert(tlCoal.params.dataBits == (1 << CoalescerConsts.MAX_SIZE) * 8, "tlCoal parameters mismatch coalescer constant")
assert(tlCoal.params.dataBits == (1 << config.MAX_SIZE) * 8,
s"tlCoal param dataBits (${tlCoal.params.dataBits}) mismatch coalescer constant")
val origReqs = reqQueues.map(q => q.io.queue.deq.bits)
newEntry.lanes.foreach { l =>
l.reqs.zipWithIndex.foreach { case (r, i) =>
// TODO: this part needs the actual coalescing logic to work
r.valid := false.B
r.source := origReqs(i).source
r.offset := (origReqs(i).address % (1 << CoalescerConsts.MAX_SIZE).U) >> CoalescerConsts.WORD_WIDTH
r.offset := (origReqs(i).address % (1 << config.MAX_SIZE).U) >> config.WORD_WIDTH
r.size := origReqs(i).size
}
}
@@ -425,22 +471,13 @@ class CoalescingUnitImp(outer: CoalescingUnit, numLanes: Int) extends LazyModule
dontTouch(newEntry)
// Uncoalescer module uncoalesces responses back to each lane
val uncoalescer = Module(
new UncoalescingUnit(
numLanes,
numPerLaneReqs,
sourceWidth,
CoalescerConsts.WORD_WIDTH,
(1 << CoalescerConsts.MAX_SIZE),
outer.numInflightCoalRequests
)
)
val uncoalescer = Module(new UncoalescingUnit(config, tlCoal.d.bits.cloneType))
uncoalescer.io.coalReqValid := coalescer.io.out_req.valid
uncoalescer.io.newEntry := newEntry
uncoalescer.io.coalRespValid := tlCoal.d.valid
uncoalescer.io.coalRespSrcId := tlCoal.d.bits.source
uncoalescer.io.coalRespData := tlCoal.d.bits.data
// richard: I changed this to use the DecoupledIO interface, which TL is using,
// previously we were not handling the ready signal
uncoalescer.io.coalResp <> tlCoal.d
// Queue up synthesized uncoalesced responses into each lane's response queue
(respQueues zip uncoalescer.io.uncoalResps).foreach { case (q, lanes) =>
@@ -466,27 +503,24 @@ class CoalescingUnitImp(outer: CoalescingUnit, numLanes: Int) extends LazyModule
dontTouch(tlCoal.d)
}
class UncoalescingUnit(
val numLanes: Int,
val numPerLaneReqs: Int,
val sourceWidth: Int,
val sizeWidth: Int,
val coalDataWidth: Int,
val numInflightCoalRequests: Int
) extends Module {
val inflightTable = Module(
new InflightCoalReqTable(numLanes, numPerLaneReqs, sourceWidth, numInflightCoalRequests)
)
class UncoalescingUnit(config: CoalescerConfig, tlCoalD: TLBundleD) extends Module {
// notes to hansung:
// val numLanes: Int, <-> config.NUM_LANES
// val numPerLaneReqs: Int, <-> config.DEPTH
// val sourceWidth: Int, <-> log2ceil(config.NUM_OLD_IDS)
// val sizeWidth: Int, <-> config.SizeEnum.width
// val coalDataWidth: Int, <-> (1 << config.MAX_SIZE)
// val numInflightCoalRequests: Int <-> config.NUM_NEW_IDS
val inflightTable = Module(new InflightCoalReqTable(config))
val io = IO(new Bundle {
val coalReqValid = Input(Bool())
val newEntry = Input(inflightTable.entryT)
val coalRespValid = Input(Bool())
val coalRespSrcId = Input(UInt(sourceWidth.W))
val coalRespData = Input(UInt(coalDataWidth.W))
val newEntry = Input(inflightTable.entryT.cloneType)
val coalResp = Flipped(Decoupled(tlCoalD))
val uncoalResps = Output(
Vec(
numLanes,
Vec(numPerLaneReqs, ValidIO(new RespQueueEntry(sourceWidth, CoalescerConsts.WORD_WIDTH, CoalescerConsts.WORD_SIZE)))
config.NUM_LANES,
Vec(config.DEPTH, ValidIO(new RespQueueEntry(
log2Ceil(config.NUM_OLD_IDS), config.WORD_WIDTH, config.WORD_SIZE)))
)
)
})
@@ -496,19 +530,20 @@ class UncoalescingUnit(
inflightTable.io.enq.bits := io.newEntry
// Look up the table with incoming coalesced responses
inflightTable.io.lookup.ready := io.coalRespValid
inflightTable.io.lookupSourceId := io.coalRespSrcId
inflightTable.io.lookup.ready := io.coalResp.valid
inflightTable.io.lookupSourceId := io.coalResp.bits.source
io.coalResp.ready := true.B // FIXME, see sw model implementation
assert(
!((io.coalReqValid === true.B) && (io.coalRespValid === true.B) &&
(io.newEntry.source === io.coalRespSrcId)),
!((io.coalReqValid === true.B) && (io.coalResp.valid === true.B) &&
(io.newEntry.source === io.coalResp.bits.source)),
"inflight table: enqueueing and looking up the same srcId at the same cycle is not handled"
)
// Un-coalescing logic
//
def getCoalescedDataChunk(data: UInt, dataWidth: Int, offset: UInt, logSize: UInt): UInt = {
val sizeInBits = (1.U << logSize) * 8.U
val sizeInBits = (1.U << logSize) << 3.U
assert(
(dataWidth > 0).B && (dataWidth.U % sizeInBits === 0.U),
s"coalesced data width ($dataWidth) not evenly divisible by core req size ($sizeInBits)"
@@ -541,7 +576,7 @@ class UncoalescingUnit(
ioOldReq.bits.source := oldReq.source
ioOldReq.bits.size := oldReq.size
ioOldReq.bits.data :=
getCoalescedDataChunk(io.coalRespData, coalDataWidth, oldReq.offset, oldReq.size)
getCoalescedDataChunk(io.coalResp.bits.data, io.coalResp.bits.data.getWidth, oldReq.offset, oldReq.size)
}
}
}
@@ -552,16 +587,14 @@ class UncoalescingUnit(
// from, what their original TileLink sourceId were, etc. We use this info to
// split the coalesced response back to individual per-lane responses with the
// right metadata.
class InflightCoalReqTable(
val numLanes: Int,
val numPerLaneReqs: Int,
val sourceWidth: Int,
val entries: Int
) extends Module {
class InflightCoalReqTable(config: CoalescerConfig) extends Module {
val offsetBits = 4 // FIXME hardcoded
val sizeBits = 2 // FIXME hardcoded
val entryT =
new InflightCoalReqTableEntry(numLanes, numPerLaneReqs, sourceWidth, offsetBits, sizeBits)
val entryT = new InflightCoalReqTableEntry(config.NUM_LANES, config.DEPTH,
log2Ceil(config.NUM_OLD_IDS), config.MAX_SIZE, config.SizeEnum.getWidth)
val entries = config.NUM_NEW_IDS
val sourceWidth = log2Ceil(config.NUM_OLD_IDS)
val io = IO(new Bundle {
val enq = Flipped(Decoupled(entryT))
@@ -575,8 +608,7 @@ class InflightCoalReqTable(
entries,
new Bundle {
val valid = Bool()
val bits =
new InflightCoalReqTableEntry(numLanes, numPerLaneReqs, sourceWidth, offsetBits, sizeBits)
val bits = entryT.cloneType
}
)
@@ -672,11 +704,11 @@ object TLUtils {
}
}
class MemTraceDriver(numLanes: Int = 4, filename: String = "vecadd.core1.thread4.trace")(implicit
class MemTraceDriver(config: CoalescerConfig, filename: String = "vecadd.core1.thread4.trace")(implicit
p: Parameters
) extends LazyModule {
// Create N client nodes together
val laneNodes = Seq.tabulate(numLanes) { i =>
val laneNodes = Seq.tabulate(config.NUM_LANES) { i =>
val clientParam = Seq(
TLMasterParameters.v1(
name = "MemTraceDriver" + i.toString,
@@ -692,7 +724,7 @@ class MemTraceDriver(numLanes: Int = 4, filename: String = "vecadd.core1.thread4
val node = TLIdentityNode()
laneNodes.foreach { l => node := l }
lazy val module = new MemTraceDriverImp(this, numLanes, filename)
lazy val module = new MemTraceDriverImp(this, config, filename)
}
trait HasTraceLine {
@@ -715,10 +747,10 @@ class TraceLine extends Bundle with HasTraceLine {
val data = UInt(64.W)
}
class MemTraceDriverImp(outer: MemTraceDriver, numLanes: Int, traceFile: String)
class MemTraceDriverImp(outer: MemTraceDriver, config: CoalescerConfig, traceFile: String)
extends LazyModuleImp(outer)
with UnitTestModule {
val sim = Module(new SimMemTrace(traceFile, numLanes))
val sim = Module(new SimMemTrace(traceFile, config.NUM_LANES))
sim.io.clock := clock
sim.io.reset := reset.asBool
sim.io.trace_read.ready := true.B
@@ -726,7 +758,7 @@ class MemTraceDriverImp(outer: MemTraceDriver, numLanes: Int, traceFile: String)
// Split output of SimMemTrace, which is flattened across all lanes,
// back to each lane's.
val laneReqs = Wire(Vec(numLanes, new TraceLine))
val laneReqs = Wire(Vec(config.NUM_LANES, new TraceLine))
val addrW = laneReqs(0).address.getWidth
val sizeW = laneReqs(0).size.getWidth
val dataW = laneReqs(0).data.getWidth
@@ -759,20 +791,20 @@ class MemTraceDriverImp(outer: MemTraceDriver, numLanes: Int, traceFile: String)
// the trace driver to act so as well.
// That means if req.size is smaller than word size, we need to pad data
// with zeros to generate a word-size request, and set mask accordingly.
val offsetInWord = req.address % CoalescerConsts.WORD_SIZE.U
val subword = req.size < log2Ceil(CoalescerConsts.WORD_SIZE).U
val offsetInWord = req.address % config.WORD_SIZE.U
val subword = req.size < log2Ceil(config.WORD_SIZE).U
val mask = Wire(UInt(CoalescerConsts.WORD_SIZE.W))
val wordData = Wire(UInt((CoalescerConsts.WORD_SIZE * 8).W))
val mask = Wire(UInt(config.WORD_SIZE.W))
val wordData = Wire(UInt((config.WORD_SIZE * 8).W))
val sizeInBytes = Wire(UInt((sizeW + 1).W))
sizeInBytes := (1.U) << req.size
mask := Mux(subword, (~((~0.U(64.W)) << sizeInBytes)) << offsetInWord, ~0.U)
wordData := Mux(subword, req.data << (offsetInWord * 8.U), req.data)
val wordAlignedAddress = req.address & ~((1 << log2Ceil(CoalescerConsts.WORD_SIZE)) - 1).U(addrW.W)
val wordAlignedAddress = req.address & ~((1 << log2Ceil(config.WORD_SIZE)) - 1).U(addrW.W)
assert(
req.size <= log2Ceil(CoalescerConsts.WORD_SIZE).U,
s"trace driver currently does not support access sizes larger than word size (${CoalescerConsts.WORD_SIZE})"
req.size <= log2Ceil(config.WORD_SIZE).U,
s"trace driver currently does not support access sizes larger than word size (${config.WORD_SIZE})"
)
val wordAlignedSize = 2.U // FIXME: hardcoded
@@ -782,7 +814,7 @@ class MemTraceDriverImp(outer: MemTraceDriver, numLanes: Int, traceFile: String)
// req.address,
// req.size,
// req.data,
// ~((1 << log2Ceil(CoalescerConsts.WORD_SIZE)) - 1).U(addrW.W),
// ~((1 << log2Ceil(config.WORD_SIZE)) - 1).U(addrW.W),
// wordAlignedAddress,
// mask,
// wordData
@@ -1153,11 +1185,11 @@ object TracePrintf {
class TLRAMCoalescerLogger(implicit p: Parameters) extends LazyModule {
// TODO: use parameters for numLanes
val numLanes = 4
val driver = LazyModule(new MemTraceDriver(numLanes))
val driver = LazyModule(new MemTraceDriver(defaultConfig))
val coreSideLogger = LazyModule(
new MemTraceLogger(numLanes, loggerName = "coreside")
)
val coal = LazyModule(new CoalescingUnit(numLanes))
val coal = LazyModule(new CoalescingUnit(defaultConfig))
val memSideLogger = LazyModule(new MemTraceLogger(numLanes + 1, loggerName = "memside"))
val rams = Seq.fill(numLanes + 1)( // +1 for coalesced edge
LazyModule(
@@ -1204,8 +1236,8 @@ class TLRAMCoalescerLoggerTest(timeout: Int = 500000)(implicit p: Parameters)
class TLRAMCoalescer(implicit p: Parameters) extends LazyModule {
// TODO: use parameters for numLanes
val numLanes = 4
val coal = LazyModule(new CoalescingUnit(numLanes))
val driver = LazyModule(new MemTraceDriver(numLanes))
val coal = LazyModule(new CoalescingUnit(defaultConfig))
val driver = LazyModule(new MemTraceDriver(defaultConfig))
val rams = Seq.fill(numLanes + 1)( // +1 for coalesced edge
LazyModule(
// NOTE: beatBytes here sets the data bitwidth of the upstream TileLink

View File

@@ -27,7 +27,7 @@ trait CanHaveGPUTracer { this: BaseSubsystem =>
//p(GPUTracerKey) is the mechnimism to pass Config's parameter down to lazymodule
p(GPUTracerKey) .map { k =>
val config = p(GPUTracerKey).get
val tracer = LazyModule(new MemTraceDriver(config.numLanes, config.traceFile)(p))
val tracer = LazyModule(new MemTraceDriver(defaultConfig, config.traceFile)(p))
// Must use :=* to ensure the N edges from Tracer doesn't get merged into 1 when connecting to SBus
sbus.fromPort(Some("gpu-tracer"))() :=* tracer.node
}