mirror of
https://github.com/Telecominfraproject/OpenCellular.git
synced 2025-12-25 17:27:18 +00:00
tpm2_lite: implement TlclGetPermissions
Implement TlclGetPermissions, which sends a TPM2_NV_ReadPublic command
and returns the attributes of the NV Index (TPM2 Spec, Part 3, Section 31.6).
BUG=chrome-os-partner:58873
BUG=chrome-os-partner:55210
BRANCH=none
TEST=Run "tpmc def" with various permissions to define new indexes,
verify that "tpmc getp" returns matching permissions for them.
Change-Id: I2ad7163332ae8793cd717875645f19baef513b26
Reviewed-on: https://chromium-review.googlesource.com/409618
Commit-Ready: Vadim Bendebury <vbendeb@chromium.org>
Tested-by: Andrey Pronin <apronin@chromium.org>
Reviewed-by: Vadim Bendebury <vbendeb@chromium.org>
This commit is contained in:
committed by
chrome-bot
parent
d28b4e1444
commit
1afcfc1366
@@ -27,6 +27,7 @@
|
||||
#define TPM2_Shutdown ((TPM_CC)0x00000145)
|
||||
#define TPM2_NV_Read ((TPM_CC)0x0000014E)
|
||||
#define TPM2_NV_ReadLock ((TPM_CC)0x0000014F)
|
||||
#define TPM2_NV_ReadPublic ((TPM_CC)0x00000169)
|
||||
#define TPM2_GetCapability ((TPM_CC)0x0000017A)
|
||||
|
||||
/* TCG Spec defined, verify for TPM2.
|
||||
@@ -106,7 +107,7 @@ typedef uint32_t TPMA_NV;
|
||||
typedef struct {
|
||||
uint16_t size;
|
||||
uint8_t *buffer;
|
||||
} TPM2B, TPM2B_DIGEST, TPM2B_AUTH;
|
||||
} TPM2B, TPM2B_DIGEST, TPM2B_AUTH, TPM2B_NAME;
|
||||
|
||||
typedef union {
|
||||
struct {
|
||||
@@ -168,6 +169,10 @@ struct tpm2_nv_write_lock_cmd {
|
||||
TPMI_RH_NV_INDEX nvIndex;
|
||||
};
|
||||
|
||||
struct tpm2_nv_read_public_cmd {
|
||||
TPMI_RH_NV_INDEX nvIndex;
|
||||
};
|
||||
|
||||
struct tpm2_hierarchy_control_cmd {
|
||||
TPMI_RH_ENABLES enable;
|
||||
TPMI_YES_NO state;
|
||||
@@ -230,12 +235,18 @@ struct get_capability_response {
|
||||
TPMS_CAPABILITY_DATA capability_data;
|
||||
} __attribute__((packed));
|
||||
|
||||
struct nv_read_public_response {
|
||||
TPMS_NV_PUBLIC nvPublic;
|
||||
TPM2B_NAME nvName;
|
||||
} __attribute__((packed));
|
||||
|
||||
struct tpm2_response {
|
||||
struct tpm_header hdr;
|
||||
union {
|
||||
struct nv_read_response nvr;
|
||||
struct tpm2_session_header def_space;
|
||||
struct get_capability_response cap;
|
||||
struct nv_read_public_response nv_read_public;
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
@@ -101,6 +101,9 @@ static uint32_t unmarshal_u32(void **buffer, int *buffer_space)
|
||||
return value;
|
||||
}
|
||||
|
||||
#define unmarshal_TPM_HANDLE(a, b) unmarshal_u32(a, b)
|
||||
#define unmarshal_ALG_ID(a, b) unmarshal_u16(a, b)
|
||||
|
||||
static void unmarshal_TPM2B_MAX_NV_BUFFER(void **buffer,
|
||||
int *size,
|
||||
TPM2B_MAX_NV_BUFFER *nv_buffer)
|
||||
@@ -156,6 +159,69 @@ static void unmarshal_nv_read(void **buffer, int *size,
|
||||
unmarshal_authorization_section(buffer, size, "NV_Read");
|
||||
}
|
||||
|
||||
static void unmarshal_TPM2B(void **buffer,
|
||||
int *size,
|
||||
TPM2B *tpm2b)
|
||||
{
|
||||
tpm2b->size = unmarshal_u16(buffer, size);
|
||||
if (tpm2b->size > *size) {
|
||||
VBDEBUG(("%s:%d - "
|
||||
"size mismatch: expected %d, remaining %d\n",
|
||||
__func__, __LINE__, tpm2b->size, *size));
|
||||
*size = -1;
|
||||
return;
|
||||
}
|
||||
|
||||
tpm2b->buffer = *buffer;
|
||||
|
||||
*buffer = ((uint8_t *)(*buffer)) + tpm2b->size;
|
||||
*size -= tpm2b->size;
|
||||
}
|
||||
|
||||
static void unmarshal_TPMS_NV_PUBLIC(void **buffer,
|
||||
int *size,
|
||||
TPMS_NV_PUBLIC *pub)
|
||||
{
|
||||
int tpm2b_size = unmarshal_u16(buffer, size);
|
||||
if (tpm2b_size > *size) {
|
||||
VBDEBUG(("%s:%d - "
|
||||
"size mismatch: expected %d, remaining %d\n",
|
||||
__func__, __LINE__, tpm2b_size, *size));
|
||||
*size = -1;
|
||||
return;
|
||||
}
|
||||
*size -= tpm2b_size;
|
||||
|
||||
pub->nvIndex = unmarshal_TPM_HANDLE(buffer, &tpm2b_size);
|
||||
pub->nameAlg = unmarshal_ALG_ID(buffer, &tpm2b_size);
|
||||
pub->attributes = unmarshal_u32(buffer, &tpm2b_size);
|
||||
unmarshal_TPM2B(buffer, &tpm2b_size, &pub->authPolicy);
|
||||
pub->dataSize = unmarshal_u16(buffer, &tpm2b_size);
|
||||
|
||||
if (tpm2b_size != 0) {
|
||||
VBDEBUG(("%s:%d - "
|
||||
"TPMS_NV_PUBLIC size doesn't match the size field\n",
|
||||
__func__, __LINE__));
|
||||
*size = -1;
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
static void unmarshal_nv_read_public(void **buffer, int *size,
|
||||
struct nv_read_public_response *nv_pub)
|
||||
{
|
||||
unmarshal_TPMS_NV_PUBLIC(buffer, size, &nv_pub->nvPublic);
|
||||
unmarshal_TPM2B(buffer, size, &nv_pub->nvName);
|
||||
|
||||
if (*size > 0) {
|
||||
VBDEBUG(("%s:%d - "
|
||||
"extra %d bytes after nvName\n",
|
||||
__func__, __LINE__, *size));
|
||||
*size = -1;
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
static void unmarshal_TPML_TAGGED_TPM_PROPERTY(void **buffer, int *size,
|
||||
TPML_TAGGED_TPM_PROPERTY *prop)
|
||||
{
|
||||
@@ -499,6 +565,15 @@ static void marshal_nv_write_lock(void **buffer,
|
||||
marshal_session_header(buffer, &session_header, buffer_space);
|
||||
}
|
||||
|
||||
static void marshal_nv_read_public(void **buffer,
|
||||
struct tpm2_nv_read_public_cmd *command_body,
|
||||
int *buffer_space)
|
||||
{
|
||||
tpm_tag = TPM_ST_NO_SESSIONS;
|
||||
|
||||
marshal_TPM_HANDLE(buffer, command_body->nvIndex, buffer_space);
|
||||
}
|
||||
|
||||
static void marshal_hierarchy_control(void **buffer,
|
||||
struct tpm2_hierarchy_control_cmd
|
||||
*command_body,
|
||||
@@ -600,6 +675,10 @@ int tpm_marshal_command(TPM_CC command, void *tpm_command_body,
|
||||
marshal_nv_write_lock(&cmd_body, tpm_command_body, &body_size);
|
||||
break;
|
||||
|
||||
case TPM2_NV_ReadPublic:
|
||||
marshal_nv_read_public(&cmd_body, tpm_command_body, &body_size);
|
||||
break;
|
||||
|
||||
case TPM2_Hierarchy_Control:
|
||||
marshal_hierarchy_control(&cmd_body,
|
||||
tpm_command_body, &body_size);
|
||||
@@ -672,6 +751,11 @@ struct tpm2_response *tpm_unmarshal_response(TPM_CC command,
|
||||
&tpm2_resp.nvr);
|
||||
break;
|
||||
|
||||
case TPM2_NV_ReadPublic:
|
||||
unmarshal_nv_read_public(&response_body, &cr_size,
|
||||
&tpm2_resp.nv_read_public);
|
||||
break;
|
||||
|
||||
case TPM2_GetCapability:
|
||||
unmarshal_get_capability(&response_body, &cr_size,
|
||||
&tpm2_resp.cap);
|
||||
|
||||
@@ -244,13 +244,37 @@ uint32_t TlclExtend(int pcr_num, const uint8_t *in_digest, uint8_t *out_digest)
|
||||
return TPM_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
static uint32_t tlcl_nv_read_public(uint32_t index,
|
||||
struct nv_read_public_response **presp)
|
||||
{
|
||||
struct tpm2_response *response;
|
||||
struct tpm2_nv_read_public_cmd read_pub;
|
||||
|
||||
memset(&read_pub, 0, sizeof(read_pub));
|
||||
read_pub.nvIndex = HR_NV_INDEX + index;
|
||||
|
||||
response = tpm_process_command(TPM2_NV_ReadPublic, &read_pub);
|
||||
if (!response || response->hdr.tpm_code)
|
||||
return TPM_E_IOERROR;
|
||||
*presp = &response->nv_read_public;
|
||||
|
||||
return TPM_SUCCESS;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the permission bits for the NVRAM space with |index|.
|
||||
*/
|
||||
uint32_t TlclGetPermissions(uint32_t index, uint32_t *permissions)
|
||||
{
|
||||
*permissions = 0;
|
||||
VBDEBUG(("%s called, NOT YET IMPLEMENTED\n", __func__));
|
||||
uint32_t rv;
|
||||
struct nv_read_public_response *resp;
|
||||
|
||||
rv = tlcl_nv_read_public(index, &resp);
|
||||
if (rv != TPM_SUCCESS)
|
||||
return rv;
|
||||
|
||||
*permissions = resp->nvPublic.attributes;
|
||||
return TPM_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user