From 7a3620b24649663857d99e8ab73ec0b3bd60e50e Mon Sep 17 00:00:00 2001 From: Masahiro Yamada Date: Sat, 6 Dec 2014 00:03:26 +0900 Subject: ARM: UniPhier: detect the number of flash banks at run-time Some UniPhier boards are equipped with an expansion slot that some optional SRAM/NOR-flash cards can be attached to. So, run-time detection of the number of flash banks would be more user-friendly. Until this commit, UniPhier boards have achieved this by (ab)using board_flash_wp_on() because the boot failed if flash_size got zero. Fortunately, this problem was solved by commit 70879a92561a (flash: do not fail even if flash_size is zero). Now it is possible to throw away such a tricky workaround. This commit also enables CONFIG_SYS_MAX_FLASH_BANKS_DETECT for further refactoring. Signed-off-by: Masahiro Yamada --- arch/arm/cpu/armv7/uniphier/Makefile | 1 + arch/arm/cpu/armv7/uniphier/board_early_init_r.c | 15 +++ arch/arm/cpu/armv7/uniphier/support_card.c | 125 +++++++++++++++-------- arch/arm/include/asm/arch-uniphier/board.h | 7 ++ 4 files changed, 108 insertions(+), 40 deletions(-) create mode 100644 arch/arm/cpu/armv7/uniphier/board_early_init_r.c (limited to 'arch') diff --git a/arch/arm/cpu/armv7/uniphier/Makefile b/arch/arm/cpu/armv7/uniphier/Makefile index 0f64d25..4a7b8a9 100644 --- a/arch/arm/cpu/armv7/uniphier/Makefile +++ b/arch/arm/cpu/armv7/uniphier/Makefile @@ -11,6 +11,7 @@ obj-y += cache_uniphier.o obj-$(CONFIG_BOARD_POSTCLK_INIT) += board_postclk_init.o obj-y += dram_init.o obj-$(CONFIG_DISPLAY_CPUINFO) += cpu_info.o +obj-$(CONFIG_BOARD_EARLY_INIT_R) += board_early_init_r.o obj-$(CONFIG_BOARD_LATE_INIT) += board_late_init.o obj-$(CONFIG_UNIPHIER_SMP) += smp.o obj-$(CONFIG_CMD_PINMON) += cmd_pinmon.o diff --git a/arch/arm/cpu/armv7/uniphier/board_early_init_r.c b/arch/arm/cpu/armv7/uniphier/board_early_init_r.c new file mode 100644 index 0000000..cb7e04f --- /dev/null +++ b/arch/arm/cpu/armv7/uniphier/board_early_init_r.c @@ -0,0 +1,15 @@ +/* + * Copyright (C) 2014 Panasonic Corporation + * Author: Masahiro Yamada + * + * SPDX-License-Identifier: GPL-2.0+ + */ + +#include +#include + +int board_early_init_r(void) +{ + uniphier_board_late_init(); + return 0; +} diff --git a/arch/arm/cpu/armv7/uniphier/support_card.c b/arch/arm/cpu/armv7/uniphier/support_card.c index 40d4940..419012e 100644 --- a/arch/arm/cpu/armv7/uniphier/support_card.c +++ b/arch/arm/cpu/armv7/uniphier/support_card.c @@ -83,6 +83,12 @@ static int support_card_show_revision(void) } #endif +int check_support_card(void) +{ + printf("SC: Micro Support Card "); + return support_card_show_revision(); +} + void support_card_init(void) { /* @@ -94,12 +100,6 @@ void support_card_init(void) support_card_reset_deassert(); } -int check_support_card(void) -{ - printf("SC: Micro Support Card "); - return support_card_show_revision(); -} - #if defined(CONFIG_SMC911X) #include @@ -112,18 +112,14 @@ int board_eth_init(bd_t *bis) #if !defined(CONFIG_SYS_NO_FLASH) #include +#include -#if CONFIG_SYS_MAX_FLASH_BANKS > 1 -static phys_addr_t flash_banks_list[CONFIG_SYS_MAX_FLASH_BANKS] = - CONFIG_SYS_FLASH_BANKS_LIST; +struct memory_bank { + phys_addr_t base; + unsigned long size; +}; -phys_addr_t cfi_flash_bank_addr(int i) -{ - return flash_banks_list[i]; -} -#endif - -int mem_is_flash(phys_addr_t base) +static int mem_is_flash(const struct memory_bank *mem) { const int loop = 128; u32 *scratch_addr; @@ -131,8 +127,9 @@ int mem_is_flash(phys_addr_t base) int ret = 1; int i; - scratch_addr = map_physmem(base + 0x01e00000, - sizeof(u32) * loop, MAP_NOCACHE); + /* just in case, use the tail of the memory bank */ + scratch_addr = map_physmem(mem->base + mem->size - sizeof(u32) * loop, + sizeof(u32) * loop, MAP_NOCACHE); for (i = 0; i < loop; i++, scratch_addr++) { saved_value = readl(scratch_addr); @@ -150,31 +147,79 @@ int mem_is_flash(phys_addr_t base) return ret; } -int board_flash_wp_on(void) +#if defined(CONFIG_PFC_MICRO_SUPPORT_CARD) + /* {address, size} */ +static const struct memory_bank memory_banks_boot_swap_off[] = { + {0x02000000, 0x01f00000}, +}; + +static const struct memory_bank memory_banks_boot_swap_on[] = { + {0x00000000, 0x01f00000}, +}; +#endif + +#if defined(CONFIG_DCC_MICRO_SUPPORT_CARD) +static const struct memory_bank memory_banks_boot_swap_off[] = { + {0x04000000, 0x04000000}, +}; + +static const struct memory_bank memory_banks_boot_swap_on[] = { + {0x00000000, 0x04000000}, + {0x04000000, 0x04000000}, +}; +#endif + +static const struct memory_bank +*flash_banks_list[CONFIG_SYS_MAX_FLASH_BANKS_DETECT]; + +phys_addr_t cfi_flash_bank_addr(int i) { - int i; - int ret = 1; + return flash_banks_list[i]->base; +} - for (i = 0; i < CONFIG_SYS_MAX_FLASH_BANKS; i++) { - if (mem_is_flash(cfi_flash_bank_addr(i))) { - /* - * We found at least one flash. - * We need to return 0 and call flash_init(). - */ - ret = 0; - } -#if CONFIG_SYS_MAX_FLASH_BANKS > 1 - else { - /* - * We might have a SRAM here. - * To prevent SRAM data from being destroyed, - * we set dummy address (SDRAM). - */ - flash_banks_list[i] = 0x80000000 + 0x10000 * i; +unsigned long cfi_flash_bank_size(int i) +{ + return flash_banks_list[i]->size; +} + +static void detect_num_flash_banks(void) +{ + const struct memory_bank *memory_bank, *end; + + cfi_flash_num_flash_banks = 0; + + if (boot_is_swapped()) { + memory_bank = memory_banks_boot_swap_on; + end = memory_bank + ARRAY_SIZE(memory_banks_boot_swap_on); + } else { + memory_bank = memory_banks_boot_swap_off; + end = memory_bank + ARRAY_SIZE(memory_banks_boot_swap_off); + } + + for (; memory_bank < end; memory_bank++) { + if (cfi_flash_num_flash_banks >= + CONFIG_SYS_MAX_FLASH_BANKS_DETECT) + break; + + if (mem_is_flash(memory_bank)) { + flash_banks_list[cfi_flash_num_flash_banks] = + memory_bank; + + debug("flash bank found: base = 0x%lx, size = 0x%lx\n", + memory_bank->base, memory_bank->size); + cfi_flash_num_flash_banks++; } -#endif } - return ret; + debug("number of flash banks: %d\n", cfi_flash_num_flash_banks); +} +#else /* ONFIG_SYS_NO_FLASH */ +void detect_num_flash_banks(void) +{ +}; +#endif /* ONFIG_SYS_NO_FLASH */ + +void support_card_late_init(void) +{ + detect_num_flash_banks(); } -#endif diff --git a/arch/arm/include/asm/arch-uniphier/board.h b/arch/arm/include/asm/arch-uniphier/board.h index e6ba4e4..e3cba5b 100644 --- a/arch/arm/include/asm/arch-uniphier/board.h +++ b/arch/arm/include/asm/arch-uniphier/board.h @@ -12,10 +12,12 @@ defined(CONFIG_DCC_MICRO_SUPPORT_CARD) void support_card_reset(void); void support_card_init(void); +void support_card_late_init(void); int check_support_card(void); #else #define support_card_reset() do {} while (0) #define support_card_init() do {} while (0) +#define support_card_late_init() do {} while (0) static inline int check_support_card(void) { return 0; @@ -32,4 +34,9 @@ static inline void uniphier_board_init(void) support_card_init(); } +static inline void uniphier_board_late_init(void) +{ + support_card_late_init(); +} + #endif /* ARCH_BOARD_H */ -- cgit v1.1