diff options
author | Kapil Hali <kapilh@broadcom.com> | 2015-12-01 11:24:08 -0500 |
---|---|---|
committer | Florian Fainelli <f.fainelli@gmail.com> | 2015-12-07 15:30:30 -0500 |
commit | 97890821bb58dea522f823d8db396f9c17c6e356 (patch) | |
tree | f693b5096ed560f482a99de1676b3aed0895cce3 | |
parent | 84320e1a635fcf90cff4185f029ce9e31bf1d4a7 (diff) |
ARM: BCM: Add SMP support for Broadcom NSP
Add SMP support for Broadcom's Northstar Plus SoC
cpu enable method. This changes also consolidates
iProc family's - BCM NSP and BCM Kona, platform
SMP handling in a common file.
Northstar Plus SoC is based on ARM Cortex-A9
revision r3p0 which requires configuration for ARM
Errata 764369 for SMP. This change adds the needed
configuration option.
Signed-off-by: Kapil Hali <kapilh@broadcom.com>
Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
-rw-r--r-- | arch/arm/mach-bcm/Kconfig | 2 | ||||
-rw-r--r-- | arch/arm/mach-bcm/Makefile | 8 | ||||
-rw-r--r-- | arch/arm/mach-bcm/platsmp.c (renamed from arch/arm/mach-bcm/kona_smp.c) | 64 |
3 files changed, 71 insertions, 3 deletions
diff --git a/arch/arm/mach-bcm/Kconfig b/arch/arm/mach-bcm/Kconfig index c32628b045e4..6e3e043ce332 100644 --- a/arch/arm/mach-bcm/Kconfig +++ b/arch/arm/mach-bcm/Kconfig | |||
@@ -40,6 +40,8 @@ config ARCH_BCM_NSP | |||
40 | select ARCH_BCM_IPROC | 40 | select ARCH_BCM_IPROC |
41 | select ARM_ERRATA_754322 | 41 | select ARM_ERRATA_754322 |
42 | select ARM_ERRATA_775420 | 42 | select ARM_ERRATA_775420 |
43 | select ARM_ERRATA_764369 if SMP | ||
44 | select HAVE_SMP | ||
43 | help | 45 | help |
44 | Support for Broadcom Northstar Plus SoC. | 46 | Support for Broadcom Northstar Plus SoC. |
45 | Broadcom Northstar Plus family of SoCs are used for switching control | 47 | Broadcom Northstar Plus family of SoCs are used for switching control |
diff --git a/arch/arm/mach-bcm/Makefile b/arch/arm/mach-bcm/Makefile index 892261fec0ae..5193a25a56ca 100644 --- a/arch/arm/mach-bcm/Makefile +++ b/arch/arm/mach-bcm/Makefile | |||
@@ -14,7 +14,11 @@ | |||
14 | obj-$(CONFIG_ARCH_BCM_CYGNUS) += bcm_cygnus.o | 14 | obj-$(CONFIG_ARCH_BCM_CYGNUS) += bcm_cygnus.o |
15 | 15 | ||
16 | # Northstar Plus | 16 | # Northstar Plus |
17 | obj-$(CONFIG_ARCH_BCM_NSP) += bcm_nsp.o | 17 | obj-$(CONFIG_ARCH_BCM_NSP) += bcm_nsp.o |
18 | |||
19 | ifeq ($(CONFIG_ARCH_BCM_NSP),y) | ||
20 | obj-$(CONFIG_SMP) += platsmp.o | ||
21 | endif | ||
18 | 22 | ||
19 | # BCM281XX | 23 | # BCM281XX |
20 | obj-$(CONFIG_ARCH_BCM_281XX) += board_bcm281xx.o | 24 | obj-$(CONFIG_ARCH_BCM_281XX) += board_bcm281xx.o |
@@ -23,7 +27,7 @@ obj-$(CONFIG_ARCH_BCM_281XX) += board_bcm281xx.o | |||
23 | obj-$(CONFIG_ARCH_BCM_21664) += board_bcm21664.o | 27 | obj-$(CONFIG_ARCH_BCM_21664) += board_bcm21664.o |
24 | 28 | ||
25 | # BCM281XX and BCM21664 SMP support | 29 | # BCM281XX and BCM21664 SMP support |
26 | obj-$(CONFIG_ARCH_BCM_MOBILE_SMP) += kona_smp.o | 30 | obj-$(CONFIG_ARCH_BCM_MOBILE_SMP) += platsmp.o |
27 | 31 | ||
28 | # BCM281XX and BCM21664 L2 cache control | 32 | # BCM281XX and BCM21664 L2 cache control |
29 | obj-$(CONFIG_ARCH_BCM_MOBILE_L2_CACHE) += kona_l2_cache.o | 33 | obj-$(CONFIG_ARCH_BCM_MOBILE_L2_CACHE) += kona_l2_cache.o |
diff --git a/arch/arm/mach-bcm/kona_smp.c b/arch/arm/mach-bcm/platsmp.c index 15af781228a5..ea4201e6d0c9 100644 --- a/arch/arm/mach-bcm/kona_smp.c +++ b/arch/arm/mach-bcm/platsmp.c | |||
@@ -12,12 +12,17 @@ | |||
12 | * GNU General Public License for more details. | 12 | * GNU General Public License for more details. |
13 | */ | 13 | */ |
14 | 14 | ||
15 | #include <linux/init.h> | 15 | #include <linux/cpumask.h> |
16 | #include <linux/delay.h> | ||
16 | #include <linux/errno.h> | 17 | #include <linux/errno.h> |
18 | #include <linux/init.h> | ||
17 | #include <linux/io.h> | 19 | #include <linux/io.h> |
20 | #include <linux/jiffies.h> | ||
18 | #include <linux/of.h> | 21 | #include <linux/of.h> |
19 | #include <linux/sched.h> | 22 | #include <linux/sched.h> |
23 | #include <linux/smp.h> | ||
20 | 24 | ||
25 | #include <asm/cacheflush.h> | ||
21 | #include <asm/smp.h> | 26 | #include <asm/smp.h> |
22 | #include <asm/smp_plat.h> | 27 | #include <asm/smp_plat.h> |
23 | #include <asm/smp_scu.h> | 28 | #include <asm/smp_scu.h> |
@@ -76,6 +81,36 @@ static int __init scu_a9_enable(void) | |||
76 | return 0; | 81 | return 0; |
77 | } | 82 | } |
78 | 83 | ||
84 | static int nsp_write_lut(void) | ||
85 | { | ||
86 | void __iomem *sku_rom_lut; | ||
87 | phys_addr_t secondary_startup_phy; | ||
88 | |||
89 | if (!secondary_boot_addr) { | ||
90 | pr_warn("required secondary boot register not specified\n"); | ||
91 | return -EINVAL; | ||
92 | } | ||
93 | |||
94 | sku_rom_lut = ioremap_nocache((phys_addr_t)secondary_boot_addr, | ||
95 | sizeof(secondary_boot_addr)); | ||
96 | if (!sku_rom_lut) { | ||
97 | pr_warn("unable to ioremap SKU-ROM LUT register\n"); | ||
98 | return -ENOMEM; | ||
99 | } | ||
100 | |||
101 | secondary_startup_phy = virt_to_phys(secondary_startup); | ||
102 | BUG_ON(secondary_startup_phy > (phys_addr_t)U32_MAX); | ||
103 | |||
104 | writel_relaxed(secondary_startup_phy, sku_rom_lut); | ||
105 | |||
106 | /* Ensure the write is visible to the secondary core */ | ||
107 | smp_wmb(); | ||
108 | |||
109 | iounmap(sku_rom_lut); | ||
110 | |||
111 | return 0; | ||
112 | } | ||
113 | |||
79 | static void __init bcm_smp_prepare_cpus(unsigned int max_cpus) | 114 | static void __init bcm_smp_prepare_cpus(unsigned int max_cpus) |
80 | { | 115 | { |
81 | static cpumask_t only_cpu_0 = { CPU_BITS_CPU0 }; | 116 | static cpumask_t only_cpu_0 = { CPU_BITS_CPU0 }; |
@@ -220,9 +255,36 @@ static int kona_boot_secondary(unsigned int cpu, struct task_struct *idle) | |||
220 | return -ENXIO; | 255 | return -ENXIO; |
221 | } | 256 | } |
222 | 257 | ||
258 | static int nsp_boot_secondary(unsigned int cpu, struct task_struct *idle) | ||
259 | { | ||
260 | int ret; | ||
261 | |||
262 | /* | ||
263 | * After wake up, secondary core branches to the startup | ||
264 | * address programmed at SKU ROM LUT location. | ||
265 | */ | ||
266 | ret = nsp_write_lut(); | ||
267 | if (ret) { | ||
268 | pr_err("unable to write startup addr to SKU ROM LUT\n"); | ||
269 | goto out; | ||
270 | } | ||
271 | |||
272 | /* Send a CPU wakeup interrupt to the secondary core */ | ||
273 | arch_send_wakeup_ipi_mask(cpumask_of(cpu)); | ||
274 | |||
275 | out: | ||
276 | return ret; | ||
277 | } | ||
278 | |||
223 | static struct smp_operations bcm_smp_ops __initdata = { | 279 | static struct smp_operations bcm_smp_ops __initdata = { |
224 | .smp_prepare_cpus = bcm_smp_prepare_cpus, | 280 | .smp_prepare_cpus = bcm_smp_prepare_cpus, |
225 | .smp_boot_secondary = kona_boot_secondary, | 281 | .smp_boot_secondary = kona_boot_secondary, |
226 | }; | 282 | }; |
227 | CPU_METHOD_OF_DECLARE(bcm_smp_bcm281xx, "brcm,bcm11351-cpu-method", | 283 | CPU_METHOD_OF_DECLARE(bcm_smp_bcm281xx, "brcm,bcm11351-cpu-method", |
228 | &bcm_smp_ops); | 284 | &bcm_smp_ops); |
285 | |||
286 | struct smp_operations nsp_smp_ops __initdata = { | ||
287 | .smp_prepare_cpus = bcm_smp_prepare_cpus, | ||
288 | .smp_boot_secondary = nsp_boot_secondary, | ||
289 | }; | ||
290 | CPU_METHOD_OF_DECLARE(bcm_smp_nsp, "brcm,bcm-nsp-smp", &nsp_smp_ops); | ||