summaryrefslogtreecommitdiff
path: root/arch/arm/cpu/armv7/tegra2
diff options
context:
space:
mode:
Diffstat (limited to 'arch/arm/cpu/armv7/tegra2')
-rw-r--r--arch/arm/cpu/armv7/tegra2/Makefile5
-rw-r--r--arch/arm/cpu/armv7/tegra2/ap20.c54
-rw-r--r--arch/arm/cpu/armv7/tegra2/ap20.h10
-rw-r--r--arch/arm/cpu/armv7/tegra2/board.c35
-rw-r--r--arch/arm/cpu/armv7/tegra2/config.mk7
-rw-r--r--arch/arm/cpu/armv7/tegra2/lowlevel_init.S118
6 files changed, 59 insertions, 170 deletions
diff --git a/arch/arm/cpu/armv7/tegra2/Makefile b/arch/arm/cpu/armv7/tegra2/Makefile
index f0dc2ffa83..955c3b6dc4 100644
--- a/arch/arm/cpu/armv7/tegra2/Makefile
+++ b/arch/arm/cpu/armv7/tegra2/Makefile
@@ -23,6 +23,11 @@
# MA 02111-1307 USA
#
+# The AVP is ARMv4T architecture so we must use special compiler
+# flags for any startup files it might use.
+CFLAGS_arch/arm/cpu/armv7/tegra2/ap20.o += -march=armv4t
+CFLAGS_arch/arm/cpu/armv7/tegra2/clock.o += -march=armv4t
+
include $(TOPDIR)/config.mk
LIB = $(obj)lib$(SOC).o
diff --git a/arch/arm/cpu/armv7/tegra2/ap20.c b/arch/arm/cpu/armv7/tegra2/ap20.c
index 5cb4b1b6a0..4c44bb3637 100644
--- a/arch/arm/cpu/armv7/tegra2/ap20.c
+++ b/arch/arm/cpu/armv7/tegra2/ap20.c
@@ -31,7 +31,12 @@
#include <asm/arch/scu.h>
#include <common.h>
-u32 s_first_boot = 1;
+/* Returns 1 if the current CPU executing is a Cortex-A9, else 0 */
+static int ap20_cpu_is_cortexa9(void)
+{
+ u32 id = readb(NV_PA_PG_UP_BASE + PG_UP_TAG_0);
+ return id == (PG_UP_TAG_0_PID_CPU & 0xff);
+}
void init_pllx(void)
{
@@ -283,38 +288,37 @@ void init_pmc_scratch(void)
writel(CONFIG_SYS_BOARD_ODMDATA, &pmc->pmc_scratch20);
}
-void cpu_start(void)
+void tegra2_start(void)
{
struct pmux_tri_ctlr *pmt = (struct pmux_tri_ctlr *)NV_PA_APB_MISC_BASE;
- /* enable JTAG */
- writel(0xC0, &pmt->pmt_cfg_ctl);
+ /* If we are the AVP, start up the first Cortex-A9 */
+ if (!ap20_cpu_is_cortexa9()) {
+ /* enable JTAG */
+ writel(0xC0, &pmt->pmt_cfg_ctl);
- if (s_first_boot) {
/*
- * Need to set this before cold-booting,
- * otherwise we'll end up in an infinite loop.
- */
- s_first_boot = 0;
- cold_boot();
+ * If we are ARM7 - give it a different stack. We are about to
+ * start up the A9 which will want to use this one.
+ */
+ asm volatile("ldr sp, =%c0\n"
+ : : "i"(AVP_EARLY_BOOT_STACK_LIMIT));
+
+ start_cpu((u32)_start);
+ halt_avp();
+ /* not reached */
}
-}
-void tegra2_start()
-{
- if (s_first_boot) {
- /* Init Debug UART Port (115200 8n1) */
- uart_init();
+ /* Init PMC scratch memory */
+ init_pmc_scratch();
- /* Init PMC scratch memory */
- init_pmc_scratch();
- }
+ enable_scu();
-#ifdef CONFIG_ENABLE_CORTEXA9
- /* take the mpcore out of reset */
- cpu_start();
+ /* enable SMP mode and FW for CPU0, by writing to Auxiliary Ctl reg */
+ asm volatile(
+ "mrc p15, 0, r0, c1, c0, 1\n"
+ "orr r0, r0, #0x41\n"
+ "mcr p15, 0, r0, c1, c0, 1\n");
- /* configure cache */
- cache_configure();
-#endif
+ /* FIXME: should have ap20's L2 disabled too? */
}
diff --git a/arch/arm/cpu/armv7/tegra2/ap20.h b/arch/arm/cpu/armv7/tegra2/ap20.h
index 49fe340a28..a4b4d73a40 100644
--- a/arch/arm/cpu/armv7/tegra2/ap20.h
+++ b/arch/arm/cpu/armv7/tegra2/ap20.h
@@ -95,10 +95,8 @@
#define HALT_COP_EVENT_IRQ_1 (1 << 11)
#define HALT_COP_EVENT_FIQ_1 (1 << 9)
-/* Prototypes */
-
+/* Start up the tegra2 SOC */
void tegra2_start(void);
-void uart_init(void);
-void udelay(unsigned long);
-void cold_boot(void);
-void cache_configure(void);
+
+/* This is the main entry into U-Boot, used by the Cortex-A9 */
+extern void _start(void);
diff --git a/arch/arm/cpu/armv7/tegra2/board.c b/arch/arm/cpu/armv7/tegra2/board.c
index 751102d180..59dce8f8de 100644
--- a/arch/arm/cpu/armv7/tegra2/board.c
+++ b/arch/arm/cpu/armv7/tegra2/board.c
@@ -23,6 +23,7 @@
#include <common.h>
#include <asm/io.h>
+#include "ap20.h"
#include <asm/arch/sys_proto.h>
#include <asm/arch/tegra2.h>
#include <asm/arch/pmc.h>
@@ -54,28 +55,10 @@ unsigned int query_sdram_size(void)
}
}
-void s_init(void)
-{
-#ifndef CONFIG_ICACHE_OFF
- icache_enable();
-#endif
- invalidate_dcache();
-}
-
int dram_init(void)
{
- unsigned long rs;
-
/* We do not initialise DRAM here. We just query the size */
- gd->bd->bi_dram[0].start = PHYS_SDRAM_1;
- gd->bd->bi_dram[0].size = gd->ram_size = query_sdram_size();
-
- /* Now check it dynamically */
- rs = get_ram_size(CONFIG_SYS_SDRAM_BASE, gd->ram_size);
- if (rs) {
- printf("dynamic ram_size = %lu\n", rs);
- gd->bd->bi_dram[0].size = gd->ram_size = rs;
- }
+ gd->ram_size = query_sdram_size();
return 0;
}
@@ -86,3 +69,17 @@ int checkboard(void)
return 0;
}
#endif /* CONFIG_DISPLAY_BOARDINFO */
+
+#ifdef CONFIG_ARCH_CPU_INIT
+/*
+ * Note this function is executed by the ARM7TDMI AVP. It does not return
+ * in this case. It is also called once the A9 starts up, but does nothing in
+ * that case.
+ */
+int arch_cpu_init(void)
+{
+ /* Fire up the Cortex A9 */
+ tegra2_start();
+ return 0;
+}
+#endif
diff --git a/arch/arm/cpu/armv7/tegra2/config.mk b/arch/arm/cpu/armv7/tegra2/config.mk
index 96c07955aa..8f9bdc9ff0 100644
--- a/arch/arm/cpu/armv7/tegra2/config.mk
+++ b/arch/arm/cpu/armv7/tegra2/config.mk
@@ -24,5 +24,8 @@
# MA 02111-1307 USA
#
-# Use ARMv4 for Tegra2 - initial code runs on the AVP, which is an ARM7TDI.
-PLATFORM_CPPFLAGS += -march=armv4
+# Tegra has an ARMv4T CPU which runs board_init_f(), so we must build this
+# file with compatible flags
+ifdef CONFIG_TEGRA2
+CFLAGS_arch/arm/lib/board.o += -march=armv4t
+endif
diff --git a/arch/arm/cpu/armv7/tegra2/lowlevel_init.S b/arch/arm/cpu/armv7/tegra2/lowlevel_init.S
index f24a2ff57d..6b866476ce 100644
--- a/arch/arm/cpu/armv7/tegra2/lowlevel_init.S
+++ b/arch/arm/cpu/armv7/tegra2/lowlevel_init.S
@@ -26,14 +26,6 @@
#include <config.h>
#include <version.h>
-
-_TEXT_BASE:
- .word CONFIG_SYS_TEXT_BASE @ sdram load addr from config file
-
-.global invalidate_dcache
-invalidate_dcache:
- mov pc, lr
-
.align 5
.global reset_cpu
reset_cpu:
@@ -47,113 +39,3 @@ _loop_forever:
b _loop_forever
rstctl:
.word PRM_RSTCTRL
-
-.globl lowlevel_init
-lowlevel_init:
- ldr sp, SRAM_STACK
- str ip, [sp]
- mov ip, lr
- bl s_init @ go setup pll, mux & memory
- ldr ip, [sp]
- mov lr, ip
-
- mov pc, lr @ back to arch calling code
-
-
-.globl startup_cpu
-startup_cpu:
- @ Initialize the AVP, clocks, and memory controller
- @ SDRAM is guaranteed to be on at this point
-
- ldr r0, =cold_boot @ R0 = reset vector for CPU
- bl start_cpu @ start the CPU
-
- @ Transfer control to the AVP code
- bl halt_avp
-
- @ Should never get here
-_loop_forever2:
- b _loop_forever2
-
-.globl cache_configure
-cache_configure:
- stmdb r13!,{r14}
- @ invalidate instruction cache
- mov r1, #0
- mcr p15, 0, r1, c7, c5, 0
-
- @ invalidate the i&d tlb entries
- mcr p15, 0, r1, c8, c5, 0
- mcr p15, 0, r1, c8, c6, 0
-
- @ enable instruction cache
- mrc p15, 0, r1, c1, c0, 0
- orr r1, r1, #(1<<12)
- mcr p15, 0, r1, c1, c0, 0
-
- bl enable_scu
-
- @ enable SMP mode and FW for CPU0, by writing to Auxiliary Ctl reg
- mrc p15, 0, r0, c1, c0, 1
- orr r0, r0, #0x41
- mcr p15, 0, r0, c1, c0, 1
-
- @ Now flush the Dcache
- mov r0, #0
- @ 256 cache lines
- mov r1, #256
-
-invalidate_loop:
- add r1, r1, #-1
- mov r0, r1, lsl #5
- @ invalidate d-cache using line (way0)
- mcr p15, 0, r0, c7, c6, 2
-
- orr r2, r0, #(1<<30)
- @ invalidate d-cache using line (way1)
- mcr p15, 0, r2, c7, c6, 2
-
- orr r2, r0, #(2<<30)
- @ invalidate d-cache using line (way2)
- mcr p15, 0, r2, c7, c6, 2
-
- orr r2, r0, #(3<<30)
- @ invalidate d-cache using line (way3)
- mcr p15, 0, r2, c7, c6, 2
- cmp r1, #0
- bne invalidate_loop
-
- @ FIXME: should have ap20's L2 disabled too?
-invalidate_done:
- ldmia r13!,{pc}
-
-.globl cold_boot
-cold_boot:
- msr cpsr_c, #0xD3
- @ Check current processor: CPU or AVP?
- @ If CPU, go to CPU boot code, else continue on AVP path
-
- ldr r0, =NV_PA_PG_UP_BASE
- ldr r1, [r0]
- ldr r2, =PG_UP_TAG_AVP
-
- @ are we the CPU?
- ldr sp, CPU_STACK
- cmp r1, r2
- @ yep, we are the CPU
- bne _armboot_start
-
- @ AVP initialization follows this path
- ldr sp, AVP_STACK
- @ Init AVP and start CPU
- b startup_cpu
-
- @ the literal pools origin
- .ltorg
-
-SRAM_STACK:
- .word LOW_LEVEL_SRAM_STACK
-AVP_STACK:
- .word EARLY_AVP_STACK
-CPU_STACK:
- .word EARLY_CPU_STACK