Merge pull request #453 from cklarhorst/zybo

Zybo: Fix for Zynq7000 and use ps7 as submodule for Soft-CPUs
This commit is contained in:
Gwenhael Goavec-Merou 2022-11-25 21:48:43 +01:00 committed by GitHub
commit b030630237
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 144 additions and 24 deletions

View File

@ -80,22 +80,45 @@ _usb_uart_pmod_io = [
_connectors = [ _connectors = [
("pmoda", "N15 L14 K16 K14 N16 L15 J16 J14"), # XADC ("pmoda", "N15 L14 K16 K14 N16 L15 J16 J14"), # XADC
("pmodb", "T20 U20 V20 W20 Y18 Y19 W18 W19"), ("pmodb", "V8 W8 U7 V7 Y7 Y6 V6 W6"),
("pmodc", "V15 W15 T11 T10 W14 Y14 T12 U12"), ("pmodc", "V15 W15 T11 T10 W14 Y14 T12 U12"),
("pmodd", "T14 T15 P14 R14 U14 U15 V17 V18"), ("pmodd", "T14 T15 P14 R14 U14 U15 V17 V18"),
("pmode", "V12 W16 J15 H15 V13 U17 T17 Y17"), ("pmode", "V12 W16 J15 H15 V13 U17 T17 Y17"),
] ]
ps7_config = {
"z7-20" : {
"PCW_UIPARAM_DDR_PARTNO" : "MT41K256M16 RE-125",
"PCW_FPGA_FCLK0_ENABLE" : "1",
"PCW_UART1_BAUD_RATE" : "115200",
"PCW_EN_UART1" : "1",
"PCW_UART1_PERIPHERAL_ENABLE" : "1",
"PCW_UART1_UART1_IO" : "MIO 48 .. 49",
"PCW_PRESET_BANK1_VOLTAGE" : "LVCMOS 1.8V",
"PCW_USE_M_AXI_GP0" : "1",
"PCW_USE_S_AXI_GP0" : "1",
"PCW_USB0_PERIPHERAL_ENABLE" : "1",
"PCW_USB0_USB0_IO" : "MIO 28 .. 39",
"PCW_USB0_RESET_ENABLE" : "1",
"PCW_USB0_RESET_IO" : "MIO 46",
"PCW_EN_USB0" : "1"
}
}
# Platform ----------------------------------------------------------------------------------------- # Platform -----------------------------------------------------------------------------------------
class Platform(Xilinx7SeriesPlatform): class Platform(Xilinx7SeriesPlatform):
default_clk_name = "clk125" default_clk_name = "clk125"
default_clk_period = 1e9/125e6 default_clk_period = 1e9/125e6
def __init__(self, toolchain="vivado"): def __init__(self, variant="z7-20", toolchain="vivado"):
Xilinx7SeriesPlatform.__init__(self, "xc7z010-clg400-1", _io, _connectors, toolchain=toolchain) device = {
"z7-10": "xc7z010-clg400-1",
"z7-20": "xc7z020-clg400-1"
}[variant]
Xilinx7SeriesPlatform.__init__(self, device, _io, _connectors, toolchain=toolchain)
self.add_extension(_ps7_io) self.add_extension(_ps7_io)
self.add_extension(_usb_uart_pmod_io) self.add_extension(_usb_uart_pmod_io)
self.ps7_config = ps7_config[variant]
def create_programmer(self): def create_programmer(self):
return VivadoProgrammer() return VivadoProgrammer()

View File

@ -19,18 +19,18 @@ from litex.soc.cores.clock import *
from litex.soc.integration.soc_core import * from litex.soc.integration.soc_core import *
from litex.soc.integration.builder import * from litex.soc.integration.builder import *
from litex.soc.cores.led import LedChaser from litex.soc.cores.led import LedChaser
from litex.soc.integration.soc import SoCRegion
from litex.soc.cores import cpu
# CRG ---------------------------------------------------------------------------------------------- # CRG ----------------------------------------------------------------------------------------------
class _CRG(LiteXModule): class _CRG(LiteXModule):
def __init__(self, platform, sys_clk_freq, use_ps7_clk=False): def __init__(self, platform, sys_clk_freq, use_ps7_clk=False):
self.rst = Signal() self.rst = Signal()
self.cd_sys = ClockDomain() self.cd_sys = ClockDomain()
# # # # # #
if use_ps7_clk: if use_ps7_clk:
assert sys_clk_freq == 100e6
self.comb += ClockSignal("sys").eq(ClockSignal("ps7")) self.comb += ClockSignal("sys").eq(ClockSignal("ps7"))
self.comb += ResetSignal("sys").eq(ResetSignal("ps7") | self.rst) self.comb += ResetSignal("sys").eq(ResetSignal("ps7") | self.rst)
else: else:
@ -43,32 +43,79 @@ class _CRG(LiteXModule):
# BaseSoC ------------------------------------------------------------------------------------------ # BaseSoC ------------------------------------------------------------------------------------------
class BaseSoC(SoCCore): class BaseSoC(SoCCore):
def __init__(self, sys_clk_freq=100e6, with_led_chaser=True, **kwargs): def __init__(self, sys_clk_freq=100e6, variant="z7-10", with_ps7=False, with_led_chaser=True, **kwargs):
platform = digilent_zybo_z7.Platform() platform = digilent_zybo_z7.Platform()
self.builder = None
# CRG -------------------------------------------------------------------------------------- # CRG --------------------------------------------------------------------------------------
self.crg = _CRG(platform, sys_clk_freq) use_ps7_clk = (kwargs.get("cpu_type", None) == "zynq7000")
self.crg = _CRG(platform, sys_clk_freq, use_ps7_clk)
# SoCCore ---------------------------------------------------------------------------------- # SoCCore ----------------------------------------------------------------------------------
if kwargs["uart_name"] == "serial": if kwargs["uart_name"] == "serial":
kwargs["uart_name"] = "usb_uart" # Use USB-UART Pmod on JB. kwargs["uart_name"] = "usb_uart" # Use USB-UART Pmod on JB.
if kwargs.get("cpu_type", None) == "zynq7000":
kwargs["integrated_sram_size"] = 0x0
kwargs["with_uart"] = False
self.mem_map = {
'csr': 0x4000_0000, # Zynq GP0 default
}
SoCCore.__init__(self, platform, sys_clk_freq, ident="LiteX SoC on Zybo Z7", **kwargs) SoCCore.__init__(self, platform, sys_clk_freq, ident="LiteX SoC on Zybo Z7", **kwargs)
# Zynq7000 Integration --------------------------------------------------------------------- # Zynq7000 Integration ---------------------------------------------------------------------
if kwargs.get("cpu_type", None) == "zynq7000": if kwargs.get("cpu_type", None) == "zynq7000":
# Get and set the pre-generated .xci FIXME: change location? add it to the repository? self.cpu.use_rom = True
os.system("wget https://github.com/litex-hub/litex-boards/files/8339591/zybo_z7_ps7.txt)") if variant == "z7-10":
# Get and set the pre-generated .xci FIXME: change location? add it to the repository? Make config
os.makedirs("xci", exist_ok=True) os.makedirs("xci", exist_ok=True)
os.system("wget https://github.com/litex-hub/litex-boards/files/8339591/zybo_z7_ps7.txt")
os.system("mv zybo_z7_ps7.txt xci/zybo_z7_ps7.xci") os.system("mv zybo_z7_ps7.txt xci/zybo_z7_ps7.xci")
self.cpu.set_ps7_xci("xci/zybo_z7_ps7.xci") self.cpu.set_ps7_xci("xci/zybo_z7_ps7.xci")
else:
self.cpu.set_ps7(name="ps", config = platform.ps7_config)
# Connect AXI GP0 to the SoC with base address of 0x43c00000 (default one) # Connect AXI GP0 to the SoC with base address of 0x40000000 (default one)
wb_gp0 = wishbone.Interface() wb_gp0 = wishbone.Interface()
self.submodules += axi.AXI2Wishbone( self.submodules += axi.AXI2Wishbone(
axi = self.cpu.add_axi_gp_master(), axi = self.cpu.add_axi_gp_master(),
wishbone = wb_gp0, wishbone = wb_gp0,
base_address = 0x43c00000) base_address = 0x40000000)
self.bus.add_master(master=wb_gp0) self.bus.add_master(master=wb_gp0)
#TODO memory size dependend on board variant
self.bus.add_region("sram", SoCRegion(
origin = self.cpu.mem_map["sram"],
size = 512 * 1024 * 1024 - self.cpu.mem_map["sram"])
)
self.bus.add_region("rom", SoCRegion(
origin = self.cpu.mem_map["rom"],
size = 256 * 1024 * 1024 // 8,
linker = True)
)
self.constants["CONFIG_CLOCK_FREQUENCY"] = 666666687
self.bus.add_region("flash", SoCRegion(
origin = 0xFC00_0000,
size = 0x4_0000,
mode = "rwx")
)
# PS7 as Slave Integration ---------------------------------------------------------------------
elif with_ps7:
if variant == "z7-20":
cpu_cls = cpu.CPUS["zynq7000"]
zynq = cpu_cls(self.platform, "standard") # zynq7000 has no variants
zynq.set_ps7(name="ps", config = platform.ps7_config)
axi_gp_slave0 = zynq.add_axi_gp_slave(clock_domain = self.crg.cd_sys.name)
self.submodules += zynq
self.bus.add_slave(
name="ps",slave=axi_gp_slave0,
region=SoCRegion(
origin=0x2000_0000,
size=0x2000_0000,
mode="rwx"
)
)
else:
#TODO: make config for zybo-z7-10
raise NotImplementedError
# Leds ------------------------------------------------------------------------------------- # Leds -------------------------------------------------------------------------------------
if with_led_chaser: if with_led_chaser:
@ -76,22 +123,72 @@ class BaseSoC(SoCCore):
pads = platform.request_all("user_led"), pads = platform.request_all("user_led"),
sys_clk_freq = sys_clk_freq) sys_clk_freq = sys_clk_freq)
def finalize(self, *args, **kwargs):
super(BaseSoC, self).finalize(*args, **kwargs)
if self.cpu_type != "zynq7000":
return
libxil_path = os.path.join(self.builder.software_dir, 'libxil')
os.makedirs(os.path.realpath(libxil_path), exist_ok=True)
lib = os.path.join(libxil_path, 'embeddedsw')
if not os.path.exists(lib):
os.system("git clone --depth 1 https://github.com/Xilinx/embeddedsw {}".format(lib))
os.makedirs(os.path.realpath(self.builder.include_dir), exist_ok=True)
for header in [
'XilinxProcessorIPLib/drivers/uartps/src/xuartps_hw.h',
'lib/bsp/standalone/src/common/xil_types.h',
'lib/bsp/standalone/src/common/xil_assert.h',
'lib/bsp/standalone/src/common/xil_io.h',
'lib/bsp/standalone/src/common/xil_printf.h',
'lib/bsp/standalone/src/common/xstatus.h',
'lib/bsp/standalone/src/common/xdebug.h',
'lib/bsp/standalone/src/arm/cortexa9/xpseudo_asm.h',
'lib/bsp/standalone/src/arm/cortexa9/xreg_cortexa9.h',
'lib/bsp/standalone/src/arm/cortexa9/xil_cache.h',
'lib/bsp/standalone/src/arm/cortexa9/xparameters_ps.h',
'lib/bsp/standalone/src/arm/cortexa9/xil_errata.h',
'lib/bsp/standalone/src/arm/cortexa9/xtime_l.h',
'lib/bsp/standalone/src/arm/common/xil_exception.h',
'lib/bsp/standalone/src/arm/common/gcc/xpseudo_asm_gcc.h',
]:
shutil.copy(os.path.join(lib, header), self.builder.include_dir)
write_to_file(os.path.join(self.builder.include_dir, 'bspconfig.h'),
'#define FPU_HARD_FLOAT_ABI_ENABLED 1')
write_to_file(os.path.join(self.builder.include_dir, 'xparameters.h'), '''
#ifndef __XPARAMETERS_H
#define __XPARAMETERS_H
#include "xparameters_ps.h"
#define STDOUT_BASEADDRESS XPS_UART1_BASEADDR
#define XPAR_PS7_DDR_0_S_AXI_BASEADDR 0x00100000
#define XPAR_PS7_DDR_0_S_AXI_HIGHADDR 0x3FFFFFFF
#endif
''')
# Build -------------------------------------------------------------------------------------------- # Build --------------------------------------------------------------------------------------------
def main(): def main():
from litex.build.parser import LiteXArgumentParser from litex.build.parser import LiteXArgumentParser
parser = LiteXArgumentParser(platform=digilent_zybo_z7.Platform, description="LiteX SoC on Zybo Z7.") parser = LiteXArgumentParser(platform=digilent_zybo_z7.Platform, description="LiteX SoC on Zybo Z7")
parser.add_target_argument("--sys-clk-freq", default=100e6, type=float, help="System clock frequency.") parser.add_target_argument("--sys-clk-freq", default=125e6, type=float, help="System clock frequency.")
parser.add_target_argument("--variant", default="z7-10", help="Board variant (z7-10 or z7-20).")
parser.add_target_argument("--with-ps7", action="store_true", help="Add the PS7 as slave for soft CPUs.")
args = parser.parse_args() args = parser.parse_args()
soc = BaseSoC( soc = BaseSoC(
sys_clk_freq = args.sys_clk_freq, sys_clk_freq = args.sys_clk_freq,
**parser.soc_argdict variant = args.variant,
with_ps7 = args.with_ps7,
**soc_core_argdict(args)
) )
builder = Builder(soc, **parser.builder_argdict) builder = Builder(soc, **builder_argdict(args))
if args.cpu_type == "zynq7000":
soc.builder = builder
builder.add_software_package('libxil')
builder.add_software_library('libxil')
if args.build: if args.build:
builder.build(**parser.toolchain_argdict) builder.build(**parser.toolchain_argdict)
if args.load: if args.load:
prog = soc.platform.create_programmer() prog = soc.platform.create_programmer()
prog.load_bitstream(builder.get_bitstream_filename(mode="sram"), device=1) prog.load_bitstream(builder.get_bitstream_filename(mode="sram"), device=1)