summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorChris Engel <cjengel@us.ibm.com>2015-11-19 11:37:23 -0600
committerDaniel M. Crowell <dcrowell@us.ibm.com>2016-03-27 23:15:23 -0400
commite3d766322fb0715c0def3ca6dd850deccbd9fbbc (patch)
treef7fe4125bb2e2a2e2b00b7d745b0c7968a14c47d /src
parent6c5ba7c0b4d3d1694a2cdf2d6c5365027534ef5a (diff)
downloadtalos-hostboot-e3d766322fb0715c0def3ca6dd850deccbd9fbbc.tar.gz
talos-hostboot-e3d766322fb0715c0def3ca6dd850deccbd9fbbc.zip
Trustedboot support for PCR Read
cherry picked from commit 93cd77a2455e60f01b003f747368e69cfef1b844 RTC: 125287 ForwardPort: yes Reviewed-on: http://ralgit01.raleigh.ibm.com/gerrit1/701 Reviewed-by: Timothy R. Block <block@us.ibm.com> Reviewed-by: Stephen M. Cprek <smcprek@us.ibm.com> Reviewed-by: Daniel M. Crowell <dcrowell@us.ibm.com> Change-Id: I37103173d417ce1f378ee3ce76646f1028339ee0 Reviewed-on: http://ralgit01.raleigh.ibm.com/gerrit1/22496 Tested-by: Jenkins Server Tested-by: FSP CI Jenkins Reviewed-by: Christopher J. Engel <cjengel@us.ibm.com>
Diffstat (limited to 'src')
-rw-r--r--src/include/usr/secureboot/trustedboot_reasoncodes.H1
-rw-r--r--src/include/usr/secureboot/trustedbootif.H3
-rw-r--r--src/usr/secureboot/trusted/base/trustedTypes_base.C2
-rwxr-xr-xsrc/usr/secureboot/trusted/test/trustedbootTest.H160
-rw-r--r--src/usr/secureboot/trusted/trustedTypes.C179
-rw-r--r--src/usr/secureboot/trusted/trustedTypes.H75
-rw-r--r--src/usr/secureboot/trusted/trustedbootCmds.C148
-rw-r--r--src/usr/secureboot/trusted/trustedbootCmds.H17
8 files changed, 580 insertions, 5 deletions
diff --git a/src/include/usr/secureboot/trustedboot_reasoncodes.H b/src/include/usr/secureboot/trustedboot_reasoncodes.H
index 6cad6ebd7..9f3ad03c5 100644
--- a/src/include/usr/secureboot/trustedboot_reasoncodes.H
+++ b/src/include/usr/secureboot/trustedboot_reasoncodes.H
@@ -51,6 +51,7 @@ namespace TRUSTEDBOOT
MOD_TPM_UNMARSHALRESPDATA = 0x05,
MOD_TPM_VERIFYFUNCTIONAL = 0x06,
MOD_TPM_CMD_PCREXTEND = 0x07,
+ MOD_TPM_CMD_PCRREAD = 0x08,
MOD_TPMLOGMGR_INITIALIZE = 0x10,
MOD_TPMLOGMGR_ADDEVENT = 0x11,
diff --git a/src/include/usr/secureboot/trustedbootif.H b/src/include/usr/secureboot/trustedbootif.H
index acd9a867f..49b81832c 100644
--- a/src/include/usr/secureboot/trustedbootif.H
+++ b/src/include/usr/secureboot/trustedbootif.H
@@ -62,7 +62,8 @@ namespace TRUSTEDBOOT
PCR_1 = 1,
PCR_4 = 4,
PCR_DEBUG = 16,
- PCR_MAX = 16,
+ PLATFORM_PCR = 24, ///< The number of PCR required by the platform spec
+ IMPLEMENTATION_PCR = 24, ///< The number of PCRs implemented by TPM
} TPM_Pcr;
diff --git a/src/usr/secureboot/trusted/base/trustedTypes_base.C b/src/usr/secureboot/trusted/base/trustedTypes_base.C
index 3c3d8d737..bff23a911 100644
--- a/src/usr/secureboot/trusted/base/trustedTypes_base.C
+++ b/src/usr/secureboot/trusted/base/trustedTypes_base.C
@@ -130,7 +130,7 @@ namespace TRUSTEDBOOT
field32 = (uint32_t*)(i_tpmBuf);
val->pcrIndex = le32toh(*field32);
// Ensure a valid pcr index
- if (val->pcrIndex >= PCR_MAX)
+ if (val->pcrIndex >= IMPLEMENTATION_PCR)
{
*o_err = true;
i_tpmBuf = NULL;
diff --git a/src/usr/secureboot/trusted/test/trustedbootTest.H b/src/usr/secureboot/trusted/test/trustedbootTest.H
index 476b7e4c0..5fad75145 100755
--- a/src/usr/secureboot/trusted/test/trustedbootTest.H
+++ b/src/usr/secureboot/trusted/test/trustedbootTest.H
@@ -475,6 +475,67 @@ class TrustedBootTest: public CxxTest::TestSuite
}
+ // Test PcrReadIn
+ {
+ TRACUCOMP( g_trac_trustedboot,
+ "testCommandMarshal - PcrReadIn" );
+ memset(dataBufIn, 0, sizeof(dataBufIn));
+ memset(dataBufOut, 0, sizeof(dataBufOut));
+ TRUSTEDBOOT::TPM2_PcrReadIn* cmdPtr =
+ reinterpret_cast<TRUSTEDBOOT::TPM2_PcrReadIn*>
+ (dataBufIn);
+ cmdPtr->base.commandCode = TRUSTEDBOOT::TPM_CC_PCR_Read;
+ cmdPtr->pcrSelectionIn.count = 1;
+ cmdPtr->pcrSelectionIn.pcrSelections[0].algorithmId =
+ TPM_ALG_SHA256;
+ cmdPtr->pcrSelectionIn.pcrSelections[0].sizeOfSelect =
+ PCR_SELECT_MAX;
+
+ runTpmMarshalTest(baseCmd,
+ dataBufOut,
+ sizeof(dataBufOut),
+ cmdSize,
+ "PcrReadIn",
+ num_ops,
+ fails,
+ sizeof(TPM2_PcrReadIn));
+
+ // Invalid number of algorithms
+ memset(dataBufIn, 0, sizeof(dataBufIn));
+ memset(dataBufOut, 0, sizeof(dataBufOut));
+ cmdPtr->base.commandCode = TRUSTEDBOOT::TPM_CC_PCR_Read;
+ cmdPtr->pcrSelectionIn.count = HASH_COUNT+1;
+ cmdPtr->pcrSelectionIn.pcrSelections[0].algorithmId =
+ TPM_ALG_SHA256;
+ cmdPtr->pcrSelectionIn.pcrSelections[0].sizeOfSelect = 1;
+ runTpmMarshalFailTest(baseCmd,
+ dataBufOut,
+ sizeof(dataBufOut),
+ cmdSize,
+ "PcrReadIn - invalid #algorithms",
+ num_ops,
+ fails);
+
+ // Invalid select size
+ memset(dataBufIn, 0, sizeof(dataBufIn));
+ memset(dataBufOut, 0, sizeof(dataBufOut));
+ cmdPtr->base.commandCode = TRUSTEDBOOT::TPM_CC_PCR_Read;
+ cmdPtr->pcrSelectionIn.count = HASH_COUNT+1;
+ cmdPtr->pcrSelectionIn.pcrSelections[0].algorithmId =
+ TPM_ALG_SHA256;
+ cmdPtr->pcrSelectionIn.pcrSelections[0].sizeOfSelect =
+ PCR_SELECT_MAX+1;
+ runTpmMarshalFailTest(baseCmd,
+ dataBufOut,
+ sizeof(dataBufOut),
+ cmdSize,
+ "PcrReadIn - invalid select size",
+ num_ops,
+ fails);
+
+ }
+
+
} while( 0 );
TRACFCOMP( g_trac_trustedboot,
@@ -567,6 +628,44 @@ class TrustedBootTest: public CxxTest::TestSuite
fails);
}
+ // Test PcrReadOut
+ {
+ TRACUCOMP( g_trac_trustedboot,
+ "testCommandUnmarshal - PcrReadOut" );
+ memset(dataBufIn, 0, sizeof(dataBufIn));
+ memset(dataBufOut, 0, sizeof(dataBufOut));
+
+ TRUSTEDBOOT::TPM2_PcrReadOut* respPtr =
+ reinterpret_cast<TRUSTEDBOOT::TPM2_PcrReadOut*>
+ (dataBufIn);
+ respPtr->pcrUpdateCounter = 0xAABBCCDD;
+ respPtr->pcrSelectionOut.count = 1;
+ respPtr->pcrSelectionOut.pcrSelections[0].sizeOfSelect =
+ PCR_SELECT_MAX;
+ respPtr->pcrValues.count = 1;
+ respPtr->pcrValues.digests[0].size = TPM_ALG_SHA256_SIZE;
+
+ runTpmUnmarshalTest(TRUSTEDBOOT::TPM_CC_PCR_Read,
+ dataBufIn,
+ sizeof(dataBufIn),
+ baseCmd,
+ sizeof(TPM2_PcrReadOut),
+ "PcrReadOut",
+ num_ops,
+ fails);
+
+ memset(dataBufIn, 0xFF, sizeof(dataBufIn));
+ respPtr->base.responseCode = TPM_SUCCESS;
+ runTpmUnmarshalFailTest(TRUSTEDBOOT::TPM_CC_PCR_Read,
+ dataBufIn,
+ sizeof(dataBufIn),
+ baseCmd,
+ sizeof(TPM2_PcrReadOut),
+ "PcrReadOut - xFF buffer",
+ num_ops,
+ fails);
+
+ }
@@ -689,6 +788,67 @@ class TrustedBootTest: public CxxTest::TestSuite
}
}
+ /**
+ * @brief TPM Read PCR
+ */
+ void testReadPCR ( void )
+ {
+ int64_t fails = 0, num_ops = 0;
+ uint8_t digest[TPM_ALG_SHA256_SIZE];
+ errlHndl_t err = NULL;
+
+ TRACFCOMP( g_trac_trustedboot,
+ "testReadPCR - Start" );
+ TpmTarget target = getTestTarget();
+
+ do
+ {
+
+ if (target.failed)
+ {
+ TS_FAIL( "testReadPCR - Master TPM not functional" );
+ break;
+ }
+
+ memset(digest, 0, sizeof(digest));
+
+ num_ops++;
+ err = tpmCmdPcrRead(&target,
+ PCR_DEBUG,
+ TPM_ALG_SHA256,
+ digest,
+ sizeof(digest));
+ if( NULL != err )
+ {
+ fails++;
+ TS_FAIL( "testReadPCR - Error detected" );
+ errlCommit( err,
+ SECURE_COMP_ID );
+ delete err;
+ err = NULL;
+ break;
+ }
+ else
+ {
+ TRACUCOMP(g_trac_trustedboot, "testReadPCR - "
+ "Read returned as expected.");
+ TRACUBIN(g_trac_trustedboot, "PCR Contents",
+ digest, sizeof(digest));
+ }
+
+
+
+ } while( 0 );
+ TRACFCOMP( g_trac_trustedboot,
+ "testReadPCR - End: %d/%d fails",
+ fails, num_ops );
+
+ if (NULL != target.logMgr)
+ {
+ delete target.logMgr;
+ }
+ }
+
};
diff --git a/src/usr/secureboot/trusted/trustedTypes.C b/src/usr/secureboot/trusted/trustedTypes.C
index 555efc141..331031ade 100644
--- a/src/usr/secureboot/trusted/trustedTypes.C
+++ b/src/usr/secureboot/trusted/trustedTypes.C
@@ -294,6 +294,185 @@ namespace TRUSTEDBOOT
i_tpmBufSize, io_cmdSize));
}
+ uint8_t* TPMS_PCR_SELECTION_marshal(TPMS_PCR_SELECTION* val,
+ uint8_t* o_tpmBuf,
+ size_t i_tpmBufSize,
+ size_t* io_cmdSize)
+ {
+ o_tpmBuf = marshalChunk(o_tpmBuf, i_tpmBufSize, io_cmdSize,
+ &(val->algorithmId), sizeof(val->algorithmId));
+ o_tpmBuf = marshalChunk(o_tpmBuf, i_tpmBufSize, io_cmdSize,
+ &(val->sizeOfSelect), sizeof(val->sizeOfSelect));
+
+ if (NULL != o_tpmBuf &&
+ PCR_SELECT_MAX < val->sizeOfSelect)
+ {
+ return NULL;
+ }
+
+ o_tpmBuf = marshalChunk(o_tpmBuf, i_tpmBufSize, io_cmdSize,
+ val->pcrSelect, val->sizeOfSelect);
+ return o_tpmBuf;
+ }
+
+ uint8_t* TPMS_PCR_SELECTION_unmarshal(TPMS_PCR_SELECTION* val,
+ uint8_t* i_tpmBuf,
+ size_t* io_tpmBufSize)
+ {
+ i_tpmBuf = unmarshalChunk(i_tpmBuf, io_tpmBufSize,
+ &(val->algorithmId),
+ sizeof(val->algorithmId));
+ i_tpmBuf = unmarshalChunk(i_tpmBuf, io_tpmBufSize,
+ &(val->sizeOfSelect),
+ sizeof(val->sizeOfSelect));
+ if (NULL != i_tpmBuf &&
+ PCR_SELECT_MAX < val->sizeOfSelect)
+ {
+ return NULL;
+ }
+ i_tpmBuf = unmarshalChunk(i_tpmBuf, io_tpmBufSize,
+ val->pcrSelect, val->sizeOfSelect);
+
+ return i_tpmBuf;
+ }
+
+ uint8_t* TPM2B_DIGEST_unmarshal(TPM2B_DIGEST* val,
+ uint8_t* i_tpmBuf,
+ size_t* io_tpmBufSize)
+ {
+ i_tpmBuf = unmarshalChunk(i_tpmBuf, io_tpmBufSize,
+ &val->size, sizeof(val->size));
+ if (NULL != i_tpmBuf &&
+ sizeof(TPMU_HA) < val->size)
+ {
+ TRACUCOMP( g_trac_trustedboot,
+ "TPM2B_DIGEST::unmarshal invalid size");
+ return NULL;
+ }
+ i_tpmBuf = unmarshalChunk(i_tpmBuf, io_tpmBufSize,
+ val->buffer, val->size);
+ return i_tpmBuf;
+
+ }
+
+ uint8_t* TPML_DIGEST_unmarshal(TPML_DIGEST* val,
+ uint8_t* i_tpmBuf,
+ size_t* io_tpmBufSize)
+ {
+ i_tpmBuf = unmarshalChunk(i_tpmBuf, io_tpmBufSize,
+ &(val->count), sizeof(val->count));
+ if (NULL != i_tpmBuf && HASH_COUNT < val->count)
+ {
+ TRACUCOMP( g_trac_trustedboot,
+ "TPML_DIGEST::unmarshal invalid count %d", val->count);
+ i_tpmBuf = NULL;
+ }
+ else if (NULL != i_tpmBuf)
+ {
+ for (size_t idx = 0; idx < val->count; idx++)
+ {
+ i_tpmBuf = TPM2B_DIGEST_unmarshal(&(val->digests[idx]),
+ i_tpmBuf,
+ io_tpmBufSize);
+ if (NULL == i_tpmBuf)
+ {
+ break;
+ }
+ }
+ }
+ return i_tpmBuf;
+
+ }
+
+ uint8_t* TPML_PCR_SELECTION_marshal(TPML_PCR_SELECTION* val,
+ uint8_t* o_tpmBuf,
+ size_t i_tpmBufSize,
+ size_t* io_cmdSize)
+ {
+ o_tpmBuf = marshalChunk(o_tpmBuf, i_tpmBufSize, io_cmdSize,
+ &(val->count), sizeof(val->count));
+ if (NULL != o_tpmBuf && HASH_COUNT < val->count)
+ {
+ TRACUCOMP( g_trac_trustedboot,
+ "TPML_PCR_SELECTION::marshal invalid count");
+ o_tpmBuf = NULL;
+ }
+ else if (NULL != o_tpmBuf)
+ {
+ for (size_t idx = 0; idx < val->count; idx++)
+ {
+ o_tpmBuf = TPMS_PCR_SELECTION_marshal(
+ &(val->pcrSelections[idx]),
+ o_tpmBuf,
+ i_tpmBufSize,
+ io_cmdSize);
+ if (NULL == o_tpmBuf)
+ {
+ break;
+ }
+ }
+ }
+ return o_tpmBuf;
+ }
+
+ uint8_t* TPML_PCR_SELECTION_unmarshal(TPML_PCR_SELECTION* val,
+ uint8_t* i_tpmBuf,
+ size_t* io_tpmBufSize)
+ {
+ i_tpmBuf = unmarshalChunk(i_tpmBuf, io_tpmBufSize,
+ &(val->count), sizeof(val->count));
+ if (NULL != i_tpmBuf && HASH_COUNT < val->count)
+ {
+ TRACUCOMP( g_trac_trustedboot,
+ "TPML_PCR_SELECTION::unmarshal invalid count");
+ i_tpmBuf = NULL;
+ }
+ else if (NULL != i_tpmBuf)
+ {
+ for (size_t idx = 0; idx < val->count; idx++)
+ {
+ i_tpmBuf = TPMS_PCR_SELECTION_unmarshal(
+ &(val->pcrSelections[idx]),
+ i_tpmBuf,
+ io_tpmBufSize);
+ if (NULL == i_tpmBuf)
+ {
+ break;
+ }
+ }
+ }
+ return i_tpmBuf;
+
+ }
+
+ uint8_t* TPM2_PcrReadIn_marshal(TPM2_PcrReadIn* val,
+ uint8_t* o_tpmBuf,
+ size_t i_tpmBufSize,
+ size_t* io_cmdSize)
+ {
+ // Base and handle has already been marshaled
+ return (TPML_PCR_SELECTION_marshal(&(val->pcrSelectionIn), o_tpmBuf,
+ i_tpmBufSize, io_cmdSize));
+ }
+
+ uint8_t* TPM2_PcrReadOut_unmarshal(TPM2_PcrReadOut* val,
+ uint8_t* i_tpmBuf,
+ size_t* io_tpmBufSize,
+ size_t i_outBufSize)
+ {
+ // Base and handle has already been marshaled
+ if (sizeof(TPM2_PcrReadOut) > i_outBufSize) return NULL;
+ i_tpmBuf = unmarshalChunk(i_tpmBuf, io_tpmBufSize,
+ &(val->pcrUpdateCounter),
+ sizeof(val->pcrUpdateCounter));
+
+ i_tpmBuf = TPML_PCR_SELECTION_unmarshal(&(val->pcrSelectionOut),
+ i_tpmBuf, io_tpmBufSize);
+ i_tpmBuf = TPML_DIGEST_unmarshal(&(val->pcrValues), i_tpmBuf,
+ io_tpmBufSize);
+ return i_tpmBuf;
+
+ }
uint8_t* TPMS_AUTH_COMMAND_marshal(TPMS_AUTH_COMMAND* val,
uint8_t* o_tpmBuf,
diff --git a/src/usr/secureboot/trusted/trustedTypes.H b/src/usr/secureboot/trusted/trustedTypes.H
index d3f98dec0..b74600652 100644
--- a/src/usr/secureboot/trusted/trustedTypes.H
+++ b/src/usr/secureboot/trusted/trustedTypes.H
@@ -78,7 +78,9 @@ namespace TRUSTEDBOOT
MAX_TPM_LOG_MSG = 128, ///< Maximum log message size
HASH_COUNT = 1, ///< Maximum # of digests
- PCR_SELECT_MAX = ((PCR_MAX+7)/8), ///< PCR selection octet max
+
+ PCR_SELECT_MAX = (IMPLEMENTATION_PCR+7)/8, ///< PCR selection octet max
+
};
typedef enum
@@ -348,6 +350,77 @@ namespace TRUSTEDBOOT
uint8_t* o_tpmBuf, size_t i_tpmBufSize,
size_t* io_cmdSize);
+ struct _TPMS_PCR_SELECTION
+ {
+ uint16_t algorithmId; ///< ID of hashing algorithm
+ uint8_t sizeOfSelect; ///< Byte size of pcrSelect array
+ uint8_t pcrSelect[PCR_SELECT_MAX];
+ } PACKED;
+ typedef struct _TPMS_PCR_SELECTION TPMS_PCR_SELECTION;
+ uint8_t* TPMS_PCR_SELECTION_marshal(TPMS_PCR_SELECTION* val,
+ uint8_t* o_tpmBuf, size_t i_tpmBufSize,
+ size_t* io_cmdSize);
+ uint8_t* TPMS_PCR_SELECTION_unmarshal(TPMS_PCR_SELECTION* val,
+ uint8_t* i_tpmBuf,
+ size_t* io_tpmBufSize);
+
+
+ struct _TPM2B_DIGEST
+ {
+ uint16_t size;
+ uint8_t buffer[sizeof(TPMU_HA)];
+ } PACKED;
+ typedef struct _TPM2B_DIGEST TPM2B_DIGEST;
+ uint8_t* TPM2B_DIGEST_unmarshal(TPM2B_DIGEST* val,
+ uint8_t* i_tpmBuf, size_t* io_tpmBufSize);
+
+ struct _TPML_DIGEST
+ {
+ uint32_t count;
+ TPM2B_DIGEST digests[HASH_COUNT];
+ } PACKED;
+ typedef struct _TPML_DIGEST TPML_DIGEST;
+ uint8_t* TPML_DIGEST_unmarshal(TPML_DIGEST* val,
+ uint8_t* i_tpmBuf, size_t* io_tpmBufSize);
+
+ struct _TPML_PCR_SELECTION
+ {
+ uint32_t count;
+ TPMS_PCR_SELECTION pcrSelections[HASH_COUNT];
+ } PACKED;
+ typedef struct _TPML_PCR_SELECTION TPML_PCR_SELECTION;
+ uint8_t* TPML_PCR_SELECTION_marshal(TPML_PCR_SELECTION* val,
+ uint8_t* o_tpmBuf, size_t i_tpmBufSize,
+ size_t* io_cmdSize);
+ uint8_t* TPML_PCR_SELECTION_unmarshal(TPML_PCR_SELECTION* val,
+ uint8_t* i_tpmBuf,
+ size_t* io_tpmBufSize);
+
+ /// Incoming PCR_Read structure
+ struct _TPM2_PcrReadIn
+ {
+ TPM2_BaseIn base;
+ TPML_PCR_SELECTION pcrSelectionIn;
+ } PACKED;
+ typedef struct _TPM2_PcrReadIn TPM2_PcrReadIn;
+ uint8_t* TPM2_PcrReadIn_marshal(TPM2_PcrReadIn* val,
+ uint8_t* o_tpmBuf, size_t i_tpmBufSize,
+ size_t* io_cmdSize);
+
+ /// Outgoing Pcr_Read structure
+ struct _TPM2_PcrReadOut
+ {
+ TPM2_BaseOut base;
+ uint32_t pcrUpdateCounter;
+ TPML_PCR_SELECTION pcrSelectionOut;
+ TPML_DIGEST pcrValues;
+ } PACKED;
+ typedef struct _TPM2_PcrReadOut TPM2_PcrReadOut;
+ uint8_t* TPM2_PcrReadOut_unmarshal(TPM2_PcrReadOut* val,
+ uint8_t* i_tpmBuf,
+ size_t* io_tpmBufSize,
+ size_t i_outBufSize);
+
/// TPM Authorization structure
/// This is not the full structure and only works for PW auth with NULL PW
struct _TPMS_AUTH_COMMAND
diff --git a/src/usr/secureboot/trusted/trustedbootCmds.C b/src/usr/secureboot/trusted/trustedbootCmds.C
index 611708c2e..d498af25d 100644
--- a/src/usr/secureboot/trusted/trustedbootCmds.C
+++ b/src/usr/secureboot/trusted/trustedbootCmds.C
@@ -212,6 +212,15 @@ errlHndl_t tpmMarshalCommandData(TPM2_BaseIn* i_cmd,
i_bufsize, o_cmdSize);
}
break;
+ case TPM_CC_PCR_Read:
+ {
+ TPM2_PcrReadIn* cmdPtr = (TPM2_PcrReadIn*)i_cmd;
+ sBuf = TPM2_PcrReadIn_marshal(cmdPtr, sBuf,
+ i_bufsize - (sBuf - o_outbuf),
+ o_cmdSize);
+ }
+ break;
+
case TPM_CC_PCR_Extend:
{
TPM2_ExtendIn* cmdPtr = (TPM2_ExtendIn*)i_cmd;
@@ -254,7 +263,7 @@ errlHndl_t tpmMarshalCommandData(TPM2_BaseIn* i_cmd,
{
TRACFCOMP( g_trac_trustedboot,
"TPM MARSHAL MARSHAL SIZE MISMATCH : %d %d",
- (sBuf - o_outbuf), *o_cmdSize );
+ (int)(sBuf - o_outbuf), (int)(*o_cmdSize) );
sBuf = NULL;
}
@@ -357,6 +366,15 @@ errlHndl_t tpmUnmarshalResponseData(uint32_t i_commandCode,
}
break;
+ case TPM_CC_PCR_Read:
+ {
+ TPM2_PcrReadOut* respPtr = (TPM2_PcrReadOut*)o_outBuf;
+ sBuf = TPM2_PcrReadOut_unmarshal(respPtr, sBuf,
+ &i_respBufSize,
+ i_outBufSize);
+ }
+ break;
+
default:
{
// Command code not supported
@@ -733,7 +751,7 @@ errlHndl_t tpmCmdPcrExtend(TpmTarget * io_target,
if (fullDigestSize == 0 ||
fullDigestSize != i_digestSize ||
NULL == i_digest ||
- PCR_MAX < i_pcr
+ IMPLEMENTATION_PCR < i_pcr
)
{
TRACFCOMP( g_trac_trustedboot,
@@ -815,6 +833,132 @@ errlHndl_t tpmCmdPcrExtend(TpmTarget * io_target,
}
+errlHndl_t tpmCmdPcrRead(TpmTarget* io_target,
+ TPM_Pcr i_pcr,
+ TPM_Alg_Id i_algId,
+ uint8_t* o_digest,
+ size_t i_digestSize)
+{
+ errlHndl_t err = NULL;
+ uint8_t dataBuf[sizeof(TPM2_PcrReadOut)];
+ size_t dataSize = sizeof(dataBuf);
+ size_t fullDigestSize = 0;
+ TPM2_PcrReadOut* resp = (TPM2_PcrReadOut*)dataBuf;
+ TPM2_PcrReadIn* cmd = (TPM2_PcrReadIn*)dataBuf;
+
+
+ TRACDCOMP( g_trac_trustedboot,
+ ">>tpmCmdPcrRead()" );
+ TRACUCOMP( g_trac_trustedboot,
+ ">>tpmCmdPcrRead() Pcr(%d) DS(%d)",
+ i_pcr, (int)i_digestSize);
+
+ do
+ {
+
+ fullDigestSize = getDigestSize(i_algId);
+
+ // Build our command block
+ memset(dataBuf, 0, sizeof(dataBuf));
+
+ // Argument verification
+ if (fullDigestSize > i_digestSize ||
+ NULL == o_digest ||
+ IMPLEMENTATION_PCR < i_pcr
+ )
+ {
+ TRACFCOMP( g_trac_trustedboot,
+ "TPM PCR READ ARG FAILURE FDS(%d) DS(%d) PCR(%d)",
+ (int)fullDigestSize, (int)i_digestSize, i_pcr);
+ /*@
+ * @errortype
+ * @reasoncode RC_TPM_INVALID_ARGS
+ * @severity ERRL_SEV_UNRECOVERABLE
+ * @moduleid MOD_TPM_CMD_PCRREAD
+ * @userdata1 Digest Ptr
+ * @userdata2[0:31] Full Digest Size
+ * @userdata2[32:63] PCR
+ * @devdesc Unmarshaling error detected
+ */
+ err = tpmCreateErrorLog(MOD_TPM_CMD_PCRREAD,
+ RC_TPM_INVALID_ARGS,
+ (uint64_t)o_digest,
+ (fullDigestSize << 32) |
+ i_pcr);
+
+ break;
+ }
+
+ cmd->base.tag = TPM_ST_NO_SESSIONS;
+ cmd->base.commandCode = TPM_CC_PCR_Read;
+ cmd->pcrSelectionIn.count = 1; // One algorithm
+ cmd->pcrSelectionIn.pcrSelections[0].algorithmId = i_algId;
+ cmd->pcrSelectionIn.pcrSelections[0].sizeOfSelect = PCR_SELECT_MAX;
+ memset(cmd->pcrSelectionIn.pcrSelections[0].pcrSelect, 0,
+ sizeof(cmd->pcrSelectionIn.pcrSelections[0].pcrSelect));
+ cmd->pcrSelectionIn.pcrSelections[0].pcrSelect[i_pcr / 8] =
+ 0x01 << (i_pcr % 8);
+
+ err = tpmTransmitCommand(io_target,
+ dataBuf,
+ sizeof(dataBuf));
+
+ if (TB_SUCCESS != err)
+ {
+ TRACFCOMP( g_trac_trustedboot,
+ "TPM PCRRead Transmit Fail ");
+ break;
+
+ }
+ else if ((sizeof(TPM2_BaseOut) > dataSize) ||
+ (TPM_SUCCESS != resp->base.responseCode) ||
+ (resp->pcrValues.count != 1) ||
+ (resp->pcrValues.digests[0].size != fullDigestSize))
+ {
+ TRACFCOMP( g_trac_trustedboot,
+ "TPM PCRRead OP Fail Ret(%X) ExSize(%d) "
+ "Size(%d) Cnt(%d) DSize(%d)",
+ resp->base.responseCode,
+ (int)sizeof(TPM2_BaseOut),
+ (int)dataSize,
+ resp->pcrValues.count,
+ resp->pcrValues.digests[0].size);
+
+ /*@
+ * @errortype
+ * @reasoncode RC_TPM_COMMAND_FAIL
+ * @severity ERRL_SEV_UNRECOVERABLE
+ * @moduleid MOD_TPM_CMD_PCRREAD
+ * @userdata1 responseCode
+ * @userdata2 dataSize
+ * @devdesc Command failure reading TPM FW version.
+ */
+ err = tpmCreateErrorLog(MOD_TPM_CMD_PCRREAD,
+ RC_TPM_COMMAND_FAIL,
+ resp->base.responseCode,
+ dataSize);
+ break;
+ }
+ else
+ {
+
+ memcpy(o_digest, resp->pcrValues.digests[0].buffer, fullDigestSize);
+
+ // Log the PCR value
+ TRACUBIN(g_trac_trustedboot, "PCR Out",
+ o_digest, fullDigestSize);
+
+ }
+
+ } while ( 0 );
+
+
+ TRACUCOMP( g_trac_trustedboot,
+ "<<tpmCmdPcrRead() - %s",
+ ((TB_SUCCESS == err) ? "No Error" : "With Error") );
+ return err;
+
+}
#ifdef __cplusplus
diff --git a/src/usr/secureboot/trusted/trustedbootCmds.H b/src/usr/secureboot/trusted/trustedbootCmds.H
index 8b68e23c4..53c7f453e 100644
--- a/src/usr/secureboot/trusted/trustedbootCmds.H
+++ b/src/usr/secureboot/trusted/trustedbootCmds.H
@@ -119,6 +119,8 @@ errlHndl_t tpmCmdGetCapFwVersion(TpmTarget* io_target);
* @param[in] i_algId Algorithm to use
* @param[in] i_digest Digest value to write to PCR, zeros appended as needed
* @param[in] i_digestSize Byte size of i_digest array
+ * @return errlHndl_t NULL if successful, otherwise a pointer to the
+ * error log.
*/
errlHndl_t tpmCmdPcrExtend(TpmTarget * io_target,
TPM_Pcr i_pcr,
@@ -126,6 +128,21 @@ errlHndl_t tpmCmdPcrExtend(TpmTarget * io_target,
uint8_t* i_digest,
size_t i_digestSize);
+/**
+ * @brief Send the TPM_Read command to the targeted TPM and log
+ * @param[in/out] io_target Current TPM target structure
+ * @param[in] i_pcr PCR to read from
+ * @param[in] i_algId Algorithm back to read from
+ * @param[out] o_digest Array to store PCR contents
+ * @param[in] i_digestSize Byte size of i_digest array
+ * @return errlHndl_t NULL if successful, otherwise a pointer to the
+ * error log.
+ */
+errlHndl_t tpmCmdPcrRead(TpmTarget* io_target,
+ TPM_Pcr i_pcr,
+ TPM_Alg_Id i_algId,
+ uint8_t* o_digest,
+ size_t i_digestSize);
#ifdef __cplusplus
} // end TRUSTEDBOOT namespace
OpenPOWER on IntegriCloud