xref: /OK3568_Linux_fs/kernel/arch/arm/mach-tango/platsmp.c (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun // SPDX-License-Identifier: GPL-2.0
2*4882a593Smuzhiyun #include <linux/delay.h>
3*4882a593Smuzhiyun #include <linux/init.h>
4*4882a593Smuzhiyun #include <linux/smp.h>
5*4882a593Smuzhiyun #include "smc.h"
6*4882a593Smuzhiyun 
tango_boot_secondary(unsigned int cpu,struct task_struct * idle)7*4882a593Smuzhiyun static int tango_boot_secondary(unsigned int cpu, struct task_struct *idle)
8*4882a593Smuzhiyun {
9*4882a593Smuzhiyun 	tango_set_aux_boot_addr(__pa_symbol(secondary_startup));
10*4882a593Smuzhiyun 	tango_start_aux_core(cpu);
11*4882a593Smuzhiyun 	return 0;
12*4882a593Smuzhiyun }
13*4882a593Smuzhiyun 
14*4882a593Smuzhiyun #ifdef CONFIG_HOTPLUG_CPU
15*4882a593Smuzhiyun /*
16*4882a593Smuzhiyun  * cpu_kill() and cpu_die() run concurrently on different cores.
17*4882a593Smuzhiyun  * Firmware will only "kill" a core once it has properly "died".
18*4882a593Smuzhiyun  * Try a few times to kill a core before giving up, and sleep
19*4882a593Smuzhiyun  * between tries to give that core enough time to die.
20*4882a593Smuzhiyun  */
tango_cpu_kill(unsigned int cpu)21*4882a593Smuzhiyun static int tango_cpu_kill(unsigned int cpu)
22*4882a593Smuzhiyun {
23*4882a593Smuzhiyun 	int i, err;
24*4882a593Smuzhiyun 
25*4882a593Smuzhiyun 	for (i = 0; i < 10; ++i) {
26*4882a593Smuzhiyun 		msleep(10);
27*4882a593Smuzhiyun 		err = tango_aux_core_kill(cpu);
28*4882a593Smuzhiyun 		if (!err)
29*4882a593Smuzhiyun 			return true;
30*4882a593Smuzhiyun 	}
31*4882a593Smuzhiyun 
32*4882a593Smuzhiyun 	return false;
33*4882a593Smuzhiyun }
34*4882a593Smuzhiyun 
tango_cpu_die(unsigned int cpu)35*4882a593Smuzhiyun static void tango_cpu_die(unsigned int cpu)
36*4882a593Smuzhiyun {
37*4882a593Smuzhiyun 	while (tango_aux_core_die(cpu) < 0)
38*4882a593Smuzhiyun 		cpu_relax();
39*4882a593Smuzhiyun 
40*4882a593Smuzhiyun 	panic("cpu %d failed to die\n", cpu);
41*4882a593Smuzhiyun }
42*4882a593Smuzhiyun #endif
43*4882a593Smuzhiyun 
44*4882a593Smuzhiyun static const struct smp_operations tango_smp_ops __initconst = {
45*4882a593Smuzhiyun 	.smp_boot_secondary	= tango_boot_secondary,
46*4882a593Smuzhiyun #ifdef CONFIG_HOTPLUG_CPU
47*4882a593Smuzhiyun 	.cpu_kill		= tango_cpu_kill,
48*4882a593Smuzhiyun 	.cpu_die		= tango_cpu_die,
49*4882a593Smuzhiyun #endif
50*4882a593Smuzhiyun };
51*4882a593Smuzhiyun 
52*4882a593Smuzhiyun CPU_METHOD_OF_DECLARE(tango4_smp, "sigma,tango4-smp", &tango_smp_ops);
53