diff options
author | Wang Long <long.wanglong@huawei.com> | 2014-12-24 06:10:02 +0300 |
---|---|---|
committer | Olof Johansson <olof@lixom.net> | 2015-01-22 01:33:39 +0300 |
commit | 7fda91e731554336c08a8157b886387d890a9676 (patch) | |
tree | 3cdf75fa716ec06d77f3ec95eccd34a9978db06c /arch/arm/mach-hisi/platsmp.c | |
parent | 29d189e1395a3f0924f7a442bb4b968c9e6de9c1 (diff) | |
download | linux-7fda91e731554336c08a8157b886387d890a9676.tar.xz |
ARM: hisi: enable smp for HiP01
Enable smp for HiP01 board.
Signed-off-by: Wang Long <long.wanglong@huawei.com>
Signed-off-by: Wei Xu <xuwei5@hisilicon.com>
[olof: split off the dts change to a separate commit]
Signed-off-by: Olof Johansson <olof@lixom.net>
Diffstat (limited to 'arch/arm/mach-hisi/platsmp.c')
-rw-r--r-- | arch/arm/mach-hisi/platsmp.c | 50 |
1 files changed, 50 insertions, 0 deletions
diff --git a/arch/arm/mach-hisi/platsmp.c b/arch/arm/mach-hisi/platsmp.c index 4a70f5610a2c..8880c8e8b296 100644 --- a/arch/arm/mach-hisi/platsmp.c +++ b/arch/arm/mach-hisi/platsmp.c @@ -10,10 +10,12 @@ #include <linux/smp.h> #include <linux/io.h> #include <linux/of_address.h> +#include <linux/delay.h> #include <asm/cacheflush.h> #include <asm/smp_plat.h> #include <asm/smp_scu.h> +#include <asm/mach/map.h> #include "core.h" @@ -132,5 +134,53 @@ struct smp_operations hix5hd2_smp_ops __initdata = { #endif }; + +#define SC_SCTL_REMAP_CLR 0x00000100 +#define HIP01_BOOT_ADDRESS 0x80000000 +#define REG_SC_CTRL 0x000 + +void hip01_set_boot_addr(phys_addr_t start_addr, phys_addr_t jump_addr) +{ + void __iomem *virt; + + virt = phys_to_virt(start_addr); + + writel_relaxed(0xe51ff004, virt); + writel_relaxed(jump_addr, virt + 4); +} + +static int hip01_boot_secondary(unsigned int cpu, struct task_struct *idle) +{ + phys_addr_t jumpaddr; + unsigned int remap_reg_value = 0; + struct device_node *node; + + + jumpaddr = virt_to_phys(hisi_secondary_startup); + hip01_set_boot_addr(HIP01_BOOT_ADDRESS, jumpaddr); + + node = of_find_compatible_node(NULL, NULL, "hisilicon,hip01-sysctrl"); + if (WARN_ON(!node)) + return -1; + ctrl_base = of_iomap(node, 0); + + /* set the secondary core boot from DDR */ + remap_reg_value = readl_relaxed(ctrl_base + REG_SC_CTRL); + barrier(); + remap_reg_value |= SC_SCTL_REMAP_CLR; + barrier(); + writel_relaxed(remap_reg_value, ctrl_base + REG_SC_CTRL); + + hip01_set_cpu(cpu, true); + + return 0; +} + +struct smp_operations hip01_smp_ops __initdata = { + .smp_prepare_cpus = hisi_common_smp_prepare_cpus, + .smp_boot_secondary = hip01_boot_secondary, +}; + CPU_METHOD_OF_DECLARE(hi3xxx_smp, "hisilicon,hi3620-smp", &hi3xxx_smp_ops); CPU_METHOD_OF_DECLARE(hix5hd2_smp, "hisilicon,hix5hd2-smp", &hix5hd2_smp_ops); +CPU_METHOD_OF_DECLARE(hip01_smp, "hisilicon,hip01-smp", &hip01_smp_ops); |