image: Add device tree setup to image library
authorSimon Glass <sjg@chromium.org>
Wed, 8 May 2013 08:06:01 +0000 (08:06 +0000)
committerTom Rini <trini@ti.com>
Tue, 14 May 2013 19:37:25 +0000 (15:37 -0400)
This seems to be a common function for several architectures, so create
a common function rather than duplicating the code in each arch.

Also make an attempt to avoid introducing #ifdefs in the new code, partly
by removing useless #ifdefs around function declarations in the image.h
header.

Signed-off-by: Simon Glass <sjg@chromium.org>
common/image-fdt.c
common/image.c
include/common.h
include/fdt_support.h
include/image.h
include/lmb.h

index 8e8f35c1cff010dbf29cf694a46d71ca57f688a4..158c9cfbf57de7f5437038740d0489649ab87dfb 100644 (file)
@@ -589,3 +589,65 @@ error:
        *of_size = 0;
        return 1;
 }
+
+/*
+ * Verify the device tree.
+ *
+ * This function is called after all device tree fix-ups have been enacted,
+ * so that the final device tree can be verified.  The definition of "verified"
+ * is up to the specific implementation.  However, it generally means that the
+ * addresses of some of the devices in the device tree are compared with the
+ * actual addresses at which U-Boot has placed them.
+ *
+ * Returns 1 on success, 0 on failure.  If 0 is returned, U-boot will halt the
+ * boot process.
+ */
+__weak int ft_verify_fdt(void *fdt)
+{
+       return 1;
+}
+
+__weak int arch_fixup_memory_node(void *blob)
+{
+       return 0;
+}
+
+int image_setup_libfdt(bootm_headers_t *images, void *blob,
+                      int of_size, struct lmb *lmb)
+{
+       ulong *initrd_start = &images->initrd_start;
+       ulong *initrd_end = &images->initrd_end;
+       int ret;
+
+       if (fdt_chosen(blob, 1) < 0) {
+               puts("ERROR: /chosen node create failed");
+               puts(" - must RESET the board to recover.\n");
+               return -1;
+       }
+       arch_fixup_memory_node(blob);
+       if (IMAAGE_OF_BOARD_SETUP)
+               ft_board_setup(blob, gd->bd);
+       fdt_fixup_ethernet(blob);
+
+       /* Delete the old LMB reservation */
+       lmb_free(lmb, (phys_addr_t)(u32)(uintptr_t)blob,
+                (phys_size_t)fdt_totalsize(blob));
+
+       ret = fdt_resize(blob);
+       if (ret < 0)
+               return ret;
+       of_size = ret;
+
+       if (*initrd_start && *initrd_end) {
+               of_size += FDT_RAMDISK_OVERHEAD;
+               fdt_set_totalsize(blob, of_size);
+       }
+       /* Create a new LMB reservation */
+       lmb_reserve(lmb, (ulong)blob, of_size);
+
+       fdt_initrd(blob, *initrd_start, *initrd_end, 1);
+       if (!ft_verify_fdt(blob))
+               return -1;
+
+       return 0;
+}
index 0792fdc2e23a67939766f50ea361ded7e8a46601..e91c89e1c5d61890bc6f9eee6476b566328b0b9d 100644 (file)
@@ -70,6 +70,10 @@ static const image_header_t *image_get_ramdisk(ulong rd_addr, uint8_t arch,
 
 #include <u-boot/crc.h>
 
+#ifndef CONFIG_SYS_BARGSIZE
+#define CONFIG_SYS_BARGSIZE 512
+#endif
+
 static const table_entry_t uimage_arch[] = {
        {       IH_ARCH_INVALID,        NULL,           "Invalid ARCH", },
        {       IH_ARCH_ALPHA,          "alpha",        "Alpha",        },
@@ -1223,4 +1227,50 @@ int boot_get_kbd(struct lmb *lmb, bd_t **kbd)
        return 0;
 }
 #endif /* CONFIG_SYS_BOOT_GET_KBD */
+
+#ifdef CONFIG_LMB
+int image_setup_linux(bootm_headers_t *images)
+{
+       ulong of_size = images->ft_len;
+       char **of_flat_tree = &images->ft_addr;
+       ulong *initrd_start = &images->initrd_start;
+       ulong *initrd_end = &images->initrd_end;
+       struct lmb *lmb = &images->lmb;
+       ulong rd_len;
+       int ret;
+
+       if (IMAGE_ENABLE_OF_LIBFDT)
+               boot_fdt_add_mem_rsv_regions(lmb, *of_flat_tree);
+
+       if (IMAGE_BOOT_GET_CMDLINE) {
+               ret = boot_get_cmdline(lmb, &images->cmdline_start,
+                               &images->cmdline_end);
+               if (ret) {
+                       puts("ERROR with allocation of cmdline\n");
+                       return ret;
+               }
+       }
+       if (IMAGE_ENABLE_RAMDISK_HIGH) {
+               rd_len = images->rd_end - images->rd_start;
+               ret = boot_ramdisk_high(lmb, images->rd_start, rd_len,
+                               initrd_start, initrd_end);
+               if (ret)
+                       return ret;
+       }
+
+       if (IMAGE_ENABLE_OF_LIBFDT) {
+               ret = boot_relocate_fdt(lmb, of_flat_tree, &of_size);
+               if (ret)
+                       return ret;
+       }
+
+       if (IMAGE_ENABLE_OF_LIBFDT && of_size) {
+               ret = image_setup_libfdt(images, *of_flat_tree, of_size, lmb);
+               if (ret)
+                       return ret;
+       }
+
+       return 0;
+}
+#endif /* CONFIG_LMB */
 #endif /* !USE_HOSTCC */
index 40e4b077fdf2d1d1d52a45c241366e84675f69ce..2d645c23b421429c32413e23a0baf55b8cabc955 100644 (file)
@@ -340,6 +340,16 @@ int update_flash_size(int flash_size);
  */
 void board_show_dram(ulong size);
 
+/**
+ * arch_fixup_memory_node() - Write arch-specific memory information to fdt
+ *
+ * Defined in arch/$(ARCH)/lib/bootm.c
+ *
+ * @blob:      FDT blob to write to
+ * @return 0 if ok, or -ve FDT_ERR_... on failure
+ */
+int arch_fixup_memory_node(void *blob);
+
 /* common/flash.c */
 void flash_perror (int);
 
index 2cccc3551db4e584325c9ea50d29285359fc68c6..8f07a670db6720cc196fa0b0db32de8797afc7de 100644 (file)
@@ -78,11 +78,9 @@ static inline void fdt_fixup_crypto_node(void *blob, int sec_rev) {}
 int fdt_pci_dma_ranges(void *blob, int phb_off, struct pci_controller *hose);
 #endif
 
-#ifdef CONFIG_OF_BOARD_SETUP
 void ft_board_setup(void *blob, bd_t *bd);
 void ft_cpu_setup(void *blob, bd_t *bd);
 void ft_pci_setup(void *blob, bd_t *bd);
-#endif
 
 void set_working_fdt_addr(void *addr);
 int fdt_resize(void *blob);
index bfce86186e78bc4b9e5080f01f695419db38feae..b8cc5236a819b2ad6b89bab1e16ae7c1b2e6133f 100644 (file)
@@ -36,6 +36,9 @@
 #include "compiler.h"
 #include <asm/byteorder.h>
 
+/* Define this to avoid #ifdefs later on */
+struct lmb;
+
 #ifdef USE_HOSTCC
 
 /* new uImage format support enabled on host */
 #define IMAGE_ENABLE_SHA1      0
 #endif
 
+#endif /* CONFIG_FIT */
+
+#ifdef CONFIG_SYS_BOOT_RAMDISK_HIGH
+# define IMAGE_ENABLE_RAMDISK_HIGH     1
+#else
+# define IMAGE_ENABLE_RAMDISK_HIGH     0
+#endif
+
+#ifdef CONFIG_OF_LIBFDT
+# define IMAGE_ENABLE_OF_LIBFDT        1
+#else
+# define IMAGE_ENABLE_OF_LIBFDT        0
+#endif
+
+#ifdef CONFIG_SYS_BOOT_GET_CMDLINE
+# define IMAGE_BOOT_GET_CMDLINE                1
+#else
+# define IMAGE_BOOT_GET_CMDLINE                0
+#endif
+
+#ifdef CONFIG_OF_BOARD_SETUP
+# define IMAAGE_OF_BOARD_SETUP         1
+#else
+# define IMAAGE_OF_BOARD_SETUP         0
 #endif
 
 /*
@@ -280,9 +307,7 @@ typedef struct bootm_headers {
 
        ulong           rd_start, rd_end;/* ramdisk start/end */
 
-#ifdef CONFIG_OF_LIBFDT
        char            *ft_addr;       /* flat dev tree address */
-#endif
        ulong           ft_len;         /* length of flat device tree */
 
        ulong           initrd_start;
@@ -390,21 +415,14 @@ 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);
 
