diff options
author | Ovidiu Panait <ovpanait@gmail.com> | 2022-05-31 21:14:31 +0300 |
---|---|---|
committer | Michal Simek <michal.simek@amd.com> | 2022-06-24 14:16:00 +0200 |
commit | 95b7a8fd128aec8214d13b33131a4ea1fa4cc9a3 (patch) | |
tree | b3686f51bf152049642c884e67f912e8d6a47f21 | |
parent | b195134984ec714f92632704e4725ced170ab1da (diff) | |
download | u-boot-95b7a8fd128aec8214d13b33131a4ea1fa4cc9a3.zip u-boot-95b7a8fd128aec8214d13b33131a4ea1fa4cc9a3.tar.gz u-boot-95b7a8fd128aec8214d13b33131a4ea1fa4cc9a3.tar.bz2 |
microblaze: cache: introduce cpuinfo structure
Introduce a minimal cpuinfo structure to hold cache related info. The
instruction/data cache size and cache line size are initialized early in
the boot to default Kconfig values. They will be overwritten with data
from PVR/dtb if the microblaze UCLASS_CPU driver is enabled.
The cpuinfo struct was placed in global_data to allow the microblaze
UCLASS_CPU driver to also run before relocation (initialized global data
should be read-only before relocation).
gd_cpuinfo() helper macro was added to avoid volatile
"-Wdiscarded-qualifiers" warnings when using the pointer directly.
Signed-off-by: Ovidiu Panait <ovpanait@gmail.com>
Link: https://lore.kernel.org/r/20220531181435.3473549-10-ovpanait@gmail.com
Signed-off-by: Michal Simek <michal.simek@amd.com> (s/bralid/brlid/)
-rw-r--r-- | arch/microblaze/cpu/Makefile | 2 | ||||
-rw-r--r-- | arch/microblaze/cpu/cache.c | 14 | ||||
-rw-r--r-- | arch/microblaze/cpu/cpuinfo.c | 20 | ||||
-rw-r--r-- | arch/microblaze/cpu/start.S | 7 | ||||
-rw-r--r-- | arch/microblaze/include/asm/cpuinfo.h | 35 | ||||
-rw-r--r-- | arch/microblaze/include/asm/global_data.h | 5 |
6 files changed, 78 insertions, 5 deletions
diff --git a/arch/microblaze/cpu/Makefile b/arch/microblaze/cpu/Makefile index 1feffc6..78d7f83 100644 --- a/arch/microblaze/cpu/Makefile +++ b/arch/microblaze/cpu/Makefile @@ -5,6 +5,6 @@ extra-y = start.o obj-y = irq.o -obj-y += interrupts.o cache.o exception.o timer.o +obj-y += interrupts.o cache.o exception.o timer.o cpuinfo.o obj-$(CONFIG_STATIC_RELA) += relocate.o obj-$(CONFIG_SPL_BUILD) += spl.o diff --git a/arch/microblaze/cpu/cache.c b/arch/microblaze/cpu/cache.c index b99b8c1..cd85079 100644 --- a/arch/microblaze/cpu/cache.c +++ b/arch/microblaze/cpu/cache.c @@ -9,11 +9,16 @@ #include <cpu_func.h> #include <asm/asm.h> #include <asm/cache.h> +#include <asm/cpuinfo.h> +#include <asm/global_data.h> + +DECLARE_GLOBAL_DATA_PTR; static void __invalidate_icache(ulong addr, ulong size) { if (CONFIG_IS_ENABLED(XILINX_MICROBLAZE0_USE_WIC)) { - for (int i = 0; i < size; i += 4) { + for (int i = 0; i < size; + i += gd_cpuinfo()->icache_line_length) { asm volatile ( "wic %0, r0;" "nop;" @@ -26,13 +31,14 @@ static void __invalidate_icache(ulong addr, ulong size) void invalidate_icache_all(void) { - __invalidate_icache(0, CONFIG_XILINX_MICROBLAZE0_ICACHE_SIZE); + __invalidate_icache(0, gd_cpuinfo()->icache_size); } static void __flush_dcache(ulong addr, ulong size) { if (CONFIG_IS_ENABLED(XILINX_MICROBLAZE0_USE_WDC)) { - for (int i = 0; i < size; i += 4) { + for (int i = 0; i < size; + i += gd_cpuinfo()->dcache_line_length) { asm volatile ( "wdc.flush %0, r0;" "nop;" @@ -45,7 +51,7 @@ static void __flush_dcache(ulong addr, ulong size) void flush_dcache_all(void) { - __flush_dcache(0, CONFIG_XILINX_MICROBLAZE0_DCACHE_SIZE); + __flush_dcache(0, gd_cpuinfo()->dcache_size); } int dcache_status(void) diff --git a/arch/microblaze/cpu/cpuinfo.c b/arch/microblaze/cpu/cpuinfo.c new file mode 100644 index 0000000..3f0b1d2 --- /dev/null +++ b/arch/microblaze/cpu/cpuinfo.c @@ -0,0 +1,20 @@ +// SPDX-License-Identifier: GPL-2.0+ +/* + * Copyright (C) 2022, Ovidiu Panait <ovpanait@gmail.com> + */ +#include <common.h> +#include <asm/cpuinfo.h> +#include <asm/global_data.h> + +DECLARE_GLOBAL_DATA_PTR; + +void microblaze_early_cpuinfo_init(void) +{ + struct microblaze_cpuinfo *ci = gd_cpuinfo(); + + ci->icache_size = CONFIG_XILINX_MICROBLAZE0_ICACHE_SIZE; + ci->icache_line_length = 4; + + ci->dcache_size = CONFIG_XILINX_MICROBLAZE0_DCACHE_SIZE; + ci->dcache_line_length = 4; +} diff --git a/arch/microblaze/cpu/start.S b/arch/microblaze/cpu/start.S index e6a30e8..de95270 100644 --- a/arch/microblaze/cpu/start.S +++ b/arch/microblaze/cpu/start.S @@ -97,6 +97,13 @@ uboot_sym_start: nop #endif + /* + * Initialize global data cpuinfo with default values (cache + * size, cache line size, etc). + */ + brlid r15, microblaze_early_cpuinfo_init + nop + /* Flush cache before enable cache */ brlid r15, flush_cache_all nop diff --git a/arch/microblaze/include/asm/cpuinfo.h b/arch/microblaze/include/asm/cpuinfo.h new file mode 100644 index 0000000..c27dd40 --- /dev/null +++ b/arch/microblaze/include/asm/cpuinfo.h @@ -0,0 +1,35 @@ +/* SPDX-License-Identifier: GPL-2.0+ */ +/* + * Copyright (C) 2022, Ovidiu Panait <ovpanait@gmail.com> + */ + +#ifndef __ASM_MICROBLAZE_CPUINFO_H +#define __ASM_MICROBLAZE_CPUINFO_H + +/** + * struct microblaze_cpuinfo - CPU info for microblaze processor core. + * + * @icache_size: Size of instruction cache memory in bytes. + * @icache_line_length: Instruction cache line length in bytes. + * @dcache_size: Size of data cache memory in bytes. + * @dcache_line_length: Data cache line length in bytes. + */ +struct microblaze_cpuinfo { + u32 icache_size; + u32 icache_line_length; + + u32 dcache_size; + u32 dcache_line_length; +}; + +/** + * microblaze_early_cpuinfo_init() - Initialize cpuinfo with default values. + * + * Initializes the global data cpuinfo structure with default values (cache + * size, cache line size, etc.). It is called very early in the boot process + * (start.S codepath right before the first cache flush call) to ensure that + * cache related operations are properly handled. + */ +void microblaze_early_cpuinfo_init(void); + +#endif /* __ASM_MICROBLAZE_CPUINFO_H */ diff --git a/arch/microblaze/include/asm/global_data.h b/arch/microblaze/include/asm/global_data.h index 05868ac..93506de 100644 --- a/arch/microblaze/include/asm/global_data.h +++ b/arch/microblaze/include/asm/global_data.h @@ -8,12 +8,17 @@ #ifndef __ASM_GBL_DATA_H #define __ASM_GBL_DATA_H +#include <asm/cpuinfo.h> + /* Architecture-specific global data */ struct arch_global_data { + struct microblaze_cpuinfo cpuinfo; }; #include <asm-generic/global_data.h> #define DECLARE_GLOBAL_DATA_PTR register volatile gd_t *gd asm ("r31") +#define gd_cpuinfo() ((struct microblaze_cpuinfo *)&gd->arch.cpuinfo) + #endif /* __ASM_GBL_DATA_H */ |