diff options
author | Vadim Bendebury <vbendeb@chromium.org> | 2018-01-10 18:34:46 -0800 |
---|---|---|
committer | ChromeOS Commit Bot <chromeos-commit-bot@chromium.org> | 2018-02-01 00:48:20 +0000 |
commit | a3d316b2b86d3c79129eecbd08c922b3b08d485c (patch) | |
tree | 3daa7100c53a5be8680866bcf3272fb6fcca92fc | |
parent | 7e35f6e9579e57bc0c100c7fe1979220356795aa (diff) | |
download | chrome-ec-a3d316b2b86d3c79129eecbd08c922b3b08d485c.tar.gz |
ccd: use async TPM reset where required
When TPM is wiped out on 'ccd open', the TPM reset could be invoked on
the TPM task context, if physical presence verification was not
required, or on the hooks task context, if PP was required.
This patch makes sure that the proper TPM reset is invoked depending
on the context. Also fixing the return value in ccd_command_wrapper(),
because it is expected to be from the ec_error_list enun, and this is
what is returned in the vendor command error response payload.
BRANCH=cr50
BUG=b:62537474
TEST=verified that TPM and device reset happen smoothly in both cases
when 'ccd open' requires and does not require PP.
Change-Id: I1935fc90b386bb8f2158001e153da371fca22d03
Signed-off-by: Vadim Bendebury <vbendeb@chromium.org>
Reviewed-on: https://chromium-review.googlesource.com/861206
Reviewed-by: Randall Spangler <rspangler@chromium.org>
(cherry picked from commit b95b487cbcdadd1e9026dee255cebbe7660dd549)
Reviewed-on: https://chromium-review.googlesource.com/896784
-rw-r--r-- | common/ccd_config.c | 34 |
1 files changed, 27 insertions, 7 deletions
diff --git a/common/ccd_config.c b/common/ccd_config.c index 01d8c8ae6f..6f65626849 100644 --- a/common/ccd_config.c +++ b/common/ccd_config.c @@ -567,24 +567,45 @@ static int ccd_set_password(const char *password) /******************************************************************************/ /* Handlers for state changes requiring physical presence */ -static void ccd_open_done(void) +/* + * Could be invoked synchronously on the TPM task context, or asynchronously, + * after physical presence is established, on the hooks task context. + * + * The appropriate TPM reset entry point needs to be invoked. Also, make sure + * that the board is always rebooted when TPM is reset. + * + * @param sync Non-zero to invoke synchronously. + */ +static void ccd_open_done(int sync) { + int rv; + if (!ccd_is_cap_enabled(CCD_CAP_OPEN_WITHOUT_TPM_WIPE)) { /* Can't open unless wipe succeeds */ - if (tpm_sync_reset(1) != EC_SUCCESS) { + if (sync) + rv = tpm_sync_reset(1); + else + rv = board_wipe_tpm(); + + if (rv != EC_SUCCESS) { CPRINTS("CCD open TPM wipe failed"); return; } } if (!ccd_is_cap_enabled(CCD_CAP_UNLOCK_WITHOUT_AP_REBOOT) || - !ccd_is_cap_enabled(CCD_CAP_OPEN_WITHOUT_TPM_WIPE)) + (!ccd_is_cap_enabled(CCD_CAP_OPEN_WITHOUT_TPM_WIPE) && sync)) board_reboot_ap(); CPRINTS("CCD opened"); ccd_set_state(CCD_STATE_OPENED); } +static void ccd_open_done_async(void) +{ + ccd_open_done(0); +} + static void ccd_unlock_done(void) { if (!ccd_is_cap_enabled(CCD_CAP_UNLOCK_WITHOUT_AP_REBOOT)) @@ -858,8 +879,7 @@ static int ccd_command_wrapper(int argc, char *password, */ return_code = be32toh(vch->tpm_header.command_code); if (return_code && (return_code != VENDOR_RC_IN_PROGRESS)) { - ccprintf("Command error %d\n", vch->ccd_subcommand); - rv = EC_ERROR_UNKNOWN; + rv = vch->ccd_subcommand; } else { rv = EC_SUCCESS; } @@ -933,7 +953,7 @@ static enum vendor_cmd_rc ccd_open(void *buf, if (need_pp) { /* Start physical presence detect */ ccprintf("Starting CCD open...\n"); - rv = physical_detect_start(is_long, ccd_open_done); + rv = physical_detect_start(is_long, ccd_open_done_async); if (rv != EC_SUCCESS) { *response_size = 1; buffer[0] = rv; @@ -943,7 +963,7 @@ static enum vendor_cmd_rc ccd_open(void *buf, } /* No physical presence required; go straight to done */ - ccd_open_done(); + ccd_open_done(1); return VENDOR_RC_SUCCESS; } |