Hi all,
Here are some patches to make kexec work for SMP omaps. To test
these you need to use the latest kexec-tools.git kexec with
Russell's recent patches in "[PATCH 0/2] Simple fix to the ARM
kexec tools implementation" thread fixed for 6x. Or else you
need to use appended DTB.
I've tested these so far on 4430 duovero, omap5-uevm, and
beagle-x15.
Regards,
Tony
Tony Lindgren (4):
ARM: OMAP4+: Initialize SAR RAM base early for proper CPU1 reset for
kexec
ARM: OMAP4+: Prevent CPU1 related hang with kexec
ARM: OMAP4+: Reset CPU1 properly for kexec
ARM: OMAP4+: Allow kexec on SMP variants
arch/arm/mach-omap2/Makefile | 4 +-
arch/arm/mach-omap2/common.h | 8 ++-
arch/arm/mach-omap2/io.c | 3 +
arch/arm/mach-omap2/omap-hotplug.c | 6 ++
arch/arm/mach-omap2/omap-mpuss-lowpower.c | 29 ++++++++--
arch/arm/mach-omap2/omap-smp.c | 96 ++++++++++++++++++++++---------
arch/arm/mach-omap2/omap4-common.c | 14 ++---
7 files changed, 118 insertions(+), 42 deletions(-)
--
2.8.1
Prepare things for making kexec work on SMP omap variants by initializing
SARM RAM base early. This allows us to configure CPU1 for kexec in case
the previous kernel has put CPU1 in low power mode.
Note that this should not prevent moving other SAR RAM code to live
under drivers. However for kexec, we will need this very early.
Signed-off-by: Tony Lindgren <tony@atomide.com>
---
arch/arm/mach-omap2/common.h | 1 +
arch/arm/mach-omap2/io.c | 2 ++
arch/arm/mach-omap2/omap4-common.c | 14 ++++++--------
3 files changed, 9 insertions(+), 8 deletions(-)
@@ -282,16 +283,13 @@ static int __init omap4_sar_ram_init(void)elseif(soc_is_omap54xx())sar_base=OMAP54XX_SAR_RAM_BASE;else-return-ENOMEM;+return;/* Static mapping, never released */sar_ram_base=ioremap(sar_base,SZ_16K);if(WARN_ON(!sar_ram_base))-return-ENOMEM;--return0;+return;}-omap_early_initcall(omap4_sar_ram_init);staticconststructof_device_idintc_match[]={{.compatible="ti,omap4-wugen-mpu",},
Kexec booted kernels on omap4 will hang early during the boot if the
booted kernel is different version from the previous kernel.
This is because the previous kernel may have configured low-power mode
using CPU1_WAKEUP_NS_PA_ADDR. In that case it points to the previous
kernel's omap4_secondary_startup(), and CPU1 can be in low power mode
from the previous kernel. When the new kernel configures the CPU1
clockdomain, CPU1 can wake from low power state prematurely during
omap44xx_clockdomains_init() running random code.
Let's fix the issue by configuring CPU1_WAKEUP_NS_PA_ADDR before we
call omap44xx_clockdomains_init(). Note that this is very early during
the init, and we will do proper CPU1 reset during SMP init a bit later
on in omap4_smp_prepare_cpus(). And we need to do this when SMP is
not enabled as the previous kernel may have had it enabled.
Signed-off-by: Tony Lindgren <tony@atomide.com>
---
arch/arm/mach-omap2/Makefile | 4 ++--
arch/arm/mach-omap2/common.h | 6 ++++--
arch/arm/mach-omap2/io.c | 1 +
arch/arm/mach-omap2/omap-mpuss-lowpower.c | 29 +++++++++++++++++++++++++----
4 files changed, 32 insertions(+), 8 deletions(-)
@@ -8,7 +8,7 @@ ccflags-y := -I$(srctree)/$(src)/include \# Common supportobj-y:=id.oio.ocontrol.omux.odevices.ofb.oserial.otimer.opm.o\common.ogpio.odma.owd_timer.odisplay.oi2c.ohdq1w.oomap_hwmod.o\-omap_device.osram.odrm.o+omap_device.oomap-headsmp.osram.odrm.ohwmod-common=omap_hwmod.oomap_hwmod_reset.o\omap_hwmod_common_data.o
@@ -32,7 +32,7 @@ obj-$(CONFIG_SOC_HAS_OMAP2_SDRC) += sdrc.o# SMP support ONLY available for OMAP4-smp-$(CONFIG_SMP)+=omap-smp.oomap-headsmp.o+smp-$(CONFIG_SMP)+=omap-smp.osmp-$(CONFIG_HOTPLUG_CPU)+=omap-hotplug.oomap-4-5-common=omap4-common.oomap-wakeupgen.oobj-$(CONFIG_ARCH_OMAP4)+=$(omap-4-5-common)$(smp-y)sleep44xx.o
@@ -366,9 +367,6 @@ int __init omap4_mpuss_init(void)return-ENODEV;}-if(cpu_is_omap44xx())-sar_base=omap4_get_sar_ram_base();-/* Initilaise per CPU PM information */pm_info=&per_cpu(omap4_pm_info,0x0);if(sar_base){
@@ -444,3 +442,26 @@ int __init omap4_mpuss_init(void)}#endif++/*+*Forkexec,wemustsetCPU1_WAKEUP_NS_PA_ADDRtopointto+*currentkernel'ssecondary_startup()earlybefore+*clockdomains_init().Otherwiseclockdomain_init()can+*wakeCPU1andcauseahang.+*/+void__initomap4_mpuss_early_init(void)+{+unsignedlongstartup_pa;++if(!cpu_is_omap44xx())+return;++sar_base=omap4_get_sar_ram_base();++if(cpu_is_omap443x())+startup_pa=virt_to_phys(omap4_secondary_startup);+else+startup_pa=virt_to_phys(omap4460_secondary_startup);++writel_relaxed(startup_pa,sar_base+CPU1_WAKEUP_NS_PA_ADDR_OFFSET);+}
We need to reset CPU1 properly for kexec when booting different
kernel versions. Otherwise CPU1 will attempt to boot the the
previous kernel's start_secondary(). Note that the restctrl
register is different from the low-power mode wakeup register
CPU1_WAKEUP_NS_PA_ADDR. We need to configure both.
Let's fix the issue by defining SoC specific data to initialize
things in a more generic way. And let's also standardize omap-smp.c
to use soc_is instead of cpu_is while at it.
Signed-off-by: Tony Lindgren <tony@atomide.com>
---
arch/arm/mach-omap2/omap-smp.c | 95 ++++++++++++++++++++++++++++++------------
1 file changed, 69 insertions(+), 26 deletions(-)
Hi all,
Here are some patches to make kexec work for SMP omaps. To test
these you need to use the latest kexec-tools.git kexec with
Russell's recent patches in "[PATCH 0/2] Simple fix to the ARM
kexec tools implementation" thread fixed for 6x. Or else you
need to use appended DTB.
I've tested these so far on 4430 duovero, omap5-uevm, and
beagle-x15.
Tony Lindgren (4):
ARM: OMAP4+: Initialize SAR RAM base early for proper CPU1 reset for
kexec
ARM: OMAP4+: Prevent CPU1 related hang with kexec
ARM: OMAP4+: Reset CPU1 properly for kexec
ARM: OMAP4+: Allow kexec on SMP variants
I suggest to do bit wider testing including PM. From
quick scan, the series looks fine to me.
FWIW, Acked-by: Santosh Shilimkar [off-list ref]
On Tuesday 21 June 2016 01:22 PM, Tony Lindgren wrote:
Hi all,
Here are some patches to make kexec work for SMP omaps. To test
these you need to use the latest kexec-tools.git kexec with
Russell's recent patches in "[PATCH 0/2] Simple fix to the ARM
kexec tools implementation" thread fixed for 6x. Or else you
need to use appended DTB.
I've tested these so far on 4430 duovero, omap5-uevm, and
beagle-x15.
More testing done with above configuration + kexec_tools change below:
initrd_base = kernel_base + _ALIGN(len * 7, getpagesize());
kexec works fine on:
am437x-gp-evm, am437x-sk-evm
am335x-bone
dra72-evm
dra7-evm
omap5-uevm
Tested-by: Keerthy <j-keerthy@ti.com>
Regards,
Keerthy
Regards,
Tony
Tony Lindgren (4):
ARM: OMAP4+: Initialize SAR RAM base early for proper CPU1 reset for
kexec
ARM: OMAP4+: Prevent CPU1 related hang with kexec
ARM: OMAP4+: Reset CPU1 properly for kexec
ARM: OMAP4+: Allow kexec on SMP variants
arch/arm/mach-omap2/Makefile | 4 +-
arch/arm/mach-omap2/common.h | 8 ++-
arch/arm/mach-omap2/io.c | 3 +
arch/arm/mach-omap2/omap-hotplug.c | 6 ++
arch/arm/mach-omap2/omap-mpuss-lowpower.c | 29 ++++++++--
arch/arm/mach-omap2/omap-smp.c | 96 ++++++++++++++++++++++---------
arch/arm/mach-omap2/omap4-common.c | 14 ++---
7 files changed, 118 insertions(+), 42 deletions(-)
@@ -8,7 +8,7 @@ ccflags-y := -I$(srctree)/$(src)/include \# Common supportobj-y:=id.oio.ocontrol.omux.odevices.ofb.oserial.otimer.opm.o\common.ogpio.odma.owd_timer.odisplay.oi2c.ohdq1w.oomap_hwmod.o\-omap_device.osram.odrm.o+omap_device.oomap-headsmp.osram.odrm.ohwmod-common=omap_hwmod.oomap_hwmod_reset.o\omap_hwmod_common_data.o
@@ -32,7 +32,7 @@ obj-$(CONFIG_SOC_HAS_OMAP2_SDRC) += sdrc.o# SMP support ONLY available for OMAP4-smp-$(CONFIG_SMP)+=omap-smp.oomap-headsmp.o+smp-$(CONFIG_SMP)+=omap-smp.osmp-$(CONFIG_HOTPLUG_CPU)+=omap-hotplug.oomap-4-5-common=omap4-common.oomap-wakeupgen.o
This doesn't work:
arch/arm/mach-omap2/built-in.o: In function `omap5_secondary_startup':
dss-common.c:(.text+0x4cc4): undefined reference to `secondary_startup'
arch/arm/mach-omap2/built-in.o: In function `hyp_boot':
dss-common.c:(.text+0x4cf0): undefined reference to `secondary_startup'
arch/arm/mach-omap2/built-in.o: In function `omap4_secondary_startup':
dss-common.c:(.text+0x4d14): undefined reference to `secondary_startup'
arch/arm/mach-omap2/built-in.o: In function `omap4460_secondary_startup':
dss-common.c:(.text+0x4d48): undefined reference to `secondary_startup'
secondary_startup() is not defined when CONFIG_SMP is disabled.
Arnd
This doesn't work:
arch/arm/mach-omap2/built-in.o: In function `omap5_secondary_startup':
dss-common.c:(.text+0x4cc4): undefined reference to `secondary_startup'
arch/arm/mach-omap2/built-in.o: In function `hyp_boot':
dss-common.c:(.text+0x4cf0): undefined reference to `secondary_startup'
arch/arm/mach-omap2/built-in.o: In function `omap4_secondary_startup':
dss-common.c:(.text+0x4d14): undefined reference to `secondary_startup'
arch/arm/mach-omap2/built-in.o: In function `omap4460_secondary_startup':
dss-common.c:(.text+0x4d48): undefined reference to `secondary_startup'
secondary_startup() is not defined when CONFIG_SMP is disabled.
Oh sorry. Looks like I did not properly check the compiler output
while fixing up the randconfig errors I got earlier. Below is a
fix for this build error.
Regards,
Tony
8< -----------------
From: Tony Lindgren <tony@atomide.com>
Date: Sun, 26 Jun 2016 22:47:06 -0700
Subject: [PATCH] ARM: OMAP2+: Fix build if CONFIG_SMP is not set
Looks like I only partially fixed up things if CONFIG_SMP
is not set for the recent kexec changes. We don't have
boot_secondary available without SMP as reported by Arnd.
Reported-by: Arnd Bergmann <arnd@arndb.de>
Signed-off-by: Tony Lindgren <tony@atomide.com>
@@ -82,7 +92,7 @@ hold: ldr r12,=0x103*we've been released from the wait loop,secondary_stack*shouldnowcontaintheSVCstackforthiscore*/-bsecondary_startup+bomap_secondary_startupENDPROC(omap4_secondary_startup)ENTRY(omap4460_secondary_startup)
@@ -119,5 +129,5 @@ hold_2: ldr r12,=0x103*we've been released from the wait loop,secondary_stack*shouldnowcontaintheSVCstackforthiscore*/-bsecondary_startup+bomap_secondary_startupENDPROC(omap4460_secondary_startup)