ARM: 8847/1: pm: fix HYP/SVC mode mismatch when MCPM is used
authorMarek Szyprowski <m.szyprowski@samsung.com>
Mon, 18 Feb 2019 08:31:41 +0000 (09:31 +0100)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Wed, 29 Jan 2020 09:24:18 +0000 (10:24 +0100)
[ Upstream commit ca70ea43f80c98582f5ffbbd1e6f4da2742da0c4 ]

MCPM does a soft reset of the CPUs and uses common cpu_resume() routine to
perform low-level platform initialization. This results in a try to install
HYP stubs for the second time for each CPU and results in false HYP/SVC
mode mismatch detection. The HYP stubs are already installed at the
beginning of the kernel initialization on the boot CPU (head.S) or in the
secondary_startup() for other CPUs. To fix this issue MCPM code should use
a cpu_resume() routine without HYP stubs installation.

This change fixes HYP/SVC mode mismatch on Samsung Exynos5422-based Odroid
XU3/XU4/HC1 boards.

Fixes: 3721924c8154 ("ARM: 8081/1: MCPM: provide infrastructure to allow for MCPM loopback")
Signed-off-by: Marek Szyprowski <m.szyprowski@samsung.com>
Acked-by: Nicolas Pitre <nico@linaro.org>
Tested-by: Anand Moon <linux.amoon@gmail.com>
Signed-off-by: Russell King <rmk+kernel@armlinux.org.uk>
Signed-off-by: Sasha Levin <sashal@kernel.org>
arch/arm/common/mcpm_entry.c
arch/arm/include/asm/suspend.h
arch/arm/kernel/sleep.S

index a923524d1040734d1f5b94b4a6e2f5d59cab99d1..8617323eb2735e80a6066f1023c857531237e40f 100644 (file)
@@ -379,7 +379,7 @@ static int __init nocache_trampoline(unsigned long _arg)
        unsigned int cluster = MPIDR_AFFINITY_LEVEL(mpidr, 1);
        phys_reset_t phys_reset;
 
-       mcpm_set_entry_vector(cpu, cluster, cpu_resume);
+       mcpm_set_entry_vector(cpu, cluster, cpu_resume_no_hyp);
        setup_mm_for_reboot();
 
        __mcpm_cpu_going_down(cpu, cluster);
index 6c7182f32cefeb247068e80af9944b4ff01e3727..e6c2f426f8c866d700db5562aa6d8cd87d3c0248 100644 (file)
@@ -7,6 +7,7 @@ struct sleep_save_sp {
 };
 
 extern void cpu_resume(void);
+extern void cpu_resume_no_hyp(void);
 extern void cpu_resume_arm(void);
 extern int cpu_suspend(unsigned long, int (*)(unsigned long));
 
index 0f6c1000582c359881b6985c57d010037cb4ac17..c8569390e7e7e8f39eb333de26aba62c9221c1ef 100644 (file)
@@ -119,6 +119,14 @@ ENDPROC(cpu_resume_after_mmu)
        .text
        .align
 
+#ifdef CONFIG_MCPM
+       .arm
+THUMB( .thumb                  )
+ENTRY(cpu_resume_no_hyp)
+ARM_BE8(setend be)                     @ ensure we are in BE mode
+       b       no_hyp
+#endif
+
 #ifdef CONFIG_MMU
        .arm
 ENTRY(cpu_resume_arm)
@@ -134,6 +142,7 @@ ARM_BE8(setend be)                  @ ensure we are in BE mode
        bl      __hyp_stub_install_secondary
 #endif
        safe_svcmode_maskall r1
+no_hyp:
        mov     r1, #0
        ALT_SMP(mrc p15, 0, r0, c0, c0, 5)
        ALT_UP_B(1f)
@@ -162,6 +171,9 @@ ENDPROC(cpu_resume)
 
 #ifdef CONFIG_MMU
 ENDPROC(cpu_resume_arm)
+#endif
+#ifdef CONFIG_MCPM
+ENDPROC(cpu_resume_no_hyp)
 #endif
 
        .align 2