summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorVadim Bendebury <vbendeb@chromium.org>2018-02-21 17:59:44 -0800
committerchrome-bot <chrome-bot@chromium.org>2018-02-23 03:36:30 -0800
commit1850d5908a348e31d61b2816f6f086fd4d3596de (patch)
treea106af82acd4e434a855805b92dfd91d25e5919c
parent8a5a83aef357b23a274f45a4377c32b77624a5fc (diff)
downloadchrome-ec-1850d5908a348e31d61b2816f6f086fd4d3596de.tar.gz
gsctool: refactor PP polling into a function
Both CCD and SPI_HASH commands need to enforce physical presence. This patch separates PP polling into a function which can be used by both commands. BRANCH=none BUG=b:73668125 TEST=verified that running 'gsctool -a -o' on a Robo device still allows to unlock CCD with PP enforced. Change-Id: I49abb0e56ad37664eaad7cc34de44e1ac06e2d1b Signed-off-by: Vadim Bendebury <vbendeb@chromium.org> Reviewed-on: https://chromium-review.googlesource.com/930567 Reviewed-by: Randall Spangler <rspangler@chromium.org>
-rw-r--r--extra/usb_updater/gsctool.c103
1 files changed, 61 insertions, 42 deletions
diff --git a/extra/usb_updater/gsctool.c b/extra/usb_updater/gsctool.c
index 6985501127..399c8fdba0 100644
--- a/extra/usb_updater/gsctool.c
+++ b/extra/usb_updater/gsctool.c
@@ -1619,57 +1619,29 @@ static void process_password(struct transfer_descriptor *td)
exit(update_error);
}
-static void process_ccd_state(struct transfer_descriptor *td, int ccd_unlock,
- int ccd_open, int ccd_lock)
+/*
+ * This function can be used to retrieve the current PP status from Cr50 and
+ * prompt the user when a PP press is required.
+ *
+ * Physical presence can be required by different gsctool options, for which
+ * Cr50 behavior also differs. The 'command' and 'poll_type' parameters are
+ * used by Cr50 to tell what the host is polling for.
+ */
+static void poll_for_pp(struct transfer_descriptor *td,
+ uint16_t command,
+ uint8_t poll_type)
{
- uint8_t payload;
uint8_t response;
uint8_t prev_response;
size_t response_size;
int rv;
- if (ccd_unlock)
- payload = CCDV_UNLOCK;
- else if (ccd_open)
- payload = CCDV_OPEN;
- else
- payload = CCDV_LOCK;
-
- response_size = sizeof(response);
- rv = send_vendor_command(td, VENDOR_CC_CCD,
- &payload, sizeof(payload),
- &response, &response_size);
-
- /*
- * If password is required - try sending the same subcommand
- * accompanied by user password.
- */
- if (rv == VENDOR_RC_PASSWORD_REQUIRED)
- rv = common_process_password(td, payload);
-
- if (rv == VENDOR_RC_SUCCESS)
- return;
-
- if (rv != VENDOR_RC_IN_PROGRESS) {
- fprintf(stderr, "Error: rv %d, response %d\n",
- rv, response_size ? response : 0);
- exit(update_error);
- }
-
- /*
- * Physical presence process started, poll for the state the user
- * asked for. Only two subcommands would return 'IN_PROGRESS'.
- */
- if (ccd_unlock)
- payload = CCDV_PP_POLL_UNLOCK;
- else
- payload = CCDV_PP_POLL_OPEN;
-
prev_response = ~0; /* Guaranteed invalid value. */
+
while (1) {
response_size = sizeof(response);
- rv = send_vendor_command(td, VENDOR_CC_CCD,
- &payload, sizeof(payload),
+ rv = send_vendor_command(td, command,
+ &poll_type, sizeof(poll_type),
&response, &response_size);
if (((rv != VENDOR_RC_SUCCESS) && (rv != VENDOR_RC_IN_PROGRESS))
@@ -1705,6 +1677,53 @@ static void process_ccd_state(struct transfer_descriptor *td, int ccd_unlock,
usleep(500 * 1000); /* Poll every half a second. */
}
+
+}
+
+static void process_ccd_state(struct transfer_descriptor *td, int ccd_unlock,
+ int ccd_open, int ccd_lock)
+{
+ uint8_t payload;
+ uint8_t response;
+ size_t response_size;
+ int rv;
+
+ if (ccd_unlock)
+ payload = CCDV_UNLOCK;
+ else if (ccd_open)
+ payload = CCDV_OPEN;
+ else
+ payload = CCDV_LOCK;
+
+ response_size = sizeof(response);
+ rv = send_vendor_command(td, VENDOR_CC_CCD,
+ &payload, sizeof(payload),
+ &response, &response_size);
+
+ /*
+ * If password is required - try sending the same subcommand
+ * accompanied by user password.
+ */
+ if (rv == VENDOR_RC_PASSWORD_REQUIRED)
+ rv = common_process_password(td, payload);
+
+ if (rv == VENDOR_RC_SUCCESS)
+ return;
+
+ if (rv != VENDOR_RC_IN_PROGRESS) {
+ fprintf(stderr, "Error: rv %d, response %d\n",
+ rv, response_size ? response : 0);
+ exit(update_error);
+ }
+
+ /*
+ * Physical presence process started, poll for the state the user
+ * asked for. Only two subcommands would return 'IN_PROGRESS'.
+ */
+ if (ccd_unlock)
+ poll_for_pp(td, VENDOR_CC_CCD, CCDV_PP_POLL_UNLOCK);
+ else
+ poll_for_pp(td, VENDOR_CC_CCD, CCDV_PP_POLL_OPEN);
}
static void process_bid(struct transfer_descriptor *td,