diff options
author | Quanyang Wang <quanyang.wang@windriver.com> | 2019-10-22 05:23:28 +0200 |
---|---|---|
committer | Michal Simek <michal.simek@xilinx.com> | 2020-01-08 15:21:09 +0100 |
commit | 6c6b3f1f260b24dc0ab9cbbf369e4fa36819ab8b (patch) | |
tree | da3dca568d3c978031b997e1baf7500b98056580 /arch/arm/mach-zynq | |
parent | Linux 5.5-rc1 (diff) | |
download | linux-6c6b3f1f260b24dc0ab9cbbf369e4fa36819ab8b.tar.xz linux-6c6b3f1f260b24dc0ab9cbbf369e4fa36819ab8b.zip |
ARM: zynq: use physical cpuid in zynq_slcr_cpu_stop/start
When kernel booting, it will create a cpuid map between the logical cpus
and physical cpus. In a normal boot, the cpuid map is as below:
Physical Logical
0 ==> 0
1 ==> 1
But in kdump, there is a condition that the crash happens at the
physical cpu1, and the crash kernel will run at the physical cpu1 too,
so the cpuid map in crash kernel is as below:
Physical Logical
1 ==> 0
0 ==> 1
The functions zynq_slcr_cpu_stop/start is to stop/start the physical
cpus, the parameter cpu should be the physical cpuid. So use
cpu_logical_map to translate the logical cpuid to physical cpuid.
Or else the logical cpu0(physical cpu1) will stop itself and
the processor will hang.
Signed-off-by: Quanyang Wang <quanyang.wang@windriver.com>
Tested-by: Michal Simek <michal.simek@xilinx.com>
Signed-off-by: Michal Simek <michal.simek@xilinx.com>
Diffstat (limited to 'arch/arm/mach-zynq')
-rw-r--r-- | arch/arm/mach-zynq/platsmp.c | 6 |
1 files changed, 4 insertions, 2 deletions
diff --git a/arch/arm/mach-zynq/platsmp.c b/arch/arm/mach-zynq/platsmp.c index a10085be9073..68ec303fa278 100644 --- a/arch/arm/mach-zynq/platsmp.c +++ b/arch/arm/mach-zynq/platsmp.c @@ -15,6 +15,7 @@ #include <linux/init.h> #include <linux/io.h> #include <asm/cacheflush.h> +#include <asm/smp_plat.h> #include <asm/smp_scu.h> #include <linux/irqchip/arm-gic.h> #include "common.h" @@ -30,6 +31,7 @@ int zynq_cpun_start(u32 address, int cpu) { u32 trampoline_code_size = &zynq_secondary_trampoline_end - &zynq_secondary_trampoline; + u32 phy_cpuid = cpu_logical_map(cpu); /* MS: Expectation that SLCR are directly map and accessible */ /* Not possible to jump to non aligned address */ @@ -39,7 +41,7 @@ int zynq_cpun_start(u32 address, int cpu) u32 trampoline_size = &zynq_secondary_trampoline_jump - &zynq_secondary_trampoline; - zynq_slcr_cpu_stop(cpu); + zynq_slcr_cpu_stop(phy_cpuid); if (address) { if (__pa(PAGE_OFFSET)) { zero = ioremap(0, trampoline_code_size); @@ -68,7 +70,7 @@ int zynq_cpun_start(u32 address, int cpu) if (__pa(PAGE_OFFSET)) iounmap(zero); } - zynq_slcr_cpu_start(cpu); + zynq_slcr_cpu_start(phy_cpuid); return 0; } |