aboutsummaryrefslogtreecommitdiff
path: root/src/drivers/intel/fsp2_0
diff options
context:
space:
mode:
authorJulian Schroeder <julianmarcusschroeder@gmail.com>2021-11-02 16:32:28 -0500
committerFelix Held <felix-coreboot@felixheld.de>2022-02-02 21:42:34 +0000
commit8a576f60ffa0f5d0599033304e6e7e34ea9c8ef6 (patch)
tree2699b4fcfd284cee04c02b965e4cad05af59ebe7 /src/drivers/intel/fsp2_0
parent7edf910d79cfefb45d4e8e0c770007c8663bb991 (diff)
drivers/intel/fsp2_0/include/fsp: fix fsp_header
This patch aligns fsp_header with the Intel specification 2.0 and 2.3. The main impetus for this change is to make the fsp_info_header fully accessible in soc/vendor code. Here items such as image_revision can be checked. TEST=verify image revision output in the coreboot serial log. compare to FSP version shown in serial debug output. verify Google Guybrush machine boots into OS. Signed-off-by: Julian Schroeder <julianmarcusschroeder@gmail.com> Change-Id: Ibf50f16b5e9793d946a95970fcdabc4c07289646 Reviewed-on: https://review.coreboot.org/c/coreboot/+/58869 Tested-by: build bot (Jenkins) <no-reply@coreboot.org> Reviewed-by: Felix Held <felix-coreboot@felixheld.de> Reviewed-by: Tim Wawrzynczak <twawrzynczak@chromium.org>
Diffstat (limited to 'src/drivers/intel/fsp2_0')
-rw-r--r--src/drivers/intel/fsp2_0/header_display.c21
-rw-r--r--src/drivers/intel/fsp2_0/include/fsp/info_header.h43
-rw-r--r--src/drivers/intel/fsp2_0/memory_init.c4
-rw-r--r--src/drivers/intel/fsp2_0/silicon_init.c6
-rw-r--r--src/drivers/intel/fsp2_0/temp_ram_exit.c2
-rw-r--r--src/drivers/intel/fsp2_0/util.c38
6 files changed, 52 insertions, 62 deletions
diff --git a/src/drivers/intel/fsp2_0/header_display.c b/src/drivers/intel/fsp2_0/header_display.c
index 4c8085ed65..d209e4ce2d 100644
--- a/src/drivers/intel/fsp2_0/header_display.c
+++ b/src/drivers/intel/fsp2_0/header_display.c
@@ -8,13 +8,14 @@ void fsp_print_header_info(const struct fsp_header *hdr)
union fsp_revision revision;
union extended_fsp_revision ext_revision;
ext_revision.val = 0;
+ int i;
/* For FSP 2.3 and later use extended image revision field present in header
* for build number and revision calculation */
if (CONFIG(PLATFORM_USES_FSP2_3))
- ext_revision.val = hdr->extended_fsp_revision;
+ ext_revision.val = hdr->extended_image_revision;
- revision.val = hdr->fsp_revision;
+ revision.val = hdr->image_revision;
printk(BIOS_SPEW, "Spec version: v%u.%u\n", (hdr->spec_version >> 4),
hdr->spec_version & 0xf);
printk(BIOS_SPEW, "Revision: %u.%u.%u, Build Number %u\n",
@@ -25,22 +26,28 @@ void fsp_print_header_info(const struct fsp_header *hdr)
printk(BIOS_SPEW, "Type: %s/%s\n",
(hdr->component_attribute & 1) ? "release" : "debug",
(hdr->component_attribute & 2) ? "official" : "test");
- printk(BIOS_SPEW, "image ID: %s, base 0x%zx + 0x%zx\n",
- hdr->image_id, (size_t)hdr->image_base, (size_t)hdr->image_size);
+
+ printk(BIOS_SPEW, "image ID: ");
+ for (i = 0; i < FSP_IMAGE_ID_LENGTH; i++)
+ printk(BIOS_SPEW, "%c", hdr->image_id[i]);
+ printk(BIOS_SPEW, "\n");
+
+ printk(BIOS_SPEW, " base 0x%zx + 0x%zx\n",
+ (size_t)hdr->image_base, (size_t)hdr->image_size);
printk(BIOS_SPEW, "\tConfig region 0x%zx + 0x%zx\n",
(size_t)hdr->cfg_region_offset, (size_t)hdr->cfg_region_size);
if ((hdr->component_attribute >> 12) == FSP_HDR_ATTRIB_FSPM) {
printk(BIOS_SPEW, "\tMemory init offset 0x%zx\n",
- (size_t)hdr->memory_init_entry_offset);
+ (size_t)hdr->fsp_memory_init_entry_offset);
}
if ((hdr->component_attribute >> 12) == FSP_HDR_ATTRIB_FSPS) {
printk(BIOS_SPEW, "\tSilicon init offset 0x%zx\n",
- (size_t)hdr->silicon_init_entry_offset);
+ (size_t)hdr->fsp_silicon_init_entry_offset);
if (CONFIG(PLATFORM_USES_FSP2_2))
printk(BIOS_SPEW, "\tMultiPhaseSiInit offset 0x%zx\n",
- (size_t)hdr->multi_phase_si_init_entry_offset);
+ (size_t)hdr->fsp_multi_phase_si_init_entry_offset);
printk(BIOS_SPEW, "\tNotify phase offset 0x%zx\n",
(size_t)hdr->notify_phase_entry_offset);
}
diff --git a/src/drivers/intel/fsp2_0/include/fsp/info_header.h b/src/drivers/intel/fsp2_0/include/fsp/info_header.h
index 136fc2b7a3..fceebec7ed 100644
--- a/src/drivers/intel/fsp2_0/include/fsp/info_header.h
+++ b/src/drivers/intel/fsp2_0/include/fsp/info_header.h
@@ -10,27 +10,34 @@
#define FSP_HDR_ATTRIB_FSPT 1
#define FSP_HDR_ATTRIB_FSPM 2
#define FSP_HDR_ATTRIB_FSPS 3
+#define FSP_IMAGE_ID_LENGTH 8
#if CONFIG(PLATFORM_USES_FSP2_X86_32)
struct fsp_header {
- uint32_t fsp_revision;
- uint16_t extended_fsp_revision;
- uint32_t image_size;
- uint32_t image_base;
- uint16_t image_attribute;
- uint8_t spec_version;
- uint16_t component_attribute;
- uint32_t cfg_region_offset;
- uint32_t cfg_region_size;
- uint32_t temp_ram_init_entry;
- uint32_t temp_ram_exit_entry;
- uint32_t notify_phase_entry_offset;
- uint32_t memory_init_entry_offset;
- uint32_t silicon_init_entry_offset;
- uint32_t multi_phase_si_init_entry_offset;
- char image_id[sizeof(uint64_t) + 1];
- uint8_t revision;
-} __packed;
+ uint32_t signature; //FSPH
+ uint32_t header_length;
+ uint8_t res1[2];
+ uint8_t spec_version;
+ uint8_t header_revision;
+ uint32_t image_revision;
+ char image_id[FSP_IMAGE_ID_LENGTH]; // not zero terminated
+ uint32_t image_size;
+ uint32_t image_base;
+ uint16_t image_attribute;
+ uint16_t component_attribute;
+ uint32_t cfg_region_offset;
+ uint32_t cfg_region_size;
+ uint32_t res2;
+ uint32_t temp_ram_init_entry_offset; //initial stack
+ uint32_t res3;
+ uint32_t notify_phase_entry_offset;
+ uint32_t fsp_memory_init_entry_offset;
+ uint32_t temp_ram_exit_entry_offset;
+ uint32_t fsp_silicon_init_entry_offset;
+ uint32_t fsp_multi_phase_si_init_entry_offset;
+ uint16_t extended_image_revision;
+ uint16_t res4;
+} __packed;
#else
#error You need to implement this struct for x86_64 FSP
#endif
diff --git a/src/drivers/intel/fsp2_0/memory_init.c b/src/drivers/intel/fsp2_0/memory_init.c
index 3c1a088bf0..3643866c43 100644
--- a/src/drivers/intel/fsp2_0/memory_init.c
+++ b/src/drivers/intel/fsp2_0/memory_init.c
@@ -206,7 +206,7 @@ uint8_t fsp_memory_soc_version(void)
static uint32_t fsp_memory_settings_version(const struct fsp_header *hdr)
{
/* Use the full FSP version by default. */
- uint32_t ver = hdr->fsp_revision;
+ uint32_t ver = hdr->image_revision;
if (!CONFIG(FSP_PLATFORM_MEMORY_SETTINGS_VERSIONS))
return ver;
@@ -291,7 +291,7 @@ static void do_fsp_memory_init(const struct fspm_context *context, bool s3wake)
post_code(POST_MEM_PREINIT_PREP_END);
/* Call FspMemoryInit */
- fsp_raminit = (void *)(uintptr_t)(hdr->image_base + hdr->memory_init_entry_offset);
+ fsp_raminit = (void *)(uintptr_t)(hdr->image_base + hdr->fsp_memory_init_entry_offset);
fsp_debug_before_memory_init(fsp_raminit, upd, &fspm_upd);
post_code(POST_FSP_MEMORY_INIT);
diff --git a/src/drivers/intel/fsp2_0/silicon_init.c b/src/drivers/intel/fsp2_0/silicon_init.c
index 83d44b140f..05cea11d55 100644
--- a/src/drivers/intel/fsp2_0/silicon_init.c
+++ b/src/drivers/intel/fsp2_0/silicon_init.c
@@ -75,7 +75,7 @@ static void fsps_return_value_handler(enum fsp_silicon_init_phases phases, uint3
bool fsp_is_multi_phase_init_enabled(void)
{
return CONFIG(FSPS_USE_MULTI_PHASE_INIT) &&
- (fsps_hdr.multi_phase_si_init_entry_offset != 0);
+ (fsps_hdr.fsp_multi_phase_si_init_entry_offset != 0);
}
static void fsp_fill_common_arch_params(FSPS_UPD *supd)
@@ -127,7 +127,7 @@ static void do_silicon_init(struct fsp_header *hdr)
/* Call SiliconInit */
silicon_init = (void *) (uintptr_t)(hdr->image_base +
- hdr->silicon_init_entry_offset);
+ hdr->fsp_silicon_init_entry_offset);
fsp_debug_before_silicon_init(silicon_init, supd, upd);
timestamp_add_now(TS_FSP_SILICON_INIT_START);
@@ -162,7 +162,7 @@ static void do_silicon_init(struct fsp_header *hdr)
/* Call MultiPhaseSiInit */
multi_phase_si_init = (void *) (uintptr_t)(hdr->image_base +
- hdr->multi_phase_si_init_entry_offset);
+ hdr->fsp_multi_phase_si_init_entry_offset);
/* Implementing multi_phase_si_init() is optional as per FSP 2.2 spec */
if (multi_phase_si_init == NULL)
diff --git a/src/drivers/intel/fsp2_0/temp_ram_exit.c b/src/drivers/intel/fsp2_0/temp_ram_exit.c
index 2192543575..87b77bcefa 100644
--- a/src/drivers/intel/fsp2_0/temp_ram_exit.c
+++ b/src/drivers/intel/fsp2_0/temp_ram_exit.c
@@ -25,7 +25,7 @@ static void fsp_temp_ram_exit(void)
if (fsp_validate_component(&hdr, mapping, size) != CB_SUCCESS)
die("Invalid FSPM header!\n");
- temp_ram_exit = (void *)(hdr.image_base + hdr.temp_ram_exit_entry);
+ temp_ram_exit = (void *)(hdr.image_base + hdr.temp_ram_exit_entry_offset);
printk(BIOS_DEBUG, "Calling TempRamExit: %p\n", temp_ram_exit);
status = temp_ram_exit(NULL);
diff --git a/src/drivers/intel/fsp2_0/util.c b/src/drivers/intel/fsp2_0/util.c
index ff79fc7715..2537b383ab 100644
--- a/src/drivers/intel/fsp2_0/util.c
+++ b/src/drivers/intel/fsp2_0/util.c
@@ -26,11 +26,9 @@ static uint32_t fsp_hdr_get_expected_min_length(void)
return dead_code_t(uint32_t);
}
-static bool looks_like_fsp_header(const uint8_t *raw_hdr)
+static bool looks_like_fsp_header(struct fsp_header *hdr)
{
- uint32_t fsp_header_length = read32(raw_hdr + 4);
-
- if (memcmp(raw_hdr, FSP_HDR_SIGNATURE, 4)) {
+ if (memcmp(&hdr->signature, FSP_HDR_SIGNATURE, 4)) {
printk(BIOS_ALERT, "Did not find a valid FSP signature\n");
return false;
}
@@ -39,8 +37,8 @@ static bool looks_like_fsp_header(const uint8_t *raw_hdr)
fields in FSP_INFO_HEADER. The new fields will be ignored based on the reported FSP
version. This check ensures that the reported header length is at least what the
reported FSP version requires so that we do not access any out-of-bound bytes. */
- if (fsp_header_length < fsp_hdr_get_expected_min_length()) {
- printk(BIOS_ALERT, "FSP header has invalid length: %d\n", fsp_header_length);
+ if (hdr->header_length < fsp_hdr_get_expected_min_length()) {
+ printk(BIOS_ALERT, "FSP header has invalid length: %d\n", hdr->header_length);
return false;
}
@@ -49,32 +47,10 @@ static bool looks_like_fsp_header(const uint8_t *raw_hdr)
enum cb_err fsp_identify(struct fsp_header *hdr, const void *fsp_blob)
{
- const uint8_t *raw_hdr = fsp_blob;
-
- if (!looks_like_fsp_header(raw_hdr))
+ memcpy(hdr, fsp_blob, sizeof(struct fsp_header));
+ if (!looks_like_fsp_header(hdr))
return CB_ERR;
- hdr->spec_version = read8(raw_hdr + 10);
- hdr->revision = read8(raw_hdr + 11);
- hdr->fsp_revision = read32(raw_hdr + 12);
- memcpy(hdr->image_id, raw_hdr + 16, ARRAY_SIZE(hdr->image_id));
- hdr->image_id[ARRAY_SIZE(hdr->image_id) - 1] = '\0';
- hdr->image_size = read32(raw_hdr + 24);
- hdr->image_base = read32(raw_hdr + 28);
- hdr->image_attribute = read16(raw_hdr + 32);
- hdr->component_attribute = read16(raw_hdr + 34);
- hdr->cfg_region_offset = read32(raw_hdr + 36);
- hdr->cfg_region_size = read32(raw_hdr + 40);
- hdr->temp_ram_init_entry = read32(raw_hdr + 48);
- hdr->temp_ram_exit_entry = read32(raw_hdr + 64);
- hdr->notify_phase_entry_offset = read32(raw_hdr + 56);
- hdr->memory_init_entry_offset = read32(raw_hdr + 60);
- hdr->silicon_init_entry_offset = read32(raw_hdr + 68);
- if (CONFIG(PLATFORM_USES_FSP2_2))
- hdr->multi_phase_si_init_entry_offset = read32(raw_hdr + 72);
- if (CONFIG(PLATFORM_USES_FSP2_3))
- hdr->extended_fsp_revision = read16(raw_hdr + 76);
-
return CB_SUCCESS;
}
@@ -192,7 +168,7 @@ void fsp_get_version(char *buf)
struct fsp_header *hdr = &fsps_hdr;
union fsp_revision revision;
- revision.val = hdr->fsp_revision;
+ revision.val = hdr->image_revision;
snprintf(buf, FSP_VER_LEN, "%u.%u-%u.%u.%u.%u", (hdr->spec_version >> 4),
hdr->spec_version & 0xf, revision.rev.major,
revision.rev.minor, revision.rev.revision, revision.rev.bld_num);