aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--arch/arm/mach-omap2/omap-headsmp.S35
-rw-r--r--arch/arm/mach-omap2/omap-smp.c24
-rw-r--r--arch/arm/plat-omap/include/plat/smp.h2
3 files changed, 37 insertions, 24 deletions
diff --git a/arch/arm/mach-omap2/omap-headsmp.S b/arch/arm/mach-omap2/omap-headsmp.S
index 4afadba09477..aa3f65c2ac97 100644
--- a/arch/arm/mach-omap2/omap-headsmp.S
+++ b/arch/arm/mach-omap2/omap-headsmp.S
@@ -27,20 +27,39 @@
27 * OMAP4 specific entry point for secondary CPU to jump from ROM 27 * OMAP4 specific entry point for secondary CPU to jump from ROM
28 * code. This routine also provides a holding flag into which 28 * code. This routine also provides a holding flag into which
29 * secondary core is held until we're ready for it to initialise. 29 * secondary core is held until we're ready for it to initialise.
30 * The primary core will update the this flag using a hardware 30 * The primary core will update this flag using a hardware
31 * register AuxCoreBoot1. 31 * register AuxCoreBoot0.
32 */ 32 */
33ENTRY(omap_secondary_startup) 33ENTRY(omap_secondary_startup)
34 mrc p15, 0, r0, c0, c0, 5 34hold: ldr r12,=0x103
35 and r0, r0, #0x0f 35 dsb
36hold: ldr r1, =OMAP4_AUX_CORE_BOOT1_PA @ read from AuxCoreBoot1 36 smc @ read from AuxCoreBoot0
37 ldr r2, [r1] 37 mov r0, r0, lsr #9
38 cmp r2, r0 38 mrc p15, 0, r4, c0, c0, 5
39 and r4, r4, #0x0f
40 cmp r0, r4
39 bne hold 41 bne hold
40 42
41 /* 43 /*
42 * we've been released from the cpu_release,secondary_stack 44 * we've been released from the wait loop,secondary_stack
43 * should now contain the SVC stack for this core 45 * should now contain the SVC stack for this core
44 */ 46 */
45 b secondary_startup 47 b secondary_startup
48END(omap_secondary_startup)
46 49
50
51ENTRY(omap_modify_auxcoreboot0)
52 stmfd sp!, {r1-r12, lr}
53 ldr r12, =0x104
54 dsb
55 smc
56 ldmfd sp!, {r1-r12, pc}
57END(omap_modify_auxcoreboot0)
58
59ENTRY(omap_auxcoreboot_addr)
60 stmfd sp!, {r2-r12, lr}
61 ldr r12, =0x105
62 dsb
63 smc
64 ldmfd sp!, {r2-r12, pc}
65END(omap_auxcoreboot_addr)
diff --git a/arch/arm/mach-omap2/omap-smp.c b/arch/arm/mach-omap2/omap-smp.c
index 4890bcf4dadd..59e847843af5 100644
--- a/arch/arm/mach-omap2/omap-smp.c
+++ b/arch/arm/mach-omap2/omap-smp.c
@@ -21,15 +21,12 @@
21#include <linux/smp.h> 21#include <linux/smp.h>
22#include <linux/io.h> 22#include <linux/io.h>
23 23
24#include <asm/cacheflush.h>
24#include <asm/localtimer.h> 25#include <asm/localtimer.h>
25#include <asm/smp_scu.h> 26#include <asm/smp_scu.h>
26#include <mach/hardware.h> 27#include <mach/hardware.h>
27#include <plat/common.h> 28#include <plat/common.h>
28 29
29/* Registers used for communicating startup information */
30static void __iomem *omap4_auxcoreboot_reg0;
31static void __iomem *omap4_auxcoreboot_reg1;
32
33/* SCU base address */ 30/* SCU base address */
34static void __iomem *scu_base; 31static void __iomem *scu_base;
35 32
@@ -74,12 +71,13 @@ int __cpuinit boot_secondary(unsigned int cpu, struct task_struct *idle)
74 spin_lock(&boot_lock); 71 spin_lock(&boot_lock);
75 72
76 /* 73 /*
77 * Update the AuxCoreBoot1 with boot state for secondary core. 74 * Update the AuxCoreBoot0 with boot state for secondary core.
78 * omap_secondary_startup() routine will hold the secondary core till 75 * omap_secondary_startup() routine will hold the secondary core till
79 * the AuxCoreBoot1 register is updated with cpu state 76 * the AuxCoreBoot1 register is updated with cpu state
80 * A barrier is added to ensure that write buffer is drained 77 * A barrier is added to ensure that write buffer is drained
81 */ 78 */
82 __raw_writel(cpu, omap4_auxcoreboot_reg1); 79 omap_modify_auxcoreboot0(0x200, 0x0);
80 flush_cache_all();
83 smp_wmb(); 81 smp_wmb();
84 82
85 timeout = jiffies + (1 * HZ); 83 timeout = jiffies + (1 * HZ);
@@ -99,17 +97,18 @@ static void __init wakeup_secondary(void)
99{ 97{
100 /* 98 /*
101 * Write the address of secondary startup routine into the 99 * Write the address of secondary startup routine into the
102 * AuxCoreBoot0 where ROM code will jump and start executing 100 * AuxCoreBoot1 where ROM code will jump and start executing
103 * on secondary core once out of WFE 101 * on secondary core once out of WFE
104 * A barrier is added to ensure that write buffer is drained 102 * A barrier is added to ensure that write buffer is drained
105 */ 103 */
106 __raw_writel(virt_to_phys(omap_secondary_startup), \ 104 omap_auxcoreboot_addr(virt_to_phys(omap_secondary_startup));
107 omap4_auxcoreboot_reg0);
108 smp_wmb(); 105 smp_wmb();
109 106
110 /* 107 /*
111 * Send a 'sev' to wake the secondary core from WFE. 108 * Send a 'sev' to wake the secondary core from WFE.
109 * Drain the outstanding writes to memory
112 */ 110 */
111 dsb();
113 set_event(); 112 set_event();
114 mb(); 113 mb();
115} 114}
@@ -136,7 +135,6 @@ void __init smp_prepare_cpus(unsigned int max_cpus)
136{ 135{
137 unsigned int ncores = get_core_count(); 136 unsigned int ncores = get_core_count();
138 unsigned int cpu = smp_processor_id(); 137 unsigned int cpu = smp_processor_id();
139 void __iomem *omap4_wkupgen_base;
140 int i; 138 int i;
141 139
142 /* sanity check */ 140 /* sanity check */
@@ -168,12 +166,6 @@ void __init smp_prepare_cpus(unsigned int max_cpus)
168 for (i = 0; i < max_cpus; i++) 166 for (i = 0; i < max_cpus; i++)
169 set_cpu_present(i, true); 167 set_cpu_present(i, true);
170 168
171 /* Never released */
172 omap4_wkupgen_base = ioremap(OMAP44XX_WKUPGEN_BASE, SZ_4K);
173 BUG_ON(!omap4_wkupgen_base);
174 omap4_auxcoreboot_reg0 = omap4_wkupgen_base + 0x800;
175 omap4_auxcoreboot_reg1 = omap4_wkupgen_base + 0x804;
176
177 if (max_cpus > 1) { 169 if (max_cpus > 1) {
178 /* 170 /*
179 * Enable the local timer or broadcast device for the 171 * Enable the local timer or broadcast device for the
diff --git a/arch/arm/plat-omap/include/plat/smp.h b/arch/arm/plat-omap/include/plat/smp.h
index dcaa8fde7063..8983d54c4fd2 100644
--- a/arch/arm/plat-omap/include/plat/smp.h
+++ b/arch/arm/plat-omap/include/plat/smp.h
@@ -28,6 +28,8 @@
28 28
29/* Needed for secondary core boot */ 29/* Needed for secondary core boot */
30extern void omap_secondary_startup(void); 30extern void omap_secondary_startup(void);
31extern u32 omap_modify_auxcoreboot0(u32 set_mask, u32 clear_mask);
32extern void omap_auxcoreboot_addr(u32 cpu_addr);
31 33
32/* 34/*
33 * We use Soft IRQ1 as the IPI 35 * We use Soft IRQ1 as the IPI