add CSV CSR map output
This commit is contained in:
parent
1672c4a176
commit
833d7c7eec
16
make.py
16
make.py
|
@ -4,10 +4,11 @@ import argparse, os, importlib, subprocess
|
|||
|
||||
from mibuild.tools import write_to_file
|
||||
|
||||
from milkymist import cif
|
||||
from milkymist import cpuif
|
||||
from milkymist.s6ddrphy import initsequence
|
||||
import top, jtag
|
||||
|
||||
def build(platform_name, build_bitstream, build_header, *soc_args, **soc_kwargs):
|
||||
def build(platform_name, build_bitstream, build_header, csr_csv_filename, *soc_args, **soc_kwargs):
|
||||
platform_module = importlib.import_module("mibuild.platforms."+platform_name)
|
||||
platform = platform_module.Platform()
|
||||
soc = top.SoC(platform, platform_name, *soc_args, **soc_kwargs)
|
||||
|
@ -46,24 +47,27 @@ TIMESPEC "TSise_sucks2" = FROM "GRPsys_clk" TO "GRPvga_clk" TIG;
|
|||
else:
|
||||
soc.finalize()
|
||||
if build_header:
|
||||
csr_header = cif.get_csr_header(soc.csr_base, soc.csrbankarray, soc.interrupt_map)
|
||||
csr_header = cpuif.get_csr_header(soc.csr_base, soc.csrbankarray, soc.interrupt_map)
|
||||
write_to_file("software/include/hw/csr.h", csr_header)
|
||||
|
||||
sdram_phy_header = cif.get_sdram_phy_header(soc.ddrphy)
|
||||
sdram_phy_header = initsequence.get_sdram_phy_header(soc.ddrphy)
|
||||
write_to_file("software/include/hw/sdram_phy.h", sdram_phy_header)
|
||||
|
||||
if csr_csv_filename:
|
||||
csr_csv = cpuif.get_csr_csv(soc.csr_base, soc.csrbankarray)
|
||||
write_to_file(csr_csv_filename, csr_csv)
|
||||
|
||||
def main():
|
||||
parser = argparse.ArgumentParser(description="milkymist-ng - a high performance SoC built on Migen technology.")
|
||||
parser.add_argument("-p", "--platform", default="mixxeo", help="platform to build for")
|
||||
parser.add_argument("-B", "--no-bitstream", default=False, action="store_true", help="do not build bitstream file")
|
||||
parser.add_argument("-H", "--no-header", default=False, action="store_true", help="do not build C header files with CSR/IRQ/SDRAM_PHY defs")
|
||||
parser.add_argument("-c", "--csr-csv", default="", help="save CSR map in CSV file")
|
||||
parser.add_argument("-l", "--load", default=False, action="store_true", help="load bitstream to SRAM")
|
||||
parser.add_argument("-f", "--flash", default=False, action="store_true", help="load bitstream to flash")
|
||||
parser.add_argument("-m", "--with-memtest", default=False, action="store_true", help="include memtest cores")
|
||||
args = parser.parse_args()
|
||||
|
||||
build(args.platform, not args.no_bitstream, not args.no_header, args.with_memtest)
|
||||
build(args.platform, not args.no_bitstream, not args.no_header, args.csr_csv, args.with_memtest)
|
||||
if args.load:
|
||||
jtag.load("build/soc-"+args.platform+".bit")
|
||||
if args.flash:
|
||||
|
|
|
@ -0,0 +1,64 @@
|
|||
from migen.bank.description import CSRStatus
|
||||
|
||||
def _get_rw_functions(reg_name, reg_base, size, read_only):
|
||||
r = ""
|
||||
if size > 8:
|
||||
raise NotImplementedError("Register too large")
|
||||
elif size > 4:
|
||||
ctype = "unsigned long long int"
|
||||
elif size > 2:
|
||||
ctype = "unsigned int"
|
||||
elif size > 1:
|
||||
ctype = "unsigned short int"
|
||||
else:
|
||||
ctype = "unsigned char"
|
||||
|
||||
r += "static inline "+ctype+" "+reg_name+"_read(void) {\n"
|
||||
if size > 1:
|
||||
r += "\t"+ctype+" r = MMPTR("+hex(reg_base)+");\n"
|
||||
for byte in range(1, size):
|
||||
r += "\tr <<= 8;\n\tr |= MMPTR("+hex(reg_base+4*byte)+");\n"
|
||||
r += "\treturn r;\n}\n"
|
||||
else:
|
||||
r += "\treturn MMPTR("+hex(reg_base)+");\n}\n"
|
||||
|
||||
if not read_only:
|
||||
r += "static inline void "+reg_name+"_write("+ctype+" value) {\n"
|
||||
for byte in range(size):
|
||||
shift = (size-byte-1)*8
|
||||
if shift:
|
||||
value_shifted = "value >> "+str(shift)
|
||||
else:
|
||||
value_shifted = "value"
|
||||
r += "\tMMPTR("+hex(reg_base+4*byte)+") = "+value_shifted+";\n"
|
||||
r += "}\n"
|
||||
return r
|
||||
|
||||
def get_csr_header(csr_base, bank_array, interrupt_map):
|
||||
r = "#ifndef __HW_CSR_H\n#define __HW_CSR_H\n#include <hw/common.h>\n"
|
||||
for name, csrs, mapaddr, rmap in bank_array.banks:
|
||||
r += "\n/* "+name+" */\n"
|
||||
reg_base = csr_base + 0x800*mapaddr
|
||||
r += "#define "+name.upper()+"_BASE "+hex(reg_base)+"\n"
|
||||
for csr in csrs:
|
||||
nr = (csr.size + 7)//8
|
||||
r += _get_rw_functions(name + "_" + csr.name, reg_base, nr, isinstance(csr, CSRStatus))
|
||||
reg_base += 4*nr
|
||||
try:
|
||||
interrupt_nr = interrupt_map[name]
|
||||
except KeyError:
|
||||
pass
|
||||
else:
|
||||
r += "#define "+name.upper()+"_INTERRUPT "+str(interrupt_nr)+"\n"
|
||||
r += "\n#endif\n"
|
||||
return r
|
||||
|
||||
def get_csr_csv(csr_base, bank_array):
|
||||
r = ""
|
||||
for name, csrs, mapaddr, rmap in bank_array.banks:
|
||||
reg_base = csr_base + 0x800*mapaddr
|
||||
for csr in csrs:
|
||||
nr = (csr.size + 7)//8
|
||||
r += "{}_{},0x{:08x},{},{}\n".format(name, csr.name, reg_base, nr, "ro" if isinstance(csr, CSRStatus) else "rw")
|
||||
reg_base += 4*nr
|
||||
return r
|
|
@ -1,70 +1,4 @@
|
|||
from operator import itemgetter
|
||||
import re
|
||||
|
||||
from migen.fhdl.std import *
|
||||
from migen.bank.description import CSRStatus
|
||||
|
||||
def get_macros(filename):
|
||||
f = open(filename, "r")
|
||||
r = {}
|
||||
for line in f:
|
||||
match = re.match("\w*#define\s+(\w+)\s+(.*)", line, re.IGNORECASE)
|
||||
if match:
|
||||
r[match.group(1)] = match.group(2)
|
||||
return r
|
||||
|
||||
def _get_rw_functions(reg_name, reg_base, size, read_only):
|
||||
r = ""
|
||||
if size > 8:
|
||||
raise NotImplementedError("Register too large")
|
||||
elif size > 4:
|
||||
ctype = "unsigned long long int"
|
||||
elif size > 2:
|
||||
ctype = "unsigned int"
|
||||
elif size > 1:
|
||||
ctype = "unsigned short int"
|
||||
else:
|
||||
ctype = "unsigned char"
|
||||
|
||||
r += "static inline "+ctype+" "+reg_name+"_read(void) {\n"
|
||||
if size > 1:
|
||||
r += "\t"+ctype+" r = MMPTR("+hex(reg_base)+");\n"
|
||||
for byte in range(1, size):
|
||||
r += "\tr <<= 8;\n\tr |= MMPTR("+hex(reg_base+4*byte)+");\n"
|
||||
r += "\treturn r;\n}\n"
|
||||
else:
|
||||
r += "\treturn MMPTR("+hex(reg_base)+");\n}\n"
|
||||
|
||||
if not read_only:
|
||||
r += "static inline void "+reg_name+"_write("+ctype+" value) {\n"
|
||||
for byte in range(size):
|
||||
shift = (size-byte-1)*8
|
||||
if shift:
|
||||
value_shifted = "value >> "+str(shift)
|
||||
else:
|
||||
value_shifted = "value"
|
||||
r += "\tMMPTR("+hex(reg_base+4*byte)+") = "+value_shifted+";\n"
|
||||
r += "}\n"
|
||||
return r
|
||||
|
||||
def get_csr_header(csr_base, bank_array, interrupt_map):
|
||||
r = "#ifndef __HW_CSR_H\n#define __HW_CSR_H\n#include <hw/common.h>\n"
|
||||
for name, csrs, mapaddr, rmap in bank_array.banks:
|
||||
r += "\n/* "+name+" */\n"
|
||||
reg_base = csr_base + 0x800*mapaddr
|
||||
r += "#define "+name.upper()+"_BASE "+hex(reg_base)+"\n"
|
||||
for csr in csrs:
|
||||
nr = (csr.size + 7)//8
|
||||
r += _get_rw_functions(name + "_" + csr.name, reg_base, nr, isinstance(csr, CSRStatus))
|
||||
reg_base += 4*nr
|
||||
try:
|
||||
interrupt_nr = interrupt_map[name]
|
||||
except KeyError:
|
||||
pass
|
||||
else:
|
||||
r += "#define "+name.upper()+"_INTERRUPT "+str(interrupt_nr)+"\n"
|
||||
r += "\n#endif\n"
|
||||
return r
|
||||
from migen.fhdl.std import log2_int
|
||||
|
||||
def get_sdram_phy_header(sdram_phy):
|
||||
if sdram_phy.phy_settings.memtype not in ["SDR", "DDR", "LPDDR", "DDR2"]:
|
3
top.py
3
top.py
|
@ -10,9 +10,8 @@ from mibuild.generic_platform import ConstraintError
|
|||
|
||||
from milkymist import mxcrg, lm32, norflash, uart, s6ddrphy, dfii, lasmicon, \
|
||||
identifier, timer, minimac3, framebuffer, dvisampler, gpio, memtest
|
||||
from milkymist.cif import get_macros
|
||||
|
||||
version = get_macros("common/version.h")["VERSION"][1:-1]
|
||||
version = "2.0"
|
||||
|
||||
clk_freq = (83 + Fraction(1, 3))*1000000
|
||||
sram_size = 4096 # in bytes
|
||||
|
|
Loading…
Reference in New Issue