mirror of
https://github.com/retroSoC/retroSoC.git
synced 2026-11-04 22:32:36 +00:00
feat: refactor memory map definitions and enhance fault handling in Mini SoC
- Updated core_wrapper and mgmt_core_wrapper to use new SOC reset and IRQ addresses. - Removed obsolete mmap_define.svh file and integrated memory map generation into the build process. - Enhanced ip_nmi_wrapper to handle fault signals and updated NMI interface assignments. - Added bus fault and sysctrl fault testbenches to validate fault handling mechanisms. - Improved memory map generation script and added tests for memory map validation and fault responder behavior.
This commit is contained in:
28 files changed
+1139
-482
No files matched your search
+1
-1
@@ -52,7 +52,7 @@ icsprout55-pdk
|
||||
IHP-Open-PDK
|
||||
skywater-pdk
|
||||
gf180mcu-pdk
|
||||
demo
|
||||
demo*
|
||||
dont_use_cell_*
|
||||
clusterip
|
||||
nanoV
|
||||
|
||||
@@ -178,6 +178,8 @@ help:
|
||||
' setup install pinned external dependencies' \
|
||||
' doctor check tools, paths, and selected configuration' \
|
||||
' config | manifest print/write the effective configuration' \
|
||||
' memory-map generate the selected address-map artifacts' \
|
||||
' check-memory-map validate the canonical address map' \
|
||||
' check-warnings | metrics analyze flow logs and reports' \
|
||||
' check-metrics apply the committed metrics policy' \
|
||||
' sw-format apply clang-format to self-owned embedded C code' \
|
||||
|
||||
+201
-201
@@ -4,6 +4,8 @@
|
||||
#include <stdint.h>
|
||||
#include <stdbool.h>
|
||||
|
||||
#include <retrosoc/generated/memory_map.h>
|
||||
|
||||
#ifdef CORE_PICORV32
|
||||
#define HW_CORE "PicoRV32"
|
||||
#elif CORE_HAZARD3
|
||||
@@ -19,231 +21,229 @@
|
||||
#define PSRAM_SCLK_MAX_FREQ 133 // unit: MHz
|
||||
#define PSRAM_SCLK_FREQ (CPU_FREQ / 2)
|
||||
|
||||
#define SPFS_MEM_START 0x00000000
|
||||
#define SPFS_MEM_OFFST 32 * 1024 * 1024
|
||||
#define NMI_MEM_START 0x10000000
|
||||
#define NMI_MEM_OFFST 256 * 1024 * 1024
|
||||
#define APB_MEM_START 0x20000000
|
||||
#define APB_MEM_OFFST 256 * 1024 * 1024
|
||||
#define SRAM_MEM_START 0x30000000
|
||||
#define SRAM_MEM_OFFST 128 * 1024
|
||||
#define SDRAM_MEM_START 0x38000000
|
||||
#define SDRAM_MEM_OFFST 64 * 1024 * 1024
|
||||
#define PSRAM_MEM_START 0x40000000
|
||||
#define PSRAM_MEM_OFFST 8 * 1024 * 1024 * PSRAM_NUM
|
||||
#define OPIPSRAM_MEM_START 0x48000000
|
||||
#define OPIPSRAM_MEM_OFFST 32 * 1024 * 1024
|
||||
#define XPI_MEM_START 0x50000000
|
||||
#define XPI_MEM_OFFST 256 * 1024 * 1024
|
||||
#define TF_CARD_START (uint32_t)0x60000000
|
||||
#define TF_CARD_OFFST (uint32_t)0x40000000
|
||||
#define SPFS_MEM_START RS_SOC_FLASH_BASE
|
||||
#define SPFS_MEM_OFFST RS_SOC_FLASH_SIZE
|
||||
#define SRAM_MEM_START RS_SOC_SRAM_BASE
|
||||
#define SRAM_MEM_OFFST RS_SOC_SRAM_SIZE
|
||||
#define SDRAM_MEM_START RS_SOC_SDRAM_BASE
|
||||
#define SDRAM_MEM_OFFST RS_SOC_SDRAM_SIZE
|
||||
#define PSRAM_MEM_START RS_SOC_PSRAM_BASE
|
||||
#define PSRAM_MEM_OFFST RS_SOC_PSRAM_SIZE
|
||||
#define XPI_MEM_START RS_SOC_XPI_BASE
|
||||
#define XPI_MEM_OFFST RS_SOC_XPI_SIZE
|
||||
#define TF_CARD_START RS_SOC_SPISD_BASE
|
||||
#define TF_CARD_OFFST RS_SOC_SPISD_SIZE
|
||||
|
||||
#define RS_SOC_REG32(base, offset) (*(volatile uint32_t *)(uintptr_t)((base) + (offset)))
|
||||
|
||||
// gpio
|
||||
#define reg_gpio_oe (*(volatile uint32_t *)0x10000000)
|
||||
#define reg_gpio_cs (*(volatile uint32_t *)0x10000004)
|
||||
#define reg_gpio_pu (*(volatile uint32_t *)0x10000008)
|
||||
#define reg_gpio_pd (*(volatile uint32_t *)0x1000000c)
|
||||
#define reg_gpio_do (*(volatile uint32_t *)0x10000010)
|
||||
#define reg_gpio_di (*(volatile uint32_t *)0x10000014)
|
||||
#define reg_gpio_ien (*(volatile uint32_t *)0x10000018)
|
||||
#define reg_gpio_itype0 (*(volatile uint32_t *)0x1000001c)
|
||||
#define reg_gpio_itype1 (*(volatile uint32_t *)0x10000020)
|
||||
#define reg_gpio_istat (*(volatile uint32_t *)0x10000024)
|
||||
#define reg_gpio_iofcfg (*(volatile uint32_t *)0x10000028)
|
||||
#define reg_gpio_pinmux (*(volatile uint32_t *)0x1000002c)
|
||||
#define reg_gpio_oe RS_SOC_REG32(RS_SOC_NMI_GPIO_BASE, UINT32_C(0x00))
|
||||
#define reg_gpio_cs RS_SOC_REG32(RS_SOC_NMI_GPIO_BASE, UINT32_C(0x04))
|
||||
#define reg_gpio_pu RS_SOC_REG32(RS_SOC_NMI_GPIO_BASE, UINT32_C(0x08))
|
||||
#define reg_gpio_pd RS_SOC_REG32(RS_SOC_NMI_GPIO_BASE, UINT32_C(0x0C))
|
||||
#define reg_gpio_do RS_SOC_REG32(RS_SOC_NMI_GPIO_BASE, UINT32_C(0x10))
|
||||
#define reg_gpio_di RS_SOC_REG32(RS_SOC_NMI_GPIO_BASE, UINT32_C(0x14))
|
||||
#define reg_gpio_ien RS_SOC_REG32(RS_SOC_NMI_GPIO_BASE, UINT32_C(0x18))
|
||||
#define reg_gpio_itype0 RS_SOC_REG32(RS_SOC_NMI_GPIO_BASE, UINT32_C(0x1C))
|
||||
#define reg_gpio_itype1 RS_SOC_REG32(RS_SOC_NMI_GPIO_BASE, UINT32_C(0x20))
|
||||
#define reg_gpio_istat RS_SOC_REG32(RS_SOC_NMI_GPIO_BASE, UINT32_C(0x24))
|
||||
#define reg_gpio_iofcfg RS_SOC_REG32(RS_SOC_NMI_GPIO_BASE, UINT32_C(0x28))
|
||||
#define reg_gpio_pinmux RS_SOC_REG32(RS_SOC_NMI_GPIO_BASE, UINT32_C(0x2C))
|
||||
// uart0
|
||||
#define reg_uart0_clkdiv (*(volatile uint32_t *)0x10001000)
|
||||
#define reg_uart0_data (*(volatile uint32_t *)0x10001004)
|
||||
#define reg_uart0_clkdiv RS_SOC_REG32(RS_SOC_NMI_UART0_BASE, UINT32_C(0x00))
|
||||
#define reg_uart0_data RS_SOC_REG32(RS_SOC_NMI_UART0_BASE, UINT32_C(0x04))
|
||||
// tim0
|
||||
#define reg_tim0_cfg (*(volatile uint32_t *)0x10002000)
|
||||
#define reg_tim0_rld (*(volatile uint32_t *)0x10002004)
|
||||
#define reg_tim0_val (*(volatile uint32_t *)0x10002008)
|
||||
#define reg_tim0_cfg RS_SOC_REG32(RS_SOC_NMI_TIM0_BASE, UINT32_C(0x00))
|
||||
#define reg_tim0_rld RS_SOC_REG32(RS_SOC_NMI_TIM0_BASE, UINT32_C(0x04))
|
||||
#define reg_tim0_val RS_SOC_REG32(RS_SOC_NMI_TIM0_BASE, UINT32_C(0x08))
|
||||
// tim1
|
||||
#define reg_tim1_cfg (*(volatile uint32_t *)0x10003000)
|
||||
#define reg_tim1_rld (*(volatile uint32_t *)0x10003004)
|
||||
#define reg_tim1_val (*(volatile uint32_t *)0x10003008)
|
||||
#define reg_tim1_cfg RS_SOC_REG32(RS_SOC_NMI_TIM1_BASE, UINT32_C(0x00))
|
||||
#define reg_tim1_rld RS_SOC_REG32(RS_SOC_NMI_TIM1_BASE, UINT32_C(0x04))
|
||||
#define reg_tim1_val RS_SOC_REG32(RS_SOC_NMI_TIM1_BASE, UINT32_C(0x08))
|
||||
// psram
|
||||
#define reg_psram_wait (*(volatile uint32_t *)0x10004000)
|
||||
#define reg_psram_chd (*(volatile uint32_t *)0x10004004)
|
||||
#define reg_psram_init (*(volatile uint32_t *)0x10004008)
|
||||
#define reg_psram_wait RS_SOC_REG32(RS_SOC_NMI_PSRAM_BASE, UINT32_C(0x00))
|
||||
#define reg_psram_chd RS_SOC_REG32(RS_SOC_NMI_PSRAM_BASE, UINT32_C(0x04))
|
||||
#define reg_psram_init RS_SOC_REG32(RS_SOC_NMI_PSRAM_BASE, UINT32_C(0x08))
|
||||
// spisd
|
||||
#define reg_spisd_mode (*(volatile uint32_t *)0x10005000)
|
||||
#define reg_spisd_clkdiv (*(volatile uint32_t *)0x10005004)
|
||||
#define reg_spisd_addr (*(volatile uint32_t *)0x10005008)
|
||||
#define reg_spisd_txdata (*(volatile uint32_t *)0x1000500C)
|
||||
#define reg_spisd_rxdata (*(volatile uint32_t *)0x10005010)
|
||||
#define reg_spisd_status (*(volatile uint32_t *)0x10005014)
|
||||
#define reg_spisd_sync (*(volatile uint32_t *)0x10005018)
|
||||
#define reg_spisd_mode RS_SOC_REG32(RS_SOC_NMI_SPISD_BASE, UINT32_C(0x00))
|
||||
#define reg_spisd_clkdiv RS_SOC_REG32(RS_SOC_NMI_SPISD_BASE, UINT32_C(0x04))
|
||||
#define reg_spisd_addr RS_SOC_REG32(RS_SOC_NMI_SPISD_BASE, UINT32_C(0x08))
|
||||
#define reg_spisd_txdata RS_SOC_REG32(RS_SOC_NMI_SPISD_BASE, UINT32_C(0x0C))
|
||||
#define reg_spisd_rxdata RS_SOC_REG32(RS_SOC_NMI_SPISD_BASE, UINT32_C(0x10))
|
||||
#define reg_spisd_status RS_SOC_REG32(RS_SOC_NMI_SPISD_BASE, UINT32_C(0x14))
|
||||
#define reg_spisd_sync RS_SOC_REG32(RS_SOC_NMI_SPISD_BASE, UINT32_C(0x18))
|
||||
// i2c0
|
||||
#define reg_i2c0_clkdiv (*(volatile uint32_t *)0x10006000)
|
||||
#define reg_i2c0_devaddr (*(volatile uint32_t *)0x10006004)
|
||||
#define reg_i2c0_regaddr (*(volatile uint32_t *)0x10006008)
|
||||
#define reg_i2c0_txdata (*(volatile uint32_t *)0x1000600C)
|
||||
#define reg_i2c0_rxdata (*(volatile uint32_t *)0x10006010)
|
||||
#define reg_i2c0_xfer (*(volatile uint32_t *)0x10006014)
|
||||
#define reg_i2c0_cfg (*(volatile uint32_t *)0x10006018)
|
||||
#define reg_i2c0_status (*(volatile uint32_t *)0x1000601C)
|
||||
#define reg_i2c0_clkdiv RS_SOC_REG32(RS_SOC_NMI_I2C0_BASE, UINT32_C(0x00))
|
||||
#define reg_i2c0_devaddr RS_SOC_REG32(RS_SOC_NMI_I2C0_BASE, UINT32_C(0x04))
|
||||
#define reg_i2c0_regaddr RS_SOC_REG32(RS_SOC_NMI_I2C0_BASE, UINT32_C(0x08))
|
||||
#define reg_i2c0_txdata RS_SOC_REG32(RS_SOC_NMI_I2C0_BASE, UINT32_C(0x0C))
|
||||
#define reg_i2c0_rxdata RS_SOC_REG32(RS_SOC_NMI_I2C0_BASE, UINT32_C(0x10))
|
||||
#define reg_i2c0_xfer RS_SOC_REG32(RS_SOC_NMI_I2C0_BASE, UINT32_C(0x14))
|
||||
#define reg_i2c0_cfg RS_SOC_REG32(RS_SOC_NMI_I2C0_BASE, UINT32_C(0x18))
|
||||
#define reg_i2c0_status RS_SOC_REG32(RS_SOC_NMI_I2C0_BASE, UINT32_C(0x1C))
|
||||
// i2s
|
||||
#define reg_i2s_mode (*(volatile uint32_t *)0x10007000)
|
||||
#define reg_i2s_format (*(volatile uint32_t *)0x10007004)
|
||||
#define reg_i2s_upbound (*(volatile uint32_t *)0x10007008)
|
||||
#define reg_i2s_lowbound (*(volatile uint32_t *)0x1000700C)
|
||||
#define reg_i2s_recven (*(volatile uint32_t *)0x10007010)
|
||||
#define reg_i2s_txdata (*(volatile uint32_t *)0x10007014)
|
||||
#define reg_i2s_rxdata (*(volatile uint32_t *)0x10007018)
|
||||
#define reg_i2s_status (*(volatile uint32_t *)0x1000701C)
|
||||
#define reg_i2s_mode RS_SOC_REG32(RS_SOC_NMI_I2S_BASE, UINT32_C(0x00))
|
||||
#define reg_i2s_format RS_SOC_REG32(RS_SOC_NMI_I2S_BASE, UINT32_C(0x04))
|
||||
#define reg_i2s_upbound RS_SOC_REG32(RS_SOC_NMI_I2S_BASE, UINT32_C(0x08))
|
||||
#define reg_i2s_lowbound RS_SOC_REG32(RS_SOC_NMI_I2S_BASE, UINT32_C(0x0C))
|
||||
#define reg_i2s_recven RS_SOC_REG32(RS_SOC_NMI_I2S_BASE, UINT32_C(0x10))
|
||||
#define reg_i2s_txdata RS_SOC_REG32(RS_SOC_NMI_I2S_BASE, UINT32_C(0x14))
|
||||
#define reg_i2s_rxdata RS_SOC_REG32(RS_SOC_NMI_I2S_BASE, UINT32_C(0x18))
|
||||
#define reg_i2s_status RS_SOC_REG32(RS_SOC_NMI_I2S_BASE, UINT32_C(0x1C))
|
||||
// onewire
|
||||
#define reg_onewire_clkdiv (*(volatile uint32_t *)0x10008000)
|
||||
#define reg_onewire_zerocnt (*(volatile uint32_t *)0x10008004)
|
||||
#define reg_onewire_onecnt (*(volatile uint32_t *)0x10008008)
|
||||
#define reg_onewire_rstcnt (*(volatile uint32_t *)0x1000800C)
|
||||
#define reg_onewire_txdata (*(volatile uint32_t *)0x10008010)
|
||||
#define reg_onewire_ctrl (*(volatile uint32_t *)0x10008014)
|
||||
#define reg_onewire_status (*(volatile uint32_t *)0x10008018)
|
||||
#define reg_onewire_clkdiv RS_SOC_REG32(RS_SOC_NMI_ONEWIRE_BASE, UINT32_C(0x00))
|
||||
#define reg_onewire_zerocnt RS_SOC_REG32(RS_SOC_NMI_ONEWIRE_BASE, UINT32_C(0x04))
|
||||
#define reg_onewire_onecnt RS_SOC_REG32(RS_SOC_NMI_ONEWIRE_BASE, UINT32_C(0x08))
|
||||
#define reg_onewire_rstcnt RS_SOC_REG32(RS_SOC_NMI_ONEWIRE_BASE, UINT32_C(0x0C))
|
||||
#define reg_onewire_txdata RS_SOC_REG32(RS_SOC_NMI_ONEWIRE_BASE, UINT32_C(0x10))
|
||||
#define reg_onewire_ctrl RS_SOC_REG32(RS_SOC_NMI_ONEWIRE_BASE, UINT32_C(0x14))
|
||||
#define reg_onewire_status RS_SOC_REG32(RS_SOC_NMI_ONEWIRE_BASE, UINT32_C(0x18))
|
||||
// xpi
|
||||
#define reg_xpi_cfgidx (*(volatile uint32_t *)0x10009000)
|
||||
#define reg_xpi_accmd (*(volatile uint32_t *)0x10009004)
|
||||
#define reg_xpi_mmstad (*(volatile uint32_t *)0x10009008)
|
||||
#define reg_xpi_mmoffst (*(volatile uint32_t *)0x1000900C)
|
||||
#define reg_xpi_mode (*(volatile uint32_t *)0x10009010)
|
||||
#define reg_xpi_nss (*(volatile uint32_t *)0x10009014)
|
||||
#define reg_xpi_clkdiv (*(volatile uint32_t *)0x10009018)
|
||||
#define reg_xpi_rdwr (*(volatile uint32_t *)0x1000901C)
|
||||
#define reg_xpi_revdat (*(volatile uint32_t *)0x10009020)
|
||||
#define reg_xpi_txupb (*(volatile uint32_t *)0x10009024)
|
||||
#define reg_xpi_txlowb (*(volatile uint32_t *)0x10009028)
|
||||
#define reg_xpi_rxupb (*(volatile uint32_t *)0x1000902C)
|
||||
#define reg_xpi_rxlowb (*(volatile uint32_t *)0x10009030)
|
||||
#define reg_xpi_flush (*(volatile uint32_t *)0x10009034)
|
||||
#define reg_xpi_cmdtyp (*(volatile uint32_t *)0x10009038)
|
||||
#define reg_xpi_cmdlen (*(volatile uint32_t *)0x1000903C)
|
||||
#define reg_xpi_cmddat (*(volatile uint32_t *)0x10009040)
|
||||
#define reg_xpi_adrtyp (*(volatile uint32_t *)0x10009044)
|
||||
#define reg_xpi_adrlen (*(volatile uint32_t *)0x10009048)
|
||||
#define reg_xpi_adrdat (*(volatile uint32_t *)0x1000904C)
|
||||
#define reg_xpi_alttyp (*(volatile uint32_t *)0x10009050)
|
||||
#define reg_xpi_altlen (*(volatile uint32_t *)0x10009054)
|
||||
#define reg_xpi_altdat (*(volatile uint32_t *)0x10009058)
|
||||
#define reg_xpi_tdulen (*(volatile uint32_t *)0x1000905C)
|
||||
#define reg_xpi_rdulen (*(volatile uint32_t *)0x10009060)
|
||||
#define reg_xpi_dattyp (*(volatile uint32_t *)0x10009064)
|
||||
#define reg_xpi_datlen (*(volatile uint32_t *)0x10009068)
|
||||
#define reg_xpi_datbit (*(volatile uint32_t *)0x1000906C)
|
||||
#define reg_xpi_hlvlen (*(volatile uint32_t *)0x10009070)
|
||||
#define reg_xpi_txdata (*(volatile uint32_t *)0x10009074)
|
||||
#define reg_xpi_rxdata (*(volatile uint32_t *)0x10009078)
|
||||
#define reg_xpi_start (*(volatile uint32_t *)0x1000907C)
|
||||
#define reg_xpi_status (*(volatile uint32_t *)0x10009080)
|
||||
#define reg_xpi_cfgidx RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x00))
|
||||
#define reg_xpi_accmd RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x04))
|
||||
#define reg_xpi_mmstad RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x08))
|
||||
#define reg_xpi_mmoffst RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x0C))
|
||||
#define reg_xpi_mode RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x10))
|
||||
#define reg_xpi_nss RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x14))
|
||||
#define reg_xpi_clkdiv RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x18))
|
||||
#define reg_xpi_rdwr RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x1C))
|
||||
#define reg_xpi_revdat RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x20))
|
||||
#define reg_xpi_txupb RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x24))
|
||||
#define reg_xpi_txlowb RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x28))
|
||||
#define reg_xpi_rxupb RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x2C))
|
||||
#define reg_xpi_rxlowb RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x30))
|
||||
#define reg_xpi_flush RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x34))
|
||||
#define reg_xpi_cmdtyp RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x38))
|
||||
#define reg_xpi_cmdlen RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x3C))
|
||||
#define reg_xpi_cmddat RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x40))
|
||||
#define reg_xpi_adrtyp RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x44))
|
||||
#define reg_xpi_adrlen RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x48))
|
||||
#define reg_xpi_adrdat RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x4C))
|
||||
#define reg_xpi_alttyp RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x50))
|
||||
#define reg_xpi_altlen RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x54))
|
||||
#define reg_xpi_altdat RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x58))
|
||||
#define reg_xpi_tdulen RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x5C))
|
||||
#define reg_xpi_rdulen RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x60))
|
||||
#define reg_xpi_dattyp RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x64))
|
||||
#define reg_xpi_datlen RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x68))
|
||||
#define reg_xpi_datbit RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x6C))
|
||||
#define reg_xpi_hlvlen RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x70))
|
||||
#define reg_xpi_txdata RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x74))
|
||||
#define reg_xpi_rxdata RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x78))
|
||||
#define reg_xpi_start RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x7C))
|
||||
#define reg_xpi_status RS_SOC_REG32(RS_SOC_NMI_XPI_BASE, UINT32_C(0x80))
|
||||
// dma(32b xfer, hardware trigger by I2S fifo, QSPI fifo)
|
||||
#define reg_dma_mode (*(volatile uint32_t *)0x1000A000)
|
||||
#define reg_dma_srcaddr (*(volatile uint32_t *)0x1000A004)
|
||||
#define reg_dma_srcincr (*(volatile uint32_t *)0x1000A008)
|
||||
#define reg_dma_dstaddr (*(volatile uint32_t *)0x1000A00C)
|
||||
#define reg_dma_dstincr (*(volatile uint32_t *)0x1000A010)
|
||||
#define reg_dma_xferlen (*(volatile uint32_t *)0x1000A014)
|
||||
#define reg_dma_start (*(volatile uint32_t *)0x1000A018)
|
||||
#define reg_dma_stop (*(volatile uint32_t *)0x1000A01C)
|
||||
#define reg_dma_reset (*(volatile uint32_t *)0x1000A020)
|
||||
#define reg_dma_status (*(volatile uint32_t *)0x1000A024)
|
||||
#define reg_dma_fsm (*(volatile uint32_t *)0x1000A028)
|
||||
#define reg_dma_mode RS_SOC_REG32(RS_SOC_NMI_DMA_BASE, UINT32_C(0x00))
|
||||
#define reg_dma_srcaddr RS_SOC_REG32(RS_SOC_NMI_DMA_BASE, UINT32_C(0x04))
|
||||
#define reg_dma_srcincr RS_SOC_REG32(RS_SOC_NMI_DMA_BASE, UINT32_C(0x08))
|
||||
#define reg_dma_dstaddr RS_SOC_REG32(RS_SOC_NMI_DMA_BASE, UINT32_C(0x0C))
|
||||
#define reg_dma_dstincr RS_SOC_REG32(RS_SOC_NMI_DMA_BASE, UINT32_C(0x10))
|
||||
#define reg_dma_xferlen RS_SOC_REG32(RS_SOC_NMI_DMA_BASE, UINT32_C(0x14))
|
||||
#define reg_dma_start RS_SOC_REG32(RS_SOC_NMI_DMA_BASE, UINT32_C(0x18))
|
||||
#define reg_dma_stop RS_SOC_REG32(RS_SOC_NMI_DMA_BASE, UINT32_C(0x1C))
|
||||
#define reg_dma_reset RS_SOC_REG32(RS_SOC_NMI_DMA_BASE, UINT32_C(0x20))
|
||||
#define reg_dma_status RS_SOC_REG32(RS_SOC_NMI_DMA_BASE, UINT32_C(0x24))
|
||||
#define reg_dma_fsm RS_SOC_REG32(RS_SOC_NMI_DMA_BASE, UINT32_C(0x28))
|
||||
// sys ctrl
|
||||
#define reg_sysctrl_coresel (*(volatile uint32_t *)0x1000B000)
|
||||
#define reg_sysctrl_ipsel (*(volatile uint32_t *)0x1000B004)
|
||||
#define reg_sysctrl_i2csel (*(volatile uint32_t *)0x1000B008)
|
||||
#define reg_sysctrl_qspicsel (*(volatile uint32_t *)0x1000B00C)
|
||||
#define RS_SOC_SYSCTRL_REG32(offset) RS_SOC_REG32(RS_SOC_NMI_SYSCTRL_BASE, (offset))
|
||||
#define reg_sysctrl_coresel RS_SOC_REG32(RS_SOC_NMI_SYSCTRL_BASE, UINT32_C(0x00))
|
||||
#define reg_sysctrl_ipsel RS_SOC_REG32(RS_SOC_NMI_SYSCTRL_BASE, UINT32_C(0x04))
|
||||
#define reg_sysctrl_i2csel RS_SOC_REG32(RS_SOC_NMI_SYSCTRL_BASE, UINT32_C(0x08))
|
||||
#define reg_sysctrl_qspicsel RS_SOC_REG32(RS_SOC_NMI_SYSCTRL_BASE, UINT32_C(0x0C))
|
||||
/* Status: bit 0 pending (W1C), bit 1 write, bits 3:2 reason (1 unmapped, 2 reserved). */
|
||||
#define reg_sysctrl_bus_fault_status RS_SOC_SYSCTRL_REG32(RS_SOC_SYSCTRL_FAULT_STATUS_OFFSET)
|
||||
#define reg_sysctrl_bus_fault_addr RS_SOC_SYSCTRL_REG32(RS_SOC_SYSCTRL_FAULT_ADDR_OFFSET)
|
||||
#define reg_sysctrl_bus_fault_count RS_SOC_SYSCTRL_REG32(RS_SOC_SYSCTRL_FAULT_COUNT_OFFSET)
|
||||
#define RS_SOC_BUS_FAULT_PENDING UINT32_C(0x00000001)
|
||||
#define RS_SOC_BUS_FAULT_WRITE UINT32_C(0x00000002)
|
||||
#define RS_SOC_BUS_FAULT_REASON_MASK UINT32_C(0x0000000C)
|
||||
#define RS_SOC_BUS_FAULT_REASON_UNMAPPED UINT32_C(0x00000004)
|
||||
#define RS_SOC_BUS_FAULT_REASON_RESERVED UINT32_C(0x00000008)
|
||||
// clint
|
||||
#define reg_clint_mtimel (*(volatile uint32_t *)0x1000C000)
|
||||
#define reg_clint_mtimeh (*(volatile uint32_t *)0x1000C004)
|
||||
#define reg_clint_mtimecmpl (*(volatile uint32_t *)0x1000C008)
|
||||
#define reg_clint_mtimecmph (*(volatile uint32_t *)0x1000C00C)
|
||||
#define reg_clint_msip (*(volatile uint32_t *)0x1000C010)
|
||||
#define reg_clint_clkdiv (*(volatile uint32_t *)0x1000C014)
|
||||
#define reg_clint_mtimel RS_SOC_REG32(RS_SOC_NMI_CLINT_BASE, UINT32_C(0x00))
|
||||
#define reg_clint_mtimeh RS_SOC_REG32(RS_SOC_NMI_CLINT_BASE, UINT32_C(0x04))
|
||||
#define reg_clint_mtimecmpl RS_SOC_REG32(RS_SOC_NMI_CLINT_BASE, UINT32_C(0x08))
|
||||
#define reg_clint_mtimecmph RS_SOC_REG32(RS_SOC_NMI_CLINT_BASE, UINT32_C(0x0C))
|
||||
#define reg_clint_msip RS_SOC_REG32(RS_SOC_NMI_CLINT_BASE, UINT32_C(0x10))
|
||||
#define reg_clint_clkdiv RS_SOC_REG32(RS_SOC_NMI_CLINT_BASE, UINT32_C(0x14))
|
||||
// sdram
|
||||
#define reg_sdram_clkdiv (*(volatile uint32_t *)0x1000D000)
|
||||
#define reg_sdram_cfg (*(volatile uint32_t *)0x1000D004)
|
||||
#define reg_sdram_clkdiv RS_SOC_REG32(RS_SOC_NMI_SDRAM_BASE, UINT32_C(0x00))
|
||||
#define reg_sdram_cfg RS_SOC_REG32(RS_SOC_NMI_SDRAM_BASE, UINT32_C(0x04))
|
||||
// dvp
|
||||
#define reg_dvp_recven (*(volatile uint32_t *)0x1000E000)
|
||||
#define reg_dvp_rxdata (*(volatile uint32_t *)0x1000E004)
|
||||
#define reg_dvp_status (*(volatile uint32_t *)0x1000E008)
|
||||
// sdio
|
||||
#define reg_sdio_cfg (*(volatile uint32_t *)0x1000F000)
|
||||
// opipsram
|
||||
#define reg_opipsram_cfg (*(volatile uint32_t *)0x10010000)
|
||||
#define reg_dvp_recven RS_SOC_REG32(RS_SOC_NMI_DVP_BASE, UINT32_C(0x00))
|
||||
#define reg_dvp_rxdata RS_SOC_REG32(RS_SOC_NMI_DVP_BASE, UINT32_C(0x04))
|
||||
#define reg_dvp_status RS_SOC_REG32(RS_SOC_NMI_DVP_BASE, UINT32_C(0x08))
|
||||
// i2c1
|
||||
#define reg_i2c1_clkdiv (*(volatile uint32_t *)0x10011000)
|
||||
#define reg_i2c1_devaddr (*(volatile uint32_t *)0x10011004)
|
||||
#define reg_i2c1_regaddr (*(volatile uint32_t *)0x10011008)
|
||||
#define reg_i2c1_txdata (*(volatile uint32_t *)0x1001100C)
|
||||
#define reg_i2c1_rxdata (*(volatile uint32_t *)0x10011010)
|
||||
#define reg_i2c1_xfer (*(volatile uint32_t *)0x10011014)
|
||||
#define reg_i2c1_cfg (*(volatile uint32_t *)0x10011018)
|
||||
#define reg_i2c1_status (*(volatile uint32_t *)0x1001101C)
|
||||
// ga
|
||||
#define reg_ga_cfg (*(volatile uint32_t *)0x10012000)
|
||||
// apu
|
||||
#define reg_apu_cfg (*(volatile uint32_t *)0x10013000)
|
||||
#define reg_i2c1_clkdiv RS_SOC_REG32(RS_SOC_NMI_I2C1_BASE, UINT32_C(0x00))
|
||||
#define reg_i2c1_devaddr RS_SOC_REG32(RS_SOC_NMI_I2C1_BASE, UINT32_C(0x04))
|
||||
#define reg_i2c1_regaddr RS_SOC_REG32(RS_SOC_NMI_I2C1_BASE, UINT32_C(0x08))
|
||||
#define reg_i2c1_txdata RS_SOC_REG32(RS_SOC_NMI_I2C1_BASE, UINT32_C(0x0C))
|
||||
#define reg_i2c1_rxdata RS_SOC_REG32(RS_SOC_NMI_I2C1_BASE, UINT32_C(0x10))
|
||||
#define reg_i2c1_xfer RS_SOC_REG32(RS_SOC_NMI_I2C1_BASE, UINT32_C(0x14))
|
||||
#define reg_i2c1_cfg RS_SOC_REG32(RS_SOC_NMI_I2C1_BASE, UINT32_C(0x18))
|
||||
#define reg_i2c1_status RS_SOC_REG32(RS_SOC_NMI_I2C1_BASE, UINT32_C(0x1C))
|
||||
// archinfo
|
||||
#define reg_archinfo_sys (*(volatile uint32_t *)0x20000000)
|
||||
#define reg_archinfo_idl (*(volatile uint32_t *)0x20000004)
|
||||
#define reg_archinfo_idh (*(volatile uint32_t *)0x20000008)
|
||||
#define reg_archinfo_sys RS_SOC_REG32(RS_SOC_APB_ARCHINFO_BASE, UINT32_C(0x00))
|
||||
#define reg_archinfo_idl RS_SOC_REG32(RS_SOC_APB_ARCHINFO_BASE, UINT32_C(0x04))
|
||||
#define reg_archinfo_idh RS_SOC_REG32(RS_SOC_APB_ARCHINFO_BASE, UINT32_C(0x08))
|
||||
// rng
|
||||
#define reg_rng_ctrl (*(volatile uint32_t *)0x20001000)
|
||||
#define reg_rng_seed (*(volatile uint32_t *)0x20001004)
|
||||
#define reg_rng_val (*(volatile uint32_t *)0x20001008)
|
||||
#define reg_rng_ctrl RS_SOC_REG32(RS_SOC_APB_RNG_BASE, UINT32_C(0x00))
|
||||
#define reg_rng_seed RS_SOC_REG32(RS_SOC_APB_RNG_BASE, UINT32_C(0x04))
|
||||
#define reg_rng_val RS_SOC_REG32(RS_SOC_APB_RNG_BASE, UINT32_C(0x08))
|
||||
// uart
|
||||
#define reg_uart1_lcr (*(volatile uint32_t *)0x20002000)
|
||||
#define reg_uart1_div (*(volatile uint32_t *)0x20002004)
|
||||
#define reg_uart1_trx (*(volatile uint32_t *)0x20002008)
|
||||
#define reg_uart1_fcr (*(volatile uint32_t *)0x2000200c)
|
||||
#define reg_uart1_lsr (*(volatile uint32_t *)0x20002010)
|
||||
#define reg_uart1_lcr RS_SOC_REG32(RS_SOC_APB_UART1_BASE, UINT32_C(0x00))
|
||||
#define reg_uart1_div RS_SOC_REG32(RS_SOC_APB_UART1_BASE, UINT32_C(0x04))
|
||||
#define reg_uart1_trx RS_SOC_REG32(RS_SOC_APB_UART1_BASE, UINT32_C(0x08))
|
||||
#define reg_uart1_fcr RS_SOC_REG32(RS_SOC_APB_UART1_BASE, UINT32_C(0x0C))
|
||||
#define reg_uart1_lsr RS_SOC_REG32(RS_SOC_APB_UART1_BASE, UINT32_C(0x10))
|
||||
// pwm
|
||||
#define reg_pwm_ctrl (*(volatile uint32_t *)0x20003000)
|
||||
#define reg_pwm_pscr (*(volatile uint32_t *)0x20003004)
|
||||
#define reg_pwm_cnt (*(volatile uint32_t *)0x20003008)
|
||||
#define reg_pwm_cmp (*(volatile uint32_t *)0x2000300c)
|
||||
#define reg_pwm_cr0 (*(volatile uint32_t *)0x20003010)
|
||||
#define reg_pwm_cr1 (*(volatile uint32_t *)0x20003014)
|
||||
#define reg_pwm_cr2 (*(volatile uint32_t *)0x20003018)
|
||||
#define reg_pwm_cr3 (*(volatile uint32_t *)0x2000301c)
|
||||
#define reg_pwm_stat (*(volatile uint32_t *)0x20003020)
|
||||
#define reg_pwm_ctrl RS_SOC_REG32(RS_SOC_APB_PWM_BASE, UINT32_C(0x00))
|
||||
#define reg_pwm_pscr RS_SOC_REG32(RS_SOC_APB_PWM_BASE, UINT32_C(0x04))
|
||||
#define reg_pwm_cnt RS_SOC_REG32(RS_SOC_APB_PWM_BASE, UINT32_C(0x08))
|
||||
#define reg_pwm_cmp RS_SOC_REG32(RS_SOC_APB_PWM_BASE, UINT32_C(0x0C))
|
||||
#define reg_pwm_cr0 RS_SOC_REG32(RS_SOC_APB_PWM_BASE, UINT32_C(0x10))
|
||||
#define reg_pwm_cr1 RS_SOC_REG32(RS_SOC_APB_PWM_BASE, UINT32_C(0x14))
|
||||
#define reg_pwm_cr2 RS_SOC_REG32(RS_SOC_APB_PWM_BASE, UINT32_C(0x18))
|
||||
#define reg_pwm_cr3 RS_SOC_REG32(RS_SOC_APB_PWM_BASE, UINT32_C(0x1C))
|
||||
#define reg_pwm_stat RS_SOC_REG32(RS_SOC_APB_PWM_BASE, UINT32_C(0x20))
|
||||
// ps2
|
||||
#define reg_ps2_ctrl (*(volatile uint32_t *)0x20004000)
|
||||
#define reg_ps2_data (*(volatile uint32_t *)0x20004004)
|
||||
#define reg_ps2_stat (*(volatile uint32_t *)0x20004008)
|
||||
#define reg_ps2_ctrl RS_SOC_REG32(RS_SOC_APB_PS2_BASE, UINT32_C(0x00))
|
||||
#define reg_ps2_data RS_SOC_REG32(RS_SOC_APB_PS2_BASE, UINT32_C(0x04))
|
||||
#define reg_ps2_stat RS_SOC_REG32(RS_SOC_APB_PS2_BASE, UINT32_C(0x08))
|
||||
// rtc
|
||||
#define reg_rtc_ctrl (*(volatile uint32_t *)0x20005000)
|
||||
#define reg_rtc_pscr (*(volatile uint32_t *)0x20005004)
|
||||
#define reg_rtc_cnt (*(volatile uint32_t *)0x20005008)
|
||||
#define reg_rtc_alrm (*(volatile uint32_t *)0x2000500C)
|
||||
#define reg_rtc_ista (*(volatile uint32_t *)0x20005010)
|
||||
#define reg_rtc_ssta (*(volatile uint32_t *)0x20005014)
|
||||
#define reg_rtc_ctrl RS_SOC_REG32(RS_SOC_APB_RTC_BASE, UINT32_C(0x00))
|
||||
#define reg_rtc_pscr RS_SOC_REG32(RS_SOC_APB_RTC_BASE, UINT32_C(0x04))
|
||||
#define reg_rtc_cnt RS_SOC_REG32(RS_SOC_APB_RTC_BASE, UINT32_C(0x08))
|
||||
#define reg_rtc_alrm RS_SOC_REG32(RS_SOC_APB_RTC_BASE, UINT32_C(0x0C))
|
||||
#define reg_rtc_ista RS_SOC_REG32(RS_SOC_APB_RTC_BASE, UINT32_C(0x10))
|
||||
#define reg_rtc_ssta RS_SOC_REG32(RS_SOC_APB_RTC_BASE, UINT32_C(0x14))
|
||||
// wdg
|
||||
#define reg_wdg_ctrl (*(volatile uint32_t *)0x20006000)
|
||||
#define reg_wdg_pscr (*(volatile uint32_t *)0x20006004)
|
||||
#define reg_wdg_cnt (*(volatile uint32_t *)0x20006008)
|
||||
#define reg_wdg_cmp (*(volatile uint32_t *)0x2000600C)
|
||||
#define reg_wdg_stat (*(volatile uint32_t *)0x20006010)
|
||||
#define reg_wdg_key (*(volatile uint32_t *)0x20006014)
|
||||
#define reg_wdg_feed (*(volatile uint32_t *)0x20006018)
|
||||
#define reg_wdg_ctrl RS_SOC_REG32(RS_SOC_APB_WDG_BASE, UINT32_C(0x00))
|
||||
#define reg_wdg_pscr RS_SOC_REG32(RS_SOC_APB_WDG_BASE, UINT32_C(0x04))
|
||||
#define reg_wdg_cnt RS_SOC_REG32(RS_SOC_APB_WDG_BASE, UINT32_C(0x08))
|
||||
#define reg_wdg_cmp RS_SOC_REG32(RS_SOC_APB_WDG_BASE, UINT32_C(0x0C))
|
||||
#define reg_wdg_stat RS_SOC_REG32(RS_SOC_APB_WDG_BASE, UINT32_C(0x10))
|
||||
#define reg_wdg_key RS_SOC_REG32(RS_SOC_APB_WDG_BASE, UINT32_C(0x14))
|
||||
#define reg_wdg_feed RS_SOC_REG32(RS_SOC_APB_WDG_BASE, UINT32_C(0x18))
|
||||
// crc
|
||||
#define reg_crc_ctrl (*(volatile uint32_t *)0x20007000)
|
||||
#define reg_crc_init (*(volatile uint32_t *)0x20007004)
|
||||
#define reg_crc_xorv (*(volatile uint32_t *)0x20007008)
|
||||
#define reg_crc_data (*(volatile uint32_t *)0x2000700C)
|
||||
#define reg_crc_stat (*(volatile uint32_t *)0x20007010)
|
||||
#define reg_crc_ctrl RS_SOC_REG32(RS_SOC_APB_CRC_BASE, UINT32_C(0x00))
|
||||
#define reg_crc_init RS_SOC_REG32(RS_SOC_APB_CRC_BASE, UINT32_C(0x04))
|
||||
#define reg_crc_xorv RS_SOC_REG32(RS_SOC_APB_CRC_BASE, UINT32_C(0x08))
|
||||
#define reg_crc_data RS_SOC_REG32(RS_SOC_APB_CRC_BASE, UINT32_C(0x0C))
|
||||
#define reg_crc_stat RS_SOC_REG32(RS_SOC_APB_CRC_BASE, UINT32_C(0x10))
|
||||
// tim3
|
||||
#define reg_tim3_ctrl (*(volatile uint32_t *)0x20008000)
|
||||
#define reg_tim3_pscr (*(volatile uint32_t *)0x20008004)
|
||||
#define reg_tim3_cnt (*(volatile uint32_t *)0x20008008)
|
||||
#define reg_tim3_cmp (*(volatile uint32_t *)0x2000800C)
|
||||
#define reg_tim3_stat (*(volatile uint32_t *)0x20008010)
|
||||
// user ip design(example)
|
||||
#define reg_user_ip_reg0 (*(volatile uint32_t *)0x2000F000)
|
||||
#define reg_user_ip_reg1 (*(volatile uint32_t *)0x2000F004)
|
||||
#define reg_user_ip_reg2 (*(volatile uint32_t *)0x2000F008)
|
||||
#define reg_user_ip_reg3 (*(volatile uint32_t *)0x2000F00C)
|
||||
#define reg_user_ip_reg4 (*(volatile uint32_t *)0x2000F010)
|
||||
#define reg_user_ip_reg5 (*(volatile uint32_t *)0x2000F014)
|
||||
#define reg_user_ip_reg6 (*(volatile uint32_t *)0x2000F018)
|
||||
// ... user custom area ...
|
||||
#define reg_tim3_ctrl RS_SOC_REG32(RS_SOC_APB_TMR_BASE, UINT32_C(0x00))
|
||||
#define reg_tim3_pscr RS_SOC_REG32(RS_SOC_APB_TMR_BASE, UINT32_C(0x04))
|
||||
#define reg_tim3_cnt RS_SOC_REG32(RS_SOC_APB_TMR_BASE, UINT32_C(0x08))
|
||||
#define reg_tim3_cmp RS_SOC_REG32(RS_SOC_APB_TMR_BASE, UINT32_C(0x0C))
|
||||
#define reg_tim3_stat RS_SOC_REG32(RS_SOC_APB_TMR_BASE, UINT32_C(0x10))
|
||||
#ifdef IP_MDD
|
||||
#define reg_user_ip_reg0 RS_SOC_REG32(RS_SOC_APB_USER_IP_BASE, UINT32_C(0x00))
|
||||
#define reg_user_ip_reg1 RS_SOC_REG32(RS_SOC_APB_USER_IP_BASE, UINT32_C(0x04))
|
||||
#define reg_user_ip_reg2 RS_SOC_REG32(RS_SOC_APB_USER_IP_BASE, UINT32_C(0x08))
|
||||
#define reg_user_ip_reg3 RS_SOC_REG32(RS_SOC_APB_USER_IP_BASE, UINT32_C(0x0C))
|
||||
#define reg_user_ip_reg4 RS_SOC_REG32(RS_SOC_APB_USER_IP_BASE, UINT32_C(0x10))
|
||||
#define reg_user_ip_reg5 RS_SOC_REG32(RS_SOC_APB_USER_IP_BASE, UINT32_C(0x14))
|
||||
#define reg_user_ip_reg6 RS_SOC_REG32(RS_SOC_APB_USER_IP_BASE, UINT32_C(0x18))
|
||||
#endif
|
||||
#endif
|
||||
@@ -1,12 +1,6 @@
|
||||
ENTRY( _start )
|
||||
|
||||
MEMORY
|
||||
{
|
||||
FLASH (rxai!w) : ORIGIN = 0x00000000, LENGTH = 16M
|
||||
SRAM (wxa!ri) : ORIGIN = 0x30000000, LENGTH = 128K
|
||||
PSRAM (wxa!ri) : ORIGIN = 0x40000000, LENGTH = 8M
|
||||
/* PSRAM (wxa!ri) : ORIGIN = 0x40000000, LENGTH = 64K */ /* for debug */
|
||||
}
|
||||
INCLUDE memory_regions.ld
|
||||
|
||||
SECTIONS {
|
||||
.init :
|
||||
|
||||
@@ -1,12 +1,6 @@
|
||||
ENTRY( _start )
|
||||
|
||||
MEMORY
|
||||
{
|
||||
FLASH (rxai!w) : ORIGIN = 0x00000000, LENGTH = 16M
|
||||
SRAM (wxa!ri) : ORIGIN = 0x30000000, LENGTH = 128K
|
||||
SDRAM (wxa!ri) : ORIGIN = 0x38000000, LENGTH = 32M
|
||||
PSRAM (wxa!ri) : ORIGIN = 0x40000000, LENGTH = 8M
|
||||
}
|
||||
INCLUDE memory_regions.ld
|
||||
|
||||
SECTIONS {
|
||||
.init :
|
||||
|
||||
@@ -1,11 +1,6 @@
|
||||
ENTRY( _start )
|
||||
|
||||
MEMORY
|
||||
{
|
||||
FLASH (rxai!w) : ORIGIN = 0x00000000, LENGTH = 16M
|
||||
SRAM (wxa!ri) : ORIGIN = 0x30000000, LENGTH = 128K
|
||||
PSRAM (wxa!ri) : ORIGIN = 0x40000000, LENGTH = 8M
|
||||
}
|
||||
INCLUDE memory_regions.ld
|
||||
|
||||
SECTIONS {
|
||||
.init :
|
||||
|
||||
+1
-6
@@ -1,11 +1,6 @@
|
||||
ENTRY( _start )
|
||||
|
||||
MEMORY
|
||||
{
|
||||
FLASH (rxai!w) : ORIGIN = 0x00000000, LENGTH = 16M
|
||||
SRAM (wxa!ri) : ORIGIN = 0x30000000, LENGTH = 128K
|
||||
PSRAM (wxa!ri) : ORIGIN = 0x40000000, LENGTH = 8M
|
||||
}
|
||||
INCLUDE memory_regions.ld
|
||||
|
||||
SECTIONS {
|
||||
.init :
|
||||
|
||||
@@ -9,9 +9,8 @@
|
||||
#include <retrosoc/lib/string.h>
|
||||
#include <retrosoc/service/shell.h>
|
||||
#include <retrosoc/service/booter.h>
|
||||
// HACK:
|
||||
#if defined(CORE_MDD) || defined(IP_MDD)
|
||||
#include <../../rtl/mini/mpw/.build/user_design_info.h>
|
||||
#include <user_design_info.h>
|
||||
#endif
|
||||
|
||||
void rs_app_info(void) {
|
||||
@@ -90,18 +89,14 @@ void rs_app_info(void) {
|
||||
printf("Inst/Memory Address Range:\n");
|
||||
printf(" QSPI Flash: @[0x%08x-0x%08x] %3d MiB\n", SPFS_MEM_START,
|
||||
SPFS_MEM_START + SPFS_MEM_OFFST - 1, SPFS_MEM_OFFST / 1024 / 1024);
|
||||
printf(" NMI IP MMIO: @[0x%08x-0x%08x] %3d MiB\n", NMI_MEM_START,
|
||||
NMI_MEM_START + NMI_MEM_OFFST - 1, NMI_MEM_OFFST / 1024 / 1024);
|
||||
printf(" APB IP MMIO: @[0x%08x-0x%08x] %3d MiB\n", APB_MEM_START,
|
||||
APB_MEM_START + APB_MEM_OFFST - 1, APB_MEM_OFFST / 1024 / 1024);
|
||||
#if RS_SOC_HAS_SRAM
|
||||
printf(" On-chip RAM: @[0x%08x-0x%08x] %3d KiB\n", SRAM_MEM_START,
|
||||
SRAM_MEM_START + SRAM_MEM_OFFST - 1, SRAM_MEM_OFFST / 1024);
|
||||
#endif
|
||||
printf(" Off-chip SDRAM: @[0x%08x-0x%08x] %3d MiB\n", SDRAM_MEM_START,
|
||||
SDRAM_MEM_START + SDRAM_MEM_OFFST - 1, SDRAM_MEM_OFFST / 1024 / 1024);
|
||||
printf(" Off-chip PSRAM: @[0x%08x-0x%08x] %3d MiB(%dx8MiB)\n", PSRAM_MEM_START,
|
||||
PSRAM_MEM_START + PSRAM_MEM_OFFST - 1, 8 * PSRAM_NUM, PSRAM_NUM);
|
||||
printf(" Off-chip OPIPSRAM: @[0x%08x-0x%08x] %3d MiB\n", OPIPSRAM_MEM_START,
|
||||
OPIPSRAM_MEM_START + OPIPSRAM_MEM_OFFST - 1, OPIPSRAM_MEM_OFFST / 1024 / 1024);
|
||||
printf(" Off-chip PSRAM: @[0x%08x-0x%08x] %3d MiB\n", PSRAM_MEM_START,
|
||||
PSRAM_MEM_START + PSRAM_MEM_OFFST - 1, PSRAM_MEM_OFFST / 1024 / 1024);
|
||||
printf(" XPI MMIO: @[0x%08x-0x%08x] %3d MiB\n", XPI_MEM_START,
|
||||
XPI_MEM_START + XPI_MEM_OFFST - 1, XPI_MEM_OFFST / 1024 / 1024);
|
||||
printf(" SPISD MMIO: @[0x%08x-0x%08x] %3d GiB\n\n", TF_CARD_START,
|
||||
@@ -123,11 +118,7 @@ void rs_app_info(void) {
|
||||
printf(" 1 x CLINT @%p\n", (void *)®_clint_mtimel);
|
||||
printf(" 1 x SDRAM @%p\n", (void *)®_sdram_clkdiv);
|
||||
printf(" 1 x DVP @%p\n", (void *)®_dvp_recven);
|
||||
printf(" 1 x SDIO @%p\n", (void *)®_sdio_cfg);
|
||||
printf(" 1 x OPIPSRAM @%p\n", (void *)®_opipsram_cfg);
|
||||
printf(" 1 x I2C1 @%p\n", (void *)®_i2c1_clkdiv);
|
||||
printf(" 1 x GA* @%p\n", (void *)®_ga_cfg);
|
||||
printf(" 1 x APU* @%p\n", (void *)®_apu_cfg);
|
||||
printf(" 1 x ARCHINFO @%p\n", (void *)®_archinfo_sys);
|
||||
printf(" 1 x RNG @%p\n", (void *)®_rng_ctrl);
|
||||
printf(" 1 x UART1(ADV) @%p\n", (void *)®_uart1_lcr);
|
||||
@@ -137,7 +128,10 @@ void rs_app_info(void) {
|
||||
printf(" 1 x WDG @%p\n", (void *)®_wdg_ctrl);
|
||||
printf(" 1 x CRC @%p\n", (void *)®_crc_ctrl);
|
||||
printf(" 1 x TIMER3(ADV) @%p\n", (void *)®_tim3_ctrl);
|
||||
printf(" 1 x USER_IP(4KiB) @%p\n\n", (void *)®_user_ip_reg0);
|
||||
#ifdef IP_MDD
|
||||
printf(" 1 x USER_IP(4KiB) @%p\n", (void *)®_user_ip_reg0);
|
||||
#endif
|
||||
printf("\n");
|
||||
printf("#############################################################\n");
|
||||
printf("#############################################################\n");
|
||||
}
|
||||
|
||||
+20
-20
@@ -69,15 +69,15 @@ module nmi2apb (
|
||||
assign crc.pprot = '0;
|
||||
assign tmr.pprot = '0;
|
||||
|
||||
assign archinfo.psel = s_xfer_valid && (nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_ARCHINFO_START);
|
||||
assign rng.psel = s_xfer_valid && (nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_RNG_START);
|
||||
assign uart.psel = s_xfer_valid && (nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_UART_START);
|
||||
assign pwm.psel = s_xfer_valid && (nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_PWM_START);
|
||||
assign ps2.psel = s_xfer_valid && (nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_PS2_START);
|
||||
assign rtc.psel = s_xfer_valid && (nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_RTC_START);
|
||||
assign wdg.psel = s_xfer_valid && (nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_WDG_START);
|
||||
assign crc.psel = s_xfer_valid && (nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_CRC_START);
|
||||
assign tmr.psel = s_xfer_valid && (nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_TMR_START);
|
||||
assign archinfo.psel = s_xfer_valid && `SOC_ADDR_IS_APB_ARCHINFO(nmi.addr);
|
||||
assign rng.psel = s_xfer_valid && `SOC_ADDR_IS_APB_RNG(nmi.addr);
|
||||
assign uart.psel = s_xfer_valid && `SOC_ADDR_IS_APB_UART1(nmi.addr);
|
||||
assign pwm.psel = s_xfer_valid && `SOC_ADDR_IS_APB_PWM(nmi.addr);
|
||||
assign ps2.psel = s_xfer_valid && `SOC_ADDR_IS_APB_PS2(nmi.addr);
|
||||
assign rtc.psel = s_xfer_valid && `SOC_ADDR_IS_APB_RTC(nmi.addr);
|
||||
assign wdg.psel = s_xfer_valid && `SOC_ADDR_IS_APB_WDG(nmi.addr);
|
||||
assign crc.psel = s_xfer_valid && `SOC_ADDR_IS_APB_CRC(nmi.addr);
|
||||
assign tmr.psel = s_xfer_valid && `SOC_ADDR_IS_APB_TMR(nmi.addr);
|
||||
|
||||
assign archinfo.penable = s_fsm_q == FSM_ENAB;
|
||||
assign rng.penable = s_fsm_q == FSM_ENAB;
|
||||
@@ -122,7 +122,7 @@ module nmi2apb (
|
||||
`ifdef IP_MDD
|
||||
assign user_ip.paddr = nmi.addr;
|
||||
assign user_ip.pprot = '0;
|
||||
assign user_ip.psel = s_xfer_valid && (nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_USR_START);
|
||||
assign user_ip.psel = s_xfer_valid && `SOC_ADDR_IS_APB_USER_IP(nmi.addr);
|
||||
assign user_ip.penable = s_fsm_q == FSM_ENAB;
|
||||
assign user_ip.pwrite = |nmi.wstrb;
|
||||
assign user_ip.pwdata = nmi.wdata;
|
||||
@@ -161,17 +161,17 @@ module nmi2apb (
|
||||
|
||||
// Capture slave-select one-hot at FSM_SETP for cleaner response mux
|
||||
// verilog_format: off
|
||||
assign s_psel_comb[0] = nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_ARCHINFO_START;
|
||||
assign s_psel_comb[1] = nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_RNG_START;
|
||||
assign s_psel_comb[2] = nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_UART_START;
|
||||
assign s_psel_comb[3] = nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_PWM_START;
|
||||
assign s_psel_comb[4] = nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_PS2_START;
|
||||
assign s_psel_comb[5] = nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_RTC_START;
|
||||
assign s_psel_comb[6] = nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_WDG_START;
|
||||
assign s_psel_comb[7] = nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_CRC_START;
|
||||
assign s_psel_comb[8] = nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_TMR_START;
|
||||
assign s_psel_comb[0] = `SOC_ADDR_IS_APB_ARCHINFO(nmi.addr);
|
||||
assign s_psel_comb[1] = `SOC_ADDR_IS_APB_RNG(nmi.addr);
|
||||
assign s_psel_comb[2] = `SOC_ADDR_IS_APB_UART1(nmi.addr);
|
||||
assign s_psel_comb[3] = `SOC_ADDR_IS_APB_PWM(nmi.addr);
|
||||
assign s_psel_comb[4] = `SOC_ADDR_IS_APB_PS2(nmi.addr);
|
||||
assign s_psel_comb[5] = `SOC_ADDR_IS_APB_RTC(nmi.addr);
|
||||
assign s_psel_comb[6] = `SOC_ADDR_IS_APB_WDG(nmi.addr);
|
||||
assign s_psel_comb[7] = `SOC_ADDR_IS_APB_CRC(nmi.addr);
|
||||
assign s_psel_comb[8] = `SOC_ADDR_IS_APB_TMR(nmi.addr);
|
||||
`ifdef IP_MDD
|
||||
assign s_psel_comb[9] = nmi.addr[31:28] == `APB_IP_START && nmi.addr[15:8] == `APB_USR_START;
|
||||
assign s_psel_comb[9] = `SOC_ADDR_IS_APB_USER_IP(nmi.addr);
|
||||
`endif
|
||||
|
||||
assign s_psel_d = (s_fsm_q == FSM_IDLE && s_mem_valid_re) ? s_psel_comb : s_psel_q;
|
||||
|
||||
@@ -125,8 +125,8 @@ module nmi_psram (
|
||||
// verilog_format: on
|
||||
|
||||
|
||||
assign s_mem_sel = nmi.addr[31:24] == `PSRAM_START;
|
||||
assign s_cfg_reg_sel = nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_PSRAM_START;
|
||||
assign s_mem_sel = `SOC_ADDR_IS_PSRAM(nmi.addr);
|
||||
assign s_cfg_reg_sel = `SOC_ADDR_IS_NMI_PSRAM(nmi.addr);
|
||||
assign nmi.ready = s_mem_sel ? s_mem_ready : 1'b1;
|
||||
always_comb begin
|
||||
nmi.rdata = '0;
|
||||
|
||||
@@ -62,7 +62,7 @@ module nmi_sdram (
|
||||
nmi_if u_mem_nmi_if ();
|
||||
|
||||
// nmi mux
|
||||
assign s_sdram_reg_sel = nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_SDRAM_START;
|
||||
assign s_sdram_reg_sel = `SOC_ADDR_IS_NMI_SDRAM(nmi.addr);
|
||||
assign u_reg_nmi_if.valid = nmi.valid && s_sdram_reg_sel;
|
||||
assign u_reg_nmi_if.addr = nmi.addr;
|
||||
assign u_reg_nmi_if.wdata = nmi.wdata;
|
||||
|
||||
@@ -46,7 +46,7 @@ module nmi_spisd (
|
||||
nmi_if u_cache_byp_nmi_if ();
|
||||
|
||||
// verilog_format: off
|
||||
assign s_cfg_reg_sel = nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_SPISD_START;
|
||||
assign s_cfg_reg_sel = `SOC_ADDR_IS_NMI_SPISD(nmi.addr);
|
||||
assign u_cfg_nmi_if.valid = nmi.valid && s_cfg_reg_sel;
|
||||
assign u_cfg_nmi_if.addr = nmi.addr;
|
||||
assign u_cfg_nmi_if.wdata = nmi.wdata;
|
||||
|
||||
@@ -16,11 +16,15 @@
|
||||
`define NATV_SYSCTRL_IPSEL 8'h04 // WR/RD
|
||||
`define NATV_SYSCTRL_I2CSEL 8'h08 // WR/RD
|
||||
`define NATV_SYSCTRL_QSPISEL 8'h0C // WR/RD
|
||||
`define NATV_SYSCTRL_FAULT_STATUS `SOC_SYSCTRL_FAULT_STATUS_OFFSET // W1C/RD
|
||||
`define NATV_SYSCTRL_FAULT_ADDR `SOC_SYSCTRL_FAULT_ADDR_OFFSET // RD
|
||||
`define NATV_SYSCTRL_FAULT_COUNT `SOC_SYSCTRL_FAULT_COUNT_OFFSET // RD
|
||||
// verilog_format: on
|
||||
|
||||
`endif
|
||||
|
||||
`include "mdd_config.svh"
|
||||
`include "mmap_define.svh"
|
||||
|
||||
interface sysctrl_if ();
|
||||
logic [`USER_CORESEL_WIDTH-1:0] core_sel_i;
|
||||
@@ -35,6 +39,10 @@ module nmi_sysctrl (
|
||||
// verilog_format: off
|
||||
input logic clk_i,
|
||||
input logic rst_n_i,
|
||||
input logic fault_valid_i,
|
||||
input logic [31:0] fault_addr_i,
|
||||
input logic [3:0] fault_wstrb_i,
|
||||
input logic fault_reserved_i,
|
||||
nmi_if.slave nmi,
|
||||
sysctrl_if.dut sysctrl
|
||||
// verilog_format: on
|
||||
@@ -52,6 +60,12 @@ module nmi_sysctrl (
|
||||
logic s_sysctrl_i2csel_d, s_sysctrl_i2csel_q;
|
||||
logic s_sysctrl_qspisel_en;
|
||||
logic s_sysctrl_qspisel_d, s_sysctrl_qspisel_q;
|
||||
logic s_fault_status_clear;
|
||||
logic s_fault_pending_d, s_fault_pending_q;
|
||||
logic s_fault_write_d, s_fault_write_q;
|
||||
logic [1:0] s_fault_reason_d, s_fault_reason_q;
|
||||
logic [31:0] s_fault_addr_d, s_fault_addr_q;
|
||||
logic [31:0] s_fault_count_d, s_fault_count_q;
|
||||
|
||||
assign s_nmi_wr_hdshk = nmi.valid && (~s_nmi_ready_q) && (|nmi.wstrb);
|
||||
assign s_nmi_rd_hdshk = nmi.valid && (~s_nmi_ready_q) && (~(|nmi.wstrb));
|
||||
@@ -100,6 +114,59 @@ module nmi_sysctrl (
|
||||
s_sysctrl_qspisel_q
|
||||
);
|
||||
|
||||
assign s_fault_status_clear = s_nmi_wr_hdshk &&
|
||||
nmi.addr[7:0] == `NATV_SYSCTRL_FAULT_STATUS &&
|
||||
nmi.wstrb[0] && nmi.wdata[0];
|
||||
always_comb begin
|
||||
s_fault_pending_d = s_fault_pending_q;
|
||||
s_fault_write_d = s_fault_write_q;
|
||||
s_fault_reason_d = s_fault_reason_q;
|
||||
s_fault_addr_d = s_fault_addr_q;
|
||||
s_fault_count_d = s_fault_count_q;
|
||||
if (s_fault_status_clear) begin
|
||||
s_fault_pending_d = 1'b0;
|
||||
end
|
||||
if (fault_valid_i) begin
|
||||
s_fault_pending_d = 1'b1;
|
||||
s_fault_write_d = |fault_wstrb_i;
|
||||
s_fault_reason_d = fault_reserved_i ? 2'd2 : 2'd1;
|
||||
s_fault_addr_d = fault_addr_i;
|
||||
if (~(&s_fault_count_q)) begin
|
||||
s_fault_count_d = s_fault_count_q + 32'd1;
|
||||
end
|
||||
end
|
||||
end
|
||||
dffr #(1) u_fault_pending_dffr (
|
||||
clk_i,
|
||||
rst_n_i,
|
||||
s_fault_pending_d,
|
||||
s_fault_pending_q
|
||||
);
|
||||
dffr #(1) u_fault_write_dffr (
|
||||
clk_i,
|
||||
rst_n_i,
|
||||
s_fault_write_d,
|
||||
s_fault_write_q
|
||||
);
|
||||
dffr #(2) u_fault_reason_dffr (
|
||||
clk_i,
|
||||
rst_n_i,
|
||||
s_fault_reason_d,
|
||||
s_fault_reason_q
|
||||
);
|
||||
dffr #(32) u_fault_addr_dffr (
|
||||
clk_i,
|
||||
rst_n_i,
|
||||
s_fault_addr_d,
|
||||
s_fault_addr_q
|
||||
);
|
||||
dffr #(32) u_fault_count_dffr (
|
||||
clk_i,
|
||||
rst_n_i,
|
||||
s_fault_count_d,
|
||||
s_fault_count_q
|
||||
);
|
||||
|
||||
assign s_nmi_ready_d = nmi.valid && (~s_nmi_ready_q);
|
||||
dffr #(1) u_nmi_ready_dffr (
|
||||
clk_i,
|
||||
@@ -117,6 +184,9 @@ module nmi_sysctrl (
|
||||
`NATV_SYSCTRL_IPSEL: s_nmi_rdata_d = {{(32 - `USER_IPSEL_WIDTH) {1'b0}}, s_sysctrl_ipsel_q};
|
||||
`NATV_SYSCTRL_I2CSEL: s_nmi_rdata_d = {31'd0, s_sysctrl_i2csel_q};
|
||||
`NATV_SYSCTRL_QSPISEL: s_nmi_rdata_d = {31'd0, s_sysctrl_qspisel_q};
|
||||
`NATV_SYSCTRL_FAULT_STATUS: s_nmi_rdata_d = {28'd0, s_fault_reason_q, s_fault_write_q, s_fault_pending_q};
|
||||
`NATV_SYSCTRL_FAULT_ADDR: s_nmi_rdata_d = s_fault_addr_q;
|
||||
`NATV_SYSCTRL_FAULT_COUNT: s_nmi_rdata_d = s_fault_count_q;
|
||||
default: s_nmi_rdata_d = s_nmi_rdata_q;
|
||||
endcase
|
||||
// verilog_format: on
|
||||
|
||||
@@ -107,7 +107,7 @@ module nmi_xpi (
|
||||
|
||||
|
||||
// nmi mux
|
||||
assign s_xpi_mm_sel = nmi.addr[31:28] == `FLASH_START || nmi.addr[31:28] == `XPI_MEM_START;
|
||||
assign s_xpi_mm_sel = `SOC_ADDR_IS_FLASH(nmi.addr) || `SOC_ADDR_IS_XPI(nmi.addr);
|
||||
assign u_reg_nmi_if.valid = nmi.valid && (~s_xpi_mm_sel);
|
||||
assign u_reg_nmi_if.addr = nmi.addr;
|
||||
assign u_reg_nmi_if.wdata = nmi.wdata;
|
||||
|
||||
+21
-3
@@ -1,4 +1,12 @@
|
||||
GENERATED_FL_DIR := $(FLOW_FILELIST_DIR)
|
||||
MEMORY_MAP_SOURCE := $(RTL_PATH)/memory_map.json
|
||||
MEMORY_MAP_SCRIPT := $(RTL_PATH)/script/generate_memory_map.py
|
||||
MEMORY_MAP_DIR := $(VARIANT_ROOT)/generated/memory_map
|
||||
MEMORY_MAP_STAMP := $(MEMORY_MAP_DIR)/.stamp
|
||||
MEMORY_MAP_RTL_DIR := $(MEMORY_MAP_DIR)/rtl
|
||||
MEMORY_MAP_C_DIR := $(MEMORY_MAP_DIR)/include
|
||||
MEMORY_MAP_LINKER_DIR := $(MEMORY_MAP_DIR)/linker
|
||||
MEMORY_MAP_FILELIST := $(MEMORY_MAP_DIR)/memory_map.fl
|
||||
MPW_STAMP := $(CACHE_ROOT)/stamps/mpw-$(LOCK_DIGEST).prepared
|
||||
MPW_OUTPUT_DIR := $(VARIANT_ROOT)/generated/mpw/$(SIM_TOOL_NAME)
|
||||
MPW_VARIANT_STAMP := $(MPW_OUTPUT_DIR)/.stamp
|
||||
@@ -25,8 +33,18 @@ $(MPW_VARIANT_STAMP): $(MPW_STAMP) $(ROOT_PATH)/scripts/generate_mpw.py
|
||||
|
||||
gen_mpw_code: $(MPW_VARIANT_STAMP)
|
||||
|
||||
$(MEMORY_MAP_STAMP): $(MEMORY_MAP_SOURCE) $(MEMORY_MAP_SCRIPT)
|
||||
python3 $(MEMORY_MAP_SCRIPT) --map $(MEMORY_MAP_SOURCE) \
|
||||
--output-dir $(MEMORY_MAP_DIR) --have-sram-if $(HAVE_SRAM_IF) --ip $(IP)
|
||||
@touch $@
|
||||
|
||||
memory-map: $(MEMORY_MAP_STAMP)
|
||||
|
||||
check-memory-map:
|
||||
python3 $(MEMORY_MAP_SCRIPT) --map $(MEMORY_MAP_SOURCE) --check
|
||||
|
||||
$(FILELIST_STAMP): $(FILELIST_TEMPLATES) $(RTL_PATH)/script/generate_filelist.py \
|
||||
$(RTL_PATH)/script/filelist.py
|
||||
$(RTL_PATH)/script/filelist.py $(MEMORY_MAP_STAMP)
|
||||
python3 $(RTL_PATH)/script/generate_filelist.py \
|
||||
--output-dir $(GENERATED_FL_DIR) \
|
||||
$(foreach define,$(DEF_LIST),--define $(define))
|
||||
@@ -53,7 +71,7 @@ NET_FLIST += -f $(GENERATED_FL_DIR)/sys_def.fl
|
||||
NET_FLIST += -f $(GENERATED_FL_DIR)/commonip.fl
|
||||
NET_FLIST += -f $(GENERATED_FL_DIR)/inc.fl
|
||||
|
||||
RTL_FLIST := $(NET_FLIST)
|
||||
RTL_FLIST := -f $(MEMORY_MAP_FILELIST) $(NET_FLIST)
|
||||
RTL_FLIST += -f $(GENERATED_FL_DIR)/clusterip.fl
|
||||
RTL_FLIST += -f $(GENERATED_FL_DIR)/ip.fl
|
||||
RTL_FLIST += -f $(GENERATED_FL_DIR)/tech.fl
|
||||
@@ -81,4 +99,4 @@ else ifeq ($(SIMU), IVERILOG)
|
||||
include $(RTL_PATH)/mk/iverilog.mk
|
||||
endif
|
||||
|
||||
.PHONY: gen_mpw_code generate_filelist firmware
|
||||
.PHONY: gen_mpw_code generate_filelist memory-map check-memory-map firmware
|
||||
@@ -0,0 +1,43 @@
|
||||
{
|
||||
"schema_version": 1,
|
||||
"cpu_reset": "0x00000000",
|
||||
"regions": [
|
||||
{"symbol": "FLASH", "base": "0x00000000", "size": "0x01000000", "route": "native", "kind": "active", "public": true, "linker": "FLASH"},
|
||||
{"symbol": "NMI_GPIO", "base": "0x10000000", "size": "0x00001000", "route": "native", "kind": "active", "public": true},
|
||||
{"symbol": "NMI_UART0", "base": "0x10001000", "size": "0x00001000", "route": "native", "kind": "active", "public": true},
|
||||
{"symbol": "NMI_TIM0", "base": "0x10002000", "size": "0x00001000", "route": "native", "kind": "active", "public": true},
|
||||
{"symbol": "NMI_TIM1", "base": "0x10003000", "size": "0x00001000", "route": "native", "kind": "active", "public": true},
|
||||
{"symbol": "NMI_PSRAM", "base": "0x10004000", "size": "0x00001000", "route": "native", "kind": "active", "public": true},
|
||||
{"symbol": "NMI_SPISD", "base": "0x10005000", "size": "0x00001000", "route": "native", "kind": "active", "public": true},
|
||||
{"symbol": "NMI_I2C0", "base": "0x10006000", "size": "0x00001000", "route": "native", "kind": "active", "public": true},
|
||||
{"symbol": "NMI_I2S", "base": "0x10007000", "size": "0x00001000", "route": "native", "kind": "active", "public": true},
|
||||
{"symbol": "NMI_ONEWIRE", "base": "0x10008000", "size": "0x00001000", "route": "native", "kind": "active", "public": true},
|
||||
{"symbol": "NMI_XPI", "base": "0x10009000", "size": "0x00001000", "route": "native", "kind": "active", "public": true},
|
||||
{"symbol": "NMI_DMA", "base": "0x1000A000", "size": "0x00001000", "route": "native", "kind": "active", "public": true},
|
||||
{"symbol": "NMI_SYSCTRL", "base": "0x1000B000", "size": "0x00001000", "route": "native", "kind": "active", "public": true},
|
||||
{"symbol": "NMI_CLINT", "base": "0x1000C000", "size": "0x00001000", "route": "native", "kind": "active", "public": true},
|
||||
{"symbol": "NMI_SDRAM", "base": "0x1000D000", "size": "0x00001000", "route": "native", "kind": "active", "public": true},
|
||||
{"symbol": "NMI_DVP", "base": "0x1000E000", "size": "0x00001000", "route": "native", "kind": "active", "public": true},
|
||||
{"symbol": "NMI_SDIO", "base": "0x1000F000", "size": "0x00001000", "route": "reserved", "kind": "reserved", "public": false},
|
||||
{"symbol": "NMI_OPIPSRAM", "base": "0x10010000", "size": "0x00001000", "route": "reserved", "kind": "reserved", "public": false},
|
||||
{"symbol": "NMI_I2C1", "base": "0x10011000", "size": "0x00001000", "route": "native", "kind": "active", "public": true},
|
||||
{"symbol": "NMI_GA", "base": "0x10012000", "size": "0x00001000", "route": "reserved", "kind": "reserved", "public": false},
|
||||
{"symbol": "NMI_APU", "base": "0x10013000", "size": "0x00001000", "route": "reserved", "kind": "reserved", "public": false},
|
||||
{"symbol": "APB_ARCHINFO", "base": "0x20000000", "size": "0x00001000", "route": "apb", "kind": "active", "public": true},
|
||||
{"symbol": "APB_RNG", "base": "0x20001000", "size": "0x00001000", "route": "apb", "kind": "active", "public": true},
|
||||
{"symbol": "APB_UART1", "base": "0x20002000", "size": "0x00001000", "route": "apb", "kind": "active", "public": true},
|
||||
{"symbol": "APB_PWM", "base": "0x20003000", "size": "0x00001000", "route": "apb", "kind": "active", "public": true},
|
||||
{"symbol": "APB_PS2", "base": "0x20004000", "size": "0x00001000", "route": "apb", "kind": "active", "public": true},
|
||||
{"symbol": "APB_RTC", "base": "0x20005000", "size": "0x00001000", "route": "apb", "kind": "active", "public": true},
|
||||
{"symbol": "APB_WDG", "base": "0x20006000", "size": "0x00001000", "route": "apb", "kind": "active", "public": true},
|
||||
{"symbol": "APB_CRC", "base": "0x20007000", "size": "0x00001000", "route": "apb", "kind": "active", "public": true},
|
||||
{"symbol": "APB_TMR", "base": "0x20008000", "size": "0x00001000", "route": "apb", "kind": "active", "public": true},
|
||||
{"symbol": "APB_USER_IP", "base": "0x2000F000", "size": "0x00001000", "route": "apb", "kind": "active", "public": true, "requires_ip": "MDD"},
|
||||
{"symbol": "SRAM", "base": "0x30000000", "size": "0x00020000", "route": "ram", "kind": "active", "public": true, "linker": "SRAM"},
|
||||
{"symbol": "SDRAM", "base": "0x38000000", "size": "0x02000000", "route": "native", "kind": "active", "public": true, "linker": "SDRAM"},
|
||||
{"symbol": "PSRAM", "base": "0x40000000", "size": "0x00800000", "route": "native", "kind": "active", "public": true, "linker": "PSRAM"},
|
||||
{"symbol": "OPIPSRAM", "base": "0x48000000", "size": "0x08000000", "route": "reserved", "kind": "reserved", "public": false},
|
||||
{"symbol": "XPI", "base": "0x50000000", "size": "0x10000000", "route": "native", "kind": "active", "public": true},
|
||||
{"symbol": "SPISD", "base": "0x60000000", "size": "0x40000000", "route": "native", "kind": "active", "public": true}
|
||||
]
|
||||
}
|
||||
@@ -110,10 +110,12 @@ CRT_SRCS += $(ROOT_PATH)/crt/arch/riscv/libgcc/mulsi3.c
|
||||
endif
|
||||
|
||||
INC_PATH := -I$(SW_BUILD_DIR)/include \
|
||||
-I$(MEMORY_MAP_C_DIR) \
|
||||
-I$(ROOT_PATH)/crt/include \
|
||||
$(addprefix -I,$(APP_INC_DIRS))
|
||||
SRC_PATH := $(CRT_SRCS) $(APP_SRCS)
|
||||
LDS_PATH := $(ROOT_PATH)/crt/linker/$(LINK_TYPE).lds
|
||||
MEMORY_REGIONS_LD := $(MEMORY_MAP_LINKER_DIR)/memory_regions.ld
|
||||
VERSION_HEADER := $(SW_BUILD_DIR)/include/socver.h
|
||||
FIRMWARE_ELF := $(SW_BUILD_DIR)/firmware
|
||||
ASM_FIRMWARE_NAME ?= retrosoc_asm
|
||||
@@ -135,10 +137,11 @@ asm: $(MPW_VARIANT_STAMP)
|
||||
cp $(SW_BUILD_DIR)/asm/hello-asm.bin $(SW_BUILD_DIR)/$(ASM_FIRMWARE_NAME).bin
|
||||
cp $(SW_BUILD_DIR)/asm/hello-asm.txt $(SW_BUILD_DIR)/$(ASM_FIRMWARE_NAME)_all.txt
|
||||
|
||||
$(FIRMWARE_ELF): $(MPW_VARIANT_STAMP) $(VERSION_HEADER) $(SRC_PATH) $(SW_HEADERS) $(LDS_PATH) \
|
||||
$(FIRMWARE_ELF): $(MPW_VARIANT_STAMP) $(MEMORY_MAP_STAMP) $(VERSION_HEADER) $(SRC_PATH) $(SW_HEADERS) $(LDS_PATH) \
|
||||
$(ROOT_PATH)/rtl/mini/mk/software.mk
|
||||
@mkdir -p $(SW_BUILD_DIR)
|
||||
cd $(SW_BUILD_DIR) && $(CP) -P -o $(LINK_TYPE).lds $(LDS_PATH)
|
||||
cp $(MEMORY_REGIONS_LD) $(SW_BUILD_DIR)/memory_regions.ld
|
||||
cd $(SW_BUILD_DIR) && $(CC) $(CFLAGS) $(INC_PATH) -o $(@F) $(SRC_PATH)
|
||||
cd $(SW_BUILD_DIR) && $(OBJC) -O verilog $(@F) $(FIRMWARE_NAME).hex
|
||||
cd $(SW_BUILD_DIR) && $(OBJC) -O binary $(@F) $(FIRMWARE_NAME).bin
|
||||
|
||||
@@ -0,0 +1,243 @@
|
||||
#!/usr/bin/env python3
|
||||
"""Generate RTL, SDK and linker address-map artifacts from one JSON source."""
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
import argparse
|
||||
import json
|
||||
import os
|
||||
import tempfile
|
||||
from pathlib import Path
|
||||
from typing import Any
|
||||
|
||||
|
||||
MAX_ADDRESS = 1 << 32
|
||||
VALID_ROUTES = {"native", "apb", "ram", "reserved"}
|
||||
VALID_KINDS = {"active", "reserved"}
|
||||
|
||||
|
||||
def parse_integer(value: Any, field: str) -> int:
|
||||
if isinstance(value, int):
|
||||
return value
|
||||
if isinstance(value, str):
|
||||
try:
|
||||
return int(value, 0)
|
||||
except ValueError as error:
|
||||
raise ValueError(f"{field} must be an integer: {value!r}") from error
|
||||
raise ValueError(f"{field} must be an integer")
|
||||
|
||||
|
||||
def read_map(path: Path) -> tuple[int, list[dict[str, Any]]]:
|
||||
with path.open(encoding="utf-8") as source:
|
||||
document = json.load(source)
|
||||
if document.get("schema_version") != 1:
|
||||
raise ValueError("schema_version must be 1")
|
||||
cpu_reset = parse_integer(document.get("cpu_reset"), "cpu_reset")
|
||||
regions = document.get("regions")
|
||||
if not isinstance(regions, list) or not regions:
|
||||
raise ValueError("regions must be a non-empty list")
|
||||
normalized: list[dict[str, Any]] = []
|
||||
symbols: set[str] = set()
|
||||
for index, region in enumerate(regions):
|
||||
if not isinstance(region, dict):
|
||||
raise ValueError(f"regions[{index}] must be an object")
|
||||
symbol = region.get("symbol")
|
||||
if not isinstance(symbol, str) or not symbol or not symbol.replace("_", "").isalnum():
|
||||
raise ValueError(f"regions[{index}].symbol must be an uppercase identifier")
|
||||
if symbol != symbol.upper() or symbol in symbols:
|
||||
raise ValueError(f"regions[{index}].symbol must be unique and uppercase")
|
||||
symbols.add(symbol)
|
||||
route = region.get("route")
|
||||
kind = region.get("kind")
|
||||
if route not in VALID_ROUTES or kind not in VALID_KINDS:
|
||||
raise ValueError(f"regions[{index}] has invalid route or kind")
|
||||
if (route == "reserved") != (kind == "reserved"):
|
||||
raise ValueError(f"regions[{index}] reserved route and kind must agree")
|
||||
requires_ip = region.get("requires_ip")
|
||||
if requires_ip is not None and requires_ip != "MDD":
|
||||
raise ValueError(f"regions[{index}].requires_ip must be MDD when present")
|
||||
base = parse_integer(region.get("base"), f"regions[{index}].base")
|
||||
size = parse_integer(region.get("size"), f"regions[{index}].size")
|
||||
if base < 0 or size <= 0 or base + size > MAX_ADDRESS:
|
||||
raise ValueError(f"regions[{index}] exceeds the 32-bit address space")
|
||||
if base % 4 != 0 or size % 4 != 0:
|
||||
raise ValueError(f"regions[{index}] must be 32-bit aligned")
|
||||
normalized.append(
|
||||
{
|
||||
"symbol": symbol,
|
||||
"base": base,
|
||||
"size": size,
|
||||
"end": base + size - 1,
|
||||
"route": route,
|
||||
"kind": kind,
|
||||
"public": region.get("public", False) is True,
|
||||
"linker": region.get("linker"),
|
||||
"requires_ip": requires_ip,
|
||||
}
|
||||
)
|
||||
previous: dict[str, Any] | None = None
|
||||
for region in sorted(normalized, key=lambda item: item["base"]):
|
||||
if previous is not None and region["base"] <= previous["end"]:
|
||||
raise ValueError(f"address-map overlap: {previous['symbol']} and {region['symbol']}")
|
||||
previous = region
|
||||
return cpu_reset, normalized
|
||||
|
||||
|
||||
def hex32(value: int) -> str:
|
||||
return f"32'h{value:08X}"
|
||||
|
||||
|
||||
def c_hex32(value: int) -> str:
|
||||
return f"UINT32_C(0x{value:08X})"
|
||||
|
||||
|
||||
def range_expression(symbol: str) -> str:
|
||||
return f"((addr) >= `SOC_ADDR_{symbol}_BASE && (addr) <= `SOC_ADDR_{symbol}_END)"
|
||||
|
||||
|
||||
def join_or(expressions: list[str]) -> str:
|
||||
return " || \\\n ".join(expressions) if expressions else "1'b0"
|
||||
|
||||
|
||||
def render_rtl(cpu_reset: int, regions: list[dict[str, Any]]) -> str:
|
||||
lines = [
|
||||
"// Generated by rtl/mini/script/generate_memory_map.py; do not edit.",
|
||||
"`ifndef RETROSOC_GENERATED_MMAP_DEFINE_SVH",
|
||||
"`define RETROSOC_GENERATED_MMAP_DEFINE_SVH",
|
||||
"",
|
||||
f"`define SOC_CPU_RESET_ADDR {hex32(cpu_reset)}",
|
||||
"`define SOC_IRQ_START_ADDR `SOC_CPU_RESET_ADDR",
|
||||
"// Compatibility aliases for managed MPW cores.",
|
||||
"`define CPU_RESET_ADDR `SOC_CPU_RESET_ADDR",
|
||||
"`define IRQ_START_ADDR `SOC_IRQ_START_ADDR",
|
||||
"",
|
||||
]
|
||||
for region in regions:
|
||||
symbol = region["symbol"]
|
||||
lines += [
|
||||
f"`define SOC_ADDR_{symbol}_BASE {hex32(region['base'])}",
|
||||
f"`define SOC_ADDR_{symbol}_END {hex32(region['end'])}",
|
||||
f"`define SOC_ADDR_IS_{symbol}(addr) {range_expression(symbol)}",
|
||||
]
|
||||
lines.append("")
|
||||
for route in ("native", "apb", "ram", "reserved"):
|
||||
selected = [
|
||||
f"`SOC_ADDR_IS_{region['symbol']}(addr)"
|
||||
for region in regions
|
||||
if region["route"] == route
|
||||
]
|
||||
lines.append(f"`define SOC_ADDR_IS_{route.upper()}(addr) ({join_or(selected)})")
|
||||
lines += [
|
||||
"",
|
||||
"`define SOC_SYSCTRL_FAULT_STATUS_OFFSET 32'h00000010",
|
||||
"`define SOC_SYSCTRL_FAULT_ADDR_OFFSET 32'h00000014",
|
||||
"`define SOC_SYSCTRL_FAULT_COUNT_OFFSET 32'h00000018",
|
||||
"",
|
||||
"`endif",
|
||||
"",
|
||||
]
|
||||
return "\n".join(lines)
|
||||
|
||||
|
||||
def render_c(cpu_reset: int, regions: list[dict[str, Any]], have_sram_if: str) -> str:
|
||||
lines = [
|
||||
"/* Generated by rtl/mini/script/generate_memory_map.py; do not edit. */",
|
||||
"#ifndef RETROSOC_GENERATED_MEMORY_MAP_H",
|
||||
"#define RETROSOC_GENERATED_MEMORY_MAP_H",
|
||||
"",
|
||||
"#include <stdint.h>",
|
||||
"",
|
||||
f"#define RS_SOC_CPU_RESET_ADDR {c_hex32(cpu_reset)}",
|
||||
f"#define RS_SOC_HAS_SRAM {1 if have_sram_if == 'YES' else 0}U",
|
||||
"",
|
||||
]
|
||||
for region in regions:
|
||||
if not region["public"]:
|
||||
continue
|
||||
symbol = region["symbol"]
|
||||
lines += [
|
||||
f"#define RS_SOC_{symbol}_BASE {c_hex32(region['base'])}",
|
||||
f"#define RS_SOC_{symbol}_SIZE {c_hex32(region['size'])}",
|
||||
f"#define RS_SOC_{symbol}_END {c_hex32(region['end'])}",
|
||||
]
|
||||
lines += [
|
||||
"",
|
||||
"#define RS_SOC_SYSCTRL_FAULT_STATUS_OFFSET UINT32_C(0x00000010)",
|
||||
"#define RS_SOC_SYSCTRL_FAULT_ADDR_OFFSET UINT32_C(0x00000014)",
|
||||
"#define RS_SOC_SYSCTRL_FAULT_COUNT_OFFSET UINT32_C(0x00000018)",
|
||||
"",
|
||||
"#endif",
|
||||
"",
|
||||
]
|
||||
return "\n".join(lines)
|
||||
|
||||
|
||||
def render_linker(regions: list[dict[str, Any]]) -> str:
|
||||
lines = [
|
||||
"/* Generated by rtl/mini/script/generate_memory_map.py; do not edit. */",
|
||||
"MEMORY",
|
||||
"{",
|
||||
]
|
||||
for region in regions:
|
||||
linker = region["linker"]
|
||||
if linker is None:
|
||||
continue
|
||||
attributes = "rx" if linker == "FLASH" else "wxa!ri"
|
||||
lines.append(
|
||||
f" {linker} ({attributes}) : ORIGIN = 0x{region['base']:08X}, "
|
||||
f"LENGTH = 0x{region['size']:08X}"
|
||||
)
|
||||
lines += ["}", ""]
|
||||
return "\n".join(lines)
|
||||
|
||||
|
||||
def atomic_write(path: Path, content: str) -> None:
|
||||
path.parent.mkdir(parents=True, exist_ok=True)
|
||||
if path.exists() and path.read_text(encoding="utf-8") == content:
|
||||
return
|
||||
descriptor, temporary_name = tempfile.mkstemp(prefix=f".{path.name}.", dir=path.parent)
|
||||
try:
|
||||
with os.fdopen(descriptor, "w", encoding="utf-8", newline="\n") as output:
|
||||
output.write(content)
|
||||
os.replace(temporary_name, path)
|
||||
except BaseException:
|
||||
Path(temporary_name).unlink(missing_ok=True)
|
||||
raise
|
||||
|
||||
|
||||
def generate(map_path: Path, output_dir: Path, have_sram_if: str, ip: str) -> None:
|
||||
cpu_reset, regions = read_map(map_path)
|
||||
enabled_regions = [
|
||||
region for region in regions if region["requires_ip"] is None or region["requires_ip"] == ip
|
||||
]
|
||||
atomic_write(output_dir / "rtl" / "mmap_define.svh", render_rtl(cpu_reset, enabled_regions))
|
||||
atomic_write(output_dir / "memory_map.fl", f"+incdir+{output_dir / 'rtl'}\n")
|
||||
atomic_write(
|
||||
output_dir / "include" / "retrosoc" / "generated" / "memory_map.h",
|
||||
render_c(cpu_reset, enabled_regions, have_sram_if),
|
||||
)
|
||||
atomic_write(output_dir / "linker" / "memory_regions.ld", render_linker(enabled_regions))
|
||||
|
||||
|
||||
def main() -> int:
|
||||
parser = argparse.ArgumentParser(description=__doc__)
|
||||
parser.add_argument("--map", required=True, type=Path)
|
||||
parser.add_argument("--output-dir", type=Path)
|
||||
parser.add_argument("--have-sram-if", choices=("YES", "NO"), default="NO")
|
||||
parser.add_argument("--ip", choices=("NONE", "MDD"), default="NONE")
|
||||
parser.add_argument("--check", action="store_true", help="validate only; write nothing")
|
||||
arguments = parser.parse_args()
|
||||
try:
|
||||
if arguments.check:
|
||||
read_map(arguments.map)
|
||||
else:
|
||||
if arguments.output_dir is None:
|
||||
parser.error("--output-dir is required unless --check is used")
|
||||
generate(arguments.map, arguments.output_dir, arguments.have_sram_if, arguments.ip)
|
||||
except (OSError, ValueError, json.JSONDecodeError) as error:
|
||||
parser.error(str(error))
|
||||
return 0
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
raise SystemExit(main())
|
||||
+21
-21
@@ -20,11 +20,15 @@ module bus (
|
||||
nmi_if.slave core_nmi,
|
||||
nmi_if.slave dma_nmi,
|
||||
nmi_if.master natv_nmi,
|
||||
nmi_if.master apb_nmi
|
||||
nmi_if.master apb_nmi,
|
||||
output logic fault_valid_o,
|
||||
output logic [31:0] fault_addr_o,
|
||||
output logic [3:0] fault_wstrb_o,
|
||||
output logic fault_reserved_o
|
||||
// verilog_format: on
|
||||
);
|
||||
|
||||
logic s_natv_sel, s_apb_sel, s_ram_sel;
|
||||
logic s_natv_sel, s_apb_sel, s_ram_sel, s_fault_sel;
|
||||
logic s_ram_valid, s_ram_ready;
|
||||
logic s_mstr_lock_d, s_mstr_lock_q;
|
||||
logic s_mstr_id_d, s_mstr_id_q;
|
||||
@@ -84,40 +88,36 @@ module bus (
|
||||
u_mstr_rgsl_nmi_if
|
||||
);
|
||||
|
||||
// bus mux — hierarchical address decode (2-level)
|
||||
// bus mux — address ownership comes from the generated address map.
|
||||
// verilog_format: off
|
||||
logic s_natv_hi_sel;
|
||||
// Level 1: fast 4-bit decode on addr[31:28]
|
||||
assign s_natv_hi_sel = u_mstr_rgsl_nmi_if.addr[31:28] == `FLASH_START ||
|
||||
u_mstr_rgsl_nmi_if.addr[31:28] == `NMI_IP_START ||
|
||||
u_mstr_rgsl_nmi_if.addr[31:28] == `SPISD_START0 ||
|
||||
u_mstr_rgsl_nmi_if.addr[31:28] == `SPISD_START1 ||
|
||||
u_mstr_rgsl_nmi_if.addr[31:28] == `SPISD_START2 ||
|
||||
u_mstr_rgsl_nmi_if.addr[31:28] == `SPISD_START3;
|
||||
// Level 2: memory-mapped ranges that need wider compare
|
||||
assign s_natv_sel = s_natv_hi_sel ||
|
||||
(u_mstr_rgsl_nmi_if.addr[31:24] >= `SDRAM_START &&
|
||||
u_mstr_rgsl_nmi_if.addr[31:24] <= `SDRAM_END) ||
|
||||
u_mstr_rgsl_nmi_if.addr[31:24] == `PSRAM_START ||
|
||||
u_mstr_rgsl_nmi_if.addr[31:24] == `OPIPSRAM_START;
|
||||
assign s_natv_sel = `SOC_ADDR_IS_NATIVE(u_mstr_rgsl_nmi_if.addr);
|
||||
assign natv_nmi.valid = u_mstr_rgsl_nmi_if.valid && s_natv_sel;
|
||||
assign natv_nmi.addr = u_mstr_rgsl_nmi_if.addr;
|
||||
assign natv_nmi.wdata = u_mstr_rgsl_nmi_if.wdata;
|
||||
assign natv_nmi.wstrb = u_mstr_rgsl_nmi_if.wstrb;
|
||||
|
||||
assign s_apb_sel = u_mstr_rgsl_nmi_if.addr[31:28] == `APB_IP_START;
|
||||
assign s_apb_sel = `SOC_ADDR_IS_APB(u_mstr_rgsl_nmi_if.addr);
|
||||
assign apb_nmi.valid = u_mstr_rgsl_nmi_if.valid && s_apb_sel;
|
||||
assign apb_nmi.addr = u_mstr_rgsl_nmi_if.addr;
|
||||
assign apb_nmi.wdata = u_mstr_rgsl_nmi_if.wdata;
|
||||
assign apb_nmi.wstrb = u_mstr_rgsl_nmi_if.wstrb;
|
||||
|
||||
`ifdef HAVE_SRAM_IF
|
||||
assign s_ram_sel = u_mstr_rgsl_nmi_if.addr[31:24] >= `SRAM_START && u_mstr_rgsl_nmi_if.addr[31:24] <= `SRAM_END;
|
||||
assign s_ram_sel = `SOC_ADDR_IS_RAM(u_mstr_rgsl_nmi_if.addr);
|
||||
assign s_ram_valid = u_mstr_rgsl_nmi_if.valid && s_ram_sel;
|
||||
assign ram.addr = u_mstr_rgsl_nmi_if.addr[16:2];
|
||||
assign ram.wdata = u_mstr_rgsl_nmi_if.wdata;
|
||||
assign ram.wstrb = s_ram_valid ? u_mstr_rgsl_nmi_if.wstrb : '0;
|
||||
`else
|
||||
assign s_ram_sel = 1'b0;
|
||||
`endif
|
||||
|
||||
assign s_fault_sel = u_mstr_rgsl_nmi_if.valid &&
|
||||
~(s_natv_sel || s_apb_sel || s_ram_sel);
|
||||
assign fault_valid_o = s_fault_sel;
|
||||
assign fault_addr_o = u_mstr_rgsl_nmi_if.addr;
|
||||
assign fault_wstrb_o = u_mstr_rgsl_nmi_if.wstrb;
|
||||
assign fault_reserved_o = `SOC_ADDR_IS_RESERVED(u_mstr_rgsl_nmi_if.addr);
|
||||
// verilog_format: on
|
||||
|
||||
`ifdef HAVE_SRAM_MACRO
|
||||
@@ -133,10 +133,10 @@ module bus (
|
||||
`ifdef HAVE_SRAM_IF
|
||||
assign u_mstr_rgsl_nmi_if.ready = (natv_nmi.valid && natv_nmi.ready) ||
|
||||
(apb_nmi.valid && apb_nmi.ready) ||
|
||||
s_ram_ready;
|
||||
s_ram_ready || s_fault_sel;
|
||||
`else
|
||||
assign u_mstr_rgsl_nmi_if.ready = (natv_nmi.valid && natv_nmi.ready) ||
|
||||
(apb_nmi.valid && apb_nmi.ready);
|
||||
(apb_nmi.valid && apb_nmi.ready) || s_fault_sel;
|
||||
`endif
|
||||
|
||||
|
||||
|
||||
@@ -31,8 +31,8 @@ module core_wrapper (
|
||||
.ENABLE_FAST_MUL(1),
|
||||
.ENABLE_DIV (1),
|
||||
.ENABLE_IRQ (0),
|
||||
.PROGADDR_RESET (`CPU_RESET_ADDR),
|
||||
.PROGADDR_IRQ (`IRQ_START_ADDR)
|
||||
.PROGADDR_RESET (`SOC_CPU_RESET_ADDR),
|
||||
.PROGADDR_IRQ (`SOC_IRQ_START_ADDR)
|
||||
) u_picorv32 (
|
||||
.clk (clk_i),
|
||||
.resetn (rst_n_i),
|
||||
@@ -72,7 +72,7 @@ module core_wrapper (
|
||||
// verilog_format: on
|
||||
|
||||
hazard3_cpu_1port #(
|
||||
.RESET_VECTOR (`CPU_RESET_ADDR),
|
||||
.RESET_VECTOR (`SOC_CPU_RESET_ADDR),
|
||||
.MTVEC_INIT (32'h0000_0000),
|
||||
.EXTENSION_A (1),
|
||||
.EXTENSION_C (1),
|
||||
|
||||
@@ -34,6 +34,10 @@ module ip_nmi_wrapper (
|
||||
sdio_if.dut sdio,
|
||||
opipsram_if.dut opipsram,
|
||||
i2c_if.dut i2c1,
|
||||
input logic fault_valid_i,
|
||||
input logic [31:0] fault_addr_i,
|
||||
input logic [3:0] fault_wstrb_i,
|
||||
input logic fault_reserved_i,
|
||||
// irq
|
||||
output logic [9:0] irq_o
|
||||
// verilog_format: on
|
||||
@@ -83,107 +87,104 @@ module ip_nmi_wrapper (
|
||||
assign u_dma_hw_trg_if.qspi_tx_proc = ~s_dma_xpi_tx_stall;
|
||||
assign u_dma_hw_trg_if.qspi_rx_proc = ~s_dma_xpi_rx_stall;
|
||||
// gpio
|
||||
assign u_gpio_nmi_if.valid = nmi.valid && (nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_GPIO_START);
|
||||
assign u_gpio_nmi_if.addr = nmi.addr;
|
||||
assign u_gpio_nmi_if.wdata = nmi.wdata;
|
||||
assign u_gpio_nmi_if.wstrb = nmi.wstrb;
|
||||
assign u_gpio_nmi_if.valid = nmi.valid && `SOC_ADDR_IS_NMI_GPIO(nmi.addr);
|
||||
assign u_gpio_nmi_if.addr = nmi.addr;
|
||||
assign u_gpio_nmi_if.wdata = nmi.wdata;
|
||||
assign u_gpio_nmi_if.wstrb = nmi.wstrb;
|
||||
// uart
|
||||
assign u_uart_nmi_if.valid = nmi.valid && (nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_UART_START);
|
||||
assign u_uart_nmi_if.addr = nmi.addr;
|
||||
assign u_uart_nmi_if.wdata = nmi.wdata;
|
||||
assign u_uart_nmi_if.wstrb = nmi.wstrb;
|
||||
assign u_uart_nmi_if.valid = nmi.valid && `SOC_ADDR_IS_NMI_UART0(nmi.addr);
|
||||
assign u_uart_nmi_if.addr = nmi.addr;
|
||||
assign u_uart_nmi_if.wdata = nmi.wdata;
|
||||
assign u_uart_nmi_if.wstrb = nmi.wstrb;
|
||||
// tim0
|
||||
assign u_tim0_nmi_if.valid = nmi.valid && (nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_TIM0_START);
|
||||
assign u_tim0_nmi_if.addr = nmi.addr;
|
||||
assign u_tim0_nmi_if.wdata = nmi.wdata;
|
||||
assign u_tim0_nmi_if.wstrb = nmi.wstrb;
|
||||
assign u_tim0_nmi_if.valid = nmi.valid && `SOC_ADDR_IS_NMI_TIM0(nmi.addr);
|
||||
assign u_tim0_nmi_if.addr = nmi.addr;
|
||||
assign u_tim0_nmi_if.wdata = nmi.wdata;
|
||||
assign u_tim0_nmi_if.wstrb = nmi.wstrb;
|
||||
// tim1
|
||||
assign u_tim1_nmi_if.valid = nmi.valid && (nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_TIM1_START);
|
||||
assign u_tim1_nmi_if.addr = nmi.addr;
|
||||
assign u_tim1_nmi_if.wdata = nmi.wdata;
|
||||
assign u_tim1_nmi_if.wstrb = nmi.wstrb;
|
||||
assign u_tim1_nmi_if.valid = nmi.valid && `SOC_ADDR_IS_NMI_TIM1(nmi.addr);
|
||||
assign u_tim1_nmi_if.addr = nmi.addr;
|
||||
assign u_tim1_nmi_if.wdata = nmi.wdata;
|
||||
assign u_tim1_nmi_if.wstrb = nmi.wstrb;
|
||||
// psram
|
||||
assign s_psram_cfg_sel = nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_PSRAM_START;
|
||||
assign s_psram_mem_sel = nmi.addr[31:24] >= `PSRAM_START && nmi.addr[31:24] <= `PSRAM_END;
|
||||
assign u_psram_nmi_if.valid = nmi.valid && (s_psram_mem_sel || s_psram_cfg_sel);
|
||||
assign u_psram_nmi_if.addr = nmi.addr;
|
||||
assign u_psram_nmi_if.wdata = nmi.wdata;
|
||||
assign u_psram_nmi_if.wstrb = nmi.wstrb;
|
||||
assign s_psram_cfg_sel = `SOC_ADDR_IS_NMI_PSRAM(nmi.addr);
|
||||
assign s_psram_mem_sel = `SOC_ADDR_IS_PSRAM(nmi.addr);
|
||||
assign u_psram_nmi_if.valid = nmi.valid && (s_psram_mem_sel || s_psram_cfg_sel);
|
||||
assign u_psram_nmi_if.addr = nmi.addr;
|
||||
assign u_psram_nmi_if.wdata = nmi.wdata;
|
||||
assign u_psram_nmi_if.wstrb = nmi.wstrb;
|
||||
// spisd
|
||||
assign s_spisd_cfg_sel = nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_SPISD_START;
|
||||
assign u_spisd_nmi_if.valid = nmi.valid && (nmi.addr[31:28] == `SPISD_START0 ||
|
||||
nmi.addr[31:28] == `SPISD_START1 ||
|
||||
nmi.addr[31:28] == `SPISD_START2 ||
|
||||
nmi.addr[31:28] == `SPISD_START3 || s_spisd_cfg_sel);
|
||||
assign u_spisd_nmi_if.addr = nmi.addr;
|
||||
assign u_spisd_nmi_if.wdata = nmi.wdata;
|
||||
assign u_spisd_nmi_if.wstrb = nmi.wstrb;
|
||||
assign s_spisd_cfg_sel = `SOC_ADDR_IS_NMI_SPISD(nmi.addr);
|
||||
assign u_spisd_nmi_if.valid = nmi.valid && (`SOC_ADDR_IS_SPISD(nmi.addr) || s_spisd_cfg_sel);
|
||||
assign u_spisd_nmi_if.addr = nmi.addr;
|
||||
assign u_spisd_nmi_if.wdata = nmi.wdata;
|
||||
assign u_spisd_nmi_if.wstrb = nmi.wstrb;
|
||||
// i2c0
|
||||
assign u_i2c0_nmi_if.valid = nmi.valid && (nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_I2C0_START);
|
||||
assign u_i2c0_nmi_if.addr = nmi.addr;
|
||||
assign u_i2c0_nmi_if.wdata = nmi.wdata;
|
||||
assign u_i2c0_nmi_if.wstrb = nmi.wstrb;
|
||||
assign u_i2c0_nmi_if.valid = nmi.valid && `SOC_ADDR_IS_NMI_I2C0(nmi.addr);
|
||||
assign u_i2c0_nmi_if.addr = nmi.addr;
|
||||
assign u_i2c0_nmi_if.wdata = nmi.wdata;
|
||||
assign u_i2c0_nmi_if.wstrb = nmi.wstrb;
|
||||
// i2s
|
||||
assign u_i2s_nmi_if.valid = nmi.valid && (nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_I2S_START);
|
||||
assign u_i2s_nmi_if.addr = nmi.addr;
|
||||
assign u_i2s_nmi_if.wdata = nmi.wdata;
|
||||
assign u_i2s_nmi_if.wstrb = nmi.wstrb;
|
||||
assign u_i2s_nmi_if.valid = nmi.valid && `SOC_ADDR_IS_NMI_I2S(nmi.addr);
|
||||
assign u_i2s_nmi_if.addr = nmi.addr;
|
||||
assign u_i2s_nmi_if.wdata = nmi.wdata;
|
||||
assign u_i2s_nmi_if.wstrb = nmi.wstrb;
|
||||
// onewire
|
||||
assign u_onewire_nmi_if.valid = nmi.valid && (nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_ONEWIRE_START);
|
||||
assign u_onewire_nmi_if.addr = nmi.addr;
|
||||
assign u_onewire_nmi_if.wdata = nmi.wdata;
|
||||
assign u_onewire_nmi_if.wstrb = nmi.wstrb;
|
||||
assign u_onewire_nmi_if.valid = nmi.valid && `SOC_ADDR_IS_NMI_ONEWIRE(nmi.addr);
|
||||
assign u_onewire_nmi_if.addr = nmi.addr;
|
||||
assign u_onewire_nmi_if.wdata = nmi.wdata;
|
||||
assign u_onewire_nmi_if.wstrb = nmi.wstrb;
|
||||
// xpi
|
||||
assign s_xpi_cfg_sel = nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_XPI_START;
|
||||
assign s_xpi_mem_sel = nmi.addr[31:28] == `FLASH_START || nmi.addr[31:28] == `XPI_MEM_START;
|
||||
assign u_xpi_nmi_if.valid = nmi.valid && (s_xpi_cfg_sel || s_xpi_mem_sel);
|
||||
assign u_xpi_nmi_if.addr = nmi.addr;
|
||||
assign u_xpi_nmi_if.wdata = nmi.wdata;
|
||||
assign u_xpi_nmi_if.wstrb = nmi.wstrb;
|
||||
assign s_xpi_cfg_sel = `SOC_ADDR_IS_NMI_XPI(nmi.addr);
|
||||
assign s_xpi_mem_sel = `SOC_ADDR_IS_FLASH(nmi.addr) || `SOC_ADDR_IS_XPI(nmi.addr);
|
||||
assign u_xpi_nmi_if.valid = nmi.valid && (s_xpi_cfg_sel || s_xpi_mem_sel);
|
||||
assign u_xpi_nmi_if.addr = nmi.addr;
|
||||
assign u_xpi_nmi_if.wdata = nmi.wdata;
|
||||
assign u_xpi_nmi_if.wstrb = nmi.wstrb;
|
||||
// dma
|
||||
assign u_dma_nmi_if.valid = nmi.valid && (nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_DMA_START);
|
||||
assign u_dma_nmi_if.addr = nmi.addr;
|
||||
assign u_dma_nmi_if.wdata = nmi.wdata;
|
||||
assign u_dma_nmi_if.wstrb = nmi.wstrb;
|
||||
assign u_dma_nmi_if.valid = nmi.valid && `SOC_ADDR_IS_NMI_DMA(nmi.addr);
|
||||
assign u_dma_nmi_if.addr = nmi.addr;
|
||||
assign u_dma_nmi_if.wdata = nmi.wdata;
|
||||
assign u_dma_nmi_if.wstrb = nmi.wstrb;
|
||||
// sysctrl
|
||||
assign u_sysctrl_nmi_if.valid = nmi.valid && (nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_SYSCTRL_START);
|
||||
assign u_sysctrl_nmi_if.addr = nmi.addr;
|
||||
assign u_sysctrl_nmi_if.wdata = nmi.wdata;
|
||||
assign u_sysctrl_nmi_if.wstrb = nmi.wstrb;
|
||||
assign u_sysctrl_nmi_if.valid = nmi.valid && `SOC_ADDR_IS_NMI_SYSCTRL(nmi.addr);
|
||||
assign u_sysctrl_nmi_if.addr = nmi.addr;
|
||||
assign u_sysctrl_nmi_if.wdata = nmi.wdata;
|
||||
assign u_sysctrl_nmi_if.wstrb = nmi.wstrb;
|
||||
// clint
|
||||
assign u_clint_nmi_if.valid = nmi.valid && (nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_CLINT_START);
|
||||
assign u_clint_nmi_if.addr = nmi.addr;
|
||||
assign u_clint_nmi_if.wdata = nmi.wdata;
|
||||
assign u_clint_nmi_if.wstrb = nmi.wstrb;
|
||||
assign u_clint_nmi_if.valid = nmi.valid && `SOC_ADDR_IS_NMI_CLINT(nmi.addr);
|
||||
assign u_clint_nmi_if.addr = nmi.addr;
|
||||
assign u_clint_nmi_if.wdata = nmi.wdata;
|
||||
assign u_clint_nmi_if.wstrb = nmi.wstrb;
|
||||
// sdram
|
||||
assign s_sdram_cfg_sel = nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_SDRAM_START;
|
||||
assign s_sdram_mem_sel = nmi.addr[31:24] >= `SDRAM_START && nmi.addr[31:24] <= `SDRAM_END;
|
||||
assign u_sdram_nmi_if.valid = nmi.valid && (s_sdram_cfg_sel || s_sdram_mem_sel);
|
||||
assign u_sdram_nmi_if.addr = nmi.addr;
|
||||
assign u_sdram_nmi_if.wdata = nmi.wdata;
|
||||
assign u_sdram_nmi_if.wstrb = nmi.wstrb;
|
||||
assign s_sdram_cfg_sel = `SOC_ADDR_IS_NMI_SDRAM(nmi.addr);
|
||||
assign s_sdram_mem_sel = `SOC_ADDR_IS_SDRAM(nmi.addr);
|
||||
assign u_sdram_nmi_if.valid = nmi.valid && (s_sdram_cfg_sel || s_sdram_mem_sel);
|
||||
assign u_sdram_nmi_if.addr = nmi.addr;
|
||||
assign u_sdram_nmi_if.wdata = nmi.wdata;
|
||||
assign u_sdram_nmi_if.wstrb = nmi.wstrb;
|
||||
// dvp
|
||||
assign u_dvp_nmi_if.valid = nmi.valid && (nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_DVP_START);
|
||||
assign u_dvp_nmi_if.addr = nmi.addr;
|
||||
assign u_dvp_nmi_if.wdata = nmi.wdata;
|
||||
assign u_dvp_nmi_if.wstrb = nmi.wstrb;
|
||||
assign u_dvp_nmi_if.valid = nmi.valid && `SOC_ADDR_IS_NMI_DVP(nmi.addr);
|
||||
assign u_dvp_nmi_if.addr = nmi.addr;
|
||||
assign u_dvp_nmi_if.wdata = nmi.wdata;
|
||||
assign u_dvp_nmi_if.wstrb = nmi.wstrb;
|
||||
// sdio
|
||||
assign u_sdio_nmi_if.valid = nmi.valid && (nmi.addr[31:28] == `NMI_IP_START && nmi.addr[15:8] == `NMI_SDIO_START);
|
||||
assign u_sdio_nmi_if.addr = nmi.addr;
|
||||
assign u_sdio_nmi_if.wdata = nmi.wdata;
|
||||
assign u_sdio_nmi_if.wstrb = nmi.wstrb;
|
||||
assign u_sdio_nmi_if.valid = 1'b0;
|
||||
assign u_sdio_nmi_if.addr = nmi.addr;
|
||||
assign u_sdio_nmi_if.wdata = nmi.wdata;
|
||||
assign u_sdio_nmi_if.wstrb = nmi.wstrb;
|
||||
// opipsram
|
||||
assign s_opipsram_cfg_sel = nmi.addr[31:28] == `NMI_IP_START && nmi.addr[19:16] == 4'd1 && nmi.addr[15:8] == `NMI_OPIPSRAM_START;
|
||||
assign s_opipsram_mem_sel = nmi.addr[31:24] >= `OPIPSRAM_START && nmi.addr[31:24] <= `OPIPSRAM_END;
|
||||
assign u_opipsram_nmi_if.valid = nmi.valid && (s_opipsram_mem_sel || s_opipsram_cfg_sel);
|
||||
assign u_opipsram_nmi_if.addr = nmi.addr;
|
||||
assign s_opipsram_cfg_sel = 1'b0;
|
||||
assign s_opipsram_mem_sel = 1'b0;
|
||||
assign u_opipsram_nmi_if.valid = 1'b0;
|
||||
assign u_opipsram_nmi_if.addr = nmi.addr;
|
||||
assign u_opipsram_nmi_if.wdata = nmi.wdata;
|
||||
assign u_opipsram_nmi_if.wstrb = nmi.wstrb;
|
||||
// i2c1
|
||||
assign u_i2c1_nmi_if.valid = nmi.valid && (nmi.addr[31:28] == `NMI_IP_START && nmi.addr[19:16] == 4'd1 && nmi.addr[15:8] == `NMI_I2C1_START);
|
||||
assign u_i2c1_nmi_if.addr = nmi.addr;
|
||||
assign u_i2c1_nmi_if.wdata = nmi.wdata;
|
||||
assign u_i2c1_nmi_if.wstrb = nmi.wstrb;
|
||||
assign u_i2c1_nmi_if.valid = nmi.valid && `SOC_ADDR_IS_NMI_I2C1(nmi.addr);
|
||||
assign u_i2c1_nmi_if.addr = nmi.addr;
|
||||
assign u_i2c1_nmi_if.wdata = nmi.wdata;
|
||||
assign u_i2c1_nmi_if.wstrb = nmi.wstrb;
|
||||
|
||||
// verilog_format: off
|
||||
// Registered one-hot slave select for response mux (breaks comb fanin)
|
||||
@@ -374,10 +375,14 @@ module ip_nmi_wrapper (
|
||||
);
|
||||
|
||||
nmi_sysctrl u_nmi_sysctrl (
|
||||
.clk_i (clk_i),
|
||||
.rst_n_i(rst_n_i),
|
||||
.nmi (u_sysctrl_nmi_if),
|
||||
.sysctrl(sysctrl)
|
||||
.clk_i (clk_i),
|
||||
.rst_n_i (rst_n_i),
|
||||
.fault_valid_i (fault_valid_i),
|
||||
.fault_addr_i (fault_addr_i),
|
||||
.fault_wstrb_i (fault_wstrb_i),
|
||||
.fault_reserved_i(fault_reserved_i),
|
||||
.nmi (u_sysctrl_nmi_if),
|
||||
.sysctrl (sysctrl)
|
||||
);
|
||||
|
||||
nmi_clint u_nmi_clint (
|
||||
|
||||
@@ -26,8 +26,8 @@ module mgmt_core_wrapper (
|
||||
.ENABLE_FAST_MUL(1),
|
||||
.ENABLE_DIV (1),
|
||||
.ENABLE_IRQ (0),
|
||||
.PROGADDR_RESET (`CPU_RESET_ADDR),
|
||||
.PROGADDR_IRQ (`IRQ_START_ADDR)
|
||||
.PROGADDR_RESET (`SOC_CPU_RESET_ADDR),
|
||||
.PROGADDR_IRQ (`SOC_IRQ_START_ADDR)
|
||||
) u_picorv32 (
|
||||
.clk (clk_i),
|
||||
.resetn (rst_n_i),
|
||||
|
||||
@@ -1,69 +0,0 @@
|
||||
// Copyright (c) 2023-2026 Yuchi Miao <miaoyuchi@ict.ac.cn>
|
||||
// retroSoC 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.
|
||||
|
||||
`ifndef INC_MMAP_DEFINE_SVH
|
||||
`define INC_MMAP_DEFINE_SVH
|
||||
|
||||
`define CPU_RESET_ADDR 32'h0000_0000
|
||||
// NOTE: need to set a right value for software!
|
||||
`define IRQ_START_ADDR 32'h0000_0000
|
||||
|
||||
`define FLASH_START 4'h0
|
||||
`define NMI_IP_START 4'h1
|
||||
`define APB_IP_START 4'h2
|
||||
`define SRAM_START 8'h30
|
||||
`define SRAM_END 8'h37
|
||||
`define SDRAM_START 8'h38
|
||||
`define SDRAM_END 8'h3F
|
||||
`define PSRAM_START 8'h40
|
||||
`define PSRAM_END 8'h47
|
||||
`define OPIPSRAM_START 8'h48
|
||||
`define OPIPSRAM_END 8'h4F
|
||||
`define XPI_MEM_START 4'h5
|
||||
`define SPISD_START0 4'h6
|
||||
`define SPISD_START1 4'h7
|
||||
`define SPISD_START2 4'h8
|
||||
`define SPISD_START3 4'h9
|
||||
|
||||
// NMI IP REG ADDR
|
||||
`define NMI_GPIO_START 8'h00
|
||||
`define NMI_UART_START 8'h10
|
||||
`define NMI_TIM0_START 8'h20
|
||||
`define NMI_TIM1_START 8'h30
|
||||
`define NMI_PSRAM_START 8'h40
|
||||
`define NMI_SPISD_START 8'h50
|
||||
`define NMI_I2C0_START 8'h60
|
||||
`define NMI_I2S_START 8'h70
|
||||
`define NMI_ONEWIRE_START 8'h80
|
||||
`define NMI_XPI_START 8'h90
|
||||
`define NMI_DMA_START 8'hA0
|
||||
`define NMI_SYSCTRL_START 8'hB0
|
||||
`define NMI_CLINT_START 8'hC0
|
||||
`define NMI_SDRAM_START 8'hD0
|
||||
`define NMI_DVP_START 8'hE0
|
||||
`define NMI_SDIO_START 8'hF0
|
||||
// new cycle
|
||||
`define NMI_OPIPSRAM_START 8'h00
|
||||
`define NMI_I2C1_START 8'h10
|
||||
`define NMI_GA_START 8'h20
|
||||
`define NMI_APU_START 8'h30
|
||||
|
||||
// APB IP REG ADDR
|
||||
`define APB_ARCHINFO_START 8'h00
|
||||
`define APB_RNG_START 8'h10
|
||||
`define APB_UART_START 8'h20
|
||||
`define APB_PWM_START 8'h30
|
||||
`define APB_PS2_START 8'h40
|
||||
`define APB_RTC_START 8'h50
|
||||
`define APB_WDG_START 8'h60
|
||||
`define APB_CRC_START 8'h70
|
||||
`define APB_TMR_START 8'h80
|
||||
`define APB_USR_START 8'hF0
|
||||
`endif
|
||||
+40
-28
@@ -67,6 +67,10 @@ module retrosoc (
|
||||
logic [31:0] s_irq;
|
||||
logic [ 9:0] s_nmi_irq;
|
||||
logic [ 6:0] s_apb_irq;
|
||||
logic s_bus_fault_valid;
|
||||
logic [31:0] s_bus_fault_addr;
|
||||
logic [ 3:0] s_bus_fault_wstrb;
|
||||
logic s_bus_fault_reserved;
|
||||
|
||||
`ifdef CORE_MDD
|
||||
assign u_sysctrl_if.core_sel_i = core_sel_i;
|
||||
@@ -371,42 +375,50 @@ module retrosoc (
|
||||
|
||||
|
||||
bus u_bus (
|
||||
.clk_i (clk_i),
|
||||
.rst_n_i (rst_n_i),
|
||||
.clk_i (clk_i),
|
||||
.rst_n_i (rst_n_i),
|
||||
`ifdef HAVE_SRAM_IF
|
||||
.ram (ram),
|
||||
.ram (ram),
|
||||
`endif
|
||||
// master
|
||||
.core_nmi(u_core_nmi_if),
|
||||
.dma_nmi (u_dma_nmi_if),
|
||||
.core_nmi (u_core_nmi_if),
|
||||
.dma_nmi (u_dma_nmi_if),
|
||||
// slave
|
||||
.natv_nmi(u_nmi_nmi_if),
|
||||
.apb_nmi (u_apb_nmi_if)
|
||||
.natv_nmi (u_nmi_nmi_if),
|
||||
.apb_nmi (u_apb_nmi_if),
|
||||
.fault_valid_o (s_bus_fault_valid),
|
||||
.fault_addr_o (s_bus_fault_addr),
|
||||
.fault_wstrb_o (s_bus_fault_wstrb),
|
||||
.fault_reserved_o(s_bus_fault_reserved)
|
||||
);
|
||||
|
||||
|
||||
ip_nmi_wrapper u_ip_nmi_wrapper (
|
||||
.clk_i (clk_i),
|
||||
.rst_n_i (rst_n_i),
|
||||
.clk_aud_i (clk_aud_i),
|
||||
.rst_aud_n_i(rst_aud_n_i),
|
||||
.nmi (u_nmi_nmi_if),
|
||||
.gpio (u_gpio_if),
|
||||
.uart (uart0),
|
||||
.psram (u_psram_if),
|
||||
.spisd (u_spisd_if),
|
||||
.i2c0 (u_i2c0_if),
|
||||
.i2s (u_i2s_if),
|
||||
.onewire (u_onewire_if),
|
||||
.xpi (xpi),
|
||||
.dma_nmi (u_dma_nmi_if),
|
||||
.sysctrl (u_sysctrl_if),
|
||||
.sdram (sdram),
|
||||
.dvp (u_dvp_if),
|
||||
.sdio (u_sdio_if),
|
||||
.opipsram (u_opipsram_if),
|
||||
.i2c1 (u_i2c1_if),
|
||||
.irq_o (s_nmi_irq)
|
||||
.clk_i (clk_i),
|
||||
.rst_n_i (rst_n_i),
|
||||
.clk_aud_i (clk_aud_i),
|
||||
.rst_aud_n_i (rst_aud_n_i),
|
||||
.nmi (u_nmi_nmi_if),
|
||||
.gpio (u_gpio_if),
|
||||
.uart (uart0),
|
||||
.psram (u_psram_if),
|
||||
.spisd (u_spisd_if),
|
||||
.i2c0 (u_i2c0_if),
|
||||
.i2s (u_i2s_if),
|
||||
.onewire (u_onewire_if),
|
||||
.xpi (xpi),
|
||||
.dma_nmi (u_dma_nmi_if),
|
||||
.sysctrl (u_sysctrl_if),
|
||||
.sdram (sdram),
|
||||
.dvp (u_dvp_if),
|
||||
.sdio (u_sdio_if),
|
||||
.opipsram (u_opipsram_if),
|
||||
.i2c1 (u_i2c1_if),
|
||||
.fault_valid_i (s_bus_fault_valid),
|
||||
.fault_addr_i (s_bus_fault_addr),
|
||||
.fault_wstrb_i (s_bus_fault_wstrb),
|
||||
.fault_reserved_i(s_bus_fault_reserved),
|
||||
.irq_o (s_nmi_irq)
|
||||
);
|
||||
|
||||
|
||||
|
||||
+17
-1
@@ -6,6 +6,7 @@ from __future__ import annotations
|
||||
import argparse
|
||||
import shutil
|
||||
import subprocess
|
||||
import sys
|
||||
import tempfile
|
||||
from pathlib import Path
|
||||
|
||||
@@ -37,7 +38,20 @@ def main() -> int:
|
||||
|
||||
root = args.root.resolve()
|
||||
with tempfile.TemporaryDirectory(prefix="retrosoc-c-tests-") as temporary_directory:
|
||||
executable = Path(temporary_directory) / "runtime_tests"
|
||||
temporary_root = Path(temporary_directory)
|
||||
memory_map_root = temporary_root / "memory_map"
|
||||
subprocess.run(
|
||||
[
|
||||
sys.executable,
|
||||
str(root / "rtl/mini/script/generate_memory_map.py"),
|
||||
"--map",
|
||||
str(root / "rtl/mini/memory_map.json"),
|
||||
"--output-dir",
|
||||
str(memory_map_root),
|
||||
],
|
||||
check=True,
|
||||
)
|
||||
executable = temporary_root / "runtime_tests"
|
||||
command = [
|
||||
compiler,
|
||||
"-std=c11",
|
||||
@@ -46,6 +60,8 @@ def main() -> int:
|
||||
"-Werror",
|
||||
"-fno-builtin",
|
||||
"-I",
|
||||
str(memory_map_root / "include"),
|
||||
"-I",
|
||||
str(root / "crt/include"),
|
||||
"-I",
|
||||
str(root / "app/media/include"),
|
||||
|
||||
@@ -0,0 +1,77 @@
|
||||
`timescale 1ns / 1ps
|
||||
|
||||
module bus_fault_tb;
|
||||
logic clk_i = 1'b0;
|
||||
logic rst_n_i = 1'b0;
|
||||
logic fault_valid_o;
|
||||
logic [31:0] fault_addr_o;
|
||||
logic [ 3:0] fault_wstrb_o;
|
||||
logic fault_reserved_o;
|
||||
nmi_if core_nmi ();
|
||||
nmi_if dma_nmi ();
|
||||
nmi_if natv_nmi ();
|
||||
nmi_if apb_nmi ();
|
||||
|
||||
always #5 clk_i = ~clk_i;
|
||||
|
||||
assign natv_nmi.ready = 1'b1;
|
||||
assign natv_nmi.rdata = 32'hCAFE_BABE;
|
||||
assign apb_nmi.ready = 1'b1;
|
||||
assign apb_nmi.rdata = 32'h1234_5678;
|
||||
|
||||
bus u_bus (
|
||||
.clk_i (clk_i),
|
||||
.rst_n_i (rst_n_i),
|
||||
.core_nmi (core_nmi),
|
||||
.dma_nmi (dma_nmi),
|
||||
.natv_nmi (natv_nmi),
|
||||
.apb_nmi (apb_nmi),
|
||||
.fault_valid_o (fault_valid_o),
|
||||
.fault_addr_o (fault_addr_o),
|
||||
.fault_wstrb_o (fault_wstrb_o),
|
||||
.fault_reserved_o(fault_reserved_o)
|
||||
);
|
||||
|
||||
task automatic expect_fault(input logic [31:0] address, input logic [3:0] write_strobes,
|
||||
input logic reserved);
|
||||
begin
|
||||
@(negedge clk_i);
|
||||
core_nmi.addr = address;
|
||||
core_nmi.wdata = 32'hA5A5_5A5A;
|
||||
core_nmi.wstrb = write_strobes;
|
||||
core_nmi.valid = 1'b1;
|
||||
|
||||
while (!fault_valid_o) @(posedge clk_i);
|
||||
if (fault_addr_o !== address || fault_wstrb_o !== write_strobes ||
|
||||
fault_reserved_o !== reserved || natv_nmi.valid || apb_nmi.valid) begin
|
||||
$fatal(1, "unexpected fault response for address %h", address);
|
||||
end
|
||||
while (!core_nmi.ready) @(posedge clk_i);
|
||||
if (core_nmi.rdata !== 32'd0) begin
|
||||
$fatal(1, "fault response data must be zero");
|
||||
end
|
||||
@(negedge clk_i);
|
||||
core_nmi.valid = 1'b0;
|
||||
while (fault_valid_o) @(posedge clk_i);
|
||||
end
|
||||
endtask
|
||||
|
||||
initial begin
|
||||
core_nmi.valid = 1'b0;
|
||||
core_nmi.addr = '0;
|
||||
core_nmi.wdata = '0;
|
||||
core_nmi.wstrb = '0;
|
||||
dma_nmi.valid = 1'b0;
|
||||
dma_nmi.addr = '0;
|
||||
dma_nmi.wdata = '0;
|
||||
dma_nmi.wstrb = '0;
|
||||
|
||||
repeat (2) @(posedge clk_i);
|
||||
rst_n_i = 1'b1;
|
||||
|
||||
expect_fault(32'h1000_F000, 4'hF, 1'b1);
|
||||
expect_fault(32'hA000_0000, 4'h0, 1'b0);
|
||||
$display("bus fault responder test passed");
|
||||
$finish;
|
||||
end
|
||||
endmodule
|
||||
@@ -0,0 +1,86 @@
|
||||
`timescale 1ns / 1ps
|
||||
|
||||
module sysctrl_fault_tb;
|
||||
logic clk_i = 1'b0;
|
||||
logic rst_n_i = 1'b0;
|
||||
logic fault_valid_i = 1'b0;
|
||||
logic [31:0] fault_addr_i = '0;
|
||||
logic [ 3:0] fault_wstrb_i = '0;
|
||||
logic fault_reserved_i = 1'b0;
|
||||
nmi_if nmi ();
|
||||
sysctrl_if sysctrl ();
|
||||
|
||||
always #5 clk_i = ~clk_i;
|
||||
|
||||
nmi_sysctrl u_sysctrl (
|
||||
.clk_i (clk_i),
|
||||
.rst_n_i (rst_n_i),
|
||||
.fault_valid_i (fault_valid_i),
|
||||
.fault_addr_i (fault_addr_i),
|
||||
.fault_wstrb_i (fault_wstrb_i),
|
||||
.fault_reserved_i(fault_reserved_i),
|
||||
.nmi (nmi),
|
||||
.sysctrl (sysctrl)
|
||||
);
|
||||
|
||||
task automatic read_register(input logic [31:0] address, output logic [31:0] data);
|
||||
begin
|
||||
@(negedge clk_i);
|
||||
nmi.addr = address;
|
||||
nmi.wdata = '0;
|
||||
nmi.wstrb = '0;
|
||||
nmi.valid = 1'b1;
|
||||
while (!nmi.ready) @(posedge clk_i);
|
||||
data = nmi.rdata;
|
||||
@(negedge clk_i);
|
||||
nmi.valid = 1'b0;
|
||||
while (nmi.ready) @(posedge clk_i);
|
||||
end
|
||||
endtask
|
||||
|
||||
task automatic write_register(input logic [31:0] address, input logic [31:0] data);
|
||||
begin
|
||||
@(negedge clk_i);
|
||||
nmi.addr = address;
|
||||
nmi.wdata = data;
|
||||
nmi.wstrb = 4'hF;
|
||||
nmi.valid = 1'b1;
|
||||
while (!nmi.ready) @(posedge clk_i);
|
||||
@(negedge clk_i);
|
||||
nmi.valid = 1'b0;
|
||||
while (nmi.ready) @(posedge clk_i);
|
||||
end
|
||||
endtask
|
||||
|
||||
logic [31:0] read_data;
|
||||
initial begin
|
||||
nmi.valid = 1'b0;
|
||||
nmi.addr = '0;
|
||||
nmi.wdata = '0;
|
||||
nmi.wstrb = '0;
|
||||
sysctrl.core_sel_i = '0;
|
||||
repeat (2) @(posedge clk_i);
|
||||
rst_n_i = 1'b1;
|
||||
|
||||
@(negedge clk_i);
|
||||
fault_valid_i = 1'b1;
|
||||
fault_addr_i = 32'h1000_F000;
|
||||
fault_wstrb_i = 4'hF;
|
||||
fault_reserved_i = 1'b1;
|
||||
@(negedge clk_i);
|
||||
fault_valid_i = 1'b0;
|
||||
|
||||
read_register(32'h1000_B010, read_data);
|
||||
if (read_data !== 32'h0000_000B) $fatal(1, "fault status was not recorded");
|
||||
read_register(32'h1000_B014, read_data);
|
||||
if (read_data !== 32'h1000_F000) $fatal(1, "fault address was not recorded");
|
||||
read_register(32'h1000_B018, read_data);
|
||||
if (read_data !== 32'h0000_0001) $fatal(1, "fault count was not incremented");
|
||||
write_register(32'h1000_B010, 32'h0000_0001);
|
||||
read_register(32'h1000_B010, read_data);
|
||||
if (read_data !== 32'h0000_000A) $fatal(1, "fault W1C did not clear pending");
|
||||
|
||||
$display("sysctrl fault registers test passed");
|
||||
$finish;
|
||||
end
|
||||
endmodule
|
||||
@@ -0,0 +1,179 @@
|
||||
"""Tests for the canonical Mini SoC address-map generator."""
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
import json
|
||||
import shutil
|
||||
import subprocess
|
||||
import sys
|
||||
from pathlib import Path
|
||||
|
||||
|
||||
ROOT = Path(__file__).resolve().parents[1]
|
||||
GENERATOR = ROOT / "rtl/mini/script/generate_memory_map.py"
|
||||
MEMORY_MAP = ROOT / "rtl/mini/memory_map.json"
|
||||
|
||||
|
||||
def generate(output_dir: Path, *, ip: str = "NONE", sram: str = "NO") -> None:
|
||||
subprocess.run(
|
||||
[
|
||||
sys.executable,
|
||||
str(GENERATOR),
|
||||
"--map",
|
||||
str(MEMORY_MAP),
|
||||
"--output-dir",
|
||||
str(output_dir),
|
||||
"--have-sram-if",
|
||||
sram,
|
||||
"--ip",
|
||||
ip,
|
||||
],
|
||||
check=True,
|
||||
)
|
||||
|
||||
|
||||
def test_generated_artifacts_share_the_capacity_baseline(tmp_path: Path) -> None:
|
||||
generate(tmp_path, sram="YES")
|
||||
|
||||
rtl = (tmp_path / "rtl/mmap_define.svh").read_text(encoding="utf-8")
|
||||
header = (tmp_path / "include/retrosoc/generated/memory_map.h").read_text(encoding="utf-8")
|
||||
linker = (tmp_path / "linker/memory_regions.ld").read_text(encoding="utf-8")
|
||||
|
||||
assert "`define SOC_ADDR_PSRAM_END 32'h407FFFFF" in rtl
|
||||
assert "`define SOC_ADDR_XPI_END 32'h5FFFFFFF" in rtl
|
||||
assert "`define CPU_RESET_ADDR `SOC_CPU_RESET_ADDR" in rtl
|
||||
assert "`define SOC_ADDR_IS_RESERVED(addr)" in rtl
|
||||
assert "RS_SOC_PSRAM_SIZE UINT32_C(0x00800000)" in header
|
||||
assert "RS_SOC_SDRAM_SIZE UINT32_C(0x02000000)" in header
|
||||
assert "RS_SOC_SPISD_SIZE UINT32_C(0x40000000)" in header
|
||||
assert "RS_SOC_NMI_SDIO_BASE" not in header
|
||||
assert "RS_SOC_OPIPSRAM_BASE" not in header
|
||||
assert "RS_SOC_HAS_SRAM 1U" in header
|
||||
assert "PSRAM (wxa!ri) : ORIGIN = 0x40000000, LENGTH = 0x00800000" in linker
|
||||
|
||||
|
||||
def test_user_ip_is_emitted_only_for_the_matching_profile(tmp_path: Path) -> None:
|
||||
none_output = tmp_path / "none"
|
||||
mdd_output = tmp_path / "mdd"
|
||||
generate(none_output)
|
||||
generate(mdd_output, ip="MDD")
|
||||
|
||||
none_rtl = (none_output / "rtl/mmap_define.svh").read_text(encoding="utf-8")
|
||||
mdd_header = (mdd_output / "include/retrosoc/generated/memory_map.h").read_text(
|
||||
encoding="utf-8"
|
||||
)
|
||||
|
||||
assert "SOC_ADDR_APB_USER_IP_BASE" not in none_rtl
|
||||
assert "RS_SOC_APB_USER_IP_BASE" in mdd_header
|
||||
|
||||
|
||||
def test_map_validation_rejects_overlaps(tmp_path: Path) -> None:
|
||||
document = json.loads(MEMORY_MAP.read_text(encoding="utf-8"))
|
||||
document["regions"][1]["base"] = document["regions"][0]["base"]
|
||||
invalid_map = tmp_path / "overlap.json"
|
||||
invalid_map.write_text(json.dumps(document), encoding="utf-8")
|
||||
|
||||
result = subprocess.run(
|
||||
[sys.executable, str(GENERATOR), "--map", str(invalid_map), "--check"],
|
||||
text=True,
|
||||
capture_output=True,
|
||||
)
|
||||
|
||||
assert result.returncode != 0
|
||||
assert "address-map overlap" in result.stderr
|
||||
|
||||
|
||||
def test_bus_fault_responder_handles_reserved_and_unmapped_addresses(tmp_path: Path) -> None:
|
||||
iverilog = shutil.which("iverilog")
|
||||
vvp = shutil.which("vvp")
|
||||
if iverilog is None or vvp is None:
|
||||
return
|
||||
generate(tmp_path)
|
||||
simulation = tmp_path / "bus_fault_tb"
|
||||
source_list = tmp_path / "bus_fault.fl"
|
||||
source_list.write_text(
|
||||
"\n".join(
|
||||
[
|
||||
"+define+SV_ASSRT_DISABLE",
|
||||
f"+incdir+{tmp_path / 'rtl'}",
|
||||
f"+incdir+{ROOT / 'rtl/clusterip/common/rtl'}",
|
||||
str(ROOT / "rtl/clusterip/common/rtl/interface/nmi_if.sv"),
|
||||
str(ROOT / "rtl/clusterip/common/rtl/utils/register.sv"),
|
||||
str(ROOT / "rtl/ip/native/nmi_regslice.sv"),
|
||||
str(ROOT / "rtl/mini/top/bus.sv"),
|
||||
str(ROOT / "tests/rtl/bus_fault_tb.sv"),
|
||||
"",
|
||||
]
|
||||
),
|
||||
encoding="utf-8",
|
||||
)
|
||||
converted = tmp_path / "bus_fault_tb.v"
|
||||
subprocess.run(
|
||||
[
|
||||
sys.executable,
|
||||
str(ROOT / "rtl/mini/script/convt_sv2v.py"),
|
||||
"-f",
|
||||
str(source_list),
|
||||
"--output",
|
||||
str(converted),
|
||||
],
|
||||
check=True,
|
||||
)
|
||||
subprocess.run(
|
||||
[
|
||||
iverilog,
|
||||
"-g2012",
|
||||
"-s",
|
||||
"bus_fault_tb",
|
||||
"-o",
|
||||
str(simulation),
|
||||
str(converted),
|
||||
],
|
||||
check=True,
|
||||
)
|
||||
result = subprocess.run([vvp, str(simulation)], text=True, capture_output=True, check=True)
|
||||
assert "bus fault responder test passed" in result.stdout
|
||||
|
||||
|
||||
def test_sysctrl_fault_registers_record_and_clear_pending(tmp_path: Path) -> None:
|
||||
iverilog = shutil.which("iverilog")
|
||||
vvp = shutil.which("vvp")
|
||||
if iverilog is None or vvp is None:
|
||||
return
|
||||
generate(tmp_path)
|
||||
source_list = tmp_path / "sysctrl_fault.fl"
|
||||
source_list.write_text(
|
||||
"\n".join(
|
||||
[
|
||||
"+define+SV_ASSRT_DISABLE",
|
||||
f"+incdir+{tmp_path / 'rtl'}",
|
||||
f"+incdir+{ROOT / 'rtl/mini/top'}",
|
||||
f"+incdir+{ROOT / 'rtl/clusterip/common/rtl'}",
|
||||
str(ROOT / "rtl/clusterip/common/rtl/interface/nmi_if.sv"),
|
||||
str(ROOT / "rtl/clusterip/common/rtl/utils/register.sv"),
|
||||
str(ROOT / "rtl/ip/native/sysctrl.sv"),
|
||||
str(ROOT / "tests/rtl/sysctrl_fault_tb.sv"),
|
||||
"",
|
||||
]
|
||||
),
|
||||
encoding="utf-8",
|
||||
)
|
||||
converted = tmp_path / "sysctrl_fault_tb.v"
|
||||
subprocess.run(
|
||||
[
|
||||
sys.executable,
|
||||
str(ROOT / "rtl/mini/script/convt_sv2v.py"),
|
||||
"-f",
|
||||
str(source_list),
|
||||
"--output",
|
||||
str(converted),
|
||||
],
|
||||
check=True,
|
||||
)
|
||||
simulation = tmp_path / "sysctrl_fault_tb"
|
||||
subprocess.run(
|
||||
[iverilog, "-g2012", "-s", "sysctrl_fault_tb", "-o", str(simulation), str(converted)],
|
||||
check=True,
|
||||
)
|
||||
result = subprocess.run([vvp, str(simulation)], text=True, capture_output=True, check=True)
|
||||
assert "sysctrl fault registers test passed" in result.stdout
|
||||
Reference in new issue
Block a user