diff options
Diffstat (limited to 'arch/arm/mach-exynos/platsmp.c')
-rw-r--r-- | arch/arm/mach-exynos/platsmp.c | 30 |
1 files changed, 24 insertions, 6 deletions
diff --git a/arch/arm/mach-exynos/platsmp.c b/arch/arm/mach-exynos/platsmp.c index f93d820ecab5..4ca8ff14a5bf 100644 --- a/arch/arm/mach-exynos/platsmp.c +++ b/arch/arm/mach-exynos/platsmp.c | |||
@@ -36,8 +36,22 @@ | |||
36 | 36 | ||
37 | extern void exynos4_secondary_startup(void); | 37 | extern void exynos4_secondary_startup(void); |
38 | 38 | ||
39 | #define CPU1_BOOT_REG (samsung_rev() == EXYNOS4210_REV_1_1 ? \ | 39 | static inline void __iomem *cpu_boot_reg_base(void) |
40 | S5P_INFORM5 : S5P_VA_SYSRAM) | 40 | { |
41 | if (soc_is_exynos4210() && samsung_rev() == EXYNOS4210_REV_1_1) | ||
42 | return S5P_INFORM5; | ||
43 | return S5P_VA_SYSRAM; | ||
44 | } | ||
45 | |||
46 | static inline void __iomem *cpu_boot_reg(int cpu) | ||
47 | { | ||
48 | void __iomem *boot_reg; | ||
49 | |||
50 | boot_reg = cpu_boot_reg_base(); | ||
51 | if (soc_is_exynos4412()) | ||
52 | boot_reg += 4*cpu; | ||
53 | return boot_reg; | ||
54 | } | ||
41 | 55 | ||
42 | /* | 56 | /* |
43 | * Write pen_release in a way that is guaranteed to be visible to all | 57 | * Write pen_release in a way that is guaranteed to be visible to all |
@@ -84,6 +98,7 @@ static void __cpuinit exynos_secondary_init(unsigned int cpu) | |||
84 | static int __cpuinit exynos_boot_secondary(unsigned int cpu, struct task_struct *idle) | 98 | static int __cpuinit exynos_boot_secondary(unsigned int cpu, struct task_struct *idle) |
85 | { | 99 | { |
86 | unsigned long timeout; | 100 | unsigned long timeout; |
101 | unsigned long phys_cpu = cpu_logical_map(cpu); | ||
87 | 102 | ||
88 | /* | 103 | /* |
89 | * Set synchronisation state between this boot processor | 104 | * Set synchronisation state between this boot processor |
@@ -99,7 +114,7 @@ static int __cpuinit exynos_boot_secondary(unsigned int cpu, struct task_struct | |||
99 | * Note that "pen_release" is the hardware CPU ID, whereas | 114 | * Note that "pen_release" is the hardware CPU ID, whereas |
100 | * "cpu" is Linux's internal ID. | 115 | * "cpu" is Linux's internal ID. |
101 | */ | 116 | */ |
102 | write_pen_release(cpu_logical_map(cpu)); | 117 | write_pen_release(phys_cpu); |
103 | 118 | ||
104 | if (!(__raw_readl(S5P_ARM_CORE1_STATUS) & S5P_CORE_LOCAL_PWR_EN)) { | 119 | if (!(__raw_readl(S5P_ARM_CORE1_STATUS) & S5P_CORE_LOCAL_PWR_EN)) { |
105 | __raw_writel(S5P_CORE_LOCAL_PWR_EN, | 120 | __raw_writel(S5P_CORE_LOCAL_PWR_EN, |
@@ -133,7 +148,7 @@ static int __cpuinit exynos_boot_secondary(unsigned int cpu, struct task_struct | |||
133 | smp_rmb(); | 148 | smp_rmb(); |
134 | 149 | ||
135 | __raw_writel(virt_to_phys(exynos4_secondary_startup), | 150 | __raw_writel(virt_to_phys(exynos4_secondary_startup), |
136 | CPU1_BOOT_REG); | 151 | cpu_boot_reg(phys_cpu)); |
137 | gic_raise_softirq(cpumask_of(cpu), 0); | 152 | gic_raise_softirq(cpumask_of(cpu), 0); |
138 | 153 | ||
139 | if (pen_release == -1) | 154 | if (pen_release == -1) |
@@ -181,6 +196,8 @@ static void __init exynos_smp_init_cpus(void) | |||
181 | 196 | ||
182 | static void __init exynos_smp_prepare_cpus(unsigned int max_cpus) | 197 | static void __init exynos_smp_prepare_cpus(unsigned int max_cpus) |
183 | { | 198 | { |
199 | int i; | ||
200 | |||
184 | if (!soc_is_exynos5250()) | 201 | if (!soc_is_exynos5250()) |
185 | scu_enable(scu_base_addr()); | 202 | scu_enable(scu_base_addr()); |
186 | 203 | ||
@@ -190,8 +207,9 @@ static void __init exynos_smp_prepare_cpus(unsigned int max_cpus) | |||
190 | * until it receives a soft interrupt, and then the | 207 | * until it receives a soft interrupt, and then the |
191 | * secondary CPU branches to this address. | 208 | * secondary CPU branches to this address. |
192 | */ | 209 | */ |
193 | __raw_writel(virt_to_phys(exynos4_secondary_startup), | 210 | for (i = 1; i < max_cpus; ++i) |
194 | CPU1_BOOT_REG); | 211 | __raw_writel(virt_to_phys(exynos4_secondary_startup), |
212 | cpu_boot_reg(cpu_logical_map(i))); | ||
195 | } | 213 | } |
196 | 214 | ||
197 | struct smp_operations exynos_smp_ops __initdata = { | 215 | struct smp_operations exynos_smp_ops __initdata = { |