Merge pull request #793 from jeenu-arm/gic-changes
GIC driver changes for extended power management
This commit is contained in:
commit
9acdafbccf
|
@ -40,6 +40,13 @@
|
|||
static const gicv3_driver_data_t *driver_data;
|
||||
static unsigned int gicv2_compat;
|
||||
|
||||
/*
|
||||
* Redistributor power operations are weakly bound so that they can be
|
||||
* overridden
|
||||
*/
|
||||
#pragma weak gicv3_rdistif_off
|
||||
#pragma weak gicv3_rdistif_on
|
||||
|
||||
/*******************************************************************************
|
||||
* This function initialises the ARM GICv3 driver in EL3 with provided platform
|
||||
* inputs.
|
||||
|
@ -188,6 +195,9 @@ void gicv3_rdistif_init(unsigned int proc_num)
|
|||
|
||||
assert(IS_IN_EL3());
|
||||
|
||||
/* Power on redistributor */
|
||||
gicv3_rdistif_on(proc_num);
|
||||
|
||||
gicr_base = driver_data->rdistif_base_addrs[proc_num];
|
||||
|
||||
/* Set the default attribute of all SGIs and PPIs */
|
||||
|
@ -210,6 +220,19 @@ void gicv3_rdistif_init(unsigned int proc_num)
|
|||
}
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
* Functions to perform power operations on GIC Redistributor
|
||||
******************************************************************************/
|
||||
void gicv3_rdistif_off(unsigned int proc_num)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
void gicv3_rdistif_on(unsigned int proc_num)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
* This function enables the GIC CPU interface of the calling CPU using only
|
||||
* system register accesses.
|
||||
|
|
|
@ -259,6 +259,8 @@ typedef struct gicv3_driver_data {
|
|||
void gicv3_driver_init(const gicv3_driver_data_t *plat_driver_data);
|
||||
void gicv3_distif_init(void);
|
||||
void gicv3_rdistif_init(unsigned int proc_num);
|
||||
void gicv3_rdistif_on(unsigned int proc_num);
|
||||
void gicv3_rdistif_off(unsigned int proc_num);
|
||||
void gicv3_cpuif_enable(unsigned int proc_num);
|
||||
void gicv3_cpuif_disable(unsigned int proc_num);
|
||||
unsigned int gicv3_get_pending_interrupt_type(void);
|
||||
|
|
|
@ -194,6 +194,8 @@ void plat_arm_gic_driver_init(void);
|
|||
void plat_arm_gic_init(void);
|
||||
void plat_arm_gic_cpuif_enable(void);
|
||||
void plat_arm_gic_cpuif_disable(void);
|
||||
void plat_arm_gic_redistif_on(void);
|
||||
void plat_arm_gic_redistif_off(void);
|
||||
void plat_arm_gic_pcpu_init(void);
|
||||
void plat_arm_security_setup(void);
|
||||
void plat_arm_pwrc_setup(void);
|
||||
|
|
|
@ -64,19 +64,6 @@ const unsigned int arm_pm_idle_states[] = {
|
|||
};
|
||||
#endif
|
||||
|
||||
/*******************************************************************************
|
||||
* Function which implements the common FVP specific operations to power down a
|
||||
* cpu in response to a CPU_OFF or CPU_SUSPEND request.
|
||||
******************************************************************************/
|
||||
static void fvp_cpu_pwrdwn_common(void)
|
||||
{
|
||||
/* Prevent interrupts from spuriously waking up this cpu */
|
||||
plat_arm_gic_cpuif_disable();
|
||||
|
||||
/* Program the power controller to power off this cpu. */
|
||||
fvp_pwrc_write_ppoffr(read_mpidr_el1());
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
* Function which implements the common FVP specific operations to power down a
|
||||
* cluster in response to a CPU_OFF or CPU_SUSPEND request.
|
||||
|
@ -180,7 +167,15 @@ void fvp_pwr_domain_off(const psci_power_state_t *target_state)
|
|||
* suspended. Perform at least the cpu specific actions followed
|
||||
* by the cluster specific operations if applicable.
|
||||
*/
|
||||
fvp_cpu_pwrdwn_common();
|
||||
|
||||
/* Prevent interrupts from spuriously waking up this cpu */
|
||||
plat_arm_gic_cpuif_disable();
|
||||
|
||||
/* Turn redistributor off */
|
||||
plat_arm_gic_redistif_off();
|
||||
|
||||
/* Program the power controller to power off this cpu. */
|
||||
fvp_pwrc_write_ppoffr(read_mpidr_el1());
|
||||
|
||||
if (target_state->pwr_domain_state[ARM_PWR_LVL1] ==
|
||||
ARM_LOCAL_STATE_OFF)
|
||||
|
@ -213,8 +208,17 @@ void fvp_pwr_domain_suspend(const psci_power_state_t *target_state)
|
|||
/* Program the power controller to enable wakeup interrupts. */
|
||||
fvp_pwrc_set_wen(mpidr);
|
||||
|
||||
/* Perform the common cpu specific operations */
|
||||
fvp_cpu_pwrdwn_common();
|
||||
/* Prevent interrupts from spuriously waking up this cpu */
|
||||
plat_arm_gic_cpuif_disable();
|
||||
|
||||
/*
|
||||
* The Redistributor is not powered off as it can potentially prevent
|
||||
* wake up events reaching the CPUIF and/or might lead to losing
|
||||
* register context.
|
||||
*/
|
||||
|
||||
/* Program the power controller to power off this cpu. */
|
||||
fvp_pwrc_write_ppoffr(read_mpidr_el1());
|
||||
|
||||
/* Perform the common cluster specific operations */
|
||||
if (target_state->pwr_domain_state[ARM_PWR_LVL1] ==
|
||||
|
|
|
@ -97,3 +97,17 @@ void plat_arm_gic_pcpu_init(void)
|
|||
{
|
||||
gicv2_pcpu_distif_init();
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
* Stubs for Redistributor power management. Although GICv2 doesn't have
|
||||
* Redistributor interface, these are provided for the sake of uniform GIC API
|
||||
*****************************************************************************/
|
||||
void plat_arm_gic_redistif_on(void)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
void plat_arm_gic_redistif_off(void)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
|
|
@ -43,6 +43,8 @@
|
|||
#pragma weak plat_arm_gic_cpuif_enable
|
||||
#pragma weak plat_arm_gic_cpuif_disable
|
||||
#pragma weak plat_arm_gic_pcpu_init
|
||||
#pragma weak plat_arm_gic_redistif_on
|
||||
#pragma weak plat_arm_gic_redistif_off
|
||||
|
||||
/* The GICv3 driver only needs to be initialized in EL3 */
|
||||
static uintptr_t rdistif_base_addrs[PLATFORM_CORE_COUNT];
|
||||
|
@ -115,3 +117,16 @@ void plat_arm_gic_pcpu_init(void)
|
|||
{
|
||||
gicv3_rdistif_init(plat_my_core_pos());
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
* ARM common helpers to power GIC redistributor interface
|
||||
*****************************************************************************/
|
||||
void plat_arm_gic_redistif_on(void)
|
||||
{
|
||||
gicv3_rdistif_on(plat_my_core_pos());
|
||||
}
|
||||
|
||||
void plat_arm_gic_redistif_off(void)
|
||||
{
|
||||
gicv3_rdistif_off(plat_my_core_pos());
|
||||
}
|
||||
|
|
|
@ -94,3 +94,17 @@ void plat_arm_gic_pcpu_init(void)
|
|||
{
|
||||
arm_gic_pcpu_distif_setup();
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
* Stubs for Redistributor power management. Although legacy configuration isn't
|
||||
* supported, these are provided for the sake of uniform GIC API
|
||||
*****************************************************************************/
|
||||
void plat_arm_gic_redistif_on(void)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
void plat_arm_gic_redistif_off(void)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue