Provide a hint to power controller for DSU cluster power down

By writing 0 to CLUSTERPWRDN DSU register bit 0, we send an
advisory to the power controller that cluster power is not required
when all cores are powered down.

The AArch32 CLUSTERPWRDN register is architecturally mapped to the
AArch64 CLUSTERPWRDN_EL1 register

Change-Id: Ie6e67c1c7d811fa25c51e2e405ca7f59bd20c81b
Signed-off-by: Madhukar Pappireddy <madhukar.pappireddy@arm.com>
This commit is contained in:
Madhukar Pappireddy 2019-10-30 14:24:39 -05:00
parent 50d8cf26dc
commit 9cf7f355ce
6 changed files with 71 additions and 1 deletions

View File

@ -701,4 +701,14 @@
#define AMEVTYPER1E p15, 0, c13, c15, 6
#define AMEVTYPER1F p15, 0, c13, c15, 7
/*******************************************************************************
* Definitions for DynamicIQ Shared Unit registers
******************************************************************************/
#define CLUSTERPWRDN p15, 0, c15, c3, 6
/* CLUSTERPWRDN register definitions */
#define DSU_CLUSTER_PWR_OFF 0
#define DSU_CLUSTER_PWR_ON 1
#define DSU_CLUSTER_PWR_MASK U(1)
#endif /* ARCH_H */

View File

@ -336,6 +336,11 @@ DEFINE_DCOP_PARAM_FUNC(cvac, DCCIMVAC)
DEFINE_DCOP_PARAM_FUNC(cvac, DCCMVAC)
#endif
/*
* DynamIQ Shared Unit power management
*/
DEFINE_COPROCR_RW_FUNCS(clusterpwrdn, CLUSTERPWRDN)
/* Previously defined accessor functions with incomplete register names */
#define dsb() dsbsy()
#define dmb() dmbsy()

View File

@ -947,4 +947,14 @@
#define RGSR_EL1 S3_0_C1_C0_5
#define GCR_EL1 S3_0_C1_C0_6
/*******************************************************************************
* Definitions for DynamicIQ Shared Unit registers
******************************************************************************/
#define CLUSTERPWRDN_EL1 S3_0_c15_c3_6
/* CLUSTERPWRDN_EL1 register definitions */
#define DSU_CLUSTER_PWR_OFF 0
#define DSU_CLUSTER_PWR_ON 1
#define DSU_CLUSTER_PWR_MASK U(1)
#endif /* ARCH_H */

View File

@ -520,6 +520,9 @@ DEFINE_RENAME_SYSREG_RW_FUNCS(tfsr_el1, TFSR_EL1)
DEFINE_RENAME_SYSREG_RW_FUNCS(rgsr_el1, RGSR_EL1)
DEFINE_RENAME_SYSREG_RW_FUNCS(gcr_el1, GCR_EL1)
/* DynamIQ Shared Unit power management */
DEFINE_RENAME_SYSREG_RW_FUNCS(clusterpwrdn_el1, CLUSTERPWRDN_EL1)
#define IS_IN_EL(x) \
(GET_EL(read_CurrentEl()) == MODE_EL##x)
@ -582,4 +585,7 @@ static inline uint64_t el_implemented(unsigned int el)
#define read_cpacr() read_cpacr_el1()
#define write_cpacr(_v) write_cpacr_el1(_v)
#define read_clusterpwrdn() read_clusterpwrdn_el1()
#define write_clusterpwrdn(_v) write_clusterpwrdn_el1(_v)
#endif /* ARCH_HELPERS_H */

View File

@ -64,6 +64,25 @@ static void fvp_cluster_pwrdwn_common(void)
/* Disable coherency if this cluster is to be turned off */
fvp_interconnect_disable();
#if HW_ASSISTED_COHERENCY
uint32_t reg;
/*
* If we have determined this core to be the last man standing and we
* intend to power down the cluster proactively, we provide a hint to
* the power controller that cluster power is not required when all
* cores are powered down.
* Note that this is only an advisory to power controller and is supported
* by SoCs with DynamIQ Shared Units only.
*/
reg = read_clusterpwrdn();
/* Clear and set bit 0 : Cluster power not required */
reg &= ~DSU_CLUSTER_PWR_MASK;
reg |= DSU_CLUSTER_PWR_OFF;
write_clusterpwrdn(reg);
#endif
/* Program the power controller to turn the cluster off */
fvp_pwrc_write_pcoffr(mpidr);
}

View File

@ -124,8 +124,28 @@ static void css_power_down_common(const psci_power_state_t *target_state)
plat_arm_gic_cpuif_disable();
/* Cluster is to be turned off, so disable coherency */
if (CSS_CLUSTER_PWR_STATE(target_state) == ARM_LOCAL_STATE_OFF)
if (CSS_CLUSTER_PWR_STATE(target_state) == ARM_LOCAL_STATE_OFF) {
plat_arm_interconnect_exit_coherency();
#if HW_ASSISTED_COHERENCY
uint32_t reg;
/*
* If we have determined this core to be the last man standing and we
* intend to power down the cluster proactively, we provide a hint to
* the power controller that cluster power is not required when all
* cores are powered down.
* Note that this is only an advisory to power controller and is supported
* by SoCs with DynamIQ Shared Units only.
*/
reg = read_clusterpwrdn();
/* Clear and set bit 0 : Cluster power not required */
reg &= ~DSU_CLUSTER_PWR_MASK;
reg |= DSU_CLUSTER_PWR_OFF;
write_clusterpwrdn(reg);
#endif
}
}
/*******************************************************************************