cpu/rocket: rework variant naming convention
The naming convention for LiteX Rocket variants has become overly complex. Simplify it while at the same time adding more flexibility. There is a new set of instances of varying main RAM memory bus port width (1x (64bit), 2x (128bit), 4x (256bit), and 8x (512bit)), of each of the following principal LiteX specific Rocket models: - small: (rv64imac, no MMU, no S, no FPU) - medium: (rv64imac, adds MMU and S-mode) - linux: (rv64imafdc, adds FPU, supports linux distros) - full: (rv64imafdcbkph[+], adds hypervisor support) NOTE: before adding H support, the feature set of the old `full` model is now represented by the `linux` model. The old `linux` did not use to have an FPU, and is now available as `medium`. In addition to the range of memory port widths, each model will be instantiated in 1, 2, 4, and 8 core variants. The naming convention is `LitexConfig_<model>_<num_cores>_<mem_width>`. E.g. `LitexConfig_full_8_2` for an 8-core full model with a 128bit main RAM AXI port. On the build command line, this example would look like: ... --cpu-type rocket --cpu-variant full \ --cpu-num-cores 8 --cpu-mem-width 2 \ ... There are a total of 4 * 4 * 4 = 64 (sub-)variants: each of the four principal models can be fitted with one of four core counts, and one of four memory bus widths. Signed-off-by: Gabriel Somlo <gsomlo@gmail.com>
This commit is contained in:
parent
1c43a71970
commit
c3e93620ec
|
@ -30,6 +30,7 @@
|
||||||
# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
import os
|
import os
|
||||||
|
import logging
|
||||||
|
|
||||||
from migen import *
|
from migen import *
|
||||||
|
|
||||||
|
@ -44,67 +45,6 @@ from litex.soc.integration.soc import SoCRegion
|
||||||
|
|
||||||
from litex.soc.cores.cpu import CPU, CPU_GCC_TRIPLE_RISCV64
|
from litex.soc.cores.cpu import CPU, CPU_GCC_TRIPLE_RISCV64
|
||||||
|
|
||||||
# Variants -----------------------------------------------------------------------------------------
|
|
||||||
|
|
||||||
CPU_VARIANTS = {
|
|
||||||
"standard" : "freechips.rocketchip.system.LitexConfig",
|
|
||||||
"linux" : "freechips.rocketchip.system.LitexLinuxConfig",
|
|
||||||
"linux4" : "freechips.rocketchip.system.LitexLinux4Config",
|
|
||||||
"linuxd" : "freechips.rocketchip.system.LitexLinuxDConfig",
|
|
||||||
"linux2d" : "freechips.rocketchip.system.LitexLinux2DConfig",
|
|
||||||
"linuxq" : "freechips.rocketchip.system.LitexLinuxQConfig",
|
|
||||||
"linux2q" : "freechips.rocketchip.system.LitexLinux2QConfig",
|
|
||||||
"full" : "freechips.rocketchip.system.LitexFullConfig",
|
|
||||||
"fulld" : "freechips.rocketchip.system.LitexFullDConfig",
|
|
||||||
"full4d" : "freechips.rocketchip.system.LitexFull4DConfig",
|
|
||||||
"fullq" : "freechips.rocketchip.system.LitexFullQConfig",
|
|
||||||
"full4q" : "freechips.rocketchip.system.LitexFull4QConfig",
|
|
||||||
"fullo" : "freechips.rocketchip.system.LitexFullOConfig",
|
|
||||||
"full4o" : "freechips.rocketchip.system.LitexFull4OConfig",
|
|
||||||
"full8o" : "freechips.rocketchip.system.LitexFull8OConfig",
|
|
||||||
}
|
|
||||||
|
|
||||||
# GCC Flags-----------------------------------------------------------------------------------------
|
|
||||||
|
|
||||||
GCC_FLAGS = {
|
|
||||||
"standard" : "-march=rv64i2p0_mac -mabi=lp64 ",
|
|
||||||
"linux" : "-march=rv64i2p0_mac -mabi=lp64 ",
|
|
||||||
"linux4" : "-march=rv64i2p0_mac -mabi=lp64 ",
|
|
||||||
"linuxd" : "-march=rv64i2p0_mac -mabi=lp64 ",
|
|
||||||
"linux2d" : "-march=rv64i2p0_mac -mabi=lp64 ",
|
|
||||||
"linuxq" : "-march=rv64i2p0_mac -mabi=lp64 ",
|
|
||||||
"linux2q" : "-march=rv64i2p0_mac -mabi=lp64 ",
|
|
||||||
"full" : "-march=rv64i2p0_mafdc -mabi=lp64 ",
|
|
||||||
"fulld" : "-march=rv64i2p0_mafdc -mabi=lp64 ",
|
|
||||||
"full4d" : "-march=rv64i2p0_mafdc -mabi=lp64 ",
|
|
||||||
"fullq" : "-march=rv64i2p0_mafdc -mabi=lp64 ",
|
|
||||||
"full4q" : "-march=rv64i2p0_mafdc -mabi=lp64 ",
|
|
||||||
"fullo" : "-march=rv64i2p0_mafdc -mabi=lp64 ",
|
|
||||||
"full4o" : "-march=rv64i2p0_mafdc -mabi=lp64 ",
|
|
||||||
"full8o" : "-march=rv64i2p0_mafdc -mabi=lp64 ",
|
|
||||||
}
|
|
||||||
|
|
||||||
# CPU Params ----------------------------------------------------------------------------------
|
|
||||||
|
|
||||||
CPU_PARAMS = {
|
|
||||||
# Variant : (mem_dw, mmio_dw, num_cores)
|
|
||||||
"standard" : ( 64, 64, 1),
|
|
||||||
"linux" : ( 64, 64, 1),
|
|
||||||
"linux4" : ( 64, 64, 4),
|
|
||||||
"linuxd" : ( 128, 64, 1),
|
|
||||||
"linux2d" : ( 128, 64, 2),
|
|
||||||
"linuxq" : ( 256, 64, 1),
|
|
||||||
"linux2q" : ( 256, 64, 2),
|
|
||||||
"full" : ( 64, 64, 1),
|
|
||||||
"fulld" : ( 128, 64, 1),
|
|
||||||
"full4d" : ( 128, 64, 4),
|
|
||||||
"fullq" : ( 256, 64, 1),
|
|
||||||
"full4q" : ( 256, 64, 4),
|
|
||||||
"fullo" : ( 512, 64, 1),
|
|
||||||
"full4o" : ( 512, 64, 4),
|
|
||||||
"full8o" : ( 512, 64, 8),
|
|
||||||
}
|
|
||||||
|
|
||||||
# Rocket ------------------------------------------------------------------------------------------
|
# Rocket ------------------------------------------------------------------------------------------
|
||||||
|
|
||||||
class Rocket(CPU):
|
class Rocket(CPU):
|
||||||
|
@ -112,7 +52,7 @@ class Rocket(CPU):
|
||||||
family = "riscv"
|
family = "riscv"
|
||||||
name = "rocket"
|
name = "rocket"
|
||||||
human_name = "RocketRV64[imac]"
|
human_name = "RocketRV64[imac]"
|
||||||
variants = CPU_VARIANTS
|
variants = ["small", "medium", "linux", "full"]
|
||||||
data_width = 64
|
data_width = 64
|
||||||
endianness = "little"
|
endianness = "little"
|
||||||
gcc_triple = CPU_GCC_TRIPLE_RISCV64
|
gcc_triple = CPU_GCC_TRIPLE_RISCV64
|
||||||
|
@ -120,13 +60,38 @@ class Rocket(CPU):
|
||||||
nop = "nop"
|
nop = "nop"
|
||||||
io_regions = {0x1200_0000: 0x7000_0000} # Origin, Length.
|
io_regions = {0x1200_0000: 0x7000_0000} # Origin, Length.
|
||||||
|
|
||||||
|
# Default parameters.
|
||||||
|
cpu_num_cores = 1
|
||||||
|
cpu_mem_width = 1
|
||||||
|
|
||||||
|
# Command line configuration arguments.
|
||||||
|
@staticmethod
|
||||||
|
def args_fill(parser):
|
||||||
|
cpu_group = parser.add_argument_group(title="CPU options")
|
||||||
|
cpu_group.add_argument("--cpu-num-cores", default=1, help="Number of cores (1, 2, 4, 8).", type=int)
|
||||||
|
cpu_group.add_argument("--cpu-mem-width", default=1, help="Width of memory port (1, 2, 4, 8).", type=int)
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def args_read(args):
|
||||||
|
logger = logging.getLogger("RocketArgs")
|
||||||
|
if int(args.cpu_num_cores) in [1, 2, 4, 8]:
|
||||||
|
Rocket.cpu_num_cores = int(args.cpu_num_cores)
|
||||||
|
else:
|
||||||
|
logger.error("Invalid '--cpu-num-cores {}' (should be 1, 2, 4, or 8)".format(args.cpu_num_cores))
|
||||||
|
quit()
|
||||||
|
if int(args.cpu_mem_width) in [1, 2, 4, 8]:
|
||||||
|
Rocket.cpu_mem_width = int(args.cpu_mem_width)
|
||||||
|
else:
|
||||||
|
logger.error("Invalid '--cpu-mem-width {}' (should be 1, 2, 4, or 8)".format(args.cpu_mem_width))
|
||||||
|
quit()
|
||||||
|
|
||||||
# Arch.
|
# Arch.
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def get_arch(variant):
|
def get_arch(variant):
|
||||||
if "full" in variant:
|
if variant in ["linux", "full"]:
|
||||||
return "rv64imafdc"
|
return "rv64i2p0_mafdc"
|
||||||
else:
|
else:
|
||||||
return "rv64imac"
|
return "rv64i2p0_mac"
|
||||||
|
|
||||||
# Memory Mapping.
|
# Memory Mapping.
|
||||||
@property
|
@property
|
||||||
|
@ -146,19 +111,20 @@ class Rocket(CPU):
|
||||||
@property
|
@property
|
||||||
def gcc_flags(self):
|
def gcc_flags(self):
|
||||||
flags = "-mno-save-restore "
|
flags = "-mno-save-restore "
|
||||||
flags += GCC_FLAGS[self.variant]
|
flags += f"-march={self.get_arch(self.variant)} -mabi=lp64 "
|
||||||
flags += "-D__rocket__ "
|
flags += "-D__rocket__ "
|
||||||
flags += "-mcmodel=medany"
|
flags += "-mcmodel=medany"
|
||||||
return flags
|
return flags
|
||||||
|
|
||||||
def __init__(self, platform, variant="standard"):
|
def __init__(self, platform, variant="linux"):
|
||||||
self.platform = platform
|
self.platform = platform
|
||||||
self.variant = variant
|
self.variant = variant
|
||||||
|
|
||||||
self.reset = Signal()
|
self.reset = Signal()
|
||||||
self.interrupt = Signal(8)
|
self.interrupt = Signal(8)
|
||||||
|
|
||||||
mem_dw, mmio_dw, num_cores = CPU_PARAMS[self.variant]
|
mem_dw = 64 * Rocket.cpu_mem_width
|
||||||
|
mmio_dw = 64
|
||||||
|
|
||||||
self.mem_axi = mem_axi = axi.AXIInterface(data_width=mem_dw, address_width=32, id_width=4)
|
self.mem_axi = mem_axi = axi.AXIInterface(data_width=mem_dw, address_width=32, id_width=4)
|
||||||
self.mmio_axi = mmio_axi = axi.AXIInterface(data_width=mmio_dw, address_width=32, id_width=4)
|
self.mmio_axi = mmio_axi = axi.AXIInterface(data_width=mmio_dw, address_width=32, id_width=4)
|
||||||
|
@ -329,7 +295,7 @@ class Rocket(CPU):
|
||||||
o_l2_frontend_bus_axi4_0_r_bits_last = l2fb_axi.r.last,
|
o_l2_frontend_bus_axi4_0_r_bits_last = l2fb_axi.r.last,
|
||||||
)
|
)
|
||||||
# additional per-core debug signals:
|
# additional per-core debug signals:
|
||||||
self.cpu_params.update({'i_resetctrl_hartIsInReset_%s'%i : Open() for i in range(num_cores)})
|
self.cpu_params.update({'i_resetctrl_hartIsInReset_%s'%i : Open() for i in range(Rocket.cpu_num_cores)})
|
||||||
|
|
||||||
# Adapt AXI interfaces to Wishbone.
|
# Adapt AXI interfaces to Wishbone.
|
||||||
mmio_a2w = axi.AXI2Wishbone(mmio_axi, mmio_wb, base_address=0)
|
mmio_a2w = axi.AXI2Wishbone(mmio_axi, mmio_wb, base_address=0)
|
||||||
|
@ -346,12 +312,14 @@ class Rocket(CPU):
|
||||||
assert reset_address == 0x1000_0000, "cpu_reset_addr hardcoded in during elaboration!"
|
assert reset_address == 0x1000_0000, "cpu_reset_addr hardcoded in during elaboration!"
|
||||||
|
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def add_sources(platform, variant="standard"):
|
def add_sources(platform, variant):
|
||||||
|
pfx = "freechips.rocketchip.system.LitexConfig"
|
||||||
|
fname = f"{pfx}_{variant}_{Rocket.cpu_num_cores}_{Rocket.cpu_mem_width}"
|
||||||
vdir = get_data_mod("cpu", "rocket").data_location
|
vdir = get_data_mod("cpu", "rocket").data_location
|
||||||
platform.add_sources(
|
platform.add_sources(
|
||||||
os.path.join(vdir, "generated-src"),
|
os.path.join(vdir, "generated-src"),
|
||||||
CPU_VARIANTS[variant] + ".v",
|
f"{fname}.v",
|
||||||
CPU_VARIANTS[variant] + ".behav_srams.v",
|
f"{fname}.behav_srams.v",
|
||||||
)
|
)
|
||||||
platform.add_sources(
|
platform.add_sources(
|
||||||
os.path.join(vdir, "vsrc"),
|
os.path.join(vdir, "vsrc"),
|
||||||
|
@ -361,16 +329,13 @@ class Rocket(CPU):
|
||||||
)
|
)
|
||||||
|
|
||||||
def add_soc_components(self, soc):
|
def add_soc_components(self, soc):
|
||||||
# Get CPU Params.
|
|
||||||
mem_dw, mmio_dw, num_cores = CPU_PARAMS[self.variant]
|
|
||||||
|
|
||||||
# Add OpenSBI/PLIC/CLINT regions.
|
# Add OpenSBI/PLIC/CLINT regions.
|
||||||
soc.bus.add_region("opensbi", SoCRegion(origin=self.mem_map["main_ram"] + 0x0000_0000, size=0x20_0000, cached=False, linker=True))
|
soc.bus.add_region("opensbi", SoCRegion(origin=self.mem_map["main_ram"] + 0x0000_0000, size=0x20_0000, cached=False, linker=True))
|
||||||
soc.bus.add_region("plic", SoCRegion(origin=soc.mem_map.get("plic"), size=0x40_0000, cached=True, linker=True))
|
soc.bus.add_region("plic", SoCRegion(origin=soc.mem_map.get("plic"), size=0x40_0000, cached=True, linker=True))
|
||||||
soc.bus.add_region("clint", SoCRegion(origin=soc.mem_map.get("clint"), size= 0x1_0000, cached=True, linker=True))
|
soc.bus.add_region("clint", SoCRegion(origin=soc.mem_map.get("clint"), size= 0x1_0000, cached=True, linker=True))
|
||||||
|
|
||||||
# Define number of CPUs
|
# Define number of CPUs
|
||||||
soc.add_config("CPU_COUNT", num_cores)
|
soc.add_config("CPU_COUNT", Rocket.cpu_num_cores)
|
||||||
soc.add_config("CPU_ISA", self.get_arch(self.variant))
|
soc.add_config("CPU_ISA", self.get_arch(self.variant))
|
||||||
soc.add_config("CPU_MMU", "sv39")
|
soc.add_config("CPU_MMU", "sv39")
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue