diff options
Diffstat (limited to 'common')
-rw-r--r-- | common/extension.c | 16 | ||||
-rw-r--r-- | common/tpm_registers.c | 31 |
2 files changed, 31 insertions, 16 deletions
diff --git a/common/extension.c b/common/extension.c index a588ce892e..d28bfad337 100644 --- a/common/extension.c +++ b/common/extension.c @@ -10,10 +10,10 @@ #define CPRINTF(format, args...) cprintf(CC_EXTENSION, format, ## args) -void extension_route_command(uint16_t command_code, - void *buffer, - size_t in_size, - size_t *out_size) +uint32_t extension_route_command(uint16_t command_code, + void *buffer, + size_t in_size, + size_t *out_size) { struct extension_command *cmd_p; struct extension_command *end_p; @@ -22,10 +22,9 @@ void extension_route_command(uint16_t command_code, end_p = (struct extension_command *)&__extension_cmds_end; while (cmd_p != end_p) { - if (cmd_p->command_code == command_code) { - cmd_p->handler(buffer, in_size, out_size); - return; - } + if (cmd_p->command_code == command_code) + return cmd_p->handler(command_code, buffer, + in_size, out_size); cmd_p++; } @@ -33,4 +32,5 @@ void extension_route_command(uint16_t command_code, /* This covers the case of the handler not found. */ *out_size = 0; + return VENDOR_RC_NO_SUCH_COMMAND; } diff --git a/common/tpm_registers.c b/common/tpm_registers.c index 444ed52e20..b5c5f8b7e5 100644 --- a/common/tpm_registers.c +++ b/common/tpm_registers.c @@ -569,10 +569,21 @@ size_t tpm_get_burst_size(void) #ifdef CONFIG_EXTENSION_COMMAND +/* Recognize both original extension and new vendor-specific command codes */ +#define IS_CUSTOM_CODE(code) \ + ((code == CONFIG_EXTENSION_COMMAND) || \ + (code & TPM_CC_VENDOR_BIT_MASK)) + static void call_extension_command(struct tpm_cmd_header *tpmh, - size_t *total_size) + size_t *total_size) { size_t command_size = be32toh(tpmh->size); + uint32_t rc; + + /* + * Note that we don't look for TPM_CC_VENDOR_CR50 anywhere. All + * vendor-specific commands are handled the same way for now. + */ /* Verify there is room for at least the extension command header. */ if (command_size >= sizeof(struct tpm_cmd_header)) { @@ -582,14 +593,18 @@ static void call_extension_command(struct tpm_cmd_header *tpmh, *total_size -= sizeof(struct tpm_cmd_header); subcommand_code = be16toh(tpmh->subcommand_code); - extension_route_command(subcommand_code, - tpmh + 1, - command_size - - sizeof(struct tpm_cmd_header), - total_size); + rc = extension_route_command(subcommand_code, + tpmh + 1, + command_size - + sizeof(struct tpm_cmd_header), + total_size); /* Add the header size back. */ *total_size += sizeof(struct tpm_cmd_header); tpmh->size = htobe32(*total_size); + /* Flag errors from commands as vendor-specific */ + if (rc) + rc |= VENDOR_RC_ERR; + tpmh->command_code = htobe32(rc); } else { *total_size = command_size; } @@ -689,7 +704,7 @@ void tpm_task(void) watchdog_reload(); #ifdef CONFIG_EXTENSION_COMMAND - if (command_code == CONFIG_EXTENSION_COMMAND) { + if (IS_CUSTOM_CODE(command_code)) { response_size = sizeof(tpm_.regs.data_fifo); call_extension_command(tpmh, &response_size); } else @@ -711,7 +726,7 @@ void tpm_task(void) if (command_code == TPM2_PCR_Read) system_process_retry_counter(); #ifdef CONFIG_EXTENSION_COMMAND - if (command_code != CONFIG_EXTENSION_COMMAND) + if (!IS_CUSTOM_CODE(command_code)) #endif { /* |