[U-Boot] [PATCH 3/7] Add support for third program loader

Haiying.Wang at freescale.com Haiying.Wang at freescale.com
Mon Nov 22 22:47:22 CET 2010


From: Haiying Wang <Haiying.Wang at freescale.com>

This patch introduces the third program loader(TPL) to load the final uboot
image after the spl code. Once the CONFIG_SYS_TPL_BOOT is defined,
the CONFIG_TPL_BOOT is enabled to generate the u-boot-tpl.bin. There are two
examples to use tpl:
1. NAND boot. The 4K NAND SPL uboot can not enable ddr through spd code because
of the 4k size limitation, and the l2/l3 as SRAM also is not large enough to
accommodate the final uboot image.
2. SD/eSPI boot. We don't want to statically init ddr in SD/eSPI's configuration
structure in ROM, but the l2/l3 SRAM size is small for final uboot.

It can also be used for other cases which need to execute the necessary init
steps before loading the final uboot image.

Signed-off-by: Haiying Wang <Haiying.Wang at freescale.com>
---
 Makefile                                 |   14 ++++
 arch/powerpc/cpu/mpc85xx/cpu_init_nand.c |   34 ++++++++++-
 arch/powerpc/cpu/mpc85xx/start.S         |   11 +++
 arch/powerpc/cpu/mpc85xx/u-boot-tpl.lds  |   98 ++++++++++++++++++++++++++++++
 nand_spl/nand_boot_fsl_elbc.c            |    6 ++-
 5 files changed, 160 insertions(+), 3 deletions(-)
 create mode 100644 arch/powerpc/cpu/mpc85xx/u-boot-tpl.lds

diff --git a/Makefile b/Makefile
index b4aae89..71aaa9c 100644
--- a/Makefile
+++ b/Makefile
@@ -287,6 +287,10 @@ LDPPFLAGS += \
 	$(shell $(LD) --version | \
 	  sed -ne 's/GNU ld version \([0-9][0-9]*\)\.\([0-9][0-9]*\).*/-DLD_MAJOR=\1 -DLD_MINOR=\2/p')
 
+ifeq ($(CONFIG_SYS_TPL_BOOT),y)
+TPL_BOOT = tpl
+endif
+
 ifeq ($(CONFIG_NAND_U_BOOT),y)
 NAND_SPL = nand_spl
 U_BOOT_NAND = $(obj)u-boot-nand.bin
@@ -404,8 +408,16 @@ $(obj)u-boot.lds: $(LDSCRIPT)
 $(NAND_SPL):	$(TIMESTAMP_FILE) $(VERSION_FILE) depend
 		$(MAKE) -C nand_spl/board/$(BOARDDIR) all
 
+$(TPL_BOOT):	$(TIMESTAMP_FILE) $(VERSION_FILE) depend
+		$(MAKE) -C tpl/board/$(BOARDDIR) all
+
+ifeq ($(CONFIG_SYS_TPL_BOOT),y)
+$(U_BOOT_NAND): $(NAND_SPL) $(TPL_BOOT) $(obj)u-boot.bin
+		cat $(obj)nand_spl/u-boot-spl-16k.bin $(obj)tpl/u-boot-tpl.bin $(obj)u-boot.bin > $(obj)u-boot-nand.bin
+else
 $(U_BOOT_NAND):	$(NAND_SPL) $(obj)u-boot.bin
 		cat $(obj)nand_spl/u-boot-spl-16k.bin $(obj)u-boot.bin > $(obj)u-boot-nand.bin
+endif
 
 $(ONENAND_IPL):	$(TIMESTAMP_FILE) $(VERSION_FILE) $(obj)include/autoconf.mk
 		$(MAKE) -C onenand_ipl/board/$(BOARDDIR) all
@@ -1223,6 +1235,7 @@ clean:
 	@rm -f $(obj)lib/asm-offsets.s
 	@rm -f $(obj)nand_spl/{u-boot.lds,u-boot-spl,u-boot-spl.map,System.map}
 	@rm -f $(obj)onenand_ipl/onenand-{ipl,ipl.bin,ipl.map}
+	@rm -f $(obj)tpl/{u-boot-tpl,u-boot-tpl.map}
 	@rm -f $(ONENAND_BIN)
 	@rm -f $(obj)onenand_ipl/u-boot.lds
 	@rm -f $(TIMESTAMP_FILE) $(VERSION_FILE)
@@ -1247,6 +1260,7 @@ clobber:	clean
 	@rm -fr $(obj)include/generated
 	@[ ! -d $(obj)nand_spl ] || find $(obj)nand_spl -name "*" -type l -print | xargs rm -f
 	@[ ! -d $(obj)onenand_ipl ] || find $(obj)onenand_ipl -name "*" -type l -print | xargs rm -f
