diff options
author | Ahmad Fatoum <ahmad@a3f.at> | 2022-12-25 22:20:04 +0100 |
---|---|---|
committer | Sascha Hauer <s.hauer@pengutronix.de> | 2023-04-05 08:49:07 +0200 |
commit | 4a6f536e4248e2bdc853250e7b9cbd1badb7cfe6 (patch) | |
tree | a3313dc689fe0a727612e60c5714b8956060911b /arch | |
parent | 4a26017f6dd70c6b0c0fd11d527291058c85cea5 (diff) | |
download | barebox-4a6f536e4248e2bdc853250e7b9cbd1badb7cfe6.tar.gz |
ARM: Rockchip: make bootsource logic generic to all SoCs
Decoding of the bootsource from the register value can be shared across
multiple Rockchip SoCs. Move the code to a common place to allow for
that.
At least with some TF-A versions the IRAM where the bootsource is stored
cannot not be accessed in normal mode, so read it out before we start
the TF-A. For this the scratch space is used.
Signed-off-by: Ahmad Fatoum <ahmad@a3f.at>
Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
Diffstat (limited to 'arch')
-rw-r--r-- | arch/arm/mach-rockchip/Makefile | 2 | ||||
-rw-r--r-- | arch/arm/mach-rockchip/atf.c | 3 | ||||
-rw-r--r-- | arch/arm/mach-rockchip/bootrom.c | 51 | ||||
-rw-r--r-- | arch/arm/mach-rockchip/rk3568.c | 29 |
4 files changed, 57 insertions, 28 deletions
diff --git a/arch/arm/mach-rockchip/Makefile b/arch/arm/mach-rockchip/Makefile index f6c575854e..04d75ce287 100644 --- a/arch/arm/mach-rockchip/Makefile +++ b/arch/arm/mach-rockchip/Makefile @@ -1,6 +1,6 @@ # SPDX-License-Identifier: GPL-2.0-only -obj-y += rockchip.o +obj-y += rockchip.o bootrom.o pbl-$(CONFIG_ARCH_ROCKCHIP_ATF) += atf.o obj-$(CONFIG_ARCH_RK3188) += rk3188.o obj-$(CONFIG_ARCH_RK3288) += rk3288.o diff --git a/arch/arm/mach-rockchip/atf.c b/arch/arm/mach-rockchip/atf.c index 9735cb8ef3..f3fb50b990 100644 --- a/arch/arm/mach-rockchip/atf.c +++ b/arch/arm/mach-rockchip/atf.c @@ -8,6 +8,8 @@ #include <asm/barebox-arm.h> #include <mach/rockchip/dmc.h> #include <mach/rockchip/rockchip.h> +#include <mach/rockchip/bootrom.h> +#include <mach/rockchip/rk3568-regs.h> static unsigned long load_elf64_image_phdr(const void *elf) { @@ -82,6 +84,7 @@ void __noreturn rk3568_barebox_entry(void *fdt) if (current_el() == 3) { rk3568_lowlevel_init(); + rockchip_store_bootrom_iram(membase, memsize, IOMEM(RK3568_IRAM_BASE)); rk3568_atf_load_bl31(fdt); /* not reached when CONFIG_ARCH_ROCKCHIP_ATF */ } diff --git a/arch/arm/mach-rockchip/bootrom.c b/arch/arm/mach-rockchip/bootrom.c new file mode 100644 index 0000000000..cdd0536cda --- /dev/null +++ b/arch/arm/mach-rockchip/bootrom.c @@ -0,0 +1,51 @@ +// SPDX-License-Identifier: GPL-2.0-only +#include <mach/rockchip/bootrom.h> +#include <io.h> +#include <bootsource.h> +#include <linux/bitfield.h> +#include <linux/bitops.h> +#include <linux/kernel.h> +#include <errno.h> + +#define BROM_BOOTSOURCE_ID 0x10 +#define BROM_BOOTSOURCE_SLOT 0x14 +#define BROM_BOOTSOURCE_SLOT_ACTIVE GENMASK(12, 10) + +static const void __iomem *rk_iram; + +int rockchip_bootsource_get_active_slot(void) +{ + if (!rk_iram) + return -EINVAL; + + return FIELD_GET(BROM_BOOTSOURCE_SLOT_ACTIVE, + readl(IOMEM(rk_iram) + BROM_BOOTSOURCE_SLOT)); +} + +struct rk_bootsource { + enum bootsource src; + int instance; +}; + +static struct rk_bootsource bootdev_map[] = { + [0x1] = { .src = BOOTSOURCE_NAND, .instance = 0 }, + [0x2] = { .src = BOOTSOURCE_MMC, .instance = 0 }, + [0x3] = { .src = BOOTSOURCE_SPI_NOR, .instance = 0 }, + [0x4] = { .src = BOOTSOURCE_SPI_NAND, .instance = 0 }, + [0x5] = { .src = BOOTSOURCE_MMC, .instance = 1 }, + [0xa] = { .src = BOOTSOURCE_USB, .instance = 0 }, +}; + +void rockchip_parse_bootrom_iram(const void *iram) +{ + u32 v; + + rk_iram = iram; + + v = readl(iram + BROM_BOOTSOURCE_ID); + + if (v >= ARRAY_SIZE(bootdev_map)) + return; + + bootsource_set(bootdev_map[v].src, bootdev_map[v].instance); +} diff --git a/arch/arm/mach-rockchip/rk3568.c b/arch/arm/mach-rockchip/rk3568.c index 39bd4772a6..c0453ea0c4 100644 --- a/arch/arm/mach-rockchip/rk3568.c +++ b/arch/arm/mach-rockchip/rk3568.c @@ -2,6 +2,7 @@ #include <common.h> #include <io.h> #include <bootsource.h> +#include <mach/rockchip/bootrom.h> #include <mach/rockchip/rk3568-regs.h> #include <mach/rockchip/rockchip.h> @@ -137,35 +138,9 @@ void rk3568_lowlevel_init(void) qos_priority_init(); } -struct rk_bootsource { - enum bootsource src; - int instance; -}; - -static struct rk_bootsource bootdev_map[] = { - [0x1] = { .src = BOOTSOURCE_NAND, .instance = 0 }, - [0x2] = { .src = BOOTSOURCE_MMC, .instance = 0 }, - [0x3] = { .src = BOOTSOURCE_SPI_NOR, .instance = 0 }, - [0x4] = { .src = BOOTSOURCE_SPI_NAND, .instance = 0 }, - [0x5] = { .src = BOOTSOURCE_MMC, .instance = 1 }, - [0xa] = { .src = BOOTSOURCE_USB, .instance = 0 }, -}; - -static void rk3568_bootsource(void) -{ - u32 v; - - v = readl(RK3568_IRAM_BASE + 0x10); - - if (v >= ARRAY_SIZE(bootdev_map)) - return; - - bootsource_set(bootdev_map[v].src, bootdev_map[v].instance); -} - int rk3568_init(void) { - rk3568_bootsource(); + rockchip_parse_bootrom_iram(rockchip_scratch_space()); return 0; } |