---
 arch/x86/cpu/start.S                |   43 ++++++++++--------
 arch/x86/include/asm/init_helpers.h |    3 +
 arch/x86/include/asm/u-boot-x86.h   |    2 -
 arch/x86/lib/board.c                |   87 ++++++++++++++++++++++++++++++----
 arch/x86/lib/init_helpers.c         |   14 ++++++
 arch/x86/lib/relocate.c             |   43 ++---------------
 include/common.h                    |   11 ++++-
 7 files changed, 131 insertions(+), 72 deletions(-)

diff --git a/arch/x86/cpu/start.S b/arch/x86/cpu/start.S
index be21d97..9cfd54d 100644
--- a/arch/x86/cpu/start.S
+++ b/arch/x86/cpu/start.S
@@ -30,7 +30,7 @@
 #include <version.h>
 #include <asm/global_data.h>
 #include <asm/processor-flags.h>
-#include <generated/asm-offsets.h>
+#include <generated/generic-asm-offsets.h>
 
 .section .text
 .code32
@@ -84,36 +84,41 @@ car_init_ret:
         */
        movl    $CONFIG_SYS_INIT_SP_ADDR, %esp
 
-       /* Set parameter to board_init_f() to boot flags */
-       xorl    %eax, %eax
-       movw    %bx, %ax
+       /*
+        * Any setting of Global Data member need to be done here
+        * NOTE: car_init must clear CAR so that Global Data is initialised
+        *       to zero!
+        */
 
-       /* Enter, U-boot! */
+       /*
+        * Enter U-boot by calling:
+        * board_init_f(location_of_gd_in_temporary_memory)
+        */
+       movl    $CONFIG_SYS_INIT_GD_ADDR, %eax
        call    board_init_f
 
        /* indicate (lack of) progress */
        movw    $0x85, %ax
        jmp     die
 
-.globl setup_sdram_environment
-.type setup_sdram_environment, @function
-setup_sdram_environment:
-       /* Leave room for Global Data - Round down to 16 byte boundary */
-       subl    %edx, %eax
+.globl board_init_f_r_trampoline
+.type board_init_f_r_trampoline, @function
+board_init_f_r_trampoline:
+       /*
+        * %eax contains the upper address of usable RAM. Create a fresh
+        * stack in RAM. x86 stack grows down, global data sits immediately
+        * above the stack, so we have to leave enough room between the top
+        * of the stack and top of RAM for global data
+        */
+       subl    $GENERATED_GBL_DATA_SIZE, %eax
        andl    $~15, %eax
-
-       /* Create a new stack */
        movl    %eax, %esp
 
        /*
-        * relocate_code(ulong stack_ptr, gd_t *id, ulong reloc_addr)
-        * %eax = Address of top of stack
-        * %edx = Address of Global Data
-        * %ecx = Base address of in-RAM copy of U-Boot (ignored)
+        * Re-enter U-Boot by calling:
+        * board_init_f_r(location_of_gd_in_RAM)
         */
-       movl    %eax, %edx
-       xorl    %ecx, %ecx
-       call    relocate_code
+       call    board_init_f_r
 
 die:
        hlt
diff --git a/arch/x86/include/asm/init_helpers.h 
b/arch/x86/include/asm/init_helpers.h
index 14ef11a..2d08834 100644
--- a/arch/x86/include/asm/init_helpers.h
+++ b/arch/x86/include/asm/init_helpers.h
@@ -28,6 +28,9 @@ int display_banner(void);
 int display_dram_config(void);
 int init_baudrate_f(void);
 
+int copy_gd_to_ram_f_r(gd_t *id);
+int init_cache_f_r(gd_t *id);
+
 int mem_malloc_init_r(void);
 int init_bd_struct_r(void);
 int flash_init_r(void);
diff --git a/arch/x86/include/asm/u-boot-x86.h 
b/arch/x86/include/asm/u-boot-x86.h
index eaa50cc..093ad11 100644
--- a/arch/x86/include/asm/u-boot-x86.h
+++ b/arch/x86/include/asm/u-boot-x86.h
@@ -63,6 +63,4 @@ u32 isa_map_rom(u32 bus_addr, int size);
 int video_bios_init(void);
 int video_init(void);
 
-void setup_sdram_environment(phys_size_t ram_size, ulong gd_size);
-
 #endif /* _U_BOOT_I386_H_ */
diff --git a/arch/x86/lib/board.c b/arch/x86/lib/board.c
index b06063a..05d362d 100644
--- a/arch/x86/lib/board.c
+++ b/arch/x86/lib/board.c
@@ -35,6 +35,7 @@
 #include <watchdog.h>
 #include <stdio_dev.h>
 #include <asm/u-boot-x86.h>
+#include <asm/relocate.h>
 
 #include <asm/init_helpers.h>
 #include <asm/init_wrappers.h>
