diff options
Diffstat (limited to 'board/xilinx/versal-net/board.c')
-rw-r--r-- | board/xilinx/versal-net/board.c | 114 |
1 files changed, 114 insertions, 0 deletions
diff --git a/board/xilinx/versal-net/board.c b/board/xilinx/versal-net/board.c index 6724c7290f..6595d6f3e8 100644 --- a/board/xilinx/versal-net/board.c +++ b/board/xilinx/versal-net/board.c @@ -10,6 +10,7 @@ #include <cpu_func.h> #include <fdtdec.h> #include <init.h> +#include <env_internal.h> #include <log.h> #include <malloc.h> #include <time.h> @@ -165,8 +166,32 @@ int board_early_init_r(void) return 0; } +static u8 versal_net_get_bootmode(void) +{ + u8 bootmode; + u32 reg = 0; + + reg = readl(&crp_base->boot_mode_usr); + + if (reg >> BOOT_MODE_ALT_SHIFT) + reg >>= BOOT_MODE_ALT_SHIFT; + + bootmode = reg & BOOT_MODES_MASK; + + return bootmode; +} + int board_late_init(void) { + u8 bootmode; + struct udevice *dev; + int bootseq = -1; + int bootseq_len = 0; + int env_targets_len = 0; + const char *mode; + char *new_targets; + char *env_targets; + if (!(gd->flags & GD_FLG_ENV_DEFAULT)) { debug("Saved variables - Skipping\n"); return 0; @@ -175,6 +200,95 @@ int board_late_init(void) if (!IS_ENABLED(CONFIG_ENV_VARS_UBOOT_RUNTIME_CONFIG)) return 0; + bootmode = versal_net_get_bootmode(); + + puts("Bootmode: "); + switch (bootmode) { + case USB_MODE: + puts("USB_MODE\n"); + mode = "usb_dfu0 usb_dfu1"; + break; + case JTAG_MODE: + puts("JTAG_MODE\n"); + mode = "jtag pxe dhcp"; + break; + case QSPI_MODE_24BIT: + puts("QSPI_MODE_24\n"); + mode = "xspi0"; + break; + case QSPI_MODE_32BIT: + puts("QSPI_MODE_32\n"); + mode = "xspi0"; + break; + case OSPI_MODE: + puts("OSPI_MODE\n"); + mode = "xspi0"; + break; + case EMMC_MODE: + puts("EMMC_MODE\n"); + mode = "mmc"; + bootseq = dev_seq(dev); + break; + case SD_MODE: + puts("SD_MODE\n"); + if (uclass_get_device_by_name(UCLASS_MMC, + "mmc@f1040000", &dev)) { + puts("Boot from SD0 but without SD0 enabled!\n"); + return -1; + } + debug("mmc0 device found at %p, seq %d\n", dev, dev_seq(dev)); + + mode = "mmc"; + bootseq = dev_seq(dev); + break; + case SD1_LSHFT_MODE: + puts("LVL_SHFT_"); + fallthrough; + case SD_MODE1: + puts("SD_MODE1\n"); + if (uclass_get_device_by_name(UCLASS_MMC, + "mmc@f1050000", &dev)) { + puts("Boot from SD1 but without SD1 enabled!\n"); + return -1; + } + debug("mmc1 device found at %p, seq %d\n", dev, dev_seq(dev)); + + mode = "mmc"; + bootseq = dev_seq(dev); + break; + default: + mode = ""; + printf("Invalid Boot Mode:0x%x\n", bootmode); + break; + } + + if (bootseq >= 0) { + bootseq_len = snprintf(NULL, 0, "%i", bootseq); + debug("Bootseq len: %x\n", bootseq_len); + } + + /* + * One terminating char + one byte for space between mode + * and default boot_targets + */ + env_targets = env_get("boot_targets"); + if (env_targets) + env_targets_len = strlen(env_targets); + + new_targets = calloc(1, strlen(mode) + env_targets_len + 2 + + bootseq_len); + if (!new_targets) + return -ENOMEM; + + if (bootseq >= 0) + sprintf(new_targets, "%s%x %s", mode, bootseq, + env_targets ? env_targets : ""); + else + sprintf(new_targets, "%s %s", mode, + env_targets ? env_targets : ""); + + env_set("boot_targets", new_targets); + return board_late_init_xilinx(); } |