2012-09-27 21:59:45 +02:00
|
|
|
package uncore
|
2012-02-15 00:51:32 +01:00
|
|
|
import Chisel._
|
|
|
|
|
2013-05-22 02:19:07 +02:00
|
|
|
abstract trait CoherenceAgentRole
|
|
|
|
abstract trait ClientCoherenceAgent extends CoherenceAgentRole
|
|
|
|
abstract trait MasterCoherenceAgent extends CoherenceAgentRole
|
2012-12-13 20:39:14 +01:00
|
|
|
|
2012-04-10 09:09:58 +02:00
|
|
|
abstract class CoherencePolicy {
|
2013-08-02 23:55:06 +02:00
|
|
|
def nClientStates: Int
|
|
|
|
def nMasterStates: Int
|
|
|
|
def nAcquireTypes: Int
|
|
|
|
def nProbeTypes: Int
|
|
|
|
def nReleaseTypes: Int
|
|
|
|
def nGrantTypes: Int
|
2013-08-12 19:36:44 +02:00
|
|
|
def clientStateWidth = log2Up(nClientStates)
|
|
|
|
def masterStateWidth = log2Up(nMasterStates)
|
|
|
|
def acquireTypeWidth = log2Up(nAcquireTypes)
|
|
|
|
def probeTypeWidth = log2Up(nProbeTypes)
|
|
|
|
def releaseTypeWidth = log2Up(nReleaseTypes)
|
|
|
|
def grantTypeWidth = log2Up(nGrantTypes)
|
|
|
|
|
|
|
|
def isHit (cmd: UInt, state: UInt): Bool
|
|
|
|
def isValid (state: UInt): Bool
|
|
|
|
|
|
|
|
def needsTransactionOnSecondaryMiss(cmd: UInt, outstanding: Acquire): Bool
|
|
|
|
def needsTransactionOnCacheControl(cmd: UInt, state: UInt): Bool
|
|
|
|
def needsWriteback (state: UInt): Bool
|
|
|
|
|
|
|
|
def newStateOnHit(cmd: UInt, state: UInt): UInt
|
|
|
|
def newStateOnCacheControl(cmd: UInt): UInt
|
|
|
|
def newStateOnWriteback(): UInt
|
|
|
|
def newStateOnFlush(): UInt
|
|
|
|
def newStateOnGrant(incoming: Grant, outstanding: Acquire): UInt
|
|
|
|
def newStateOnProbe(incoming: Probe, state: UInt): Bits
|
|
|
|
|
|
|
|
def getAcquireTypeOnPrimaryMiss(cmd: UInt, state: UInt): UInt
|
|
|
|
def getAcquireTypeOnSecondaryMiss(cmd: UInt, state: UInt, outstanding: Acquire): UInt
|
|
|
|
def getProbeType(a_type: UInt, global_state: UInt): UInt
|
|
|
|
def getReleaseTypeOnCacheControl(cmd: UInt): Bits
|
2013-03-01 03:13:41 +01:00
|
|
|
def getReleaseTypeOnVoluntaryWriteback(): Bits
|
2013-08-12 19:36:44 +02:00
|
|
|
def getReleaseTypeOnProbe(incoming: Probe, state: UInt): Bits
|
|
|
|
def getGrantType(a_type: UInt, count: UInt): Bits
|
|
|
|
def getGrantType(rel: Release, count: UInt): Bits
|
2012-04-05 00:51:33 +02:00
|
|
|
|
2013-03-20 22:10:16 +01:00
|
|
|
def messageHasData (rel: SourcedMessage): Bool
|
2013-01-22 02:17:26 +01:00
|
|
|
def messageUpdatesDataArray (reply: Grant): Bool
|
|
|
|
def messageIsUncached(acq: Acquire): Bool
|
2012-04-05 00:51:33 +02:00
|
|
|
|
|
|
|
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool
|
2013-01-29 01:39:45 +01:00
|
|
|
def isVoluntary(rel: Release): Bool
|
2013-03-01 03:13:41 +01:00
|
|
|
def isVoluntary(gnt: Grant): Bool
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsOuterRead(a_type: UInt, global_state: UInt): Bool
|
|
|
|
def needsOuterWrite(a_type: UInt, global_state: UInt): Bool
|
|
|
|
def needsAckReply(a_type: UInt, global_state: UInt): Bool
|
2013-03-01 04:49:05 +01:00
|
|
|
def needsSelfProbe(acq: Acquire): Bool
|
2013-01-29 01:39:45 +01:00
|
|
|
def requiresAck(grant: Grant): Bool
|
|
|
|
def requiresAck(release: Release): Bool
|
2013-08-12 19:36:44 +02:00
|
|
|
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool
|
2013-03-01 03:13:41 +01:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def uSIntListContains(list: List[UInt], elem: UInt): Bool = list.map(elem === _).reduceLeft(_||_)
|
2012-04-05 00:51:33 +02:00
|
|
|
}
|
2012-03-02 03:49:00 +01:00
|
|
|
|
2012-04-10 09:09:58 +02:00
|
|
|
trait UncachedTransactions {
|
2013-08-02 23:55:06 +02:00
|
|
|
def getUncachedReadAcquireType: Bits
|
|
|
|
def getUncachedWriteAcquireType: Bits
|
|
|
|
def getUncachedReadWordAcquireType: Bits
|
|
|
|
def getUncachedWriteWordAcquireType: Bits
|
|
|
|
def getUncachedAtomicAcquireType: Bits
|
2013-01-22 02:17:26 +01:00
|
|
|
def isUncachedReadTransaction(acq: Acquire): Bool
|
2012-04-10 09:09:58 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
abstract class CoherencePolicyWithUncached extends CoherencePolicy with UncachedTransactions
|
|
|
|
|
|
|
|
abstract class IncoherentPolicy extends CoherencePolicy {
|
2012-04-05 00:51:33 +02:00
|
|
|
// UNIMPLEMENTED
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnProbe(incoming: Probe, state: UInt): Bits = state
|
|
|
|
def getReleaseTypeOnProbe(incoming: Probe, state: UInt): Bits = Bits(0)
|
2012-04-05 00:51:33 +02:00
|
|
|
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool = Bool(false)
|
2013-08-12 19:36:44 +02:00
|
|
|
def getGrantType(a_type: UInt, count: UInt): Bits = Bits(0)
|
|
|
|
def getGrantType(rel: Release, count: UInt): Bits = Bits(0)
|
|
|
|
def getProbeType(a_type: UInt, global_state: UInt): UInt = UInt(0)
|
|
|
|
def needsOuterRead(a_type: UInt, global_state: UInt): Bool = Bool(false)
|
|
|
|
def needsOuterWrite(a_type: UInt, global_state: UInt): Bool = Bool(false)
|
|
|
|
def needsAckReply(a_type: UInt, global_state: UInt): Bool = Bool(false)
|
2013-03-01 04:49:05 +01:00
|
|
|
def needsSelfProbe(acq: Acquire) = Bool(false)
|
2013-01-29 01:39:45 +01:00
|
|
|
def requiresAck(grant: Grant) = Bool(true)
|
|
|
|
def requiresAck(release: Release) = Bool(false)
|
2013-08-12 19:36:44 +02:00
|
|
|
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool = Bool(false)
|
2013-03-01 03:13:41 +01:00
|
|
|
|
2012-04-05 00:51:33 +02:00
|
|
|
}
|
2012-02-15 00:51:32 +01:00
|
|
|
|
2012-04-10 09:09:58 +02:00
|
|
|
class ThreeStateIncoherence extends IncoherentPolicy {
|
2013-08-02 23:55:06 +02:00
|
|
|
def nClientStates = 3
|
|
|
|
def nMasterStates = 0
|
|
|
|
def nAcquireTypes = 3
|
|
|
|
def nProbeTypes = 0
|
|
|
|
def nReleaseTypes = 2
|
|
|
|
def nGrantTypes = 3
|
2013-08-12 19:36:44 +02:00
|
|
|
val tileInvalid :: tileClean :: tileDirty :: Nil = Enum(nClientStates){ UInt() }
|
|
|
|
val acquireReadClean :: acquireReadDirty :: acquireWriteback :: Nil = Enum(nAcquireTypes){ UInt() }
|
|
|
|
val releaseVoluntaryInvalidateData :: releaseInvalidateAck :: Nil = Enum(nReleaseTypes){ UInt() }
|
|
|
|
val grantVoluntaryAck :: grantData :: grantAck :: Nil = Enum(nGrantTypes){ UInt() }
|
2013-03-01 03:13:41 +01:00
|
|
|
val uncachedAcquireTypeList = List()
|
|
|
|
val hasDataAcquireTypeList = List(acquireWriteback)
|
|
|
|
val hasDataReleaseTypeList = List(acquireWriteback)
|
|
|
|
val hasDataGrantTypeList = List(grantData)
|
2012-02-15 00:51:32 +01:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def isHit ( cmd: UInt, state: UInt): Bool = (state === tileClean || state === tileDirty)
|
|
|
|
def isValid (state: UInt): Bool = state != tileInvalid
|
2012-04-05 00:51:33 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsTransactionOnSecondaryMiss(cmd: UInt, outstanding: Acquire) = Bool(false)
|
|
|
|
def needsTransactionOnCacheControl(cmd: UInt, state: UInt): Bool = state === tileDirty
|
|
|
|
def needsWriteback (state: UInt): Bool = state === tileDirty
|
2012-02-15 00:51:32 +01:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def newState(cmd: UInt, state: UInt): UInt = {
|
2013-04-08 04:23:44 +02:00
|
|
|
Mux(isWrite(cmd), tileDirty, Mux(isRead(cmd), Mux(state === tileDirty, tileDirty, tileClean), state))
|
2012-02-15 00:51:32 +01:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnHit(cmd: UInt, state: UInt): UInt = newState(cmd, state)
|
|
|
|
def newStateOnCacheControl(cmd: UInt) = tileInvalid //TODO
|
2012-04-05 00:51:33 +02:00
|
|
|
def newStateOnWriteback() = tileInvalid
|
|
|
|
def newStateOnFlush() = tileInvalid
|
2013-01-22 02:17:26 +01:00
|
|
|
def newStateOnGrant(incoming: Grant, outstanding: Acquire) = {
|
|
|
|
MuxLookup(incoming.g_type, tileInvalid, Array(
|
|
|
|
grantData -> Mux(outstanding.a_type === acquireReadDirty, tileDirty, tileClean),
|
|
|
|
grantAck -> tileInvalid
|
2012-04-05 00:51:33 +02:00
|
|
|
))
|
|
|
|
}
|
|
|
|
|
2013-01-29 01:39:45 +01:00
|
|
|
def isVoluntary(rel: Release) = rel.r_type === releaseVoluntaryInvalidateData
|
2013-03-01 03:13:41 +01:00
|
|
|
def isVoluntary(gnt: Grant) = gnt.g_type === grantVoluntaryAck
|
2013-01-29 01:39:45 +01:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def getAcquireTypeOnPrimaryMiss(cmd: UInt, state: UInt): UInt = {
|
2013-04-04 07:13:51 +02:00
|
|
|
Mux(isWriteIntent(cmd), acquireReadDirty, acquireReadClean)
|
2012-02-15 00:51:32 +01:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def getAcquireTypeOnSecondaryMiss(cmd: UInt, state: UInt, outstanding: Acquire): UInt = {
|
2013-04-08 04:23:44 +02:00
|
|
|
Mux(isWriteIntent(cmd), acquireReadDirty, outstanding.a_type)
|
2012-03-07 10:26:35 +01:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def getReleaseTypeOnCacheControl(cmd: UInt): Bits = releaseVoluntaryInvalidateData // TODO
|
2013-03-01 03:13:41 +01:00
|
|
|
def getReleaseTypeOnVoluntaryWriteback(): Bits = releaseVoluntaryInvalidateData
|
2012-04-05 00:51:33 +02:00
|
|
|
|
2013-03-20 22:10:16 +01:00
|
|
|
def messageHasData( msg: SourcedMessage ) = msg match {
|
2013-08-12 19:36:44 +02:00
|
|
|
case acq: Acquire => uSIntListContains(hasDataAcquireTypeList, acq.a_type)
|
|
|
|
case grant: Grant => uSIntListContains(hasDataGrantTypeList, grant.g_type)
|
2013-03-20 22:10:16 +01:00
|
|
|
case rel: Release => Bool(false)
|
|
|
|
case _ => Bool(false)
|
|
|
|
}
|
2013-01-22 02:17:26 +01:00
|
|
|
def messageUpdatesDataArray (reply: Grant) = (reply.g_type === grantData)
|
2013-08-12 19:36:44 +02:00
|
|
|
def messageIsUncached(acq: Acquire): Bool = uSIntListContains(uncachedAcquireTypeList, acq.a_type)
|
2012-04-10 09:09:58 +02:00
|
|
|
}
|
|
|
|
|
2012-04-12 02:56:59 +02:00
|
|
|
class MICoherence extends CoherencePolicyWithUncached {
|
2013-08-02 23:55:06 +02:00
|
|
|
def nClientStates = 2
|
|
|
|
def nMasterStates = 2
|
|
|
|
def nAcquireTypes = 6
|
|
|
|
def nProbeTypes = 2
|
|
|
|
def nReleaseTypes = 5
|
|
|
|
def nGrantTypes = 7
|
2012-04-10 09:09:58 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
val tileInvalid :: tileValid :: Nil = Enum(nClientStates){ UInt() }
|
|
|
|
val globalInvalid :: globalValid :: Nil = Enum(nMasterStates){ UInt() }
|
2013-08-02 23:55:06 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
val acquireReadExclusive :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: Nil = Enum(nAcquireTypes){ UInt() }
|
|
|
|
val probeInvalidate :: probeCopy :: Nil = Enum(nProbeTypes){ UInt() }
|
|
|
|
val releaseVoluntaryInvalidateData :: releaseInvalidateData :: releaseCopyData :: releaseInvalidateAck :: releaseCopyAck :: Nil = Enum(nReleaseTypes){ UInt() }
|
|
|
|
val grantVoluntaryAck :: grantReadExclusive :: grantReadUncached :: grantWriteUncached :: grantReadWordUncached :: grantWriteWordUncached :: grantAtomicUncached :: Nil = Enum(nGrantTypes){ UInt() }
|
2012-04-10 09:09:58 +02:00
|
|
|
|
2013-03-01 03:13:41 +01:00
|
|
|
val uncachedAcquireTypeList = List(acquireReadUncached, acquireWriteUncached, acquireReadWordUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
|
|
|
val hasDataAcquireTypeList = List(acquireWriteUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
|
|
|
val hasDataReleaseTypeList = List(releaseVoluntaryInvalidateData, releaseInvalidateData, releaseCopyData)
|
|
|
|
val hasDataGrantTypeList = List(grantReadExclusive, grantReadUncached, grantReadWordUncached, grantAtomicUncached)
|
2012-04-10 09:09:58 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def isHit (cmd: UInt, state: UInt): Bool = state != tileInvalid
|
|
|
|
def isValid (state: UInt): Bool = state != tileInvalid
|
2012-04-10 09:09:58 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsTransactionOnSecondaryMiss(cmd: UInt, outstanding: Acquire): Bool = (outstanding.a_type != acquireReadExclusive)
|
|
|
|
def needsTransactionOnCacheControl(cmd: UInt, state: UInt): Bool = {
|
2012-04-10 09:09:58 +02:00
|
|
|
MuxLookup(cmd, (state === tileValid), Array(
|
|
|
|
M_INV -> (state === tileValid),
|
|
|
|
M_CLN -> (state === tileValid)
|
|
|
|
))
|
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsWriteback (state: UInt): Bool = {
|
2012-04-10 09:09:58 +02:00
|
|
|
needsTransactionOnCacheControl(M_INV, state)
|
|
|
|
}
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnHit(cmd: UInt, state: UInt): UInt = state
|
|
|
|
def newStateOnCacheControl(cmd: UInt) = {
|
2012-04-10 09:09:58 +02:00
|
|
|
MuxLookup(cmd, tileInvalid, Array(
|
|
|
|
M_INV -> tileInvalid,
|
|
|
|
M_CLN -> tileValid
|
|
|
|
))
|
|
|
|
}
|
|
|
|
def newStateOnWriteback() = newStateOnCacheControl(M_INV)
|
|
|
|
def newStateOnFlush() = newStateOnCacheControl(M_INV)
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnGrant(incoming: Grant, outstanding: Acquire): UInt = {
|
2013-01-22 02:17:26 +01:00
|
|
|
MuxLookup(incoming.g_type, tileInvalid, Array(
|
|
|
|
grantReadExclusive -> tileValid,
|
|
|
|
grantReadUncached -> tileInvalid,
|
|
|
|
grantWriteUncached -> tileInvalid,
|
|
|
|
grantReadWordUncached -> tileInvalid,
|
|
|
|
grantWriteWordUncached -> tileInvalid,
|
|
|
|
grantAtomicUncached -> tileInvalid
|
2012-04-10 09:09:58 +02:00
|
|
|
))
|
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnProbe(incoming: Probe, state: UInt): Bits = {
|
2012-04-10 09:09:58 +02:00
|
|
|
MuxLookup(incoming.p_type, state, Array(
|
2013-01-22 02:17:26 +01:00
|
|
|
probeInvalidate -> tileInvalid,
|
|
|
|
probeCopy -> state
|
2012-04-10 09:09:58 +02:00
|
|
|
))
|
|
|
|
}
|
|
|
|
|
2013-08-02 23:55:06 +02:00
|
|
|
def getUncachedReadAcquireType = acquireReadUncached
|
|
|
|
def getUncachedWriteAcquireType = acquireWriteUncached
|
|
|
|
def getUncachedReadWordAcquireType = acquireReadWordUncached
|
|
|
|
def getUncachedWriteWordAcquireType = acquireWriteWordUncached
|
|
|
|
def getUncachedAtomicAcquireType = acquireAtomicUncached
|
2013-01-22 02:17:26 +01:00
|
|
|
def isUncachedReadTransaction(acq: Acquire) = acq.a_type === acquireReadUncached
|
2013-01-29 01:39:45 +01:00
|
|
|
def isVoluntary(rel: Release) = rel.r_type === releaseVoluntaryInvalidateData
|
2013-03-01 03:13:41 +01:00
|
|
|
def isVoluntary(gnt: Grant) = gnt.g_type === grantVoluntaryAck
|
2012-10-02 01:05:37 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def getAcquireTypeOnPrimaryMiss(cmd: UInt, state: UInt): UInt = acquireReadExclusive
|
|
|
|
def getAcquireTypeOnSecondaryMiss(cmd: UInt, state: UInt, outstanding: Acquire): UInt = acquireReadExclusive
|
|
|
|
def getReleaseTypeOnCacheControl(cmd: UInt): Bits = releaseVoluntaryInvalidateData // TODO
|
2013-03-01 03:13:41 +01:00
|
|
|
def getReleaseTypeOnVoluntaryWriteback(): Bits = getReleaseTypeOnCacheControl(M_INV)
|
2013-08-12 19:36:44 +02:00
|
|
|
def getReleaseTypeOnProbe(incoming: Probe, state: UInt): Bits = {
|
2013-01-22 02:17:26 +01:00
|
|
|
val with_data = MuxLookup(incoming.p_type, releaseInvalidateData, Array(
|
|
|
|
probeInvalidate -> releaseInvalidateData,
|
|
|
|
probeCopy -> releaseCopyData
|
2012-04-10 09:09:58 +02:00
|
|
|
))
|
2013-01-22 02:17:26 +01:00
|
|
|
val without_data = MuxLookup(incoming.p_type, releaseInvalidateAck, Array(
|
|
|
|
probeInvalidate -> releaseInvalidateAck,
|
|
|
|
probeCopy -> releaseCopyAck
|
2012-04-10 09:09:58 +02:00
|
|
|
))
|
2013-08-02 23:55:06 +02:00
|
|
|
Mux(needsWriteback(state), with_data, without_data)
|
2012-04-10 09:09:58 +02:00
|
|
|
}
|
|
|
|
|
2013-03-20 22:10:16 +01:00
|
|
|
def messageHasData(msg: SourcedMessage) = msg match {
|
2013-08-12 19:36:44 +02:00
|
|
|
case acq: Acquire => uSIntListContains(hasDataAcquireTypeList, acq.a_type)
|
|
|
|
case grant: Grant => uSIntListContains(hasDataGrantTypeList, grant.g_type)
|
|
|
|
case rel: Release => uSIntListContains(hasDataReleaseTypeList, rel.r_type)
|
2013-03-20 22:10:16 +01:00
|
|
|
case _ => Bool(false)
|
|
|
|
}
|
2013-01-22 02:17:26 +01:00
|
|
|
def messageUpdatesDataArray (reply: Grant): Bool = {
|
|
|
|
(reply.g_type === grantReadExclusive)
|
2012-04-10 09:09:58 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def messageIsUncached(acq: Acquire): Bool = uSIntListContains(uncachedAcquireTypeList, acq.a_type)
|
2012-04-10 09:09:58 +02:00
|
|
|
|
|
|
|
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool = (addr1 === addr2)
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def getGrantType(a_type: UInt, count: UInt): Bits = {
|
2013-01-22 02:17:26 +01:00
|
|
|
MuxLookup(a_type, grantReadUncached, Array(
|
|
|
|
acquireReadExclusive -> grantReadExclusive,
|
|
|
|
acquireReadUncached -> grantReadUncached,
|
|
|
|
acquireWriteUncached -> grantWriteUncached,
|
|
|
|
acquireReadWordUncached -> grantReadWordUncached,
|
|
|
|
acquireWriteWordUncached -> grantWriteWordUncached,
|
|
|
|
acquireAtomicUncached -> grantAtomicUncached
|
2012-04-10 09:09:58 +02:00
|
|
|
))
|
|
|
|
}
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def getGrantType(rel: Release, count: UInt): Bits = {
|
2013-01-29 01:39:45 +01:00
|
|
|
MuxLookup(rel.r_type, grantReadUncached, Array(
|
|
|
|
releaseVoluntaryInvalidateData -> grantVoluntaryAck
|
|
|
|
))
|
|
|
|
}
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def getProbeType(a_type: UInt, global_state: UInt): UInt = {
|
2013-01-22 02:17:26 +01:00
|
|
|
MuxLookup(a_type, probeCopy, Array(
|
|
|
|
acquireReadExclusive -> probeInvalidate,
|
|
|
|
acquireReadUncached -> probeCopy,
|
|
|
|
acquireWriteUncached -> probeInvalidate,
|
|
|
|
acquireReadWordUncached -> probeCopy,
|
|
|
|
acquireWriteWordUncached -> probeInvalidate,
|
|
|
|
acquireAtomicUncached -> probeInvalidate
|
2012-04-10 09:09:58 +02:00
|
|
|
))
|
|
|
|
}
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsOuterRead(a_type: UInt, global_state: UInt): Bool = {
|
2013-01-22 02:17:26 +01:00
|
|
|
(a_type != acquireWriteUncached)
|
2012-04-10 09:09:58 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsOuterWrite(a_type: UInt, global_state: UInt): Bool = {
|
2013-01-22 02:17:26 +01:00
|
|
|
(a_type === acquireWriteUncached)
|
2012-04-10 09:09:58 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsAckReply(a_type: UInt, global_state: UInt): Bool = {
|
2013-01-22 02:17:26 +01:00
|
|
|
(a_type === acquireWriteUncached)
|
2012-04-10 09:09:58 +02:00
|
|
|
}
|
2013-04-10 22:46:31 +02:00
|
|
|
def requiresAck(grant: Grant) = grant.g_type != grantVoluntaryAck
|
2013-01-29 01:39:45 +01:00
|
|
|
def requiresAck(release: Release) = Bool(false)
|
2013-03-26 00:20:12 +01:00
|
|
|
def needsSelfProbe(acq: Acquire) = Bool(false)
|
2013-08-12 19:36:44 +02:00
|
|
|
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool = (r_type === releaseVoluntaryInvalidateData)
|
2012-04-10 09:09:58 +02:00
|
|
|
}
|
|
|
|
|
2012-04-12 02:56:59 +02:00
|
|
|
class MEICoherence extends CoherencePolicyWithUncached {
|
2013-08-02 23:55:06 +02:00
|
|
|
def nClientStates = 3
|
|
|
|
def nMasterStates = 2
|
|
|
|
def nAcquireTypes = 7
|
|
|
|
def nProbeTypes = 3
|
|
|
|
def nReleaseTypes = 7
|
|
|
|
def nGrantTypes = 8
|
2012-04-10 09:09:58 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
val tileInvalid :: tileExclusiveClean :: tileExclusiveDirty :: Nil = Enum(nClientStates){ UInt() }
|
|
|
|
val globalInvalid :: globalExclusiveClean :: Nil = Enum(nMasterStates){ UInt() }
|
2012-04-10 09:09:58 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
val acquireReadExclusiveClean :: acquireReadExclusiveDirty :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: Nil = Enum(nAcquireTypes){ UInt() }
|
|
|
|
val probeInvalidate :: probeDowngrade :: probeCopy :: Nil = Enum(nProbeTypes){ UInt() }
|
|
|
|
val releaseVoluntaryInvalidateData :: releaseInvalidateData :: releaseDowngradeData :: releaseCopyData :: releaseInvalidateAck :: releaseDowngradeAck :: releaseCopyAck :: Nil = Enum(nReleaseTypes){ UInt() }
|
|
|
|
val grantVoluntaryAck :: grantReadExclusive :: grantReadUncached :: grantWriteUncached :: grantReadExclusiveAck :: grantReadWordUncached :: grantWriteWordUncached :: grantAtomicUncached :: Nil = Enum(nGrantTypes){ UInt() }
|
2013-03-01 03:13:41 +01:00
|
|
|
|
|
|
|
val uncachedAcquireTypeList = List(acquireReadUncached, acquireWriteUncached, acquireReadWordUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
|
|
|
val hasDataAcquireTypeList = List(acquireWriteUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
|
|
|
val hasDataReleaseTypeList = List(releaseVoluntaryInvalidateData, releaseInvalidateData, releaseDowngradeData, releaseCopyData)
|
|
|
|
val hasDataGrantTypeList = List(grantReadExclusive, grantReadUncached, grantReadWordUncached, grantAtomicUncached)
|
2012-04-10 09:09:58 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def isHit (cmd: UInt, state: UInt): Bool = state != tileInvalid
|
|
|
|
def isValid (state: UInt): Bool = state != tileInvalid
|
2012-04-10 09:09:58 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsTransactionOnSecondaryMiss(cmd: UInt, outstanding: Acquire): Bool = {
|
2013-04-08 04:23:44 +02:00
|
|
|
(isRead(cmd) && messageIsUncached(outstanding)) ||
|
|
|
|
(isWriteIntent(cmd) && (outstanding.a_type != acquireReadExclusiveDirty))
|
2012-04-10 09:09:58 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsTransactionOnCacheControl(cmd: UInt, state: UInt): Bool = {
|
2012-04-10 09:09:58 +02:00
|
|
|
MuxLookup(cmd, (state === tileExclusiveDirty), Array(
|
|
|
|
M_INV -> (state === tileExclusiveDirty),
|
|
|
|
M_CLN -> (state === tileExclusiveDirty)
|
|
|
|
))
|
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsWriteback (state: UInt): Bool = {
|
2012-04-10 09:09:58 +02:00
|
|
|
needsTransactionOnCacheControl(M_INV, state)
|
|
|
|
}
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnHit(cmd: UInt, state: UInt): UInt = {
|
2013-04-08 04:23:44 +02:00
|
|
|
Mux(isWrite(cmd), tileExclusiveDirty, state)
|
2012-04-10 09:09:58 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnCacheControl(cmd: UInt) = {
|
2012-04-10 09:09:58 +02:00
|
|
|
MuxLookup(cmd, tileInvalid, Array(
|
|
|
|
M_INV -> tileInvalid,
|
|
|
|
M_CLN -> tileExclusiveClean
|
|
|
|
))
|
|
|
|
}
|
|
|
|
def newStateOnWriteback() = newStateOnCacheControl(M_INV)
|
|
|
|
def newStateOnFlush() = newStateOnCacheControl(M_INV)
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnGrant(incoming: Grant, outstanding: Acquire): UInt = {
|
2013-01-22 02:17:26 +01:00
|
|
|
MuxLookup(incoming.g_type, tileInvalid, Array(
|
|
|
|
grantReadExclusive -> Mux(outstanding.a_type === acquireReadExclusiveDirty, tileExclusiveDirty, tileExclusiveClean),
|
|
|
|
grantReadExclusiveAck -> tileExclusiveDirty,
|
|
|
|
grantReadUncached -> tileInvalid,
|
|
|
|
grantWriteUncached -> tileInvalid,
|
|
|
|
grantReadWordUncached -> tileInvalid,
|
|
|
|
grantWriteWordUncached -> tileInvalid,
|
|
|
|
grantAtomicUncached -> tileInvalid
|
2012-04-10 09:09:58 +02:00
|
|
|
))
|
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnProbe(incoming: Probe, state: UInt): Bits = {
|
2012-04-10 09:09:58 +02:00
|
|
|
MuxLookup(incoming.p_type, state, Array(
|
2013-01-22 02:17:26 +01:00
|
|
|
probeInvalidate -> tileInvalid,
|
|
|
|
probeDowngrade -> tileExclusiveClean,
|
|
|
|
probeCopy -> state
|
2012-04-10 09:09:58 +02:00
|
|
|
))
|
|
|
|
}
|
|
|
|
|
2013-08-02 23:55:06 +02:00
|
|
|
def getUncachedReadAcquireType = acquireReadUncached
|
|
|
|
def getUncachedWriteAcquireType = acquireWriteUncached
|
|
|
|
def getUncachedReadWordAcquireType = acquireReadWordUncached
|
|
|
|
def getUncachedWriteWordAcquireType = acquireWriteWordUncached
|
|
|
|
def getUncachedAtomicAcquireType = acquireAtomicUncached
|
2013-01-22 02:17:26 +01:00
|
|
|
def isUncachedReadTransaction(acq: Acquire) = acq.a_type === acquireReadUncached
|
2013-01-29 01:39:45 +01:00
|
|
|
def isVoluntary(rel: Release) = rel.r_type === releaseVoluntaryInvalidateData
|
2013-03-01 03:13:41 +01:00
|
|
|
def isVoluntary(gnt: Grant) = gnt.g_type === grantVoluntaryAck
|
2012-10-02 01:05:37 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def getAcquireTypeOnPrimaryMiss(cmd: UInt, state: UInt): UInt = {
|
2013-04-08 04:23:44 +02:00
|
|
|
Mux(isWriteIntent(cmd), acquireReadExclusiveDirty, acquireReadExclusiveClean)
|
2012-04-10 09:09:58 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def getAcquireTypeOnSecondaryMiss(cmd: UInt, state: UInt, outstanding: Acquire): UInt = {
|
2013-04-08 04:23:44 +02:00
|
|
|
Mux(isWriteIntent(cmd), acquireReadExclusiveDirty, outstanding.a_type)
|
2012-04-10 09:09:58 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def getReleaseTypeOnCacheControl(cmd: UInt): Bits = releaseVoluntaryInvalidateData // TODO
|
2013-03-01 03:13:41 +01:00
|
|
|
def getReleaseTypeOnVoluntaryWriteback(): Bits = getReleaseTypeOnCacheControl(M_INV)
|
2013-08-12 19:36:44 +02:00
|
|
|
def getReleaseTypeOnProbe(incoming: Probe, state: UInt): Bits = {
|
2013-01-22 02:17:26 +01:00
|
|
|
val with_data = MuxLookup(incoming.p_type, releaseInvalidateData, Array(
|
|
|
|
probeInvalidate -> releaseInvalidateData,
|
|
|
|
probeDowngrade -> releaseDowngradeData,
|
|
|
|
probeCopy -> releaseCopyData
|
2012-04-10 09:09:58 +02:00
|
|
|
))
|
2013-01-22 02:17:26 +01:00
|
|
|
val without_data = MuxLookup(incoming.p_type, releaseInvalidateAck, Array(
|
|
|
|
probeInvalidate -> releaseInvalidateAck,
|
|
|
|
probeDowngrade -> releaseDowngradeAck,
|
|
|
|
probeCopy -> releaseCopyAck
|
2012-04-10 09:09:58 +02:00
|
|
|
))
|
2013-08-02 23:55:06 +02:00
|
|
|
Mux(needsWriteback(state), with_data, without_data)
|
2012-04-10 09:09:58 +02:00
|
|
|
}
|
|
|
|
|
2013-03-20 22:10:16 +01:00
|
|
|
def messageHasData(msg: SourcedMessage) = msg match {
|
2013-08-12 19:36:44 +02:00
|
|
|
case acq: Acquire => uSIntListContains(hasDataAcquireTypeList, acq.a_type)
|
|
|
|
case grant: Grant => uSIntListContains(hasDataGrantTypeList, grant.g_type)
|
|
|
|
case rel: Release => uSIntListContains(hasDataReleaseTypeList, rel.r_type)
|
2013-03-20 22:10:16 +01:00
|
|
|
case _ => Bool(false)
|
|
|
|
}
|
2013-01-22 02:17:26 +01:00
|
|
|
def messageUpdatesDataArray (reply: Grant): Bool = {
|
|
|
|
(reply.g_type === grantReadExclusive)
|
2012-04-10 09:09:58 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def messageIsUncached(acq: Acquire): Bool = uSIntListContains(uncachedAcquireTypeList, acq.a_type)
|
2012-04-10 09:09:58 +02:00
|
|
|
|
|
|
|
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool = (addr1 === addr2)
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def getGrantType(a_type: UInt, count: UInt): Bits = {
|
2013-01-22 02:17:26 +01:00
|
|
|
MuxLookup(a_type, grantReadUncached, Array(
|
|
|
|
acquireReadExclusiveClean -> grantReadExclusive,
|
|
|
|
acquireReadExclusiveDirty -> grantReadExclusive,
|
|
|
|
acquireReadUncached -> grantReadUncached,
|
|
|
|
acquireWriteUncached -> grantWriteUncached,
|
|
|
|
acquireReadWordUncached -> grantReadWordUncached,
|
|
|
|
acquireWriteWordUncached -> grantWriteWordUncached,
|
|
|
|
acquireAtomicUncached -> grantAtomicUncached
|
2012-04-10 09:09:58 +02:00
|
|
|
))
|
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def getGrantType(rel: Release, count: UInt): Bits = {
|
2013-01-29 01:39:45 +01:00
|
|
|
MuxLookup(rel.r_type, grantReadUncached, Array(
|
|
|
|
releaseVoluntaryInvalidateData -> grantVoluntaryAck
|
|
|
|
))
|
|
|
|
}
|
|
|
|
|
2012-04-10 09:09:58 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def getProbeType(a_type: UInt, global_state: UInt): UInt = {
|
2013-01-22 02:17:26 +01:00
|
|
|
MuxLookup(a_type, probeCopy, Array(
|
|
|
|
acquireReadExclusiveClean -> probeInvalidate,
|
|
|
|
acquireReadExclusiveDirty -> probeInvalidate,
|
|
|
|
acquireReadUncached -> probeCopy,
|
|
|
|
acquireWriteUncached -> probeInvalidate,
|
|
|
|
acquireReadWordUncached -> probeCopy,
|
|
|
|
acquireWriteWordUncached -> probeInvalidate,
|
|
|
|
acquireAtomicUncached -> probeInvalidate
|
2012-04-10 09:09:58 +02:00
|
|
|
))
|
|
|
|
}
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsOuterRead(a_type: UInt, global_state: UInt): Bool = {
|
2013-01-22 02:17:26 +01:00
|
|
|
(a_type != acquireWriteUncached)
|
2012-04-10 09:09:58 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsOuterWrite(a_type: UInt, global_state: UInt): Bool = {
|
2013-01-22 02:17:26 +01:00
|
|
|
(a_type === acquireWriteUncached)
|
2012-04-10 09:09:58 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsAckReply(a_type: UInt, global_state: UInt): Bool = {
|
2013-01-22 02:17:26 +01:00
|
|
|
(a_type === acquireWriteUncached)
|
2012-04-10 09:09:58 +02:00
|
|
|
}
|
2013-04-10 22:46:31 +02:00
|
|
|
def requiresAck(grant: Grant) = grant.g_type != grantVoluntaryAck
|
2013-01-29 01:39:45 +01:00
|
|
|
def requiresAck(release: Release) = Bool(false)
|
2013-03-26 00:20:12 +01:00
|
|
|
def needsSelfProbe(acq: Acquire) = Bool(false)
|
2013-03-01 03:13:41 +01:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool = (r_type === releaseVoluntaryInvalidateData)
|
2012-02-15 00:51:32 +01:00
|
|
|
}
|
|
|
|
|
2012-04-12 02:56:59 +02:00
|
|
|
class MSICoherence extends CoherencePolicyWithUncached {
|
2013-08-02 23:55:06 +02:00
|
|
|
def nClientStates = 3
|
|
|
|
def nMasterStates = 3
|
|
|
|
def nAcquireTypes = 7
|
|
|
|
def nProbeTypes = 3
|
|
|
|
def nReleaseTypes = 7
|
|
|
|
def nGrantTypes = 9
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
val tileInvalid :: tileShared :: tileExclusiveDirty :: Nil = Enum(nClientStates){ UInt() }
|
|
|
|
val globalInvalid :: globalShared :: globalExclusive :: Nil = Enum(nMasterStates){ UInt() }
|
2012-04-12 02:56:59 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
val acquireReadShared :: acquireReadExclusive :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: Nil = Enum(nAcquireTypes){ UInt() }
|
|
|
|
val probeInvalidate :: probeDowngrade :: probeCopy :: Nil = Enum(nProbeTypes){ UInt() }
|
|
|
|
val releaseVoluntaryInvalidateData :: releaseInvalidateData :: releaseDowngradeData :: releaseCopyData :: releaseInvalidateAck :: releaseDowngradeAck :: releaseCopyAck :: Nil = Enum(nReleaseTypes){ UInt() }
|
|
|
|
val grantVoluntaryAck :: grantReadShared :: grantReadExclusive :: grantReadUncached :: grantWriteUncached :: grantReadExclusiveAck :: grantReadWordUncached :: grantWriteWordUncached :: grantAtomicUncached :: Nil = Enum(nGrantTypes){ UInt() }
|
2012-04-12 02:56:59 +02:00
|
|
|
|
2013-03-01 03:13:41 +01:00
|
|
|
val uncachedAcquireTypeList = List(acquireReadUncached, acquireWriteUncached, acquireReadWordUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
|
|
|
val hasDataAcquireTypeList = List(acquireWriteUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
|
|
|
val hasDataReleaseTypeList = List(releaseVoluntaryInvalidateData, releaseInvalidateData, releaseDowngradeData, releaseCopyData)
|
|
|
|
val hasDataGrantTypeList = List(grantReadShared, grantReadExclusive, grantReadUncached, grantReadWordUncached, grantAtomicUncached)
|
2012-04-12 02:56:59 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def isHit (cmd: UInt, state: UInt): Bool = {
|
2013-04-08 04:23:44 +02:00
|
|
|
Mux(isWriteIntent(cmd), (state === tileExclusiveDirty),
|
2012-04-12 02:56:59 +02:00
|
|
|
(state === tileShared || state === tileExclusiveDirty))
|
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def isValid (state: UInt): Bool = {
|
2012-04-12 02:56:59 +02:00
|
|
|
state != tileInvalid
|
|
|
|
}
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsTransactionOnSecondaryMiss(cmd: UInt, outstanding: Acquire): Bool = {
|
2013-04-08 04:23:44 +02:00
|
|
|
(isRead(cmd) && messageIsUncached(outstanding)) ||
|
|
|
|
(isWriteIntent(cmd) && (outstanding.a_type != acquireReadExclusive))
|
2012-04-12 02:56:59 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsTransactionOnCacheControl(cmd: UInt, state: UInt): Bool = {
|
2012-04-12 02:56:59 +02:00
|
|
|
MuxLookup(cmd, (state === tileExclusiveDirty), Array(
|
|
|
|
M_INV -> (state === tileExclusiveDirty),
|
|
|
|
M_CLN -> (state === tileExclusiveDirty)
|
|
|
|
))
|
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsWriteback (state: UInt): Bool = {
|
2012-04-12 02:56:59 +02:00
|
|
|
needsTransactionOnCacheControl(M_INV, state)
|
|
|
|
}
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnHit(cmd: UInt, state: UInt): UInt = {
|
2013-04-08 04:23:44 +02:00
|
|
|
Mux(isWrite(cmd), tileExclusiveDirty, state)
|
2012-04-12 02:56:59 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnCacheControl(cmd: UInt) = {
|
2012-04-12 02:56:59 +02:00
|
|
|
MuxLookup(cmd, tileInvalid, Array(
|
|
|
|
M_INV -> tileInvalid,
|
|
|
|
M_CLN -> tileShared
|
|
|
|
))
|
|
|
|
}
|
|
|
|
def newStateOnWriteback() = newStateOnCacheControl(M_INV)
|
|
|
|
def newStateOnFlush() = newStateOnCacheControl(M_INV)
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnGrant(incoming: Grant, outstanding: Acquire): UInt = {
|
2013-01-22 02:17:26 +01:00
|
|
|
MuxLookup(incoming.g_type, tileInvalid, Array(
|
|
|
|
grantReadShared -> tileShared,
|
|
|
|
grantReadExclusive -> tileExclusiveDirty,
|
|
|
|
grantReadExclusiveAck -> tileExclusiveDirty,
|
|
|
|
grantReadUncached -> tileInvalid,
|
|
|
|
grantWriteUncached -> tileInvalid,
|
|
|
|
grantReadWordUncached -> tileInvalid,
|
|
|
|
grantWriteWordUncached -> tileInvalid,
|
|
|
|
grantAtomicUncached -> tileInvalid
|
2012-04-12 02:56:59 +02:00
|
|
|
))
|
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnProbe(incoming: Probe, state: UInt): Bits = {
|
2012-04-12 02:56:59 +02:00
|
|
|
MuxLookup(incoming.p_type, state, Array(
|
2013-01-22 02:17:26 +01:00
|
|
|
probeInvalidate -> tileInvalid,
|
|
|
|
probeDowngrade -> tileShared,
|
|
|
|
probeCopy -> state
|
2012-04-12 02:56:59 +02:00
|
|
|
))
|
|
|
|
}
|
|
|
|
|
2013-08-02 23:55:06 +02:00
|
|
|
def getUncachedReadAcquireType = acquireReadUncached
|
|
|
|
def getUncachedWriteAcquireType = acquireWriteUncached
|
|
|
|
def getUncachedReadWordAcquireType = acquireReadWordUncached
|
|
|
|
def getUncachedWriteWordAcquireType = acquireWriteWordUncached
|
|
|
|
def getUncachedAtomicAcquireType = acquireAtomicUncached
|
2013-01-22 02:17:26 +01:00
|
|
|
def isUncachedReadTransaction(acq: Acquire) = acq.a_type === acquireReadUncached
|
2013-01-29 01:39:45 +01:00
|
|
|
def isVoluntary(rel: Release) = rel.r_type === releaseVoluntaryInvalidateData
|
2013-03-01 03:13:41 +01:00
|
|
|
def isVoluntary(gnt: Grant) = gnt.g_type === grantVoluntaryAck
|
2012-10-02 01:05:37 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def getAcquireTypeOnPrimaryMiss(cmd: UInt, state: UInt): UInt = {
|
2013-04-04 07:13:51 +02:00
|
|
|
Mux(isWriteIntent(cmd), acquireReadExclusive, acquireReadShared)
|
2012-04-12 02:56:59 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def getAcquireTypeOnSecondaryMiss(cmd: UInt, state: UInt, outstanding: Acquire): UInt = {
|
2013-04-08 04:23:44 +02:00
|
|
|
Mux(isWriteIntent(cmd), acquireReadExclusive, outstanding.a_type)
|
2012-04-12 02:56:59 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def getReleaseTypeOnCacheControl(cmd: UInt): Bits = releaseVoluntaryInvalidateData // TODO
|
2013-03-01 03:13:41 +01:00
|
|
|
def getReleaseTypeOnVoluntaryWriteback(): Bits = getReleaseTypeOnCacheControl(M_INV)
|
2013-08-12 19:36:44 +02:00
|
|
|
def getReleaseTypeOnProbe(incoming: Probe, state: UInt): Bits = {
|
2013-01-22 02:17:26 +01:00
|
|
|
val with_data = MuxLookup(incoming.p_type, releaseInvalidateData, Array(
|
|
|
|
probeInvalidate -> releaseInvalidateData,
|
|
|
|
probeDowngrade -> releaseDowngradeData,
|
|
|
|
probeCopy -> releaseCopyData
|
2012-04-12 02:56:59 +02:00
|
|
|
))
|
2013-01-22 02:17:26 +01:00
|
|
|
val without_data = MuxLookup(incoming.p_type, releaseInvalidateAck, Array(
|
|
|
|
probeInvalidate -> releaseInvalidateAck,
|
|
|
|
probeDowngrade -> releaseDowngradeAck,
|
|
|
|
probeCopy -> releaseCopyAck
|
2012-04-12 02:56:59 +02:00
|
|
|
))
|
2013-08-02 23:55:06 +02:00
|
|
|
Mux(needsWriteback(state), with_data, without_data)
|
2012-04-12 02:56:59 +02:00
|
|
|
}
|
|
|
|
|
2013-03-20 22:10:16 +01:00
|
|
|
def messageHasData(msg: SourcedMessage) = msg match {
|
2013-08-12 19:36:44 +02:00
|
|
|
case acq: Acquire => uSIntListContains(hasDataAcquireTypeList, acq.a_type)
|
|
|
|
case grant: Grant => uSIntListContains(hasDataGrantTypeList, grant.g_type)
|
|
|
|
case rel: Release => uSIntListContains(hasDataReleaseTypeList, rel.r_type)
|
2013-03-20 22:10:16 +01:00
|
|
|
case _ => Bool(false)
|
|
|
|
}
|
2013-01-22 02:17:26 +01:00
|
|
|
def messageUpdatesDataArray (reply: Grant): Bool = {
|
|
|
|
(reply.g_type === grantReadShared || reply.g_type === grantReadExclusive)
|
2012-04-12 02:56:59 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def messageIsUncached(acq: Acquire): Bool = uSIntListContains(uncachedAcquireTypeList, acq.a_type)
|
2012-04-12 02:56:59 +02:00
|
|
|
|
|
|
|
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool = (addr1 === addr2)
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def getGrantType(a_type: UInt, count: UInt): Bits = {
|
2013-01-22 02:17:26 +01:00
|
|
|
MuxLookup(a_type, grantReadUncached, Array(
|
2013-08-12 19:36:44 +02:00
|
|
|
acquireReadShared -> Mux(count > UInt(0), grantReadShared, grantReadExclusive),
|
2013-01-22 02:17:26 +01:00
|
|
|
acquireReadExclusive -> grantReadExclusive,
|
|
|
|
acquireReadUncached -> grantReadUncached,
|
|
|
|
acquireWriteUncached -> grantWriteUncached,
|
|
|
|
acquireReadWordUncached -> grantReadWordUncached,
|
|
|
|
acquireWriteWordUncached -> grantWriteWordUncached,
|
|
|
|
acquireAtomicUncached -> grantAtomicUncached
|
2012-04-12 02:56:59 +02:00
|
|
|
))
|
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def getGrantType(rel: Release, count: UInt): Bits = {
|
2013-01-29 01:39:45 +01:00
|
|
|
MuxLookup(rel.r_type, grantReadUncached, Array(
|
|
|
|
releaseVoluntaryInvalidateData -> grantVoluntaryAck
|
|
|
|
))
|
|
|
|
}
|
|
|
|
|
2012-04-12 02:56:59 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def getProbeType(a_type: UInt, global_state: UInt): UInt = {
|
2013-01-22 02:17:26 +01:00
|
|
|
MuxLookup(a_type, probeCopy, Array(
|
|
|
|
acquireReadShared -> probeDowngrade,
|
|
|
|
acquireReadExclusive -> probeInvalidate,
|
|
|
|
acquireReadUncached -> probeCopy,
|
|
|
|
acquireWriteUncached -> probeInvalidate
|
2012-04-12 02:56:59 +02:00
|
|
|
))
|
|
|
|
}
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsOuterRead(a_type: UInt, global_state: UInt): Bool = {
|
2013-01-22 02:17:26 +01:00
|
|
|
(a_type != acquireWriteUncached)
|
2012-04-12 02:56:59 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsOuterWrite(a_type: UInt, global_state: UInt): Bool = {
|
2013-01-22 02:17:26 +01:00
|
|
|
(a_type === acquireWriteUncached)
|
2012-04-12 02:56:59 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsAckReply(a_type: UInt, global_state: UInt): Bool = {
|
2013-01-22 02:17:26 +01:00
|
|
|
(a_type === acquireWriteUncached)
|
2012-04-12 02:56:59 +02:00
|
|
|
}
|
2013-04-10 22:46:31 +02:00
|
|
|
def requiresAck(grant: Grant) = grant.g_type != grantVoluntaryAck
|
2013-01-29 01:39:45 +01:00
|
|
|
def requiresAck(release: Release) = Bool(false)
|
2013-03-26 00:20:12 +01:00
|
|
|
def needsSelfProbe(acq: Acquire) = Bool(false)
|
2013-03-01 03:13:41 +01:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool = (r_type === releaseVoluntaryInvalidateData)
|
2012-04-12 02:56:59 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
class MESICoherence extends CoherencePolicyWithUncached {
|
2013-08-02 23:55:06 +02:00
|
|
|
def nClientStates = 4
|
|
|
|
def nMasterStates = 3
|
|
|
|
def nAcquireTypes = 7
|
|
|
|
def nProbeTypes = 3
|
|
|
|
def nReleaseTypes = 7
|
|
|
|
def nGrantTypes = 9
|
2012-02-15 00:51:32 +01:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
val tileInvalid :: tileShared :: tileExclusiveClean :: tileExclusiveDirty :: Nil = Enum(nClientStates){ UInt() }
|
|
|
|
val globalInvalid :: globalShared :: globalExclusiveClean :: Nil = Enum(nMasterStates){ UInt() }
|
2012-02-15 00:51:32 +01:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
val acquireReadShared :: acquireReadExclusive :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: Nil = Enum(nAcquireTypes){ UInt() }
|
|
|
|
val probeInvalidate :: probeDowngrade :: probeCopy :: Nil = Enum(nProbeTypes){ UInt() }
|
|
|
|
val releaseVoluntaryInvalidateData :: releaseInvalidateData :: releaseDowngradeData :: releaseCopyData :: releaseInvalidateAck :: releaseDowngradeAck :: releaseCopyAck :: Nil = Enum(nReleaseTypes){ UInt() }
|
|
|
|
val grantVoluntaryAck :: grantReadShared :: grantReadExclusive :: grantReadUncached :: grantWriteUncached :: grantReadExclusiveAck :: grantReadWordUncached :: grantWriteWordUncached :: grantAtomicUncached :: Nil = Enum(nGrantTypes){ UInt() }
|
2013-03-01 03:13:41 +01:00
|
|
|
|
|
|
|
val uncachedAcquireTypeList = List(acquireReadUncached, acquireWriteUncached, acquireReadWordUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
|
|
|
val hasDataAcquireTypeList = List(acquireWriteUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
|
|
|
val hasDataReleaseTypeList = List(releaseVoluntaryInvalidateData, releaseInvalidateData, releaseDowngradeData, releaseCopyData)
|
|
|
|
val hasDataGrantTypeList = List(grantReadShared, grantReadExclusive, grantReadUncached, grantReadWordUncached, grantAtomicUncached)
|
2012-04-03 21:03:05 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def isHit (cmd: UInt, state: UInt): Bool = {
|
2013-04-08 04:23:44 +02:00
|
|
|
Mux(isWriteIntent(cmd), (state === tileExclusiveClean || state === tileExclusiveDirty),
|
2012-03-12 18:38:37 +01:00
|
|
|
(state === tileShared || state === tileExclusiveClean || state === tileExclusiveDirty))
|
2012-02-16 21:59:38 +01:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def isValid (state: UInt): Bool = {
|
2012-02-16 21:59:38 +01:00
|
|
|
state != tileInvalid
|
2012-02-15 00:51:32 +01:00
|
|
|
}
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsTransactionOnSecondaryMiss(cmd: UInt, outstanding: Acquire): Bool = {
|
2013-04-08 04:23:44 +02:00
|
|
|
(isRead(cmd) && messageIsUncached(outstanding)) ||
|
|
|
|
(isWriteIntent(cmd) && (outstanding.a_type != acquireReadExclusive))
|
2012-04-03 21:03:05 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsTransactionOnCacheControl(cmd: UInt, state: UInt): Bool = {
|
2012-04-03 21:03:05 +02:00
|
|
|
MuxLookup(cmd, (state === tileExclusiveDirty), Array(
|
|
|
|
M_INV -> (state === tileExclusiveDirty),
|
|
|
|
M_CLN -> (state === tileExclusiveDirty)
|
|
|
|
))
|
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsWriteback (state: UInt): Bool = {
|
2012-04-03 21:03:05 +02:00
|
|
|
needsTransactionOnCacheControl(M_INV, state)
|
2012-02-15 00:51:32 +01:00
|
|
|
}
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnHit(cmd: UInt, state: UInt): UInt = {
|
2013-04-08 04:23:44 +02:00
|
|
|
Mux(isWrite(cmd), tileExclusiveDirty, state)
|
2012-03-03 06:58:50 +01:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnCacheControl(cmd: UInt) = {
|
2012-04-03 21:03:05 +02:00
|
|
|
MuxLookup(cmd, tileInvalid, Array(
|
|
|
|
M_INV -> tileInvalid,
|
2012-04-12 02:56:59 +02:00
|
|
|
M_CLN -> tileShared
|
2012-04-03 21:03:05 +02:00
|
|
|
))
|
2012-03-07 10:26:35 +01:00
|
|
|
}
|
2012-04-03 21:03:05 +02:00
|
|
|
def newStateOnWriteback() = newStateOnCacheControl(M_INV)
|
|
|
|
def newStateOnFlush() = newStateOnCacheControl(M_INV)
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnGrant(incoming: Grant, outstanding: Acquire): UInt = {
|
2013-01-22 02:17:26 +01:00
|
|
|
MuxLookup(incoming.g_type, tileInvalid, Array(
|
|
|
|
grantReadShared -> tileShared,
|
|
|
|
grantReadExclusive -> Mux(outstanding.a_type === acquireReadExclusive, tileExclusiveDirty, tileExclusiveClean),
|
|
|
|
grantReadExclusiveAck -> tileExclusiveDirty,
|
|
|
|
grantReadUncached -> tileInvalid,
|
|
|
|
grantWriteUncached -> tileInvalid,
|
|
|
|
grantReadWordUncached -> tileInvalid,
|
|
|
|
grantWriteWordUncached -> tileInvalid,
|
|
|
|
grantAtomicUncached -> tileInvalid
|
2012-03-03 06:58:50 +01:00
|
|
|
))
|
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnProbe(incoming: Probe, state: UInt): Bits = {
|
2012-03-02 03:23:46 +01:00
|
|
|
MuxLookup(incoming.p_type, state, Array(
|
2013-01-22 02:17:26 +01:00
|
|
|
probeInvalidate -> tileInvalid,
|
|
|
|
probeDowngrade -> tileShared,
|
|
|
|
probeCopy -> state
|
2012-03-02 03:23:46 +01:00
|
|
|
))
|
2012-02-15 00:51:32 +01:00
|
|
|
}
|
2012-03-02 02:03:56 +01:00
|
|
|
|
2013-08-02 23:55:06 +02:00
|
|
|
def getUncachedReadAcquireType = acquireReadUncached
|
|
|
|
def getUncachedWriteAcquireType = acquireWriteUncached
|
|
|
|
def getUncachedReadWordAcquireType = acquireReadWordUncached
|
|
|
|
def getUncachedWriteWordAcquireType = acquireWriteWordUncached
|
|
|
|
def getUncachedAtomicAcquireType = acquireAtomicUncached
|
2013-01-22 02:17:26 +01:00
|
|
|
def isUncachedReadTransaction(acq: Acquire) = acq.a_type === acquireReadUncached
|
2013-01-29 01:39:45 +01:00
|
|
|
def isVoluntary(rel: Release) = rel.r_type === releaseVoluntaryInvalidateData
|
2013-03-01 03:13:41 +01:00
|
|
|
def isVoluntary(gnt: Grant) = gnt.g_type === grantVoluntaryAck
|
2012-10-02 01:05:37 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def getAcquireTypeOnPrimaryMiss(cmd: UInt, state: UInt): UInt = {
|
2013-04-04 07:13:51 +02:00
|
|
|
Mux(isWriteIntent(cmd), acquireReadExclusive, acquireReadShared)
|
2012-04-03 21:03:05 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def getAcquireTypeOnSecondaryMiss(cmd: UInt, state: UInt, outstanding: Acquire): UInt = {
|
2013-04-08 04:23:44 +02:00
|
|
|
Mux(isWriteIntent(cmd), acquireReadExclusive, outstanding.a_type)
|
2012-04-03 21:03:05 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def getReleaseTypeOnCacheControl(cmd: UInt): Bits = releaseVoluntaryInvalidateData // TODO
|
2013-03-01 03:13:41 +01:00
|
|
|
def getReleaseTypeOnVoluntaryWriteback(): Bits = getReleaseTypeOnCacheControl(M_INV)
|
2013-08-12 19:36:44 +02:00
|
|
|
def getReleaseTypeOnProbe(incoming: Probe, state: UInt): Bits = {
|
2013-01-22 02:17:26 +01:00
|
|
|
val with_data = MuxLookup(incoming.p_type, releaseInvalidateData, Array(
|
|
|
|
probeInvalidate -> releaseInvalidateData,
|
|
|
|
probeDowngrade -> releaseDowngradeData,
|
|
|
|
probeCopy -> releaseCopyData
|
2012-03-14 00:43:35 +01:00
|
|
|
))
|
2013-01-22 02:17:26 +01:00
|
|
|
val without_data = MuxLookup(incoming.p_type, releaseInvalidateAck, Array(
|
|
|
|
probeInvalidate -> releaseInvalidateAck,
|
|
|
|
probeDowngrade -> releaseDowngradeAck,
|
|
|
|
probeCopy -> releaseCopyAck
|
2012-03-14 00:43:35 +01:00
|
|
|
))
|
2013-08-02 23:55:06 +02:00
|
|
|
Mux(needsWriteback(state), with_data, without_data)
|
2012-03-14 00:43:35 +01:00
|
|
|
}
|
2012-04-03 21:03:05 +02:00
|
|
|
|
2013-03-20 22:10:16 +01:00
|
|
|
def messageHasData(msg: SourcedMessage) = msg match {
|
2013-08-12 19:36:44 +02:00
|
|
|
case acq: Acquire => uSIntListContains(hasDataAcquireTypeList, acq.a_type)
|
|
|
|
case grant: Grant => uSIntListContains(hasDataGrantTypeList, grant.g_type)
|
|
|
|
case rel: Release => uSIntListContains(hasDataReleaseTypeList, rel.r_type)
|
2013-03-20 22:10:16 +01:00
|
|
|
case _ => Bool(false)
|
|
|
|
}
|
2013-01-22 02:17:26 +01:00
|
|
|
def messageUpdatesDataArray (reply: Grant): Bool = {
|
|
|
|
(reply.g_type === grantReadShared || reply.g_type === grantReadExclusive)
|
2012-04-10 09:09:58 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def messageIsUncached(acq: Acquire): Bool = uSIntListContains(uncachedAcquireTypeList, acq.a_type)
|
2012-02-15 00:51:32 +01:00
|
|
|
|
2012-04-03 21:03:05 +02:00
|
|
|
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool = (addr1 === addr2)
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def getGrantType(a_type: UInt, count: UInt): Bits = {
|
2013-01-22 02:17:26 +01:00
|
|
|
MuxLookup(a_type, grantReadUncached, Array(
|
2013-08-12 19:36:44 +02:00
|
|
|
acquireReadShared -> Mux(count > UInt(0), grantReadShared, grantReadExclusive),
|
2013-01-22 02:17:26 +01:00
|
|
|
acquireReadExclusive -> grantReadExclusive,
|
|
|
|
acquireReadUncached -> grantReadUncached,
|
|
|
|
acquireWriteUncached -> grantWriteUncached,
|
|
|
|
acquireReadWordUncached -> grantReadWordUncached,
|
|
|
|
acquireWriteWordUncached -> grantWriteWordUncached,
|
|
|
|
acquireAtomicUncached -> grantAtomicUncached
|
2012-04-03 21:03:05 +02:00
|
|
|
))
|
2012-02-23 03:24:52 +01:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def getGrantType(rel: Release, count: UInt): Bits = {
|
2013-01-29 01:39:45 +01:00
|
|
|
MuxLookup(rel.r_type, grantReadUncached, Array(
|
|
|
|
releaseVoluntaryInvalidateData -> grantVoluntaryAck
|
|
|
|
))
|
|
|
|
}
|
|
|
|
|
2012-02-22 21:14:57 +01:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def getProbeType(a_type: UInt, global_state: UInt): UInt = {
|
2013-01-22 02:17:26 +01:00
|
|
|
MuxLookup(a_type, probeCopy, Array(
|
|
|
|
acquireReadShared -> probeDowngrade,
|
|
|
|
acquireReadExclusive -> probeInvalidate,
|
|
|
|
acquireReadUncached -> probeCopy,
|
|
|
|
acquireWriteUncached -> probeInvalidate,
|
|
|
|
acquireReadWordUncached -> probeCopy,
|
|
|
|
acquireWriteWordUncached -> probeInvalidate,
|
|
|
|
acquireAtomicUncached -> probeInvalidate
|
2012-03-03 08:51:53 +01:00
|
|
|
))
|
2012-02-29 02:33:06 +01:00
|
|
|
}
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsOuterRead(a_type: UInt, global_state: UInt): Bool = {
|
2013-01-22 02:17:26 +01:00
|
|
|
(a_type != acquireWriteUncached)
|
2012-02-29 11:59:27 +01:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsOuterWrite(a_type: UInt, global_state: UInt): Bool = {
|
2013-01-22 02:17:26 +01:00
|
|
|
(a_type === acquireWriteUncached)
|
2012-02-29 11:59:27 +01:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsAckReply(a_type: UInt, global_state: UInt): Bool = {
|
2013-01-22 02:17:26 +01:00
|
|
|
(a_type === acquireWriteUncached)
|
2012-02-27 20:26:18 +01:00
|
|
|
}
|
2013-01-29 01:39:45 +01:00
|
|
|
|
2013-04-10 22:46:31 +02:00
|
|
|
def requiresAck(grant: Grant) = grant.g_type != grantVoluntaryAck
|
2013-01-29 01:39:45 +01:00
|
|
|
def requiresAck(release: Release) = Bool(false)
|
2013-03-26 00:20:12 +01:00
|
|
|
def needsSelfProbe(acq: Acquire) = Bool(false)
|
2013-03-01 03:13:41 +01:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool = (r_type === releaseVoluntaryInvalidateData)
|
2012-02-23 03:24:52 +01:00
|
|
|
}
|
2012-10-24 03:01:53 +02:00
|
|
|
|
|
|
|
class MigratoryCoherence extends CoherencePolicyWithUncached {
|
2013-08-02 23:55:06 +02:00
|
|
|
def nClientStates = 7
|
|
|
|
def nMasterStates = 0
|
|
|
|
def nAcquireTypes = 8
|
|
|
|
def nProbeTypes = 4
|
|
|
|
def nReleaseTypes = 11
|
|
|
|
def nGrantTypes = 9
|
2012-10-24 03:01:53 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
val tileInvalid :: tileShared :: tileExclusiveClean :: tileExclusiveDirty :: tileSharedByTwo :: tileMigratoryClean :: tileMigratoryDirty :: Nil = Enum(nClientStates){ UInt() }
|
2012-10-24 03:01:53 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
val acquireReadShared :: acquireReadExclusive :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: acquireInvalidateOthers :: Nil = Enum(nAcquireTypes){ UInt() }
|
|
|
|
val probeInvalidate :: probeDowngrade :: probeCopy :: probeInvalidateOthers :: Nil = Enum(nProbeTypes){ UInt() }
|
|
|
|
val releaseVoluntaryInvalidateData :: releaseInvalidateData :: releaseDowngradeData :: releaseCopyData :: releaseInvalidateAck :: releaseDowngradeAck :: releaseCopyAck :: releaseDowngradeDataMigratory :: releaseDowngradeAckHasCopy :: releaseInvalidateDataMigratory :: releaseInvalidateAckMigratory :: Nil = Enum(nReleaseTypes){ UInt() }
|
|
|
|
val grantVoluntaryAck :: grantReadShared :: grantReadExclusive :: grantReadUncached :: grantWriteUncached :: grantReadExclusiveAck :: grantReadWordUncached :: grantWriteWordUncached :: grantAtomicUncached :: grantReadMigratory :: Nil = Enum(nGrantTypes){ UInt() }
|
2012-10-24 03:01:53 +02:00
|
|
|
|
2013-03-01 03:13:41 +01:00
|
|
|
val uncachedAcquireTypeList = List(acquireReadUncached, acquireWriteUncached, acquireReadWordUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
|
|
|
val hasDataAcquireTypeList = List(acquireWriteUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
|
|
|
val hasDataGrantTypeList = List(grantReadShared, grantReadExclusive, grantReadUncached, grantReadMigratory, grantReadWordUncached, grantAtomicUncached)
|
|
|
|
val hasDataReleaseTypeList = List(releaseVoluntaryInvalidateData, releaseInvalidateData, releaseDowngradeData, releaseCopyData, releaseInvalidateDataMigratory, releaseDowngradeDataMigratory)
|
2012-10-24 03:01:53 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def isHit (cmd: UInt, state: UInt): Bool = {
|
|
|
|
Mux(isWriteIntent(cmd), uSIntListContains(List(tileExclusiveClean, tileExclusiveDirty, tileMigratoryClean, tileMigratoryDirty), state), (state != tileInvalid))
|
2012-10-24 03:01:53 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def isValid (state: UInt): Bool = {
|
2012-10-24 03:01:53 +02:00
|
|
|
state != tileInvalid
|
|
|
|
}
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsTransactionOnSecondaryMiss(cmd: UInt, outstanding: Acquire): Bool = {
|
2013-04-08 04:23:44 +02:00
|
|
|
(isRead(cmd) && messageIsUncached(outstanding)) ||
|
|
|
|
(isWriteIntent(cmd) && (outstanding.a_type != acquireReadExclusive && outstanding.a_type != acquireInvalidateOthers))
|
2012-10-24 03:01:53 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsTransactionOnCacheControl(cmd: UInt, state: UInt): Bool = {
|
2012-10-24 03:01:53 +02:00
|
|
|
MuxLookup(cmd, (state === tileExclusiveDirty), Array(
|
2013-08-12 19:36:44 +02:00
|
|
|
M_INV -> uSIntListContains(List(tileExclusiveDirty,tileMigratoryDirty),state),
|
|
|
|
M_CLN -> uSIntListContains(List(tileExclusiveDirty,tileMigratoryDirty),state)
|
2012-10-24 03:01:53 +02:00
|
|
|
))
|
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsWriteback (state: UInt): Bool = {
|
2012-10-24 03:01:53 +02:00
|
|
|
needsTransactionOnCacheControl(M_INV, state)
|
|
|
|
}
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnHit(cmd: UInt, state: UInt): UInt = {
|
2013-04-08 04:23:44 +02:00
|
|
|
Mux(isWrite(cmd), MuxLookup(state, tileExclusiveDirty, Array(
|
2012-10-24 03:01:53 +02:00
|
|
|
tileExclusiveClean -> tileExclusiveDirty,
|
|
|
|
tileMigratoryClean -> tileMigratoryDirty)), state)
|
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnCacheControl(cmd: UInt) = {
|
2012-10-24 03:01:53 +02:00
|
|
|
MuxLookup(cmd, tileInvalid, Array(
|
|
|
|
M_INV -> tileInvalid,
|
|
|
|
M_CLN -> tileShared
|
|
|
|
))
|
|
|
|
}
|
|
|
|
def newStateOnWriteback() = newStateOnCacheControl(M_INV)
|
|
|
|
def newStateOnFlush() = newStateOnCacheControl(M_INV)
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnGrant(incoming: Grant, outstanding: Acquire): UInt = {
|
2013-01-22 02:17:26 +01:00
|
|
|
MuxLookup(incoming.g_type, tileInvalid, Array(
|
|
|
|
grantReadShared -> tileShared,
|
|
|
|
grantReadExclusive -> MuxLookup(outstanding.a_type, tileExclusiveDirty, Array(
|
|
|
|
acquireReadExclusive -> tileExclusiveDirty,
|
|
|
|
acquireReadShared -> tileExclusiveClean)),
|
|
|
|
grantReadExclusiveAck -> tileExclusiveDirty,
|
|
|
|
grantReadUncached -> tileInvalid,
|
|
|
|
grantWriteUncached -> tileInvalid,
|
|
|
|
grantReadWordUncached -> tileInvalid,
|
|
|
|
grantWriteWordUncached -> tileInvalid,
|
|
|
|
grantAtomicUncached -> tileInvalid,
|
|
|
|
grantReadMigratory -> MuxLookup(outstanding.a_type, tileMigratoryDirty, Array(
|
|
|
|
acquireInvalidateOthers -> tileMigratoryDirty,
|
|
|
|
acquireReadExclusive -> tileMigratoryDirty,
|
|
|
|
acquireReadShared -> tileMigratoryClean))
|
2012-10-24 03:01:53 +02:00
|
|
|
))
|
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def newStateOnProbe(incoming: Probe, state: UInt): Bits = {
|
2012-10-24 03:01:53 +02:00
|
|
|
MuxLookup(incoming.p_type, state, Array(
|
2013-01-22 02:17:26 +01:00
|
|
|
probeInvalidate -> tileInvalid,
|
|
|
|
probeInvalidateOthers -> tileInvalid,
|
|
|
|
probeCopy -> state,
|
|
|
|
probeDowngrade -> MuxLookup(state, tileShared, Array(
|
2012-10-24 03:01:53 +02:00
|
|
|
tileExclusiveClean -> tileSharedByTwo,
|
|
|
|
tileExclusiveDirty -> tileSharedByTwo,
|
|
|
|
tileSharedByTwo -> tileShared,
|
|
|
|
tileMigratoryClean -> tileSharedByTwo,
|
|
|
|
tileMigratoryDirty -> tileInvalid))
|
|
|
|
))
|
|
|
|
}
|
|
|
|
|
2013-08-02 23:55:06 +02:00
|
|
|
def getUncachedReadAcquireType = acquireReadUncached
|
|
|
|
def getUncachedWriteAcquireType = acquireWriteUncached
|
|
|
|
def getUncachedReadWordAcquireType = acquireReadWordUncached
|
|
|
|
def getUncachedWriteWordAcquireType = acquireWriteWordUncached
|
|
|
|
def getUncachedAtomicAcquireType = acquireAtomicUncached
|
2013-01-22 02:17:26 +01:00
|
|
|
def isUncachedReadTransaction(acq: Acquire) = acq.a_type === acquireReadUncached
|
2013-01-29 01:39:45 +01:00
|
|
|
def isVoluntary(rel: Release) = rel.r_type === releaseVoluntaryInvalidateData
|
2013-03-01 03:13:41 +01:00
|
|
|
def isVoluntary(gnt: Grant) = gnt.g_type === grantVoluntaryAck
|
2012-10-24 03:01:53 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def getAcquireTypeOnPrimaryMiss(cmd: UInt, state: UInt): UInt = {
|
2013-04-04 07:13:51 +02:00
|
|
|
Mux(isWriteIntent(cmd), Mux(state === tileInvalid, acquireReadExclusive, acquireInvalidateOthers), acquireReadShared)
|
2012-10-24 03:01:53 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def getAcquireTypeOnSecondaryMiss(cmd: UInt, state: UInt, outstanding: Acquire): UInt = {
|
2013-04-08 04:23:44 +02:00
|
|
|
Mux(isWriteIntent(cmd), Mux(state === tileInvalid, acquireReadExclusive, acquireInvalidateOthers), outstanding.a_type)
|
2013-01-22 02:17:26 +01:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def getReleaseTypeOnCacheControl(cmd: UInt): Bits = releaseVoluntaryInvalidateData // TODO
|
2013-03-01 03:13:41 +01:00
|
|
|
def getReleaseTypeOnVoluntaryWriteback(): Bits = getReleaseTypeOnCacheControl(M_INV)
|
2013-08-12 19:36:44 +02:00
|
|
|
def getReleaseTypeOnProbe(incoming: Probe, state: UInt): Bits = {
|
2013-01-22 02:17:26 +01:00
|
|
|
val with_data = MuxLookup(incoming.p_type, releaseInvalidateData, Array(
|
2013-08-12 19:36:44 +02:00
|
|
|
probeInvalidate -> Mux(uSIntListContains(List(tileExclusiveDirty, tileMigratoryDirty), state),
|
2013-01-22 02:17:26 +01:00
|
|
|
releaseInvalidateDataMigratory, releaseInvalidateData),
|
2013-08-02 23:55:06 +02:00
|
|
|
probeDowngrade -> Mux(state === tileMigratoryDirty, releaseDowngradeDataMigratory, releaseDowngradeData),
|
|
|
|
probeCopy -> releaseCopyData
|
2013-01-22 02:17:26 +01:00
|
|
|
))
|
|
|
|
val without_data = MuxLookup(incoming.p_type, releaseInvalidateAck, Array(
|
2013-08-02 23:55:06 +02:00
|
|
|
probeInvalidate -> Mux(tileExclusiveClean === state, releaseInvalidateAckMigratory, releaseInvalidateAck),
|
2013-01-22 02:17:26 +01:00
|
|
|
probeInvalidateOthers -> Mux(state === tileSharedByTwo, releaseInvalidateAckMigratory, releaseInvalidateAck),
|
|
|
|
probeDowngrade -> Mux(state != tileInvalid, releaseDowngradeAckHasCopy, releaseDowngradeAck),
|
|
|
|
probeCopy -> releaseCopyAck
|
|
|
|
))
|
2013-08-02 23:55:06 +02:00
|
|
|
Mux(needsWriteback(state), with_data, without_data)
|
2012-10-24 03:01:53 +02:00
|
|
|
}
|
|
|
|
|
2013-03-20 22:10:16 +01:00
|
|
|
def messageHasData(msg: SourcedMessage) = msg match {
|
2013-08-12 19:36:44 +02:00
|
|
|
case acq: Acquire => uSIntListContains(hasDataAcquireTypeList, acq.a_type)
|
|
|
|
case grant: Grant => uSIntListContains(hasDataGrantTypeList, grant.g_type)
|
|
|
|
case rel: Release => uSIntListContains(hasDataReleaseTypeList, rel.r_type)
|
2013-03-20 22:10:16 +01:00
|
|
|
case _ => Bool(false)
|
|
|
|
}
|
2013-01-22 02:17:26 +01:00
|
|
|
def messageUpdatesDataArray (reply: Grant): Bool = {
|
2013-08-12 19:36:44 +02:00
|
|
|
uSIntListContains(List(grantReadShared, grantReadExclusive, grantReadMigratory), reply.g_type)
|
2012-10-24 03:01:53 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def messageIsUncached(acq: Acquire): Bool = uSIntListContains(uncachedAcquireTypeList, acq.a_type)
|
2012-10-24 03:01:53 +02:00
|
|
|
|
|
|
|
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool = (addr1 === addr2)
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def getGrantType(a_type: UInt, count: UInt): Bits = {
|
2013-01-22 02:17:26 +01:00
|
|
|
MuxLookup(a_type, grantReadUncached, Array(
|
2013-08-12 19:36:44 +02:00
|
|
|
acquireReadShared -> Mux(count > UInt(0), grantReadShared, grantReadExclusive), //TODO: what is count? Depend on release.p_type???
|
2013-01-22 02:17:26 +01:00
|
|
|
acquireReadExclusive -> grantReadExclusive,
|
|
|
|
acquireReadUncached -> grantReadUncached,
|
|
|
|
acquireWriteUncached -> grantWriteUncached,
|
|
|
|
acquireReadWordUncached -> grantReadWordUncached,
|
|
|
|
acquireWriteWordUncached -> grantWriteWordUncached,
|
|
|
|
acquireAtomicUncached -> grantAtomicUncached,
|
|
|
|
acquireInvalidateOthers -> grantReadExclusiveAck //TODO: add this to MESI?
|
2012-10-24 03:01:53 +02:00
|
|
|
))
|
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def getGrantType(rel: Release, count: UInt): Bits = {
|
2013-01-29 01:39:45 +01:00
|
|
|
MuxLookup(rel.r_type, grantReadUncached, Array(
|
|
|
|
releaseVoluntaryInvalidateData -> grantVoluntaryAck
|
|
|
|
))
|
|
|
|
}
|
|
|
|
|
2012-10-24 03:01:53 +02:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def getProbeType(a_type: UInt, global_state: UInt): UInt = {
|
2013-01-22 02:17:26 +01:00
|
|
|
MuxLookup(a_type, probeCopy, Array(
|
|
|
|
acquireReadShared -> probeDowngrade,
|
|
|
|
acquireReadExclusive -> probeInvalidate,
|
|
|
|
acquireReadUncached -> probeCopy,
|
|
|
|
acquireWriteUncached -> probeInvalidate,
|
|
|
|
acquireReadWordUncached -> probeCopy,
|
|
|
|
acquireWriteWordUncached -> probeInvalidate,
|
|
|
|
acquireAtomicUncached -> probeInvalidate,
|
|
|
|
acquireInvalidateOthers -> probeInvalidateOthers
|
2012-10-24 03:01:53 +02:00
|
|
|
))
|
|
|
|
}
|
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsOuterRead(a_type: UInt, global_state: UInt): Bool = {
|
2013-01-22 02:17:26 +01:00
|
|
|
(a_type != acquireWriteUncached && a_type != acquireInvalidateOthers)
|
2012-10-24 03:01:53 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsOuterWrite(a_type: UInt, global_state: UInt): Bool = {
|
2013-01-22 02:17:26 +01:00
|
|
|
(a_type === acquireWriteUncached || a_type === acquireWriteWordUncached || a_type === acquireAtomicUncached)
|
2012-10-24 03:01:53 +02:00
|
|
|
}
|
2013-08-12 19:36:44 +02:00
|
|
|
def needsAckReply(a_type: UInt, global_state: UInt): Bool = {
|
2013-01-22 02:17:26 +01:00
|
|
|
(a_type === acquireWriteUncached || a_type === acquireWriteWordUncached ||a_type === acquireInvalidateOthers)
|
2012-10-24 03:01:53 +02:00
|
|
|
}
|
2013-04-10 22:46:31 +02:00
|
|
|
def requiresAck(grant: Grant) = grant.g_type != grantVoluntaryAck
|
2013-01-29 01:39:45 +01:00
|
|
|
def requiresAck(release: Release) = Bool(false)
|
2013-03-26 00:20:12 +01:00
|
|
|
def needsSelfProbe(acq: Acquire) = Bool(false)
|
2013-03-01 03:13:41 +01:00
|
|
|
|
2013-08-12 19:36:44 +02:00
|
|
|
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool = (r_type === releaseVoluntaryInvalidateData)
|
2012-10-24 03:01:53 +02:00
|
|
|
}
|