]> git.ipfire.org Git - thirdparty/kernel/linux.git/commitdiff
ARM: rockchip: fix kernel hang during smp initialization
authorAlexander Kochetkov <al.kochet@gmail.com>
Thu, 3 Jul 2025 14:04:53 +0000 (17:04 +0300)
committerHeiko Stuebner <heiko@sntech.de>
Mon, 14 Jul 2025 13:38:40 +0000 (15:38 +0200)
In order to bring up secondary CPUs main CPU write trampoline
code to SRAM. The trampoline code is written while secondary
CPUs are powered on (at least that true for RK3188 CPU).
Sometimes that leads to kernel hang. Probably because secondary
CPU execute trampoline code while kernel doesn't expect.

The patch moves SRAM initialization step to the point where all
secondary CPUs are powered down.

That fixes rarely hangs on RK3188:
[    0.091568] CPU0: thread -1, cpu 0, socket 0, mpidr 80000000
[    0.091996] rockchip_smp_prepare_cpus: ncores 4

Signed-off-by: Alexander Kochetkov <al.kochet@gmail.com>
Link: https://lore.kernel.org/r/20250703140453.1273027-1-al.kochet@gmail.com
Signed-off-by: Heiko Stuebner <heiko@sntech.de>
arch/arm/mach-rockchip/platsmp.c

index 36915a073c2340c5813355a1d863c8bf97ca4a81..f432d22bfed8444267b31236d2b0cbed25c23f6a 100644 (file)
@@ -279,11 +279,6 @@ static void __init rockchip_smp_prepare_cpus(unsigned int max_cpus)
        }
 
        if (read_cpuid_part() == ARM_CPU_PART_CORTEX_A9) {
-               if (rockchip_smp_prepare_sram(node)) {
-                       of_node_put(node);
-                       return;
-               }
-
                /* enable the SCU power domain */
                pmu_set_power_domain(PMU_PWRDN_SCU, true);
 
@@ -316,11 +311,19 @@ static void __init rockchip_smp_prepare_cpus(unsigned int max_cpus)
                asm ("mrc p15, 1, %0, c9, c0, 2\n" : "=r" (l2ctlr));
                ncores = ((l2ctlr >> 24) & 0x3) + 1;
        }
-       of_node_put(node);
 
        /* Make sure that all cores except the first are really off */
        for (i = 1; i < ncores; i++)
                pmu_set_power_domain(0 + i, false);
+
+       if (read_cpuid_part() == ARM_CPU_PART_CORTEX_A9) {
+               if (rockchip_smp_prepare_sram(node)) {
+                       of_node_put(node);
+                       return;
+               }
+       }
+
+       of_node_put(node);
 }
 
 static void __init rk3036_smp_prepare_cpus(unsigned int max_cpus)