+	@[ ! -d $(obj)tpl ] || find $(obj)tpl -name "*" -type l -print | xargs rm -f
 
 ifeq ($(OBJTREE),$(SRCTREE))
 mrproper \
diff --git a/arch/powerpc/cpu/mpc85xx/cpu_init_nand.c b/arch/powerpc/cpu/mpc85xx/cpu_init_nand.c
index 8fb27ab..decedca 100644
--- a/arch/powerpc/cpu/mpc85xx/cpu_init_nand.c
+++ b/arch/powerpc/cpu/mpc85xx/cpu_init_nand.c
@@ -1,5 +1,5 @@
 /*
- * Copyright 2009 Freescale Semiconductor, Inc.
+ * Copyright 2010 Freescale Semiconductor, Inc.
  *
  * See file CREDITS for list of people who contributed to this
  * project.
@@ -40,7 +40,8 @@ void cpu_init_f(void)
 #error  CONFIG_NAND_BR_PRELIM, CONFIG_NAND_OR_PRELIM must be defined
 #endif
 
-#if defined(CONFIG_SYS_RAMBOOT) && defined(CONFIG_SYS_INIT_L2_ADDR)
+#if defined(CONFIG_SYS_RAMBOOT) && defined(CONFIG_SYS_INIT_L2_ADDR) \
+	&& !defined(CONFIG_TPL_BOOT)
 	ccsr_l2cache_t *l2cache = (void *)CONFIG_SYS_MPC85xx_L2_ADDR;
 	char *l2srbar;
 	int i;
@@ -60,4 +61,33 @@ void cpu_init_f(void)
 	for (i = 0; i < CONFIG_SYS_L2_SIZE; i++)
 		l2srbar[i] = 0;
 #endif
+#ifdef CONFIG_TPL_BOOT
+	init_used_tlb_cams();
+#endif
+}
+
+#ifdef CONFIG_TPL_BOOT
+/*
+ * Because the primary cpu's info is enough for the 2nd stage,  we define the
+ * cpu number to 1 so as to keep code size for 2nd stage binary as small as
+ * possible.
+ */
+int cpu_numcores()
+{
+	return 1;
+}
+
+DECLARE_GLOBAL_DATA_PTR;
+
+/*
+ * Get timebase clock frequency
+ */
+unsigned long get_tbclk(void)
+{
+#ifdef CONFIG_FSL_CORENET
+	return (gd->bus_clk + 8) / 16;
+#else
+	return (gd->bus_clk + 4UL)/8UL;
+#endif
 }
+#endif /* CONFIG_TPL_BOOT */
diff --git a/arch/powerpc/cpu/mpc85xx/start.S b/arch/powerpc/cpu/mpc85xx/start.S
index 945c1b8..91f9eeb 100644
--- a/arch/powerpc/cpu/mpc85xx/start.S
+++ b/arch/powerpc/cpu/mpc85xx/start.S
@@ -58,12 +58,14 @@
 	GOT_ENTRY(_GOT2_TABLE_)
 	GOT_ENTRY(_FIXUP_TABLE_)
 
+#ifndef CONFIG_TPL_BOOT
 #ifndef CONFIG_NAND_SPL
 	GOT_ENTRY(_start)
 	GOT_ENTRY(_start_of_vectors)
 	GOT_ENTRY(_end_of_vectors)
 	GOT_ENTRY(transfer_to_handler)
 #endif
+#endif /* !CONFIG_TPL_BOOT */
 
 	GOT_ENTRY(__init_end)
 	GOT_ENTRY(_end)
@@ -436,6 +438,7 @@ _start_cont:
 	/* NOTREACHED - board_init_f() does not return */
 
 #ifndef CONFIG_NAND_SPL
+#ifndef CONFIG_TPL_BOOT
 	. = EXC_OFF_SYS_RESET
 	.globl	_start_of_vectors
 _start_of_vectors:
@@ -680,6 +683,7 @@ mck_return:
 	lwz	r1,GPR1(r1)
 	SYNC
 	rfmci
+#endif /* !CONFIG_TPL_BOOT */
 
 /* Cache functions.
 */
@@ -903,6 +907,7 @@ write_tlb:
 	isync
 	blr
 
+/* #ifndef CONFIG_TPL_BOOT */
 /*
  * void relocate_code (addr_sp, gd, addr_moni)
  *
@@ -1067,6 +1072,7 @@ clear_bss:
 	mr	r4,r10		/* Destination Address		*/
 	bl	board_init_r
 
+#ifndef CONFIG_TPL_BOOT
 #ifndef CONFIG_NAND_SPL
 	/*
 	 * Copy exception vector code to low memory
@@ -1154,7 +1160,10 @@ unlock_ram_in_cache:
 	tlbivax	0,r3
 	isync
 	blr
+#endif /* !CONFIG_NAND_SPL */
+#endif /* !CONFIG_TPL_BOOT */
 