-
-#ifdef CONFIG_OF_LIBFDT
 int boot_get_fdt(int flag, int argc, char * const argv[],
                bootm_headers_t *images, char **of_flat_tree, ulong *of_size);
 void boot_fdt_add_mem_rsv_regions(struct lmb *lmb, void *fdt_blob);
 int boot_relocate_fdt(struct lmb *lmb, char **of_flat_tree, ulong *of_size);
-#endif
 
-#ifdef CONFIG_SYS_BOOT_RAMDISK_HIGH
 int boot_ramdisk_high(struct lmb *lmb, ulong rd_data, ulong rd_len,
                  ulong *initrd_start, ulong *initrd_end);
-#endif /* CONFIG_SYS_BOOT_RAMDISK_HIGH */
-#ifdef CONFIG_SYS_BOOT_GET_CMDLINE
 int boot_get_cmdline(struct lmb *lmb, ulong *cmd_start, ulong *cmd_end);
-#endif /* CONFIG_SYS_BOOT_GET_CMDLINE */
 #ifdef CONFIG_SYS_BOOT_GET_KBD
 int boot_get_kbd(struct lmb *lmb, bd_t **kbd);
 #endif /* CONFIG_SYS_BOOT_GET_KBD */
@@ -546,6 +564,31 @@ static inline int image_check_target_arch(const image_header_t *hdr)
 }
 #endif /* USE_HOSTCC */
 
