From da1841647ba2f95fd221fc5e5b259bb89f384f56 Mon Sep 17 00:00:00 2001 From: Akila N Date: Tue, 5 Apr 2016 22:31:28 +0530 Subject: [PATCH] qca: ipq40xx: Configure u-boot environment in nand Change-Id: Ic7849ca28adcebf24f376900abd22e409194cd3e Signed-off-by: Akila N --- board/qca/ipq40xx/ipq40xx.c | 77 ++++++++++++++++++++++++++++++++++++- common/env_nand.c | 40 ++++++++++--------- include/common.h | 4 ++ include/configs/ipq40xx.h | 16 +++++++- 4 files changed, 116 insertions(+), 21 deletions(-) diff --git a/board/qca/ipq40xx/ipq40xx.c b/board/qca/ipq40xx/ipq40xx.c index fe150cde9d..8b98ce9815 100644 --- a/board/qca/ipq40xx/ipq40xx.c +++ b/board/qca/ipq40xx/ipq40xx.c @@ -19,6 +19,7 @@ #include #include "ipq40xx.h" #include "ipq40xx_board_param.h" +#include #include #include @@ -27,7 +28,15 @@ DECLARE_GLOBAL_DATA_PTR; loff_t board_env_offset; loff_t board_env_range; loff_t board_env_size; - +extern int nand_env_device; +char *env_name_spec; +extern char *nand_env_name_spec; +int (*saveenv)(void); +env_t *env_ptr; +extern env_t *nand_env_ptr; +extern int nand_env_init(void); +extern int nand_saveenv(void); +extern void nand_env_relocate_spec(void); /* * Don't have this as a '.bss' variable. The '.bss' and '.rel.dyn' * sections seem to overlap. @@ -82,6 +91,47 @@ static board_ipq40xx_params_t *get_board_param(unsigned int machid) for (;;); } +int env_init(void) +{ + int ret; + qca_smem_flash_info_t sfi; + + smem_get_boot_flash(&sfi.flash_type, + &sfi.flash_index, + &sfi.flash_chip_select, + &sfi.flash_block_size, + &sfi.flash_density); + + if (sfi.flash_type != SMEM_BOOT_MMC_FLASH) { + ret = nand_env_init(); +#ifdef CONFIG_QCA_MMC + } else { + ret = mmc_env_init(); +#endif + } + + return ret; +} + +void env_relocate_spec(void) +{ + qca_smem_flash_info_t sfi; + + smem_get_boot_flash(&sfi.flash_type, + &sfi.flash_index, + &sfi.flash_chip_select, + &sfi.flash_block_size, + &sfi.flash_density); + + if (sfi.flash_type != SMEM_BOOT_MMC_FLASH) { + nand_env_relocate_spec(); +#ifdef CONFIG_QCA_MMC + } else { + mmc_env_relocate_spec(); +#endif + } + +}; int board_init(void) { @@ -116,6 +166,15 @@ int board_init(void) } } + if (sfi->flash_type == SMEM_BOOT_NAND_FLASH) { + nand_env_device = CONFIG_QPIC_NAND_NAND_INFO_IDX; + } else if (sfi->flash_type == SMEM_BOOT_SPI_FLASH) { + nand_env_device = CONFIG_IPQ_SPI_NOR_INFO_IDX; + } else if (sfi->flash_type != SMEM_BOOT_MMC_FLASH) { + printf("BUG: unsupported flash type : %d\n", sfi->flash_type); + BUG(); + } + if (sfi->flash_type != SMEM_BOOT_MMC_FLASH) { ret = smem_getpart("0:APPSBLENV", &start_blocks, &size_blocks); if (ret < 0) { @@ -141,6 +200,18 @@ int board_init(void) printf("BUG: unsupported flash type : %d\n", sfi->flash_type); BUG(); } + + if (sfi->flash_type != SMEM_BOOT_MMC_FLASH) { + saveenv = nand_saveenv; + env_ptr = nand_env_ptr; + env_name_spec = nand_env_name_spec; +#ifdef CONFIG_QCA_MMC + } else { + saveenv = mmc_saveenv; + env_ptr = mmc_env_ptr; + env_name_spec = mmc_env_name_spec; +#endif + } return 0; } @@ -239,6 +310,10 @@ int dram_init(void) return 0; } +void board_nand_init(void) +{ +} + int board_eth_init(bd_t *bis) { return 0; diff --git a/common/env_nand.c b/common/env_nand.c index b32eeac9d7..8a8aa8bf39 100644 --- a/common/env_nand.c +++ b/common/env_nand.c @@ -39,18 +39,19 @@ #define CONFIG_ENV_RANGE CONFIG_ENV_SIZE #endif -char *env_name_spec = "NAND"; +char *nand_env_name_spec = "NAND"; #if defined(ENV_IS_EMBEDDED) -env_t *env_ptr = &environment; +env_t *nand_env_ptr = &environment; #elif defined(CONFIG_NAND_ENV_DST) -env_t *env_ptr = (env_t *)CONFIG_NAND_ENV_DST; +env_t *nand_env_ptr = (env_t *)CONFIG_NAND_ENV_DST; #else /* ! ENV_IS_EMBEDDED */ -env_t *env_ptr; +env_t *nand_env_ptr; #endif /* ENV_IS_EMBEDDED */ DECLARE_GLOBAL_DATA_PTR; +int nand_env_device = 0; /* * This is called before nand_init() so we can't read NAND to * validate env data. @@ -63,7 +64,7 @@ DECLARE_GLOBAL_DATA_PTR; * This way the SPL loads not only the U-Boot image from NAND but * also the environment. */ -int env_init(void) +int nand_env_init(void) { #if defined(ENV_IS_EMBEDDED) || defined(CONFIG_NAND_ENV_DST) int crc1_ok = 0, crc2_ok = 0; @@ -132,15 +133,16 @@ static int writeenv(size_t offset, u_char *buf) size_t blocksize, len; u_char *char_ptr; - blocksize = nand_info[0].erasesize; + blocksize = nand_info[nand_env_device].erasesize; len = min(blocksize, (size_t)CONFIG_ENV_SIZE); while (amount_saved < CONFIG_ENV_SIZE && offset < end) { - if (nand_block_isbad(&nand_info[0], offset)) { + if (nand_block_isbad(&nand_info[nand_env_device], offset)) { offset += blocksize; } else { char_ptr = &buf[amount_saved]; - if (nand_write(&nand_info[0], offset, &len, char_ptr)) + if (nand_write(&nand_info[nand_env_device], + offset, &len, char_ptr)) return 1; offset += blocksize; @@ -155,7 +157,7 @@ static int writeenv(size_t offset, u_char *buf) struct env_location { const char *name; - const nand_erase_options_t erase_opts; + nand_erase_options_t erase_opts; }; static int erase_and_write_env(const struct env_location *location, @@ -164,7 +166,7 @@ static int erase_and_write_env(const struct env_location *location, int ret = 0; printf("Erasing %s...\n", location->name); - if (nand_erase_opts(&nand_info[0], &location->erase_opts)) + if (nand_erase_opts(&nand_info[nand_env_device], &location->erase_opts)) return 1; printf("Writing to %s... ", location->name); @@ -178,12 +180,12 @@ static int erase_and_write_env(const struct env_location *location, static unsigned char env_flags; #endif -int saveenv(void) +int nand_saveenv(void) { int ret = 0; ALLOC_CACHE_ALIGN_BUFFER(env_t, env_new, 1); int env_idx = 0; - static const struct env_location location[] = { + struct env_location location[] = { { .name = "NAND", .erase_opts = { @@ -247,20 +249,20 @@ static int readenv(size_t offset, u_char *buf) size_t blocksize, len; u_char *char_ptr; - blocksize = nand_info[0].erasesize; + blocksize = nand_info[nand_env_device].erasesize; if (!blocksize) return 1; len = min(blocksize, (size_t)CONFIG_ENV_SIZE); while (amount_loaded < CONFIG_ENV_SIZE && offset < end) { - if (nand_block_isbad(&nand_info[0], offset)) { + if (nand_block_isbad(&nand_info[nand_env_device], offset)) { offset += blocksize; } else { char_ptr = &buf[amount_loaded]; - if (nand_read_skip_bad(&nand_info[0], offset, + if (nand_read_skip_bad(&nand_info[nand_env_device], offset, &len, NULL, - nand_info[0].size, char_ptr)) + nand_info[nand_env_device].size, char_ptr)) return 1; offset += blocksize; @@ -308,7 +310,7 @@ int get_nand_env_oob(nand_info_t *nand, unsigned long *result) #endif #ifdef CONFIG_ENV_OFFSET_REDUND -void env_relocate_spec(void) +void nand_env_relocate_spec(void) { #if !defined(ENV_IS_EMBEDDED) int read1_fail = 0, read2_fail = 0; @@ -380,14 +382,14 @@ done: * device i.e., nand_dev_desc + 0. This is also the behaviour using * the new NAND code. */ -void env_relocate_spec(void) +void nand_env_relocate_spec(void) { #if !defined(ENV_IS_EMBEDDED) int ret; ALLOC_CACHE_ALIGN_BUFFER(char, buf, CONFIG_ENV_SIZE); #if defined(CONFIG_ENV_OFFSET_OOB) - ret = get_nand_env_oob(&nand_info[0], &nand_env_oob_offset); + ret = get_nand_env_oob(&nand_info[nand_env_device], &nand_env_oob_offset); /* * If unable to read environment offset from NAND OOB then fall through * to the normal environment reading code below diff --git a/include/common.h b/include/common.h index 75c78d5ac2..17e4b07a43 100644 --- a/include/common.h +++ b/include/common.h @@ -386,7 +386,11 @@ ulong getenv_hex(const char *varname, ulong default_val); * Return -1 if variable does not exist (default to true) */ int getenv_yesno(const char *var); +#ifdef CONFIG_IPQ40XX_ENV +extern int (*saveenv)(void); +#else int saveenv (void); +#endif int setenv (const char *, const char *); int setenv_ulong(const char *varname, ulong value); int setenv_hex(const char *varname, ulong value); diff --git a/include/configs/ipq40xx.h b/include/configs/ipq40xx.h index f7443a969c..c9b87ab8ae 100644 --- a/include/configs/ipq40xx.h +++ b/include/configs/ipq40xx.h @@ -30,7 +30,6 @@ #define CONFIG_SYS_CACHELINE_SIZE 64 #define CONFIG_SKIP_LOWLEVEL_INIT #define CONFIG_SYS_HZ 1000 -#define CONFIG_ENV_IS_NOWHERE 1 #define CONFIG_IPQ40XX_UART #define CONFIG_CONS_INDEX 1 @@ -56,6 +55,8 @@ #define CONFIG_IPQ_APPSBL_IMG_TYPE 0x5 +#define CONFIG_IPQ40XX_ENV +#define CONFIG_ENV_IS_IN_NAND #define CONFIG_EXTRA_ENV_SETTINGS \ "fdtcontroladdr=0x84000000\0" @@ -114,6 +115,19 @@ typedef struct { * size is configured to 64 */ #define CONFIG_SYS_CACHELINE_SIZE 64 +#define CONFIG_CMD_NAND + +#define CONFIG_SYS_MAX_NAND_DEVICE (CONFIG_IPQ_MAX_NAND_DEVICE + \ + CONFIG_IPQ_MAX_SPI_DEVICE) + +#define CONFIG_IPQ_MAX_SPI_DEVICE 2 +#define CONFIG_IPQ_MAX_NAND_DEVICE 1 + +#define CONFIG_SYS_NAND_SELF_INIT +#define CONFIG_IPQ_NAND_NAND_INFO_IDX 0 +#define CONFIG_QPIC_NAND_NAND_INFO_IDX 0 +#define CONFIG_IPQ_SPI_NAND_INFO_IDX 1 +#define CONFIG_IPQ_SPI_NOR_INFO_IDX 2 /* * SPI Flash Configs */