提交 e98af34d 编写于 作者: Z zhanglinjuan

MissQueue/DCache: reply GrantAck via channel E before sending pipe req

上级 70051210
......@@ -253,10 +253,12 @@ class DCacheImp(outer: DCache) extends LazyModuleImp(outer) with HasDCacheParame
// tilelink stuff
bus.a <> missQueue.io.mem_acquire
bus.e <> missQueue.io.mem_finish
missQueue.io.probe_req := bus.b.bits.address
//----------------------------------------
// probe
probeQueue.io.mem_probe <> bus.b
// probeQueue.io.mem_probe <> bus.b
block_decoupled(bus.b, probeQueue.io.mem_probe, missQueue.io.probe_block)
//----------------------------------------
// mainPipe
......
......@@ -58,9 +58,12 @@ class MissEntry(edge: TLEdgeOut) extends DCacheModule
val pipe_req = DecoupledIO(new MainPipeReq)
val pipe_resp = Flipped(ValidIO(new MainPipeResp))
// block probe
val block_addr = ValidIO(UInt(PAddrBits.W))
})
// MSHR:
// old MSHR:
// 1. receive req
// 2. send acquire req
// 3. receive grant resp
......@@ -72,7 +75,10 @@ class MissEntry(edge: TLEdgeOut) extends DCacheModule
// See Tilelink spec 1.8.1 page 69
// A slave should not issue a Probe if there is a pending GrantAck on the block. Once the Probe is
// issued, the slave should not issue further Probes on that block until it receives a ProbeAck.
val s_invalid :: s_refill_req :: s_refill_resp :: s_main_pipe_req :: s_main_pipe_resp :: s_mem_finish :: Nil = Enum(6)
// new MSHR:
// send finish to end the transaction before sending pipe_req
val s_invalid :: s_refill_req :: s_refill_resp :: s_mem_finish :: s_main_pipe_req :: s_main_pipe_resp :: Nil = Enum(6)
val state = RegInit(s_invalid)
......@@ -147,6 +153,9 @@ class MissEntry(edge: TLEdgeOut) extends DCacheModule
io.pipe_req.valid := false.B
io.pipe_req.bits := DontCare
io.block_addr.valid := state === s_mem_finish || state === s_main_pipe_req || state === s_main_pipe_resp
io.block_addr.bits := req.addr
when (state =/= s_invalid) {
XSDebug("entry: %d state: %d\n", io.id, state)
req.dump()
......@@ -277,7 +286,7 @@ class MissEntry(edge: TLEdgeOut) extends DCacheModule
grantack.bits := edge.GrantAck(io.mem_grant.bits)
grant_param := io.mem_grant.bits.param
state := s_main_pipe_req
state := s_mem_finish
}
}
......@@ -316,7 +325,7 @@ class MissEntry(edge: TLEdgeOut) extends DCacheModule
when (state === s_main_pipe_resp) {
when (io.pipe_resp.fire()) {
state := s_mem_finish
state := s_invalid
}
}
......@@ -326,7 +335,7 @@ class MissEntry(edge: TLEdgeOut) extends DCacheModule
when (io.mem_finish.fire()) {
grantack.valid := false.B
state := s_invalid
state := s_main_pipe_req
}
}
}
......@@ -344,6 +353,10 @@ class MissQueue(edge: TLEdgeOut) extends DCacheModule with HasTLDump
val pipe_req = DecoupledIO(new MainPipeReq)
val pipe_resp = Flipped(ValidIO(new MainPipeResp))
// block probe
val probe_req = Input(UInt(PAddrBits.W))
val probe_block = Output(Bool())
})
val pipe_req_arb = Module(new RRArbiter(new MainPipeReq, cfg.nMissEntries))
......@@ -353,6 +366,7 @@ class MissQueue(edge: TLEdgeOut) extends DCacheModule with HasTLDump
val primary_ready = Wire(Vec(cfg.nMissEntries, Bool()))
val secondary_ready = Wire(Vec(cfg.nMissEntries, Bool()))
val secondary_reject = Wire(Vec(cfg.nMissEntries, Bool()))
val probe_block_vec = Wire(Vec(cfg.nMissEntries, Bool()))
// try merging with existing reqs
val merge = secondary_ready.asUInt.orR
......@@ -390,6 +404,7 @@ class MissQueue(edge: TLEdgeOut) extends DCacheModule with HasTLDump
primary_ready(i) := entry.io.primary_ready
secondary_ready(i) := entry.io.secondary_ready
secondary_reject(i) := entry.io.secondary_reject
probe_block_vec(i) := entry.io.block_addr.valid && entry.io.block_addr.bits === io.probe_req
entry.io.req := io.req.bits
// entry refill
......@@ -440,6 +455,7 @@ class MissQueue(edge: TLEdgeOut) extends DCacheModule with HasTLDump
io.pipe_req <> pipe_req_arb.io.out
io.probe_block := probe_block_vec.asUInt.orR
// print all input/output requests for debug purpose
......@@ -492,6 +508,10 @@ class MissQueue(edge: TLEdgeOut) extends DCacheModule with HasTLDump
io.mem_finish.bits.dump
}
when (io.probe_block) {
XSDebug(p"block probe req ${Hexadecimal(io.probe_req)}\n")
}
if (!env.FPGAPlatform && !env.DualCore) {
ExcitingUtils.addSource(io.req.fire(), "perfCntDCacheMiss", Perf)
}
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册