Merge branch 'release-xacts'
Conflicts: src/package.scala src/uncore.scala
This commit is contained in:
commit
06f5de3b68
@ -28,23 +28,31 @@ abstract class CoherencePolicy {
|
|||||||
|
|
||||||
def getAcquireTypeOnPrimaryMiss(cmd: Bits, state: UFix): UFix
|
def getAcquireTypeOnPrimaryMiss(cmd: Bits, state: UFix): UFix
|
||||||
def getAcquireTypeOnSecondaryMiss(cmd: Bits, state: UFix, outstanding: Acquire): UFix
|
def getAcquireTypeOnSecondaryMiss(cmd: Bits, state: UFix, outstanding: Acquire): UFix
|
||||||
def getAcquireTypeOnCacheControl(cmd: Bits): Bits
|
def getReleaseTypeOnCacheControl(cmd: Bits): Bits
|
||||||
def getAcquireTypeOnWriteback(): Bits
|
def getReleaseTypeOnVoluntaryWriteback(): Bits
|
||||||
|
|
||||||
def newRelease (incoming: Probe, state: UFix): Release
|
def getVoluntaryWriteback(addr: UFix, client_id: UFix, master_id: UFix): Release
|
||||||
|
def newRelease (incoming: Probe, state: UFix, id: UFix): Release
|
||||||
|
|
||||||
def messageHasData (reply: Release): Bool
|
def messageHasData (rel: SourcedMessage): Bool
|
||||||
def messageHasData (acq: Acquire): Bool
|
|
||||||
def messageHasData (reply: Grant): Bool
|
|
||||||
def messageUpdatesDataArray (reply: Grant): Bool
|
def messageUpdatesDataArray (reply: Grant): Bool
|
||||||
def messageIsUncached(acq: Acquire): Bool
|
def messageIsUncached(acq: Acquire): Bool
|
||||||
|
|
||||||
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool
|
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool
|
||||||
|
def isVoluntary(rel: Release): Bool
|
||||||
|
def isVoluntary(gnt: Grant): Bool
|
||||||
def getGrantType(a_type: UFix, count: UFix): Bits
|
def getGrantType(a_type: UFix, count: UFix): Bits
|
||||||
|
def getGrantType(rel: Release, count: UFix): Bits
|
||||||
def getProbeType(a_type: UFix, global_state: UFix): UFix
|
def getProbeType(a_type: UFix, global_state: UFix): UFix
|
||||||
def needsMemRead(a_type: UFix, global_state: UFix): Bool
|
def needsOuterRead(a_type: UFix, global_state: UFix): Bool
|
||||||
def needsMemWrite(a_type: UFix, global_state: UFix): Bool
|
def needsOuterWrite(a_type: UFix, global_state: UFix): Bool
|
||||||
def needsAckReply(a_type: UFix, global_state: UFix): Bool
|
def needsAckReply(a_type: UFix, global_state: UFix): Bool
|
||||||
|
def needsSelfProbe(acq: Acquire): Bool
|
||||||
|
def requiresAck(grant: Grant): Bool
|
||||||
|
def requiresAck(release: Release): Bool
|
||||||
|
def pendingVoluntaryReleaseIsSufficient(r_type: UFix, p_type: UFix): Bool
|
||||||
|
|
||||||
|
def uFixListContains(list: List[UFix], elem: UFix): Bool = list.map(elem === _).reduceLeft(_||_)
|
||||||
}
|
}
|
||||||
|
|
||||||
trait UncachedTransactions {
|
trait UncachedTransactions {
|
||||||
@ -61,28 +69,30 @@ abstract class CoherencePolicyWithUncached extends CoherencePolicy with Uncached
|
|||||||
abstract class IncoherentPolicy extends CoherencePolicy {
|
abstract class IncoherentPolicy extends CoherencePolicy {
|
||||||
// UNIMPLEMENTED
|
// UNIMPLEMENTED
|
||||||
def newStateOnProbe(incoming: Probe, state: UFix): Bits = state
|
def newStateOnProbe(incoming: Probe, state: UFix): Bits = state
|
||||||
def newRelease (incoming: Probe, state: UFix): Release = {
|
def newRelease (incoming: Probe, state: UFix, id: UFix): Release = Release( UFix(0), UFix(0), UFix(0), UFix(0))
|
||||||
val reply = new Release
|
|
||||||
reply.r_type := UFix(0)
|
|
||||||
reply.master_xact_id := UFix(0)
|
|
||||||
reply
|
|
||||||
}
|
|
||||||
def messageHasData (reply: Release) = Bool(false)
|
|
||||||
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool = Bool(false)
|
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool = Bool(false)
|
||||||
def getGrantType(a_type: UFix, count: UFix): Bits = Bits(0)
|
def getGrantType(a_type: UFix, count: UFix): Bits = Bits(0)
|
||||||
|
def getGrantType(rel: Release, count: UFix): Bits = Bits(0)
|
||||||
def getProbeType(a_type: UFix, global_state: UFix): UFix = UFix(0)
|
def getProbeType(a_type: UFix, global_state: UFix): UFix = UFix(0)
|
||||||
def needsMemRead(a_type: UFix, global_state: UFix): Bool = Bool(false)
|
def needsOuterRead(a_type: UFix, global_state: UFix): Bool = Bool(false)
|
||||||
def needsMemWrite(a_type: UFix, global_state: UFix): Bool = Bool(false)
|
def needsOuterWrite(a_type: UFix, global_state: UFix): Bool = Bool(false)
|
||||||
def needsAckReply(a_type: UFix, global_state: UFix): Bool = Bool(false)
|
def needsAckReply(a_type: UFix, global_state: UFix): Bool = Bool(false)
|
||||||
|
def needsSelfProbe(acq: Acquire) = Bool(false)
|
||||||
|
def requiresAck(grant: Grant) = Bool(true)
|
||||||
|
def requiresAck(release: Release) = Bool(false)
|
||||||
|
def pendingVoluntaryReleaseIsSufficient(r_type: UFix, p_type: UFix): Bool = Bool(false)
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
class ThreeStateIncoherence extends IncoherentPolicy {
|
class ThreeStateIncoherence extends IncoherentPolicy {
|
||||||
val tileInvalid :: tileClean :: tileDirty :: Nil = Enum(3){ UFix() }
|
val tileInvalid :: tileClean :: tileDirty :: Nil = Enum(3){ UFix() }
|
||||||
val acquireReadClean :: acquireReadDirty :: acquireWriteback :: Nil = Enum(3){ UFix() }
|
val acquireReadClean :: acquireReadDirty :: acquireWriteback :: Nil = Enum(3){ UFix() }
|
||||||
val grantData :: grantAck :: Nil = Enum(2){ UFix() }
|
val grantVoluntaryAck :: grantData :: grantAck :: Nil = Enum(3){ UFix() }
|
||||||
val releaseInvalidateAck :: Nil = Enum(1){ UFix() }
|
val releaseVoluntaryInvalidateData :: releaseInvalidateAck :: Nil = Enum(2){ UFix() }
|
||||||
val uncachedTypeList = List()
|
val uncachedAcquireTypeList = List()
|
||||||
val hasDataTypeList = List(acquireWriteback)
|
val hasDataAcquireTypeList = List(acquireWriteback)
|
||||||
|
val hasDataReleaseTypeList = List(acquireWriteback)
|
||||||
|
val hasDataGrantTypeList = List(grantData)
|
||||||
|
|
||||||
def isHit ( cmd: Bits, state: UFix): Bool = (state === tileClean || state === tileDirty)
|
def isHit ( cmd: Bits, state: UFix): Bool = (state === tileClean || state === tileDirty)
|
||||||
def isValid (state: UFix): Bool = state != tileInvalid
|
def isValid (state: UFix): Bool = state != tileInvalid
|
||||||
@ -106,6 +116,10 @@ class ThreeStateIncoherence extends IncoherentPolicy {
|
|||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
def getVoluntaryWriteback(addr: UFix, client_id: UFix, master_id: UFix) = Release(releaseVoluntaryInvalidateData, addr, client_id, master_id)
|
||||||
|
def isVoluntary(rel: Release) = rel.r_type === releaseVoluntaryInvalidateData
|
||||||
|
def isVoluntary(gnt: Grant) = gnt.g_type === grantVoluntaryAck
|
||||||
|
|
||||||
def getAcquireTypeOnPrimaryMiss(cmd: Bits, state: UFix): UFix = {
|
def getAcquireTypeOnPrimaryMiss(cmd: Bits, state: UFix): UFix = {
|
||||||
val (read, write) = cpuCmdToRW(cmd)
|
val (read, write) = cpuCmdToRW(cmd)
|
||||||
Mux(write || cmd === M_PFW, acquireReadDirty, acquireReadClean)
|
Mux(write || cmd === M_PFW, acquireReadDirty, acquireReadClean)
|
||||||
@ -114,13 +128,17 @@ class ThreeStateIncoherence extends IncoherentPolicy {
|
|||||||
val (read, write) = cpuCmdToRW(cmd)
|
val (read, write) = cpuCmdToRW(cmd)
|
||||||
Mux(write, acquireReadDirty, outstanding.a_type)
|
Mux(write, acquireReadDirty, outstanding.a_type)
|
||||||
}
|
}
|
||||||
def getAcquireTypeOnCacheControl(cmd: Bits): Bits = acquireWriteback //TODO
|
def getReleaseTypeOnCacheControl(cmd: Bits): Bits = releaseVoluntaryInvalidateData // TODO
|
||||||
def getAcquireTypeOnWriteback(): Bits = acquireWriteback
|
def getReleaseTypeOnVoluntaryWriteback(): Bits = releaseVoluntaryInvalidateData
|
||||||
|
|
||||||
def messageHasData (init: Acquire): Bool = hasDataTypeList.map(t => init.a_type === t).reduceLeft(_||_)
|
def messageHasData( msg: SourcedMessage ) = msg match {
|
||||||
def messageHasData (reply: Grant) = (reply.g_type === grantData)
|
case acq: Acquire => uFixListContains(hasDataAcquireTypeList, acq.a_type)
|
||||||
|
case grant: Grant => uFixListContains(hasDataGrantTypeList, grant.g_type)
|
||||||
|
case rel: Release => Bool(false)
|
||||||
|
case _ => Bool(false)
|
||||||
|
}
|
||||||
def messageUpdatesDataArray (reply: Grant) = (reply.g_type === grantData)
|
def messageUpdatesDataArray (reply: Grant) = (reply.g_type === grantData)
|
||||||
def messageIsUncached(init: Acquire): Bool = uncachedTypeList.map(t => init.a_type === t).reduceLeft(_||_)
|
def messageIsUncached(acq: Acquire): Bool = uFixListContains(uncachedAcquireTypeList, acq.a_type)
|
||||||
}
|
}
|
||||||
|
|
||||||
class MICoherence extends CoherencePolicyWithUncached {
|
class MICoherence extends CoherencePolicyWithUncached {
|
||||||
@ -129,11 +147,13 @@ class MICoherence extends CoherencePolicyWithUncached {
|
|||||||
val globalInvalid :: globalValid :: Nil = Enum(2){ UFix() }
|
val globalInvalid :: globalValid :: Nil = Enum(2){ UFix() }
|
||||||
|
|
||||||
val acquireReadExclusive :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: Nil = Enum(6){ UFix() }
|
val acquireReadExclusive :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: Nil = Enum(6){ UFix() }
|
||||||
val grantReadExclusive :: grantReadUncached :: grantWriteUncached :: grantReadWordUncached :: grantWriteWordUncached :: grantAtomicUncached :: Nil = Enum(6){ UFix() }
|
val grantVoluntaryAck :: grantReadExclusive :: grantReadUncached :: grantWriteUncached :: grantReadWordUncached :: grantWriteWordUncached :: grantAtomicUncached :: Nil = Enum(7){ UFix() }
|
||||||
val probeInvalidate :: probeCopy :: Nil = Enum(2){ UFix() }
|
val probeInvalidate :: probeCopy :: Nil = Enum(2){ UFix() }
|
||||||
val releaseInvalidateData :: releaseCopyData :: releaseInvalidateAck :: releaseCopyAck :: Nil = Enum(4){ UFix() }
|
val releaseVoluntaryInvalidateData :: releaseInvalidateData :: releaseCopyData :: releaseInvalidateAck :: releaseCopyAck :: Nil = Enum(5){ UFix() }
|
||||||
val uncachedTypeList = List(acquireReadUncached, acquireWriteUncached, grantReadWordUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
val uncachedAcquireTypeList = List(acquireReadUncached, acquireWriteUncached, acquireReadWordUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
||||||
val hasDataTypeList = List(acquireWriteUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
val hasDataAcquireTypeList = List(acquireWriteUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
||||||
|
val hasDataReleaseTypeList = List(releaseVoluntaryInvalidateData, releaseInvalidateData, releaseCopyData)
|
||||||
|
val hasDataGrantTypeList = List(grantReadExclusive, grantReadUncached, grantReadWordUncached, grantAtomicUncached)
|
||||||
|
|
||||||
def isHit (cmd: Bits, state: UFix): Bool = state != tileInvalid
|
def isHit (cmd: Bits, state: UFix): Bool = state != tileInvalid
|
||||||
def isValid (state: UFix): Bool = state != tileInvalid
|
def isValid (state: UFix): Bool = state != tileInvalid
|
||||||
@ -180,15 +200,17 @@ class MICoherence extends CoherencePolicyWithUncached {
|
|||||||
def getUncachedReadWordAcquire(addr: UFix, id: UFix) = Acquire(acquireReadWordUncached, addr, id)
|
def getUncachedReadWordAcquire(addr: UFix, id: UFix) = Acquire(acquireReadWordUncached, addr, id)
|
||||||
def getUncachedWriteWordAcquire(addr: UFix, id: UFix, write_mask: Bits) = Acquire(acquireWriteWordUncached, addr, id, write_mask)
|
def getUncachedWriteWordAcquire(addr: UFix, id: UFix, write_mask: Bits) = Acquire(acquireWriteWordUncached, addr, id, write_mask)
|
||||||
def getUncachedAtomicAcquire(addr: UFix, id: UFix, subword_addr: UFix, atomic_op: UFix) = Acquire(acquireAtomicUncached, addr, id, subword_addr, atomic_op)
|
def getUncachedAtomicAcquire(addr: UFix, id: UFix, subword_addr: UFix, atomic_op: UFix) = Acquire(acquireAtomicUncached, addr, id, subword_addr, atomic_op)
|
||||||
|
def getVoluntaryWriteback(addr: UFix, client_id: UFix, master_id: UFix) = Release(releaseVoluntaryInvalidateData, addr, client_id, master_id)
|
||||||
def isUncachedReadTransaction(acq: Acquire) = acq.a_type === acquireReadUncached
|
def isUncachedReadTransaction(acq: Acquire) = acq.a_type === acquireReadUncached
|
||||||
|
def isVoluntary(rel: Release) = rel.r_type === releaseVoluntaryInvalidateData
|
||||||
|
def isVoluntary(gnt: Grant) = gnt.g_type === grantVoluntaryAck
|
||||||
|
|
||||||
def getAcquireTypeOnPrimaryMiss(cmd: Bits, state: UFix): UFix = acquireReadExclusive
|
def getAcquireTypeOnPrimaryMiss(cmd: Bits, state: UFix): UFix = acquireReadExclusive
|
||||||
def getAcquireTypeOnSecondaryMiss(cmd: Bits, state: UFix, outstanding: Acquire): UFix = acquireReadExclusive
|
def getAcquireTypeOnSecondaryMiss(cmd: Bits, state: UFix, outstanding: Acquire): UFix = acquireReadExclusive
|
||||||
def getAcquireTypeOnCacheControl(cmd: Bits): Bits = acquireWriteUncached
|
def getReleaseTypeOnCacheControl(cmd: Bits): Bits = releaseVoluntaryInvalidateData // TODO
|
||||||
def getAcquireTypeOnWriteback(): Bits = getAcquireTypeOnCacheControl(M_INV)
|
def getReleaseTypeOnVoluntaryWriteback(): Bits = getReleaseTypeOnCacheControl(M_INV)
|
||||||
|
|
||||||
def newRelease (incoming: Probe, state: UFix): Release = {
|
def newRelease (incoming: Probe, state: UFix, id: UFix): Release = {
|
||||||
val reply = new Release
|
|
||||||
val with_data = MuxLookup(incoming.p_type, releaseInvalidateData, Array(
|
val with_data = MuxLookup(incoming.p_type, releaseInvalidateData, Array(
|
||||||
probeInvalidate -> releaseInvalidateData,
|
probeInvalidate -> releaseInvalidateData,
|
||||||
probeCopy -> releaseCopyData
|
probeCopy -> releaseCopyData
|
||||||
@ -197,23 +219,19 @@ class MICoherence extends CoherencePolicyWithUncached {
|
|||||||
probeInvalidate -> releaseInvalidateAck,
|
probeInvalidate -> releaseInvalidateAck,
|
||||||
probeCopy -> releaseCopyAck
|
probeCopy -> releaseCopyAck
|
||||||
))
|
))
|
||||||
reply.r_type := Mux(needsWriteback(state), with_data, without_data)
|
Release( Mux(needsWriteback(state), with_data, without_data), incoming.addr, id, incoming.master_xact_id)
|
||||||
reply.master_xact_id := incoming.master_xact_id
|
|
||||||
reply
|
|
||||||
}
|
}
|
||||||
|
|
||||||
def messageHasData (reply: Release): Bool = {
|
def messageHasData(msg: SourcedMessage) = msg match {
|
||||||
(reply.r_type === releaseInvalidateData ||
|
case acq: Acquire => uFixListContains(hasDataAcquireTypeList, acq.a_type)
|
||||||
reply.r_type === releaseCopyData)
|
case grant: Grant => uFixListContains(hasDataGrantTypeList, grant.g_type)
|
||||||
}
|
case rel: Release => uFixListContains(hasDataReleaseTypeList, rel.r_type)
|
||||||
def messageHasData (acq: Acquire): Bool = hasDataTypeList.map(t => acq.a_type === t).reduceLeft(_||_)
|
case _ => Bool(false)
|
||||||
def messageHasData (reply: Grant): Bool = {
|
|
||||||
(reply.g_type != grantWriteUncached && reply.g_type != grantWriteWordUncached)
|
|
||||||
}
|
}
|
||||||
def messageUpdatesDataArray (reply: Grant): Bool = {
|
def messageUpdatesDataArray (reply: Grant): Bool = {
|
||||||
(reply.g_type === grantReadExclusive)
|
(reply.g_type === grantReadExclusive)
|
||||||
}
|
}
|
||||||
def messageIsUncached(acq: Acquire): Bool = uncachedTypeList.map(t => acq.a_type === t).reduceLeft(_||_)
|
def messageIsUncached(acq: Acquire): Bool = uFixListContains(uncachedAcquireTypeList, acq.a_type)
|
||||||
|
|
||||||
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool = (addr1 === addr2)
|
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool = (addr1 === addr2)
|
||||||
|
|
||||||
@ -228,6 +246,12 @@ class MICoherence extends CoherencePolicyWithUncached {
|
|||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
def getGrantType(rel: Release, count: UFix): Bits = {
|
||||||
|
MuxLookup(rel.r_type, grantReadUncached, Array(
|
||||||
|
releaseVoluntaryInvalidateData -> grantVoluntaryAck
|
||||||
|
))
|
||||||
|
}
|
||||||
|
|
||||||
def getProbeType(a_type: UFix, global_state: UFix): UFix = {
|
def getProbeType(a_type: UFix, global_state: UFix): UFix = {
|
||||||
MuxLookup(a_type, probeCopy, Array(
|
MuxLookup(a_type, probeCopy, Array(
|
||||||
acquireReadExclusive -> probeInvalidate,
|
acquireReadExclusive -> probeInvalidate,
|
||||||
@ -239,15 +263,19 @@ class MICoherence extends CoherencePolicyWithUncached {
|
|||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
def needsMemRead(a_type: UFix, global_state: UFix): Bool = {
|
def needsOuterRead(a_type: UFix, global_state: UFix): Bool = {
|
||||||
(a_type != acquireWriteUncached)
|
(a_type != acquireWriteUncached)
|
||||||
}
|
}
|
||||||
def needsMemWrite(a_type: UFix, global_state: UFix): Bool = {
|
def needsOuterWrite(a_type: UFix, global_state: UFix): Bool = {
|
||||||
(a_type === acquireWriteUncached)
|
(a_type === acquireWriteUncached)
|
||||||
}
|
}
|
||||||
def needsAckReply(a_type: UFix, global_state: UFix): Bool = {
|
def needsAckReply(a_type: UFix, global_state: UFix): Bool = {
|
||||||
(a_type === acquireWriteUncached)
|
(a_type === acquireWriteUncached)
|
||||||
}
|
}
|
||||||
|
def requiresAck(grant: Grant) = Bool(true)
|
||||||
|
def requiresAck(release: Release) = Bool(false)
|
||||||
|
def needsSelfProbe(acq: Acquire) = acq.a_type === acquireReadUncached
|
||||||
|
def pendingVoluntaryReleaseIsSufficient(r_type: UFix, p_type: UFix): Bool = (r_type === releaseVoluntaryInvalidateData)
|
||||||
}
|
}
|
||||||
|
|
||||||
class MEICoherence extends CoherencePolicyWithUncached {
|
class MEICoherence extends CoherencePolicyWithUncached {
|
||||||
@ -256,11 +284,14 @@ class MEICoherence extends CoherencePolicyWithUncached {
|
|||||||
val globalInvalid :: globalExclusiveClean :: Nil = Enum(2){ UFix() }
|
val globalInvalid :: globalExclusiveClean :: Nil = Enum(2){ UFix() }
|
||||||
|
|
||||||
val acquireReadExclusiveClean :: acquireReadExclusiveDirty :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: Nil = Enum(7){ UFix() }
|
val acquireReadExclusiveClean :: acquireReadExclusiveDirty :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: Nil = Enum(7){ UFix() }
|
||||||
val grantReadExclusive :: grantReadUncached :: grantWriteUncached :: grantReadExclusiveAck :: grantReadWordUncached :: grantWriteWordUncached :: grantAtomicUncached :: Nil = Enum(7){ UFix() }
|
val grantVoluntaryAck :: grantReadExclusive :: grantReadUncached :: grantWriteUncached :: grantReadExclusiveAck :: grantReadWordUncached :: grantWriteWordUncached :: grantAtomicUncached :: Nil = Enum(8){ UFix() }
|
||||||
val probeInvalidate :: probeDowngrade :: probeCopy :: Nil = Enum(3){ UFix() }
|
val probeInvalidate :: probeDowngrade :: probeCopy :: Nil = Enum(3){ UFix() }
|
||||||
val releaseInvalidateData :: releaseDowngradeData :: releaseCopyData :: releaseInvalidateAck :: releaseDowngradeAck :: releaseCopyAck :: Nil = Enum(6){ UFix() }
|
val releaseVoluntaryInvalidateData :: releaseInvalidateData :: releaseDowngradeData :: releaseCopyData :: releaseInvalidateAck :: releaseDowngradeAck :: releaseCopyAck :: Nil = Enum(7){ UFix() }
|
||||||
val uncachedTypeList = List(acquireReadUncached, acquireWriteUncached, grantReadWordUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
|
||||||
val hasDataTypeList = List(acquireWriteUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
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)
|
||||||
|
|
||||||
def isHit (cmd: Bits, state: UFix): Bool = state != tileInvalid
|
def isHit (cmd: Bits, state: UFix): Bool = state != tileInvalid
|
||||||
def isValid (state: UFix): Bool = state != tileInvalid
|
def isValid (state: UFix): Bool = state != tileInvalid
|
||||||
@ -316,7 +347,10 @@ class MEICoherence extends CoherencePolicyWithUncached {
|
|||||||
def getUncachedReadWordAcquire(addr: UFix, id: UFix) = Acquire(acquireReadWordUncached, addr, id)
|
def getUncachedReadWordAcquire(addr: UFix, id: UFix) = Acquire(acquireReadWordUncached, addr, id)
|
||||||
def getUncachedWriteWordAcquire(addr: UFix, id: UFix, write_mask: Bits) = Acquire(acquireWriteWordUncached, addr, id, write_mask)
|
def getUncachedWriteWordAcquire(addr: UFix, id: UFix, write_mask: Bits) = Acquire(acquireWriteWordUncached, addr, id, write_mask)
|
||||||
def getUncachedAtomicAcquire(addr: UFix, id: UFix, subword_addr: UFix, atomic_op: UFix) = Acquire(acquireAtomicUncached, addr, id, subword_addr, atomic_op)
|
def getUncachedAtomicAcquire(addr: UFix, id: UFix, subword_addr: UFix, atomic_op: UFix) = Acquire(acquireAtomicUncached, addr, id, subword_addr, atomic_op)
|
||||||
|
def getVoluntaryWriteback(addr: UFix, client_id: UFix, master_id: UFix) = Release(releaseVoluntaryInvalidateData, addr, client_id, master_id)
|
||||||
def isUncachedReadTransaction(acq: Acquire) = acq.a_type === acquireReadUncached
|
def isUncachedReadTransaction(acq: Acquire) = acq.a_type === acquireReadUncached
|
||||||
|
def isVoluntary(rel: Release) = rel.r_type === releaseVoluntaryInvalidateData
|
||||||
|
def isVoluntary(gnt: Grant) = gnt.g_type === grantVoluntaryAck
|
||||||
|
|
||||||
def getAcquireTypeOnPrimaryMiss(cmd: Bits, state: UFix): UFix = {
|
def getAcquireTypeOnPrimaryMiss(cmd: Bits, state: UFix): UFix = {
|
||||||
val (read, write) = cpuCmdToRW(cmd)
|
val (read, write) = cpuCmdToRW(cmd)
|
||||||
@ -326,11 +360,10 @@ class MEICoherence extends CoherencePolicyWithUncached {
|
|||||||
val (read, write) = cpuCmdToRW(cmd)
|
val (read, write) = cpuCmdToRW(cmd)
|
||||||
Mux(write, acquireReadExclusiveDirty, outstanding.a_type)
|
Mux(write, acquireReadExclusiveDirty, outstanding.a_type)
|
||||||
}
|
}
|
||||||
def getAcquireTypeOnCacheControl(cmd: Bits): Bits = acquireWriteUncached
|
def getReleaseTypeOnCacheControl(cmd: Bits): Bits = releaseVoluntaryInvalidateData // TODO
|
||||||
def getAcquireTypeOnWriteback(): Bits = getAcquireTypeOnCacheControl(M_INV)
|
def getReleaseTypeOnVoluntaryWriteback(): Bits = getReleaseTypeOnCacheControl(M_INV)
|
||||||
|
|
||||||
def newRelease (incoming: Probe, state: UFix): Release = {
|
def newRelease (incoming: Probe, state: UFix, id: UFix): Release = {
|
||||||
val reply = new Release
|
|
||||||
val with_data = MuxLookup(incoming.p_type, releaseInvalidateData, Array(
|
val with_data = MuxLookup(incoming.p_type, releaseInvalidateData, Array(
|
||||||
probeInvalidate -> releaseInvalidateData,
|
probeInvalidate -> releaseInvalidateData,
|
||||||
probeDowngrade -> releaseDowngradeData,
|
probeDowngrade -> releaseDowngradeData,
|
||||||
@ -341,24 +374,19 @@ class MEICoherence extends CoherencePolicyWithUncached {
|
|||||||
probeDowngrade -> releaseDowngradeAck,
|
probeDowngrade -> releaseDowngradeAck,
|
||||||
probeCopy -> releaseCopyAck
|
probeCopy -> releaseCopyAck
|
||||||
))
|
))
|
||||||
reply.r_type := Mux(needsWriteback(state), with_data, without_data)
|
Release( Mux(needsWriteback(state), with_data, without_data), incoming.addr, id, incoming.master_xact_id)
|
||||||
reply.master_xact_id := incoming.master_xact_id
|
|
||||||
reply
|
|
||||||
}
|
}
|
||||||
|
|
||||||
def messageHasData (reply: Release): Bool = {
|
def messageHasData(msg: SourcedMessage) = msg match {
|
||||||
(reply.r_type === releaseInvalidateData ||
|
case acq: Acquire => uFixListContains(hasDataAcquireTypeList, acq.a_type)
|
||||||
reply.r_type === releaseDowngradeData ||
|
case grant: Grant => uFixListContains(hasDataGrantTypeList, grant.g_type)
|
||||||
reply.r_type === releaseCopyData)
|
case rel: Release => uFixListContains(hasDataReleaseTypeList, rel.r_type)
|
||||||
}
|
case _ => Bool(false)
|
||||||
def messageHasData (acq: Acquire): Bool = hasDataTypeList.map(t => acq.a_type === t).reduceLeft(_||_)
|
|
||||||
def messageHasData (reply: Grant): Bool = {
|
|
||||||
(reply.g_type != grantWriteUncached && reply.g_type != grantReadExclusiveAck && reply.g_type != grantWriteWordUncached)
|
|
||||||
}
|
}
|
||||||
def messageUpdatesDataArray (reply: Grant): Bool = {
|
def messageUpdatesDataArray (reply: Grant): Bool = {
|
||||||
(reply.g_type === grantReadExclusive)
|
(reply.g_type === grantReadExclusive)
|
||||||
}
|
}
|
||||||
def messageIsUncached(init: Acquire): Bool = uncachedTypeList.map(t => init.a_type === t).reduceLeft(_||_)
|
def messageIsUncached(acq: Acquire): Bool = uFixListContains(uncachedAcquireTypeList, acq.a_type)
|
||||||
|
|
||||||
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool = (addr1 === addr2)
|
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool = (addr1 === addr2)
|
||||||
|
|
||||||
@ -373,6 +401,12 @@ class MEICoherence extends CoherencePolicyWithUncached {
|
|||||||
acquireAtomicUncached -> grantAtomicUncached
|
acquireAtomicUncached -> grantAtomicUncached
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
def getGrantType(rel: Release, count: UFix): Bits = {
|
||||||
|
MuxLookup(rel.r_type, grantReadUncached, Array(
|
||||||
|
releaseVoluntaryInvalidateData -> grantVoluntaryAck
|
||||||
|
))
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
def getProbeType(a_type: UFix, global_state: UFix): UFix = {
|
def getProbeType(a_type: UFix, global_state: UFix): UFix = {
|
||||||
MuxLookup(a_type, probeCopy, Array(
|
MuxLookup(a_type, probeCopy, Array(
|
||||||
@ -386,15 +420,20 @@ class MEICoherence extends CoherencePolicyWithUncached {
|
|||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
def needsMemRead(a_type: UFix, global_state: UFix): Bool = {
|
def needsOuterRead(a_type: UFix, global_state: UFix): Bool = {
|
||||||
(a_type != acquireWriteUncached)
|
(a_type != acquireWriteUncached)
|
||||||
}
|
}
|
||||||
def needsMemWrite(a_type: UFix, global_state: UFix): Bool = {
|
def needsOuterWrite(a_type: UFix, global_state: UFix): Bool = {
|
||||||
(a_type === acquireWriteUncached)
|
(a_type === acquireWriteUncached)
|
||||||
}
|
}
|
||||||
def needsAckReply(a_type: UFix, global_state: UFix): Bool = {
|
def needsAckReply(a_type: UFix, global_state: UFix): Bool = {
|
||||||
(a_type === acquireWriteUncached)
|
(a_type === acquireWriteUncached)
|
||||||
}
|
}
|
||||||
|
def requiresAck(grant: Grant) = Bool(true)
|
||||||
|
def requiresAck(release: Release) = Bool(false)
|
||||||
|
def needsSelfProbe(acq: Acquire) = acq.a_type === acquireReadUncached
|
||||||
|
|
||||||
|
def pendingVoluntaryReleaseIsSufficient(r_type: UFix, p_type: UFix): Bool = (r_type === releaseVoluntaryInvalidateData)
|
||||||
}
|
}
|
||||||
|
|
||||||
class MSICoherence extends CoherencePolicyWithUncached {
|
class MSICoherence extends CoherencePolicyWithUncached {
|
||||||
@ -403,11 +442,13 @@ class MSICoherence extends CoherencePolicyWithUncached {
|
|||||||
val globalInvalid :: globalShared :: globalExclusive :: Nil = Enum(3){ UFix() }
|
val globalInvalid :: globalShared :: globalExclusive :: Nil = Enum(3){ UFix() }
|
||||||
|
|
||||||
val acquireReadShared :: acquireReadExclusive :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: Nil = Enum(7){ UFix() }
|
val acquireReadShared :: acquireReadExclusive :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: Nil = Enum(7){ UFix() }
|
||||||
val grantReadShared :: grantReadExclusive :: grantReadUncached :: grantWriteUncached :: grantReadExclusiveAck :: grantReadWordUncached :: grantWriteWordUncached :: grantAtomicUncached :: Nil = Enum(8){ UFix() }
|
val grantVoluntaryAck :: grantReadShared :: grantReadExclusive :: grantReadUncached :: grantWriteUncached :: grantReadExclusiveAck :: grantReadWordUncached :: grantWriteWordUncached :: grantAtomicUncached :: Nil = Enum(9){ UFix() }
|
||||||
val probeInvalidate :: probeDowngrade :: probeCopy :: Nil = Enum(3){ UFix() }
|
val probeInvalidate :: probeDowngrade :: probeCopy :: Nil = Enum(3){ UFix() }
|
||||||
val releaseInvalidateData :: releaseDowngradeData :: releaseCopyData :: releaseInvalidateAck :: releaseDowngradeAck :: releaseCopyAck :: Nil = Enum(6){ UFix() }
|
val releaseVoluntaryInvalidateData :: releaseInvalidateData :: releaseDowngradeData :: releaseCopyData :: releaseInvalidateAck :: releaseDowngradeAck :: releaseCopyAck :: Nil = Enum(7){ UFix() }
|
||||||
val uncachedTypeList = List(acquireReadUncached, acquireWriteUncached, grantReadWordUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
val uncachedAcquireTypeList = List(acquireReadUncached, acquireWriteUncached, acquireReadWordUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
||||||
val hasDataTypeList = List(acquireWriteUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
val hasDataAcquireTypeList = List(acquireWriteUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
||||||
|
val hasDataReleaseTypeList = List(releaseVoluntaryInvalidateData, releaseInvalidateData, releaseDowngradeData, releaseCopyData)
|
||||||
|
val hasDataGrantTypeList = List(grantReadShared, grantReadExclusive, grantReadUncached, grantReadWordUncached, grantAtomicUncached)
|
||||||
|
|
||||||
def isHit (cmd: Bits, state: UFix): Bool = {
|
def isHit (cmd: Bits, state: UFix): Bool = {
|
||||||
val (read, write) = cpuCmdToRW(cmd)
|
val (read, write) = cpuCmdToRW(cmd)
|
||||||
@ -470,7 +511,10 @@ class MSICoherence extends CoherencePolicyWithUncached {
|
|||||||
def getUncachedReadWordAcquire(addr: UFix, id: UFix) = Acquire(acquireReadWordUncached, addr, id)
|
def getUncachedReadWordAcquire(addr: UFix, id: UFix) = Acquire(acquireReadWordUncached, addr, id)
|
||||||
def getUncachedWriteWordAcquire(addr: UFix, id: UFix, write_mask: Bits) = Acquire(acquireWriteWordUncached, addr, id, write_mask)
|
def getUncachedWriteWordAcquire(addr: UFix, id: UFix, write_mask: Bits) = Acquire(acquireWriteWordUncached, addr, id, write_mask)
|
||||||
def getUncachedAtomicAcquire(addr: UFix, id: UFix, subword_addr: UFix, atomic_op: UFix) = Acquire(acquireAtomicUncached, addr, id, subword_addr, atomic_op)
|
def getUncachedAtomicAcquire(addr: UFix, id: UFix, subword_addr: UFix, atomic_op: UFix) = Acquire(acquireAtomicUncached, addr, id, subword_addr, atomic_op)
|
||||||
|
def getVoluntaryWriteback(addr: UFix, client_id: UFix, master_id: UFix) = Release(releaseVoluntaryInvalidateData, addr, client_id, master_id)
|
||||||
def isUncachedReadTransaction(acq: Acquire) = acq.a_type === acquireReadUncached
|
def isUncachedReadTransaction(acq: Acquire) = acq.a_type === acquireReadUncached
|
||||||
|
def isVoluntary(rel: Release) = rel.r_type === releaseVoluntaryInvalidateData
|
||||||
|
def isVoluntary(gnt: Grant) = gnt.g_type === grantVoluntaryAck
|
||||||
|
|
||||||
def getAcquireTypeOnPrimaryMiss(cmd: Bits, state: UFix): UFix = {
|
def getAcquireTypeOnPrimaryMiss(cmd: Bits, state: UFix): UFix = {
|
||||||
val (read, write) = cpuCmdToRW(cmd)
|
val (read, write) = cpuCmdToRW(cmd)
|
||||||
@ -480,11 +524,10 @@ class MSICoherence extends CoherencePolicyWithUncached {
|
|||||||
val (read, write) = cpuCmdToRW(cmd)
|
val (read, write) = cpuCmdToRW(cmd)
|
||||||
Mux(write, acquireReadExclusive, outstanding.a_type)
|
Mux(write, acquireReadExclusive, outstanding.a_type)
|
||||||
}
|
}
|
||||||
def getAcquireTypeOnCacheControl(cmd: Bits): Bits = acquireWriteUncached
|
def getReleaseTypeOnCacheControl(cmd: Bits): Bits = releaseVoluntaryInvalidateData // TODO
|
||||||
def getAcquireTypeOnWriteback(): Bits = getAcquireTypeOnCacheControl(M_INV)
|
def getReleaseTypeOnVoluntaryWriteback(): Bits = getReleaseTypeOnCacheControl(M_INV)
|
||||||
|
|
||||||
def newRelease (incoming: Probe, state: UFix): Release = {
|
def newRelease (incoming: Probe, state: UFix, id: UFix): Release = {
|
||||||
val reply = new Release
|
|
||||||
val with_data = MuxLookup(incoming.p_type, releaseInvalidateData, Array(
|
val with_data = MuxLookup(incoming.p_type, releaseInvalidateData, Array(
|
||||||
probeInvalidate -> releaseInvalidateData,
|
probeInvalidate -> releaseInvalidateData,
|
||||||
probeDowngrade -> releaseDowngradeData,
|
probeDowngrade -> releaseDowngradeData,
|
||||||
@ -495,24 +538,19 @@ class MSICoherence extends CoherencePolicyWithUncached {
|
|||||||
probeDowngrade -> releaseDowngradeAck,
|
probeDowngrade -> releaseDowngradeAck,
|
||||||
probeCopy -> releaseCopyAck
|
probeCopy -> releaseCopyAck
|
||||||
))
|
))
|
||||||
reply.r_type := Mux(needsWriteback(state), with_data, without_data)
|
Release( Mux(needsWriteback(state), with_data, without_data), incoming.addr, id, incoming.master_xact_id)
|
||||||
reply.master_xact_id := incoming.master_xact_id
|
|
||||||
reply
|
|
||||||
}
|
}
|
||||||
|
|
||||||
def messageHasData (reply: Release): Bool = {
|
def messageHasData(msg: SourcedMessage) = msg match {
|
||||||
(reply.r_type === releaseInvalidateData ||
|
case acq: Acquire => uFixListContains(hasDataAcquireTypeList, acq.a_type)
|
||||||
reply.r_type === releaseDowngradeData ||
|
case grant: Grant => uFixListContains(hasDataGrantTypeList, grant.g_type)
|
||||||
reply.r_type === releaseCopyData)
|
case rel: Release => uFixListContains(hasDataReleaseTypeList, rel.r_type)
|
||||||
}
|
case _ => Bool(false)
|
||||||
def messageHasData (acq: Acquire): Bool = hasDataTypeList.map(t => acq.a_type === t).reduceLeft(_||_)
|
|
||||||
def messageHasData (reply: Grant): Bool = {
|
|
||||||
(reply.g_type != grantWriteUncached && reply.g_type != grantReadExclusiveAck && reply.g_type != grantWriteWordUncached)
|
|
||||||
}
|
}
|
||||||
def messageUpdatesDataArray (reply: Grant): Bool = {
|
def messageUpdatesDataArray (reply: Grant): Bool = {
|
||||||
(reply.g_type === grantReadShared || reply.g_type === grantReadExclusive)
|
(reply.g_type === grantReadShared || reply.g_type === grantReadExclusive)
|
||||||
}
|
}
|
||||||
def messageIsUncached(acq: Acquire): Bool = uncachedTypeList.map(t => acq.a_type === t).reduceLeft(_||_)
|
def messageIsUncached(acq: Acquire): Bool = uFixListContains(uncachedAcquireTypeList, acq.a_type)
|
||||||
|
|
||||||
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool = (addr1 === addr2)
|
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool = (addr1 === addr2)
|
||||||
|
|
||||||
@ -527,6 +565,12 @@ class MSICoherence extends CoherencePolicyWithUncached {
|
|||||||
acquireAtomicUncached -> grantAtomicUncached
|
acquireAtomicUncached -> grantAtomicUncached
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
def getGrantType(rel: Release, count: UFix): Bits = {
|
||||||
|
MuxLookup(rel.r_type, grantReadUncached, Array(
|
||||||
|
releaseVoluntaryInvalidateData -> grantVoluntaryAck
|
||||||
|
))
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
def getProbeType(a_type: UFix, global_state: UFix): UFix = {
|
def getProbeType(a_type: UFix, global_state: UFix): UFix = {
|
||||||
MuxLookup(a_type, probeCopy, Array(
|
MuxLookup(a_type, probeCopy, Array(
|
||||||
@ -537,15 +581,20 @@ class MSICoherence extends CoherencePolicyWithUncached {
|
|||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
def needsMemRead(a_type: UFix, global_state: UFix): Bool = {
|
def needsOuterRead(a_type: UFix, global_state: UFix): Bool = {
|
||||||
(a_type != acquireWriteUncached)
|
(a_type != acquireWriteUncached)
|
||||||
}
|
}
|
||||||
def needsMemWrite(a_type: UFix, global_state: UFix): Bool = {
|
def needsOuterWrite(a_type: UFix, global_state: UFix): Bool = {
|
||||||
(a_type === acquireWriteUncached)
|
(a_type === acquireWriteUncached)
|
||||||
}
|
}
|
||||||
def needsAckReply(a_type: UFix, global_state: UFix): Bool = {
|
def needsAckReply(a_type: UFix, global_state: UFix): Bool = {
|
||||||
(a_type === acquireWriteUncached)
|
(a_type === acquireWriteUncached)
|
||||||
}
|
}
|
||||||
|
def requiresAck(grant: Grant) = Bool(true)
|
||||||
|
def requiresAck(release: Release) = Bool(false)
|
||||||
|
def needsSelfProbe(acq: Acquire) = acq.a_type === acquireReadUncached
|
||||||
|
|
||||||
|
def pendingVoluntaryReleaseIsSufficient(r_type: UFix, p_type: UFix): Bool = (r_type === releaseVoluntaryInvalidateData)
|
||||||
}
|
}
|
||||||
|
|
||||||
class MESICoherence extends CoherencePolicyWithUncached {
|
class MESICoherence extends CoherencePolicyWithUncached {
|
||||||
@ -554,11 +603,14 @@ class MESICoherence extends CoherencePolicyWithUncached {
|
|||||||
val globalInvalid :: globalShared :: globalExclusiveClean :: Nil = Enum(3){ UFix() }
|
val globalInvalid :: globalShared :: globalExclusiveClean :: Nil = Enum(3){ UFix() }
|
||||||
|
|
||||||
val acquireReadShared :: acquireReadExclusive :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: Nil = Enum(7){ UFix() }
|
val acquireReadShared :: acquireReadExclusive :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: Nil = Enum(7){ UFix() }
|
||||||
val grantReadShared :: grantReadExclusive :: grantReadUncached :: grantWriteUncached :: grantReadExclusiveAck :: grantReadWordUncached :: grantWriteWordUncached :: grantAtomicUncached :: Nil = Enum(8){ UFix() }
|
val grantVoluntaryAck :: grantReadShared :: grantReadExclusive :: grantReadUncached :: grantWriteUncached :: grantReadExclusiveAck :: grantReadWordUncached :: grantWriteWordUncached :: grantAtomicUncached :: Nil = Enum(9){ UFix() }
|
||||||
val probeInvalidate :: probeDowngrade :: probeCopy :: Nil = Enum(3){ UFix() }
|
val probeInvalidate :: probeDowngrade :: probeCopy :: Nil = Enum(3){ UFix() }
|
||||||
val releaseInvalidateData :: releaseDowngradeData :: releaseCopyData :: releaseInvalidateAck :: releaseDowngradeAck :: releaseCopyAck :: Nil = Enum(6){ UFix() }
|
val releaseVoluntaryInvalidateData :: releaseInvalidateData :: releaseDowngradeData :: releaseCopyData :: releaseInvalidateAck :: releaseDowngradeAck :: releaseCopyAck :: Nil = Enum(7){ UFix() }
|
||||||
val uncachedTypeList = List(acquireReadUncached, acquireWriteUncached, acquireReadWordUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
|
||||||
val hasDataTypeList = List(acquireWriteUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
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)
|
||||||
|
|
||||||
def isHit (cmd: Bits, state: UFix): Bool = {
|
def isHit (cmd: Bits, state: UFix): Bool = {
|
||||||
val (read, write) = cpuCmdToRW(cmd)
|
val (read, write) = cpuCmdToRW(cmd)
|
||||||
@ -621,7 +673,10 @@ class MESICoherence extends CoherencePolicyWithUncached {
|
|||||||
def getUncachedReadWordAcquire(addr: UFix, id: UFix) = Acquire(acquireReadWordUncached, addr, id)
|
def getUncachedReadWordAcquire(addr: UFix, id: UFix) = Acquire(acquireReadWordUncached, addr, id)
|
||||||
def getUncachedWriteWordAcquire(addr: UFix, id: UFix, write_mask: Bits) = Acquire(acquireWriteWordUncached, addr, id, write_mask)
|
def getUncachedWriteWordAcquire(addr: UFix, id: UFix, write_mask: Bits) = Acquire(acquireWriteWordUncached, addr, id, write_mask)
|
||||||
def getUncachedAtomicAcquire(addr: UFix, id: UFix, subword_addr: UFix, atomic_op: UFix) = Acquire(acquireAtomicUncached, addr, id, subword_addr, atomic_op)
|
def getUncachedAtomicAcquire(addr: UFix, id: UFix, subword_addr: UFix, atomic_op: UFix) = Acquire(acquireAtomicUncached, addr, id, subword_addr, atomic_op)
|
||||||
|
def getVoluntaryWriteback(addr: UFix, client_id: UFix, master_id: UFix) = Release(releaseVoluntaryInvalidateData, addr, client_id, master_id)
|
||||||
def isUncachedReadTransaction(acq: Acquire) = acq.a_type === acquireReadUncached
|
def isUncachedReadTransaction(acq: Acquire) = acq.a_type === acquireReadUncached
|
||||||
|
def isVoluntary(rel: Release) = rel.r_type === releaseVoluntaryInvalidateData
|
||||||
|
def isVoluntary(gnt: Grant) = gnt.g_type === grantVoluntaryAck
|
||||||
|
|
||||||
def getAcquireTypeOnPrimaryMiss(cmd: Bits, state: UFix): UFix = {
|
def getAcquireTypeOnPrimaryMiss(cmd: Bits, state: UFix): UFix = {
|
||||||
val (read, write) = cpuCmdToRW(cmd)
|
val (read, write) = cpuCmdToRW(cmd)
|
||||||
@ -631,11 +686,10 @@ class MESICoherence extends CoherencePolicyWithUncached {
|
|||||||
val (read, write) = cpuCmdToRW(cmd)
|
val (read, write) = cpuCmdToRW(cmd)
|
||||||
Mux(write, acquireReadExclusive, outstanding.a_type)
|
Mux(write, acquireReadExclusive, outstanding.a_type)
|
||||||
}
|
}
|
||||||
def getAcquireTypeOnCacheControl(cmd: Bits): Bits = acquireWriteUncached
|
def getReleaseTypeOnCacheControl(cmd: Bits): Bits = releaseVoluntaryInvalidateData // TODO
|
||||||
def getAcquireTypeOnWriteback(): Bits = getAcquireTypeOnCacheControl(M_INV)
|
def getReleaseTypeOnVoluntaryWriteback(): Bits = getReleaseTypeOnCacheControl(M_INV)
|
||||||
|
|
||||||
def newRelease (incoming: Probe, state: UFix): Release = {
|
def newRelease (incoming: Probe, state: UFix, id: UFix): Release = {
|
||||||
val reply = new Release
|
|
||||||
val with_data = MuxLookup(incoming.p_type, releaseInvalidateData, Array(
|
val with_data = MuxLookup(incoming.p_type, releaseInvalidateData, Array(
|
||||||
probeInvalidate -> releaseInvalidateData,
|
probeInvalidate -> releaseInvalidateData,
|
||||||
probeDowngrade -> releaseDowngradeData,
|
probeDowngrade -> releaseDowngradeData,
|
||||||
@ -646,24 +700,19 @@ class MESICoherence extends CoherencePolicyWithUncached {
|
|||||||
probeDowngrade -> releaseDowngradeAck,
|
probeDowngrade -> releaseDowngradeAck,
|
||||||
probeCopy -> releaseCopyAck
|
probeCopy -> releaseCopyAck
|
||||||
))
|
))
|
||||||
reply.r_type := Mux(needsWriteback(state), with_data, without_data)
|
Release( Mux(needsWriteback(state), with_data, without_data), incoming.addr, id, incoming.master_xact_id)
|
||||||
reply.master_xact_id := incoming.master_xact_id
|
|
||||||
reply
|
|
||||||
}
|
}
|
||||||
|
|
||||||
def messageHasData (reply: Release): Bool = {
|
def messageHasData(msg: SourcedMessage) = msg match {
|
||||||
(reply.r_type === releaseInvalidateData ||
|
case acq: Acquire => uFixListContains(hasDataAcquireTypeList, acq.a_type)
|
||||||
reply.r_type === releaseDowngradeData ||
|
case grant: Grant => uFixListContains(hasDataGrantTypeList, grant.g_type)
|
||||||
reply.r_type === releaseCopyData)
|
case rel: Release => uFixListContains(hasDataReleaseTypeList, rel.r_type)
|
||||||
}
|
case _ => Bool(false)
|
||||||
def messageHasData (acq: Acquire): Bool = hasDataTypeList.map(t => acq.a_type === t).reduceLeft(_||_)
|
|
||||||
def messageHasData (reply: Grant): Bool = {
|
|
||||||
(reply.g_type != grantWriteUncached && reply.g_type != grantReadExclusiveAck && reply.g_type != grantWriteWordUncached)
|
|
||||||
}
|
}
|
||||||
def messageUpdatesDataArray (reply: Grant): Bool = {
|
def messageUpdatesDataArray (reply: Grant): Bool = {
|
||||||
(reply.g_type === grantReadShared || reply.g_type === grantReadExclusive)
|
(reply.g_type === grantReadShared || reply.g_type === grantReadExclusive)
|
||||||
}
|
}
|
||||||
def messageIsUncached(acq: Acquire): Bool = uncachedTypeList.map(t => acq.a_type === t).reduceLeft(_||_)
|
def messageIsUncached(acq: Acquire): Bool = uFixListContains(uncachedAcquireTypeList, acq.a_type)
|
||||||
|
|
||||||
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool = (addr1 === addr2)
|
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool = (addr1 === addr2)
|
||||||
|
|
||||||
@ -678,6 +727,12 @@ class MESICoherence extends CoherencePolicyWithUncached {
|
|||||||
acquireAtomicUncached -> grantAtomicUncached
|
acquireAtomicUncached -> grantAtomicUncached
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
def getGrantType(rel: Release, count: UFix): Bits = {
|
||||||
|
MuxLookup(rel.r_type, grantReadUncached, Array(
|
||||||
|
releaseVoluntaryInvalidateData -> grantVoluntaryAck
|
||||||
|
))
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
def getProbeType(a_type: UFix, global_state: UFix): UFix = {
|
def getProbeType(a_type: UFix, global_state: UFix): UFix = {
|
||||||
MuxLookup(a_type, probeCopy, Array(
|
MuxLookup(a_type, probeCopy, Array(
|
||||||
@ -691,15 +746,21 @@ class MESICoherence extends CoherencePolicyWithUncached {
|
|||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
def needsMemRead(a_type: UFix, global_state: UFix): Bool = {
|
def needsOuterRead(a_type: UFix, global_state: UFix): Bool = {
|
||||||
(a_type != acquireWriteUncached)
|
(a_type != acquireWriteUncached)
|
||||||
}
|
}
|
||||||
def needsMemWrite(a_type: UFix, global_state: UFix): Bool = {
|
def needsOuterWrite(a_type: UFix, global_state: UFix): Bool = {
|
||||||
(a_type === acquireWriteUncached)
|
(a_type === acquireWriteUncached)
|
||||||
}
|
}
|
||||||
def needsAckReply(a_type: UFix, global_state: UFix): Bool = {
|
def needsAckReply(a_type: UFix, global_state: UFix): Bool = {
|
||||||
(a_type === acquireWriteUncached)
|
(a_type === acquireWriteUncached)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
def requiresAck(grant: Grant) = Bool(true)
|
||||||
|
def requiresAck(release: Release) = Bool(false)
|
||||||
|
def needsSelfProbe(acq: Acquire) = acq.a_type === acquireReadUncached
|
||||||
|
|
||||||
|
def pendingVoluntaryReleaseIsSufficient(r_type: UFix, p_type: UFix): Bool = (r_type === releaseVoluntaryInvalidateData)
|
||||||
}
|
}
|
||||||
|
|
||||||
class MigratoryCoherence extends CoherencePolicyWithUncached {
|
class MigratoryCoherence extends CoherencePolicyWithUncached {
|
||||||
@ -707,13 +768,14 @@ class MigratoryCoherence extends CoherencePolicyWithUncached {
|
|||||||
val tileInvalid :: tileShared :: tileExclusiveClean :: tileExclusiveDirty :: tileSharedByTwo :: tileMigratoryClean :: tileMigratoryDirty :: Nil = Enum(7){ UFix() }
|
val tileInvalid :: tileShared :: tileExclusiveClean :: tileExclusiveDirty :: tileSharedByTwo :: tileMigratoryClean :: tileMigratoryDirty :: Nil = Enum(7){ UFix() }
|
||||||
|
|
||||||
val acquireReadShared :: acquireReadExclusive :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: acquireInvalidateOthers :: Nil = Enum(8){ UFix() }
|
val acquireReadShared :: acquireReadExclusive :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: acquireInvalidateOthers :: Nil = Enum(8){ UFix() }
|
||||||
val grantReadShared :: grantReadExclusive :: grantReadUncached :: grantWriteUncached :: grantReadExclusiveAck :: grantReadWordUncached :: grantWriteWordUncached :: grantAtomicUncached :: grantReadMigratory :: Nil = Enum(9){ UFix() }
|
val grantVoluntaryAck :: grantReadShared :: grantReadExclusive :: grantReadUncached :: grantWriteUncached :: grantReadExclusiveAck :: grantReadWordUncached :: grantWriteWordUncached :: grantAtomicUncached :: grantReadMigratory :: Nil = Enum(10){ UFix() }
|
||||||
val probeInvalidate :: probeDowngrade :: probeCopy :: probeInvalidateOthers :: Nil = Enum(4){ UFix() }
|
val probeInvalidate :: probeDowngrade :: probeCopy :: probeInvalidateOthers :: Nil = Enum(4){ UFix() }
|
||||||
val releaseInvalidateData :: releaseDowngradeData :: releaseCopyData :: releaseInvalidateAck :: releaseDowngradeAck :: releaseCopyAck :: releaseDowngradeDataMigratory :: releaseDowngradeAckHasCopy :: releaseInvalidateDataMigratory :: releaseInvalidateAckMigratory :: Nil = Enum(10){ UFix() }
|
val releaseVoluntaryInvalidateData :: releaseInvalidateData :: releaseDowngradeData :: releaseCopyData :: releaseInvalidateAck :: releaseDowngradeAck :: releaseCopyAck :: releaseDowngradeDataMigratory :: releaseDowngradeAckHasCopy :: releaseInvalidateDataMigratory :: releaseInvalidateAckMigratory :: Nil = Enum(11){ UFix() }
|
||||||
val uncachedTypeList = List(acquireReadUncached, acquireWriteUncached, acquireReadWordUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
|
||||||
val hasDataTypeList = List(acquireWriteUncached, acquireWriteWordUncached, acquireAtomicUncached)
|
|
||||||
|
|
||||||
def uFixListContains(list: List[UFix], elem: UFix): Bool = list.map(elem === _).reduceLeft(_||_)
|
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)
|
||||||
|
|
||||||
def isHit (cmd: Bits, state: UFix): Bool = {
|
def isHit (cmd: Bits, state: UFix): Bool = {
|
||||||
val (read, write) = cpuCmdToRW(cmd)
|
val (read, write) = cpuCmdToRW(cmd)
|
||||||
@ -789,7 +851,10 @@ class MigratoryCoherence extends CoherencePolicyWithUncached {
|
|||||||
def getUncachedReadWordAcquire(addr: UFix, id: UFix) = Acquire(acquireReadWordUncached, addr, id)
|
def getUncachedReadWordAcquire(addr: UFix, id: UFix) = Acquire(acquireReadWordUncached, addr, id)
|
||||||
def getUncachedWriteWordAcquire(addr: UFix, id: UFix, write_mask: Bits) = Acquire(acquireWriteWordUncached, addr, id, write_mask)
|
def getUncachedWriteWordAcquire(addr: UFix, id: UFix, write_mask: Bits) = Acquire(acquireWriteWordUncached, addr, id, write_mask)
|
||||||
def getUncachedAtomicAcquire(addr: UFix, id: UFix, subword_addr: UFix, atomic_op: UFix) = Acquire(acquireAtomicUncached, addr, id, subword_addr, atomic_op)
|
def getUncachedAtomicAcquire(addr: UFix, id: UFix, subword_addr: UFix, atomic_op: UFix) = Acquire(acquireAtomicUncached, addr, id, subword_addr, atomic_op)
|
||||||
|
def getVoluntaryWriteback(addr: UFix, client_id: UFix, master_id: UFix) = Release(releaseVoluntaryInvalidateData, addr, client_id, master_id)
|
||||||
def isUncachedReadTransaction(acq: Acquire) = acq.a_type === acquireReadUncached
|
def isUncachedReadTransaction(acq: Acquire) = acq.a_type === acquireReadUncached
|
||||||
|
def isVoluntary(rel: Release) = rel.r_type === releaseVoluntaryInvalidateData
|
||||||
|
def isVoluntary(gnt: Grant) = gnt.g_type === grantVoluntaryAck
|
||||||
|
|
||||||
def getAcquireTypeOnPrimaryMiss(cmd: Bits, state: UFix): UFix = {
|
def getAcquireTypeOnPrimaryMiss(cmd: Bits, state: UFix): UFix = {
|
||||||
val (read, write) = cpuCmdToRW(cmd)
|
val (read, write) = cpuCmdToRW(cmd)
|
||||||
@ -799,12 +864,11 @@ class MigratoryCoherence extends CoherencePolicyWithUncached {
|
|||||||
val (read, write) = cpuCmdToRW(cmd)
|
val (read, write) = cpuCmdToRW(cmd)
|
||||||
Mux(write, Mux(state === tileInvalid, acquireReadExclusive, acquireInvalidateOthers), outstanding.a_type)
|
Mux(write, Mux(state === tileInvalid, acquireReadExclusive, acquireInvalidateOthers), outstanding.a_type)
|
||||||
}
|
}
|
||||||
def getAcquireTypeOnCacheControl(cmd: Bits): Bits = acquireWriteUncached
|
def getReleaseTypeOnCacheControl(cmd: Bits): Bits = releaseVoluntaryInvalidateData // TODO
|
||||||
def getAcquireTypeOnWriteback(): Bits = getAcquireTypeOnCacheControl(M_INV)
|
def getReleaseTypeOnVoluntaryWriteback(): Bits = getReleaseTypeOnCacheControl(M_INV)
|
||||||
|
|
||||||
def newRelease (incoming: Probe, state: UFix): Release = {
|
def newRelease (incoming: Probe, state: UFix, id: UFix): Release = {
|
||||||
Assert( incoming.p_type === probeInvalidateOthers && needsWriteback(state), "Bad probe request type, should be impossible.")
|
Assert( incoming.p_type === probeInvalidateOthers && needsWriteback(state), "Bad probe request type, should be impossible.")
|
||||||
val reply = new Release()
|
|
||||||
val with_data = MuxLookup(incoming.p_type, releaseInvalidateData, Array(
|
val with_data = MuxLookup(incoming.p_type, releaseInvalidateData, Array(
|
||||||
probeInvalidate -> Mux(uFixListContains(List(tileExclusiveDirty, tileMigratoryDirty), state),
|
probeInvalidate -> Mux(uFixListContains(List(tileExclusiveDirty, tileMigratoryDirty), state),
|
||||||
releaseInvalidateDataMigratory, releaseInvalidateData),
|
releaseInvalidateDataMigratory, releaseInvalidateData),
|
||||||
@ -817,22 +881,19 @@ class MigratoryCoherence extends CoherencePolicyWithUncached {
|
|||||||
probeDowngrade -> Mux(state != tileInvalid, releaseDowngradeAckHasCopy, releaseDowngradeAck),
|
probeDowngrade -> Mux(state != tileInvalid, releaseDowngradeAckHasCopy, releaseDowngradeAck),
|
||||||
probeCopy -> releaseCopyAck
|
probeCopy -> releaseCopyAck
|
||||||
))
|
))
|
||||||
reply.r_type := Mux(needsWriteback(state), with_data, without_data)
|
Release( Mux(needsWriteback(state), with_data, without_data), incoming.addr, id, incoming.master_xact_id)
|
||||||
reply.master_xact_id := incoming.master_xact_id
|
|
||||||
reply
|
|
||||||
}
|
}
|
||||||
|
|
||||||
def messageHasData (reply: Release): Bool = {
|
def messageHasData(msg: SourcedMessage) = msg match {
|
||||||
uFixListContains(List(releaseInvalidateData, releaseDowngradeData, releaseCopyData, releaseInvalidateDataMigratory, releaseDowngradeDataMigratory), reply.r_type)
|
case acq: Acquire => uFixListContains(hasDataAcquireTypeList, acq.a_type)
|
||||||
}
|
case grant: Grant => uFixListContains(hasDataGrantTypeList, grant.g_type)
|
||||||
def messageHasData (acq: Acquire): Bool = uFixListContains(hasDataTypeList, acq.a_type)
|
case rel: Release => uFixListContains(hasDataReleaseTypeList, rel.r_type)
|
||||||
def messageHasData (reply: Grant): Bool = {
|
case _ => Bool(false)
|
||||||
uFixListContains(List(grantReadShared, grantReadExclusive, grantReadUncached, grantReadMigratory, grantReadWordUncached, grantAtomicUncached), reply.g_type)
|
|
||||||
}
|
}
|
||||||
def messageUpdatesDataArray (reply: Grant): Bool = {
|
def messageUpdatesDataArray (reply: Grant): Bool = {
|
||||||
uFixListContains(List(grantReadShared, grantReadExclusive, grantReadMigratory), reply.g_type)
|
uFixListContains(List(grantReadShared, grantReadExclusive, grantReadMigratory), reply.g_type)
|
||||||
}
|
}
|
||||||
def messageIsUncached(acq: Acquire): Bool = uFixListContains(uncachedTypeList, acq.a_type)
|
def messageIsUncached(acq: Acquire): Bool = uFixListContains(uncachedAcquireTypeList, acq.a_type)
|
||||||
|
|
||||||
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool = (addr1 === addr2)
|
def isCoherenceConflict(addr1: Bits, addr2: Bits): Bool = (addr1 === addr2)
|
||||||
|
|
||||||
@ -848,6 +909,12 @@ class MigratoryCoherence extends CoherencePolicyWithUncached {
|
|||||||
acquireInvalidateOthers -> grantReadExclusiveAck //TODO: add this to MESI?
|
acquireInvalidateOthers -> grantReadExclusiveAck //TODO: add this to MESI?
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
def getGrantType(rel: Release, count: UFix): Bits = {
|
||||||
|
MuxLookup(rel.r_type, grantReadUncached, Array(
|
||||||
|
releaseVoluntaryInvalidateData -> grantVoluntaryAck
|
||||||
|
))
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
def getProbeType(a_type: UFix, global_state: UFix): UFix = {
|
def getProbeType(a_type: UFix, global_state: UFix): UFix = {
|
||||||
MuxLookup(a_type, probeCopy, Array(
|
MuxLookup(a_type, probeCopy, Array(
|
||||||
@ -862,13 +929,18 @@ class MigratoryCoherence extends CoherencePolicyWithUncached {
|
|||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
def needsMemRead(a_type: UFix, global_state: UFix): Bool = {
|
def needsOuterRead(a_type: UFix, global_state: UFix): Bool = {
|
||||||
(a_type != acquireWriteUncached && a_type != acquireInvalidateOthers)
|
(a_type != acquireWriteUncached && a_type != acquireInvalidateOthers)
|
||||||
}
|
}
|
||||||
def needsMemWrite(a_type: UFix, global_state: UFix): Bool = {
|
def needsOuterWrite(a_type: UFix, global_state: UFix): Bool = {
|
||||||
(a_type === acquireWriteUncached || a_type === acquireWriteWordUncached || a_type === acquireAtomicUncached)
|
(a_type === acquireWriteUncached || a_type === acquireWriteWordUncached || a_type === acquireAtomicUncached)
|
||||||
}
|
}
|
||||||
def needsAckReply(a_type: UFix, global_state: UFix): Bool = {
|
def needsAckReply(a_type: UFix, global_state: UFix): Bool = {
|
||||||
(a_type === acquireWriteUncached || a_type === acquireWriteWordUncached ||a_type === acquireInvalidateOthers)
|
(a_type === acquireWriteUncached || a_type === acquireWriteWordUncached ||a_type === acquireInvalidateOthers)
|
||||||
}
|
}
|
||||||
|
def requiresAck(grant: Grant) = Bool(true)
|
||||||
|
def requiresAck(release: Release) = Bool(false)
|
||||||
|
def needsSelfProbe(acq: Acquire) = acq.a_type === acquireReadUncached
|
||||||
|
|
||||||
|
def pendingVoluntaryReleaseIsSufficient(r_type: UFix, p_type: UFix): Bool = (r_type === releaseVoluntaryInvalidateData)
|
||||||
}
|
}
|
||||||
|
@ -11,7 +11,7 @@ abstract trait CoherenceConfigConstants {
|
|||||||
|
|
||||||
trait UncoreConstants {
|
trait UncoreConstants {
|
||||||
val NGLOBAL_XACTS = 8
|
val NGLOBAL_XACTS = 8
|
||||||
val MASTER_XACT_ID_BITS = log2Up(NGLOBAL_XACTS)
|
val MASTER_XACT_ID_MAX_BITS = log2Up(NGLOBAL_XACTS)
|
||||||
val CACHE_DATA_SIZE_IN_BYTES = 1 << 6
|
val CACHE_DATA_SIZE_IN_BYTES = 1 << 6
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -29,7 +29,7 @@ trait TileLinkTypeConstants {
|
|||||||
trait TileLinkSizeConstants extends
|
trait TileLinkSizeConstants extends
|
||||||
TileLinkTypeConstants
|
TileLinkTypeConstants
|
||||||
{
|
{
|
||||||
val CLIENT_XACT_ID_BITS = 5
|
val CLIENT_XACT_ID_MAX_BITS = 10
|
||||||
val ACQUIRE_WRITE_MASK_BITS = 6
|
val ACQUIRE_WRITE_MASK_BITS = 6
|
||||||
val ACQUIRE_SUBWORD_ADDR_BITS = 3
|
val ACQUIRE_SUBWORD_ADDR_BITS = 3
|
||||||
val ACQUIRE_ATOMIC_OP_BITS = 4
|
val ACQUIRE_ATOMIC_OP_BITS = 4
|
||||||
@ -72,7 +72,7 @@ trait MemoryInterfaceConstants extends
|
|||||||
UncoreConstants with
|
UncoreConstants with
|
||||||
TileLinkSizeConstants
|
TileLinkSizeConstants
|
||||||
{
|
{
|
||||||
val MEM_TAG_BITS = max(CLIENT_XACT_ID_BITS, MASTER_XACT_ID_BITS)
|
val MEM_TAG_BITS = max(CLIENT_XACT_ID_MAX_BITS, MASTER_XACT_ID_MAX_BITS)
|
||||||
val MEM_DATA_BITS = 128
|
val MEM_DATA_BITS = 128
|
||||||
val REFILL_CYCLES = CACHE_DATA_SIZE_IN_BYTES*8/MEM_DATA_BITS
|
val REFILL_CYCLES = CACHE_DATA_SIZE_IN_BYTES*8/MEM_DATA_BITS
|
||||||
}
|
}
|
||||||
|
@ -40,15 +40,13 @@ class BasicCrossbar[T <: Data]()(data: => T)(implicit conf: PhysicalNetworkConfi
|
|||||||
rdy := arb.ready && (in.bits.header.dst === UFix(i))
|
rdy := arb.ready && (in.bits.header.dst === UFix(i))
|
||||||
}}
|
}}
|
||||||
out <> rrarb.io.out
|
out <> rrarb.io.out
|
||||||
//out.bits.header.src := rrarb.io.chosen.toUFix
|
|
||||||
//out.bits.header.dst := UFix(i)
|
|
||||||
}}
|
}}
|
||||||
for(i <- 0 until conf.nEndpoints) {
|
for(i <- 0 until conf.nEndpoints) {
|
||||||
io.in(i).ready := rdyVecs.map(r => r(i)).reduceLeft(_||_)
|
io.in(i).ready := rdyVecs.map(r => r(i)).reduceLeft(_||_)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
case class LogicalNetworkConfiguration(nEndpoints: Int, idBits: Int, nHubs: Int, nTiles: Int)
|
case class LogicalNetworkConfiguration(nEndpoints: Int, idBits: Int, nMasters: Int, nClients: Int)
|
||||||
|
|
||||||
abstract class LogicalNetwork[TileLinkType <: Bundle](endpoints: Seq[CoherenceAgentRole])(implicit conf: LogicalNetworkConfiguration) extends Component {
|
abstract class LogicalNetwork[TileLinkType <: Bundle](endpoints: Seq[CoherenceAgentRole])(implicit conf: LogicalNetworkConfiguration) extends Component {
|
||||||
val io: Vec[TileLinkType]
|
val io: Vec[TileLinkType]
|
||||||
@ -106,4 +104,5 @@ class LogicalNetworkIO[T <: Data]()(data: => T)(implicit conf: LogicalNetworkCon
|
|||||||
val payload = data
|
val payload = data
|
||||||
override def clone = { new LogicalNetworkIO()(data).asInstanceOf[this.type] }
|
override def clone = { new LogicalNetworkIO()(data).asInstanceOf[this.type] }
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -3,20 +3,30 @@ package uncore
|
|||||||
import Chisel._
|
import Chisel._
|
||||||
import Constants._
|
import Constants._
|
||||||
|
|
||||||
class PhysicalAddress extends Bundle {
|
trait HasPhysicalAddress extends Bundle {
|
||||||
val addr = UFix(width = PADDR_BITS - OFFSET_BITS)
|
val addr = UFix(width = PADDR_BITS - OFFSET_BITS)
|
||||||
}
|
}
|
||||||
|
|
||||||
class MemData extends Bundle {
|
trait HasClientTransactionId extends Bundle {
|
||||||
|
val client_xact_id = Bits(width = CLIENT_XACT_ID_MAX_BITS)
|
||||||
|
}
|
||||||
|
|
||||||
|
trait HasMasterTransactionId extends Bundle {
|
||||||
|
val master_xact_id = Bits(width = MASTER_XACT_ID_MAX_BITS)
|
||||||
|
}
|
||||||
|
|
||||||
|
trait HasMemData extends Bundle {
|
||||||
val data = Bits(width = MEM_DATA_BITS)
|
val data = Bits(width = MEM_DATA_BITS)
|
||||||
}
|
}
|
||||||
|
|
||||||
class MemReqCmd extends PhysicalAddress {
|
class MemData extends Bundle with HasMemData
|
||||||
|
|
||||||
|
class MemReqCmd extends Bundle with HasPhysicalAddress {
|
||||||
val rw = Bool()
|
val rw = Bool()
|
||||||
val tag = Bits(width = MEM_TAG_BITS)
|
val tag = Bits(width = MEM_TAG_BITS)
|
||||||
}
|
}
|
||||||
|
|
||||||
class MemResp extends MemData {
|
class MemResp extends Bundle with HasMemData {
|
||||||
val tag = Bits(width = MEM_TAG_BITS)
|
val tag = Bits(width = MEM_TAG_BITS)
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -32,9 +42,12 @@ class ioMemPipe extends Bundle {
|
|||||||
val resp = (new PipeIO) { new MemResp() }.flip
|
val resp = (new PipeIO) { new MemResp() }.flip
|
||||||
}
|
}
|
||||||
|
|
||||||
class Acquire extends PhysicalAddress {
|
trait SourcedMessage extends Bundle
|
||||||
|
trait ClientSourcedMessage extends SourcedMessage
|
||||||
|
trait MasterSourcedMessage extends SourcedMessage
|
||||||
|
|
||||||
|
class Acquire extends ClientSourcedMessage with HasPhysicalAddress with HasClientTransactionId {
|
||||||
val a_type = Bits(width = ACQUIRE_TYPE_MAX_BITS)
|
val a_type = Bits(width = ACQUIRE_TYPE_MAX_BITS)
|
||||||
val client_xact_id = Bits(width = CLIENT_XACT_ID_BITS)
|
|
||||||
val write_mask = Bits(width = ACQUIRE_WRITE_MASK_BITS)
|
val write_mask = Bits(width = ACQUIRE_WRITE_MASK_BITS)
|
||||||
val subword_addr = Bits(width = ACQUIRE_SUBWORD_ADDR_BITS)
|
val subword_addr = Bits(width = ACQUIRE_SUBWORD_ADDR_BITS)
|
||||||
val atomic_opcode = Bits(width = ACQUIRE_ATOMIC_OP_BITS)
|
val atomic_opcode = Bits(width = ACQUIRE_ATOMIC_OP_BITS)
|
||||||
@ -47,6 +60,9 @@ object Acquire
|
|||||||
acq.a_type := a_type
|
acq.a_type := a_type
|
||||||
acq.addr := addr
|
acq.addr := addr
|
||||||
acq.client_xact_id := client_xact_id
|
acq.client_xact_id := client_xact_id
|
||||||
|
acq.write_mask := Bits(0, width = ACQUIRE_WRITE_MASK_BITS)
|
||||||
|
acq.subword_addr := Bits(0, width = ACQUIRE_SUBWORD_ADDR_BITS)
|
||||||
|
acq.atomic_opcode := Bits(0, width = ACQUIRE_ATOMIC_OP_BITS)
|
||||||
acq
|
acq
|
||||||
}
|
}
|
||||||
def apply(a_type: Bits, addr: UFix, client_xact_id: UFix, write_mask: Bits) = {
|
def apply(a_type: Bits, addr: UFix, client_xact_id: UFix, write_mask: Bits) = {
|
||||||
@ -55,6 +71,8 @@ object Acquire
|
|||||||
acq.addr := addr
|
acq.addr := addr
|
||||||
acq.client_xact_id := client_xact_id
|
acq.client_xact_id := client_xact_id
|
||||||
acq.write_mask := write_mask
|
acq.write_mask := write_mask
|
||||||
|
acq.subword_addr := Bits(0, width = ACQUIRE_SUBWORD_ADDR_BITS)
|
||||||
|
acq.atomic_opcode := Bits(0, width = ACQUIRE_ATOMIC_OP_BITS)
|
||||||
acq
|
acq
|
||||||
}
|
}
|
||||||
def apply(a_type: Bits, addr: UFix, client_xact_id: UFix, subword_addr: UFix, atomic_opcode: UFix) = {
|
def apply(a_type: Bits, addr: UFix, client_xact_id: UFix, subword_addr: UFix, atomic_opcode: UFix) = {
|
||||||
@ -64,51 +82,127 @@ object Acquire
|
|||||||
acq.client_xact_id := client_xact_id
|
acq.client_xact_id := client_xact_id
|
||||||
acq.subword_addr := subword_addr
|
acq.subword_addr := subword_addr
|
||||||
acq.atomic_opcode := atomic_opcode
|
acq.atomic_opcode := atomic_opcode
|
||||||
|
acq.write_mask := Bits(0, width = ACQUIRE_WRITE_MASK_BITS)
|
||||||
acq
|
acq
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class AcquireData extends MemData
|
class AcquireData extends ClientSourcedMessage with HasMemData
|
||||||
|
|
||||||
class Abort extends Bundle {
|
class Probe extends MasterSourcedMessage with HasPhysicalAddress with HasMasterTransactionId {
|
||||||
val client_xact_id = Bits(width = CLIENT_XACT_ID_BITS)
|
|
||||||
}
|
|
||||||
|
|
||||||
class Probe extends PhysicalAddress {
|
|
||||||
val p_type = Bits(width = PROBE_TYPE_MAX_BITS)
|
val p_type = Bits(width = PROBE_TYPE_MAX_BITS)
|
||||||
val master_xact_id = Bits(width = MASTER_XACT_ID_BITS)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
class Release extends Bundle {
|
object Release
|
||||||
|
{
|
||||||
|
def apply(r_type: Bits, addr: UFix, client_xact_id: UFix, master_xact_id: UFix) = {
|
||||||
|
val rel = new Release
|
||||||
|
rel.r_type := r_type
|
||||||
|
rel.addr := addr
|
||||||
|
rel.client_xact_id := client_xact_id
|
||||||
|
rel.master_xact_id := master_xact_id
|
||||||
|
rel
|
||||||
|
}
|
||||||
|
}
|
||||||
|
class Release extends ClientSourcedMessage with HasPhysicalAddress with HasClientTransactionId with HasMasterTransactionId {
|
||||||
val r_type = Bits(width = RELEASE_TYPE_MAX_BITS)
|
val r_type = Bits(width = RELEASE_TYPE_MAX_BITS)
|
||||||
val master_xact_id = Bits(width = MASTER_XACT_ID_BITS)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
class ReleaseData extends MemData
|
class ReleaseData extends ClientSourcedMessage with HasMemData
|
||||||
|
|
||||||
class Grant extends MemData {
|
class Grant extends MasterSourcedMessage with HasMemData with HasClientTransactionId with HasMasterTransactionId {
|
||||||
val g_type = Bits(width = GRANT_TYPE_MAX_BITS)
|
val g_type = Bits(width = GRANT_TYPE_MAX_BITS)
|
||||||
val client_xact_id = Bits(width = CLIENT_XACT_ID_BITS)
|
|
||||||
val master_xact_id = Bits(width = MASTER_XACT_ID_BITS)
|
|
||||||
val require_ack = Bool()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
class GrantAck extends Bundle {
|
class GrantAck extends ClientSourcedMessage with HasMasterTransactionId
|
||||||
val master_xact_id = Bits(width = MASTER_XACT_ID_BITS)
|
|
||||||
}
|
|
||||||
|
|
||||||
abstract class DirectionalFIFOIO[T <: Data]()(data: => T) extends FIFOIO()(data)
|
abstract class DirectionalFIFOIO[T <: Data]()(data: => T) extends FIFOIO()(data)
|
||||||
class ClientSourcedIO[T <: Data]()(data: => T) extends DirectionalFIFOIO()(data)
|
class ClientSourcedIO[T <: Data]()(data: => T) extends DirectionalFIFOIO()(data)
|
||||||
class MasterSourcedIO[T <: Data]()(data: => T) extends DirectionalFIFOIO()(data) {flip()}
|
class MasterSourcedIO[T <: Data]()(data: => T) extends DirectionalFIFOIO()(data) {flip()}
|
||||||
|
|
||||||
class TileLinkIO(implicit conf: LogicalNetworkConfiguration) extends Bundle {
|
class UncachedTileLinkIO(implicit conf: LogicalNetworkConfiguration) extends Bundle {
|
||||||
val acquire = (new ClientSourcedIO){(new LogicalNetworkIO){new Acquire }}
|
val acquire = (new ClientSourcedIO){(new LogicalNetworkIO){new Acquire }}
|
||||||
val acquire_data = (new ClientSourcedIO){(new LogicalNetworkIO){new AcquireData }}
|
val acquire_data = (new ClientSourcedIO){(new LogicalNetworkIO){new AcquireData }}
|
||||||
val abort = (new MasterSourcedIO){(new LogicalNetworkIO){new Abort }}
|
val grant = (new MasterSourcedIO) {(new LogicalNetworkIO){new Grant }}
|
||||||
|
val grant_ack = (new ClientSourcedIO){(new LogicalNetworkIO){new GrantAck }}
|
||||||
|
override def clone = { new UncachedTileLinkIO().asInstanceOf[this.type] }
|
||||||
|
}
|
||||||
|
|
||||||
|
class TileLinkIO(implicit conf: LogicalNetworkConfiguration) extends UncachedTileLinkIO()(conf) {
|
||||||
val probe = (new MasterSourcedIO){(new LogicalNetworkIO){new Probe }}
|
val probe = (new MasterSourcedIO){(new LogicalNetworkIO){new Probe }}
|
||||||
val release = (new ClientSourcedIO){(new LogicalNetworkIO){new Release }}
|
val release = (new ClientSourcedIO){(new LogicalNetworkIO){new Release }}
|
||||||
val release_data = (new ClientSourcedIO){(new LogicalNetworkIO){new ReleaseData }}
|
val release_data = (new ClientSourcedIO){(new LogicalNetworkIO){new ReleaseData }}
|
||||||
val grant = (new MasterSourcedIO){(new LogicalNetworkIO){new Grant }}
|
|
||||||
val grant_ack = (new ClientSourcedIO){(new LogicalNetworkIO){new GrantAck }}
|
|
||||||
override def clone = { new TileLinkIO().asInstanceOf[this.type] }
|
override def clone = { new TileLinkIO().asInstanceOf[this.type] }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
object UncachedTileLinkIOArbiterShim {
|
||||||
|
def apply[T <: HasClientTransactionId](in: ClientSourcedIO[LogicalNetworkIO[T]], id: Int, max: Int)(implicit lconf: LogicalNetworkConfiguration) = {
|
||||||
|
val shim = (new UncachedTileLinkIOArbiterShim(id, max)){in.bits.payload.clone}
|
||||||
|
shim.io.in <> in
|
||||||
|
shim.io.out
|
||||||
|
}
|
||||||
|
}
|
||||||
|
class UncachedTileLinkIOArbiterShim[T <: HasClientTransactionId](id: Int, max: Int)(data: => T)(implicit lconf: LogicalNetworkConfiguration) extends Component {
|
||||||
|
val io = new Bundle {
|
||||||
|
val in = (new ClientSourcedIO){(new LogicalNetworkIO){ data }}.flip
|
||||||
|
val out = (new ClientSourcedIO){(new LogicalNetworkIO){ data }}
|
||||||
|
}
|
||||||
|
io.out.bits := io.in.bits
|
||||||
|
io.out.bits.payload.client_xact_id := Cat(io.in.bits.payload.client_xact_id, UFix(id, log2Up(max)))
|
||||||
|
io.out.valid := io.in.valid
|
||||||
|
io.in.ready := io.out.ready
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
class UncachedTileLinkIOArbiter(n: Int)(implicit conf: LogicalNetworkConfiguration) extends Component {
|
||||||
|
val io = new Bundle {
|
||||||
|
val in = Vec(n) { new UncachedTileLinkIO }.flip
|
||||||
|
val out = new UncachedTileLinkIO
|
||||||
|
}
|
||||||
|
|
||||||
|
val mem_cnt = Reg(resetVal = UFix(0, width = log2Up(REFILL_CYCLES)))
|
||||||
|
val mem_cnt_next = mem_cnt + UFix(1)
|
||||||
|
val locked = Reg(resetVal = Bool(false))
|
||||||
|
val lock_idx = Reg(resetVal = UFix(n))
|
||||||
|
|
||||||
|
when(io.out.acquire_data.valid && io.out.acquire_data.ready) {
|
||||||
|
mem_cnt := mem_cnt_next
|
||||||
|
when(!locked) {
|
||||||
|
locked := Bool(true)
|
||||||
|
lock_idx := Vec(io.in.map{ in => in.acquire_data.ready && in.acquire_data.valid}){Bool()}.indexWhere{i: Bool => i}
|
||||||
|
}
|
||||||
|
when(mem_cnt_next === UFix(0)) {
|
||||||
|
locked := Bool(false)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
val acqd_grant = ArbiterCtrl(io.in.map(_.acquire_data.valid))
|
||||||
|
(0 until n).map(i => io.in(i).acquire_data.ready := Mux(locked, UFix(i) === lock_idx, acqd_grant(i)) && io.out.acquire_data.ready)
|
||||||
|
var acqd_bits = io.in(n-1).acquire_data.bits
|
||||||
|
for (i <- n-2 to 0 by -1) {
|
||||||
|
acqd_bits = Mux(io.in(i).acquire_data.valid, io.in(i).acquire_data.bits, acqd_bits)
|
||||||
|
}
|
||||||
|
val locked_req = io.in(lock_idx).acquire_data
|
||||||
|
io.out.acquire_data.bits := Mux(locked, locked_req.bits, acqd_bits)
|
||||||
|
io.out.acquire_data.valid := Mux(locked, locked_req.valid, io.in.map(_.acquire_data.valid).reduce(_||_))
|
||||||
|
|
||||||
|
val acq_arb = (new Arbiter(n)){ (new LogicalNetworkIO){new Acquire} }
|
||||||
|
io.out.acquire <> acq_arb.io.out
|
||||||
|
io.in.map(_.acquire).zipWithIndex.map{ case(acq, id) => UncachedTileLinkIOArbiterShim(acq, id, n) }.zip(acq_arb.io.in).map{ case (req, arb) => req <> arb}
|
||||||
|
|
||||||
|
val grant_ack_arb = (new Arbiter(n)){ (new LogicalNetworkIO){new GrantAck} }
|
||||||
|
io.out.grant_ack <> grant_ack_arb.io.out
|
||||||
|
grant_ack_arb.io.in zip io.in map { case (arb, req) => arb <> req.grant_ack }
|
||||||
|
|
||||||
|
io.out.grant.ready := Bool(false)
|
||||||
|
for (i <- 0 until n) {
|
||||||
|
val tag = io.out.grant.bits.payload.client_xact_id
|
||||||
|
io.in(i).grant.valid := Bool(false)
|
||||||
|
when (tag(log2Up(n)-1,0) === UFix(i)) {
|
||||||
|
io.in(i).grant.valid := io.out.grant.valid
|
||||||
|
io.out.grant.ready := io.in(i).grant.ready
|
||||||
|
}
|
||||||
|
io.in(i).grant.bits := io.out.grant.bits
|
||||||
|
io.in(i).grant.bits.payload.client_xact_id := tag >> UFix(log2Up(n))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
File diff suppressed because it is too large
Load Diff
Loading…
Reference in New Issue
Block a user