@@ -51,12 +52,35 @@ DECLARE_GLOBAL_DATA_PTR = (gd_t *) 
(CONFIG_SYS_INIT_GD_ADDR);
 /*
  * Breath some life into the board...
  *
- * Initialize an SMC for serial comms, and carry out some hardware
- * tests.
+ * Getting the board up and running is a three-stage process:
+ *  1) Execute from Flash, SDRAM Uninitialised
+ *     At this point, there is a limited amount of non-SDRAM memory
+ *     (typically the CPU cache, but can also be SRAM or even a buffer of
+ *     of some peripheral). This limited memory is used to hold the initial
+ *     copy of the Global Data Structure and a temporary stack.
  *
- * The first part of initialization is running from Flash memory;
- * its main purpose is to initialize the RAM so that we
- * can relocate the monitor code to RAM.
+ *     The following is performed during this phase of execution:
+ *      - Core low-level CPU initialisation
+ *      - Console initialisation
+ *      - SDRAM initialisation
+ *
+ *  2) Execute from Flash, SDRAM Initialised
+ *     At this point we copy Global Data from the initial non-SDRAM
+ *     memory and set up the permanent stack in SDRAM. The CPU cache is no
+ *     longer being used as temporary memory, so we can now fully enable
+ *     it.
+ *
+ *     The following is performed during this phase of execution:
+ *      - Create final stack in SDRAM
+ *      - Copy Global Data from temporary memory to SDRAM
+ *      - Enabling of CPU cache(s),
+ *      - Copying of U-Boot code and data from Flash to RAM
+ *      - Clearing of the BSS
+ *      - ELF relocation adjustments
+ *
+ *  3) Execute from SDRAM
+ *     The following is performed during this phase of execution:
+ *      - All remaining initialisation
  */
 
 /*
@@ -72,6 +96,7 @@ DECLARE_GLOBAL_DATA_PTR = (gd_t *) (CONFIG_SYS_INIT_GD_ADDR);
  * "continue" and != 0 means "fatal error, hang the system".
  */
 typedef int (init_fnc_t) (void);
+typedef int (init_fnc_gd_t) (gd_t *);
 
 init_fnc_t *init_sequence_f[] = {
        cpu_init_f,
@@ -85,6 +110,18 @@ init_fnc_t *init_sequence_f[] = {
        NULL,
 };
 
+init_fnc_gd_t *init_sequence_f_r[] = {
+       copy_gd_to_ram_f_r,
+       init_cache_f_r,
+       calculate_relocation_address,
+       copy_uboot_to_ram,
+       clear_bss,
+       do_elf_reloc_fixups,
+
+       NULL,
+};
+
+
 init_fnc_t *init_sequence_r[] = {
        init_bd_struct_r,
        mem_malloc_init_r,
@@ -161,15 +198,28 @@ static void do_init_loop(init_fnc_t **init_fnc_ptr)
        }
 }
 
+static void do_init_loop_gt(init_fnc_gd_t **init_fnc_ptr, gd_t *id)
+{
+       for (; *init_fnc_ptr; ++init_fnc_ptr) {
+               WATCHDOG_RESET();
+               if ((*init_fnc_ptr)(id) != 0)
+                       hang();
+       }
+}
+
 /* Perform all steps necessary to get RAM initialised ready for relocation */
-void board_init_f(ulong boot_flags)
+void board_init_f(gd_t *id)
 {
-       gd->flags = boot_flags;
+       /*
+        * NOTE: The gd_t pointer parameter is not used, but should be, in
+        *       future, passed to the init_xxx_f functions which would
+        *       allow the DECLARE_GLOBAL_DATA_PTR 'hack' to be removed
+        */
 
        do_init_loop(init_sequence_f);
 
        /*
-        * SDRAM is now initialised setup a new stack in SDRAM
+        * SDRAM is now initialised - setup the final stack in SDRAM
         *
         * Code execution will continue in Flash, but with the stack
         * in SDRAM. This allows us to copy global data out of the CPU
@@ -177,14 +227,29 @@ void board_init_f(ulong boot_flags)
         * enable caching for the copy operation (which speeds it up
         * considerably)
         */
-       setup_sdram_environment(gd->ram_size, GENERATED_GBL_DATA_SIZE);
+       board_init_f_r_trampoline(gd->ram_size);
+
+       /* NOTREACHED - board_init_f_r_trampoline() does not return */
+       while (1)
+               ;
+}
+
+void board_init_f_r(gd_t *id)
+{
+       do_init_loop_gt(init_sequence_f_r, id);
+
+       /*
+        * Transfer execution from Flash to RAM by calculating the address
+        * of the in-RAM copy of board_init_r() and calling it
+        */
+       (board_init_r + id->reloc_off)(id);
 
-       /* NOTREACHED - setup_sdram_environment() does not return */
+       /* NOTREACHED - board_init_r() does not return */
        while (1)
                ;
 }
 
-void board_init_r(gd_t *id, ulong dest_addr)
+void board_init_r(gd_t *id)
 {
        /* Global data pointer is now writable */
        gd = id;
diff --git a/arch/x86/lib/init_helpers.c b/arch/x86/lib/init_helpers.c
index a589fd3..c932812 100644
--- a/arch/x86/lib/init_helpers.c
+++ b/arch/x86/lib/init_helpers.c
@@ -70,6 +70,20 @@ int init_baudrate_f(void)
        return 0;
 }
 
