summaryrefslogtreecommitdiffstats
path: root/src/usr/secureboot/trusted
diff options
context:
space:
mode:
authorIlya Smirnov <ismirno@us.ibm.com>2019-01-15 16:08:48 -0600
committerDaniel M. Crowell <dcrowell@us.ibm.com>2019-02-19 16:56:50 -0600
commit00325c6de8baa143c8e06e9324d6ba997465aa1f (patch)
tree819430f83cbfdb317e99878b05a6991734bd1852 /src/usr/secureboot/trusted
parent6781c16acf6de4b08cbc55f2569062ba1c655592 (diff)
downloadtalos-hostboot-00325c6de8baa143c8e06e9324d6ba997465aa1f.tar.gz
talos-hostboot-00325c6de8baa143c8e06e9324d6ba997465aa1f.zip
Secureboot: Enhanced Multinode Comm: Slave Node
This commit introduces the logic to create the slave response for the new enhanced multinode comm protocol. The slave response consists of an eye catcher, node ID, quote and signature data from TPM, PCR contents of the slave node TPM, Attestation Key Certificate, and the TPM log. All of the above data is packaged into a binary blob to be sent back to the master node. Change-Id: I927c6ca937e6c07af4185cf54c782697c5d822f6 RTC: 203643 Reviewed-on: http://rchgit01.rchland.ibm.com/gerrit1/70791 Tested-by: Jenkins Server <pfd-jenkins+hostboot@us.ibm.com> Reviewed-by: Michael Baiocchi <mbaiocch@us.ibm.com> Tested-by: Jenkins OP Build CI <op-jenkins+hostboot@us.ibm.com> Tested-by: FSP CI Jenkins <fsp-CI-jenkins+hostboot@us.ibm.com> Reviewed-by: Nicholas E. Bofferding <bofferdn@us.ibm.com> Reviewed-by: Marshall J. Wilks <mjwilks@us.ibm.com> Reviewed-by: Christopher J. Engel <cjengel@us.ibm.com> Tested-by: Jenkins OP HW <op-hw-jenkins+hostboot@us.ibm.com> Reviewed-by: Daniel M. Crowell <dcrowell@us.ibm.com>
Diffstat (limited to 'src/usr/secureboot/trusted')
-rw-r--r--src/usr/secureboot/trusted/base/trustedbootMsg.H33
-rw-r--r--src/usr/secureboot/trusted/base/trustedboot_base.C64
-rw-r--r--src/usr/secureboot/trusted/trustedTypes.C6
-rw-r--r--src/usr/secureboot/trusted/trustedTypes.H53
-rw-r--r--src/usr/secureboot/trusted/trustedboot.C68
-rw-r--r--src/usr/secureboot/trusted/trustedboot.H4
-rw-r--r--src/usr/secureboot/trusted/trustedbootCmds.C23
-rw-r--r--src/usr/secureboot/trusted/trustedbootCmds.H5
8 files changed, 217 insertions, 39 deletions
diff --git a/src/usr/secureboot/trusted/base/trustedbootMsg.H b/src/usr/secureboot/trusted/base/trustedbootMsg.H
index 9789c4fed..929233111 100644
--- a/src/usr/secureboot/trusted/base/trustedbootMsg.H
+++ b/src/usr/secureboot/trusted/base/trustedbootMsg.H
@@ -62,7 +62,8 @@ namespace TRUSTEDBOOT
MSG_TYPE_READ_AK_CERT,
MSG_TYPE_GEN_QUOTE,
MSG_TYPE_FLUSH_CONTEXT,
- MSG_TYPE_LAST = MSG_TYPE_FLUSH_CONTEXT,
+ MSG_TYPE_PCR_READ,
+ MSG_TYPE_LAST = MSG_TYPE_PCR_READ,
};
/// PCREXTEND message data
@@ -103,8 +104,8 @@ namespace TRUSTEDBOOT
struct ReadAKCertData
{
TpmTarget* tpm;
- AKCertificate_t* data; // The output of NVRAM read
- ReadAKCertData(TpmTarget* i_tpm, AKCertificate_t* i_data) :
+ TPM2B_MAX_NV_BUFFER* data; // The output of NVRAM read
+ ReadAKCertData(TpmTarget* i_tpm, TPM2B_MAX_NV_BUFFER* i_data) :
tpm(i_tpm), data(i_data)
{
}
@@ -114,10 +115,10 @@ namespace TRUSTEDBOOT
struct GenQuoteData
{
TpmTarget* tpm;
- MasterTpmNonce_t* masterNonce; // 32-byte nonce value
+ const MasterTpmNonce_t* const masterNonce; // 32-byte nonce value
QuoteDataOut* data; // Output - the quote and signature fields
GenQuoteData(TpmTarget* i_tpm,
- MasterTpmNonce_t* i_masterNonce,
+ const MasterTpmNonce_t* const i_masterNonce,
QuoteDataOut* o_data) :
tpm(i_tpm),
masterNonce(i_masterNonce),
@@ -126,6 +127,28 @@ namespace TRUSTEDBOOT
}
};
+ // The struct used to read a PCR from TPM
+ struct PcrReadData
+ {
+ TpmTarget* tpm; // TPM target whose PCRs are to be read
+ TPM_Pcr pcr; // The PCR to read
+ TPM_Alg_Id alg; // The PCR bank to read
+ uint8_t* digest; // The buffer to hold the PCR contents
+ size_t digestSize; // The size of the digest buffer
+ PcrReadData(TpmTarget* i_tpm,
+ TPM_Pcr i_pcr,
+ TPM_Alg_Id i_alg,
+ uint8_t* o_digest,
+ size_t i_digestSize) :
+ tpm(i_tpm),
+ pcr(i_pcr),
+ alg(i_alg),
+ digest(o_digest),
+ digestSize(i_digestSize)
+ {
+ }
+ };
+
// Trustedboot message class
class Message
{
diff --git a/src/usr/secureboot/trusted/base/trustedboot_base.C b/src/usr/secureboot/trusted/base/trustedboot_base.C
index 5c68e3c2f..e0170b164 100644
--- a/src/usr/secureboot/trusted/base/trustedboot_base.C
+++ b/src/usr/secureboot/trusted/base/trustedboot_base.C
@@ -902,7 +902,7 @@ errlHndl_t createAttestationKeys(TpmTarget* i_target)
return l_errl;
}
-errlHndl_t readAKCertificate(TpmTarget* i_target, AKCertificate_t* o_data)
+errlHndl_t readAKCertificate(TpmTarget* i_target, TPM2B_MAX_NV_BUFFER* o_data)
{
errlHndl_t l_errl = nullptr;
#ifdef CONFIG_TPMDD
@@ -955,7 +955,7 @@ errlHndl_t readAKCertificate(TpmTarget* i_target, AKCertificate_t* o_data)
}
errlHndl_t generateQuote(TpmTarget* i_target,
- MasterTpmNonce_t* i_masterNonce,
+ const MasterTpmNonce_t* const i_masterNonce,
QuoteDataOut* o_data)
{
errlHndl_t l_errl = nullptr;
@@ -1060,4 +1060,64 @@ errlHndl_t flushContext(TpmTarget* i_target)
return l_errl;
}
+errlHndl_t pcrRead(TpmTarget* i_target,
+ const TPM_Pcr i_pcr,
+ const TPM_Alg_Id i_algId,
+ const size_t i_digestSize,
+ uint8_t* const o_digest)
+{
+ errlHndl_t l_errl = nullptr;
+#ifdef CONFIG_TPMDD
+ Message* l_msg = nullptr;
+
+ PcrReadData* l_data = new PcrReadData{i_target,
+ i_pcr,
+ i_algId,
+ o_digest,
+ i_digestSize};
+
+ l_msg = Message::factory(MSG_TYPE_PCR_READ,
+ sizeof(*l_data),
+ reinterpret_cast<uint8_t*>(l_data),
+ MSG_MODE_SYNC);
+ assert(l_msg != nullptr, "pcrRead: l_msg is nullptr");
+ l_data = nullptr; //l_msg now owns l_data
+
+ int l_rc = msg_sendrecv(systemData.msgQ, l_msg->iv_msg);
+ if(l_rc)
+ {
+ /*@
+ * @errortype ERRL_SEV_UNRECOVERABLE
+ * @moduleid MOD_PCR_READ
+ * @reasoncode RC_SENDRECV_FAIL
+ * @userdata1 rc from msg_sendrecv
+ * @userdata2 TPM HUID
+ * @devdesc msg_sendrecv failed for pcrRead
+ * @custdesc trustedboot failure
+ */
+ l_errl = new ERRORLOG::ErrlEntry(ERRORLOG::ERRL_SEV_UNRECOVERABLE,
+ MOD_PCR_READ,
+ RC_SENDRECV_FAIL,
+ l_rc,
+ TARGETING::get_huid(i_target),
+ ERRORLOG::ErrlEntry::ADD_SW_CALLOUT);
+ l_errl->collectTrace(SECURE_COMP_NAME);
+ l_errl->collectTrace(TRBOOT_COMP_NAME);
+ }
+ else
+ {
+ l_errl = l_msg->iv_errl;
+ l_msg->iv_errl = nullptr;
+ }
+
+ if(l_msg)
+ {
+ delete l_msg;
+ l_msg = nullptr;
+ }
+
+#endif
+ return l_errl;
+}
+
} // end TRUSTEDBOOT
diff --git a/src/usr/secureboot/trusted/trustedTypes.C b/src/usr/secureboot/trusted/trustedTypes.C
index fe8112151..f78b7411a 100644
--- a/src/usr/secureboot/trusted/trustedTypes.C
+++ b/src/usr/secureboot/trusted/trustedTypes.C
@@ -5,7 +5,7 @@
/* */
/* OpenPOWER HostBoot Project */
/* */
-/* Contributors Listed Below - COPYRIGHT 2015,2017 */
+/* Contributors Listed Below - COPYRIGHT 2015,2019 */
/* [+] International Business Machines Corp. */
/* */
/* */
@@ -378,7 +378,7 @@ namespace TRUSTEDBOOT
sizeof(TPMU_HA) < val->size)
{
TRACUCOMP( g_trac_trustedboot,
- "TPM2B_DIGEST::unmarshal invalid size");
+ "TPM2B_DIGEST::unmarshal invalid size (%d)", val->size);
return NULL;
}
i_tpmBuf = unmarshalChunk(i_tpmBuf, io_tpmBufSize,
@@ -393,7 +393,7 @@ namespace TRUSTEDBOOT
{
i_tpmBuf = unmarshalChunk(i_tpmBuf, io_tpmBufSize,
&(val->count), sizeof(val->count));
- if (NULL != i_tpmBuf && HASH_COUNT < val->count)
+ if (NULL != i_tpmBuf && FW_USED_PCR_COUNT < val->count)
{
TRACUCOMP( g_trac_trustedboot,
"TPML_DIGEST::unmarshal invalid count %d", val->count);
diff --git a/src/usr/secureboot/trusted/trustedTypes.H b/src/usr/secureboot/trusted/trustedTypes.H
index 7efa1d901..ae3f3e233 100644
--- a/src/usr/secureboot/trusted/trustedTypes.H
+++ b/src/usr/secureboot/trusted/trustedTypes.H
@@ -59,14 +59,6 @@ namespace TRUSTEDBOOT
MAX_TRANSMIT_SIZE = 1024, ///< Maximum send/receive transmit size
};
- /// TPM Algorithm defines
- typedef enum
- {
- TPM_ALG_SHA1 = 0x0004, ///< SHA1 Id
- TPM_ALG_SHA256 = 0x000B, ///< SHA256 Id
- TPM_ALG_INVALID_ID ///< Used for error checking
- } TPM_Alg_Id;
-
typedef enum
{
TPM_ALG_SHA1_SIZE = 20, ///< SHA1 digest byte size
@@ -164,6 +156,39 @@ namespace TRUSTEDBOOT
// Command structures taken from Trusted Platform Module Library Part 3:
// Commands Family "2.0"
+ /* TPM data structures naming conventions
+ (taken from the TCG TPM spec v2)
+
+ _TPM_ an indication/signal from the TPM’s system interface
+ TPM_ a constant or an enumerated type
+ TPM2_ a command defined by this specification
+ TPM2B_ a structure that is a sized buffer where the size of the buffer is
+ contained in a 16-bit, unsigned value. The first parameter is the
+ size in octets of the second parameter. The second parameter may be
+ any type.
+ TPMA_ a structure where each of the fields defines an attribute and each
+ field is usually a single bit. All the attributes in an attribute
+ structure are packed with the overall size of the structure
+ indicated in the heading of the attribute description
+ (UINT8, UINT16, or UINT32).
+ TPM_ALG_ an enumerated type that indicates an algorithm
+ A TPM_ALG_ is often used as a selector for a union.
+ TPMI_ an interface type. The value is specified for purposes of dynamic
+ type checking when unmarshaled.
+ TPML_ a list length followed by the indicated number of entries of the
+ indicated type. This is an array with a length field.
+ TPMS_ a structure that is not a size buffer or a tagged buffer or a
+ list
+ TPMT_ a structure with the first parameter being a structure tag,
+ indicating the type of the structure that follows. A structure tag
+ may be either a TPMT_ST_ or TPM_ALG_ depending on context.
+ TPMU_ a union of structures, lists, or unions. If a union exists, there
+ will normally be a companion TPMT_ that is the expression of the
+ union in a tagged structure, where the tag is the selector
+ indicating which member of the union is present.
+ */
+
+
/// TPM capability response structure
struct _TPMS_TAGGED_PROPERTY
{
@@ -419,8 +444,9 @@ namespace TRUSTEDBOOT
struct _TPM2B_DIGEST
{
- uint16_t size;
- uint8_t buffer[sizeof(TPMU_HA)];
+ uint16_t size; // size in octets of the buffer field; may be 0
+ uint8_t buffer[sizeof(TPMU_HA)]; // the buffer area that can be no
+ // larger than a digest
} PACKED;
typedef struct _TPM2B_DIGEST TPM2B_DIGEST;
const uint8_t* TPM2B_DIGEST_unmarshal(TPM2B_DIGEST* val,
@@ -439,8 +465,9 @@ namespace TRUSTEDBOOT
struct _TPML_PCR_SELECTION
{
- uint32_t count;
- TPMS_PCR_SELECTION pcrSelections[HASH_COUNT];
+ uint32_t count; //number of selection structures;
+ // a value of zero is allowed.
+ TPMS_PCR_SELECTION pcrSelections[HASH_COUNT]; // list of selections
} PACKED;
typedef struct _TPML_PCR_SELECTION TPML_PCR_SELECTION;
uint8_t* TPML_PCR_SELECTION_marshal(const TPML_PCR_SELECTION* val,
@@ -541,7 +568,7 @@ namespace TRUSTEDBOOT
struct _TPM2_NVReadOut
{
TPM2_BaseOut base;
- uint8_t NVData[TPM_NV_DATA_SIZE];
+ TPM2B_MAX_NV_BUFFER data;
} PACKED;
typedef struct _TPM2_NVReadOut TPM2_NVReadOut;
diff --git a/src/usr/secureboot/trusted/trustedboot.C b/src/usr/secureboot/trusted/trustedboot.C
index 1f5e159a2..28521dc7b 100644
--- a/src/usr/secureboot/trusted/trustedboot.C
+++ b/src/usr/secureboot/trusted/trustedboot.C
@@ -1501,7 +1501,7 @@ errlHndl_t doCreateAttKeys(TpmTarget* i_tpm)
return l_errl;
}
-errlHndl_t doReadAKCert(TpmTarget* i_tpm, AKCertificate_t* o_data)
+errlHndl_t doReadAKCert(TpmTarget* i_tpm, TPM2B_MAX_NV_BUFFER* o_data)
{
errlHndl_t l_errl = nullptr;
@@ -1523,7 +1523,7 @@ errlHndl_t doReadAKCert(TpmTarget* i_tpm, AKCertificate_t* o_data)
}
errlHndl_t doGenQuote(TpmTarget* i_tpm,
- MasterTpmNonce_t* i_masterNonce,
+ const MasterTpmNonce_t* const i_masterNonce,
QuoteDataOut* o_data)
{
errlHndl_t l_errl = nullptr;
@@ -1566,6 +1566,35 @@ errlHndl_t doFlushContext(TpmTarget* i_tpm)
return l_errl;
}
+errlHndl_t doPcrRead(TpmTarget* i_target,
+ const TPM_Pcr i_pcr,
+ const TPM_Alg_Id i_algId,
+ const size_t i_digestSize,
+ uint8_t* const o_digest)
+{
+ errlHndl_t l_errl = nullptr;
+
+ do {
+ l_errl = validateTpmHandle(i_target);
+ if(l_errl)
+ {
+ break;
+ }
+
+ l_errl = tpmCmdPcrRead(i_target,
+ i_pcr,
+ i_algId,
+ o_digest,
+ i_digestSize);
+ if(l_errl)
+ {
+ break;
+ }
+
+ } while(0);
+ return l_errl;
+}
+
void* tpmDaemon(void* unused)
{
bool shutdownPending = false;
@@ -1815,6 +1844,19 @@ void* tpmDaemon(void* unused)
}
break;
+ case TRUSTEDBOOT::MSG_TYPE_PCR_READ:
+ {
+ tb_msg = static_cast<TRUSTEDBOOT::Message*>(msg->extra_data);
+ PcrReadData* l_data =
+ reinterpret_cast<PcrReadData*>(tb_msg->iv_data);
+ tb_msg->iv_errl = doPcrRead(l_data->tpm,
+ l_data->pcr,
+ l_data->alg,
+ l_data->digestSize,
+ l_data->digest);
+ }
+ break;
+
default:
assert(false, "Invalid msg command");
break;
@@ -2219,4 +2261,26 @@ errlHndl_t poisonTpm(const TpmTarget* i_pTpm)
return l_errl;
}
+errlHndl_t poisonAllTpms()
+{
+ errlHndl_t l_errl = nullptr;
+#ifdef CONFIG_TPMDD
+ do {
+
+ TARGETING::TargetHandleList l_tpms;
+ getTPMs(l_tpms, TRUSTEDBOOT::TPM_FILTER::ALL_FUNCTIONAL);
+ for(auto l_tpm : l_tpms)
+ {
+ l_errl = poisonTpm(l_tpm);
+ if(l_errl)
+ {
+ break;
+ }
+ }
+
+ } while(0);
+#endif
+ return l_errl;
+}
+
} // end TRUSTEDBOOT
diff --git a/src/usr/secureboot/trusted/trustedboot.H b/src/usr/secureboot/trusted/trustedboot.H
index 155bbf696..53ddb40fc 100644
--- a/src/usr/secureboot/trusted/trustedboot.H
+++ b/src/usr/secureboot/trusted/trustedboot.H
@@ -5,7 +5,7 @@
/* */
/* OpenPOWER HostBoot Project */
/* */
-/* Contributors Listed Below - COPYRIGHT 2015,2018 */
+/* Contributors Listed Below - COPYRIGHT 2015,2019 */
/* [+] International Business Machines Corp. */
/* */
/* */
@@ -46,7 +46,7 @@ extern trace_desc_t* g_trac_trustedboot;
// Easy macro replace for unit testing
//#define TRACUCOMP(args...) TRACFCOMP(args)
-#define TRACUCOMP(args...)
+#define TRACUCOMP(args...) TRACDCOMP(args)
//#define TRACUBIN(args...) TRACFBIN(args)
#define TRACUBIN(args...)
diff --git a/src/usr/secureboot/trusted/trustedbootCmds.C b/src/usr/secureboot/trusted/trustedbootCmds.C
index 1aeb387f9..c989de719 100644
--- a/src/usr/secureboot/trusted/trustedbootCmds.C
+++ b/src/usr/secureboot/trusted/trustedbootCmds.C
@@ -411,9 +411,9 @@ errlHndl_t tpmUnmarshalResponseData(uint32_t i_commandCode,
reinterpret_cast<TPM2_NVReadOut*>(o_outBuf);
TPM2_NVReadOut* l_tpmRespData =
reinterpret_cast<TPM2_NVReadOut*>(i_respBuf);
- memcpy(l_tpmRespData->NVData,
- l_respPtr->NVData,
- TPM_NV_DATA_SIZE);
+ memcpy(reinterpret_cast<uint8_t*>(&l_tpmRespData->data),
+ reinterpret_cast<uint8_t*>(&l_respPtr->data),
+ sizeof(l_tpmRespData->data));
}
break;
@@ -1346,7 +1346,7 @@ errlHndl_t tpmCmdCreateAttestationKeys(TpmTarget* i_target)
return l_errl;
}
-errlHndl_t tpmCmdReadAKCertificate(TpmTarget* i_target, AKCertificate_t* o_data)
+errlHndl_t tpmCmdReadAKCertificate(TpmTarget* i_target, TPM2B_MAX_NV_BUFFER* o_data)
{
TRACFCOMP(g_trac_trustedboot, ENTER_MRK"tpmCmdReadAKCertificate()");
errlHndl_t l_errl = nullptr;
@@ -1413,8 +1413,10 @@ errlHndl_t tpmCmdReadAKCertificate(TpmTarget* i_target, AKCertificate_t* o_data)
}
TPM2_NVReadOut* l_read = reinterpret_cast<TPM2_NVReadOut*>(l_resp);
- // NVRAM holds the AK certificate. Copy out a fixed size of 500 bytes
- memcpy(*o_data, l_read->NVData, TPM_NV_DATA_SIZE);
+ // NVRAM holds the AK certificate. Copy out the size and the certificate
+ memcpy(reinterpret_cast<uint8_t*>(o_data),
+ reinterpret_cast<uint8_t*>(&l_read->data),
+ sizeof(*o_data));
}while(0);
@@ -1423,7 +1425,7 @@ errlHndl_t tpmCmdReadAKCertificate(TpmTarget* i_target, AKCertificate_t* o_data)
}
errlHndl_t tpmCmdGenerateQuote(TpmTarget* i_target,
- MasterTpmNonce_t* i_masterNonce,
+ const MasterTpmNonce_t* const i_masterNonce,
QuoteDataOut* o_data)
{
TRACFCOMP(g_trac_trustedboot, ENTER_MRK"tpmCmdGenerateQuote()");
@@ -1457,9 +1459,12 @@ errlHndl_t tpmCmdGenerateQuote(TpmTarget* i_target,
l_cmd->quoteData.pcrSelection.pcrSelections[0].algorithmId = TPM_ALG_SHA256;
l_cmd->quoteData.pcrSelection.pcrSelections[0].sizeOfSelect =PCR_SELECT_MAX;
- for(size_t i = PCR_0; i <= PCR_7 ; ++i)
+ memset(l_cmd->quoteData.pcrSelection.pcrSelections[0].pcrSelect, 0,
+ sizeof(l_cmd->quoteData.pcrSelection.pcrSelections[0].pcrSelect));
+
+ for(size_t i = PCR_0; i <= FW_USED_PCR_COUNT; ++i)
{
- l_cmd->quoteData.pcrSelection.pcrSelections[0].pcrSelect[i/8] =
+ l_cmd->quoteData.pcrSelection.pcrSelections[0].pcrSelect[i/8] |=
0x01 << (i % 8);
}
diff --git a/src/usr/secureboot/trusted/trustedbootCmds.H b/src/usr/secureboot/trusted/trustedbootCmds.H
index 9b0e99aaa..571b5224c 100644
--- a/src/usr/secureboot/trusted/trustedbootCmds.H
+++ b/src/usr/secureboot/trusted/trustedbootCmds.H
@@ -175,7 +175,6 @@ errlHndl_t tpmCmdPcrRead(TpmTarget* io_target,
uint8_t* o_digest,
size_t i_digestSize);
-
/**
* @brief Send the TPM_CC_Create to the TPM
* @param[in] i_target the target TPM (must not be nullptr)
@@ -192,7 +191,7 @@ errlHndl_t tpmCmdCreateAttestationKeys(TpmTarget* i_target);
* @return nullptr on success; non-nullptr on error
*/
errlHndl_t tpmCmdReadAKCertificate(TpmTarget* i_target,
- AKCertificate_t* o_data);
+ TPM2B_MAX_NV_BUFFER* o_data);
/**
* @brief Send the TPM_CC_Quote command to the given TPM to generate quote
@@ -204,7 +203,7 @@ errlHndl_t tpmCmdReadAKCertificate(TpmTarget* i_target,
* @return nullptr on success; non-nullptr on error
*/
errlHndl_t tpmCmdGenerateQuote(TpmTarget* i_target,
- MasterTpmNonce_t* i_masterNonce,
+ const MasterTpmNonce_t* i_masterNonce,
QuoteDataOut* o_data);
/**
OpenPOWER on IntegriCloud