增加tlb相关常量定义
This commit is contained in:
parent
78ca79384e
commit
eeb076b060
|
@ -13,6 +13,8 @@ import pipeline.memory._
|
||||||
import pipeline.writeback._
|
import pipeline.writeback._
|
||||||
import ctrl._
|
import ctrl._
|
||||||
import cache.mmu._
|
import cache.mmu._
|
||||||
|
import cache.mmu.DTlb
|
||||||
|
import cache.mmu.ITlb
|
||||||
|
|
||||||
class Core(implicit val cpuConfig: CpuConfig) extends Module {
|
class Core(implicit val cpuConfig: CpuConfig) extends Module {
|
||||||
val io = IO(new Bundle {
|
val io = IO(new Bundle {
|
||||||
|
@ -35,14 +37,16 @@ class Core(implicit val cpuConfig: CpuConfig) extends Module {
|
||||||
val memoryUnit = Module(new MemoryUnit()).io
|
val memoryUnit = Module(new MemoryUnit()).io
|
||||||
val writeBackStage = Module(new WriteBackStage()).io
|
val writeBackStage = Module(new WriteBackStage()).io
|
||||||
val writeBackUnit = Module(new WriteBackUnit()).io
|
val writeBackUnit = Module(new WriteBackUnit()).io
|
||||||
val itlbL1 = Module(new ITlbL1()).io
|
val itlbL1 = Module(new ITlb()).io
|
||||||
val dtlbL1 = Module(new DTlbL1()).io
|
val dtlbL1 = Module(new DTlb()).io
|
||||||
|
|
||||||
itlbL1.addr := fetchUnit.iCache.pc
|
itlbL1.addr := fetchUnit.iCache.pc
|
||||||
itlbL1.cache <> io.inst.tlb
|
itlbL1.cache <> io.inst.tlb
|
||||||
|
itlbL1.csr <> csr.tlb
|
||||||
|
|
||||||
dtlbL1.addr := memoryUnit.dataMemory.out.addr
|
dtlbL1.addr := memoryUnit.dataMemory.out.addr
|
||||||
dtlbL1.cache <> io.data.tlb
|
dtlbL1.cache <> io.data.tlb
|
||||||
|
dtlbL1.csr <> csr.tlb
|
||||||
|
|
||||||
ctrl.decoderUnit <> decoderUnit.ctrl
|
ctrl.decoderUnit <> decoderUnit.ctrl
|
||||||
ctrl.executeUnit <> executeUnit.ctrl
|
ctrl.executeUnit <> executeUnit.ctrl
|
||||||
|
|
|
@ -24,10 +24,16 @@ case class CpuConfig(
|
||||||
val branchPredictor: String = "adaptive" // adaptive, global
|
val branchPredictor: String = "adaptive" // adaptive, global
|
||||||
)
|
)
|
||||||
|
|
||||||
|
/* BPU 的配置文件 */
|
||||||
case class BranchPredictorConfig(
|
case class BranchPredictorConfig(
|
||||||
val bhtDepth: Int = 5,
|
val bhtDepth: Int = 5,
|
||||||
val phtDepth: Int = 6)
|
val phtDepth: Int = 6)
|
||||||
|
|
||||||
|
/* TLB L2 的配置文件 */
|
||||||
|
case class TLBConfig(
|
||||||
|
nindex: Int = 16,
|
||||||
|
nway: Int = 2)
|
||||||
|
|
||||||
case class CacheConfig(
|
case class CacheConfig(
|
||||||
cacheType: String = "icache" // icache, dcache
|
cacheType: String = "icache" // icache, dcache
|
||||||
) extends Sv39Const {
|
) extends Sv39Const {
|
||||||
|
|
|
@ -74,8 +74,8 @@ class DCache(cacheConfig: CacheConfig)(implicit cpuConfig: CpuConfig) extends Mo
|
||||||
})
|
})
|
||||||
|
|
||||||
// * fsm * //
|
// * fsm * //
|
||||||
val s_idle :: s_uncached :: s_fence :: s_replace :: s_wait :: Nil = Enum(5)
|
val s_idle :: s_uncached :: s_fence :: s_replace :: s_wait :: s_tlb_refill :: Nil = Enum(6)
|
||||||
val state = RegInit(s_idle)
|
val state = RegInit(s_idle)
|
||||||
|
|
||||||
// ==========================================================
|
// ==========================================================
|
||||||
// | tag | index | offset |
|
// | tag | index | offset |
|
||||||
|
@ -94,9 +94,6 @@ class DCache(cacheConfig: CacheConfig)(implicit cpuConfig: CpuConfig) extends Mo
|
||||||
// else
|
// else
|
||||||
// 0.U
|
// 0.U
|
||||||
|
|
||||||
val tlb_fill = RegInit(false.B)
|
|
||||||
io.cpu.tlb.fill := tlb_fill
|
|
||||||
|
|
||||||
// axi信号中size的宽度,对于cached段,size为3位
|
// axi信号中size的宽度,对于cached段,size为3位
|
||||||
val cached_size = log2Ceil(AXI_DATA_WID / 8)
|
val cached_size = log2Ceil(AXI_DATA_WID / 8)
|
||||||
val cached_len = (nbank - 1)
|
val cached_len = (nbank - 1)
|
||||||
|
@ -150,7 +147,7 @@ class DCache(cacheConfig: CacheConfig)(implicit cpuConfig: CpuConfig) extends Mo
|
||||||
val bank_replication = RegInit(VecInit(Seq.fill(nbank)(0.U(XLEN.W))))
|
val bank_replication = RegInit(VecInit(Seq.fill(nbank)(0.U(XLEN.W))))
|
||||||
|
|
||||||
// 是否使用exe的地址进行提前访存
|
// 是否使用exe的地址进行提前访存
|
||||||
val use_next_addr = (state === s_idle && !tlb_fill) || (state === s_wait)
|
val use_next_addr = (state === s_idle) || (state === s_wait)
|
||||||
val do_replace = RegInit(false.B)
|
val do_replace = RegInit(false.B)
|
||||||
// replace index 表示行的索引
|
// replace index 表示行的索引
|
||||||
val replace_index = io.cpu.addr(indexWidth + offsetWidth - 1, offsetWidth)
|
val replace_index = io.cpu.addr(indexWidth + offsetWidth - 1, offsetWidth)
|
||||||
|
@ -179,7 +176,7 @@ class DCache(cacheConfig: CacheConfig)(implicit cpuConfig: CpuConfig) extends Mo
|
||||||
val select_way = tag_compare_valid(1)
|
val select_way = tag_compare_valid(1)
|
||||||
|
|
||||||
val dcache_stall = Mux(
|
val dcache_stall = Mux(
|
||||||
state === s_idle && !tlb_fill,
|
state === s_idle,
|
||||||
Mux(
|
Mux(
|
||||||
io.cpu.en,
|
io.cpu.en,
|
||||||
(cached_stall || mmio_read_stall || mmio_write_stall || !io.cpu.tlb.translation_ok),
|
(cached_stall || mmio_read_stall || mmio_write_stall || !io.cpu.tlb.translation_ok),
|
||||||
|
@ -227,7 +224,7 @@ class DCache(cacheConfig: CacheConfig)(implicit cpuConfig: CpuConfig) extends Mo
|
||||||
io.cpu.tlb.translation_ok // 页表有效
|
io.cpu.tlb.translation_ok // 页表有效
|
||||||
|
|
||||||
replace_wstrb(j)(i) := Mux(
|
replace_wstrb(j)(i) := Mux(
|
||||||
tag_compare_valid(i) && io.cpu.en && io.cpu.wen.orR && !io.cpu.tlb.uncached && state === s_idle && !tlb_fill,
|
tag_compare_valid(i) && io.cpu.en && io.cpu.wen.orR && !io.cpu.tlb.uncached && state === s_idle,
|
||||||
wstrb(j)(i),
|
wstrb(j)(i),
|
||||||
Fill(AXI_STRB_WID, burst.wstrb(i)(j))
|
Fill(AXI_STRB_WID, burst.wstrb(i)(j))
|
||||||
)
|
)
|
||||||
|
@ -288,20 +285,11 @@ class DCache(cacheConfig: CacheConfig)(implicit cpuConfig: CpuConfig) extends Mo
|
||||||
|
|
||||||
switch(state) {
|
switch(state) {
|
||||||
is(s_idle) {
|
is(s_idle) {
|
||||||
when(tlb_fill) {
|
when(io.cpu.en) {
|
||||||
tlb_fill := false.B
|
|
||||||
when(!io.cpu.tlb.hit) {
|
|
||||||
state := s_wait
|
|
||||||
}
|
|
||||||
}.elsewhen(io.cpu.en) {
|
|
||||||
when(addr_err) {
|
when(addr_err) {
|
||||||
acc_err := true.B
|
acc_err := true.B
|
||||||
}.elsewhen(!io.cpu.tlb.translation_ok) {
|
}.elsewhen(!io.cpu.tlb.translation_ok) {
|
||||||
when(io.cpu.tlb.tlb1_ok) {
|
state := s_tlb_refill
|
||||||
state := s_wait
|
|
||||||
}.otherwise {
|
|
||||||
tlb_fill := true.B
|
|
||||||
}
|
|
||||||
}.elsewhen(io.cpu.tlb.uncached) {
|
}.elsewhen(io.cpu.tlb.uncached) {
|
||||||
when(io.cpu.wen.orR) {
|
when(io.cpu.wen.orR) {
|
||||||
when(writeFifo.io.enq.ready) {
|
when(writeFifo.io.enq.ready) {
|
||||||
|
|
|
@ -75,16 +75,15 @@ class ICache(cacheConfig: CacheConfig)(implicit cpuConfig: CpuConfig) extends Mo
|
||||||
val bank_index = io.cpu.addr(0)(offsetWidth - 1, bankOffsetWidth)
|
val bank_index = io.cpu.addr(0)(offsetWidth - 1, bankOffsetWidth)
|
||||||
val bank_offset = io.cpu.addr(0)(bankOffsetWidth - 1, log2Ceil(INST_WID / 8)) // PC低2位必定是0
|
val bank_offset = io.cpu.addr(0)(bankOffsetWidth - 1, log2Ceil(INST_WID / 8)) // PC低2位必定是0
|
||||||
|
|
||||||
val tlb_fill = RegInit(false.B)
|
|
||||||
// * fsm * //
|
// * fsm * //
|
||||||
val s_idle :: s_uncached :: s_replace :: s_wait :: s_fence :: Nil = Enum(5)
|
val s_idle :: s_uncached :: s_replace :: s_wait :: s_fence :: s_tlb_refill :: Nil = Enum(6)
|
||||||
val state = RegInit(s_idle)
|
val state = RegInit(s_idle)
|
||||||
|
|
||||||
// nway 路,每路 nindex 行,每行 nbank 个 bank,每行的nbank共用一个valid
|
// nway 路,每路 nindex 行,每行 nbank 个 bank,每行的nbank共用一个valid
|
||||||
val valid = RegInit(VecInit(Seq.fill(nway)(VecInit(Seq.fill(nindex)(false.B)))))
|
val valid = RegInit(VecInit(Seq.fill(nway)(VecInit(Seq.fill(nindex)(false.B)))))
|
||||||
|
|
||||||
// * should choose next addr * //
|
// * should choose next addr * //
|
||||||
val use_next_addr = (state === s_idle && !tlb_fill) || (state === s_wait)
|
val use_next_addr = (state === s_idle) || (state === s_wait)
|
||||||
|
|
||||||
// 读取一个cache条目中的所有bank行
|
// 读取一个cache条目中的所有bank行
|
||||||
val data = Wire(Vec(nway, Vec(nbank, Vec(instBlocksPerBank, UInt(AXI_DATA_WID.W)))))
|
val data = Wire(Vec(nway, Vec(nbank, Vec(instBlocksPerBank, UInt(AXI_DATA_WID.W)))))
|
||||||
|
@ -95,10 +94,6 @@ class ICache(cacheConfig: CacheConfig)(implicit cpuConfig: CpuConfig) extends Mo
|
||||||
val tag_wstrb = RegInit(VecInit(Seq.fill(nway)(false.B)))
|
val tag_wstrb = RegInit(VecInit(Seq.fill(nway)(false.B)))
|
||||||
val tag_wdata = RegInit(0.U(tagWidth.W))
|
val tag_wdata = RegInit(0.U(tagWidth.W))
|
||||||
|
|
||||||
// * itlb * //
|
|
||||||
when(tlb_fill) { tlb_fill := false.B }
|
|
||||||
io.cpu.tlb.fill := tlb_fill
|
|
||||||
|
|
||||||
// * lru * //// TODO:检查lru的正确性,增加可拓展性,目前只支持两路的cache
|
// * lru * //// TODO:检查lru的正确性,增加可拓展性,目前只支持两路的cache
|
||||||
val lru = RegInit(VecInit(Seq.fill(nindex)(false.B)))
|
val lru = RegInit(VecInit(Seq.fill(nindex)(false.B)))
|
||||||
|
|
||||||
|
@ -176,8 +171,8 @@ class ICache(cacheConfig: CacheConfig)(implicit cpuConfig: CpuConfig) extends Mo
|
||||||
}
|
}
|
||||||
|
|
||||||
for { i <- 0 until instFetchNum } {
|
for { i <- 0 until instFetchNum } {
|
||||||
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_valid(i) := Mux(state === s_idle, 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)
|
io.cpu.inst(i) := Mux(state === s_idle, inst(i), rdata_in_wait(i).inst)
|
||||||
}
|
}
|
||||||
|
|
||||||
for { i <- 0 until nway } {
|
for { i <- 0 until nway } {
|
||||||
|
@ -191,7 +186,7 @@ class ICache(cacheConfig: CacheConfig)(implicit cpuConfig: CpuConfig) extends Mo
|
||||||
tagBram.io.wdata := tag_wdata
|
tagBram.io.wdata := tag_wdata
|
||||||
}
|
}
|
||||||
|
|
||||||
io.cpu.icache_stall := Mux(state === s_idle && !tlb_fill, (!cache_hit_available && io.cpu.req), state =/= s_wait)
|
io.cpu.icache_stall := Mux(state === s_idle, (!cache_hit_available && io.cpu.req), state =/= s_wait)
|
||||||
|
|
||||||
val ar = RegInit(0.U.asTypeOf(new AR()))
|
val ar = RegInit(0.U.asTypeOf(new AR()))
|
||||||
val arvalid = RegInit(false.B)
|
val arvalid = RegInit(false.B)
|
||||||
|
@ -211,20 +206,14 @@ class ICache(cacheConfig: CacheConfig)(implicit cpuConfig: CpuConfig) extends Mo
|
||||||
|
|
||||||
switch(state) {
|
switch(state) {
|
||||||
is(s_idle) {
|
is(s_idle) {
|
||||||
when(tlb_fill) {
|
when(io.cpu.req) {
|
||||||
when(!io.cpu.tlb.hit) {
|
|
||||||
state := s_wait
|
|
||||||
rdata_in_wait(0).inst := 0.U
|
|
||||||
rdata_in_wait(0).valid := true.B
|
|
||||||
}
|
|
||||||
}.elsewhen(io.cpu.req) {
|
|
||||||
when(addr_err) {
|
when(addr_err) {
|
||||||
acc_err := true.B
|
acc_err := true.B
|
||||||
state := s_wait
|
state := s_wait
|
||||||
rdata_in_wait(0).inst := 0.U
|
rdata_in_wait(0).inst := 0.U
|
||||||
rdata_in_wait(0).valid := true.B
|
rdata_in_wait(0).valid := true.B
|
||||||
}.elsewhen(!io.cpu.tlb.translation_ok) {
|
}.elsewhen(!io.cpu.tlb.translation_ok) {
|
||||||
tlb_fill := true.B
|
state := s_tlb_refill
|
||||||
}.elsewhen(io.cpu.tlb.uncached) {
|
}.elsewhen(io.cpu.tlb.uncached) {
|
||||||
state := s_uncached
|
state := s_uncached
|
||||||
ar.addr := io.cpu.tlb.paddr
|
ar.addr := io.cpu.tlb.paddr
|
||||||
|
@ -303,6 +292,11 @@ class ICache(cacheConfig: CacheConfig)(implicit cpuConfig: CpuConfig) extends Mo
|
||||||
state := s_idle
|
state := s_idle
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
is(s_tlb_refill) {
|
||||||
|
when(io.cpu.tlb.hit_L2){
|
||||||
|
state := s_idle
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// * fence * //
|
// * fence * //
|
||||||
|
|
|
@ -0,0 +1,33 @@
|
||||||
|
package cache.mmu
|
||||||
|
|
||||||
|
import chisel3._
|
||||||
|
import chisel3.util._
|
||||||
|
import cpu.defines._
|
||||||
|
import cpu.defines.Const._
|
||||||
|
import cpu.CacheConfig
|
||||||
|
import cpu.pipeline.execute.CsrTlb
|
||||||
|
|
||||||
|
class Tlb_DCache extends Bundle {
|
||||||
|
val cacheConfig = CacheConfig("dcache")
|
||||||
|
|
||||||
|
val uncached = Output(Bool())
|
||||||
|
val translation_ok = Output(Bool())
|
||||||
|
val hit_L2 = Output(Bool())
|
||||||
|
val ptag = Output(UInt(cacheConfig.tagWidth.W))
|
||||||
|
val paddr = Output(UInt(PADDR_WID.W))
|
||||||
|
}
|
||||||
|
|
||||||
|
class DTlb extends Module with Sv39Const {
|
||||||
|
val io = IO(new Bundle {
|
||||||
|
val addr = Input(UInt(XLEN.W))
|
||||||
|
val cache = new Tlb_DCache()
|
||||||
|
val csr = Flipped(new CsrTlb())
|
||||||
|
})
|
||||||
|
|
||||||
|
io.cache.uncached := AddressSpace.isMMIO(io.addr)
|
||||||
|
io.cache.translation_ok := true.B
|
||||||
|
io.cache.hit_L2 := true.B
|
||||||
|
io.cache.ptag := io.addr(PADDR_WID - 1, offsetLen)
|
||||||
|
io.cache.paddr := Cat(io.cache.ptag, io.addr(offsetLen - 1, 0))
|
||||||
|
|
||||||
|
}
|
|
@ -1,28 +0,0 @@
|
||||||
package cache.mmu
|
|
||||||
|
|
||||||
import chisel3._
|
|
||||||
import chisel3.util._
|
|
||||||
import cpu.defines._
|
|
||||||
import cpu.defines.Const._
|
|
||||||
import cpu.CacheConfig
|
|
||||||
|
|
||||||
class DTlbL1 extends Module {
|
|
||||||
val io = IO(new Bundle {
|
|
||||||
val cache = new Tlb_DCache()
|
|
||||||
val addr = Input(UInt(XLEN.W))
|
|
||||||
})
|
|
||||||
|
|
||||||
val cacheConfig = CacheConfig("dcache")
|
|
||||||
|
|
||||||
io.cache.uncached := AddressSpace.isMMIO(io.addr)
|
|
||||||
io.cache.translation_ok := true.B
|
|
||||||
io.cache.hit := true.B
|
|
||||||
io.cache.tlb1_ok := true.B
|
|
||||||
io.cache.ptag := io.addr(PADDR_WID - 1, cacheConfig.offsetWidth + cacheConfig.indexWidth)
|
|
||||||
io.cache.paddr := Cat(io.cache.ptag, io.addr(cacheConfig.offsetWidth + cacheConfig.indexWidth - 1, 0))
|
|
||||||
|
|
||||||
println("----------------------------------------")
|
|
||||||
println("DTlbL1")
|
|
||||||
println("tag from " + (PADDR_WID - 1) + " to " + (cacheConfig.offsetWidth + cacheConfig.indexWidth))
|
|
||||||
println("----------------------------------------")
|
|
||||||
}
|
|
|
@ -0,0 +1,39 @@
|
||||||
|
package cache.mmu
|
||||||
|
|
||||||
|
import chisel3._
|
||||||
|
import chisel3.util._
|
||||||
|
import cpu.defines._
|
||||||
|
import cpu.defines.Const._
|
||||||
|
import cpu.CacheConfig
|
||||||
|
import cpu.pipeline.execute.CsrTlb
|
||||||
|
|
||||||
|
class Tlb_ICache extends Bundle {
|
||||||
|
val cacheConfig = CacheConfig("icache")
|
||||||
|
|
||||||
|
val uncached = Output(Bool())
|
||||||
|
val translation_ok = Output(Bool())
|
||||||
|
val hit_L2 = Output(Bool())
|
||||||
|
val ptag = Output(UInt(cacheConfig.tagWidth.W))
|
||||||
|
val paddr = Output(UInt(PADDR_WID.W))
|
||||||
|
}
|
||||||
|
|
||||||
|
class ITlb extends Module with Sv39Const with HasCSRConst {
|
||||||
|
val io = IO(new Bundle {
|
||||||
|
val addr = Input(UInt(XLEN.W))
|
||||||
|
val cache = new Tlb_ICache()
|
||||||
|
val csr = Flipped(new CsrTlb())
|
||||||
|
// val tlbL2 = Flipped(new TlbL2_TlbL1())
|
||||||
|
})
|
||||||
|
|
||||||
|
val satp = WireInit(io.csr.satp)
|
||||||
|
val mode = WireInit(io.csr.mode)
|
||||||
|
|
||||||
|
val vm_enabled = (satp.asTypeOf(satpBundle).mode === 8.U) && (mode < ModeM)
|
||||||
|
|
||||||
|
io.cache.uncached := AddressSpace.isMMIO(io.addr)
|
||||||
|
io.cache.translation_ok := !vm_enabled
|
||||||
|
io.cache.hit_L2 := true.B
|
||||||
|
io.cache.ptag := Mux(vm_enabled, DontCare, io.addr(PADDR_WID - 1, offsetLen))
|
||||||
|
io.cache.paddr := Cat(io.cache.ptag, io.addr(offsetLen - 1, 0))
|
||||||
|
|
||||||
|
}
|
|
@ -1,27 +0,0 @@
|
||||||
package cache.mmu
|
|
||||||
|
|
||||||
import chisel3._
|
|
||||||
import chisel3.util._
|
|
||||||
import cpu.defines._
|
|
||||||
import cpu.defines.Const._
|
|
||||||
import cpu.CacheConfig
|
|
||||||
|
|
||||||
class ITlbL1 extends Module {
|
|
||||||
val io = IO(new Bundle {
|
|
||||||
val addr = Input(UInt(XLEN.W))
|
|
||||||
val cache = new Tlb_ICache()
|
|
||||||
})
|
|
||||||
|
|
||||||
val cacheConfig = CacheConfig("icache")
|
|
||||||
|
|
||||||
io.cache.uncached := AddressSpace.isMMIO(io.addr)
|
|
||||||
io.cache.translation_ok := true.B
|
|
||||||
io.cache.hit := true.B
|
|
||||||
io.cache.ptag := io.addr(PADDR_WID - 1, cacheConfig.offsetWidth + cacheConfig.indexWidth)
|
|
||||||
io.cache.paddr := Cat(io.cache.ptag, io.addr(cacheConfig.offsetWidth + cacheConfig.indexWidth - 1, 0))
|
|
||||||
|
|
||||||
println("----------------------------------------")
|
|
||||||
println("ITlbL1")
|
|
||||||
println("tag from " + (PADDR_WID - 1) + " to " + (cacheConfig.offsetWidth + cacheConfig.indexWidth))
|
|
||||||
println("----------------------------------------")
|
|
||||||
}
|
|
|
@ -0,0 +1,22 @@
|
||||||
|
package cache.mmu
|
||||||
|
|
||||||
|
import chisel3._
|
||||||
|
import chisel3.util._
|
||||||
|
import cpu.defines._
|
||||||
|
import cpu.defines.Const._
|
||||||
|
import cpu.TLBConfig
|
||||||
|
|
||||||
|
class TlbL2_TlbL1 extends Bundle {
|
||||||
|
val page_fault = Output(Bool())
|
||||||
|
}
|
||||||
|
|
||||||
|
class TlbL2 extends Module with HasTlbConst {
|
||||||
|
val io = IO(new Bundle {
|
||||||
|
val itlb = new TlbL2_TlbL1()
|
||||||
|
val dtlb = new TlbL2_TlbL1()
|
||||||
|
})
|
||||||
|
|
||||||
|
// tlb l2
|
||||||
|
val tlb = RegInit(VecInit(Seq.fill(nindex)(VecInit(Seq.fill(nway)(0.U.asTypeOf(tlbBundle))))))
|
||||||
|
|
||||||
|
}
|
|
@ -5,6 +5,7 @@ import chisel3.util._
|
||||||
import cpu.defines._
|
import cpu.defines._
|
||||||
import cpu.defines.Const._
|
import cpu.defines.Const._
|
||||||
import cpu.CpuConfig
|
import cpu.CpuConfig
|
||||||
|
import cache.mmu
|
||||||
|
|
||||||
class ExceptionInfo extends Bundle {
|
class ExceptionInfo extends Bundle {
|
||||||
val exception = Vec(EXC_WID, Bool())
|
val exception = Vec(EXC_WID, Bool())
|
||||||
|
@ -120,7 +121,7 @@ class Cache_ICache(implicit val cpuConfig: CpuConfig) extends Bundle {
|
||||||
val icache_stall = Input(Bool()) // icache_stall
|
val icache_stall = Input(Bool()) // icache_stall
|
||||||
|
|
||||||
// tlb
|
// tlb
|
||||||
val tlb = new Tlb_ICache()
|
val tlb = new mmu.Tlb_ICache()
|
||||||
}
|
}
|
||||||
|
|
||||||
// cpu to dcache
|
// cpu to dcache
|
||||||
|
@ -139,7 +140,7 @@ class Cache_DCache extends Bundle {
|
||||||
val acc_err = Input(Bool())
|
val acc_err = Input(Bool())
|
||||||
val dcache_ready = Input(Bool())
|
val dcache_ready = Input(Bool())
|
||||||
|
|
||||||
val tlb = new Tlb_DCache()
|
val tlb = new mmu.Tlb_DCache()
|
||||||
}
|
}
|
||||||
|
|
||||||
// axi
|
// axi
|
||||||
|
|
|
@ -4,6 +4,7 @@ import chisel3._
|
||||||
import chisel3.util._
|
import chisel3.util._
|
||||||
import cpu.defines.Const._
|
import cpu.defines.Const._
|
||||||
import cpu.CacheConfig
|
import cpu.CacheConfig
|
||||||
|
import cpu.TLBConfig
|
||||||
|
|
||||||
trait Sv39Const extends CoreParameter {
|
trait Sv39Const extends CoreParameter {
|
||||||
val PAddrBits = PADDR_WID
|
val PAddrBits = PADDR_WID
|
||||||
|
@ -114,27 +115,51 @@ trait Sv39Const extends CoreParameter {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
class Tlb_ICache extends Bundle {
|
trait HasTlbConst extends Sv39Const {
|
||||||
val cacheConfig = CacheConfig("icache")
|
val tlbConfig = TLBConfig()
|
||||||
|
|
||||||
val fill = Input(Bool())
|
val maskLen = vpn0Len + vpn1Len // 18
|
||||||
val uncached = Output(Bool())
|
val metaLen = vpnLen + asidLen + maskLen + flagLen // 27 + 16 + 18 + 8 = 69, is asid necessary
|
||||||
|
val dataLen = ppnLen + PAddrBits //
|
||||||
|
val tlbLen = metaLen + dataLen
|
||||||
|
val nway = tlbConfig.nway
|
||||||
|
val nindex = tlbConfig.nindex
|
||||||
|
val indexWid = log2Up(nindex)
|
||||||
|
val tagWid = vpnLen - indexWid
|
||||||
|
|
||||||
val translation_ok = Output(Bool())
|
def vaddrTlbBundle = new Bundle {
|
||||||
val hit = Output(Bool())
|
val tag = UInt(tagWid.W)
|
||||||
val ptag = Output(UInt(cacheConfig.tagWidth.W))
|
val index = UInt(indexWid.W)
|
||||||
val paddr = Output(UInt(PADDR_WID.W))
|
val off = UInt(offsetLen.W)
|
||||||
}
|
}
|
||||||
|
|
||||||
class Tlb_DCache extends Bundle {
|
def metaBundle = new Bundle {
|
||||||
val cacheConfig = CacheConfig("dcache")
|
val vpn = UInt(vpnLen.W)
|
||||||
|
val asid = UInt(asidLen.W)
|
||||||
val fill = Input(Bool())
|
val mask = UInt(maskLen.W) // to support super page
|
||||||
val uncached = Output(Bool())
|
val flag = UInt(flagLen.W)
|
||||||
val tlb1_ok = Output(Bool())
|
}
|
||||||
|
|
||||||
val translation_ok = Output(Bool())
|
def dataBundle = new Bundle {
|
||||||
val hit = Output(Bool())
|
val ppn = UInt(ppnLen.W)
|
||||||
val ptag = Output(UInt(cacheConfig.tagWidth.W))
|
val pteaddr = UInt(PAddrBits.W) // pte addr, used to write back pte when flag changes (flag.d, flag.v)
|
||||||
val paddr = Output(UInt(PADDR_WID.W))
|
}
|
||||||
|
|
||||||
|
def tlbBundle = new Bundle {
|
||||||
|
val vpn = UInt(vpnLen.W)
|
||||||
|
val asid = UInt(asidLen.W)
|
||||||
|
val mask = UInt(maskLen.W)
|
||||||
|
val flag = UInt(flagLen.W)
|
||||||
|
val ppn = UInt(ppnLen.W)
|
||||||
|
val pteaddr = UInt(PAddrBits.W)
|
||||||
|
}
|
||||||
|
|
||||||
|
def tlbBundle2 = new Bundle {
|
||||||
|
val meta = UInt(metaLen.W)
|
||||||
|
val data = UInt(dataLen.W)
|
||||||
|
}
|
||||||
|
|
||||||
|
def getIndex(vaddr: UInt): UInt = {
|
||||||
|
vaddr.asTypeOf(vaddrTlbBundle).index
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -47,12 +47,18 @@ class CsrDecoderUnit extends Bundle {
|
||||||
val interrupt = Output(UInt(INT_WID.W))
|
val interrupt = Output(UInt(INT_WID.W))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
class CsrTlb extends Bundle {
|
||||||
|
val satp = Output(UInt(XLEN.W))
|
||||||
|
val mode = Output(Priv())
|
||||||
|
}
|
||||||
|
|
||||||
class Csr(implicit val cpuConfig: CpuConfig) extends Module with HasCSRConst {
|
class Csr(implicit val cpuConfig: CpuConfig) extends Module with HasCSRConst {
|
||||||
val io = IO(new Bundle {
|
val io = IO(new Bundle {
|
||||||
val ext_int = Input(new ExtInterrupt())
|
val ext_int = Input(new ExtInterrupt())
|
||||||
val decoderUnit = new CsrDecoderUnit()
|
val decoderUnit = new CsrDecoderUnit()
|
||||||
val executeUnit = new CsrExecuteUnit()
|
val executeUnit = new CsrExecuteUnit()
|
||||||
val memoryUnit = new CsrMemoryUnit()
|
val memoryUnit = new CsrMemoryUnit()
|
||||||
|
val tlb = new CsrTlb()
|
||||||
})
|
})
|
||||||
|
|
||||||
// 目前的csr只支持64位
|
// 目前的csr只支持64位
|
||||||
|
@ -407,6 +413,8 @@ class Csr(implicit val cpuConfig: CpuConfig) extends Module with HasCSRConst {
|
||||||
ret_target := sepc(VADDR_WID - 1, 0)
|
ret_target := sepc(VADDR_WID - 1, 0)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
io.tlb.mode := mode
|
||||||
|
io.tlb.satp := satp
|
||||||
io.decoderUnit.mode := mode
|
io.decoderUnit.mode := mode
|
||||||
io.executeUnit.out.ex := io.executeUnit.in.ex
|
io.executeUnit.out.ex := io.executeUnit.in.ex
|
||||||
io.executeUnit.out.ex.exception(illegalInstr) :=
|
io.executeUnit.out.ex.exception(illegalInstr) :=
|
||||||
|
|
Loading…
Reference in New Issue