1
0

make sure trackers can handle case where there are no caching clients

This commit is contained in:
Howard Mao 2016-06-27 16:29:51 -07:00
parent a93a70c8ec
commit ec5b9dfc86

View File

@ -3,6 +3,7 @@
package uncore package uncore
import Chisel._ import Chisel._
import cde.{Parameters, Field} import cde.{Parameters, Field}
import scala.math.max
class TrackerAllocation extends Bundle { class TrackerAllocation extends Bundle {
val matches = Bool(OUTPUT) val matches = Bool(OUTPUT)
@ -321,30 +322,41 @@ trait EmitsInnerProbes extends HasBlockAddressBuffer
with HasPendingBitHelpers { with HasPendingBitHelpers {
def io: HierarchicalXactTrackerIO def io: HierarchicalXactTrackerIO
val pending_iprbs = Reg(UInt(width = innerNCachingClients)) val needs_probes = (innerNCachingClients > 0)
val pending_iprbs = Reg(UInt(width = max(innerNCachingClients, 1)))
val curr_probe_dst = PriorityEncoder(pending_iprbs) val curr_probe_dst = PriorityEncoder(pending_iprbs)
val irel_counter = Wire(new TwoWayBeatCounterStatus)
def full_representation: UInt def full_representation: UInt
def initializeProbes() { pending_iprbs := full_representation & ~io.incoherent.toBits } def initializeProbes() {
if (needs_probes)
pending_iprbs := full_representation & ~io.incoherent.toBits
else
pending_iprbs := UInt(0)
}
def irel_same_xact = io.irel().conflicts(xact_addr_block) && def irel_same_xact = io.irel().conflicts(xact_addr_block) &&
!io.irel().isVoluntary() && !io.irel().isVoluntary() &&
state === s_inner_probe state === s_inner_probe
def innerProbe(prb: Probe, next: UInt) { def innerProbe(prb: Probe, next: UInt) {
pending_iprbs := pending_iprbs & dropPendingBitAtDest(io.inner.probe) if (needs_probes) {
io.inner.probe.valid := state === s_inner_probe && pending_iprbs.orR val irel_counter = Wire(new TwoWayBeatCounterStatus)
io.inner.probe.bits := prb
connectTwoWayBeatCounters(
status = irel_counter,
up = io.inner.probe,
down = io.inner.release,
max = innerNCachingClients,
trackDown = (r: Release) => (state =/= s_idle) && !r.isVoluntary())
when(state === s_inner_probe && !(pending_iprbs.orR || irel_counter.pending)) { pending_iprbs := pending_iprbs & dropPendingBitAtDest(io.inner.probe)
state := next io.inner.probe.valid := state === s_inner_probe && pending_iprbs.orR
io.inner.probe.bits := prb
connectTwoWayBeatCounters(
status = irel_counter,
up = io.inner.probe,
down = io.inner.release,
max = innerNCachingClients,
trackDown = (r: Release) => (state =/= s_idle) && !r.isVoluntary())
when(state === s_inner_probe && !(pending_iprbs.orR || irel_counter.pending)) {
state := next
}
} else {
when (state === s_inner_probe) { state := next }
} }
//N.B. no pending bits added to scoreboard because all handled in s_inner_probe //N.B. no pending bits added to scoreboard because all handled in s_inner_probe