mirror of
https://github.com/ARM-software/arm-trusted-firmware.git
synced 2025-04-15 17:14:21 +00:00
clear wakeup enable bit upon resuming from suspend
The FVP specific code that gets called after a cpu has been physically powered on after having been turned off or suspended earlier does not clear the PWRC.PWKUPR.WEN bit. Not doing so causes problems if: a cpu is suspended, woken from suspend, powered down through a cpu_off call & receives a spurious interrupt. Since the WEN bit is not cleared after the cpu woke up from suspend, the spurious wakeup will power the cpu on. Since the cpu_off call clears the jump address in the mailbox this spurious wakeup will cause the cpu to crash. This patch fixes this issue by clearing the WEN bit whenever a cpu is powered up. Change-Id: Ic91f5dffe1ed01d76bc7fc807acf0ecd3e38ce5b
This commit is contained in:
parent
4a826ddad8
commit
b127cdb879
4 changed files with 21 additions and 3 deletions
|
@ -45,6 +45,9 @@ Detailed changes since last release
|
|||
instructions for how to contribute and update copyright text in all files to
|
||||
acknowledge contributors.
|
||||
|
||||
* The wake up enable bit in the FVP power controller is cleared when a cpu is
|
||||
physically powered up to prevent a spurious wake up from a subsequent cpu
|
||||
off state.
|
||||
|
||||
ARM Trusted Firmware - version 0.2
|
||||
==================================
|
||||
|
|
|
@ -77,7 +77,7 @@ void fvp_pwrc_write_ppoffr(unsigned long mpidr)
|
|||
bakery_lock_release(mpidr, &pwrc_lock);
|
||||
}
|
||||
|
||||
void fvp_pwrc_write_pwkupr(unsigned long mpidr)
|
||||
void fvp_pwrc_set_wen(unsigned long mpidr)
|
||||
{
|
||||
bakery_lock_get(mpidr, &pwrc_lock);
|
||||
mmio_write_32(PWRC_BASE + PWKUPR_OFF,
|
||||
|
@ -85,6 +85,14 @@ void fvp_pwrc_write_pwkupr(unsigned long mpidr)
|
|||
bakery_lock_release(mpidr, &pwrc_lock);
|
||||
}
|
||||
|
||||
void fvp_pwrc_clr_wen(unsigned long mpidr)
|
||||
{
|
||||
bakery_lock_get(mpidr, &pwrc_lock);
|
||||
mmio_write_32(PWRC_BASE + PWKUPR_OFF,
|
||||
(unsigned int) mpidr);
|
||||
bakery_lock_release(mpidr, &pwrc_lock);
|
||||
}
|
||||
|
||||
void fvp_pwrc_write_pcoffr(unsigned long mpidr)
|
||||
{
|
||||
bakery_lock_get(mpidr, &pwrc_lock);
|
||||
|
|
|
@ -67,7 +67,8 @@ extern int fvp_pwrc_setup(void);
|
|||
extern void fvp_pwrc_write_pcoffr(unsigned long);
|
||||
extern void fvp_pwrc_write_ppoffr(unsigned long);
|
||||
extern void fvp_pwrc_write_pponr(unsigned long);
|
||||
extern void fvp_pwrc_write_pwkupr(unsigned long);
|
||||
extern void fvp_pwrc_set_wen(unsigned long);
|
||||
extern void fvp_pwrc_clr_wen(unsigned long);
|
||||
extern unsigned int fvp_pwrc_read_psysr(unsigned long);
|
||||
extern unsigned int fvp_pwrc_get_cpu_wkr(unsigned long);
|
||||
|
||||
|
|
|
@ -251,7 +251,7 @@ int fvp_affinst_suspend(unsigned long mpidr,
|
|||
* Program the power controller to power this
|
||||
* cpu off and enable wakeup interrupts.
|
||||
*/
|
||||
fvp_pwrc_write_pwkupr(mpidr);
|
||||
fvp_pwrc_set_wen(mpidr);
|
||||
fvp_pwrc_write_ppoffr(mpidr);
|
||||
}
|
||||
break;
|
||||
|
@ -309,6 +309,12 @@ int fvp_affinst_on_finish(unsigned long mpidr,
|
|||
write_cpuectlr(ectlr);
|
||||
}
|
||||
|
||||
/*
|
||||
* Clear PWKUPR.WEN bit to ensure interrupts do not interfere
|
||||
* with a cpu power down unless the bit is set again
|
||||
*/
|
||||
fvp_pwrc_clr_wen(mpidr);
|
||||
|
||||
/* Zero the jump address in the mailbox for this cpu */
|
||||
fvp_mboxes = (mailbox *) (TZDRAM_BASE + MBOX_OFF);
|
||||
linear_id = platform_get_core_pos(mpidr);
|
||||
|
|
Loading…
Add table
Reference in a new issue