[Skiboot] [PATCH 5/5] hdata/tpmrel.c: add cvc offset nodes
Claudio Carvalho
cclaudio at linux.vnet.ibm.com
Thu Aug 31 17:42:52 AEST 2017
This parses the hdat tpmrel structure to get the offsets of the
functions provided by the container verification code and then creates
one 'ibm,container-verification-code' child node for each offset found.
Signed-off-by: Claudio Carvalho <cclaudio at linux.vnet.ibm.com>
---
hdata/spira.h | 12 +++++++++
hdata/tpmrel.c | 78 +++++++++++++++++++++++++++++++++++++++++++++++++++++++---
2 files changed, 87 insertions(+), 3 deletions(-)
diff --git a/hdata/spira.h b/hdata/spira.h
index d4c3023..799f0d7 100644
--- a/hdata/spira.h
+++ b/hdata/spira.h
@@ -1132,6 +1132,18 @@ struct secureboot_tpm_info {
__be32 drtm_log_size;
} __packed;
+/* Idata index 2: Hash and Verification Function Offsets Array */
+#define TPMREL_IDATA_HASH_VERIF_OFFSETS 2
+
+struct hash_and_verification {
+#define TPMREL_HV_SHA512 0x00
+#define TPMREL_HV_CONTAINER_VERIFY 0x01
+ __be32 type;
+ __be32 version;
+ __be32 dbob_id;
+ __be32 offset;
+} __packed;
+
static inline const char *cpu_state(u32 flags)
{
switch ((flags & CPU_ID_VERIFY_MASK) >> CPU_ID_VERIFY_SHIFT) {
diff --git a/hdata/tpmrel.c b/hdata/tpmrel.c
index 81e6443..cc80f3f 100644
--- a/hdata/tpmrel.c
+++ b/hdata/tpmrel.c
@@ -99,6 +99,75 @@ static struct hdat_container_verification_code *map_cvc(uint32_t type)
return NULL;
}
+struct {
+ uint32_t container_version;
+ uint32_t type;
+ uint32_t version;
+ const char *compat;
+} cvc_offsets[] = {
+ {0x1, TPMREL_HV_SHA512, 0x1, "ibm,sha512-hash"},
+ {0x1, TPMREL_HV_CONTAINER_VERIFY, 0x1, "ibm,container-verify"}
+};
+
+static const char *map_offset_compat(uint32_t container_version, uint32_t type,
+ uint32_t version)
+{
+ int i;
+
+ for (i = 0; i < ARRAY_SIZE(cvc_offsets); i++) {
+ if (cvc_offsets[i].container_version == container_version &&
+ cvc_offsets[i].type == type &&
+ cvc_offsets[i].version == version)
+ return cvc_offsets[i].compat;
+ }
+ return NULL;
+}
+
+static int cvc_add_code_offset_nodes(struct dt_node *parent,
+ struct HDIF_common_hdr *hdif_hdr,
+ struct hdat_container_verification_code *cvc)
+{
+ const struct hash_and_verification *hv;
+ const char *compat;
+ uint32_t type, version;
+ int count, i;
+
+ count = HDIF_get_iarray_size(hdif_hdr, TPMREL_IDATA_HASH_VERIF_OFFSETS);
+
+ if (count > cvc->num_offsets) {
+ prlog(PR_ALERT, "found %d cvc offsets for %s. (expected=%d) "
+ "HOSTBOOT BUG?", count, cvc->compat, cvc->num_offsets);
+ return -1;
+ }
+
+ for (i = 0; i < count; i++) {
+
+ hv = HDIF_get_iarray_item(hdif_hdr,
+ TPMREL_IDATA_HASH_VERIF_OFFSETS,
+ i, NULL);
+
+ type = be32_to_cpu(hv->type);
+ version = be32_to_cpu(hv->version);
+
+ compat = map_offset_compat(cvc->container_version, type, version);
+ if (compat) {
+ uint32_t reg;
+ struct dt_node *code;
+
+ reg = be32_to_cpu(hv->offset);
+
+ code = dt_new_addr(parent, "ibm,code-offset", reg);
+ dt_add_property_strings(code, "compatible", compat);
+ dt_add_property_cells(code, "reg", reg);
+ } else {
+ prlog(PR_INFO, "cvc offset not added. UNKNOWN:"
+ "cv=%d, type=%d, version=%d\n",
+ cvc->container_version, type, version);
+ }
+ }
+ return 0;
+}
+
#define HRMOR_BIT (1ul << 63)
static struct dt_node *get_reserved_memory(const struct msvpd_hb_reserved_mem *hb_resv_mem)
@@ -127,7 +196,7 @@ static struct dt_node *get_reserved_memory(const struct msvpd_hb_reserved_mem *h
return node;
}
-static void cvc_init(struct dt_node *parent)
+static void cvc_init(struct dt_node *parent, struct HDIF_common_hdr *hdif_hdr)
{
const struct msvpd_hb_reserved_mem *hb_resv_mem;
const struct HDIF_common_hdr *ms_vpd;
@@ -153,7 +222,8 @@ static void cvc_init(struct dt_node *parent)
* to find it.
*
* Once we find the container verification code we create a new node
- * with a cross reference to its reserved memory.
+ * with a cross reference to its reserved memory and also create inner
+ * nodes (one for each code offset provided).
*/
for (i = 0; i < count; i++) {
hb_resv_mem = HDIF_get_iarray_item(ms_vpd,
@@ -182,6 +252,8 @@ static void cvc_init(struct dt_node *parent)
dt_add_property_cells(node, "#size-cells", 0);
dt_add_property_strings(node, "compatible", cvc->compat);
dt_add_property_cells(node, "memory-region", reserved_mem->phandle);
+
+ cvc_add_code_offset_nodes(node, hdif_hdr, cvc);
}
}
return;
@@ -206,5 +278,5 @@ void node_stb_parse(void)
return;
}
- cvc_init(node);
+ cvc_init(node, hdif_hdr);
}
--
2.7.4
More information about the Skiboot
mailing list