未验证 提交 2f30d658 编写于 作者: Y Yinan Xu 提交者: GitHub

top: change physical address width to 36 (#1188)

上级 34ab1ae9
Subproject commit 3793b789dc6e3c9592f8783cd29aeda73c85e081
Subproject commit cb97f940276cbaf713856d1cfcf2b808d824ac22
......@@ -37,6 +37,7 @@ case object SoCParamsKey extends Field[SoCParameters]
case class SoCParameters
(
EnableILA: Boolean = false,
PAddrBits: Int = 36,
extIntrs: Int = 150,
L3NBanks: Int = 4,
L3CacheParamsOpt: Option[HCCacheParameters] = Some(HCCacheParameters(
......@@ -46,7 +47,6 @@ case class SoCParameters
sets = 2048 // 1MB per bank
))
){
val PAddrBits = 40
// L3 configurations
val L3InnerBusWidth = 256
val L3BlockSize = 64
......@@ -128,8 +128,8 @@ trait HaveSlaveAXI4Port {
trait HaveAXI4MemPort {
this: BaseSoC =>
val device = new MemoryDevice
// 40-bit physical address
val memRange = AddressSet(0x00000000L, 0xffffffffffL).subtract(AddressSet(0x0L, 0x7fffffffL))
// 36-bit physical address
val memRange = AddressSet(0x00000000L, 0xfffffffffL).subtract(AddressSet(0x0L, 0x7fffffffL))
val memAXI4SlaveNode = AXI4SlaveNode(Seq(
AXI4SlavePortParameters(
slaves = Seq(
......@@ -154,6 +154,7 @@ trait HaveAXI4MemPort {
}
val mem_xbar = TLXbar()
mem_xbar :=* TLCacheCork() :=* bankedNode
mem_xbar := TLBuffer() := TLWidthWidget(8) := TLBuffer() := peripheralXbar
val (buf_l, buf_r) = mem_buffN(5)
memAXI4SlaveNode := buf_l
buf_r :=
......
/***************************************************************************************
* Copyright (c) 2020-2021 Institute of Computing Technology, Chinese Academy of Sciences
* Copyright (c) 2020-2021 Peng Cheng Laboratory
*
* XiangShan is licensed under Mulan PSL v2.
* You can use this software according to the terms and conditions of the Mulan PSL v2.
* You may obtain a copy of Mulan PSL v2 at:
* http://license.coscl.org.cn/MulanPSL2
*
* THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
* EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
* MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
*
* See the Mulan PSL v2 for more details.
***************************************************************************************/
package xiangshan
import chisel3._
import chisel3.util._
import utils._
import Chisel.experimental.chiselName
import chipsalliance.rocketchip.config.Parameters
import xiangshan.cache.{DCache, DCacheParameters, HasDCacheParameters, Uncache}
import xiangshan.cache.mmu.PTW
object MemMap {
def apply (base: String, top: String, width: String, description: String, mode: String): ((String, String), Map[String, String]) = {
((base, top) -> Map(
"width" -> width, // 0 means no limitation
"description" -> description,
"mode" -> mode,
))
}
}
object AddressSpace {
def SimpleMemMapList = List(
// Base address Top address Width Description Mode (RWXIDSAC)
MemMap("h00_0000_0000", "h00_0FFF_FFFF", "h0", "Reserved", "RW"),
MemMap("h00_1000_0000", "h00_1FFF_FFFF", "h0", "QSPI_Flash", "RWX"),
MemMap("h00_2000_0000", "h00_2FFF_FFFF", "h0", "Reserved", "RW"),
MemMap("h00_3000_0000", "h00_3000_FFFF", "h0", "DMA", "RW"),
MemMap("h00_3001_0000", "h00_3004_FFFF", "h0", "GPU", "RWC"),
MemMap("h00_3005_0000", "h00_3006_FFFF", "h0", "USB/SDMMC", "RW"),
MemMap("h00_3007_0000", "h00_30FF_FFFF", "h0", "Reserved", "RW"),
MemMap("h00_3100_0000", "h00_3111_FFFF", "h0", "MMIO", "RW"),
MemMap("h00_3112_0000", "h00_37FF_FFFF", "h0", "Reserved", "RW"),
MemMap("h00_3800_0000", "h00_3800_FFFF", "h0", "CLINT", "RW"),
MemMap("h00_3801_0000", "h00_3801_FFFF", "h0", "BEU", "RW"),
MemMap("h00_3802_0000", "h00_3802_0FFF", "h0", "DebugModule", "RWX"),
MemMap("h00_3802_1000", "h00_3BFF_FFFF", "h0", "Reserved", ""),
MemMap("h00_3C00_0000", "h00_3FFF_FFFF", "h0", "PLIC", "RW"),
MemMap("h00_4000_0000", "h00_7FFF_FFFF", "h0", "PCIe", "RW"),
MemMap("h00_8000_0000", "h1F_FFFF_FFFF", "h0", "DDR", "RWXIDSA"),
)
def FullMemMapList = List(
// Base address Top address Width Description Mode (RWXIDSAC)
MemMap("h00_0000_0000", "h00_0000_0FFF", "h0", "DebugModule", "RWX"),
MemMap("h00_0000_1000", "h00_0FFF_FFFF", "h0", "Reserved", ""),
MemMap("h00_1000_0000", "h00_1FFF_FFFF", "h0", "QSPI_Flash", "RX"),
MemMap("h00_2000_0000", "h00_2FFF_FFFF", "h0", "Reserved", ""),
MemMap("h00_3000_0000", "h00_3000_FFFF", "h0", "DMA", "RW"),
MemMap("h00_3001_0000", "h00_3004_FFFF", "h0", "GPU", "RWC"),
MemMap("h00_3005_0000", "h00_3005_FFFF", "h0", "USB", "RW"),
MemMap("h00_3006_0000", "h00_3006_FFFF", "h0", "SDMMC", "RW"),
MemMap("h00_3007_0000", "h00_30FF_FFFF", "h0", "Reserved", ""),
MemMap("h00_3100_0000", "h00_3100_FFFF", "h0", "QSPI", "RW"),
MemMap("h00_3101_0000", "h00_3101_FFFF", "h0", "GMAC", "RW"),
MemMap("h00_3102_0000", "h00_3102_FFFF", "h0", "HDMI", "RW"),
MemMap("h00_3103_0000", "h00_3103_FFFF", "h0", "HDMI_PHY", "RW"),
MemMap("h00_3104_0000", "h00_3105_FFFF", "h0", "DP", "RW"),
MemMap("h00_3106_0000", "h00_3106_FFFF", "h0", "DDR0", "RW"),
MemMap("h00_3107_0000", "h00_3107_FFFF", "h0", "DDR0_PHY", "RW"),
MemMap("h00_3108_0000", "h00_3108_FFFF", "h0", "DDR1", "RW"),
MemMap("h00_3109_0000", "h00_3109_FFFF", "h0", "DDR1_PHY", "RW"),
MemMap("h00_310A_0000", "h00_310A_FFFF", "h0", "IIS", "RW"),
MemMap("h00_310B_0000", "h00_310B_FFFF", "h0", "UART0", "RW"),
MemMap("h00_310C_0000", "h00_310C_FFFF", "h0", "UART1", "RW"),
MemMap("h00_310D_0000", "h00_310D_FFFF", "h0", "IIC0", "RW"),
MemMap("h00_310E_0000", "h00_310E_FFFF", "h0", "IIC1", "RW"),
MemMap("h00_310F_0000", "h00_310F_FFFF", "h0", "IIC2", "RW"),
MemMap("h00_3110_0000", "h00_3110_FFFF", "h0", "GPIO", "RW"),
MemMap("h00_3111_0000", "h00_3111_FFFF", "h0", "CRU", "RW"),
MemMap("h00_3112_0000", "h00_37FF_FFFF", "h0", "Reserved", ""),
MemMap("h00_3800_0000", "h00_3800_FFFF", "h0", "CLINT", "RW"),
MemMap("h00_3801_0000", "h00_3BFF_FFFF", "h0", "Reserved", ""),
MemMap("h00_3C00_0000", "h00_3FFF_FFFF", "h0", "PLIC", "RW"),
MemMap("h00_4000_0000", "h00_4FFF_FFFF", "h0", "PCIe0", "RW"),
MemMap("h00_5000_0000", "h00_5FFF_FFFF", "h0", "PCIe1", "RW"),
MemMap("h00_6000_0000", "h00_6FFF_FFFF", "h0", "PCIe2", "RW"),
MemMap("h00_7000_0000", "h00_7FFF_FFFF", "h0", "PCIe3", "RW"),
MemMap("h00_8000_0000", "h1F_FFFF_FFFF", "h0", "DDR", "RWXIDSA"),
)
def MemMapList = SimpleMemMapList
def printMemmap(){
println("\nMemory map:")
for(i <- MemMapList){
println("[" + i._1._1 + " -> " + i._1._2 + "] Width:" + (if(i._2.get("width").get == "h0") "unlimited" else i._2.get("width").get) + " Description:" + i._2.get("description").get + " [" + i._2.get("mode").get + "]")
}
println("")
}
def checkMemmap(){
for(i <- MemMapList){
// pma mode check
val s = i._2.get("mode").get
if(
s.toUpperCase.indexOf("A") >= 0 &&
!(s.toUpperCase.indexOf("R") >= 0 && s.toUpperCase.indexOf("W") >= 0)
){
println("[error] pma atomicable area must be both readable and writeable")
throw new IllegalArgumentException
}
// pma area size check
if(!i._1._1.endsWith("000") || !i._1._2.endsWith("FFF")){
println("[error] pma area must be larger than 4KB")
throw new IllegalArgumentException()
}
}
}
def genMemmapMatchVec(addr: UInt): UInt = {
VecInit(MemMapList.map(i => {
// calculate addr tag and compare mask
// val mask = i._1._2.U - i._1._1.U
// (~(i._1._1.U ^ addr) | mask).andR
// pma is not current critical path, use simple compare for now
i._1._1.U <= addr && addr < i._1._2.U
}).toSeq).asUInt
}
def queryMode(matchVec: UInt): UInt = {
Mux1H(matchVec, VecInit(MemMapList.map(i => {
PMAMode.strToMode(i._2.get("mode").get)
}).toSeq))
}
// TODO: FIXME
def queryModeFast(matchVec: UInt): UInt = {
var r = WireInit(false.B)
var w = WireInit(false.B)
var x = WireInit(false.B)
var i = WireInit(false.B)
var d = WireInit(false.B)
var s = WireInit(false.B)
var a = WireInit(false.B)
var c = WireInit(false.B)
for((j, idx) <- MemMapList.zipWithIndex){
val modes = j._2.get("mode").get
if (modes.toUpperCase.indexOf("R") >= 0) r = r || matchVec(idx).asBool
if (modes.toUpperCase.indexOf("W") >= 0) w = w || matchVec(idx).asBool
if (modes.toUpperCase.indexOf("X") >= 0) x = x || matchVec(idx).asBool
if (modes.toUpperCase.indexOf("I") >= 0) i = i || matchVec(idx).asBool
if (modes.toUpperCase.indexOf("D") >= 0) d = d || matchVec(idx).asBool
if (modes.toUpperCase.indexOf("S") >= 0) s = s || matchVec(idx).asBool
if (modes.toUpperCase.indexOf("A") >= 0) a = a || matchVec(idx).asBool
if (modes.toUpperCase.indexOf("C") >= 0) c = c || matchVec(idx).asBool
}
VecInit(Seq(r, w, x, i, d, s, a, c)).asUInt
}
def queryWidth(matchVec: UInt): UInt = {
Mux1H(matchVec, VecInit(MemMapList.map(i => {
i._2.get("width").get.U
}).toSeq))
}
def memmapAddrMatch(addr: UInt): (UInt, UInt) = {
val matchVec = genMemmapMatchVec(addr)
// when(queryMode(matchVec) =/= queryModeFast(matchVec)){
// printf("pma fail: right %b wrong %b\n", queryMode(matchVec), queryModeFast(matchVec))
// }
assert(queryMode(matchVec) === queryModeFast(matchVec))
(queryModeFast(matchVec), queryWidth(matchVec))
}
def isDMMIO(addr: UInt): Bool = !PMAMode.dcache(memmapAddrMatch(addr)._1)
def isIMMIO(addr: UInt): Bool = !PMAMode.icache(memmapAddrMatch(addr)._1)
def isConfigableAddr(addr: UInt): Bool = {
VecInit(MemMapList.map(i => {
i._1._1.U <= addr && addr < i._1._2.U && (i._2.get("mode").get.toUpperCase.indexOf("C") >= 0).B
}).toSeq).asUInt.orR
}
}
class PMAChecker(implicit p: Parameters) extends XSModule with HasDCacheParameters
{
val io = IO(new Bundle() {
val paddr = Input(UInt(VAddrBits.W))
val mode = Output(PMAMode())
val widthLimit = Output(UInt(8.W)) // TODO: fixme
val updateCConfig = Input(Valid(Bool()))
})
val enableConfigableCacheZone = RegInit(false.B)
val updateCConfig = RegNext(RegNext(RegNext(io.updateCConfig)))
when(updateCConfig.valid) {
enableConfigableCacheZone := updateCConfig.bits
}
val (mode, widthLimit) = AddressSpace.memmapAddrMatch(io.paddr)
io.mode := Mux(AddressSpace.isConfigableAddr(io.paddr) && enableConfigableCacheZone, mode | PMAMode.D, mode)
io.widthLimit := widthLimit
}
......@@ -27,7 +27,7 @@ import huancun.{CacheParameters, HCCacheParameters}
import xiangshan.frontend.{BIM, BasePredictor, BranchPredictionResp, FTB, FakePredictor, ICacheParameters, MicroBTB, RAS, Tage, ITTage, Tage_SC}
import xiangshan.cache.mmu.{TLBParameters, L2TLBParameters}
import freechips.rocketchip.diplomacy.AddressSet
import system.SoCParamsKey
case object XSTileKey extends Field[Seq[XSCoreParameters]]
......@@ -45,7 +45,6 @@ case class XSCoreParameters
HasDCache: Boolean = true,
AddrBits: Int = 64,
VAddrBits: Int = 39,
PAddrBits: Int = 40,
HasFPU: Boolean = true,
HasCustomCSRCacheOp: Boolean = true,
FetchWidth: Int = 8,
......@@ -237,6 +236,8 @@ trait HasXSParameter {
implicit val p: Parameters
val PAddrBits = p(SoCParamsKey).PAddrBits // PAddrBits is Phyical Memory addr bits
val coreParams = p(XSCoreParamsKey)
val env = p(DebugOptionsKey)
......@@ -253,7 +254,6 @@ trait HasXSParameter {
val HasDcache = coreParams.HasDCache
val AddrBits = coreParams.AddrBits // AddrBits is used in some cases
val VAddrBits = coreParams.VAddrBits // VAddrBits is Virtual Memory addr bits
val PAddrBits = coreParams.PAddrBits // PAddrBits is Phyical Memory addr bits
val AsidLength = coreParams.AsidLength
val AddrBytes = AddrBits / 8 // unused
val DataBits = XLEN
......
......@@ -171,8 +171,6 @@ class XSCoreImp(outer: XSCoreBase) extends LazyModuleImp(outer)
})
println(s"FPGAPlatform:${env.FPGAPlatform} EnableDebug:${env.EnableDebug}")
AddressSpace.checkMemmap()
AddressSpace.printMemmap()
val ctrlBlock = Module(new CtrlBlock)
......
......@@ -43,7 +43,7 @@ trait PMAMethod extends HasXSParameter with PMPConst { this: XSModule =>
MemMap("h00_3802_1000", "h00_3BFF_FFFF", "h0", "Reserved", ""),
MemMap("h00_3C00_0000", "h00_3FFF_FFFF", "h0", "PLIC", "RW"),
MemMap("h00_4000_0000", "h00_7FFF_FFFF", "h0", "PCIe", "RW"),
MemMap("h00_8000_0000", "h1F_FFFF_FFFF", "h0", "DDR", "RWXIDSA"),
MemMap("h00_8000_0000", "h0F_FFFF_FFFF", "h0", "DDR", "RWXIDSA"),
)
*/
......@@ -61,8 +61,11 @@ trait PMAMethod extends HasXSParameter with PMPConst { this: XSModule =>
addr := DontCare
mask := DontCare
addr(15) := 0x3FFFFFFFEL.U
cfg(15).a := 1.U; cfg(15).r := true.B; cfg(15).w := true.B; cfg(15).x := true.B; cfg(15).c := true.B; cfg(14).atomic := true.B
// use tor instead of napot, for napot may be confusing and hard to understand
addr(14) := shift_addr( 0x2000000000L)
addr(14) := shift_addr(0xFFFFFFFFFL)
cfg(14).a := 1.U; cfg(14).r := true.B; cfg(14).w := true.B; cfg(14).x := true.B; cfg(14).c := true.B; cfg(14).atomic := true.B
addr(13) := shift_addr(0x80000000L)
......
......@@ -129,7 +129,7 @@ class ProbeQueue(edge: TLEdgeOut)(implicit p: Parameters) extends DCacheModule w
if(DCacheAboveIndexOffset > DCacheTagOffset) {
// have alias problem, extra alias bits needed for index
req.vaddr := Cat(
io.mem_probe.bits.address(VAddrBits - 1, DCacheAboveIndexOffset), // dontcare
io.mem_probe.bits.address(PAddrBits - 1, DCacheAboveIndexOffset), // dontcare
alias_addr_frag(DCacheAboveIndexOffset - DCacheTagOffset - 1, 0), // index
io.mem_probe.bits.address(DCacheTagOffset - 1, 0) // index & others
)
......
......@@ -41,7 +41,7 @@ class InstrMMIOEntry(edge: TLEdgeOut)(implicit p: Parameters) extends XSModule w
val io = IO(new Bundle {
val id = Input(UInt(log2Up(cacheParams.nMMIOs).W))
// client requests
val req = Flipped(DecoupledIO(new InsUncacheReq ))
val req = Flipped(DecoupledIO(new InsUncacheReq))
val resp = DecoupledIO(new InsUncacheResp)
val mmio_acquire = DecoupledIO(new TLBundleA(edge.bundle))
......@@ -86,10 +86,11 @@ class InstrMMIOEntry(edge: TLEdgeOut)(implicit p: Parameters) extends XSModule w
when (state === s_refill_req) {
val address_aligned = req.addr(req.addr.getWidth - 1, log2Ceil(mmioBusBytes))
io.mmio_acquire.valid := true.B
io.mmio_acquire.bits := edge.Get(
io.mmio_acquire.bits := edge.Get(
fromSource = io.id,
toAddress = align(req.addr, mmioBusBytes),
toAddress = Cat(address_aligned, 0.U(log2Ceil(mmioBusBytes).W)),
lgSize = log2Ceil(mmioBusBytes).U
)._2
......
......@@ -28,7 +28,7 @@ import xiangshan.backend.fu.{PMPReqBundle, PMPRespBundle}
trait HasInstrMMIOConst extends HasXSParameter with HasIFUConst{
def mmioBusWidth = 64
def mmioBusBytes = mmioBusWidth /8
def mmioBusBytes = mmioBusWidth / 8
def maxInstrLen = 32
}
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册