diff options
author | Felix Held <felix-coreboot@felixheld.de> | 2024-08-05 23:15:55 +0200 |
---|---|---|
committer | Felix Held <felix-coreboot@felixheld.de> | 2024-08-07 16:32:57 +0000 |
commit | febf3e26dff56d0475451f9565fa5a2e64d47f5c (patch) | |
tree | cd1a63efc402ddf3d1d12d861aaeafe4a393dc2c | |
parent | c12392b316cfc3213a61b900bc7d4064e5ee09d7 (diff) |
soc/amd/common/psp_smi_flash: add find_psp_spi_flash_device_region
Add 'find_psp_spi_flash_device_region' to get a pointer to the spi_flash
struct of the SPI flash used in the system and the region_device struct
for the target FMAP region specified by the target NV ID from the PSP
to x86 mailbox command. In order to have small patches, the newly added
static 'find_psp_spi_flash_device_region' function is marked as inline;
that inline will be removed in a following patch that calls this new
function.
This patch is a slightly reworked version of parts of CB:65523.
Document #55758 Rev. 2.04 was used as a reference.
Test=When selecting SOC_AMD_COMMON_BLOCK_PSP_SMI, Mandolin still builds
Signed-off-by: Felix Held <felix-coreboot@felixheld.de>
Signed-off-by: Ritul Guru <ritul.bits@gmail.com>
Change-Id: I64b8fba2392de46ecd4c786cef0d5b6acdbd865a
Reviewed-on: https://review.coreboot.org/c/coreboot/+/83774
Reviewed-by: Martin Roth <martin.roth@amd.corp-partner.google.com>
Tested-by: build bot (Jenkins) <no-reply@coreboot.org>
-rw-r--r-- | src/soc/amd/common/block/psp/psp_smi_flash.c | 67 |
1 files changed, 67 insertions, 0 deletions
diff --git a/src/soc/amd/common/block/psp/psp_smi_flash.c b/src/soc/amd/common/block/psp/psp_smi_flash.c index f1b9d85fbb..4c83fcd358 100644 --- a/src/soc/amd/common/block/psp/psp_smi_flash.c +++ b/src/soc/amd/common/block/psp/psp_smi_flash.c @@ -1,7 +1,11 @@ /* SPDX-License-Identifier: GPL-2.0-only */ +#include <boot_device.h> +#include <commonlib/region.h> #include <console/console.h> #include <device/mmio.h> +#include <fmap.h> +#include <spi_flash.h> #include <types.h> #include "psp_def.h" @@ -67,6 +71,69 @@ static bool is_valid_psp_spi_erase(struct mbox_pspv2_cmd_spi_erase *cmd_buf) return is_valid_psp_spi_id(read64(&cmd_buf->req.target_nv_id)); } +static const char *id_to_region_name(u64 target_nv_id) +{ + switch (target_nv_id) { + case SMI_TARGET_NVRAM: + return "PSP_NVRAM"; + case SMI_TARGET_RPMC_NVRAM: + return "PSP_RPMC_NVRAM"; + } + return NULL; +} + +/* + * Do not cache the location to cope with flash changing underneath (e.g. due + * to an update) + */ +static int lookup_store(u64 target_nv_id, struct region_device *rstore) +{ + /* read_rdev, write_rdev and store_irdev need to be static to not go out of scope when + this function returns */ + static struct region_device read_rdev, write_rdev; + static struct incoherent_rdev store_irdev; + const char *name; + struct region region; + const struct region_device *rdev; + + name = id_to_region_name(target_nv_id); + if (!name) + return -1; + + if (fmap_locate_area(name, ®ion) < 0) + return -1; + + if (boot_device_ro_subregion(®ion, &read_rdev) < 0) + return -1; + + if (boot_device_rw_subregion(®ion, &write_rdev) < 0) + return -1; + + rdev = incoherent_rdev_init(&store_irdev, ®ion, &read_rdev, &write_rdev); + if (rdev == NULL) + return -1; + + return rdev_chain(rstore, rdev, 0, region_device_sz(rdev)); +} + +static inline enum mbox_p2c_status find_psp_spi_flash_device_region(u64 target_nv_id, + struct region_device *store, + const struct spi_flash **flash) +{ + *flash = boot_device_spi_flash(); + if (*flash == NULL) { + printk(BIOS_ERR, "PSP: Unable to find SPI device\n"); + return MBOX_PSP_COMMAND_PROCESS_ERROR; + } + + if (lookup_store(target_nv_id, store) < 0) { + printk(BIOS_ERR, "PSP: Unable to find PSP SPI region\n"); + return MBOX_PSP_COMMAND_PROCESS_ERROR; + } + + return MBOX_PSP_SUCCESS; +} + enum mbox_p2c_status psp_smi_spi_get_info(struct mbox_default_buffer *buffer) { struct mbox_pspv2_cmd_spi_info *const cmd_buf = |