soc/intel/cmd/block: Implement an API to get firmware partition details
This patch retrieves details of a specified firmware partition table.
The information retrieved includes the current firmware version and
other information about the firmware partition. The patch communicates
with the ME using the HECI command to acquire this information.
BUG=b:273661726
Test=Verified the changes for ISH partition on nissa board.
Signed-off-by: Dinesh Gehlot <digehlot@google.com>
Change-Id: I0582010bbb836bd4734f843a8c74dee49d203fd8
Reviewed-on: https://review.coreboot.org/c/coreboot/+/74005
Tested-by: build bot (Jenkins) <no-reply@coreboot.org>
Reviewed-by: Sridhar Siricilla <sridhar.siricilla@intel.com>
diff --git a/src/soc/intel/common/block/cse/cse.c b/src/soc/intel/common/block/cse/cse.c
index 1aa3454..9a4cd45 100644
--- a/src/soc/intel/common/block/cse/cse.c
+++ b/src/soc/intel/common/block/cse/cse.c
@@ -1213,6 +1213,63 @@
}
}
+static enum cb_err send_get_fpt_partition_info_cmd(enum fpt_partition_id id,
+ struct fw_version_resp *resp)
+{
+ enum cse_tx_rx_status ret;
+ struct fw_version_msg {
+ struct mkhi_hdr hdr;
+ enum fpt_partition_id partition_id;
+ } __packed msg = {
+ .hdr = {
+ .group_id = MKHI_GROUP_ID_GEN,
+ .command = GEN_GET_IMAGE_FW_VERSION,
+ },
+ .partition_id = id,
+ };
+
+ /*
+ * Prerequisites:
+ * 1) HFSTS1 CWS is Normal
+ * 2) HFSTS1 COM is Normal
+ * 3) Only sent after DID (accomplished by compiling this into ramstage)
+ */
+
+ if (cse_is_hfs1_com_soft_temp_disable() || !cse_is_hfs1_cws_normal() ||
+ !cse_is_hfs1_com_normal()) {
+ printk(BIOS_ERR,
+ "HECI: Prerequisites not met for Get Image Firmware Version command\n");
+ return CB_ERR;
+ }
+
+ size_t resp_size = sizeof(struct fw_version_resp);
+ ret = heci_send_receive(&msg, sizeof(msg), resp, &resp_size, HECI_MKHI_ADDR);
+
+ if (ret || resp->hdr.result) {
+ printk(BIOS_ERR, "CSE: Failed to get partition information for %d: 0x%x\n",
+ id, resp->hdr.result);
+ return CB_ERR;
+ }
+
+ return CB_SUCCESS;
+}
+
+enum cb_err cse_get_fpt_partition_info(enum fpt_partition_id id, struct fw_version_resp *resp)
+{
+ if (vboot_recovery_mode_enabled()) {
+ printk(BIOS_WARNING,
+ "CSE: Skip sending Get Image Info command during recovery mode!\n");
+ return CB_ERR;
+ }
+
+ if (id == FPT_PARTITION_NAME_ISHC && !CONFIG(DRIVERS_INTEL_ISH)) {
+ printk(BIOS_WARNING, "CSE: Info request denied, no ISH partition\n");
+ return CB_ERR;
+ }
+
+ return send_get_fpt_partition_info_cmd(id, resp);
+}
+
#if ENV_RAMSTAGE
/*
diff --git a/src/soc/intel/common/block/include/intelblocks/cse.h b/src/soc/intel/common/block/include/intelblocks/cse.h
index b39ae7f..6b708ca 100644
--- a/src/soc/intel/common/block/include/intelblocks/cse.h
+++ b/src/soc/intel/common/block/include/intelblocks/cse.h
@@ -49,6 +49,7 @@
#define MKHI_BUP_COMMON_GET_BOOT_PARTITION_INFO 0x1c
#define MKHI_BUP_COMMON_SET_BOOT_PARTITION_INFO 0x1d
#define MKHI_BUP_COMMON_DATA_CLEAR 0x20
+#define GEN_GET_IMAGE_FW_VERSION 0x1c
/* Get boot performance command id */
#define MKHI_BUP_COMMON_GET_BOOT_PERF_DATA 0x8
@@ -85,6 +86,12 @@
PCI_ME_HFSTS6 = 0x6C,
};
+/* CSE partition list */
+enum fpt_partition_id {
+ FPT_PARTITION_NAME_UNDEFINED = 0x0,
+ FPT_PARTITION_NAME_ISHC = 0x43485349,
+};
+
/* MKHI Message Header */
struct mkhi_hdr {
uint8_t group_id;
@@ -118,6 +125,25 @@
struct me_version fitc;
} __packed;
+/* Module data from manifest */
+struct flash_partition_data {
+ enum fpt_partition_id partition_id;
+ uint8_t reserved1[8];
+ struct fw_version version;
+ uint32_t vendor_id;
+ uint32_t tcb_svn;
+ uint32_t arb_svn;
+ uint32_t vcn;
+ uint32_t reserved2[13];
+};
+
+/* Response header for partition information request */
+struct fw_version_resp {
+ struct mkhi_hdr hdr;
+ uint32_t module_count;
+ struct flash_partition_data manifest_data;
+};
+
/* CSE RX and TX error status */
enum cse_tx_rx_status {
/*
@@ -502,4 +528,10 @@
*/
enum cb_err cse_get_fw_feature_state(uint32_t *feature_state);
+/*
+ * The function sends a HECI command to get the partition information of the shared ID.
+ * The retrieved partition is stored in the memory pointed to by the resp pointer.
+ * The function returns 0 on success and < 0 on failure.
+ */
+enum cb_err cse_get_fpt_partition_info(enum fpt_partition_id id, struct fw_version_resp *resp);
#endif // SOC_INTEL_COMMON_CSE_H