+/**
+ * Set up properties in the FDT
+ *
+ * This sets up properties in the FDT that is to be passed to linux.
+ *
+ * @images:    Images information
+ * @blob:      FDT to update
+ * @of_size:   Size of the FDT
+ * @lmb:       Points to logical memory block structure
+ * @return 0 if ok, <0 on failure
+ */
+int image_setup_libfdt(bootm_headers_t *images, void *blob,
+                      int of_size, struct lmb *lmb);
+
+/**
+ * Set up the FDT to use for booting a kernel
+ *
+ * This performs ramdisk setup, sets up the FDT if required, and adds
+ * paramters to the FDT if libfdt is available.
+ *
+ * @param images       Images information
+ * @return 0 if ok, <0 on failure
+ */
+int image_setup_linux(bootm_headers_t *images);
+
 /*******************************************************************/
 /* New uImage format specific code (prefixed with fit_) */
 /*******************************************************************/
index 5d1f4b624a2695b06e478dd7fcf205508d1a5cc1..43082a393fded52ec71f4bca686cffef0e1aedf8 100644 (file)
@@ -1,7 +1,6 @@
 #ifndef _LINUX_LMB_H
 #define _LINUX_LMB_H
 #ifdef __KERNEL__
-#ifdef CONFIG_LMB
 
 #include <asm/types.h>
 /*
@@ -57,7 +56,6 @@ lmb_size_bytes(struct lmb_region *type, unsigned long region_nr)
 void board_lmb_reserve(struct lmb *lmb);
 void arch_lmb_reserve(struct lmb *lmb);
 
-#endif /* CONFIG_LMB */
 #endif /* __KERNEL__ */
 
 #endif /* _LINUX_LMB_H */