new tshrs, compiles but does not elaborate
This commit is contained in:
parent
394eb38a96
commit
86bdbd6535
@ -353,10 +353,14 @@ abstract class L2XactTracker(innerId: String, outerId: String) extends L2HellaCa
|
|||||||
val c_ack = io.inner.finish.bits
|
val c_ack = io.inner.finish.bits
|
||||||
val m_gnt = io.outer.grant.bits
|
val m_gnt = io.outer.grant.bits
|
||||||
|
|
||||||
|
def mergeData(acq: Acquire, data: UInt): UInt = {
|
||||||
|
//TODO wite mask
|
||||||
|
Mux(co.messageHasData(acq), acq.data, data)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class L2VoluntaryReleaseTracker(trackerId: Int, bankId: Int, innerId: String, outerId: String) extends L2XactTracker(innerId, outerId) {
|
class L2VoluntaryReleaseTracker(trackerId: Int, bankId: Int, innerId: String, outerId: String) extends L2XactTracker(innerId, outerId) {
|
||||||
val s_idle :: s_meta_read :: s_meta_resp :: s_meta_write :: s_data_write :: s_ack :: s_busy :: Nil = Enum(UInt(), 6)
|
val s_idle :: s_meta_read :: s_meta_resp :: s_meta_write :: s_data_write :: s_grant :: s_busy :: Nil = Enum(UInt(), 6)
|
||||||
val state = Reg(init=s_idle)
|
val state = Reg(init=s_idle)
|
||||||
val xact = Reg{ new Release }
|
val xact = Reg{ new Release }
|
||||||
val xact_internal = Reg{ new L2MetaResp }
|
val xact_internal = Reg{ new L2MetaResp }
|
||||||
@ -412,18 +416,26 @@ class L2VoluntaryReleaseTracker(trackerId: Int, bankId: Int, innerId: String, ou
|
|||||||
}
|
}
|
||||||
is(s_meta_resp) {
|
is(s_meta_resp) {
|
||||||
when(io.meta_resp.valid) {
|
when(io.meta_resp.valid) {
|
||||||
xact_internal := io.meta_resp.bits
|
xact_internal := co.masterMetadataOnRelease(xact,
|
||||||
state := s_meta_write
|
io.meta_resp.bits.meta.coh,
|
||||||
|
init_client_id)
|
||||||
|
state := Mux(io.meta_resp.bits.tag_match,
|
||||||
|
Mux(co.messageHasData(xact), s_data_write, s_meta_write),
|
||||||
|
s_grant)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
is(s_data_write) {
|
||||||
|
io.data_write.valid := Bool(true)
|
||||||
|
when(io.data_write.ready) { state := s_meta_write }
|
||||||
|
}
|
||||||
is(s_meta_write) {
|
is(s_meta_write) {
|
||||||
io.meta_write.valid := Bool(true)
|
io.meta_write.valid := Bool(true)
|
||||||
when(io.outer.acquire.ready) { state := s_ack }
|
when(io.meta_write.ready) { state := s_grant }
|
||||||
}
|
}
|
||||||
is(s_ack) {
|
is(s_grant) {
|
||||||
io.inner.grant.valid := Bool(true)
|
io.inner.grant.valid := Bool(true)
|
||||||
when(io.inner.grant.ready) {
|
when(io.inner.grant.ready) {
|
||||||
state := Mux(co.requiresAckForGrant(io.inner.grant.bits.payload.g_type),
|
state := Mux(co.requiresAckForGrant(c_gnt.payload.g_type),
|
||||||
s_busy, s_idle)
|
s_busy, s_idle)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -434,61 +446,71 @@ class L2VoluntaryReleaseTracker(trackerId: Int, bankId: Int, innerId: String, ou
|
|||||||
}
|
}
|
||||||
|
|
||||||
class L2AcquireTracker(trackerId: Int, bankId: Int, innerId: String, outerId: String) extends L2XactTracker(innerId, outerId) {
|
class L2AcquireTracker(trackerId: Int, bankId: Int, innerId: String, outerId: String) extends L2XactTracker(innerId, outerId) {
|
||||||
val s_idle :: s_probe :: s_mem_read :: s_mem_write :: s_make_grant :: s_busy :: Nil = Enum(UInt(), 6)
|
val s_idle :: s_meta_read :: s_meta_resp :: s_probe :: s_data_read_wb :: s_data_resp_wb :: s_outer_write_wb :: s_outer_read :: s_outer_resp :: s_data_read_hit :: s_data_resp_hit :: s_data_write :: s_outer_write_acq :: s_meta_write :: s_grant :: s_busy :: Nil = Enum(UInt(), 16)
|
||||||
val state = Reg(init=s_idle)
|
val state = Reg(init=s_idle)
|
||||||
val xact = Reg{ new Acquire }
|
val xact = Reg{ new Acquire }
|
||||||
val xact_internal = Reg{ new L2MetaResp }
|
val xact_internal = Reg{ new L2MetaResp }
|
||||||
val init_client_id = Reg(init=UInt(0, width = log2Up(nClients)))
|
val init_client_id = Reg(init=UInt(0, width = log2Up(nClients)))
|
||||||
//TODO: Will need id reg for merged release xacts
|
//TODO: Will need id reg for merged release xacts
|
||||||
|
|
||||||
val release_count = if (nClients == 1) UInt(0) else Reg(init=UInt(0, width = log2Up(nClients)))
|
|
||||||
val probe_flags = Reg(init=Bits(0, width = nClients))
|
|
||||||
val curr_p_id = PriorityEncoder(probe_flags)
|
|
||||||
|
|
||||||
val pending_outer_write = co.messageHasData(xact)
|
val release_count = Reg(init = UInt(0, width = log2Up(nClients)))
|
||||||
val pending_outer_read = co.requiresOuterRead(xact.a_type)
|
val pending_probes = Reg(init = co.dir())
|
||||||
|
val curr_p_id = pending_probes.next()
|
||||||
|
|
||||||
|
val is_uncached = co.messageIsUncached(xact)
|
||||||
|
val tag_match = xact_internal.tag_match
|
||||||
|
val needs_writeback = co.needsWriteback(xact_internal.meta.coh)
|
||||||
|
val is_hit = co.isHit(xact, xact_internal.meta.coh)
|
||||||
|
val needs_probes = co.requiresProbes(xact.a_type, xact_internal.meta.coh)
|
||||||
|
val c_rel_had_data = Reg{Bool()}
|
||||||
|
val c_rel_was_voluntary = Reg{Bool()}
|
||||||
|
val wb_buffer = Reg{xact.data.clone}
|
||||||
|
|
||||||
|
io.has_acquire_conflict := co.isCoherenceConflict(xact.addr, c_acq.payload.addr) &&
|
||||||
|
(state != s_idle) //TODO: Also indexes
|
||||||
|
io.has_release_conflict := co.isCoherenceConflict(xact.addr, c_rel.payload.addr) &&
|
||||||
|
(state != s_idle) //TODO: Also indexes?
|
||||||
|
|
||||||
val outer_write_acq = Bundle(Acquire(co.getUncachedWriteAcquireType,
|
val outer_write_acq = Bundle(Acquire(co.getUncachedWriteAcquireType,
|
||||||
xact.addr, UInt(trackerId), xact.data),
|
xact.addr,
|
||||||
{ case TLId => outerId })
|
UInt(trackerId),
|
||||||
val outer_write_rel = Bundle(Acquire(co.getUncachedWriteAcquireType,
|
xact.data), { case TLId => outerId })
|
||||||
xact.addr, UInt(trackerId), c_rel.payload.data),
|
val outer_write_wb = Bundle(Acquire(co.getUncachedWriteAcquireType,
|
||||||
{ case TLId => outerId })
|
Cat(xact_internal.meta.tag,
|
||||||
val outer_read = Bundle(Acquire(co.getUncachedReadAcquireType, xact.addr, UInt(trackerId)),
|
xact.addr(untagBits-1,blockOffBits)),
|
||||||
{ case TLId => outerId })
|
UInt(trackerId),
|
||||||
|
wb_buffer), { case TLId => outerId })
|
||||||
val probe_initial_flags = Bits(width = nClients)
|
val outer_read = Bundle(Acquire(co.getUncachedReadAcquireType,
|
||||||
probe_initial_flags := Bits(0)
|
xact.addr,
|
||||||
if (nClients > 1) {
|
UInt(trackerId)), { case TLId => outerId })
|
||||||
// issue self-probes for uncached read xacts to facilitate I$ coherence
|
|
||||||
val probe_self = Bool(true) //co.needsSelfProbe(io.inner.acquire.bits.payload)
|
|
||||||
val myflag = Mux(probe_self, Bits(0), UIntToOH(c_acq.header.src(log2Up(nClients)-1,0)))
|
|
||||||
probe_initial_flags := ~(io.tile_incoherent | myflag)
|
|
||||||
}
|
|
||||||
|
|
||||||
io.has_acquire_conflict := co.isCoherenceConflict(xact.addr, c_acq.payload.addr) && (state != s_idle)
|
|
||||||
io.has_release_conflict := co.isCoherenceConflict(xact.addr, c_rel.payload.addr) && (state != s_idle)
|
|
||||||
|
|
||||||
io.outer.acquire.valid := Bool(false)
|
io.outer.acquire.valid := Bool(false)
|
||||||
|
io.outer.acquire.bits.payload := outer_read //default
|
||||||
io.outer.acquire.bits.header.src := UInt(bankId)
|
io.outer.acquire.bits.header.src := UInt(bankId)
|
||||||
io.outer.acquire.bits.payload := outer_read
|
io.outer.grant.ready := Bool(true) //grant.data -> xact.data
|
||||||
io.outer.grant.ready := io.inner.grant.ready
|
|
||||||
|
|
||||||
|
val inner_probe_cacq = Probe(co.getProbeType(xact, xact_internal.meta.coh),
|
||||||
|
xact.addr,
|
||||||
|
UInt(trackerId))
|
||||||
|
val inner_probe_wb = Probe(co.getProbeTypeOnVoluntaryWriteback,
|
||||||
|
xact.addr,
|
||||||
|
UInt(trackerId))
|
||||||
|
//TODO inner_probe_mprb
|
||||||
io.inner.probe.valid := Bool(false)
|
io.inner.probe.valid := Bool(false)
|
||||||
io.inner.probe.bits.header.src := UInt(bankId)
|
io.inner.probe.bits.header.src := UInt(bankId)
|
||||||
io.inner.probe.bits.header.dst := curr_p_id
|
io.inner.probe.bits.header.dst := curr_p_id
|
||||||
io.inner.probe.bits.payload := Probe(co.getProbeType(xact, /*xact_internal.meta), TODO*/
|
io.inner.probe.bits.payload := Mux(needs_writeback,
|
||||||
co.masterMetadataOnFlush),
|
inner_probe_wb,
|
||||||
xact.addr,
|
inner_probe_cacq)
|
||||||
UInt(trackerId))
|
|
||||||
|
|
||||||
val grant_type = co.getGrantType(xact, co.masterMetadataOnFlush)// TODO xact_internal.meta)
|
val grant_type = co.getGrantType(xact, xact_internal.meta.coh)
|
||||||
io.inner.grant.valid := Bool(false)
|
io.inner.grant.valid := Bool(false)
|
||||||
io.inner.grant.bits.header.src := UInt(bankId)
|
io.inner.grant.bits.header.src := UInt(bankId)
|
||||||
io.inner.grant.bits.header.dst := init_client_id
|
io.inner.grant.bits.header.dst := init_client_id
|
||||||
io.inner.grant.bits.payload := Grant(grant_type,
|
io.inner.grant.bits.payload := Grant(grant_type,
|
||||||
xact.client_xact_id,
|
xact.client_xact_id,
|
||||||
UInt(trackerId),
|
UInt(trackerId),
|
||||||
m_gnt.payload.data)
|
xact.data)
|
||||||
|
|
||||||
io.inner.acquire.ready := Bool(false)
|
io.inner.acquire.ready := Bool(false)
|
||||||
io.inner.release.ready := Bool(false)
|
io.inner.release.ready := Bool(false)
|
||||||
@ -511,91 +533,154 @@ class L2AcquireTracker(trackerId: Int, bankId: Int, innerId: String, outerId: St
|
|||||||
io.meta_write.bits.id := UInt(trackerId)
|
io.meta_write.bits.id := UInt(trackerId)
|
||||||
io.meta_write.bits.idx := xact.addr(untagBits-1,blockOffBits)
|
io.meta_write.bits.idx := xact.addr(untagBits-1,blockOffBits)
|
||||||
io.meta_write.bits.way_en := xact_internal.way_en
|
io.meta_write.bits.way_en := xact_internal.way_en
|
||||||
io.meta_write.bits.data := xact_internal.meta
|
io.meta_write.bits.data.tag := xact.addr >> UInt(untagBits)
|
||||||
|
io.meta_write.bits.data.coh := xact_internal.meta.coh
|
||||||
when(io.meta_resp.valid && io.meta_resp.bits.id === UInt(trackerId)) { xact_internal := io.meta_resp.bits }
|
|
||||||
|
|
||||||
switch (state) {
|
switch (state) {
|
||||||
is(s_idle) {
|
is(s_idle) {
|
||||||
io.inner.acquire.ready := Bool(true)
|
io.inner.acquire.ready := Bool(true)
|
||||||
val needs_outer_write = co.messageHasData(c_acq.payload)
|
|
||||||
val needs_outer_read = co.requiresOuterRead(c_acq.payload.a_type)
|
|
||||||
when( io.inner.acquire.valid ) {
|
when( io.inner.acquire.valid ) {
|
||||||
xact := c_acq.payload
|
xact := c_acq.payload
|
||||||
init_client_id := c_acq.header.src
|
init_client_id := c_acq.header.src
|
||||||
probe_flags := probe_initial_flags
|
state := s_meta_read
|
||||||
if(nClients > 1) {
|
|
||||||
release_count := PopCount(probe_initial_flags)
|
|
||||||
state := Mux(probe_initial_flags.orR, s_probe,
|
|
||||||
Mux(needs_outer_write, s_mem_write,
|
|
||||||
Mux(needs_outer_read, s_mem_read, s_make_grant)))
|
|
||||||
} else state := Mux(needs_outer_write, s_mem_write,
|
|
||||||
Mux(needs_outer_read, s_mem_read, s_make_grant))
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// s_read_meta
|
is(s_meta_read) {
|
||||||
// xact_internal := resp
|
io.meta_read.valid := Bool(true)
|
||||||
is(s_probe) {
|
when(io.meta_read.ready) { state := s_meta_resp }
|
||||||
// Generate probes
|
}
|
||||||
io.inner.probe.valid := probe_flags.orR
|
is(s_meta_resp) {
|
||||||
when(io.inner.probe.ready) {
|
when(io.meta_resp.valid) {
|
||||||
probe_flags := probe_flags & ~(UIntToOH(curr_p_id))
|
val coh = io.meta_resp.bits.meta.coh
|
||||||
|
val _tag_match = io.meta_resp.bits.tag_match
|
||||||
|
val _needs_writeback = co.needsWriteback(coh)
|
||||||
|
val _is_hit = co.isHit(xact, coh)
|
||||||
|
val _needs_probes = co.requiresProbes(xact.a_type, coh)
|
||||||
|
xact_internal := io.meta_resp.bits
|
||||||
|
when(!_needs_writeback) {
|
||||||
|
xact_internal.meta.coh := co.masterMetadataOnFlush
|
||||||
|
}
|
||||||
|
when(_needs_probes) {
|
||||||
|
pending_probes := coh.sharers
|
||||||
|
release_count := coh.sharers.count()
|
||||||
|
c_rel_had_data := Bool(false)
|
||||||
|
c_rel_was_voluntary := Bool(false)
|
||||||
|
}
|
||||||
|
state := Mux(_tag_match,
|
||||||
|
Mux(_is_hit,
|
||||||
|
Mux(_needs_probes, s_probe, s_data_read_hit),
|
||||||
|
Mux(_needs_probes, s_probe, s_outer_read)),
|
||||||
|
Mux(_needs_writeback,
|
||||||
|
Mux(_needs_probes, s_probe, s_data_read_wb),
|
||||||
|
s_outer_read))
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
is(s_probe) {
|
||||||
|
val skip = io.tile_incoherent(curr_p_id) ||
|
||||||
|
((curr_p_id === init_client_id) &&
|
||||||
|
!co.requiresSelfProbe(xact.a_type))
|
||||||
|
io.inner.probe.valid := !(pending_probes.none() || skip)
|
||||||
|
when(io.inner.probe.ready || skip) {
|
||||||
|
pending_probes.pop(curr_p_id)
|
||||||
|
}
|
||||||
|
when(skip) { release_count := release_count - UInt(1) }
|
||||||
|
|
||||||
// Handle releases, which may have data to be written back
|
// Handle releases, which may have data being written back
|
||||||
|
io.inner.release.ready := Bool(true)
|
||||||
when(io.inner.release.valid) {
|
when(io.inner.release.valid) {
|
||||||
//xact_internal.meta.coh := tl.co.masterMetadataOnRelease(
|
xact_internal.meta.coh := co.masterMetadataOnRelease(
|
||||||
// io.inner.release.bits.payload,
|
c_rel.payload,
|
||||||
// xact_internal.meta.coh,
|
xact_internal.meta.coh,
|
||||||
// init_client_id)
|
c_rel.header.src)
|
||||||
when(co.messageHasData(c_rel.payload)) {
|
when(co.messageHasData(c_rel.payload)) {
|
||||||
io.outer.acquire.valid := Bool(true)
|
c_rel_had_data := Bool(true)
|
||||||
io.outer.acquire.bits.payload := outer_write_rel
|
when(tag_match) {
|
||||||
when(io.outer.acquire.ready) {
|
xact.data := mergeData(xact, io.inner.release.bits.payload.data)
|
||||||
io.inner.release.ready := Bool(true)
|
} .otherwise {
|
||||||
if(nClients > 1) release_count := release_count - UInt(1)
|
wb_buffer := io.inner.release.bits.payload.data
|
||||||
when(release_count === UInt(1)) {
|
|
||||||
state := Mux(pending_outer_write, s_mem_write,
|
|
||||||
Mux(pending_outer_read, s_mem_read, s_make_grant))
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
} .otherwise {
|
}
|
||||||
io.inner.release.ready := Bool(true)
|
when(co.isVoluntary(c_rel.payload)) {
|
||||||
if(nClients > 1) release_count := release_count - UInt(1)
|
c_rel_was_voluntary := Bool(true)
|
||||||
|
}
|
||||||
|
when(!co.isVoluntary(c_rel.payload)) {
|
||||||
|
release_count := release_count - Mux(skip, UInt(2), UInt(1))
|
||||||
when(release_count === UInt(1)) {
|
when(release_count === UInt(1)) {
|
||||||
state := Mux(pending_outer_write, s_mem_write,
|
state := Mux(tag_match,
|
||||||
Mux(pending_outer_read, s_mem_read, s_make_grant))
|
Mux(is_hit,
|
||||||
|
Mux(c_rel_had_data, s_meta_write, s_data_read_hit),
|
||||||
|
s_outer_read),
|
||||||
|
Mux(c_rel_had_data, s_outer_write_wb, s_data_read_wb))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
is(s_mem_read) {
|
is(s_data_read_wb) {
|
||||||
|
io.data_read.valid := Bool(true)
|
||||||
|
when(io.data_read.ready) {
|
||||||
|
state := s_data_resp_wb
|
||||||
|
}
|
||||||
|
}
|
||||||
|
is(s_data_resp_wb) {
|
||||||
|
when(io.data_resp.valid) {
|
||||||
|
wb_buffer := io.data_resp.bits
|
||||||
|
state := s_outer_write_wb
|
||||||
|
}
|
||||||
|
}
|
||||||
|
is(s_outer_write_wb) {
|
||||||
|
io.outer.acquire.valid := Bool(true)
|
||||||
|
io.outer.acquire.bits.payload := outer_write_wb
|
||||||
|
when(io.outer.acquire.ready) {
|
||||||
|
state := s_outer_read
|
||||||
|
}
|
||||||
|
}
|
||||||
|
is(s_outer_read) {
|
||||||
io.outer.acquire.valid := Bool(true)
|
io.outer.acquire.valid := Bool(true)
|
||||||
io.outer.acquire.bits.payload := outer_read
|
io.outer.acquire.bits.payload := outer_read
|
||||||
when(io.outer.acquire.ready) {
|
when(io.outer.acquire.ready) {
|
||||||
state := Mux(co.requiresAckForGrant(grant_type), s_busy, s_idle)
|
state := s_outer_resp
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
is(s_mem_write) {
|
is(s_outer_resp) {
|
||||||
io.outer.acquire.valid := Bool(true)
|
io.outer.grant.ready := Bool(true)
|
||||||
io.outer.acquire.bits.payload := outer_write_acq
|
when(io.outer.grant.valid) {
|
||||||
when(io.outer.acquire.ready) {
|
xact.data := mergeData(xact, io.outer.grant.bits.payload.data)
|
||||||
state := Mux(pending_outer_read, s_mem_read, s_make_grant)
|
//TODO: set pending client state in xact_internal.meta.coh
|
||||||
|
state := Mux(co.messageHasData(io.outer.grant.bits.payload),
|
||||||
|
s_data_write, s_data_read_hit)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
is(s_make_grant) {
|
is(s_data_read_hit) {
|
||||||
|
io.data_read.valid := Bool(true)
|
||||||
|
when(io.data_read.ready) {
|
||||||
|
state := s_data_resp_hit
|
||||||
|
}
|
||||||
|
}
|
||||||
|
is(s_data_resp_hit) {
|
||||||
|
when(io.data_resp.valid) {
|
||||||
|
xact.data := mergeData(xact, io.data_resp.bits.data)
|
||||||
|
state := s_meta_write
|
||||||
|
}
|
||||||
|
}
|
||||||
|
is(s_data_write) {
|
||||||
|
io.data_write.valid := Bool(true)
|
||||||
|
when(io.data_write.ready) {
|
||||||
|
state := s_meta_write
|
||||||
|
}
|
||||||
|
}
|
||||||
|
is(s_meta_write) {
|
||||||
|
io.meta_write.valid := Bool(true)
|
||||||
|
when(io.meta_write.ready) { state := s_grant }
|
||||||
|
}
|
||||||
|
is(s_grant) {
|
||||||
io.inner.grant.valid := Bool(true)
|
io.inner.grant.valid := Bool(true)
|
||||||
when(io.inner.grant.ready) {
|
when(io.inner.grant.ready) {
|
||||||
state := Mux(co.requiresAckForGrant(grant_type), s_busy, s_idle)
|
state := Mux(co.requiresAckForGrant(c_gnt.payload.g_type),
|
||||||
|
s_busy, s_idle)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
is(s_busy) { // Nothing left to do but wait for transaction to complete
|
is(s_busy) {
|
||||||
when(io.outer.grant.valid && m_gnt.payload.client_xact_id === UInt(trackerId)) {
|
when(io.inner.finish.valid) { state := s_idle }
|
||||||
io.inner.grant.valid := Bool(true)
|
|
||||||
}
|
|
||||||
when(io.inner.finish.valid && c_ack.payload.master_xact_id === UInt(trackerId)) {
|
|
||||||
state := s_idle
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -51,7 +51,6 @@ class MixedMetadata(inner: CoherencePolicy, outer: CoherencePolicy) extends Cohe
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
abstract class DirectoryRepresentation extends Bundle {
|
abstract class DirectoryRepresentation extends Bundle {
|
||||||
val internal: UInt
|
|
||||||
def pop(id: UInt): DirectoryRepresentation
|
def pop(id: UInt): DirectoryRepresentation
|
||||||
def push(id: UInt): DirectoryRepresentation
|
def push(id: UInt): DirectoryRepresentation
|
||||||
def flush(dummy: Int = 0): DirectoryRepresentation
|
def flush(dummy: Int = 0): DirectoryRepresentation
|
||||||
@ -106,6 +105,7 @@ abstract class CoherencePolicy(val dir: () => DirectoryRepresentation) {
|
|||||||
def needsTransactionOnSecondaryMiss(cmd: UInt, outstanding: Acquire): Bool
|
def needsTransactionOnSecondaryMiss(cmd: UInt, outstanding: Acquire): Bool
|
||||||
def needsTransactionOnCacheControl(cmd: UInt, m: ClientMetadata): Bool
|
def needsTransactionOnCacheControl(cmd: UInt, m: ClientMetadata): Bool
|
||||||
def needsWriteback(m: ClientMetadata): Bool
|
def needsWriteback(m: ClientMetadata): Bool
|
||||||
|
def needsWriteback(m: MasterMetadata): Bool
|
||||||
|
|
||||||
def clientMetadataOnHit(cmd: UInt, m: ClientMetadata): ClientMetadata
|
def clientMetadataOnHit(cmd: UInt, m: ClientMetadata): ClientMetadata
|
||||||
def clientMetadataOnCacheControl(cmd: UInt): ClientMetadata
|
def clientMetadataOnCacheControl(cmd: UInt): ClientMetadata
|
||||||
@ -114,33 +114,33 @@ abstract class CoherencePolicy(val dir: () => DirectoryRepresentation) {
|
|||||||
def clientMetadataOnProbe(incoming: Probe, m: ClientMetadata): ClientMetadata
|
def clientMetadataOnProbe(incoming: Probe, m: ClientMetadata): ClientMetadata
|
||||||
def masterMetadataOnFlush: MasterMetadata
|
def masterMetadataOnFlush: MasterMetadata
|
||||||
def masterMetadataOnRelease(incoming: Release, m: MasterMetadata, src: UInt): MasterMetadata
|
def masterMetadataOnRelease(incoming: Release, m: MasterMetadata, src: UInt): MasterMetadata
|
||||||
|
def masterMetadataOnGrant(outgoing: Grant, m: MasterMetadata, dst: UInt): MasterMetadata
|
||||||
|
|
||||||
def getAcquireTypeOnPrimaryMiss(cmd: UInt, m: ClientMetadata): UInt
|
def getAcquireTypeOnPrimaryMiss(cmd: UInt, m: ClientMetadata): UInt
|
||||||
def getAcquireTypeOnSecondaryMiss(cmd: UInt, m: ClientMetadata, outstanding: Acquire): UInt
|
def getAcquireTypeOnSecondaryMiss(cmd: UInt, m: ClientMetadata, outstanding: Acquire): UInt
|
||||||
def getProbeType(a: Acquire, m: MasterMetadata): UInt
|
def getProbeType(a: Acquire, m: MasterMetadata): UInt
|
||||||
|
def getProbeTypeOnVoluntaryWriteback: UInt
|
||||||
def getReleaseTypeOnCacheControl(cmd: UInt): UInt
|
def getReleaseTypeOnCacheControl(cmd: UInt): UInt
|
||||||
def getReleaseTypeOnVoluntaryWriteback(): UInt
|
def getReleaseTypeOnVoluntaryWriteback(): UInt
|
||||||
def getReleaseTypeOnProbe(p: Probe, m: ClientMetadata): UInt
|
def getReleaseTypeOnProbe(p: Probe, m: ClientMetadata): UInt
|
||||||
def getGrantType(a: Acquire, m: MasterMetadata): UInt
|
def getGrantType(a: Acquire, m: MasterMetadata): UInt
|
||||||
def getGrantType(r: Release, m: MasterMetadata): UInt
|
def getGrantType(r: Release, m: MasterMetadata): UInt
|
||||||
//def getGrantType(a: Acquire) = getGrantType(a, new NullRepresentation) // TODO
|
|
||||||
//def getGrantType(r: Release) = getGrantType(r, new NullRepresentation)
|
|
||||||
|
|
||||||
def messageHasData (rel: SourcedMessage): Bool
|
def messageHasData (rel: SourcedMessage): Bool
|
||||||
def messageUpdatesDataArray (reply: Grant): Bool
|
def messageUpdatesDataArray (reply: Grant): Bool
|
||||||
def messageIsUncached(acq: Acquire): Bool
|
def messageIsUncached(acq: Acquire): Bool
|
||||||
|
|
||||||
def isCoherenceConflict(addr1: UInt, addr2: UInt): Bool
|
|
||||||
def isVoluntary(rel: Release): Bool
|
def isVoluntary(rel: Release): Bool
|
||||||
def isVoluntary(gnt: Grant): Bool
|
def isVoluntary(gnt: Grant): Bool
|
||||||
def requiresOuterRead(a_type: UInt, m: MasterMetadata): Bool
|
|
||||||
def requiresOuterWrite(a_type: UInt, m: MasterMetadata): Bool
|
|
||||||
def requiresOuterRead(a_type: UInt): Bool
|
def requiresOuterRead(a_type: UInt): Bool
|
||||||
def requiresOuterWrite(a_type: UInt): Bool
|
def requiresOuterWrite(a_type: UInt): Bool
|
||||||
def requiresSelfProbe(a_type: UInt): Bool
|
def requiresSelfProbe(a_type: UInt): Bool
|
||||||
|
def requiresProbes(a_type: UInt, m: MasterMetadata): Bool
|
||||||
def requiresAckForGrant(g_type: UInt): Bool
|
def requiresAckForGrant(g_type: UInt): Bool
|
||||||
def requiresAckForRelease(r_type: UInt): Bool
|
def requiresAckForRelease(r_type: UInt): Bool
|
||||||
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool
|
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool
|
||||||
|
|
||||||
|
def isCoherenceConflict(addr1: UInt, addr2: UInt): Bool
|
||||||
}
|
}
|
||||||
|
|
||||||
trait UncachedTransactions {
|
trait UncachedTransactions {
|
||||||
@ -191,6 +191,7 @@ class MICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWit
|
|||||||
def needsWriteback (m: ClientMetadata): Bool = {
|
def needsWriteback (m: ClientMetadata): Bool = {
|
||||||
needsTransactionOnCacheControl(M_INV, m)
|
needsTransactionOnCacheControl(M_INV, m)
|
||||||
}
|
}
|
||||||
|
def needsWriteback(m: MasterMetadata) = isValid(m)
|
||||||
|
|
||||||
def clientMetadataOnHit(cmd: UInt, m: ClientMetadata) = m
|
def clientMetadataOnHit(cmd: UInt, m: ClientMetadata) = m
|
||||||
def clientMetadataOnCacheControl(cmd: UInt) = ClientMetadata(
|
def clientMetadataOnCacheControl(cmd: UInt) = ClientMetadata(
|
||||||
@ -214,16 +215,19 @@ class MICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWit
|
|||||||
probeCopy -> m.state
|
probeCopy -> m.state
|
||||||
)))(this)
|
)))(this)
|
||||||
def masterMetadataOnFlush = MasterMetadata(masterInvalid)(this)
|
def masterMetadataOnFlush = MasterMetadata(masterInvalid)(this)
|
||||||
def masterMetadataOnRelease(incoming: Release, m: MasterMetadata, src: UInt) = {
|
def masterMetadataOnRelease(r: Release, m: MasterMetadata, src: UInt) = {
|
||||||
val popped = m.sharers.pop(src)
|
val next = MasterMetadata(masterValid, m.sharers.pop(src))(this)
|
||||||
val next = MasterMetadata(Mux(popped.none(), masterInvalid, masterValid), popped)(this)
|
|
||||||
def is(r: UInt) = incoming.r_type === r
|
|
||||||
MuxBundle(m, Array(
|
MuxBundle(m, Array(
|
||||||
is(releaseVoluntaryInvalidateData) -> next,
|
r.is(releaseVoluntaryInvalidateData) -> next,
|
||||||
is(releaseInvalidateData) -> next,
|
r.is(releaseInvalidateData) -> next,
|
||||||
is(releaseCopyData) -> m,
|
r.is(releaseInvalidateAck) -> next
|
||||||
is(releaseInvalidateAck) -> next,
|
))
|
||||||
is(releaseCopyAck) -> m
|
}
|
||||||
|
def masterMetadataOnGrant(g: Grant, m: MasterMetadata, dst: UInt) = {
|
||||||
|
val cached = MasterMetadata(masterValid, m.sharers.push(dst))(this)
|
||||||
|
val uncached = MasterMetadata(masterValid, m.sharers)(this)
|
||||||
|
MuxBundle(uncached, Array(
|
||||||
|
g.is(grantReadExclusive) -> cached
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -292,6 +296,7 @@ class MICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWit
|
|||||||
acquireAtomicUncached -> probeInvalidate
|
acquireAtomicUncached -> probeInvalidate
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
def getProbeTypeOnVoluntaryWriteback: UInt = probeInvalidate
|
||||||
|
|
||||||
def requiresOuterRead(a_type: UInt) = {
|
def requiresOuterRead(a_type: UInt) = {
|
||||||
(a_type != acquireWriteUncached)
|
(a_type != acquireWriteUncached)
|
||||||
@ -299,11 +304,10 @@ class MICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWit
|
|||||||
def requiresOuterWrite(a_type: UInt) = {
|
def requiresOuterWrite(a_type: UInt) = {
|
||||||
(a_type === acquireWriteUncached)
|
(a_type === acquireWriteUncached)
|
||||||
}
|
}
|
||||||
def requiresOuterRead(a_type: UInt, m: MasterMetadata) = requiresOuterRead(a_type)
|
|
||||||
def requiresOuterWrite(a_type: UInt, m: MasterMetadata) = requiresOuterWrite(a_type)
|
|
||||||
def requiresAckForGrant(g_type: UInt) = g_type != grantVoluntaryAck
|
def requiresAckForGrant(g_type: UInt) = g_type != grantVoluntaryAck
|
||||||
def requiresAckForRelease(r_type: UInt) = Bool(false)
|
def requiresAckForRelease(r_type: UInt) = Bool(false)
|
||||||
def requiresSelfProbe(a_type: UInt) = Bool(false)
|
def requiresSelfProbe(a_type: UInt) = a_type === acquireReadUncached
|
||||||
|
def requiresProbes(a_type: UInt, m: MasterMetadata) = !m.sharers.none()
|
||||||
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool = (r_type === releaseVoluntaryInvalidateData)
|
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool = (r_type === releaseVoluntaryInvalidateData)
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -346,6 +350,7 @@ class MEICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWi
|
|||||||
def needsWriteback (m: ClientMetadata): Bool = {
|
def needsWriteback (m: ClientMetadata): Bool = {
|
||||||
needsTransactionOnCacheControl(M_INV, m)
|
needsTransactionOnCacheControl(M_INV, m)
|
||||||
}
|
}
|
||||||
|
def needsWriteback(m: MasterMetadata) = isValid(m)
|
||||||
|
|
||||||
def clientMetadataOnHit(cmd: UInt, m: ClientMetadata) =
|
def clientMetadataOnHit(cmd: UInt, m: ClientMetadata) =
|
||||||
ClientMetadata(Mux(isWrite(cmd), clientExclusiveDirty, m.state))(this)
|
ClientMetadata(Mux(isWrite(cmd), clientExclusiveDirty, m.state))(this)
|
||||||
@ -374,18 +379,20 @@ class MEICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWi
|
|||||||
probeCopy -> m.state
|
probeCopy -> m.state
|
||||||
)))(this)
|
)))(this)
|
||||||
def masterMetadataOnFlush = MasterMetadata(masterInvalid)(this)
|
def masterMetadataOnFlush = MasterMetadata(masterInvalid)(this)
|
||||||
def masterMetadataOnRelease(incoming: Release, m: MasterMetadata, src: UInt) = {
|
def masterMetadataOnRelease(r: Release, m: MasterMetadata, src: UInt) = {
|
||||||
val popped = m.sharers.pop(src)
|
val next = MasterMetadata(masterValid, m.sharers.pop(src))(this)
|
||||||
val next = MasterMetadata(Mux(popped.none(), masterInvalid, masterValid), popped)(this)
|
|
||||||
def is(r: UInt) = incoming.r_type === r
|
|
||||||
MuxBundle(m, Array(
|
MuxBundle(m, Array(
|
||||||
is(releaseVoluntaryInvalidateData) -> next,
|
r.is(releaseVoluntaryInvalidateData) -> next,
|
||||||
is(releaseInvalidateData) -> next,
|
r.is(releaseInvalidateData) -> next,
|
||||||
is(releaseDowngradeData) -> m,
|
r.is(releaseInvalidateAck) -> next
|
||||||
is(releaseCopyData) -> m,
|
))
|
||||||
is(releaseInvalidateAck) -> next,
|
}
|
||||||
is(releaseDowngradeAck) -> m,
|
def masterMetadataOnGrant(g: Grant, m: MasterMetadata, dst: UInt) = {
|
||||||
is(releaseCopyAck) -> m
|
val cached = MasterMetadata(masterValid, m.sharers.push(dst))(this)
|
||||||
|
val uncached = MasterMetadata(masterValid, m.sharers)(this)
|
||||||
|
MuxBundle(uncached, Array(
|
||||||
|
g.is(grantReadExclusive) -> cached,
|
||||||
|
g.is(grantReadExclusiveAck) -> cached
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -462,6 +469,7 @@ class MEICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWi
|
|||||||
acquireAtomicUncached -> probeInvalidate
|
acquireAtomicUncached -> probeInvalidate
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
def getProbeTypeOnVoluntaryWriteback: UInt = probeInvalidate
|
||||||
|
|
||||||
def requiresOuterRead(a_type: UInt) = {
|
def requiresOuterRead(a_type: UInt) = {
|
||||||
(a_type != acquireWriteUncached)
|
(a_type != acquireWriteUncached)
|
||||||
@ -469,25 +477,25 @@ class MEICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWi
|
|||||||
def requiresOuterWrite(a_type: UInt) = {
|
def requiresOuterWrite(a_type: UInt) = {
|
||||||
(a_type === acquireWriteUncached)
|
(a_type === acquireWriteUncached)
|
||||||
}
|
}
|
||||||
def requiresOuterRead(a_type: UInt, m: MasterMetadata) = requiresOuterRead(a_type)
|
|
||||||
def requiresOuterWrite(a_type: UInt, m: MasterMetadata) = requiresOuterWrite(a_type)
|
|
||||||
def requiresAckForGrant(g_type: UInt) = g_type != grantVoluntaryAck
|
def requiresAckForGrant(g_type: UInt) = g_type != grantVoluntaryAck
|
||||||
def requiresAckForRelease(r_type: UInt) = Bool(false)
|
def requiresAckForRelease(r_type: UInt) = Bool(false)
|
||||||
def requiresSelfProbe(a_type: UInt) = Bool(false)
|
def requiresSelfProbe(a_type: UInt) = a_type === acquireReadUncached
|
||||||
|
def requiresProbes(a_type: UInt, m: MasterMetadata) = !m.sharers.none()
|
||||||
|
|
||||||
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool = (r_type === releaseVoluntaryInvalidateData)
|
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool = (r_type === releaseVoluntaryInvalidateData)
|
||||||
}
|
}
|
||||||
|
|
||||||
class MSICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWithUncached(dir) {
|
class MSICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWithUncached(dir) {
|
||||||
def nClientStates = 3
|
def nClientStates = 3
|
||||||
def nMasterStates = 3
|
def nMasterStates = 2
|
||||||
def nAcquireTypes = 7
|
def nAcquireTypes = 7
|
||||||
def nProbeTypes = 3
|
def nProbeTypes = 3
|
||||||
def nReleaseTypes = 7
|
def nReleaseTypes = 7
|
||||||
def nGrantTypes = 9
|
def nGrantTypes = 9
|
||||||
|
|
||||||
val clientInvalid :: clientShared :: clientExclusiveDirty :: Nil = Enum(UInt(), nClientStates)
|
val clientInvalid :: clientShared :: clientExclusiveDirty :: Nil = Enum(UInt(), nClientStates)
|
||||||
val masterInvalid :: masterShared :: masterExclusive :: Nil = Enum(UInt(), nMasterStates)
|
//val masterInvalid :: masterShared :: masterExclusive :: Nil = Enum(UInt(), nMasterStates)
|
||||||
|
val masterInvalid :: masterValid :: Nil = Enum(UInt(), nMasterStates)
|
||||||
|
|
||||||
val acquireReadShared :: acquireReadExclusive :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: Nil = Enum(UInt(), nAcquireTypes)
|
val acquireReadShared :: acquireReadExclusive :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: Nil = Enum(UInt(), nAcquireTypes)
|
||||||
val probeInvalidate :: probeDowngrade :: probeCopy :: Nil = Enum(UInt(), nProbeTypes)
|
val probeInvalidate :: probeDowngrade :: probeCopy :: Nil = Enum(UInt(), nProbeTypes)
|
||||||
@ -522,6 +530,7 @@ class MSICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWi
|
|||||||
def needsWriteback (m: ClientMetadata): Bool = {
|
def needsWriteback (m: ClientMetadata): Bool = {
|
||||||
needsTransactionOnCacheControl(M_INV, m)
|
needsTransactionOnCacheControl(M_INV, m)
|
||||||
}
|
}
|
||||||
|
def needsWriteback(m: MasterMetadata) = isValid(m)
|
||||||
|
|
||||||
def clientMetadataOnHit(cmd: UInt, m: ClientMetadata) =
|
def clientMetadataOnHit(cmd: UInt, m: ClientMetadata) =
|
||||||
ClientMetadata(Mux(isWrite(cmd), clientExclusiveDirty, m.state))(this)
|
ClientMetadata(Mux(isWrite(cmd), clientExclusiveDirty, m.state))(this)
|
||||||
@ -549,20 +558,21 @@ class MSICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWi
|
|||||||
probeCopy -> m.state
|
probeCopy -> m.state
|
||||||
)))(this)
|
)))(this)
|
||||||
def masterMetadataOnFlush = MasterMetadata(masterInvalid)(this)
|
def masterMetadataOnFlush = MasterMetadata(masterInvalid)(this)
|
||||||
def masterMetadataOnRelease(incoming: Release, m: MasterMetadata, src: UInt) = {
|
def masterMetadataOnRelease(r: Release, m: MasterMetadata, src: UInt) = {
|
||||||
val popped = m.sharers.pop(src)
|
val next = MasterMetadata(masterValid, m.sharers.pop(src))(this)
|
||||||
val next = MasterMetadata(
|
|
||||||
Mux(popped.none(), masterInvalid,
|
|
||||||
Mux(popped.one(), masterExclusive, masterShared)), popped)(this)
|
|
||||||
def is(r: UInt) = incoming.r_type === r
|
|
||||||
MuxBundle(m, Array(
|
MuxBundle(m, Array(
|
||||||
is(releaseVoluntaryInvalidateData) -> next,
|
r.is(releaseVoluntaryInvalidateData) -> next,
|
||||||
is(releaseInvalidateData) -> next,
|
r.is(releaseInvalidateData) -> next,
|
||||||
is(releaseDowngradeData) -> m,
|
r.is(releaseInvalidateAck) -> next
|
||||||
is(releaseCopyData) -> m,
|
))
|
||||||
is(releaseInvalidateAck) -> next,
|
}
|
||||||
is(releaseDowngradeAck) -> m,
|
def masterMetadataOnGrant(g: Grant, m: MasterMetadata, dst: UInt) = {
|
||||||
is(releaseCopyAck) -> m
|
val cached = MasterMetadata(masterValid, m.sharers.push(dst))(this)
|
||||||
|
val uncached = MasterMetadata(masterValid, m.sharers)(this)
|
||||||
|
MuxBundle(uncached, Array(
|
||||||
|
g.is(grantReadShared) -> cached,
|
||||||
|
g.is(grantReadExclusive) -> cached,
|
||||||
|
g.is(grantReadExclusiveAck) -> cached
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -612,7 +622,7 @@ class MSICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWi
|
|||||||
|
|
||||||
def getGrantType(a: Acquire, m: MasterMetadata): UInt = {
|
def getGrantType(a: Acquire, m: MasterMetadata): UInt = {
|
||||||
MuxLookup(a.a_type, grantReadUncached, Array(
|
MuxLookup(a.a_type, grantReadUncached, Array(
|
||||||
acquireReadShared -> Mux(m.sharers.count() > UInt(0), grantReadShared, grantReadExclusive),
|
acquireReadShared -> Mux(!m.sharers.none(), grantReadShared, grantReadExclusive),
|
||||||
acquireReadExclusive -> grantReadExclusive,
|
acquireReadExclusive -> grantReadExclusive,
|
||||||
acquireReadUncached -> grantReadUncached,
|
acquireReadUncached -> grantReadUncached,
|
||||||
acquireWriteUncached -> grantWriteUncached,
|
acquireWriteUncached -> grantWriteUncached,
|
||||||
@ -635,6 +645,7 @@ class MSICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWi
|
|||||||
acquireWriteUncached -> probeInvalidate
|
acquireWriteUncached -> probeInvalidate
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
def getProbeTypeOnVoluntaryWriteback: UInt = probeInvalidate
|
||||||
|
|
||||||
def requiresOuterRead(a_type: UInt) = {
|
def requiresOuterRead(a_type: UInt) = {
|
||||||
(a_type != acquireWriteUncached)
|
(a_type != acquireWriteUncached)
|
||||||
@ -642,25 +653,25 @@ class MSICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWi
|
|||||||
def requiresOuterWrite(a_type: UInt) = {
|
def requiresOuterWrite(a_type: UInt) = {
|
||||||
(a_type === acquireWriteUncached)
|
(a_type === acquireWriteUncached)
|
||||||
}
|
}
|
||||||
def requiresOuterRead(a_type: UInt, m: MasterMetadata) = requiresOuterRead(a_type)
|
|
||||||
def requiresOuterWrite(a_type: UInt, m: MasterMetadata) = requiresOuterWrite(a_type)
|
|
||||||
def requiresAckForGrant(g_type: UInt) = g_type != grantVoluntaryAck
|
def requiresAckForGrant(g_type: UInt) = g_type != grantVoluntaryAck
|
||||||
def requiresAckForRelease(r_type: UInt) = Bool(false)
|
def requiresAckForRelease(r_type: UInt) = Bool(false)
|
||||||
def requiresSelfProbe(a_type: UInt) = Bool(false)
|
def requiresSelfProbe(a_type: UInt) = a_type === acquireReadUncached
|
||||||
|
def requiresProbes(a_type: UInt, m: MasterMetadata) = !m.sharers.none()
|
||||||
|
|
||||||
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool = (r_type === releaseVoluntaryInvalidateData)
|
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool = (r_type === releaseVoluntaryInvalidateData)
|
||||||
}
|
}
|
||||||
|
|
||||||
class MESICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWithUncached(dir) {
|
class MESICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWithUncached(dir) {
|
||||||
def nClientStates = 4
|
def nClientStates = 4
|
||||||
def nMasterStates = 3
|
def nMasterStates = 2
|
||||||
def nAcquireTypes = 7
|
def nAcquireTypes = 7
|
||||||
def nProbeTypes = 3
|
def nProbeTypes = 3
|
||||||
def nReleaseTypes = 7
|
def nReleaseTypes = 7
|
||||||
def nGrantTypes = 9
|
def nGrantTypes = 9
|
||||||
|
|
||||||
val clientInvalid :: clientShared :: clientExclusiveClean :: clientExclusiveDirty :: Nil = Enum(UInt(), nClientStates)
|
val clientInvalid :: clientShared :: clientExclusiveClean :: clientExclusiveDirty :: Nil = Enum(UInt(), nClientStates)
|
||||||
val masterInvalid :: masterShared :: masterExclusive :: Nil = Enum(UInt(), nMasterStates)
|
//val masterInvalid :: masterShared :: masterExclusive :: Nil = Enum(UInt(), nMasterStates)
|
||||||
|
val masterInvalid :: masterValid :: Nil = Enum(UInt(), nMasterStates)
|
||||||
|
|
||||||
val acquireReadShared :: acquireReadExclusive :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: Nil = Enum(UInt(), nAcquireTypes)
|
val acquireReadShared :: acquireReadExclusive :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: Nil = Enum(UInt(), nAcquireTypes)
|
||||||
val probeInvalidate :: probeDowngrade :: probeCopy :: Nil = Enum(UInt(), nProbeTypes)
|
val probeInvalidate :: probeDowngrade :: probeCopy :: Nil = Enum(UInt(), nProbeTypes)
|
||||||
@ -695,6 +706,7 @@ class MESICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyW
|
|||||||
def needsWriteback (m: ClientMetadata): Bool = {
|
def needsWriteback (m: ClientMetadata): Bool = {
|
||||||
needsTransactionOnCacheControl(M_INV, m)
|
needsTransactionOnCacheControl(M_INV, m)
|
||||||
}
|
}
|
||||||
|
def needsWriteback(m: MasterMetadata) = isValid(m)
|
||||||
|
|
||||||
def clientMetadataOnHit(cmd: UInt, m: ClientMetadata) =
|
def clientMetadataOnHit(cmd: UInt, m: ClientMetadata) =
|
||||||
ClientMetadata(Mux(isWrite(cmd), clientExclusiveDirty, m.state))(this)
|
ClientMetadata(Mux(isWrite(cmd), clientExclusiveDirty, m.state))(this)
|
||||||
@ -723,20 +735,21 @@ class MESICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyW
|
|||||||
probeCopy -> m.state
|
probeCopy -> m.state
|
||||||
)))(this)
|
)))(this)
|
||||||
def masterMetadataOnFlush = MasterMetadata(masterInvalid)(this)
|
def masterMetadataOnFlush = MasterMetadata(masterInvalid)(this)
|
||||||
def masterMetadataOnRelease(incoming: Release, m: MasterMetadata, src: UInt) = {
|
def masterMetadataOnRelease(r: Release, m: MasterMetadata, src: UInt) = {
|
||||||
val popped = m.sharers.pop(src)
|
val next = MasterMetadata(masterValid, m.sharers.pop(src))(this)
|
||||||
val next = MasterMetadata(
|
|
||||||
Mux(popped.none(), masterInvalid,
|
|
||||||
Mux(popped.one(), masterExclusive, masterShared)), popped)(this)
|
|
||||||
def is(r: UInt) = incoming.r_type === r
|
|
||||||
MuxBundle(m, Array(
|
MuxBundle(m, Array(
|
||||||
is(releaseVoluntaryInvalidateData) -> next,
|
r.is(releaseVoluntaryInvalidateData) -> next,
|
||||||
is(releaseInvalidateData) -> next,
|
r.is(releaseInvalidateData) -> next,
|
||||||
is(releaseDowngradeData) -> m,
|
r.is(releaseInvalidateAck) -> next
|
||||||
is(releaseCopyData) -> m,
|
))
|
||||||
is(releaseInvalidateAck) -> next,
|
}
|
||||||
is(releaseDowngradeAck) -> m,
|
def masterMetadataOnGrant(g: Grant, m: MasterMetadata, dst: UInt) = {
|
||||||
is(releaseCopyAck) -> m
|
val cached = MasterMetadata(masterValid, m.sharers.push(dst))(this)
|
||||||
|
val uncached = MasterMetadata(masterValid, m.sharers)(this)
|
||||||
|
MuxBundle(uncached, Array(
|
||||||
|
g.is(grantReadShared) -> cached,
|
||||||
|
g.is(grantReadExclusive) -> cached,
|
||||||
|
g.is(grantReadExclusiveAck) -> cached
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -786,7 +799,7 @@ class MESICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyW
|
|||||||
|
|
||||||
def getGrantType(a: Acquire, m: MasterMetadata): UInt = {
|
def getGrantType(a: Acquire, m: MasterMetadata): UInt = {
|
||||||
MuxLookup(a.a_type, grantReadUncached, Array(
|
MuxLookup(a.a_type, grantReadUncached, Array(
|
||||||
acquireReadShared -> Mux(m.sharers.count() > UInt(0), grantReadShared, grantReadExclusive),
|
acquireReadShared -> Mux(!m.sharers.none(), grantReadShared, grantReadExclusive),
|
||||||
acquireReadExclusive -> grantReadExclusive,
|
acquireReadExclusive -> grantReadExclusive,
|
||||||
acquireReadUncached -> grantReadUncached,
|
acquireReadUncached -> grantReadUncached,
|
||||||
acquireWriteUncached -> grantWriteUncached,
|
acquireWriteUncached -> grantWriteUncached,
|
||||||
@ -813,6 +826,7 @@ class MESICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyW
|
|||||||
acquireAtomicUncached -> probeInvalidate
|
acquireAtomicUncached -> probeInvalidate
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
def getProbeTypeOnVoluntaryWriteback: UInt = probeInvalidate
|
||||||
|
|
||||||
def requiresOuterRead(a_type: UInt) = {
|
def requiresOuterRead(a_type: UInt) = {
|
||||||
(a_type != acquireWriteUncached)
|
(a_type != acquireWriteUncached)
|
||||||
@ -820,26 +834,26 @@ class MESICoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyW
|
|||||||
def requiresOuterWrite(a_type: UInt) = {
|
def requiresOuterWrite(a_type: UInt) = {
|
||||||
(a_type === acquireWriteUncached)
|
(a_type === acquireWriteUncached)
|
||||||
}
|
}
|
||||||
def requiresOuterRead(a_type: UInt, m: MasterMetadata) = requiresOuterRead(a_type)
|
|
||||||
def requiresOuterWrite(a_type: UInt, m: MasterMetadata) = requiresOuterWrite(a_type)
|
|
||||||
|
|
||||||
def requiresAckForGrant(g_type: UInt) = g_type != grantVoluntaryAck
|
def requiresAckForGrant(g_type: UInt) = g_type != grantVoluntaryAck
|
||||||
def requiresAckForRelease(r_type: UInt) = Bool(false)
|
def requiresAckForRelease(r_type: UInt) = Bool(false)
|
||||||
def requiresSelfProbe(a_type: UInt) = Bool(false)
|
def requiresSelfProbe(a_type: UInt) = a_type === acquireReadUncached
|
||||||
|
def requiresProbes(a_type: UInt, m: MasterMetadata) = !m.sharers.none()
|
||||||
|
|
||||||
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool = (r_type === releaseVoluntaryInvalidateData)
|
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool = (r_type === releaseVoluntaryInvalidateData)
|
||||||
}
|
}
|
||||||
|
|
||||||
class MigratoryCoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWithUncached(dir) {
|
class MigratoryCoherence(dir: () => DirectoryRepresentation) extends CoherencePolicyWithUncached(dir) {
|
||||||
def nClientStates = 7
|
def nClientStates = 7
|
||||||
def nMasterStates = 3
|
def nMasterStates = 2
|
||||||
def nAcquireTypes = 8
|
def nAcquireTypes = 8
|
||||||
def nProbeTypes = 4
|
def nProbeTypes = 4
|
||||||
def nReleaseTypes = 11
|
def nReleaseTypes = 11
|
||||||
def nGrantTypes = 9
|
def nGrantTypes = 9
|
||||||
|
|
||||||
val clientInvalid :: clientShared :: clientExclusiveClean :: clientExclusiveDirty :: clientSharedByTwo :: clientMigratoryClean :: clientMigratoryDirty :: Nil = Enum(UInt(), nClientStates)
|
val clientInvalid :: clientShared :: clientExclusiveClean :: clientExclusiveDirty :: clientSharedByTwo :: clientMigratoryClean :: clientMigratoryDirty :: Nil = Enum(UInt(), nClientStates)
|
||||||
val masterInvalid :: masterShared :: masterExclusive :: Nil = Enum(UInt(), nMasterStates)
|
//val masterInvalid :: masterShared :: masterExclusive :: Nil = Enum(UInt(), nMasterStates)
|
||||||
|
val masterInvalid :: masterValid :: Nil = Enum(UInt(), nMasterStates)
|
||||||
|
|
||||||
val acquireReadShared :: acquireReadExclusive :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: acquireInvalidateOthers :: Nil = Enum(UInt(), nAcquireTypes)
|
val acquireReadShared :: acquireReadExclusive :: acquireReadUncached :: acquireWriteUncached :: acquireReadWordUncached :: acquireWriteWordUncached :: acquireAtomicUncached :: acquireInvalidateOthers :: Nil = Enum(UInt(), nAcquireTypes)
|
||||||
val probeInvalidate :: probeDowngrade :: probeCopy :: probeInvalidateOthers :: Nil = Enum(UInt(), nProbeTypes)
|
val probeInvalidate :: probeDowngrade :: probeCopy :: probeInvalidateOthers :: Nil = Enum(UInt(), nProbeTypes)
|
||||||
@ -873,6 +887,7 @@ class MigratoryCoherence(dir: () => DirectoryRepresentation) extends CoherencePo
|
|||||||
def needsWriteback (m: ClientMetadata): Bool = {
|
def needsWriteback (m: ClientMetadata): Bool = {
|
||||||
needsTransactionOnCacheControl(M_INV, m)
|
needsTransactionOnCacheControl(M_INV, m)
|
||||||
}
|
}
|
||||||
|
def needsWriteback(m: MasterMetadata) = isValid(m)
|
||||||
|
|
||||||
def clientMetadataOnHit(cmd: UInt, m: ClientMetadata) = ClientMetadata(
|
def clientMetadataOnHit(cmd: UInt, m: ClientMetadata) = ClientMetadata(
|
||||||
Mux(isWrite(cmd), MuxLookup(m.state, clientExclusiveDirty, Array(
|
Mux(isWrite(cmd), MuxLookup(m.state, clientExclusiveDirty, Array(
|
||||||
@ -914,25 +929,24 @@ class MigratoryCoherence(dir: () => DirectoryRepresentation) extends CoherencePo
|
|||||||
clientMigratoryDirty -> clientInvalid))
|
clientMigratoryDirty -> clientInvalid))
|
||||||
)))(this)
|
)))(this)
|
||||||
def masterMetadataOnFlush = MasterMetadata(masterInvalid)(this)
|
def masterMetadataOnFlush = MasterMetadata(masterInvalid)(this)
|
||||||
def masterMetadataOnRelease(incoming: Release, m: MasterMetadata, src: UInt) = {
|
def masterMetadataOnRelease(r: Release, m: MasterMetadata, src: UInt) = {
|
||||||
val popped = m.sharers.pop(src)
|
val next = MasterMetadata(masterValid, m.sharers.pop(src))(this)
|
||||||
val next = MasterMetadata(
|
|
||||||
Mux(popped.none(), masterInvalid,
|
|
||||||
Mux(popped.one(), masterExclusive, masterShared)),
|
|
||||||
popped)(this)
|
|
||||||
def is(r: UInt) = incoming.r_type === r
|
|
||||||
MuxBundle(m, Array(
|
MuxBundle(m, Array(
|
||||||
is(releaseVoluntaryInvalidateData) -> next,
|
r.is(releaseVoluntaryInvalidateData) -> next,
|
||||||
is(releaseInvalidateData) -> next,
|
r.is(releaseInvalidateData) -> next,
|
||||||
is(releaseDowngradeData) -> m,
|
r.is(releaseInvalidateAck) -> next,
|
||||||
is(releaseCopyData) -> m,
|
r.is(releaseInvalidateDataMigratory) -> next,
|
||||||
is(releaseInvalidateAck) -> next,
|
r.is(releaseInvalidateAckMigratory) -> next
|
||||||
is(releaseDowngradeAck) -> m,
|
))
|
||||||
is(releaseCopyAck) -> m,
|
}
|
||||||
is(releaseDowngradeDataMigratory) -> m,
|
def masterMetadataOnGrant(g: Grant, m: MasterMetadata, dst: UInt) = {
|
||||||
is(releaseDowngradeAckHasCopy) -> m,
|
val cached = MasterMetadata(masterValid, m.sharers.push(dst))(this)
|
||||||
is(releaseInvalidateDataMigratory) -> next,
|
val uncached = MasterMetadata(masterValid, m.sharers)(this)
|
||||||
is(releaseInvalidateAckMigratory) -> next
|
MuxBundle(uncached, Array(
|
||||||
|
g.is(grantReadShared) -> cached,
|
||||||
|
g.is(grantReadExclusive) -> cached,
|
||||||
|
g.is(grantReadExclusiveAck) -> cached,
|
||||||
|
g.is(grantReadMigratory) -> cached
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -983,7 +997,7 @@ class MigratoryCoherence(dir: () => DirectoryRepresentation) extends CoherencePo
|
|||||||
|
|
||||||
def getGrantType(a: Acquire, m: MasterMetadata): UInt = {
|
def getGrantType(a: Acquire, m: MasterMetadata): UInt = {
|
||||||
MuxLookup(a.a_type, grantReadUncached, Array(
|
MuxLookup(a.a_type, grantReadUncached, Array(
|
||||||
acquireReadShared -> Mux(m.sharers.count() > UInt(0), grantReadShared, grantReadExclusive), //TODO: what is count? Depend on release.p_type???
|
acquireReadShared -> Mux(!m.sharers.none(), grantReadShared, grantReadExclusive), //TODO: what is count? Depend on release.p_type???
|
||||||
acquireReadExclusive -> grantReadExclusive,
|
acquireReadExclusive -> grantReadExclusive,
|
||||||
acquireReadUncached -> grantReadUncached,
|
acquireReadUncached -> grantReadUncached,
|
||||||
acquireWriteUncached -> grantWriteUncached,
|
acquireWriteUncached -> grantWriteUncached,
|
||||||
@ -1012,6 +1026,7 @@ class MigratoryCoherence(dir: () => DirectoryRepresentation) extends CoherencePo
|
|||||||
acquireInvalidateOthers -> probeInvalidateOthers
|
acquireInvalidateOthers -> probeInvalidateOthers
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
def getProbeTypeOnVoluntaryWriteback: UInt = probeInvalidate
|
||||||
|
|
||||||
def requiresOuterRead(a_type: UInt) = {
|
def requiresOuterRead(a_type: UInt) = {
|
||||||
(a_type != acquireWriteUncached && a_type != acquireInvalidateOthers)
|
(a_type != acquireWriteUncached && a_type != acquireInvalidateOthers)
|
||||||
@ -1019,12 +1034,11 @@ class MigratoryCoherence(dir: () => DirectoryRepresentation) extends CoherencePo
|
|||||||
def requiresOuterWrite(a_type: UInt) = {
|
def requiresOuterWrite(a_type: UInt) = {
|
||||||
(a_type === acquireWriteUncached || a_type === acquireWriteWordUncached || a_type === acquireAtomicUncached)
|
(a_type === acquireWriteUncached || a_type === acquireWriteWordUncached || a_type === acquireAtomicUncached)
|
||||||
}
|
}
|
||||||
def requiresOuterRead(a_type: UInt, m: MasterMetadata) = requiresOuterRead(a_type)
|
|
||||||
def requiresOuterWrite(a_type: UInt, m: MasterMetadata) = requiresOuterWrite(a_type)
|
|
||||||
|
|
||||||
def requiresAckForGrant(g_type: UInt) = g_type != grantVoluntaryAck
|
def requiresAckForGrant(g_type: UInt) = g_type != grantVoluntaryAck
|
||||||
def requiresAckForRelease(r_type: UInt) = Bool(false)
|
def requiresAckForRelease(r_type: UInt) = Bool(false)
|
||||||
def requiresSelfProbe(a_type: UInt) = Bool(false)
|
def requiresSelfProbe(a_type: UInt) = a_type === acquireReadUncached
|
||||||
|
def requiresProbes(a_type: UInt, m: MasterMetadata) = !m.sharers.none()
|
||||||
|
|
||||||
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool = (r_type === releaseVoluntaryInvalidateData)
|
def pendingVoluntaryReleaseIsSufficient(r_type: UInt, p_type: UInt): Bool = (r_type === releaseVoluntaryInvalidateData)
|
||||||
}
|
}
|
||||||
|
@ -77,6 +77,7 @@ class Acquire extends ClientSourcedMessage
|
|||||||
val write_mask = Bits(width = params(TLWriteMaskBits))
|
val write_mask = Bits(width = params(TLWriteMaskBits))
|
||||||
val subword_addr = Bits(width = params(TLWordAddrBits))
|
val subword_addr = Bits(width = params(TLWordAddrBits))
|
||||||
val atomic_opcode = Bits(width = params(TLAtomicOpBits))
|
val atomic_opcode = Bits(width = params(TLAtomicOpBits))
|
||||||
|
def is(t: UInt) = a_type === t
|
||||||
}
|
}
|
||||||
|
|
||||||
object Probe
|
object Probe
|
||||||
@ -94,6 +95,7 @@ class Probe extends MasterSourcedMessage
|
|||||||
with HasPhysicalAddress
|
with HasPhysicalAddress
|
||||||
with HasMasterTransactionId {
|
with HasMasterTransactionId {
|
||||||
val p_type = UInt(width = params(TLCoherence).probeTypeWidth)
|
val p_type = UInt(width = params(TLCoherence).probeTypeWidth)
|
||||||
|
def is(t: UInt) = p_type === t
|
||||||
}
|
}
|
||||||
|
|
||||||
object Release
|
object Release
|
||||||
@ -127,6 +129,7 @@ class Release extends ClientSourcedMessage
|
|||||||
with HasMasterTransactionId
|
with HasMasterTransactionId
|
||||||
with HasTileLinkData {
|
with HasTileLinkData {
|
||||||
val r_type = UInt(width = params(TLCoherence).releaseTypeWidth)
|
val r_type = UInt(width = params(TLCoherence).releaseTypeWidth)
|
||||||
|
def is(t: UInt) = r_type === t
|
||||||
}
|
}
|
||||||
|
|
||||||
object Grant
|
object Grant
|
||||||
@ -151,6 +154,7 @@ class Grant extends MasterSourcedMessage
|
|||||||
with HasClientTransactionId
|
with HasClientTransactionId
|
||||||
with HasMasterTransactionId {
|
with HasMasterTransactionId {
|
||||||
val g_type = UInt(width = params(TLCoherence).grantTypeWidth)
|
val g_type = UInt(width = params(TLCoherence).grantTypeWidth)
|
||||||
|
def is(t: UInt) = g_type === t
|
||||||
}
|
}
|
||||||
|
|
||||||
class Finish extends ClientSourcedMessage with HasMasterTransactionId
|
class Finish extends ClientSourcedMessage with HasMasterTransactionId
|
||||||
|
Loading…
Reference in New Issue
Block a user