summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKees Cook <keescook@chromium.org>2012-02-29 16:09:14 -0800
committerGerrit <chrome-bot@google.com>2012-03-01 15:25:31 -0800
commitf0605cbdc36f58829a908a3333e438c565c8c7af (patch)
tree3cbf146c627d95d2d01461ac0224d90234e802fe
parent5ee257d94cb8aab2f3717c5cd4ceb37fbba3ec41 (diff)
downloadvboot-f0605cbdc36f58829a908a3333e438c565c8c7af.tar.gz
tpm_lite: implement TPM_GetRandom
Provide TPM_GetRandom function to library callers. BUG=chromium-os:22172 TEST=lumpy build & manual testing Change-Id: Id604fd92490ba697033158a580b0b4df1d975932 Signed-off-by: Kees Cook <keescook@chromium.org> Reviewed-on: https://gerrit.chromium.org/gerrit/17120 Reviewed-by: Luigi Semenzato <semenzato@chromium.org>
-rw-r--r--firmware/include/tlcl.h7
-rw-r--r--firmware/include/tss_constants.h3
-rw-r--r--firmware/lib/tpm_lite/include/tlcl_structures.h6
-rw-r--r--firmware/lib/tpm_lite/tlcl.c33
-rw-r--r--utility/tlcl_generator.c11
-rw-r--r--utility/tpmc.c33
6 files changed, 88 insertions, 5 deletions
diff --git a/firmware/include/tlcl.h b/firmware/include/tlcl.h
index 6f0db1b6..c8632e43 100644
--- a/firmware/include/tlcl.h
+++ b/firmware/include/tlcl.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010 The Chromium OS Authors. All rights reserved.
+/* Copyright (c) 2012 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.
*/
@@ -150,4 +150,9 @@ uint32_t TlclGetPermanentFlags(TPM_PERMANENT_FLAGS* pflags);
*/
uint32_t TlclGetSTClearFlags(TPM_STCLEAR_FLAGS* pflags);
+/* Requests [length] bytes from TPM RNG to be stored in [data]. Actual
+ * number of bytes read is stored in [size]. The TPM error code is returned.
+ */
+uint32_t TlclGetRandom(uint8_t* data, uint32_t length, uint32_t* size);
+
#endif /* TPM_LITE_TLCL_H_ */
diff --git a/firmware/include/tss_constants.h b/firmware/include/tss_constants.h
index 68a9c6ff..b28c3c60 100644
--- a/firmware/include/tss_constants.h
+++ b/firmware/include/tss_constants.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2011 The Chromium OS Authors. All rights reserved.
+/* Copyright (c) 2012 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.
*
@@ -36,6 +36,7 @@
#define TPM_E_MUST_REBOOT ((uint32_t)0x00005002) /* vboot local */
#define TPM_E_CORRUPTED_STATE ((uint32_t)0x00005003) /* vboot local */
#define TPM_E_COMMUNICATION_ERROR ((uint32_t)0x00005004) /* vboot local */
+#define TPM_E_RESPONSE_TOO_LARGE ((uint32_t)0x00005005) /* vboot local */
#define TPM_NV_INDEX0 ((uint32_t)0x00000000)
#define TPM_NV_INDEX_LOCK ((uint32_t)0xffffffff)
diff --git a/firmware/lib/tpm_lite/include/tlcl_structures.h b/firmware/lib/tpm_lite/include/tlcl_structures.h
index e0a7a46b..c4d80ba3 100644
--- a/firmware/lib/tpm_lite/include/tlcl_structures.h
+++ b/firmware/lib/tpm_lite/include/tlcl_structures.h
@@ -7,6 +7,12 @@ const struct s_tpm_extend_cmd{
} tpm_extend_cmd = {{0x0, 0xc1, 0x0, 0x0, 0x0, 0x22, 0x0, 0x0, 0x0, 0x14, },
10, 14, };
+const struct s_tpm_get_random_cmd{
+ uint8_t buffer[14];
+ uint16_t bytesRequested;
+} tpm_get_random_cmd = {{0x0, 0xc1, 0x0, 0x0, 0x0, 0xe, 0x0, 0x0, 0x0, 0x46, },
+10, };
+
const struct s_tpm_getpermissions_cmd{
uint8_t buffer[22];
uint16_t index;
diff --git a/firmware/lib/tpm_lite/tlcl.c b/firmware/lib/tpm_lite/tlcl.c
index 338e2f67..9e9ece84 100644
--- a/firmware/lib/tpm_lite/tlcl.c
+++ b/firmware/lib/tpm_lite/tlcl.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
+/* Copyright (c) 2012 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.
*/
@@ -396,3 +396,34 @@ uint32_t TlclGetPermissions(uint32_t index, uint32_t* permissions) {
FromTpmUint32(nvdata + kNvDataPublicPermissionsOffset, permissions);
return result;
}
+
+uint32_t TlclGetRandom(uint8_t* data, uint32_t length, uint32_t *size) {
+ struct s_tpm_get_random_cmd cmd;
+ uint8_t response[TPM_LARGE_ENOUGH_COMMAND_SIZE];
+ uint32_t result;
+
+ VBDEBUG(("TPM: TlclGetRandom(%d)\n", length));
+ Memcpy(&cmd, &tpm_get_random_cmd, sizeof(cmd));
+ ToTpmUint32(cmd.buffer + tpm_get_random_cmd.bytesRequested, length);
+ /* There must be room in the response buffer for the bytes. */
+ if (length > TPM_LARGE_ENOUGH_COMMAND_SIZE - kTpmResponseHeaderLength
+ - sizeof(uint32_t)) {
+ return TPM_E_IOERROR;
+ }
+
+ result = TlclSendReceive(cmd.buffer, response, sizeof(response));
+ if (result == TPM_SUCCESS) {
+ uint8_t* get_random_cursor;
+ FromTpmUint32(response + kTpmResponseHeaderLength, size);
+
+ /* There must be room in the target buffer for the bytes. */
+ if (*size > length) {
+ return TPM_E_RESPONSE_TOO_LARGE;
+ }
+ get_random_cursor = response + kTpmResponseHeaderLength
+ + sizeof(uint32_t);
+ Memcpy(data, get_random_cursor, *size);
+ }
+
+ return result;
+}
diff --git a/utility/tlcl_generator.c b/utility/tlcl_generator.c
index f905784f..bbc379c1 100644
--- a/utility/tlcl_generator.c
+++ b/utility/tlcl_generator.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010 The Chromium OS Authors. All rights reserved.
+/* Copyright (c) 2012 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.
*/
@@ -362,6 +362,14 @@ Command* BuildGetPermissionsCommand(void) {
return cmd;
}
+Command* BuildGetRandomCommand(void) {
+ int size = kTpmRequestHeaderLength + sizeof(uint32_t);
+ Command* cmd = newCommand(TPM_ORD_GetRandom, size);
+ cmd->name = "tpm_get_random_cmd";
+ AddVisibleField(cmd, "bytesRequested", kTpmRequestHeaderLength);
+ return cmd;
+}
+
/* Output the fields of a structure.
*/
void OutputFields(Field* fld) {
@@ -480,6 +488,7 @@ Command* (*builders[])(void) = {
BuildGetFlagsCommand,
BuildGetSTClearFlagsCommand,
BuildGetPermissionsCommand,
+ BuildGetRandomCommand,
BuildExtendCommand,
};
diff --git a/utility/tpmc.c b/utility/tpmc.c
index d8fb07a5..68ce6d3f 100644
--- a/utility/tpmc.c
+++ b/utility/tpmc.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010 The Chromium OS Authors. All rights reserved.
+/* Copyright (c) 2012 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.
*
@@ -228,6 +228,35 @@ static uint32_t HandlerGetPermissions(void) {
return result;
}
+static uint32_t HandlerGetRandom(void) {
+ uint32_t length, size;
+ uint8_t* bytes;
+ uint32_t result;
+ int i;
+ if (nargs != 3) {
+ fprintf(stderr, "usage: tpmc getrandom <size>\n");
+ exit(OTHER_ERROR);
+ }
+ if (HexStringToUint32(args[2], &length) != 0) {
+ fprintf(stderr, "<size> must be 32-bit hex (0x[0-9a-f]+)\n");
+ exit(OTHER_ERROR);
+ }
+ bytes = calloc(1, length);
+ if (bytes == NULL) {
+ perror("calloc");
+ exit(OTHER_ERROR);
+ }
+ result = TlclGetRandom(bytes, length, &size);
+ if (result == 0 && size > 0) {
+ for (i = 0; i < size; i++) {
+ printf("%02x", bytes[i]);
+ }
+ printf("\n");
+ }
+ free(bytes);
+ return result;
+}
+
static uint32_t HandlerGetPermanentFlags(void) {
TPM_PERMANENT_FLAGS pflags;
uint32_t result = TlclGetPermanentFlags(&pflags);
@@ -312,6 +341,8 @@ command_record command_table[] = {
HandlerGetPermissions },
{ "getpermanentflags", "getpf", "print all permanent flags",
HandlerGetPermanentFlags },
+ { "getrandom", "rand", "read bytes from RNG (rand <size>)",
+ HandlerGetRandom },
{ "getstclearflags", "getvf", "print all volatile (ST_CLEAR) flags",
HandlerGetSTClearFlags },
{ "resume", "res", "execute TPM_Startup(ST_STATE)", TlclResume },