diff options
-rw-r--r-- | docs/plat/allwinner.rst | 12 | ||||
-rw-r--r-- | maintainers.rst | 2 | ||||
-rw-r--r-- | plat/allwinner/common/include/platform_def.h | 8 | ||||
-rw-r--r-- | plat/allwinner/common/sunxi_bl31_setup.c | 33 | ||||
-rw-r--r-- | plat/allwinner/common/sunxi_common.c | 21 | ||||
-rw-r--r-- | plat/allwinner/common/sunxi_cpu_ops.c | 8 | ||||
-rw-r--r-- | plat/allwinner/common/sunxi_pm.c | 3 | ||||
-rw-r--r-- | plat/allwinner/common/sunxi_private.h | 1 | ||||
-rw-r--r-- | plat/allwinner/common/sunxi_security.c | 2 | ||||
-rw-r--r-- | plat/allwinner/sun50i_a64/include/sunxi_mmap.h | 1 |
10 files changed, 78 insertions, 13 deletions
diff --git a/docs/plat/allwinner.rst b/docs/plat/allwinner.rst index a7e84a30..825fded4 100644 --- a/docs/plat/allwinner.rst +++ b/docs/plat/allwinner.rst @@ -4,9 +4,11 @@ Trusted Firmware-A for Allwinner ARMv8 SoCs Trusted Firmware-A (TF-A) implements the EL3 firmware layer for Allwinner SoCs with ARMv8 cores. Only BL31 is used to provide proper EL3 setup and PSCI runtime services. + U-Boot's SPL acts as a loader, loading both BL31 and BL33 (typically U-Boot). Loading is done from SD card, eMMC or SPI flash, also via an USB debug interface (FEL). + BL31 lives in SRAM A2, which is documented to be accessible from secure world only. @@ -27,3 +29,13 @@ To build: make CROSS_COMPILE=aarch64-linux-gnu- PLAT=sun50i_a64 DEBUG=1 bl31 .. _U-Boot documentation: http://git.denx.de/?p=u-boot.git;f=board/sunxi/README.sunxi64;hb=HEAD + +Trusted OS dispatcher +===================== + +One can boot Trusted OS(OP-TEE OS, bl32 image) along side bl31 image on Allwinner A64. + +In order to include the 'opteed' dispatcher in the image, pass 'SPD=opteed' on the command line +while compiling the bl31 image and make sure the loader (SPL) loads the Trusted OS binary to +the beginning of DRAM (0x40000000). + diff --git a/maintainers.rst b/maintainers.rst index 94bb5d31..c01d97ad 100644 --- a/maintainers.rst +++ b/maintainers.rst @@ -20,6 +20,8 @@ Allwinner ARMv8 platform port ----------------------------- :M: Andre Przywara <andre.przywara@arm.com> :G: `Andre-ARM`_ +:M: Samuel Holland <samuel@sholland.org> +:G: `smaeul`_ :F: docs/plat/allwinner.rst :F: plat/allwinner/ diff --git a/plat/allwinner/common/include/platform_def.h b/plat/allwinner/common/include/platform_def.h index ca7db2f2..d0391888 100644 --- a/plat/allwinner/common/include/platform_def.h +++ b/plat/allwinner/common/include/platform_def.h @@ -39,7 +39,13 @@ #define PLATFORM_CORE_COUNT (PLATFORM_CLUSTER_COUNT * \ PLATFORM_MAX_CPUS_PER_CLUSTER) #define PLATFORM_MAX_CPUS_PER_CLUSTER 4 -#define PLATFORM_MMAP_REGIONS 4 +#define PLATFORM_MMAP_REGIONS 3 #define PLATFORM_STACK_SIZE (0x1000 / PLATFORM_CORE_COUNT) +#ifndef SPD_none +#ifndef BL32_BASE +#define BL32_BASE SUNXI_DRAM_BASE +#endif +#endif + #endif /* __PLATFORM_DEF_H__ */ diff --git a/plat/allwinner/common/sunxi_bl31_setup.c b/plat/allwinner/common/sunxi_bl31_setup.c index d1f1aa15..e910ee54 100644 --- a/plat/allwinner/common/sunxi_bl31_setup.c +++ b/plat/allwinner/common/sunxi_bl31_setup.c @@ -18,6 +18,7 @@ #include "sunxi_private.h" +static entry_point_info_t bl32_image_ep_info; static entry_point_info_t bl33_image_ep_info; static console_16550_t console; @@ -34,6 +35,13 @@ void bl31_early_platform_setup2(u_register_t arg0, u_register_t arg1, console_16550_register(SUNXI_UART0_BASE, SUNXI_UART0_CLK_IN_HZ, SUNXI_UART0_BAUDRATE, &console); +#ifdef BL32_BASE + /* Populate entry point information for BL32 */ + SET_PARAM_HEAD(&bl32_image_ep_info, PARAM_EP, VERSION_1, 0); + SET_SECURITY_STATE(bl32_image_ep_info.h.attr, SECURE); + bl32_image_ep_info.pc = BL32_BASE; +#endif + /* Populate entry point information for BL33 */ SET_PARAM_HEAD(&bl33_image_ep_info, PARAM_EP, VERSION_1, 0); /* @@ -56,6 +64,22 @@ void bl31_plat_arch_setup(void) void bl31_platform_setup(void) { + const char *soc_name; + uint16_t soc_id = sunxi_read_soc_id(); + + switch (soc_id) { + case 0x1689: + soc_name = "A64/H64/R18"; + break; + case 0x1718: + soc_name = "H5"; + break; + default: + soc_name = "unknown"; + break; + } + NOTICE("BL31: Detected Allwinner %s SoC (%04x)\n", soc_name, soc_id); + generic_delay_timer_init(); /* Configure the interrupt controller */ @@ -72,7 +96,12 @@ void bl31_platform_setup(void) entry_point_info_t *bl31_plat_get_next_image_ep_info(uint32_t type) { assert(sec_state_is_valid(type) != 0); - assert(type == NON_SECURE); - return &bl33_image_ep_info; + if (type == NON_SECURE) + return &bl33_image_ep_info; + + if ((type == SECURE) && bl32_image_ep_info.pc) + return &bl32_image_ep_info; + + return NULL; } diff --git a/plat/allwinner/common/sunxi_common.c b/plat/allwinner/common/sunxi_common.c index e36c8b07..fc9bf209 100644 --- a/plat/allwinner/common/sunxi_common.c +++ b/plat/allwinner/common/sunxi_common.c @@ -4,14 +4,15 @@ * SPDX-License-Identifier: BSD-3-Clause */ +#include <mmio.h> #include <platform.h> #include <platform_def.h> #include <sunxi_def.h> #include <xlat_tables_v2.h> +#include "sunxi_private.h" + static mmap_region_t sunxi_mmap[PLATFORM_MMAP_REGIONS + 1] = { - MAP_REGION_FLAT(SUNXI_ROM_BASE, SUNXI_ROM_SIZE, - MT_MEMORY | MT_RO | MT_SECURE), MAP_REGION_FLAT(SUNXI_SRAM_BASE, SUNXI_SRAM_SIZE, MT_MEMORY | MT_RW | MT_SECURE), MAP_REGION_FLAT(SUNXI_DEV_BASE, SUNXI_DEV_SIZE, @@ -54,3 +55,19 @@ void sunxi_configure_mmu_el3(int flags) enable_mmu_el3(0); } + +#define SRAM_VER_REG (SUNXI_SYSCON_BASE + 0x24) +uint16_t sunxi_read_soc_id(void) +{ + uint32_t reg = mmio_read_32(SRAM_VER_REG); + + /* Set bit 15 to prepare for the SOCID read. */ + mmio_write_32(SRAM_VER_REG, reg | BIT(15)); + + reg = mmio_read_32(SRAM_VER_REG); + + /* deactivate the SOCID access again */ + mmio_write_32(SRAM_VER_REG, reg & ~BIT(15)); + + return reg >> 16; +} diff --git a/plat/allwinner/common/sunxi_cpu_ops.c b/plat/allwinner/common/sunxi_cpu_ops.c index be72dee4..aaee65c6 100644 --- a/plat/allwinner/common/sunxi_cpu_ops.c +++ b/plat/allwinner/common/sunxi_cpu_ops.c @@ -18,7 +18,7 @@ static void sunxi_cpu_disable_power(unsigned int cluster, unsigned int core) if (mmio_read_32(SUNXI_CPU_POWER_CLAMP_REG(cluster, core)) == 0xff) return; - INFO("PSCI: Disabling power to cluster %d core %d\n", cluster, core); + VERBOSE("PSCI: Disabling power to cluster %d core %d\n", cluster, core); mmio_write_32(SUNXI_CPU_POWER_CLAMP_REG(cluster, core), 0xff); } @@ -28,7 +28,7 @@ static void sunxi_cpu_enable_power(unsigned int cluster, unsigned int core) if (mmio_read_32(SUNXI_CPU_POWER_CLAMP_REG(cluster, core)) == 0) return; - INFO("PSCI: Enabling power to cluster %d core %d\n", cluster, core); + VERBOSE("PSCI: Enabling power to cluster %d core %d\n", cluster, core); /* Power enable sequence from original Allwinner sources */ mmio_write_32(SUNXI_CPU_POWER_CLAMP_REG(cluster, core), 0xfe); @@ -40,7 +40,7 @@ static void sunxi_cpu_enable_power(unsigned int cluster, unsigned int core) void sunxi_cpu_off(unsigned int cluster, unsigned int core) { - INFO("PSCI: Powering off cluster %d core %d\n", cluster, core); + VERBOSE("PSCI: Powering off cluster %d core %d\n", cluster, core); /* Deassert DBGPWRDUP */ mmio_clrbits_32(SUNXI_CPUCFG_DBG_REG0, BIT(core)); @@ -54,7 +54,7 @@ void sunxi_cpu_off(unsigned int cluster, unsigned int core) void sunxi_cpu_on(unsigned int cluster, unsigned int core) { - INFO("PSCI: Powering on cluster %d core %d\n", cluster, core); + VERBOSE("PSCI: Powering on cluster %d core %d\n", cluster, core); /* Assert CPU core reset */ mmio_clrbits_32(SUNXI_CPUCFG_RST_CTRL_REG(cluster), BIT(core)); diff --git a/plat/allwinner/common/sunxi_pm.c b/plat/allwinner/common/sunxi_pm.c index fcab130c..2a1f2231 100644 --- a/plat/allwinner/common/sunxi_pm.c +++ b/plat/allwinner/common/sunxi_pm.c @@ -76,8 +76,7 @@ static void __dead2 sunxi_system_reset(void) static int sunxi_validate_ns_entrypoint(uintptr_t ns_entrypoint) { /* The non-secure entry point must be in DRAM */ - if (ns_entrypoint >= SUNXI_DRAM_BASE && - ns_entrypoint < SUNXI_DRAM_BASE + SUNXI_DRAM_SIZE) + if (ns_entrypoint >= SUNXI_DRAM_BASE) return PSCI_E_SUCCESS; return PSCI_E_INVALID_ADDRESS; diff --git a/plat/allwinner/common/sunxi_private.h b/plat/allwinner/common/sunxi_private.h index b9f0fb41..e45f494e 100644 --- a/plat/allwinner/common/sunxi_private.h +++ b/plat/allwinner/common/sunxi_private.h @@ -12,6 +12,7 @@ void sunxi_cpu_off(unsigned int cluster, unsigned int core); void sunxi_cpu_on(unsigned int cluster, unsigned int core); void sunxi_disable_secondary_cpus(unsigned int primary_cpu); +uint16_t sunxi_read_soc_id(void); void sunxi_security_setup(void); #endif /* __SUNXI_PRIVATE_H__ */ diff --git a/plat/allwinner/common/sunxi_security.c b/plat/allwinner/common/sunxi_security.c index e7600728..80fed6ad 100644 --- a/plat/allwinner/common/sunxi_security.c +++ b/plat/allwinner/common/sunxi_security.c @@ -25,9 +25,9 @@ */ void sunxi_security_setup(void) { +#ifdef SUNXI_SPC_BASE int i; -#ifdef SUNXI_SPC_BASE INFO("Configuring SPC Controller\n"); /* SPC setup: set all devices to non-secure */ for (i = 0; i < 6; i++) diff --git a/plat/allwinner/sun50i_a64/include/sunxi_mmap.h b/plat/allwinner/sun50i_a64/include/sunxi_mmap.h index cb202a83..7d46487d 100644 --- a/plat/allwinner/sun50i_a64/include/sunxi_mmap.h +++ b/plat/allwinner/sun50i_a64/include/sunxi_mmap.h @@ -27,7 +27,6 @@ #define SUNXI_CPU_MBIST_BASE 0x01502000 #define SUNXI_CPUCFG_BASE 0x01700000 #define SUNXI_SYSCON_BASE 0x01c00000 -#define SUNXI_SRAM_VER_REG (SUNXI_SYSCON_BASE + 0x24) #define SUNXI_DMA_BASE 0x01c02000 #define SUNXI_KEYMEM_BASE 0x01c0b000 #define SUNXI_SMHC0_BASE 0x01c0f000 |