X-Git-Url: https://git.sur5r.net/?a=blobdiff_plain;ds=sidebyside;f=env%2Fenv.c;h=9a89832c1aafc79ba4d59536306a0561e84e2db2;hb=3703526f1e0a572b1e8e61dea039348b0f260ae1;hp=14324bbdd207945a63c01f297a5feb7dfd4aea8a;hpb=3574ba019ed626ffa4581ed0a4b0d628ebc048b4;p=u-boot diff --git a/env/env.c b/env/env.c index 14324bbdd2..9a89832c1a 100644 --- a/env/env.c +++ b/env/env.c @@ -26,6 +26,61 @@ static struct env_driver *_env_driver_lookup(enum env_location loc) return NULL; } +static enum env_location env_locations[] = { +#ifdef CONFIG_ENV_IS_IN_EEPROM + ENVL_EEPROM, +#endif +#ifdef CONFIG_ENV_IS_IN_EXT4 + ENVL_EXT4, +#endif +#ifdef CONFIG_ENV_IS_IN_FAT + ENVL_FAT, +#endif +#ifdef CONFIG_ENV_IS_IN_FLASH + ENVL_FLASH, +#endif +#ifdef CONFIG_ENV_IS_IN_MMC + ENVL_MMC, +#endif +#ifdef CONFIG_ENV_IS_IN_NAND + ENVL_NAND, +#endif +#ifdef CONFIG_ENV_IS_IN_NVRAM + ENVL_NVRAM, +#endif +#ifdef CONFIG_ENV_IS_IN_REMOTE + ENVL_REMOTE, +#endif +#ifdef CONFIG_ENV_IS_IN_SPI_FLASH + ENVL_SPI_FLASH, +#endif +#ifdef CONFIG_ENV_IS_IN_UBI + ENVL_UBI, +#endif +#ifdef CONFIG_ENV_IS_NOWHERE + ENVL_NOWHERE, +#endif +}; + +static enum env_location env_load_location = ENVL_UNKNOWN; + +static bool env_has_inited(enum env_location location) +{ + return gd->env_has_init & BIT(location); +} + +static void env_set_inited(enum env_location location) +{ + /* + * We're using a 32-bits bitmask stored in gd (env_has_init) + * using the above enum value as the bit index. We need to + * make sure that we're not overflowing it. + */ + BUILD_BUG_ON(ARRAY_SIZE(env_locations) > BITS_PER_LONG); + + gd->env_has_init |= BIT(location); +} + /** * env_get_location() - Returns the best env location for a board * @op: operations performed on the environment @@ -33,6 +88,7 @@ static struct env_driver *_env_driver_lookup(enum env_location loc) * highest priority * * This will return the preferred environment for the given priority. + * This is overridable by boards if they need to. * * All implementations are free to use the operation, the priority and * any other data relevant to their choice, but must take into account @@ -43,40 +99,23 @@ static struct env_driver *_env_driver_lookup(enum env_location loc) * Returns: * an enum env_location value on success, a negative error code otherwise */ -static enum env_location env_get_location(enum env_operation op, int prio) +__weak enum env_location env_get_location(enum env_operation op, int prio) { - /* - * We support a single environment, so any environment asked - * with a priority that is not zero is out of our supported - * bounds. - */ - if (prio >= 1) - return ENVL_UNKNOWN; - - if IS_ENABLED(CONFIG_ENV_IS_IN_EEPROM) - return ENVL_EEPROM; - else if IS_ENABLED(CONFIG_ENV_IS_IN_FAT) - return ENVL_FAT; - else if IS_ENABLED(CONFIG_ENV_IS_IN_EXT4) - return ENVL_EXT4; - else if IS_ENABLED(CONFIG_ENV_IS_IN_FLASH) - return ENVL_FLASH; - else if IS_ENABLED(CONFIG_ENV_IS_IN_MMC) - return ENVL_MMC; - else if IS_ENABLED(CONFIG_ENV_IS_IN_NAND) - return ENVL_NAND; - else if IS_ENABLED(CONFIG_ENV_IS_IN_NVRAM) - return ENVL_NVRAM; - else if IS_ENABLED(CONFIG_ENV_IS_IN_REMOTE) - return ENVL_REMOTE; - else if IS_ENABLED(CONFIG_ENV_IS_IN_SPI_FLASH) - return ENVL_SPI_FLASH; - else if IS_ENABLED(CONFIG_ENV_IS_IN_UBI) - return ENVL_UBI; - else if IS_ENABLED(CONFIG_ENV_IS_NOWHERE) - return ENVL_NOWHERE; - else - return ENVL_UNKNOWN; + switch (op) { + case ENVOP_GET_CHAR: + case ENVOP_INIT: + case ENVOP_LOAD: + if (prio >= ARRAY_SIZE(env_locations)) + return ENVL_UNKNOWN; + + env_load_location = env_locations[prio]; + return env_load_location; + + case ENVOP_SAVE: + return env_load_location; + } + + return ENVL_UNKNOWN; } @@ -124,6 +163,9 @@ int env_get_char(int index) if (!drv->get_char) continue; + if (!env_has_inited(drv->location)) + continue; + ret = drv->get_char(index); if (!ret) return 0; @@ -146,6 +188,9 @@ int env_load(void) if (!drv->load) continue; + if (!env_has_inited(drv->location)) + continue; + printf("Loading Environment from %s... ", drv->name); ret = drv->load(); if (ret) @@ -171,6 +216,9 @@ int env_save(void) if (!drv->save) continue; + if (!env_has_inited(drv->location)) + continue; + printf("Saving Environment to %s... ", drv->name); ret = drv->save(); if (ret) @@ -192,14 +240,10 @@ int env_init(void) int prio; for (prio = 0; (drv = env_driver_lookup(ENVOP_INIT, prio)); prio++) { - if (!drv->init) - continue; - - ret = drv->init(); - if (!ret) - return 0; + if (!drv->init || !(ret = drv->init())) + env_set_inited(drv->location); - debug("%s: Environment %s failed to init (err=%d)\n", __func__, + debug("%s: Environment %s init done (ret=%d)\n", __func__, drv->name, ret); }