aboutsummaryrefslogtreecommitdiffstats
path: root/arch
diff options
context:
space:
mode:
authorFlorian Fainelli <florian@openwrt.org>2013-07-24 12:12:11 -0400
committerRalf Baechle <ralf@linux-mips.org>2013-07-30 12:54:29 -0400
commitff5fadaff39180dc0b652753b5614a564711be29 (patch)
tree07662c3a1f58bd8355a4f7d3da23c2962f15be07 /arch
parentc4091d3fbbed922a3641e5e749655e49cc0d4dee (diff)
MIPS: BMIPS: fix slave CPU booting when physical CPU is not 0
The current BMIPS SMP code assumes that the slave CPU is physical and logical CPU 1, but on some systems such as BCM3368, the slave CPU is physical CPU0. Fix the code to read the physical CPU (thread ID) we are running this code on, and adjust the relocation vector address based on it. This allows bringing up the second CPU on BCM3368 for instance. Signed-off-by: Florian Fainelli <florian@openwrt.org> Cc: linux-mips@linux-mips.org Cc: cernekee@gmail.com Cc: jogo@openwrt.org Cc: blogic@openwrt.org Patchwork: https://patchwork.linux-mips.org/patch/5621/ Signed-off-by: Ralf Baechle <ralf@linux-mips.org>
Diffstat (limited to 'arch')
-rw-r--r--arch/mips/kernel/bmips_vec.S6
-rw-r--r--arch/mips/kernel/smp-bmips.c10
2 files changed, 13 insertions, 3 deletions
diff --git a/arch/mips/kernel/bmips_vec.S b/arch/mips/kernel/bmips_vec.S
index f739aedcb509..bd79c4f9bff4 100644
--- a/arch/mips/kernel/bmips_vec.S
+++ b/arch/mips/kernel/bmips_vec.S
@@ -54,7 +54,11 @@ LEAF(bmips_smp_movevec)
54 /* set up CPU1 CBR; move BASE to 0xa000_0000 */ 54 /* set up CPU1 CBR; move BASE to 0xa000_0000 */
55 li k0, 0xff400000 55 li k0, 0xff400000
56 mtc0 k0, $22, 6 56 mtc0 k0, $22, 6
57 li k1, CKSEG1 | BMIPS_RELO_VECTOR_CONTROL_1 57 /* set up relocation vector address based on thread ID */
58 mfc0 k1, $22, 3
59 srl k1, 16
60 andi k1, 0x8000
61 or k1, CKSEG1 | BMIPS_RELO_VECTOR_CONTROL_0
58 or k0, k1 62 or k0, k1
59 li k1, 0xa0080000 63 li k1, 0xa0080000
60 sw k1, 0(k0) 64 sw k1, 0(k0)
diff --git a/arch/mips/kernel/smp-bmips.c b/arch/mips/kernel/smp-bmips.c
index 89417c9c6aca..159abc8842d2 100644
--- a/arch/mips/kernel/smp-bmips.c
+++ b/arch/mips/kernel/smp-bmips.c
@@ -196,9 +196,15 @@ static void bmips_init_secondary(void)
196#if defined(CONFIG_CPU_BMIPS4350) || defined(CONFIG_CPU_BMIPS4380) 196#if defined(CONFIG_CPU_BMIPS4350) || defined(CONFIG_CPU_BMIPS4380)
197 void __iomem *cbr = BMIPS_GET_CBR(); 197 void __iomem *cbr = BMIPS_GET_CBR();
198 unsigned long old_vec; 198 unsigned long old_vec;
199 unsigned long relo_vector;
200 int boot_cpu;
199 201
200 old_vec = __raw_readl(cbr + BMIPS_RELO_VECTOR_CONTROL_1); 202 boot_cpu = !!(read_c0_brcm_cmt_local() & (1 << 31));
201 __raw_writel(old_vec & ~0x20000000, cbr + BMIPS_RELO_VECTOR_CONTROL_1); 203 relo_vector = boot_cpu ? BMIPS_RELO_VECTOR_CONTROL_0 :
204 BMIPS_RELO_VECTOR_CONTROL_1;
205
206 old_vec = __raw_readl(cbr + relo_vector);
207 __raw_writel(old_vec & ~0x20000000, cbr + relo_vector);
202 208
203 clear_c0_cause(smp_processor_id() ? C_SW1 : C_SW0); 209 clear_c0_cause(smp_processor_id() ? C_SW1 : C_SW0);
204#elif defined(CONFIG_CPU_BMIPS5000) 210#elif defined(CONFIG_CPU_BMIPS5000)