diff options
-rw-r--r-- | board/cr50/build.mk | 1 | ||||
-rw-r--r-- | board/cr50/recovery_button.c | 73 | ||||
-rw-r--r-- | include/tpm_vendor_cmds.h | 1 |
3 files changed, 75 insertions, 0 deletions
diff --git a/board/cr50/build.mk b/board/cr50/build.mk index 4babeef552..dd99f31380 100644 --- a/board/cr50/build.mk +++ b/board/cr50/build.mk @@ -33,6 +33,7 @@ board-y = board.o ec_state.o board-${CONFIG_RDD} += rdd.o board-${CONFIG_USB_SPI} += usb_spi.o board-${CONFIG_USB_I2C} += usb_i2c.o +board-y += recovery_button.o board-y += tpm2/NVMem.o board-y += tpm2/aes.o board-y += tpm2/ecc.o diff --git a/board/cr50/recovery_button.c b/board/cr50/recovery_button.c new file mode 100644 index 0000000000..af4d4d7c87 --- /dev/null +++ b/board/cr50/recovery_button.c @@ -0,0 +1,73 @@ +/* Copyright 2017 The Chromium OS Authors. All rights reserved. + * Use of this source code is governed by a BSD-style license that can be + * found in the LICENSE file. + */ + +/* Recovery button override module. */ + +#include "common.h" +#include "console.h" +#include "extension.h" +#include "registers.h" +#include "util.h" + +/* + * The recovery button, on some systems only, is wired to KEY0 in rbox. For + * testing, we need to be able override the value. We'll have a vendor command + * such that the AP can query the state of the recovery button. However, the + * reported state can only be overridden with a console command given sufficient + * privileges. + */ +static uint8_t rec_btn_force_pressed; + +static uint8_t is_rec_btn_pressed(void) +{ + if (rec_btn_force_pressed) + return 1; + + /* + * If not force pressed, check the actual state of button. Note, + * the value is inverted because the button is active low. + */ + return !GREAD_FIELD(RBOX, CHECK_INPUT, KEY0_IN); +} + +static int command_recbtnforce(int argc, char **argv) +{ + int val; + + if (argc > 2) + return EC_ERROR_PARAM_COUNT; + + if (argc == 2) { + /* Make sure we're allowed to override the recovery button. */ + if (console_is_restricted()) + return EC_ERROR_ACCESS_DENIED; + + if (!parse_bool(argv[1], &val)) + return EC_ERROR_PARAM1; + + rec_btn_force_pressed = val; + } + + ccprintf("RecBtn: %s pressed\n", + rec_btn_force_pressed ? "forced" : + is_rec_btn_pressed() ? "" : "not"); + + return EC_SUCCESS; +} +DECLARE_SAFE_CONSOLE_COMMAND(recbtnforce, command_recbtnforce, + "[enable | disable]", + "Force enable the reported recbtn state."); + +static enum vendor_cmd_rc vc_get_rec_btn(enum vendor_cmd_cc code, + void *buf, + size_t input_size, + size_t *response_size) +{ + *(uint8_t *)buf = is_rec_btn_pressed(); + *response_size = 1; + + return VENDOR_RC_SUCCESS; +} +DECLARE_VENDOR_COMMAND(VENDOR_CC_GET_REC_BTN, vc_get_rec_btn); diff --git a/include/tpm_vendor_cmds.h b/include/tpm_vendor_cmds.h index f76685373c..59331313d9 100644 --- a/include/tpm_vendor_cmds.h +++ b/include/tpm_vendor_cmds.h @@ -42,6 +42,7 @@ enum vendor_cmd_cc { VENDOR_CC_SET_BOARD_ID = 26, VENDOR_CC_U2F_APDU = 27, VENDOR_CC_POP_LOG_ENTRY = 28, + VENDOR_CC_GET_REC_BTN = 29, LAST_VENDOR_COMMAND = 65535, }; |