tilelink2: split suportsAcquire into T and B variants
This commit is contained in:
@ -253,7 +253,7 @@ class TLAtomicAutomata(logical: Boolean = true, arithmetic: Boolean = true, conc
|
||||
in.d.bits := out.d.bits
|
||||
}
|
||||
|
||||
if (edgeOut.manager.anySupportAcquire && edgeIn.client.anySupportProbe) {
|
||||
if (edgeOut.manager.anySupportAcquireB && edgeIn.client.anySupportProbe) {
|
||||
in.b.valid := out.b.valid
|
||||
out.b.ready := in.b.ready
|
||||
in.b.bits := out.b.bits
|
||||
|
@ -22,22 +22,24 @@ class TLBroadcast(lineBytes: Int, numTrackers: Int = 4, bufferless: Boolean = fa
|
||||
endSinkId = numTrackers,
|
||||
managers = mp.managers.map { m =>
|
||||
// We are the last level manager
|
||||
require (m.regionType != RegionType.CACHED)
|
||||
require (m.regionType != RegionType.TRACKED)
|
||||
require (!m.supportsAcquire)
|
||||
require (!m.supportsAcquireB)
|
||||
// We only manage addresses which are uncached
|
||||
if (m.regionType == RegionType.UNCACHED && m.supportsGet) {
|
||||
if (m.regionType == RegionType.UNCACHED) {
|
||||
// The device had better support line transfers
|
||||
val lowerBound = max(m.supportsPutFull.min, m.supportsGet.min)
|
||||
require (!m.supportsPutFull || m.supportsPutFull.contains(lineBytes))
|
||||
require (!m.supportsGet || m.supportsGet .contains(lineBytes))
|
||||
m.copy(
|
||||
regionType = RegionType.TRACKED,
|
||||
supportsAcquire = TransferSizes(lowerBound, lineBytes),
|
||||
supportsAcquireB = TransferSizes(lowerBound, lineBytes),
|
||||
supportsAcquireT = if (m.supportsPutFull) TransferSizes(lowerBound, lineBytes) else TransferSizes.none,
|
||||
// truncate supported accesses to lineBytes (we only ever probe for one line)
|
||||
supportsPutFull = TransferSizes(m.supportsPutFull .min, min(m.supportsPutFull .max, lineBytes)),
|
||||
supportsPutPartial = TransferSizes(m.supportsPutPartial.min, min(m.supportsPutPartial.max, lineBytes)),
|
||||
supportsGet = TransferSizes(m.supportsGet .min, min(m.supportsGet .max, lineBytes)),
|
||||
supportsHint = TransferSizes(m.supportsHint .min, min(m.supportsHint .max, lineBytes)),
|
||||
supportsArithmetic = TransferSizes(m.supportsArithmetic.min, min(m.supportsArithmetic.max, lineBytes)),
|
||||
supportsLogical = TransferSizes(m.supportsLogical .min, min(m.supportsLogical .max, lineBytes)),
|
||||
fifoId = None // trackers do not respond in FIFO order!
|
||||
)
|
||||
} else {
|
||||
|
@ -31,7 +31,7 @@ class TLBuffer(a: Int = 2, b: Int = 2, c: Int = 2, d: Int = 2, e: Int = 2, pipe:
|
||||
if (a>0) { out.a <> Queue(in .a, a, pipe && a<2) } else { out.a <> in.a }
|
||||
if (d>0) { in .d <> Queue(out.d, d, pipe && d<2) } else { in.d <> out.d }
|
||||
|
||||
if (edgeOut.manager.anySupportAcquire && edgeOut.client.anySupportProbe) {
|
||||
if (edgeOut.manager.anySupportAcquireB && edgeOut.client.anySupportProbe) {
|
||||
if (b>0) { in .b <> Queue(out.b, b, pipe && b<2) } else { in.b <> out.b }
|
||||
if (c>0) { out.c <> Queue(in .c, c, pipe && c<2) } else { out.c <> in.c }
|
||||
if (e>0) { out.e <> Queue(in .e, e, pipe && e<2) } else { out.e <> in.e }
|
||||
|
@ -20,7 +20,7 @@ class TLAsyncCrossingSource(sync: Int = 3)(implicit p: Parameters) extends LazyM
|
||||
|
||||
((io.in zip io.out) zip (node.edgesIn zip node.edgesOut)) foreach { case ((in, out), (edgeIn, edgeOut)) =>
|
||||
val sink_reset_n = out.a.sink_reset_n
|
||||
val bce = edgeIn.manager.anySupportAcquire && edgeIn.client.anySupportProbe
|
||||
val bce = edgeIn.manager.anySupportAcquireB && edgeIn.client.anySupportProbe
|
||||
val depth = edgeOut.manager.depth
|
||||
|
||||
out.a <> ToAsyncBundle(in.a, depth, sync)
|
||||
@ -54,7 +54,7 @@ class TLAsyncCrossingSink(depth: Int = 8, sync: Int = 3)(implicit p: Parameters)
|
||||
|
||||
((io.in zip io.out) zip (node.edgesIn zip node.edgesOut)) foreach { case ((in, out), (edgeIn, edgeOut)) =>
|
||||
val source_reset_n = in.a.source_reset_n
|
||||
val bce = edgeOut.manager.anySupportAcquire && edgeOut.client.anySupportProbe
|
||||
val bce = edgeOut.manager.anySupportAcquireB && edgeOut.client.anySupportProbe
|
||||
|
||||
out.a <> FromAsyncBundle(in.a, sync)
|
||||
in.d <> ToAsyncBundle(out.d, depth, sync)
|
||||
|
@ -27,7 +27,7 @@ class TLEdge(
|
||||
// Do there exist A messages with Data?
|
||||
val aDataYes = manager.anySupportArithmetic || manager.anySupportLogical || manager.anySupportPutFull || manager.anySupportPutPartial
|
||||
// Do there exist A messages without Data?
|
||||
val aDataNo = manager.anySupportAcquire || manager.anySupportGet || manager.anySupportHint
|
||||
val aDataNo = manager.anySupportAcquireB || manager.anySupportGet || manager.anySupportHint
|
||||
// Statically optimize the case where hasData is a constant
|
||||
if (!aDataYes) Some(false) else if (!aDataNo) Some(true) else None
|
||||
}
|
||||
@ -48,9 +48,9 @@ class TLEdge(
|
||||
}
|
||||
case _:TLBundleD => {
|
||||
// Do there eixst D messages with Data?
|
||||
val dDataYes = manager.anySupportGet || manager.anySupportArithmetic || manager.anySupportLogical || manager.anySupportAcquire
|
||||
val dDataYes = manager.anySupportGet || manager.anySupportArithmetic || manager.anySupportLogical || manager.anySupportAcquireB
|
||||
// Do there exist D messages without Data?
|
||||
val dDataNo = manager.anySupportPutFull || manager.anySupportPutPartial || manager.anySupportHint || manager.anySupportAcquire
|
||||
val dDataNo = manager.anySupportPutFull || manager.anySupportPutPartial || manager.anySupportHint || manager.anySupportAcquireT
|
||||
if (!dDataYes) Some(false) else if (!dDataNo) Some(true) else None
|
||||
}
|
||||
case _:TLBundleE => Some(false)
|
||||
@ -244,8 +244,8 @@ class TLEdgeOut(
|
||||
{
|
||||
// Transfers
|
||||
def Acquire(fromSource: UInt, toAddress: UInt, lgSize: UInt, growPermissions: UInt) = {
|
||||
require (manager.anySupportAcquire)
|
||||
val legal = manager.supportsAcquireFast(toAddress, lgSize)
|
||||
require (manager.anySupportAcquireB)
|
||||
val legal = manager.supportsAcquireBFast(toAddress, lgSize)
|
||||
val a = Wire(new TLBundleA(bundle))
|
||||
a.opcode := TLMessages.Acquire
|
||||
a.param := growPermissions
|
||||
@ -258,8 +258,8 @@ class TLEdgeOut(
|
||||
}
|
||||
|
||||
def Release(fromSource: UInt, toAddress: UInt, lgSize: UInt, shrinkPermissions: UInt) = {
|
||||
require (manager.anySupportAcquire)
|
||||
val legal = manager.supportsAcquireFast(toAddress, lgSize)
|
||||
require (manager.anySupportAcquireB)
|
||||
val legal = manager.supportsAcquireBFast(toAddress, lgSize)
|
||||
val c = Wire(new TLBundleC(bundle))
|
||||
c.opcode := TLMessages.Release
|
||||
c.param := shrinkPermissions
|
||||
@ -272,8 +272,8 @@ class TLEdgeOut(
|
||||
}
|
||||
|
||||
def Release(fromSource: UInt, toAddress: UInt, lgSize: UInt, shrinkPermissions: UInt, data: UInt) = {
|
||||
require (manager.anySupportAcquire)
|
||||
val legal = manager.supportsAcquireFast(toAddress, lgSize)
|
||||
require (manager.anySupportAcquireB)
|
||||
val legal = manager.supportsAcquireBFast(toAddress, lgSize)
|
||||
val c = Wire(new TLBundleC(bundle))
|
||||
c.opcode := TLMessages.ReleaseData
|
||||
c.param := shrinkPermissions
|
||||
|
@ -22,7 +22,8 @@ class TLFilter(select: AddressSet)(implicit p: Parameters) extends LazyModule
|
||||
if (filtered.isEmpty) { None } else {
|
||||
Some(m.copy(
|
||||
address = filtered,
|
||||
supportsAcquire = m.supportsAcquire .intersect(cap),
|
||||
supportsAcquireT = m.supportsAcquireT .intersect(cap),
|
||||
supportsAcquireB = m.supportsAcquireB .intersect(cap),
|
||||
supportsArithmetic = m.supportsArithmetic.intersect(cap),
|
||||
supportsLogical = m.supportsLogical .intersect(cap),
|
||||
supportsGet = m.supportsGet .intersect(cap),
|
||||
|
@ -62,7 +62,7 @@ class TLFragmenter(val minSize: Int, val maxSize: Int, val alwaysMin: Boolean =
|
||||
// We don't support fragmenting to sub-beat accesses
|
||||
require (minSize >= beatBytes)
|
||||
// We can't support devices which are cached on both sides of us
|
||||
require (!edgeOut.manager.anySupportAcquire || !edgeIn.client.anySupportProbe)
|
||||
require (!edgeOut.manager.anySupportAcquireB || !edgeIn.client.anySupportProbe)
|
||||
|
||||
/* The Fragmenter is a bit tricky, because there are 5 sizes in play:
|
||||
* max size -- the maximum transfer size possible
|
||||
|
@ -27,7 +27,7 @@ class TLHintHandler(supportManagers: Boolean = true, supportClients: Boolean = f
|
||||
val edgeOut = node.edgesOut(0)
|
||||
|
||||
// Don't add support for clients if there is no BCE channel
|
||||
val bce = edgeOut.manager.anySupportAcquire && edgeIn.client.anySupportProbe
|
||||
val bce = edgeOut.manager.anySupportAcquireB && edgeIn.client.anySupportProbe
|
||||
require (!supportClients || bce)
|
||||
|
||||
// Does it even make sense to add the HintHandler?
|
||||
|
@ -57,7 +57,7 @@ class TLIsolation(fOut: (Bool, UInt) => UInt, fIn: (Bool, UInt) => UInt)(implici
|
||||
ABo(out.a, in .a)
|
||||
ABi(in .d, out.d)
|
||||
|
||||
if (edgeOut.manager.base.anySupportAcquire && edgeOut.client.base.anySupportProbe) {
|
||||
if (edgeOut.manager.base.anySupportAcquireB && edgeOut.client.base.anySupportProbe) {
|
||||
ABi(in .b, out.b)
|
||||
ABo(out.c, in .c)
|
||||
ABo(out.e, in .e)
|
||||
|
@ -42,7 +42,7 @@ class TLMonitor(args: TLMonitorArgs) extends TLMonitorBase(args)
|
||||
val mask = edge.full_mask(bundle)
|
||||
|
||||
when (bundle.opcode === TLMessages.Acquire) {
|
||||
assert (edge.manager.supportsAcquireSafe(edge.address(bundle), bundle.size), "'A' channel carries Acquire type unsupported by manager" + extra)
|
||||
assert (edge.manager.supportsAcquireBSafe(edge.address(bundle), bundle.size), "'A' channel carries Acquire type unsupported by manager" + extra)
|
||||
assert (source_ok, "'A' channel Acquire carries invalid source ID" + extra)
|
||||
assert (bundle.size >= UInt(log2Ceil(edge.manager.beatBytes)), "'A' channel Acquire smaller than a beat" + extra)
|
||||
assert (is_aligned, "'A' channel Acquire address not aligned to size" + extra)
|
||||
@ -189,7 +189,7 @@ class TLMonitor(args: TLMonitorArgs) extends TLMonitorBase(args)
|
||||
}
|
||||
|
||||
when (bundle.opcode === TLMessages.Release) {
|
||||
assert (edge.manager.supportsAcquireSafe(edge.address(bundle), bundle.size), "'C' channel carries Release type unsupported by manager" + extra)
|
||||
assert (edge.manager.supportsAcquireBSafe(edge.address(bundle), bundle.size), "'C' channel carries Release type unsupported by manager" + extra)
|
||||
assert (source_ok, "'C' channel Release carries invalid source ID" + extra)
|
||||
assert (bundle.size >= UInt(log2Ceil(edge.manager.beatBytes)), "'C' channel Release smaller than a beat" + extra)
|
||||
assert (is_aligned, "'C' channel Release address not aligned to size" + extra)
|
||||
@ -198,7 +198,7 @@ class TLMonitor(args: TLMonitorArgs) extends TLMonitorBase(args)
|
||||
}
|
||||
|
||||
when (bundle.opcode === TLMessages.ReleaseData) {
|
||||
assert (edge.manager.supportsAcquireSafe(edge.address(bundle), bundle.size), "'C' channel carries ReleaseData type unsupported by manager" + extra)
|
||||
assert (edge.manager.supportsAcquireBSafe(edge.address(bundle), bundle.size), "'C' channel carries ReleaseData type unsupported by manager" + extra)
|
||||
assert (source_ok, "'C' channel ReleaseData carries invalid source ID" + extra)
|
||||
assert (bundle.size >= UInt(log2Ceil(edge.manager.beatBytes)), "'C' channel ReleaseData smaller than a beat" + extra)
|
||||
assert (is_aligned, "'C' channel ReleaseData address not aligned to size" + extra)
|
||||
|
@ -12,7 +12,8 @@ case class TLManagerParameters(
|
||||
executable: Boolean = false, // processor can execute from this memory
|
||||
nodePath: Seq[BaseNode] = Seq(),
|
||||
// Supports both Acquire+Release+Finish of these sizes
|
||||
supportsAcquire: TransferSizes = TransferSizes.none,
|
||||
supportsAcquireT: TransferSizes = TransferSizes.none,
|
||||
supportsAcquireB: TransferSizes = TransferSizes.none,
|
||||
supportsArithmetic: TransferSizes = TransferSizes.none,
|
||||
supportsLogical: TransferSizes = TransferSizes.none,
|
||||
supportsGet: TransferSizes = TransferSizes.none,
|
||||
@ -28,10 +29,20 @@ case class TLManagerParameters(
|
||||
|
||||
address.combinations(2).foreach { case Seq(x,y) => require (!x.overlaps(y)) }
|
||||
require (supportsPutFull.contains(supportsPutPartial))
|
||||
require (supportsPutFull.contains(supportsArithmetic))
|
||||
require (supportsPutFull.contains(supportsLogical))
|
||||
require (supportsGet.contains(supportsArithmetic))
|
||||
require (supportsGet.contains(supportsLogical))
|
||||
require (supportsAcquireB.contains(supportsAcquireT))
|
||||
|
||||
// Make sure that the regionType agrees with the capabilities
|
||||
require ((regionType == RegionType.CACHED || regionType == RegionType.TRACKED) != supportsAcquireB.none)
|
||||
require (regionType != RegionType.UNCACHED || supportsGet)
|
||||
|
||||
// Largest support transfer of all types
|
||||
val maxTransfer = List(
|
||||
supportsAcquire.max,
|
||||
supportsAcquireT.max,
|
||||
supportsAcquireB.max,
|
||||
supportsArithmetic.max,
|
||||
supportsLogical.max,
|
||||
supportsGet.max,
|
||||
@ -73,7 +84,8 @@ case class TLManagerPortParameters(
|
||||
def maxTransfer = managers.map(_.maxTransfer).max
|
||||
|
||||
// Operation sizes supported by all outward Managers
|
||||
val allSupportAcquire = managers.map(_.supportsAcquire) .reduce(_ intersect _)
|
||||
val allSupportAcquireT = managers.map(_.supportsAcquireT) .reduce(_ intersect _)
|
||||
val allSupportAcquireB = managers.map(_.supportsAcquireB) .reduce(_ intersect _)
|
||||
val allSupportArithmetic = managers.map(_.supportsArithmetic).reduce(_ intersect _)
|
||||
val allSupportLogical = managers.map(_.supportsLogical) .reduce(_ intersect _)
|
||||
val allSupportGet = managers.map(_.supportsGet) .reduce(_ intersect _)
|
||||
@ -82,7 +94,8 @@ case class TLManagerPortParameters(
|
||||
val allSupportHint = managers.map(_.supportsHint) .reduce(_ intersect _)
|
||||
|
||||
// Operation supported by at least one outward Managers
|
||||
val anySupportAcquire = managers.map(!_.supportsAcquire.none) .reduce(_ || _)
|
||||
val anySupportAcquireT = managers.map(!_.supportsAcquireT.none) .reduce(_ || _)
|
||||
val anySupportAcquireB = managers.map(!_.supportsAcquireB.none) .reduce(_ || _)
|
||||
val anySupportArithmetic = managers.map(!_.supportsArithmetic.none).reduce(_ || _)
|
||||
val anySupportLogical = managers.map(!_.supportsLogical.none) .reduce(_ || _)
|
||||
val anySupportGet = managers.map(!_.supportsGet.none) .reduce(_ || _)
|
||||
@ -122,7 +135,8 @@ case class TLManagerPortParameters(
|
||||
}
|
||||
|
||||
// Check for support of a given operation at a specific address
|
||||
val supportsAcquireSafe = safe_helper(_.supportsAcquire) _
|
||||
val supportsAcquireTSafe = safe_helper(_.supportsAcquireT) _
|
||||
val supportsAcquireBSafe = safe_helper(_.supportsAcquireB) _
|
||||
val supportsArithmeticSafe = safe_helper(_.supportsArithmetic) _
|
||||
val supportsLogicalSafe = safe_helper(_.supportsLogical) _
|
||||
val supportsGetSafe = safe_helper(_.supportsGet) _
|
||||
@ -130,7 +144,8 @@ case class TLManagerPortParameters(
|
||||
val supportsPutPartialSafe = safe_helper(_.supportsPutPartial) _
|
||||
val supportsHintSafe = safe_helper(_.supportsHint) _
|
||||
|
||||
val supportsAcquireFast = fast_helper(_.supportsAcquire) _
|
||||
val supportsAcquireTFast = fast_helper(_.supportsAcquireT) _
|
||||
val supportsAcquireBFast = fast_helper(_.supportsAcquireB) _
|
||||
val supportsArithmeticFast = fast_helper(_.supportsArithmetic) _
|
||||
val supportsLogicalFast = fast_helper(_.supportsLogical) _
|
||||
val supportsGetFast = fast_helper(_.supportsGet) _
|
||||
@ -296,7 +311,8 @@ object ManagerUnification
|
||||
regionType: RegionType.T,
|
||||
executable: Boolean,
|
||||
lastNode: BaseNode,
|
||||
supportsAcquire: TransferSizes,
|
||||
supportsAcquireT: TransferSizes,
|
||||
supportsAcquireB: TransferSizes,
|
||||
supportsArithmetic: TransferSizes,
|
||||
supportsLogical: TransferSizes,
|
||||
supportsGet: TransferSizes,
|
||||
@ -307,7 +323,8 @@ object ManagerUnification
|
||||
regionType = x.regionType,
|
||||
executable = x.executable,
|
||||
lastNode = x.nodePath.last,
|
||||
supportsAcquire = x.supportsAcquire,
|
||||
supportsAcquireT = x.supportsAcquireT,
|
||||
supportsAcquireB = x.supportsAcquireB,
|
||||
supportsArithmetic = x.supportsArithmetic,
|
||||
supportsLogical = x.supportsLogical,
|
||||
supportsGet = x.supportsGet,
|
||||
|
@ -31,7 +31,7 @@ class TLSourceShrinker(maxInFlight: Int)(implicit p: Parameters) extends LazyMod
|
||||
|
||||
// Acquires cannot pass this adapter; it makes Probes impossible
|
||||
require (!edgeIn.client.anySupportProbe ||
|
||||
!edgeOut.manager.anySupportAcquire)
|
||||
!edgeOut.manager.anySupportAcquireB)
|
||||
|
||||
out.b.ready := Bool(true)
|
||||
out.c.valid := Bool(false)
|
||||
|
@ -84,9 +84,9 @@ class TLToAXI4(idBits: Int, combinational: Boolean = true)(implicit p: Parameter
|
||||
val a_last = edgeIn.last(in.a)
|
||||
|
||||
// Make sure the fields are within the bounds we assumed
|
||||
assert (a_source < UInt(1 << sourceBits))
|
||||
assert (a_size < UInt(1 << sizeBits))
|
||||
assert (a_addr_lo < UInt(1 << addrBits))
|
||||
assert (a_source < UInt(BigInt(1) << sourceBits))
|
||||
assert (a_size < UInt(BigInt(1) << sizeBits))
|
||||
assert (a_addr_lo < UInt(BigInt(1) << addrBits))
|
||||
|
||||
// Carefully pack/unpack fields into the state we send
|
||||
val baseEnd = 0
|
||||
|
@ -147,7 +147,7 @@ class TLWidthWidget(innerBeatBytes: Int)(implicit p: Parameters) extends LazyMod
|
||||
splice(edgeIn, in.a, edgeOut, out.a)
|
||||
splice(edgeOut, out.d, edgeIn, in.d)
|
||||
|
||||
if (edgeOut.manager.anySupportAcquire && edgeIn.client.anySupportProbe) {
|
||||
if (edgeOut.manager.anySupportAcquireB && edgeIn.client.anySupportProbe) {
|
||||
splice(edgeOut, out.b, edgeIn, in.b)
|
||||
splice(edgeIn, in.c, edgeOut, out.c)
|
||||
in.e.ready := out.e.ready
|
||||
|
@ -164,7 +164,7 @@ class TLXbar(policy: TLArbiter.Policy = TLArbiter.lowestIndexFirst)(implicit p:
|
||||
for (o <- 0 until out.size) {
|
||||
val allowI = Seq.tabulate(in.size) { i =>
|
||||
node.edgesIn(i).client.anySupportProbe &&
|
||||
node.edgesOut(o).manager.anySupportAcquire
|
||||
node.edgesOut(o).manager.anySupportAcquireB
|
||||
}
|
||||
TLArbiter(policy)(out(o).a, (beatsAI zip portsAOI(o) ):_*)
|
||||
TLArbiter(policy)(out(o).c, filter(beatsCI zip portsCOI(o), allowI):_*)
|
||||
@ -174,7 +174,7 @@ class TLXbar(policy: TLArbiter.Policy = TLArbiter.lowestIndexFirst)(implicit p:
|
||||
for (i <- 0 until in.size) {
|
||||
val allowO = Seq.tabulate(out.size) { o =>
|
||||
node.edgesIn(i).client.anySupportProbe &&
|
||||
node.edgesOut(o).manager.anySupportAcquire
|
||||
node.edgesOut(o).manager.anySupportAcquireB
|
||||
}
|
||||
TLArbiter(policy)(in(i).b, filter(beatsBO zip portsBIO(i), allowO):_*)
|
||||
TLArbiter(policy)(in(i).d, (beatsDO zip portsDIO(i) ):_*)
|
||||
|
Reference in New Issue
Block a user