tilelink2: move error from type into Bundle and add HintAck
We need Grant with errors too. We also want to match response type to request type more easily.
This commit is contained in:
parent
534d7f6eb6
commit
ec1f901a38
@ -34,25 +34,25 @@ object TLMessages
|
|||||||
val LogicalData = UInt(3) // . .
|
val LogicalData = UInt(3) // . .
|
||||||
val Get = UInt(4) // . .
|
val Get = UInt(4) // . .
|
||||||
val Hint = UInt(5) // . .
|
val Hint = UInt(5) // . .
|
||||||
val AccessAck = UInt(0) // . .
|
|
||||||
val AccessAckData = UInt(1) // . .
|
|
||||||
val AccessAckError = UInt(6) // . .
|
|
||||||
val Acquire = UInt(6) // .
|
val Acquire = UInt(6) // .
|
||||||
val Probe = UInt(6) // .
|
val Probe = UInt(6) // .
|
||||||
val ProbeAck = UInt(2) // .
|
val AccessAck = UInt(0) // . .
|
||||||
val ProbeAckData = UInt(3) // .
|
val AccessAckData = UInt(1) // . .
|
||||||
val Release = UInt(4) // .
|
val HintAck = UInt(2) // . .
|
||||||
val ReleaseData = UInt(5) // .
|
//val PutThroughData = UInt(3) // . // future extension ?
|
||||||
//val PutThroughData = UInt(7) // . // future extension ?
|
val ProbeAck = UInt(4) // .
|
||||||
val Grant = UInt(2) // .
|
val ProbeAckData = UInt(5) // .
|
||||||
val GrantData = UInt(3) // .
|
val Release = UInt(6) // .
|
||||||
val ReleaseAck = UInt(4) // .
|
val ReleaseData = UInt(7) // .
|
||||||
|
val Grant = UInt(4) // .
|
||||||
|
val GrantData = UInt(5) // .
|
||||||
|
val ReleaseAck = UInt(6) // .
|
||||||
val GrantAck = UInt(0) // .
|
val GrantAck = UInt(0) // .
|
||||||
|
|
||||||
def isA(x: UInt) = x <= Acquire
|
def isA(x: UInt) = x <= Acquire
|
||||||
def isB(x: UInt) = x <= Probe
|
def isB(x: UInt) = x <= Probe
|
||||||
def isC(x: UInt) = x <= ReleaseData
|
def isC(x: UInt) = x <= ReleaseData
|
||||||
def isD(x: UInt) = x <= GrantData
|
def isD(x: UInt) = x <= ReleaseAck
|
||||||
}
|
}
|
||||||
|
|
||||||
object TLPermissions
|
object TLPermissions
|
||||||
@ -122,9 +122,6 @@ trait HasTLData extends HasTLOpcode
|
|||||||
def wmask(x: Bogus = Bogus()): UInt
|
def wmask(x: Bogus = Bogus()): UInt
|
||||||
}
|
}
|
||||||
|
|
||||||
// !!! trait HasTLSource|Sink|Address
|
|
||||||
// !!! trait param: from and to perms
|
|
||||||
|
|
||||||
class TLBundleA(params: TLBundleParameters)
|
class TLBundleA(params: TLBundleParameters)
|
||||||
extends TLBundleBase(params)
|
extends TLBundleBase(params)
|
||||||
with HasTLData
|
with HasTLData
|
||||||
@ -177,12 +174,13 @@ class TLBundleC(params: TLBundleParameters)
|
|||||||
val source = UInt(width = params.sourceBits) // from
|
val source = UInt(width = params.sourceBits) // from
|
||||||
val address = UInt(width = params.addressBits) // to
|
val address = UInt(width = params.addressBits) // to
|
||||||
val data = UInt(width = params.dataBits)
|
val data = UInt(width = params.dataBits)
|
||||||
|
val error = Bool() // AccessAck[Data]
|
||||||
|
|
||||||
def hasData(x: Bogus = Bogus()) = opcode(0)
|
def hasData(x: Bogus = Bogus()) = opcode(0)
|
||||||
// opcode === TLMessages.AccessAckData ||
|
// opcode === TLMessages.AccessAckData ||
|
||||||
// opcode === TLMessages.ProbeAckData ||
|
// opcode === TLMessages.ProbeAckData ||
|
||||||
// opcode === TLMessages.ReleaseData
|
// opcode === TLMessages.ReleaseData
|
||||||
def hasFollowUp(x: Bogus = Bogus()) = opcode(2) && !opcode(1)
|
def hasFollowUp(x: Bogus = Bogus()) = opcode(2) && opcode(1)
|
||||||
// opcode === TLMessages.Release ||
|
// opcode === TLMessages.Release ||
|
||||||
// opcode === TLMessages.ReleaseData
|
// opcode === TLMessages.ReleaseData
|
||||||
def size(x: Bogus = Bogus()) = size
|
def size(x: Bogus = Bogus()) = size
|
||||||
@ -200,11 +198,12 @@ class TLBundleD(params: TLBundleParameters)
|
|||||||
val source = UInt(width = params.sourceBits) // to
|
val source = UInt(width = params.sourceBits) // to
|
||||||
val sink = UInt(width = params.sinkBits) // from
|
val sink = UInt(width = params.sinkBits) // from
|
||||||
val data = UInt(width = params.dataBits)
|
val data = UInt(width = params.dataBits)
|
||||||
|
val error = Bool() // AccessAck[Data], Grant[Data]
|
||||||
|
|
||||||
def hasData(x: Bogus = Bogus()) = opcode(0)
|
def hasData(x: Bogus = Bogus()) = opcode(0)
|
||||||
// opcode === TLMessages.AccessAckData ||
|
// opcode === TLMessages.AccessAckData ||
|
||||||
// opcode === TLMessages.GrantData
|
// opcode === TLMessages.GrantData
|
||||||
def hasFollowUp(x: Bogus = Bogus()) = !opcode(2) && opcode(1)
|
def hasFollowUp(x: Bogus = Bogus()) = opcode(2) && !opcode(1)
|
||||||
// opcode === TLMessages.Grant ||
|
// opcode === TLMessages.Grant ||
|
||||||
// opcode === TLMessages.GrantData
|
// opcode === TLMessages.GrantData
|
||||||
def size(x: Bogus = Bogus()) = size
|
def size(x: Bogus = Bogus()) = size
|
||||||
|
@ -183,19 +183,19 @@ object TLMonitor
|
|||||||
assert (bundle.param === UInt(0), "'C' channel AccessAck carries invalid param")(sourceInfo)
|
assert (bundle.param === UInt(0), "'C' channel AccessAck carries invalid param")(sourceInfo)
|
||||||
}
|
}
|
||||||
|
|
||||||
when (bundle.opcode === TLMessages.AccessAckError) {
|
|
||||||
assert (address_ok, "'C' channel AccessAckError carries unmanaged address")(sourceInfo)
|
|
||||||
// source is ignored
|
|
||||||
assert (is_aligned, "'C' channel AccessAckError address not aligned to size")(sourceInfo)
|
|
||||||
assert (bundle.param === UInt(0), "'C' channel AccessAckError carries invalid param")(sourceInfo)
|
|
||||||
}
|
|
||||||
|
|
||||||
when (bundle.opcode === TLMessages.AccessAckData) {
|
when (bundle.opcode === TLMessages.AccessAckData) {
|
||||||
assert (address_ok, "'C' channel AccessAckData carries unmanaged address")(sourceInfo)
|
assert (address_ok, "'C' channel AccessAckData carries unmanaged address")(sourceInfo)
|
||||||
// source is ignored
|
// source is ignored
|
||||||
assert (is_aligned, "'C' channel AccessAckData address not aligned to size")(sourceInfo)
|
assert (is_aligned, "'C' channel AccessAckData address not aligned to size")(sourceInfo)
|
||||||
assert (bundle.param === UInt(0), "'C' channel AccessAckData carries invalid param")(sourceInfo)
|
assert (bundle.param === UInt(0), "'C' channel AccessAckData carries invalid param")(sourceInfo)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
when (bundle.opcode === TLMessages.HintAck) {
|
||||||
|
assert (address_ok, "'C' channel HintAck carries unmanaged address")(sourceInfo)
|
||||||
|
// source is ignored
|
||||||
|
assert (is_aligned, "'C' channel HintAck address not aligned to size")(sourceInfo)
|
||||||
|
assert (bundle.param === UInt(0), "'C' channel HintAck carries invalid param")(sourceInfo)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
def legalizeD(bundle: TLBundleD, edge: TLEdgeIn, sourceInfo: SourceInfo) = {
|
def legalizeD(bundle: TLBundleD, edge: TLEdgeIn, sourceInfo: SourceInfo) = {
|
||||||
@ -232,19 +232,19 @@ object TLMonitor
|
|||||||
assert (bundle.param === UInt(0), "'D' channel AccessAck carries invalid param")(sourceInfo)
|
assert (bundle.param === UInt(0), "'D' channel AccessAck carries invalid param")(sourceInfo)
|
||||||
}
|
}
|
||||||
|
|
||||||
when (bundle.opcode === TLMessages.AccessAckError) {
|
|
||||||
assert (source_ok, "'D' channel AccessAckError carries invalid source ID")(sourceInfo)
|
|
||||||
// sink is ignored
|
|
||||||
// size is ignored
|
|
||||||
assert (bundle.param === UInt(0), "'D' channel AccessAckError carries invalid param")(sourceInfo)
|
|
||||||
}
|
|
||||||
|
|
||||||
when (bundle.opcode === TLMessages.AccessAckData) {
|
when (bundle.opcode === TLMessages.AccessAckData) {
|
||||||
assert (source_ok, "'D' channel AccessAckData carries invalid source ID")(sourceInfo)
|
assert (source_ok, "'D' channel AccessAckData carries invalid source ID")(sourceInfo)
|
||||||
// sink is ignored
|
// sink is ignored
|
||||||
// size is ignored
|
// size is ignored
|
||||||
assert (bundle.param === UInt(0), "'D' channel AccessAckData carries invalid param")(sourceInfo)
|
assert (bundle.param === UInt(0), "'D' channel AccessAckData carries invalid param")(sourceInfo)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
when (bundle.opcode === TLMessages.HintAck) {
|
||||||
|
assert (source_ok, "'D' channel HintAck carries invalid source ID")(sourceInfo)
|
||||||
|
// sink is ignored
|
||||||
|
// size is ignored
|
||||||
|
assert (bundle.param === UInt(0), "'D' channel HintAck carries invalid param")(sourceInfo)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
def legalizeE(bundle: TLBundleE, edge: TLEdgeOut, sourceInfo: SourceInfo) = {
|
def legalizeE(bundle: TLBundleE, edge: TLEdgeOut, sourceInfo: SourceInfo) = {
|
||||||
|
@ -12,7 +12,7 @@ class TLEdge(
|
|||||||
def isAligned(address: UInt, lgSize: UInt) =
|
def isAligned(address: UInt, lgSize: UInt) =
|
||||||
if (maxLgSize == 0) Bool(true) else {
|
if (maxLgSize == 0) Bool(true) else {
|
||||||
val mask = Vec.tabulate(maxLgSize) { UInt(_) < lgSize }
|
val mask = Vec.tabulate(maxLgSize) { UInt(_) < lgSize }
|
||||||
(address & mask.toBits.asUInt) === UInt(0)
|
(address & Cat(mask.reverse)) === UInt(0)
|
||||||
}
|
}
|
||||||
|
|
||||||
// This gets used everywhere, so make the smallest circuit possible ...
|
// This gets used everywhere, so make the smallest circuit possible ...
|
||||||
@ -34,7 +34,7 @@ class TLEdge(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Vec(helper(lgBytes).map(_._1)).toBits.asUInt
|
Cat(helper(lgBytes).map(_._1).reverse)
|
||||||
}
|
}
|
||||||
|
|
||||||
def numBeats(bundle: HasTLOpcode) = {
|
def numBeats(bundle: HasTLOpcode) = {
|
||||||
@ -43,7 +43,7 @@ class TLEdge(
|
|||||||
val cutoff = log2Ceil(manager.beatBytes)
|
val cutoff = log2Ceil(manager.beatBytes)
|
||||||
val small = size <= UInt(cutoff)
|
val small = size <= UInt(cutoff)
|
||||||
val decode = Vec.tabulate (1+maxLgSize-cutoff) { i => UInt(i + cutoff) === size }
|
val decode = Vec.tabulate (1+maxLgSize-cutoff) { i => UInt(i + cutoff) === size }
|
||||||
Mux(!hasData || small, UInt(1), decode.toBits.asUInt)
|
Mux(!hasData || small, UInt(1), Cat(decode.reverse))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -77,6 +77,7 @@ class TLEdgeOut(
|
|||||||
c.source := fromSource
|
c.source := fromSource
|
||||||
c.address := toAddress
|
c.address := toAddress
|
||||||
c.data := UInt(0)
|
c.data := UInt(0)
|
||||||
|
c.error := Bool(false)
|
||||||
(legal, c)
|
(legal, c)
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -90,6 +91,7 @@ class TLEdgeOut(
|
|||||||
c.source := fromSource
|
c.source := fromSource
|
||||||
c.address := toAddress
|
c.address := toAddress
|
||||||
c.data := data
|
c.data := data
|
||||||
|
c.error := Bool(false)
|
||||||
(legal, c)
|
(legal, c)
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -101,6 +103,7 @@ class TLEdgeOut(
|
|||||||
c.source := UInt(0)
|
c.source := UInt(0)
|
||||||
c.address := toAddress
|
c.address := toAddress
|
||||||
c.data := UInt(0)
|
c.data := UInt(0)
|
||||||
|
c.error := Bool(false)
|
||||||
c
|
c
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -112,6 +115,7 @@ class TLEdgeOut(
|
|||||||
c.source := UInt(0)
|
c.source := UInt(0)
|
||||||
c.address := toAddress
|
c.address := toAddress
|
||||||
c.data := data
|
c.data := data
|
||||||
|
c.error := Bool(false)
|
||||||
c
|
c
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -206,7 +210,8 @@ class TLEdgeOut(
|
|||||||
(legal, a)
|
(legal, a)
|
||||||
}
|
}
|
||||||
|
|
||||||
def AccessAck(toAddress: UInt, lgSize: UInt) = {
|
def AccessAck(toAddress: UInt, lgSize: UInt): TLBundleC = AccessAck(toAddress, lgSize, Bool(false))
|
||||||
|
def AccessAck(toAddress: UInt, lgSize: UInt, error: Bool) = {
|
||||||
val c = Wire(new TLBundleC(bundle))
|
val c = Wire(new TLBundleC(bundle))
|
||||||
c.opcode := TLMessages.AccessAck
|
c.opcode := TLMessages.AccessAck
|
||||||
c.param := UInt(0)
|
c.param := UInt(0)
|
||||||
@ -214,21 +219,12 @@ class TLEdgeOut(
|
|||||||
c.source := UInt(0)
|
c.source := UInt(0)
|
||||||
c.address := toAddress
|
c.address := toAddress
|
||||||
c.data := UInt(0)
|
c.data := UInt(0)
|
||||||
|
c.error := error
|
||||||
c
|
c
|
||||||
}
|
}
|
||||||
|
|
||||||
def AccessAckError(toAddress: UInt, lgSize: UInt) = {
|
def AccessAck(toAddress: UInt, lgSize: UInt, data: UInt): TLBundleC = AccessAck(toAddress, lgSize, data, Bool(false))
|
||||||
val c = Wire(new TLBundleC(bundle))
|
def AccessAck(toAddress: UInt, lgSize: UInt, data: UInt, error: Bool) = {
|
||||||
c.opcode := TLMessages.AccessAckError
|
|
||||||
c.param := UInt(0)
|
|
||||||
c.size := lgSize
|
|
||||||
c.source := UInt(0)
|
|
||||||
c.address := toAddress
|
|
||||||
c.data := UInt(0)
|
|
||||||
c
|
|
||||||
}
|
|
||||||
|
|
||||||
def AccessAck(toAddress: UInt, lgSize: UInt, data: UInt) = {
|
|
||||||
val c = Wire(new TLBundleC(bundle))
|
val c = Wire(new TLBundleC(bundle))
|
||||||
c.opcode := TLMessages.AccessAckData
|
c.opcode := TLMessages.AccessAckData
|
||||||
c.param := UInt(0)
|
c.param := UInt(0)
|
||||||
@ -236,6 +232,19 @@ class TLEdgeOut(
|
|||||||
c.source := UInt(0)
|
c.source := UInt(0)
|
||||||
c.address := toAddress
|
c.address := toAddress
|
||||||
c.data := data
|
c.data := data
|
||||||
|
c.error := error
|
||||||
|
c
|
||||||
|
}
|
||||||
|
|
||||||
|
def HintAck(toAddress: UInt, lgSize: UInt) = {
|
||||||
|
val c = Wire(new TLBundleC(bundle))
|
||||||
|
c.opcode := TLMessages.HintAck
|
||||||
|
c.param := UInt(0)
|
||||||
|
c.size := lgSize
|
||||||
|
c.source := UInt(0)
|
||||||
|
c.address := toAddress
|
||||||
|
c.data := UInt(0)
|
||||||
|
c.error := Bool(false)
|
||||||
c
|
c
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -260,7 +269,8 @@ class TLEdgeIn(
|
|||||||
(legal, b)
|
(legal, b)
|
||||||
}
|
}
|
||||||
|
|
||||||
def Grant(fromSink: UInt, toSource: UInt, lgSize: UInt, capPermissions: UInt) = {
|
def Grant(fromSink: UInt, toSource: UInt, lgSize: UInt, capPermissions: UInt): TLBundleD = Grant(fromSink, toSource, lgSize, capPermissions, Bool(false))
|
||||||
|
def Grant(fromSink: UInt, toSource: UInt, lgSize: UInt, capPermissions: UInt, error: Bool) = {
|
||||||
val d = Wire(new TLBundleD(bundle))
|
val d = Wire(new TLBundleD(bundle))
|
||||||
d.opcode := TLMessages.Grant
|
d.opcode := TLMessages.Grant
|
||||||
d.param := capPermissions
|
d.param := capPermissions
|
||||||
@ -268,10 +278,12 @@ class TLEdgeIn(
|
|||||||
d.source := toSource
|
d.source := toSource
|
||||||
d.sink := fromSink
|
d.sink := fromSink
|
||||||
d.data := UInt(0)
|
d.data := UInt(0)
|
||||||
|
d.error := error
|
||||||
d
|
d
|
||||||
}
|
}
|
||||||
|
|
||||||
def GrantData(fromSink: UInt, toSource: UInt, lgSize: UInt, capPermissions: UInt, data: UInt) = {
|
def Grant(fromSink: UInt, toSource: UInt, lgSize: UInt, capPermissions: UInt, data: UInt): TLBundleD = Grant(fromSink, toSource, lgSize, capPermissions, data, Bool(false))
|
||||||
|
def Grant(fromSink: UInt, toSource: UInt, lgSize: UInt, capPermissions: UInt, data: UInt, error: Bool) = {
|
||||||
val d = Wire(new TLBundleD(bundle))
|
val d = Wire(new TLBundleD(bundle))
|
||||||
d.opcode := TLMessages.GrantData
|
d.opcode := TLMessages.GrantData
|
||||||
d.param := capPermissions
|
d.param := capPermissions
|
||||||
@ -279,6 +291,7 @@ class TLEdgeIn(
|
|||||||
d.source := toSource
|
d.source := toSource
|
||||||
d.sink := fromSink
|
d.sink := fromSink
|
||||||
d.data := data
|
d.data := data
|
||||||
|
d.error := error
|
||||||
d
|
d
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -290,6 +303,7 @@ class TLEdgeIn(
|
|||||||
d.source := toSource
|
d.source := toSource
|
||||||
d.sink := UInt(0)
|
d.sink := UInt(0)
|
||||||
d.data := UInt(0)
|
d.data := UInt(0)
|
||||||
|
d.error := Bool(false)
|
||||||
d
|
d
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -378,7 +392,8 @@ class TLEdgeIn(
|
|||||||
(legal, b)
|
(legal, b)
|
||||||
}
|
}
|
||||||
|
|
||||||
def AccessAck(toSource: UInt, lgSize: UInt) = {
|
def AccessAck(toSource: UInt, lgSize: UInt): TLBundleD = AccessAck(toSource, lgSize, Bool(false))
|
||||||
|
def AccessAck(toSource: UInt, lgSize: UInt, error: Bool) = {
|
||||||
val d = Wire(new TLBundleD(bundle))
|
val d = Wire(new TLBundleD(bundle))
|
||||||
d.opcode := TLMessages.AccessAck
|
d.opcode := TLMessages.AccessAck
|
||||||
d.param := UInt(0)
|
d.param := UInt(0)
|
||||||
@ -386,21 +401,12 @@ class TLEdgeIn(
|
|||||||
d.source := toSource
|
d.source := toSource
|
||||||
d.sink := UInt(0)
|
d.sink := UInt(0)
|
||||||
d.data := UInt(0)
|
d.data := UInt(0)
|
||||||
|
d.error := error
|
||||||
d
|
d
|
||||||
}
|
}
|
||||||
|
|
||||||
def AccessAckError(toSource: UInt, lgSize: UInt) = {
|
def AccessAck(toSource: UInt, lgSize: UInt, data: UInt): TLBundleD = AccessAck(toSource, lgSize, data, Bool(false))
|
||||||
val d = Wire(new TLBundleD(bundle))
|
def AccessAck(toSource: UInt, lgSize: UInt, data: UInt, error: Bool) = {
|
||||||
d.opcode := TLMessages.AccessAckError
|
|
||||||
d.param := UInt(0)
|
|
||||||
d.size := lgSize
|
|
||||||
d.source := toSource
|
|
||||||
d.sink := UInt(0)
|
|
||||||
d.data := UInt(0)
|
|
||||||
d
|
|
||||||
}
|
|
||||||
|
|
||||||
def AccessAck(toSource: UInt, lgSize: UInt, data: UInt) = {
|
|
||||||
val d = Wire(new TLBundleD(bundle))
|
val d = Wire(new TLBundleD(bundle))
|
||||||
d.opcode := TLMessages.AccessAckData
|
d.opcode := TLMessages.AccessAckData
|
||||||
d.param := UInt(0)
|
d.param := UInt(0)
|
||||||
@ -408,6 +414,19 @@ class TLEdgeIn(
|
|||||||
d.source := toSource
|
d.source := toSource
|
||||||
d.sink := UInt(0)
|
d.sink := UInt(0)
|
||||||
d.data := data
|
d.data := data
|
||||||
|
d.error := error
|
||||||
|
d
|
||||||
|
}
|
||||||
|
|
||||||
|
def HintAck(toSource: UInt, lgSize: UInt) = {
|
||||||
|
val d = Wire(new TLBundleD(bundle))
|
||||||
|
d.opcode := TLMessages.HintAck
|
||||||
|
d.param := UInt(0)
|
||||||
|
d.size := lgSize
|
||||||
|
d.source := toSource
|
||||||
|
d.sink := UInt(0)
|
||||||
|
d.data := UInt(0)
|
||||||
|
d.error := Bool(false)
|
||||||
d
|
d
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user