+
+int copy_gd_to_ram_f_r(gd_t *id)
+{
+       memcpy(id, gd, sizeof(gd_t));
+
+       return 0;
+}
+
+int init_cache_f_r(gd_t *id)
+{
+       /* Initialise the CPU cache(s) */
+       return init_cache();
+}
+
 int mem_malloc_init_r(void)
 {
        mem_malloc_init(((gd->relocaddr - CONFIG_SYS_MALLOC_LEN)+3)&~3,
diff --git a/arch/x86/lib/relocate.c b/arch/x86/lib/relocate.c
index f8c0b3f..cbce22b 100644
--- a/arch/x86/lib/relocate.c
+++ b/arch/x86/lib/relocate.c
@@ -34,14 +34,10 @@
 #include <common.h>
 #include <malloc.h>
 #include <asm/u-boot-x86.h>
+#include <asm/relocate.h>
 #include <elf.h>
 
-static int calculate_relocation_address(gd_t *);
-static int copy_uboot_to_ram(gd_t *);
-static int clear_bss(gd_t *);
-static int do_elf_reloc_fixups(gd_t *);
-
-static int calculate_relocation_address(gd_t *id)
+int calculate_relocation_address(gd_t *id)
 {
        ulong text_start = (ulong)&__text_start;
        ulong bss_end = (ulong)&__bss_end;
@@ -67,7 +63,7 @@ static int calculate_relocation_address(gd_t *id)
        return 0;
 }
 
-static int copy_uboot_to_ram(gd_t *id)
+int copy_uboot_to_ram(gd_t *id)
 {
        size_t len = (size_t)&__data_end - (size_t)&__text_start;
 
@@ -76,7 +72,7 @@ static int copy_uboot_to_ram(gd_t *id)
        return 0;
 }
 
-static int clear_bss(gd_t *id)
+int clear_bss(gd_t *id)
 {
        ulong dst_addr = (ulong)&__bss_start + id->reloc_off;
        size_t len = (size_t)&__bss_end - (size_t)&__bss_start;
@@ -86,7 +82,7 @@ static int clear_bss(gd_t *id)
        return 0;
 }
 
-static int do_elf_reloc_fixups(gd_t *id)
+int do_elf_reloc_fixups(gd_t *id)
 {
        Elf32_Rel *re_src = (Elf32_Rel *)(&__rel_dyn_start);
        Elf32_Rel *re_end = (Elf32_Rel *)(&__rel_dyn_end);
@@ -119,32 +115,3 @@ static int do_elf_reloc_fixups(gd_t *id)
 
        return 0;
 }
-
-typedef void (board_init_r_t) (gd_t *, ulong);
-
-__attribute__ ((__noreturn__))
-void relocate_code(ulong dummy_1, gd_t *id, ulong dummy_2)
-{
-       board_init_r_t *board_init_r_func;
-
-       /* We are running from flash, but the stack is now in SDRAM */
-
-       /* gd is still in CAR - Copy it into SDRAM */
-       memcpy(id, gd, sizeof(gd_t));
-
-       if (init_cache() != 0)
-               hang();
-
-       calculate_relocation_address(id);
-       copy_uboot_to_ram(id);
-       clear_bss(id);
-       do_elf_reloc_fixups(id);
-
-       board_init_r_func = board_init_r;
-       board_init_r_func += id->reloc_off;
-       board_init_r_func(id, id->relocaddr);
-
-       /* NOTREACHED - relocate_code() does not return */
-       while (1)
-               ;
-}
diff --git a/include/common.h b/include/common.h
index 05a658c..4ef2a80 100644
--- a/include/common.h
+++ b/include/common.h
@@ -275,8 +275,15 @@ int        abortboot(int bootdelay);
 extern char console_buffer[];
 
 /* arch/$(ARCH)/lib/board.c */
-void   board_init_f  (ulong) __attribute__ ((noreturn));
-void   board_init_r  (gd_t *, ulong) __attribute__ ((noreturn));
+#ifndef CONFIG_X86     /* Horrible Hack */
+void   board_init_f   (ulong) __attribute__ ((noreturn));
+void   board_init_r   (gd_t *, ulong) __attribute__ ((noreturn));
+#else
+void board_init_f(gd_t *) __attribute__ ((noreturn));
+void board_init_f_r_trampoline(ulong) __attribute__ ((noreturn));
+void board_init_f_r(gd_t *) __attribute__ ((noreturn));
+void board_init_r(gd_t *) __attribute__ ((noreturn));
+#endif
 int    checkboard    (void);
 int    checkflash    (void);
 int    checkdram     (void);
-- 
1.7.5.2.317.g391b14

_______________________________________________
U-Boot mailing list
[email protected]
http://lists.denx.de/mailman/listinfo/u-boot

Reply via email to