xref: /rk3399_ARM-atf/plat/allwinner/common/sunxi_cpu_ops.c (revision 27f9616fd721145d4db86584c19758de1c05f7d7)
1333d66cfSSamuel Holland /*
2333d66cfSSamuel Holland  * Copyright (c) 2017-2018, ARM Limited and Contributors. All rights reserved.
3333d66cfSSamuel Holland  *
4333d66cfSSamuel Holland  * SPDX-License-Identifier: BSD-3-Clause
5333d66cfSSamuel Holland  */
6333d66cfSSamuel Holland 
7333d66cfSSamuel Holland #include <debug.h>
8333d66cfSSamuel Holland #include <mmio.h>
9333d66cfSSamuel Holland #include <platform_def.h>
10333d66cfSSamuel Holland #include <sunxi_mmap.h>
11333d66cfSSamuel Holland #include <sunxi_cpucfg.h>
12333d66cfSSamuel Holland #include <utils_def.h>
13333d66cfSSamuel Holland 
14333d66cfSSamuel Holland #include "sunxi_private.h"
15333d66cfSSamuel Holland 
16333d66cfSSamuel Holland static void sunxi_cpu_disable_power(unsigned int cluster, unsigned int core)
17333d66cfSSamuel Holland {
18333d66cfSSamuel Holland 	if (mmio_read_32(SUNXI_CPU_POWER_CLAMP_REG(cluster, core)) == 0xff)
19333d66cfSSamuel Holland 		return;
20333d66cfSSamuel Holland 
21*27f9616fSAndre Przywara 	VERBOSE("PSCI: Disabling power to cluster %d core %d\n", cluster, core);
22333d66cfSSamuel Holland 
23333d66cfSSamuel Holland 	mmio_write_32(SUNXI_CPU_POWER_CLAMP_REG(cluster, core), 0xff);
24333d66cfSSamuel Holland }
25333d66cfSSamuel Holland 
26333d66cfSSamuel Holland static void sunxi_cpu_enable_power(unsigned int cluster, unsigned int core)
27333d66cfSSamuel Holland {
28333d66cfSSamuel Holland 	if (mmio_read_32(SUNXI_CPU_POWER_CLAMP_REG(cluster, core)) == 0)
29333d66cfSSamuel Holland 		return;
30333d66cfSSamuel Holland 
31*27f9616fSAndre Przywara 	VERBOSE("PSCI: Enabling power to cluster %d core %d\n", cluster, core);
32333d66cfSSamuel Holland 
33333d66cfSSamuel Holland 	/* Power enable sequence from original Allwinner sources */
34333d66cfSSamuel Holland 	mmio_write_32(SUNXI_CPU_POWER_CLAMP_REG(cluster, core), 0xfe);
35333d66cfSSamuel Holland 	mmio_write_32(SUNXI_CPU_POWER_CLAMP_REG(cluster, core), 0xf8);
36333d66cfSSamuel Holland 	mmio_write_32(SUNXI_CPU_POWER_CLAMP_REG(cluster, core), 0xe0);
37333d66cfSSamuel Holland 	mmio_write_32(SUNXI_CPU_POWER_CLAMP_REG(cluster, core), 0x80);
38333d66cfSSamuel Holland 	mmio_write_32(SUNXI_CPU_POWER_CLAMP_REG(cluster, core), 0x00);
39333d66cfSSamuel Holland }
40333d66cfSSamuel Holland 
41333d66cfSSamuel Holland void sunxi_cpu_off(unsigned int cluster, unsigned int core)
42333d66cfSSamuel Holland {
43*27f9616fSAndre Przywara 	VERBOSE("PSCI: Powering off cluster %d core %d\n", cluster, core);
44333d66cfSSamuel Holland 
45333d66cfSSamuel Holland 	/* Deassert DBGPWRDUP */
46333d66cfSSamuel Holland 	mmio_clrbits_32(SUNXI_CPUCFG_DBG_REG0, BIT(core));
47333d66cfSSamuel Holland 	/* Activate the core output clamps */
48333d66cfSSamuel Holland 	mmio_setbits_32(SUNXI_POWEROFF_GATING_REG(cluster), BIT(core));
49333d66cfSSamuel Holland 	/* Assert CPU power-on reset */
50333d66cfSSamuel Holland 	mmio_clrbits_32(SUNXI_POWERON_RST_REG(cluster), BIT(core));
51333d66cfSSamuel Holland 	/* Remove power from the CPU */
52333d66cfSSamuel Holland 	sunxi_cpu_disable_power(cluster, core);
53333d66cfSSamuel Holland }
54333d66cfSSamuel Holland 
55333d66cfSSamuel Holland void sunxi_cpu_on(unsigned int cluster, unsigned int core)
56333d66cfSSamuel Holland {
57*27f9616fSAndre Przywara 	VERBOSE("PSCI: Powering on cluster %d core %d\n", cluster, core);
58333d66cfSSamuel Holland 
59333d66cfSSamuel Holland 	/* Assert CPU core reset */
60333d66cfSSamuel Holland 	mmio_clrbits_32(SUNXI_CPUCFG_RST_CTRL_REG(cluster), BIT(core));
61333d66cfSSamuel Holland 	/* Assert CPU power-on reset */
62333d66cfSSamuel Holland 	mmio_clrbits_32(SUNXI_POWERON_RST_REG(cluster), BIT(core));
63333d66cfSSamuel Holland 	/* Set CPU to start in AArch64 mode */
64333d66cfSSamuel Holland 	mmio_setbits_32(SUNXI_CPUCFG_CLS_CTRL_REG0(cluster), BIT(24 + core));
65333d66cfSSamuel Holland 	/* Apply power to the CPU */
66333d66cfSSamuel Holland 	sunxi_cpu_enable_power(cluster, core);
67333d66cfSSamuel Holland 	/* Release the core output clamps */
68333d66cfSSamuel Holland 	mmio_clrbits_32(SUNXI_POWEROFF_GATING_REG(cluster), BIT(core));
69333d66cfSSamuel Holland 	/* Deassert CPU power-on reset */
70333d66cfSSamuel Holland 	mmio_setbits_32(SUNXI_POWERON_RST_REG(cluster), BIT(core));
71333d66cfSSamuel Holland 	/* Deassert CPU core reset */
72333d66cfSSamuel Holland 	mmio_setbits_32(SUNXI_CPUCFG_RST_CTRL_REG(cluster), BIT(core));
73333d66cfSSamuel Holland 	/* Assert DBGPWRDUP */
74333d66cfSSamuel Holland 	mmio_setbits_32(SUNXI_CPUCFG_DBG_REG0, BIT(core));
75333d66cfSSamuel Holland }
76333d66cfSSamuel Holland 
77333d66cfSSamuel Holland void sunxi_disable_secondary_cpus(unsigned int primary_cpu)
78333d66cfSSamuel Holland {
79333d66cfSSamuel Holland 	for (unsigned int cpu = 0; cpu < PLATFORM_CORE_COUNT; cpu += 1) {
80333d66cfSSamuel Holland 		if (cpu == primary_cpu)
81333d66cfSSamuel Holland 			continue;
82333d66cfSSamuel Holland 		sunxi_cpu_off(cpu / PLATFORM_MAX_CPUS_PER_CLUSTER,
83333d66cfSSamuel Holland 			       cpu % PLATFORM_MAX_CPUS_PER_CLUSTER);
84333d66cfSSamuel Holland 	}
85333d66cfSSamuel Holland }
86