[U-Boot] [PATCH v1 1/3] add boot_get_loadables() to load listed images

Karl Apsite
2015-05-13T12:53:58Z

From: Karl Apsite <karl.apsite@dornerworks.com>

Added a trimmed down instance of boot_get_<thing>() to satisfy the
minimum requierments of the added feature. The function follows the
normal patterns set by other boot_get<thing>'s, which should make it a
bit easier to combine them all together into one boot_get_image()
function in a later refactor.

Documentation for the new function can be found in source:
common/image.c

Signed-off-by: Karl Apsite <Karl.Apsite@dornerworks.com>
---

common/bootm.c | 22 +++++++++++++
common/image-fit.c | 8 ++++-
common/image.c | 93 +++++++++++++++++++++++++++++++++++++++++++++++++++++
include/bootstage.h | 1 +
include/image.h | 5 ++-
5 files changed, 127 insertions(+), 2 deletions(-)

diff --git a/common/bootm.c b/common/bootm.c
index 6842029..f04e49b 100644
--- a/common/bootm.c
+++ b/common/bootm.c
@@ -240,6 +240,23 @@ static int bootm_find_fdt(int flag, int argc, char * const argv[])
}
#endif

+#if defined(CONFIG_FIT)
+static int bootm_find_loadables(int flag, int argc, char * const argv[])
+{
+ int ret;
+
+ /* find all of the loadables */
+ ret = boot_get_loadable(argc, argv, &images, IH_ARCH_DEFAULT,
+ NULL, NULL);
+ if (ret) {
+ puts("Loadable(s) is corrupt or invalid\n");
+ return 1;
+ }
+
+ return 0;
+}
+#endif
+
int bootm_find_ramdisk_fdt(int flag, int argc, char * const argv[])
{
if (bootm_find_ramdisk(flag, argc, argv))
@@ -250,6 +267,11 @@ int bootm_find_ramdisk_fdt(int flag, int argc, char * const argv[])
return 1;
#endif

+#if defined(CONFIG_FIT)
+ if (bootm_find_loadables(flag, argc, argv))
+ return 1;
+#endif
+
return 0;
}

diff --git a/common/image-fit.c b/common/image-fit.c
index 245264d..fe23c13 100644
--- a/common/image-fit.c
+++ b/common/image-fit.c
@@ -1544,6 +1544,8 @@ static const char *fit_get_image_type_property(int type)
return FIT_RAMDISK_PROP;
case IH_TYPE_X86_SETUP:
return FIT_SETUP_PROP;
+ case IH_TYPE_LOADABLE:
+ return FIT_LOADABLE_PROP;
}