+#ifndef CONFIG_NAND_SPL
 .globl flush_dcache
 flush_dcache:
 	mfspr	r3,SPRN_L1CFG0
@@ -1202,9 +1211,11 @@ flush_dcache:
 
 	blr
 
+#ifndef CONFIG_TPL_BOOT
 .globl setup_ivors
 setup_ivors:
 
 #include "fixed_ivor.S"
 	blr
 #endif /* !CONFIG_NAND_SPL */
+#endif /* !CONFIG_TPL_BOOT */
diff --git a/arch/powerpc/cpu/mpc85xx/u-boot-tpl.lds b/arch/powerpc/cpu/mpc85xx/u-boot-tpl.lds
new file mode 100644
index 0000000..ea946cf
--- /dev/null
+++ b/arch/powerpc/cpu/mpc85xx/u-boot-tpl.lds
@@ -0,0 +1,98 @@
+/*
+ * Copyright 2010 Freescale Semiconductor, Inc.
+ *
+ * See file CREDITS for list of people who contributed to this
+ * project.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of
+ * the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
+ * MA 02111-1307 USA
+ */
+
+OUTPUT_ARCH(powerpc)
+PHDRS
+{
+  text PT_LOAD;
+  bss PT_LOAD;
+}
+
+SECTIONS
+{
+  /* Read-only sections, merged into text segment: */
+  . = + SIZEOF_HEADERS;
+  .interp : { *(.interp) }
+  .text      :
+  {
+    *(.text*)
+   } :text
+    _etext = .;
+    PROVIDE (etext = .);
+    .rodata    :
+   {
+    *(SORT_BY_ALIGNMENT(SORT_BY_NAME(.rodata*)))
+  } :text
+
+  /* Read-write section, merged into data segment: */
+  . = (. + 0x00FF) & 0xFFFFFF00;
+  _erotext = .;
+  PROVIDE (erotext = .);
+
+ .reloc   :
+  {
+    *(.got)
+    _GOT2_TABLE_ = .;
+    *(.got2)
+    _FIXUP_TABLE_ = .;
+    *(.fixup)
+  }
+  __got2_entries = (_FIXUP_TABLE_ - _GOT2_TABLE_) >> 2;
+  __fixup_entries = (. - _FIXUP_TABLE_) >> 2;
+
+  .data    :
+  {
+    *(.data*)
+    *(.sdata*)
+  }
+  _edata  =  .;
+  PROVIDE (edata = .);
+
+  . = .;
+  __u_boot_cmd_start = .;
+  .u_boot_cmd : { *(.u_boot_cmd) }
+  __u_boot_cmd_end = .;
+
+  . = ALIGN(256);
+  __init_begin = .;
+  .text.init : { *(.text.init) }
+  .data.init : { *(.data.init) }
+  . = ALIGN(256);
+  __init_end = .;
+
+  .bootpg ADDR(.text) - 0x1000 :
+  {
+    start.o	KEEP(*(.bootpg))
+  } :text = 0xffff
+
+  __bss_start = .;
+  .bss (NOLOAD)       :
+  {
+   *(.sbss*)
+   *(.bss*)
+   *(COMMON)
+  } :bss
+
+  . = ALIGN(4);
+  _end = . ;
+  PROVIDE (end = .);
+}
diff --git a/nand_spl/nand_boot_fsl_elbc.c b/nand_spl/nand_boot_fsl_elbc.c
index 9547d44..7bd84ce 100644
--- a/nand_spl/nand_boot_fsl_elbc.c
+++ b/nand_spl/nand_boot_fsl_elbc.c
@@ -4,7 +4,7 @@
  * (C) Copyright 2006-2008
  * Stefan Roese, DENX Software Engineering, sr at denx.de.
  *
- * Copyright (c) 2008 Freescale Semiconductor, Inc.
+ * Copyright (c) 2008-2010 Freescale Semiconductor, Inc.
  * Author: Scott Wood <scottwood at freescale.com>
  *
  * This program is free software; you can redistribute it and/or
@@ -47,7 +47,11 @@ static void nand_wait(void)
 	}
 }
 
+#ifdef CONFIG_TPL_BOOT
+void nand_load(unsigned int offs, int uboot_size, uchar *dst)
+#else
 static void nand_load(unsigned int offs, int uboot_size, uchar *dst)
+#endif
 {
 	fsl_lbc_t *regs = LBC_BASE_ADDR;
 	uchar *buf = (uchar *)CONFIG_SYS_NAND_BASE;
-- 
1.7.3.1.50.g1e633




More information about the U-Boot mailing list