summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLouis Yung-Chieh Lo <yjlou@chromium.org>2014-05-06 17:12:52 -0700
committerchrome-internal-fetch <chrome-internal-fetch@google.com>2014-05-09 04:45:19 +0000
commit2cff588c1aaf05db05d07a4325881dffe24db761 (patch)
tree745ebbf5a1a2d303d249e22438040e5014fbe2eb
parent6803674335d88f7ce1b3f61b2b19b88f55464116 (diff)
downloadchrome-ec-2cff588c1aaf05db05d07a4325881dffe24db761.tar.gz
tegra: fixed a corner case that AP_OFF flag is not cleared.
If we follow the TEST steps below, the power state machine in AP and EC were out of sync -- due to the un-clear bit and wrong initial power state. BUG=chrome-os-partner:24835 BRANCH=tot,nyan TEST=on big. > reboot > power off // De-assert XPSHOLD > reboot ap-off > sysinfo // This reset flags does NOT contain "ap-off". > power on % ectool reboot_ec RW // The following message is NOT observed. // "system is on, but RESET_FLAG_AP_OFF is on". > power // This should show the AP is "on". // ensure everything still works. > reboot ap-off // AP keeps off. > reboot // AP is on. Change-Id: I51afed7201d16ebcd889ad12a7af90026591cc2d Signed-off-by: Louis Yung-Chieh Lo <yjlou@chromium.org> Reviewed-on: https://chromium-review.googlesource.com/198587 Reviewed-by: David Hendricks <dhendrix@chromium.org>
-rw-r--r--power/tegra.c19
1 files changed, 16 insertions, 3 deletions
diff --git a/power/tegra.c b/power/tegra.c
index fe549f41db..91d10790bd 100644
--- a/power/tegra.c
+++ b/power/tegra.c
@@ -231,6 +231,8 @@ DECLARE_HOOK(HOOK_LID_CHANGE, tegra_lid_event, HOOK_PRIO_DEFAULT);
enum power_state power_chipset_init(void)
{
+ int init_power_state;
+
/*
* Force the AP shutdown unless we are doing SYSJUMP. Otherwise,
* the AP could stay in strange state.
@@ -244,6 +246,14 @@ enum power_state power_chipset_init(void)
* flash SPI from USB).
*/
chipset_reset(0);
+
+ init_power_state = POWER_G3;
+ } else {
+ /* In the SYSJUMP case, we check if the AP is on */
+ if (power_get_signals() & IN_XPSHOLD)
+ init_power_state = POWER_S0;
+ else
+ init_power_state = POWER_G3;
}
/* Leave power off only if requested by reset flags */
@@ -253,7 +263,7 @@ enum power_state power_chipset_init(void)
auto_power_on = 1;
}
- return POWER_G3;
+ return init_power_state;
}
/*****************************************************************************/
@@ -293,13 +303,16 @@ void chipset_force_shutdown(void)
*/
static int check_for_power_on_event(void)
{
+ int ap_off_flag;
+
+ ap_off_flag = system_get_reset_flags() & RESET_FLAG_AP_OFF;
+ system_clear_reset_flags(RESET_FLAG_AP_OFF);
/* check if system is already ON */
if (power_get_signals() & IN_XPSHOLD) {
- if (system_get_reset_flags() & RESET_FLAG_AP_OFF) {
+ if (ap_off_flag) {
CPRINTF(
"[%T system is on, but "
"RESET_FLAG_AP_OFF is on]\n");
- system_clear_reset_flags(RESET_FLAG_AP_OFF);
return 0;
} else {
CPRINTF(