summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDaisuke Nojiri <dnojiri@chromium.org>2020-05-22 13:54:49 -0700
committerCommit Bot <commit-bot@chromium.org>2020-06-09 00:53:20 +0000
commita46980b1865aeaed3d685e5ff2b14f790159894a (patch)
treed1478be414fd9032694243e7d514b99e64c83384
parente938e49b2d7319158d46f596fbee38a066f11a99 (diff)
downloadchrome-ec-a46980b1865aeaed3d685e5ff2b14f790159894a.tar.gz
x86 power: Initialize chipset state to S5 after sysjump
Currently, RW initializes the chipset state to G3 and forces the chipset to shut down unless the AP is already powered on. This behavior is based on the assumption that sysjump happens only upon a request from the AP. With EFS2, it's no longer the case because EC jumps while the AP is off. AP may be off, resetting (i.e. s0->s5->s0), or shutting down (s0->s5). This patch makes RW set the chipset state to S5 if the corresponding power signals are on. BUG=b:154778457 BRANCH=none TEST=Verify test_that suite:faft_bios passes. Signed-off-by: Daisuke Nojiri <dnojiri@chromium.org> Change-Id: I65cbb6c6e7f8a01e80d83a74e376ceb9628b9789 Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/platform/ec/+/2213733 Reviewed-by: Aseda Aboagye <aaboagye@chromium.org> Reviewed-by: Aaron Durbin <adurbin@google.com>
-rw-r--r--power/intel_x86.c40
1 files changed, 26 insertions, 14 deletions
diff --git a/power/intel_x86.c b/power/intel_x86.c
index a4de71ff5f..8457c3bb0a 100644
--- a/power/intel_x86.c
+++ b/power/intel_x86.c
@@ -340,23 +340,35 @@ void chipset_throttle_cpu(int throttle)
enum power_state power_chipset_init(void)
{
+ CPRINTS("%s: power_signal=0x%x", __func__, power_get_signals());
+
+ if (!system_jumped_to_this_image())
+ return POWER_G3;
/*
- * If we're switching between images without rebooting, see if the x86
- * is already powered on; if so, leave it there instead of cycling
- * through G3.
+ * We are here as RW. We need to handle the following cases:
+ *
+ * 1. Late sysjump by software sync. AP is in S0.
+ * 2. Shutting down in recovery mode then sysjump by EFS2. AP is in S5
+ * and expected to sequence down.
+ * 3. Rebooting from recovery mode then sysjump by EFS2. AP is in S5
+ * and expected to sequence up.
+ * 4. RO jumps to RW from main() by EFS2. (a.k.a. power on reset, cold
+ * reset). AP is in G3.
*/
- if (system_jumped_to_this_image()) {
- if ((power_get_signals() & IN_ALL_S0) == IN_ALL_S0) {
- /* Disable idle task deep sleep when in S0. */
- disable_sleep(SLEEP_MASK_AP_RUN);
- CPRINTS("already in S0");
- return POWER_S0;
- }
-
- /* Force all signals to their G3 states */
- chipset_force_g3();
+ if ((power_get_signals() & IN_ALL_S0) == IN_ALL_S0) {
+ /* case #1. Disable idle task deep sleep when in S0. */
+ disable_sleep(SLEEP_MASK_AP_RUN);
+ CPRINTS("already in S0");
+ return POWER_S0;
}
-
+ if ((power_get_signals() & CHIPSET_G3S5_POWERUP_SIGNAL)
+ == CHIPSET_G3S5_POWERUP_SIGNAL) {
+ /* case #2 & #3 */
+ CPRINTS("already in S5");
+ return POWER_S5;
+ }
+ /* case #4 */
+ chipset_force_g3();
return POWER_G3;
}