diff options
author | Mary Ruthven <mruthven@google.com> | 2019-01-29 16:08:02 -0800 |
---|---|---|
committer | chrome-bot <chrome-bot@chromium.org> | 2019-03-06 06:51:02 -0800 |
commit | 36469aa61c23e0e0180541db54f29a292e3d9845 (patch) | |
tree | 2c991489d44ec62b4e912319dcdb878be8ec2911 /board/cr50/ap_state.c | |
parent | b559bd558a357afd29ba4898d22374b3b2050f02 (diff) | |
download | chrome-ec-36469aa61c23e0e0180541db54f29a292e3d9845.tar.gz |
cr50: use closed loop reset based on board property
Use the closed loop reset when cr50 needs to reset the device. Cr50
expects the board to reset in three places: board_reboot_ap,
board_reboot_ec, or during init after any cr50 reset other than deep
sleep. This change modifies these to use the closed loop reset if the
board property is set.
In board_reboot_ap and board_reboot_ec it calls board_closed_loop_reset
instead of doing the normal reset steps if the board property is set. In
init_ap_detect call board_closed_loop_reset if cr50 just resumed from any
reset other than hibernate. Don't trigger the tpm_rst_isr manually.
BUG=b:123544145
BRANCH=cr50
TEST=manual
Flash firmware that supports resetting the AP when EC_RST_L is
asserted.
Reboot cr50 and verify deferred_tpm_rst_isr is only called after
tpm_rst_asserted.
Open Cr50. Verify the AP is reset
Flash old Mistral firmware which seems to take around 12 seconds
for the warm reset to happen.
Boot the AP.
Reboot cr50 while the AP is up.
The AP wont reset for a while.
While the AP is still up, verify Cr50 keeps EC_RST_L asserted,
the AP state is Unknown, and tpm commands fail while the AP is
in this state.
Eventually the AP resets. Make sure the TPM becomes usable again
and the AP state is on.
Change-Id: I6f0e8728717f1ed35c96b2669f1796078ebf93f7
Signed-off-by: Mary Ruthven <mruthven@chromium.org>
Reviewed-on: https://chromium-review.googlesource.com/1447001
Reviewed-by: Vadim Bendebury <vbendeb@chromium.org>
Diffstat (limited to 'board/cr50/ap_state.c')
-rw-r--r-- | board/cr50/ap_state.c | 43 |
1 files changed, 33 insertions, 10 deletions
diff --git a/board/cr50/ap_state.c b/board/cr50/ap_state.c index f40360fa0c..fc75f4a86e 100644 --- a/board/cr50/ap_state.c +++ b/board/cr50/ap_state.c @@ -159,18 +159,41 @@ static void init_ap_detect(void) gpio_enable_interrupt(GPIO_TPM_RST_L); gpio_enable_interrupt(GPIO_DETECT_TPM_RST_L_ASSERTED); /* - * Enable TPM reset GPIO interrupt. + * After resuming from any reset other than deep sleep, cr50 needs to + * make sure the rest of the system has reset. If cr50 needs a closed + * loop reset to reset the system, it can't rely on the short EC_RST + * pulse from RO. Use the closed loop reset to ensure the system has + * actually been reset. * - * If the TPM_RST_L signal is already high when cr50 wakes up or - * transitions to high before we are able to configure the gpio then we - * will have missed the edge and the tpm reset isr will not get - * called. Check that we haven't already missed the rising edge. If we - * have alert tpm_rst_isr. + * During this reset, the ap state will not be set to 'on' until the AP + * enters and then leaves reset. The tpm waits until the ap is on before + * allowing any tpm activity, so it wont do anything until the reset is + * complete. */ - if (gpio_get_level(GPIO_TPM_RST_L)) - tpm_rst_deasserted(GPIO_TPM_RST_L); - else - tpm_rst_asserted(GPIO_TPM_RST_L); + if (board_uses_closed_loop_reset() && + !(system_get_reset_flags() & RESET_FLAG_HIBERNATE)) { + board_closed_loop_reset(); + } else { + /* + * If the TPM_RST_L signal is already high when cr50 wakes up or + * transitions to high before we are able to configure the gpio + * then we will have missed the edge and the tpm reset isr will + * not get called. Check that we haven't already missed the + * rising edge. If we have alert tpm_rst_isr. + * + * DONT alert tpm_rst_isr if the board is waiting for the closed + * loop reset to finish. The isr is edge triggered, so + * tpm_rst_deasserted wont be called until the AP enters and + * exits reset. That is what we want. The TPM and other + * peripherals check ap_is_on before enabling interactions with + * the AP, and we want these to be disabled until the closed + * loop reset is complete. + */ + if (gpio_get_level(GPIO_TPM_RST_L)) + tpm_rst_deasserted(GPIO_TPM_RST_L); + else + tpm_rst_asserted(GPIO_TPM_RST_L); + } } /* * TPM_RST_L isn't setup until board_init. Make sure init_ap_detect happens |