return "unknown";
@@ -1661,7 +1663,11 @@ int fit_image_load(bootm_headers_t *images, ulong addr,
os_ok = image_type == IH_TYPE_FLATDT ||
fit_image_check_os(fit, noffset, IH_OS_LINUX) ||
fit_image_check_os(fit, noffset, IH_OS_OPENRTOS);
- if (!type_ok || !os_ok) {
+
+ /* If either of the checks fail, we should report an error, but
+ * if the image type is coming from the "loadables" field, we
+ * don't care about what it is */
+ if ((!type_ok || !os_ok) && image_type != IH_TYPE_LOADABLE) {
fit_image_get_os(fit, noffset, &os);
printf("No %s %s %s Image\n",
genimg_get_os_name(os),
diff --git a/common/image.c b/common/image.c
index fdec496..dc7e795 100644
--- a/common/image.c
+++ b/common/image.c
@@ -1165,6 +1165,99 @@ int boot_get_setup(bootm_headers_t *images, uint8_t arch,
#endif
}

+/**
+ * boot_get_loadable - routine to load a list of binaries to memory
+ * @argc: Ignored Argument
+ * @argv: Ignored Argument
+ * @images: pointer to the bootm images structure
+ * @arch: expected architecture for the image
+ * @ld_start: Ignored Argument
+ * @ld_len: Ignored Argument
+ *
+ * boot_get_loadable() will take the given FIT configuration, and look
+ * for a field named "loadables". Loadables, is a list of elements in
+ * the FIT given as strings. exe:
+ * loadables = "linux_kernel at 1", "fdt at 2";
+ * this function will attempt to parse each string, and load the
+ * corresponding element from the FIT into memory. Once placed,
+ * no aditional actions are taken.
+ *
+ * returns:
+ * 0, if only valid images or no images are found
+ * error code, if an error occurs during fit_image_load
+ */
+#if defined(CONFIG_FIT)
+int boot_get_loadable(int argc, char * const argv[], bootm_headers_t *images,
+ uint8_t arch, const ulong *ld_start, ulong * const ld_len)
+{
+ /*
+ * These variabels are used to hold the current image location
+ * in system memory.
+ */
+ ulong tmp_img_addr;
+ /* These are not used */
+ ulong img_data, img_len;
+ void *buf;
+ char *uname;
+ char *uname_end;
+ int len, fit_img_result;
+ /* Check to see if the images struct has a FIT configuration */
+ if (genimg_has_config(images)) {
+ /*
+ * Obtain the os FIT header from the images struct
+ * copy from dataflash if needed
+ */
+ tmp_img_addr = map_to_sysmem(images->fit_hdr_os);
+ tmp_img_addr = genimg_get_image(tmp_img_addr);
+ buf = map_sysmem(tmp_img_addr, 0);
+ /*
+ * Check image type. For FIT images get FIT node
+ * and attempt to locate a generic binary.
+ */
+ switch (genimg_get_format(buf)) {
+ case IMAGE_FORMAT_FIT:
+ /*
+ * Try to obtain the 'loadables' field from the
+ * configuration If it exists, then try and load
+ * all of the listed strings
+ *
+ * This logic assumes a character is one byte
+ */
+ uname = (char *)fdt_getprop(buf,
+ fit_conf_get_node(buf, images->fit_uname_cfg),
+ FIT_LOADABLE_PROP, &len);
+ uname_end = uname + len;
+ if (NULL != uname) {
+ do {
+ fit_img_result = fit_image_load(images,
+ tmp_img_addr,
+ (const char **)&uname,
+ &(images->fit_uname_cfg), arch,
+ IH_TYPE_LOADABLE,
+ BOOTSTAGE_ID_FIT_LOADS_START,
+ FIT_LOAD_OPTIONAL_NON_ZERO,
+ &img_data, &img_len);
+ if (fit_img_result < 0) {
+ /* Something went wrong! */
+ return fit_img_result;
+ }
+ uname += strnlen(uname,
+ uname_end - uname) + 1;
+ } while (uname < uname_end);
+ }
+ break;
+ default:
+ puts("The given image format is not supported (corrupt?)\n");
+ return 1;
+ }
+ } else {
+ debug("## FIT configuration was not specified\n");
+ }
+
+ return 0;
+}
+#endif
+
#ifdef CONFIG_SYS_BOOT_GET_CMDLINE
/**
* boot_get_cmdline - allocate and initialize kernel cmdline
diff --git a/include/bootstage.h b/include/bootstage.h
index be44014..4e2e0fb 100644
--- a/include/bootstage.h
+++ b/include/bootstage.h
@@ -168,6 +168,7 @@ enum bootstage_id {
BOOTSTAGE_ID_NAND_FIT_READ = 150,
BOOTSTAGE_ID_NAND_FIT_READ_OK,

+ BOOTSTAGE_ID_FIT_LOADS_START = 160, /* for Loadable Images */
/*
* These boot stages are new, higher level, and not directly related
* to the old boot progress numbers. They are useful for recording
diff --git a/include/image.h b/include/image.h
index 97b96b3..0b0b55b 100644
--- a/include/image.h
+++ b/include/image.h
@@ -244,6 +244,7 @@ struct lmb;
#define IH_TYPE_SOCFPGAIMAGE 19 /* Altera SOCFPGA Preloader */
#define IH_TYPE_X86_SETUP 20 /* x86 setup.bin Image */
#define IH_TYPE_LPC32XXIMAGE 21 /* x86 setup.bin Image */
+#define IH_TYPE_LOADABLE 22 /* A list of typeless images */

/*
* Compression Types
@@ -455,7 +456,9 @@ ulong genimg_get_image(ulong img_addr);

int boot_get_ramdisk(int argc, char * const argv[], bootm_headers_t *images,
uint8_t arch, ulong *rd_start, ulong *rd_end);
-#endif
+int boot_get_loadable(int argc, char * const argv[], bootm_headers_t *images,
+ uint8_t arch, const ulong *ld_start, ulong * const ld_len);
+#endif /* !USE_HOSTCC */

int boot_get_setup_fit(bootm_headers_t *images, uint8_t arch,
ulong *setup_start, ulong *setup_len);
--
2.3.7