refactor(cache): 进行部分变量替换
This commit is contained in:
parent
4355bc3b5d
commit
b45e0194fa
|
@ -107,20 +107,21 @@ class DCache(cacheConfig: CacheConfig)(implicit config: CpuConfig) extends Modul
|
|||
val dirty = RegInit(VecInit(Seq.fill(nindex)(VecInit(Seq.fill(nway)(false.B)))))
|
||||
val lru = RegInit(VecInit(Seq.fill(nindex)(false.B))) // TODO:支持更多路数,目前只支持2路
|
||||
|
||||
val writeFifo = Module(new Queue(new WriteBufferUnit(), writeFifoDepth))
|
||||
val writeFifo = Module(new Queue(new WriteBufferUnit(), writeFifoDepth))
|
||||
val writeFifo_axi_busy = RegInit(false.B)
|
||||
val writeFifo_busy = (writeFifo.io.deq.valid || writeFifo_axi_busy)
|
||||
|
||||
writeFifo.io.enq.valid := false.B
|
||||
writeFifo.io.enq.bits := 0.U.asTypeOf(new WriteBufferUnit())
|
||||
writeFifo.io.deq.ready := false.B
|
||||
|
||||
val axi_cnt = Counter(cached_len + 1)
|
||||
val read_ready_cnt = RegInit(0.U((offsetWidth - log2Ceil(XLEN / 8)).W))
|
||||
val axi_cnt = Counter(cached_len + 1)
|
||||
|
||||
// * victim cache * //
|
||||
val victim = RegInit(0.U.asTypeOf(new Bundle {
|
||||
val valid = Bool()
|
||||
val index = UInt(indexWidth.W)
|
||||
val waddr = UInt((indexWidth + offsetWidth - log2Ceil(XLEN / 8) + 1).W)
|
||||
val waddr = UInt((indexWidth + offsetWidth - log2Ceil(XLEN / 8)).W)
|
||||
val wstrb = Vec(nway, UInt(AXI_STRB_WID.W))
|
||||
val working = Bool()
|
||||
val writeback = Bool()
|
||||
|
@ -128,12 +129,12 @@ class DCache(cacheConfig: CacheConfig)(implicit config: CpuConfig) extends Modul
|
|||
val victim_cnt = Counter(cached_len + 1)
|
||||
val victim_addr = Cat(victim.index, victim_cnt.value)
|
||||
|
||||
val fence_index = index
|
||||
val fence = RegInit(0.U.asTypeOf(new Bundle {
|
||||
val working = Bool()
|
||||
}))
|
||||
val fence = RegInit(false.B)
|
||||
|
||||
// 用于解决在replace时读写时序不一致的问题
|
||||
val read_ready_cnt = RegInit(0.U((offsetWidth - log2Ceil(XLEN / 8)).W))
|
||||
val read_buffer = RegInit(VecInit(Seq.fill(nbank * dataBlocksPerBank)(0.U(XLEN.W))))
|
||||
|
||||
val read_buffer = RegInit(VecInit(Seq.fill(16)(0.U(XLEN.W))))
|
||||
val ar_handshake = RegInit(false.B)
|
||||
val aw_handshake = RegInit(false.B)
|
||||
|
||||
|
@ -215,7 +216,6 @@ class DCache(cacheConfig: CacheConfig)(implicit config: CpuConfig) extends Modul
|
|||
|
||||
last_wstrb(i) := Cat((AXI_STRB_WID - 1 to 0 by -1).map(j => Fill(8, replace_wstrb(i)(j))))
|
||||
}
|
||||
val writeFifo_axi_busy = RegInit(false.B)
|
||||
|
||||
val ar = RegInit(0.U.asTypeOf(new AR()))
|
||||
val arvalid = RegInit(false.B)
|
||||
|
@ -295,8 +295,8 @@ class DCache(cacheConfig: CacheConfig)(implicit config: CpuConfig) extends Modul
|
|||
|
||||
state := s_wait
|
||||
}
|
||||
}.elsewhen(!(writeFifo.io.deq.valid || writeFifo_axi_busy)) {
|
||||
ar.addr := Mux(io.cpu.rlen === 2.U, Cat(io.cpu.tlb.paddr(31, 2), 0.U(2.W)), io.cpu.tlb.paddr)
|
||||
}.elsewhen(!writeFifo_busy) {
|
||||
ar.addr := io.cpu.tlb.paddr
|
||||
ar.len := 0.U
|
||||
ar.size := io.cpu.rlen
|
||||
arvalid := true.B
|
||||
|
@ -328,19 +328,19 @@ class DCache(cacheConfig: CacheConfig)(implicit config: CpuConfig) extends Modul
|
|||
}
|
||||
}
|
||||
}.elsewhen(io.cpu.fence) {
|
||||
when(dirty(fence_index).contains(true.B)) {
|
||||
when(!(writeFifo.io.deq.valid || writeFifo_axi_busy)) {
|
||||
when(dirty(index).contains(true.B)) {
|
||||
when(!writeFifo_busy) {
|
||||
state := s_writeback
|
||||
axi_cnt.reset()
|
||||
victim.index := fence_index
|
||||
victim.index := index
|
||||
victim_cnt.reset()
|
||||
read_ready_cnt := 0.U
|
||||
victim.valid := true.B
|
||||
}
|
||||
}.otherwise {
|
||||
when(valid(fence_index).contains(true.B)) {
|
||||
valid(fence_index)(0) := false.B
|
||||
valid(fence_index)(1) := false.B
|
||||
when(valid(index).contains(true.B)) {
|
||||
valid(index)(0) := false.B
|
||||
valid(index)(1) := false.B
|
||||
}
|
||||
state := s_wait
|
||||
}
|
||||
|
@ -357,18 +357,18 @@ class DCache(cacheConfig: CacheConfig)(implicit config: CpuConfig) extends Modul
|
|||
}
|
||||
}
|
||||
is(s_writeback) {
|
||||
when(fence.working) {
|
||||
when(fence) {
|
||||
when(victim_cnt.value =/= (cached_len).U) {
|
||||
victim_cnt.inc()
|
||||
}
|
||||
read_ready_cnt := victim_cnt.value
|
||||
read_buffer(read_ready_cnt) := data(dirty(fence_index)(1))
|
||||
read_buffer(read_ready_cnt) := data(dirty(index)(1))
|
||||
when(!aw_handshake) {
|
||||
aw.addr := Cat(tag(dirty(fence_index)(1)), fence_index, 0.U(6.W))
|
||||
aw.addr := Cat(tag(dirty(index)(1)), index, 0.U(offsetWidth.W))
|
||||
aw.len := cached_len.U
|
||||
aw.size := cached_size.U
|
||||
awvalid := true.B
|
||||
w.data := data(dirty(fence_index)(1))
|
||||
w.data := data(dirty(index)(1))
|
||||
w.strb := ~0.U(AXI_STRB_WID.W)
|
||||
w.last := false.B
|
||||
wvalid := true.B
|
||||
|
@ -383,7 +383,7 @@ class DCache(cacheConfig: CacheConfig)(implicit config: CpuConfig) extends Modul
|
|||
}.otherwise {
|
||||
w.data := Mux(
|
||||
((axi_cnt.value + 1.U) === read_ready_cnt),
|
||||
data(dirty(fence_index)(1)),
|
||||
data(dirty(index)(1)),
|
||||
read_buffer(axi_cnt.value + 1.U)
|
||||
)
|
||||
axi_cnt.inc()
|
||||
|
@ -393,20 +393,20 @@ class DCache(cacheConfig: CacheConfig)(implicit config: CpuConfig) extends Modul
|
|||
}
|
||||
}
|
||||
when(io.axi.b.valid) {
|
||||
dirty(fence_index)(dirty(fence_index)(1)) := false.B
|
||||
fence.working := false.B
|
||||
victim.valid := false.B
|
||||
acc_err := io.axi.b.bits.resp =/= RESP_OKEY.U
|
||||
state := s_idle
|
||||
dirty(index)(dirty(index)(1)) := false.B
|
||||
fence := false.B
|
||||
victim.valid := false.B
|
||||
acc_err := io.axi.b.bits.resp =/= RESP_OKEY.U
|
||||
state := s_idle
|
||||
}
|
||||
}.otherwise {
|
||||
aw_handshake := false.B
|
||||
fence.working := true.B
|
||||
aw_handshake := false.B
|
||||
fence := true.B
|
||||
victim_cnt.inc()
|
||||
}
|
||||
}
|
||||
is(s_replace) {
|
||||
when(!(writeFifo.io.deq.valid || writeFifo_axi_busy)) {
|
||||
when(!writeFifo_busy) {
|
||||
when(victim.working) {
|
||||
when(victim.writeback) {
|
||||
when(victim_cnt.value =/= (cached_len).U) {
|
||||
|
|
|
@ -148,7 +148,7 @@ class ICache(cacheConfig: CacheConfig)(implicit config: CpuConfig) extends Modul
|
|||
Seq.tabulate(instFetchNum)(i => cache_hit_available && i.U <= ((instFetchNum - 1).U - bank_offset))
|
||||
)
|
||||
|
||||
val saved = RegInit(VecInit(Seq.fill(instFetchNum)(0.U.asTypeOf(new Bundle {
|
||||
val rdata_in_wait = RegInit(VecInit(Seq.fill(instFetchNum)(0.U.asTypeOf(new Bundle {
|
||||
val inst = UInt(INST_WID.W)
|
||||
val valid = Bool()
|
||||
}))))
|
||||
|
@ -185,8 +185,8 @@ class ICache(cacheConfig: CacheConfig)(implicit config: CpuConfig) extends Modul
|
|||
}
|
||||
|
||||
for { i <- 0 until instFetchNum } {
|
||||
io.cpu.inst_valid(i) := Mux(state === s_idle && !tlb_fill, inst_valid(i), saved(i).valid) && io.cpu.req
|
||||
io.cpu.inst(i) := Mux(state === s_idle && !tlb_fill, inst(i), saved(i).inst)
|
||||
io.cpu.inst_valid(i) := Mux(state === s_idle && !tlb_fill, inst_valid(i), rdata_in_wait(i).valid) && io.cpu.req
|
||||
io.cpu.inst(i) := Mux(state === s_idle && !tlb_fill, inst(i), rdata_in_wait(i).inst)
|
||||
}
|
||||
|
||||
for { i <- 0 until nway } {
|
||||
|
@ -222,16 +222,16 @@ class ICache(cacheConfig: CacheConfig)(implicit config: CpuConfig) extends Modul
|
|||
is(s_idle) {
|
||||
when(tlb_fill) {
|
||||
when(!io.cpu.tlb.hit) {
|
||||
state := s_wait
|
||||
saved(0).inst := 0.U
|
||||
saved(0).valid := true.B
|
||||
state := s_wait
|
||||
rdata_in_wait(0).inst := 0.U
|
||||
rdata_in_wait(0).valid := true.B
|
||||
}
|
||||
}.elsewhen(io.cpu.req) {
|
||||
when(addr_err) {
|
||||
acc_err := true.B
|
||||
state := s_wait
|
||||
saved(0).inst := 0.U
|
||||
saved(0).valid := true.B
|
||||
acc_err := true.B
|
||||
state := s_wait
|
||||
rdata_in_wait(0).inst := 0.U
|
||||
rdata_in_wait(0).valid := true.B
|
||||
}.elsewhen(!io.cpu.tlb.translation_ok) {
|
||||
tlb_fill := true.B
|
||||
}.elsewhen(io.cpu.tlb.uncached) {
|
||||
|
@ -258,8 +258,8 @@ class ICache(cacheConfig: CacheConfig)(implicit config: CpuConfig) extends Modul
|
|||
replace_way := ~select_way
|
||||
when(!io.cpu.complete_single_request) {
|
||||
state := s_wait
|
||||
(1 until instFetchNum).foreach(i => saved(i).inst := inst(i))
|
||||
(0 until instFetchNum).foreach(i => saved(i).valid := inst_valid(i))
|
||||
(1 until instFetchNum).foreach(i => rdata_in_wait(i).inst := inst(i))
|
||||
(0 until instFetchNum).foreach(i => rdata_in_wait(i).valid := inst_valid(i))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -272,11 +272,11 @@ class ICache(cacheConfig: CacheConfig)(implicit config: CpuConfig) extends Modul
|
|||
}
|
||||
}.elsewhen(io.axi.r.fire) {
|
||||
// * uncached not support burst transport * //
|
||||
state := s_wait
|
||||
saved(0).inst := Mux(ar.addr(2), io.axi.r.bits.data(63, 32), io.axi.r.bits.data(31, 0))
|
||||
saved(0).valid := true.B
|
||||
rready := false.B
|
||||
acc_err := io.axi.r.bits.resp =/= RESP_OKEY.U
|
||||
state := s_wait
|
||||
rdata_in_wait(0).inst := Mux(ar.addr(2), io.axi.r.bits.data(63, 32), io.axi.r.bits.data(31, 0))
|
||||
rdata_in_wait(0).valid := true.B
|
||||
rready := false.B
|
||||
acc_err := io.axi.r.bits.resp =/= RESP_OKEY.U
|
||||
}
|
||||
}
|
||||
is(s_replace) {
|
||||
|
@ -304,7 +304,7 @@ class ICache(cacheConfig: CacheConfig)(implicit config: CpuConfig) extends Modul
|
|||
// 等待流水线的allow_to_go信号,防止多次发出读请求
|
||||
when(io.cpu.complete_single_request) {
|
||||
state := s_idle
|
||||
(0 until instFetchNum).foreach(i => saved(i).valid := false.B)
|
||||
(0 until instFetchNum).foreach(i => rdata_in_wait(i).valid := false.B)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -114,105 +114,105 @@ class DataMemoryAccess(implicit val config: CpuConfig) extends Module {
|
|||
lsExe.in.info.op := func
|
||||
lsExe.in.wdata := src2
|
||||
io.memoryUnit.out.ready := lsExe.out.ready && io.dataMemory.out.en || scInvalid
|
||||
when(io.memoryUnit.out.ready) {
|
||||
when(allow_to_go) {
|
||||
state := s_idle
|
||||
}
|
||||
state := s_wait_allow;
|
||||
}
|
||||
when(amoReq) { state := s_amo_l }
|
||||
when(lrReq) {
|
||||
lsExe.in.mem_en := true.B
|
||||
lsExe.in.mem_addr := src1
|
||||
lsExe.in.info.op := Mux(atomWidthD, LSUOpType.ld, LSUOpType.lw)
|
||||
lsExe.in.wdata := DontCare
|
||||
io.memoryUnit.out.ready := lsExe.out.ready && io.dataMemory.out.en
|
||||
when(lsExe.out.ready) {
|
||||
when(allow_to_go) {
|
||||
state := s_idle
|
||||
}
|
||||
state := s_wait_allow;
|
||||
}
|
||||
}
|
||||
when(scReq) { state := Mux(scInvalid, s_idle, s_sc) }
|
||||
// when(io.memoryUnit.out.ready) {
|
||||
// when(allow_to_go) {
|
||||
// state := s_idle
|
||||
// }
|
||||
// state := s_wait_allow;
|
||||
// }
|
||||
// when(amoReq) { state := s_amo_l }
|
||||
// when(lrReq) {
|
||||
// lsExe.in.mem_en := true.B
|
||||
// lsExe.in.mem_addr := src1
|
||||
// lsExe.in.info.op := Mux(atomWidthD, LSUOpType.ld, LSUOpType.lw)
|
||||
// lsExe.in.wdata := DontCare
|
||||
// io.memoryUnit.out.ready := lsExe.out.ready && io.dataMemory.out.en
|
||||
// when(lsExe.out.ready) {
|
||||
// when(allow_to_go) {
|
||||
// state := s_idle
|
||||
// }
|
||||
// state := s_wait_allow;
|
||||
// }
|
||||
// }
|
||||
// when(scReq) { state := Mux(scInvalid, s_idle, s_sc) }
|
||||
}
|
||||
|
||||
is(s_amo_l) {
|
||||
lsExe.in.mem_en := true.B
|
||||
lsExe.in.mem_addr := src1
|
||||
lsExe.in.info.op := Mux(atomWidthD, LSUOpType.ld, LSUOpType.lw)
|
||||
lsExe.in.wdata := DontCare
|
||||
io.memoryUnit.out.ready := false.B
|
||||
when(lsExe.out.ready) {
|
||||
state := s_amo_l_wait;
|
||||
}
|
||||
}
|
||||
// is(s_amo_l) {
|
||||
// lsExe.in.mem_en := true.B
|
||||
// lsExe.in.mem_addr := src1
|
||||
// lsExe.in.info.op := Mux(atomWidthD, LSUOpType.ld, LSUOpType.lw)
|
||||
// lsExe.in.wdata := DontCare
|
||||
// io.memoryUnit.out.ready := false.B
|
||||
// when(lsExe.out.ready) {
|
||||
// state := s_amo_l_wait;
|
||||
// }
|
||||
// }
|
||||
|
||||
is(s_amo_l_wait) {
|
||||
lsExe.in.mem_en := false.B
|
||||
lsExe.in.mem_addr := src1
|
||||
lsExe.in.info.op := Mux(atomWidthD, LSUOpType.ld, LSUOpType.lw)
|
||||
lsExe.in.wdata := DontCare
|
||||
io.memoryUnit.out.ready := false.B
|
||||
atomMemReg := lsExe.out.rdata
|
||||
atomRegReg := lsExe.out.rdata
|
||||
when(lsExe.out.ready) {
|
||||
state := s_amo_a;
|
||||
}
|
||||
}
|
||||
// is(s_amo_l_wait) {
|
||||
// lsExe.in.mem_en := false.B
|
||||
// lsExe.in.mem_addr := src1
|
||||
// lsExe.in.info.op := Mux(atomWidthD, LSUOpType.ld, LSUOpType.lw)
|
||||
// lsExe.in.wdata := DontCare
|
||||
// io.memoryUnit.out.ready := false.B
|
||||
// atomMemReg := lsExe.out.rdata
|
||||
// atomRegReg := lsExe.out.rdata
|
||||
// when(lsExe.out.ready) {
|
||||
// state := s_amo_a;
|
||||
// }
|
||||
// }
|
||||
|
||||
is(s_amo_a) {
|
||||
lsExe.in.mem_en := false.B
|
||||
lsExe.in.mem_addr := DontCare
|
||||
lsExe.in.info.op := DontCare
|
||||
lsExe.in.wdata := DontCare
|
||||
io.memoryUnit.out.ready := false.B
|
||||
state := s_amo_s
|
||||
atomMemReg := atomAlu.out.result
|
||||
}
|
||||
// is(s_amo_a) {
|
||||
// lsExe.in.mem_en := false.B
|
||||
// lsExe.in.mem_addr := DontCare
|
||||
// lsExe.in.info.op := DontCare
|
||||
// lsExe.in.wdata := DontCare
|
||||
// io.memoryUnit.out.ready := false.B
|
||||
// state := s_amo_s
|
||||
// atomMemReg := atomAlu.out.result
|
||||
// }
|
||||
|
||||
is(s_amo_s) {
|
||||
lsExe.in.mem_en := true.B
|
||||
lsExe.in.mem_addr := src1
|
||||
lsExe.in.info.op := Mux(atomWidthD, LSUOpType.sd, LSUOpType.sw)
|
||||
lsExe.in.wdata := atomMemReg
|
||||
io.memoryUnit.out.ready := lsExe.out.ready && io.dataMemory.out.en
|
||||
when(lsExe.out.ready) {
|
||||
when(allow_to_go) {
|
||||
state := s_idle
|
||||
}
|
||||
state := s_wait_allow;
|
||||
}
|
||||
}
|
||||
is(s_sc) {
|
||||
lsExe.in.mem_en := true.B
|
||||
lsExe.in.mem_addr := src1
|
||||
lsExe.in.info.op := Mux(atomWidthD, LSUOpType.sd, LSUOpType.sw)
|
||||
lsExe.in.wdata := src2
|
||||
io.memoryUnit.out.ready := lsExe.out.ready && io.dataMemory.out.en
|
||||
when(lsExe.out.ready) {
|
||||
when(allow_to_go) {
|
||||
state := s_idle
|
||||
}
|
||||
state := s_wait_allow;
|
||||
}
|
||||
}
|
||||
is(s_wait_allow) {
|
||||
lsExe.in.mem_en := false.B
|
||||
lsExe.in.info.op := MuxCase(
|
||||
func,
|
||||
Seq(
|
||||
lrReq -> Mux(atomWidthD, LSUOpType.ld, LSUOpType.lw),
|
||||
scReq -> Mux(atomWidthD, LSUOpType.sd, LSUOpType.sw)
|
||||
)
|
||||
)
|
||||
lsExe.in.mem_addr := Mux(amoReq || lrReq || scReq, src1, src1 + imm)
|
||||
lsExe.in.wdata := DontCare
|
||||
io.memoryUnit.out.ready := io.dataMemory.in.ready
|
||||
when(allow_to_go && io.dataMemory.in.ready) {
|
||||
state := s_idle
|
||||
}
|
||||
}
|
||||
// is(s_amo_s) {
|
||||
// lsExe.in.mem_en := true.B
|
||||
// lsExe.in.mem_addr := src1
|
||||
// lsExe.in.info.op := Mux(atomWidthD, LSUOpType.sd, LSUOpType.sw)
|
||||
// lsExe.in.wdata := atomMemReg
|
||||
// io.memoryUnit.out.ready := lsExe.out.ready && io.dataMemory.out.en
|
||||
// when(lsExe.out.ready) {
|
||||
// when(allow_to_go) {
|
||||
// state := s_idle
|
||||
// }
|
||||
// state := s_wait_allow;
|
||||
// }
|
||||
// }
|
||||
// is(s_sc) {
|
||||
// lsExe.in.mem_en := true.B
|
||||
// lsExe.in.mem_addr := src1
|
||||
// lsExe.in.info.op := Mux(atomWidthD, LSUOpType.sd, LSUOpType.sw)
|
||||
// lsExe.in.wdata := src2
|
||||
// io.memoryUnit.out.ready := lsExe.out.ready && io.dataMemory.out.en
|
||||
// when(lsExe.out.ready) {
|
||||
// when(allow_to_go) {
|
||||
// state := s_idle
|
||||
// }
|
||||
// state := s_wait_allow;
|
||||
// }
|
||||
// }
|
||||
// is(s_wait_allow) {
|
||||
// lsExe.in.mem_en := false.B
|
||||
// lsExe.in.info.op := MuxCase(
|
||||
// func,
|
||||
// Seq(
|
||||
// lrReq -> Mux(atomWidthD, LSUOpType.ld, LSUOpType.lw),
|
||||
// scReq -> Mux(atomWidthD, LSUOpType.sd, LSUOpType.sw)
|
||||
// )
|
||||
// )
|
||||
// lsExe.in.mem_addr := Mux(amoReq || lrReq || scReq, src1, src1 + imm)
|
||||
// lsExe.in.wdata := DontCare
|
||||
// io.memoryUnit.out.ready := io.dataMemory.in.ready
|
||||
// when(allow_to_go && io.dataMemory.in.ready) {
|
||||
// state := s_idle
|
||||
// }
|
||||
// }
|
||||
}
|
||||
when(
|
||||
lsExe.out.loadAddrMisaligned ||
|
||||
|
|
Loading…
Reference in New Issue