From: Jean-François Nguyen Date: Thu, 26 Mar 2020 11:27:02 +0000 (+0100) Subject: soc.cpu: add CPUSoC and BIOSBuilder X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=0959a2c55b76de39e16955a345b1358d4e8db86e;p=lambdasoc.git soc.cpu: add CPUSoC and BIOSBuilder --- diff --git a/.gitmodules b/.gitmodules new file mode 100644 index 0000000..d1c001b --- /dev/null +++ b/.gitmodules @@ -0,0 +1,3 @@ +[submodule "lambdasoc/software/bios"] + path = lambdasoc/software/bios + url = git@github.com:lambdaconcept/lambdasoc-bios diff --git a/lambdasoc/soc/cpu.py b/lambdasoc/soc/cpu.py new file mode 100644 index 0000000..dac9624 --- /dev/null +++ b/lambdasoc/soc/cpu.py @@ -0,0 +1,84 @@ +from .base import * +from ..cpu import CPU +from ..periph.intc import InterruptController +from ..periph.sram import SRAMPeripheral +from ..periph.serial import AsyncSerialPeripheral +from ..periph.timer import TimerPeripheral + + +__all__ = ["CPUSoC", "BIOSBuilder"] + + +class CPUSoC(SoC): + cpu = socproperty(CPU) + intc = socproperty(InterruptController) + rom = socproperty(SRAMPeripheral) + ram = socproperty(SRAMPeripheral) # TODO: abstract class for storage peripherals. + uart = socproperty(AsyncSerialPeripheral) + timer = socproperty(TimerPeripheral) + + # TODO: implement a CRG peripheral and expose clock frequencies through CSRs. + clk_freq = socproperty(int) + + def build(self, name=None, + build_dir="build/soc", do_build=True, + do_init=False): + """TODO + """ + plan = BIOSBuilder().prepare(self, build_dir, name) + if not do_build: + return plan + + products = plan.execute_local(build_dir) + if not do_init: + return products + + with products.extract("bios.bin") as bios_filename: + with open(bios_filename, "rb") as f: + words = iter(lambda: f.read(self.cpu.data_width // 8), b'') + bios = [int.from_bytes(w, self.cpu.byteorder) for w in words] + self.rom.init = bios + + +class BIOSBuilder(ConfigBuilder): + file_templates = { + **ConfigBuilder.file_templates, + "{{name}}.config": r""" + # {{autogenerated}} + CONFIG_CPU_{{soc.cpu.name.upper()}}=y + CONFIG_CPU_RESET_ADDR={{hex(soc.cpu.reset_addr)}} + CONFIG_CPU_BYTEORDER="{{soc.cpu.byteorder}}" + CONFIG_ARCH_{{soc.cpu.arch.upper()}}=y + {% if soc.cpu.muldiv == "soft" %} + CONFIG_{{soc.cpu.arch.upper()}}_MULDIV_SOFT=y + {% else %} + CONFIG_{{soc.cpu.arch.upper()}}_MULDIV_SOFT=n + {% endif %} + CONFIG_ROM_START={{hex(periph_addr(soc.rom))}} + CONFIG_ROM_SIZE={{hex(soc.rom.size)}} + CONFIG_RAM_START={{hex(periph_addr(soc.ram))}} + CONFIG_RAM_SIZE={{hex(soc.ram.size)}} + CONFIG_UART_START={{hex(periph_addr(soc.uart))}} + CONFIG_UART_IRQNO={{soc.intc.find_index(soc.uart.irq)}} + CONFIG_UART_RX_RINGBUF_SIZE_LOG2=7 + CONFIG_UART_TX_RINGBUF_SIZE_LOG2=7 + CONFIG_TIMER_START={{hex(periph_addr(soc.timer))}} + CONFIG_TIMER_IRQNO={{soc.intc.find_index(soc.timer.irq)}} + CONFIG_TIMER_CTR_WIDTH={{soc.timer.width}} + CONFIG_CLOCK_FREQ={{soc.clk_freq}} + """, + } + command_templates = [ + *ConfigBuilder.command_templates, + r""" + build={{build_dir}} + KCONFIG_CONFIG={{build_dir}}/{{name}}.config + make -C {{software_dir}}/bios + """, + ] + + def prepare(self, soc, build_dir, name): + if not isinstance(soc, CPUSoC): + raise TypeError("SoC must be an instance of CPUSoC, not {!r}" + .format(soc)) + return super().prepare(soc, build_dir, name) diff --git a/lambdasoc/software/__init__.py b/lambdasoc/software/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/lambdasoc/software/bios b/lambdasoc/software/bios new file mode 160000 index 0000000..38c21eb --- /dev/null +++ b/lambdasoc/software/bios @@ -0,0 +1 @@ +Subproject commit 38c21eb2b3302710f553de6d0708aa10b228d82b