rma_reset: add server side response

Add support for generating the authcode from cr50's challenge.

BUG=b:74019846
BRANCH=none
TEST=create a cr50 image with test keys. Verify that the output from
rma_reset -c opens cr50.

Change-Id: I85a209e55dc23daa118e0071e868878b6fbfcb69
Signed-off-by: Mary Ruthven <mruthven@chromium.org>
Reviewed-on: https://chromium-review.googlesource.com/945419
Reviewed-by: Randall Spangler <rspangler@chromium.org>
This commit is contained in:
Mary Ruthven
2018-03-01 20:17:40 -08:00
committed by chrome-bot
parent b14b974ee4
commit 52c3a72b73

View File

@@ -47,9 +47,10 @@ static char challenge[RMA_CHALLENGE_BUF_SIZE];
static char authcode[RMA_AUTHCODE_BUF_SIZE];
static char *progname;
static char *short_opts = "k:b:d:a:w:th";
static char *short_opts = "c:k:b:d:a:w:th";
static const struct option long_opts[] = {
/* name hasarg *flag val */
{"challenge", 1, NULL, 'c'},
{"key_id", 1, NULL, 'k'},
{"board_id", 1, NULL, 'b'},
{"device_id", 1, NULL, 'd'},
@@ -101,6 +102,51 @@ void rand_bytes(void *buffer, size_t len)
}
}
static int rma_server_side(const char *generated_challenge)
{
int key_id, version;
uint8_t secret[32];
uint8_t hmac[32];
struct rma_challenge c;
uint8_t *cptr = (uint8_t *)&c;
/* Convert the challenge back into binary */
if (base32_decode(cptr, 8 * sizeof(c), generated_challenge, 9) !=
8 * sizeof(c)) {
printf("Error decoding challenge\n");
return -1;
}
version = RMA_CHALLENGE_GET_VERSION(c.version_key_id);
key_id = RMA_CHALLENGE_GET_KEY_ID(c.version_key_id);
printf("Challenge: %s\n", generated_challenge);
printf("Version: %d\n", version);
printf("Server KeyID: %d\n", key_id);
if (version != RMA_CHALLENGE_VERSION)
printf("Unsupported challenge version %d\n", version);
if (key_id != RMA_TEST_SERVER_KEY_ID)
printf("Unsupported KeyID %d\n", key_id);
/* Calculate the shared secret */
X25519(secret, server_pri_key, c.device_pub_key);
/*
* Auth code is a truncated HMAC of the ephemeral public key, BoardID,
* and DeviceID.
*/
hmac_SHA256(hmac, secret, sizeof(secret), cptr + 1, sizeof(c) - 1);
if (base32_encode(authcode, RMA_AUTHCODE_BUF_SIZE,
hmac, RMA_AUTHCODE_CHARS * 5, 0)) {
printf("Error encoding auth code\n");
return -1;
}
printf("Authcode: %s\n", authcode);
return 0;
};
int rma_create_challenge(void)
{
uint8_t temp[32]; /* Private key or HMAC */
@@ -205,11 +251,17 @@ static void print_params(void)
static void usage(void)
{
printf("\nUsage: %s --key_id <arg> --board_id <arg> --device_id <arg>"
"--hw_id <arg> | --auth_code <arg>\n"
"--hw_id <arg> | --auth_code <arg> | "
"--challenge <arg>\n"
"\n"
"This generates a challenge response and "
"sends authoriztion code to reset device.\n"
"This is used to generate the cr50 or server responses for rma "
"open.\n"
"The cr50 side can be used to generate a challenge response "
"and sends authoriztion code to reset device.\n"
"The server side can generate an authcode from cr50's "
"rma challenge.\n"
"\n"
" -c,--challenge The challenge generated by cr50\n"
" -k,--key_id Index of the server private key\n"
" -b,--board_id BoardID type field\n"
" -d,--device_id Device-unique identifier\n"
@@ -339,6 +391,8 @@ int main(int argc, char **argv)
case 't':
t_flag = 1;
break;
case 'c':
return rma_server_side(optarg);
case 'k':
if (set_server_key_id(optarg)) {
printf("Malformed key id\n");
@@ -414,8 +468,9 @@ int main(int argc, char **argv)
} else {
if (!t_flag) { /* Use default values */
if (!k_flag || !b_flag || !d_flag || !w_flag) {
printf("Flags -k, -b, -d, and -w are "
"mandiatory\n");
printf("server-side: Flag -c is mandatory\n");
printf("cr50-side: Flags -k, -b, -d, and -w "
"are mandatory\n");
return 1;
}
}