[PATCH 00/18] FWU: Migrate FWU metadata to version 2

The following patches migrate the FWU metadata access code to version 2 of the structure. This is based on the structure definition as defined in the latest rev of the FWU Multi Bank Update specification [1].
Since the version 1 of the structure has currently been adopted on a couple of platforms, it was decided to have a clean migration of the metadata to version 2 only, instead of supporting both the versions of the structure. Also, based on consultations with the main author of the specification, it is expected that any further changes in the structure would be minor tweaks, and not be significant. Hence a migration to version 2.
Similar migration is also being done in TF-A, including migrating the ST platform port to support version 2 of the metadata structure [2].
The patches have been tested on STM32MP1 DK2 board and the Synquacer board from Socionext. This covers testing both the GPT and the MTD partitioned storage devices for the metadata access.
[1] - https://developer.arm.com/documentation/den0118/latest/ [2] - https://review.trustedfirmware.org/q/topic:%22topics/fwu_metadata_v2_migrati...
Sughosh Ganu (18): configs: fwu: Remove FWU configs for metadata V2 migration fwu: metadata: Migrate to version 2 of the structure drivers: fwu: Add the size parameter to the metadata access API's fwu: Add some API's for metadata version 2 access lib: fwu: Make changes to support version 2 of FWU metadata drivers: fwu: mtd: Allocate buffer for image info dynamically drivers: fwu: Allocate memory for metadata copies fwu: Add a function to put a bank in Trial State capsule: Accept a bank on a successful update fwu: mtd: Modify the DFU API's to align with metadata version 2 efi_firmware: fwu: Do not read FWU metadata on sandbox efi_firmware: fwu: Get the number of FWU banks at runtime cmd: fwu: Align the command with metadata version 2 test: fwu: Align the FWU metadata access test with version 2 fwu: Remove the config symbols for number of banks and images tools: mkfwumdata: Migrate to metadata version 2 configs: fwu: Re-enable FWU configs doc: fwu: Make changes for supporting FWU Metadata version 2
arch/sandbox/Kconfig | 6 - board/armltd/corstone1000/corstone1000.c | 2 +- cmd/fwu_mdata.c | 43 +++- configs/synquacer_developerbox_defconfig | 1 - doc/board/socionext/developerbox.rst | 9 +- doc/develop/uefi/fwu_updates.rst | 12 +- doc/usage/cmd/fwu_mdata.rst | 12 +- drivers/fwu-mdata/fwu-mdata-uclass.c | 10 +- drivers/fwu-mdata/gpt_blk.c | 27 +- drivers/fwu-mdata/raw_mtd.c | 85 ++++--- include/fwu.h | 94 ++++++- include/fwu_mdata.h | 56 +++-- lib/efi_loader/efi_capsule.c | 12 +- lib/efi_loader/efi_firmware.c | 20 +- lib/fwu_updates/Kconfig | 11 - lib/fwu_updates/fwu.c | 308 ++++++++++++++++++----- lib/fwu_updates/fwu_mtd.c | 76 ++++-- test/dm/fwu_mdata.c | 56 +++-- test/dm/fwu_mdata_disk_image.h | 124 ++++----- tools/mkfwumdata.c | 43 +++- 20 files changed, 705 insertions(+), 302 deletions(-)

The FWU metadata is to be migrated to version 2. Disable the FWU feature on platforms that enable it for the migration.
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org --- configs/corstone1000_defconfig | 2 -- configs/sandbox64_defconfig | 1 - configs/synquacer_developerbox_defconfig | 4 ---- 3 files changed, 7 deletions(-)
diff --git a/configs/corstone1000_defconfig b/configs/corstone1000_defconfig index e45415b90c..24b7984959 100644 --- a/configs/corstone1000_defconfig +++ b/configs/corstone1000_defconfig @@ -25,7 +25,6 @@ CONFIG_BOARD_LATE_INIT=y CONFIG_SYS_PROMPT="corstone1000# " CONFIG_SYS_MAXARGS=64 # CONFIG_CMD_CONSOLE is not set -CONFIG_CMD_FWU_METADATA=y CONFIG_CMD_BOOTZ=y # CONFIG_CMD_XIMG is not set CONFIG_CMD_GPT=y @@ -67,4 +66,3 @@ CONFIG_FFA_SHARED_MM_BUF_OFFSET=0 CONFIG_FFA_SHARED_MM_BUF_ADDR=0x02000000 CONFIG_EFI_CAPSULE_ON_DISK=y CONFIG_EFI_IGNORE_OSINDICATIONS=y -CONFIG_FWU_MULTI_BANK_UPDATE=y diff --git a/configs/sandbox64_defconfig b/configs/sandbox64_defconfig index 996bb7aa4f..7b5888af38 100644 --- a/configs/sandbox64_defconfig +++ b/configs/sandbox64_defconfig @@ -274,7 +274,6 @@ CONFIG_EFI_CAPSULE_ON_DISK=y CONFIG_EFI_CAPSULE_FIRMWARE_RAW=y CONFIG_EFI_SECURE_BOOT=y CONFIG_TEST_FDTDEC=y -CONFIG_FWU_MULTI_BANK_UPDATE=y CONFIG_UNIT_TEST=y CONFIG_UT_TIME=y CONFIG_UT_DM=y diff --git a/configs/synquacer_developerbox_defconfig b/configs/synquacer_developerbox_defconfig index 2a0407de40..616d410074 100644 --- a/configs/synquacer_developerbox_defconfig +++ b/configs/synquacer_developerbox_defconfig @@ -11,14 +11,12 @@ CONFIG_DM_GPIO=y CONFIG_DEFAULT_DEVICE_TREE="synquacer-sc2a11-developerbox" CONFIG_SYS_LOAD_ADDR=0x80000000 CONFIG_TARGET_DEVELOPERBOX=y -CONFIG_FWU_NUM_IMAGES_PER_BANK=1 CONFIG_AHCI=y CONFIG_FIT=y CONFIG_SYS_BOOTM_LEN=0x800000 CONFIG_BOOTSTAGE_STASH_SIZE=4096 CONFIG_HUSH_PARSER=y CONFIG_SYS_MAXARGS=128 -CONFIG_CMD_FWU_METADATA=y CONFIG_CMD_IMLS=y CONFIG_CMD_ERASEENV=y CONFIG_CMD_NVEDIT_EFI=y @@ -53,7 +51,6 @@ CONFIG_DFU_TFTP=y CONFIG_DFU_MTD=y CONFIG_DFU_RAM=y CONFIG_DFU_SF=y -CONFIG_FWU_MDATA_MTD=y CONFIG_DM_I2C=y CONFIG_SYS_I2C_SYNQUACER=y CONFIG_MMC_SDHCI=y @@ -96,4 +93,3 @@ CONFIG_EFI_RUNTIME_UPDATE_CAPSULE=y CONFIG_EFI_CAPSULE_ON_DISK=y CONFIG_EFI_IGNORE_OSINDICATIONS=y CONFIG_EFI_CAPSULE_FIRMWARE_RAW=y -CONFIG_FWU_MULTI_BANK_UPDATE=y

On Mon, Jan 22, 2024 at 05:24:22PM +0530, Sughosh Ganu wrote:
The FWU metadata is to be migrated to version 2. Disable the FWU feature on platforms that enable it for the migration.
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org
configs/corstone1000_defconfig | 2 -- configs/sandbox64_defconfig | 1 - configs/synquacer_developerbox_defconfig | 4 ---- 3 files changed, 7 deletions(-)
diff --git a/configs/corstone1000_defconfig b/configs/corstone1000_defconfig index e45415b90c..24b7984959 100644 --- a/configs/corstone1000_defconfig +++ b/configs/corstone1000_defconfig @@ -25,7 +25,6 @@ CONFIG_BOARD_LATE_INIT=y CONFIG_SYS_PROMPT="corstone1000# " CONFIG_SYS_MAXARGS=64 # CONFIG_CMD_CONSOLE is not set -CONFIG_CMD_FWU_METADATA=y CONFIG_CMD_BOOTZ=y # CONFIG_CMD_XIMG is not set CONFIG_CMD_GPT=y @@ -67,4 +66,3 @@ CONFIG_FFA_SHARED_MM_BUF_OFFSET=0 CONFIG_FFA_SHARED_MM_BUF_ADDR=0x02000000 CONFIG_EFI_CAPSULE_ON_DISK=y CONFIG_EFI_IGNORE_OSINDICATIONS=y -CONFIG_FWU_MULTI_BANK_UPDATE=y diff --git a/configs/sandbox64_defconfig b/configs/sandbox64_defconfig index 996bb7aa4f..7b5888af38 100644 --- a/configs/sandbox64_defconfig +++ b/configs/sandbox64_defconfig @@ -274,7 +274,6 @@ CONFIG_EFI_CAPSULE_ON_DISK=y CONFIG_EFI_CAPSULE_FIRMWARE_RAW=y CONFIG_EFI_SECURE_BOOT=y CONFIG_TEST_FDTDEC=y -CONFIG_FWU_MULTI_BANK_UPDATE=y CONFIG_UNIT_TEST=y CONFIG_UT_TIME=y CONFIG_UT_DM=y diff --git a/configs/synquacer_developerbox_defconfig b/configs/synquacer_developerbox_defconfig index 2a0407de40..616d410074 100644 --- a/configs/synquacer_developerbox_defconfig +++ b/configs/synquacer_developerbox_defconfig @@ -11,14 +11,12 @@ CONFIG_DM_GPIO=y CONFIG_DEFAULT_DEVICE_TREE="synquacer-sc2a11-developerbox" CONFIG_SYS_LOAD_ADDR=0x80000000 CONFIG_TARGET_DEVELOPERBOX=y -CONFIG_FWU_NUM_IMAGES_PER_BANK=1 CONFIG_AHCI=y CONFIG_FIT=y CONFIG_SYS_BOOTM_LEN=0x800000 CONFIG_BOOTSTAGE_STASH_SIZE=4096 CONFIG_HUSH_PARSER=y CONFIG_SYS_MAXARGS=128 -CONFIG_CMD_FWU_METADATA=y CONFIG_CMD_IMLS=y CONFIG_CMD_ERASEENV=y CONFIG_CMD_NVEDIT_EFI=y @@ -53,7 +51,6 @@ CONFIG_DFU_TFTP=y CONFIG_DFU_MTD=y CONFIG_DFU_RAM=y CONFIG_DFU_SF=y -CONFIG_FWU_MDATA_MTD=y CONFIG_DM_I2C=y CONFIG_SYS_I2C_SYNQUACER=y CONFIG_MMC_SDHCI=y @@ -96,4 +93,3 @@ CONFIG_EFI_RUNTIME_UPDATE_CAPSULE=y CONFIG_EFI_CAPSULE_ON_DISK=y CONFIG_EFI_IGNORE_OSINDICATIONS=y CONFIG_EFI_CAPSULE_FIRMWARE_RAW=y
-CONFIG_FWU_MULTI_BANK_UPDATE=y
2.34.1
Reviewed-by: Ilias Apalodimas ilias.apalodimas@linaro.org

The latest version of the FWU specification [1] has changes to the metadata structure. This is version 2 of the structure.
Primary changes include - bank_state field in the top level structure - Total metadata size in the top level structure - Image description structures now optional - Number of banks and images per bank values part of the structure
Migrate to the version 2 of the metadata structure.
[1] - https://developer.arm.com/documentation/den0118/latest/
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org --- include/fwu_mdata.h | 56 +++++++++++++++++++++++++++++++++------------ 1 file changed, 42 insertions(+), 14 deletions(-)
diff --git a/include/fwu_mdata.h b/include/fwu_mdata.h index 56189e2f40..050ee969e3 100644 --- a/include/fwu_mdata.h +++ b/include/fwu_mdata.h @@ -11,7 +11,7 @@
/** * struct fwu_image_bank_info - firmware image information - * @image_uuid: Guid value of the image in this bank + * @image_guid: Guid value of the image in this bank * @accepted: Acceptance status of the image * @reserved: Reserved * @@ -20,15 +20,15 @@ * acceptance status */ struct fwu_image_bank_info { - efi_guid_t image_uuid; + efi_guid_t image_guid; uint32_t accepted; uint32_t reserved; } __packed;
/** * struct fwu_image_entry - information for a particular type of image - * @image_type_uuid: Guid value for identifying the image type - * @location_uuid: Guid of the storage volume where the image is located + * @image_type_guid: Guid value for identifying the image type + * @location_guid: Guid of the storage volume where the image is located * @img_bank_info: Array containing properties of images * * This structure contains information on various types of updatable @@ -36,9 +36,30 @@ struct fwu_image_bank_info { * information per bank. */ struct fwu_image_entry { - efi_guid_t image_type_uuid; - efi_guid_t location_uuid; - struct fwu_image_bank_info img_bank_info[CONFIG_FWU_NUM_BANKS]; + efi_guid_t image_type_guid; + efi_guid_t location_guid; + struct fwu_image_bank_info img_bank_info[]; +} __packed; + +/** + * struct fwu_fw_desc_store - FWU updatable image information + * @num_banks: Number of firmware banks + * num_images: Number of images per bank + * @img_entry_size: The size of the img_entry array + * @bank_info_entry_size: The size of the img_bank_info array + * @img_entry: Array of image entries each giving information on a image + * + * This image descriptor structure contains information on the number of + * updatable banks and images per bank. It also gives the total sizes of + * the fwu_image_entry and fwu_image_bank_info arrays. + */ +struct fwu_fw_store_desc { + uint8_t num_banks; + uint8_t reserved; + uint16_t num_images; + uint16_t img_entry_size; + uint16_t bank_info_entry_size; + struct fwu_image_entry img_entry[]; } __packed;
/** @@ -48,21 +69,28 @@ struct fwu_image_entry { * @active_index: Index of the bank currently used for booting images * @previous_active_inde: Index of the bank used before the current bank * being used for booting - * @img_entry: Array of information on various firmware images that can - * be updated + * @metadata_size: Size of the entire metadata structure, including the + * image descriptors + * @desc_offset: The offset from the start of this structure where the + * image descriptor structure starts. 0 if absent + * @bank_state: State of each bank, valid, invalid or accepted + * @fw_desc: The structure describing the FWU updatable images * - * This structure is used to store all the needed information for performing + * This is the top level structure used to store all information for performing * multi bank updates on the platform. This contains info on the bank being - * used to boot along with the information needed for identification of - * individual images + * used to boot along with the information on state of individual banks. */ struct fwu_mdata { uint32_t crc32; uint32_t version; uint32_t active_index; uint32_t previous_active_index; - - struct fwu_image_entry img_entry[CONFIG_FWU_NUM_IMAGES_PER_BANK]; + uint32_t metadata_size; + uint16_t desc_offset; + uint16_t reserved1; + uint8_t bank_state[4]; + uint32_t reserved2; + struct fwu_fw_store_desc fw_desc[]; } __packed;
#endif /* _FWU_MDATA_H_ */

Hi Sughosh,
On Mon, Jan 22, 2024 at 05:24:23PM +0530, Sughosh Ganu wrote:
The latest version of the FWU specification [1] has changes to the metadata structure. This is version 2 of the structure.
Primary changes include
- bank_state field in the top level structure
- Total metadata size in the top level structure
- Image description structures now optional
- Number of banks and images per bank values part of the structure
Migrate to the version 2 of the metadata structure.
[1] - https://developer.arm.com/documentation/den0118/latest/
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org
include/fwu_mdata.h | 56 +++++++++++++++++++++++++++++++++------------ 1 file changed, 42 insertions(+), 14 deletions(-)
diff --git a/include/fwu_mdata.h b/include/fwu_mdata.h index 56189e2f40..050ee969e3 100644 --- a/include/fwu_mdata.h +++ b/include/fwu_mdata.h @@ -11,7 +11,7 @@
/**
- struct fwu_image_bank_info - firmware image information
- @image_uuid: Guid value of the image in this bank
- @image_guid: Guid value of the image in this bank
- @accepted: Acceptance status of the image
- @reserved: Reserved
@@ -20,15 +20,15 @@
- acceptance status
*/ struct fwu_image_bank_info {
- efi_guid_t image_uuid;
- efi_guid_t image_guid; uint32_t accepted; uint32_t reserved;
} __packed;
/**
- struct fwu_image_entry - information for a particular type of image
- @image_type_uuid: Guid value for identifying the image type
- @location_uuid: Guid of the storage volume where the image is located
- @image_type_guid: Guid value for identifying the image type
- @location_guid: Guid of the storage volume where the image is located
- @img_bank_info: Array containing properties of images
- This structure contains information on various types of updatable
@@ -36,9 +36,30 @@ struct fwu_image_bank_info {
- information per bank.
*/ struct fwu_image_entry {
- efi_guid_t image_type_uuid;
- efi_guid_t location_uuid;
- struct fwu_image_bank_info img_bank_info[CONFIG_FWU_NUM_BANKS];
- efi_guid_t image_type_guid;
- efi_guid_t location_guid;
- struct fwu_image_bank_info img_bank_info[];
+} __packed;
+/**
- struct fwu_fw_desc_store - FWU updatable image information
- @num_banks: Number of firmware banks
- num_images: Number of images per bank
- @img_entry_size: The size of the img_entry array
- @bank_info_entry_size: The size of the img_bank_info array
- @img_entry: Array of image entries each giving information on a image
- This image descriptor structure contains information on the number of
- updatable banks and images per bank. It also gives the total sizes of
- the fwu_image_entry and fwu_image_bank_info arrays.
- */
+struct fwu_fw_store_desc {
- uint8_t num_banks;
- uint8_t reserved;
- uint16_t num_images;
- uint16_t img_entry_size;
- uint16_t bank_info_entry_size;
- struct fwu_image_entry img_entry[];
This is a bit problematic. When a struct is defined using flexible array members, you are not supposed to include it on other structs or arrays [0]. We need a way of working around this
} __packed;
/** @@ -48,21 +69,28 @@ struct fwu_image_entry {
- @active_index: Index of the bank currently used for booting images
- @previous_active_inde: Index of the bank used before the current bank
being used for booting
- @img_entry: Array of information on various firmware images that can
be updated
- @metadata_size: Size of the entire metadata structure, including the
image descriptors
- @desc_offset: The offset from the start of this structure where the
image descriptor structure starts. 0 if absent
- @bank_state: State of each bank, valid, invalid or accepted
- @fw_desc: The structure describing the FWU updatable images
- This structure is used to store all the needed information for performing
- This is the top level structure used to store all information for performing
- multi bank updates on the platform. This contains info on the bank being
- used to boot along with the information needed for identification of
- individual images
*/
- used to boot along with the information on state of individual banks.
struct fwu_mdata { uint32_t crc32; uint32_t version; uint32_t active_index; uint32_t previous_active_index;
- struct fwu_image_entry img_entry[CONFIG_FWU_NUM_IMAGES_PER_BANK];
- uint32_t metadata_size;
- uint16_t desc_offset;
- uint16_t reserved1;
- uint8_t bank_state[4];
- uint32_t reserved2;
- struct fwu_fw_store_desc fw_desc[];
ditto
} __packed;
#endif /* _FWU_MDATA_H_ */
2.34.1
[0] git show b10bfd0019f601

In version 2 of the metadata structure, the size of the structure cannot be determined statically at build time. The structure is now broken into the top level structure which contains a field indicating the total size of the structure.
Add a size parameter to the metadata access API functions to indicate the number of bytes to be accessed. This is then used to either read the entire structure, or only the top level structure.
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org --- drivers/fwu-mdata/fwu-mdata-uclass.c | 10 ++++++---- drivers/fwu-mdata/gpt_blk.c | 23 +++++++++++++---------- drivers/fwu-mdata/raw_mtd.c | 10 ++++++---- include/fwu.h | 14 ++++++++++---- 4 files changed, 35 insertions(+), 22 deletions(-)
diff --git a/drivers/fwu-mdata/fwu-mdata-uclass.c b/drivers/fwu-mdata/fwu-mdata-uclass.c index 0a8edaaa41..145479bab0 100644 --- a/drivers/fwu-mdata/fwu-mdata-uclass.c +++ b/drivers/fwu-mdata/fwu-mdata-uclass.c @@ -20,7 +20,8 @@ * * Return: 0 if OK, -ve on error */ -int fwu_read_mdata(struct udevice *dev, struct fwu_mdata *mdata, bool primary) +int fwu_read_mdata(struct udevice *dev, struct fwu_mdata *mdata, bool primary, + uint32_t size) { const struct fwu_mdata_ops *ops = device_get_ops(dev);
@@ -29,7 +30,7 @@ int fwu_read_mdata(struct udevice *dev, struct fwu_mdata *mdata, bool primary) return -ENOSYS; }
- return ops->read_mdata(dev, mdata, primary); + return ops->read_mdata(dev, mdata, primary, size); }
/** @@ -37,7 +38,8 @@ int fwu_read_mdata(struct udevice *dev, struct fwu_mdata *mdata, bool primary) * * Return: 0 if OK, -ve on error */ -int fwu_write_mdata(struct udevice *dev, struct fwu_mdata *mdata, bool primary) +int fwu_write_mdata(struct udevice *dev, struct fwu_mdata *mdata, bool primary, + uint32_t size) { const struct fwu_mdata_ops *ops = device_get_ops(dev);
@@ -46,7 +48,7 @@ int fwu_write_mdata(struct udevice *dev, struct fwu_mdata *mdata, bool primary) return -ENOSYS; }
- return ops->write_mdata(dev, mdata, primary); + return ops->write_mdata(dev, mdata, primary, size); }
UCLASS_DRIVER(fwu_mdata) = { diff --git a/drivers/fwu-mdata/gpt_blk.c b/drivers/fwu-mdata/gpt_blk.c index c7284916c4..97eac3611f 100644 --- a/drivers/fwu-mdata/gpt_blk.c +++ b/drivers/fwu-mdata/gpt_blk.c @@ -81,15 +81,14 @@ static int gpt_get_mdata_disk_part(struct blk_desc *desc, return -ENOENT; }
-static int gpt_read_write_mdata(struct blk_desc *desc, - struct fwu_mdata *mdata, - u8 access, u32 part_num) +static int gpt_read_write_mdata(struct blk_desc *desc, struct fwu_mdata *mdata, + u8 access, u32 part_num, u32 size) { int ret; u32 len, blk_start, blkcnt; struct disk_partition info;
- ALLOC_CACHE_ALIGN_BUFFER_PAD(struct fwu_mdata, mdata_aligned, 1, + ALLOC_CACHE_ALIGN_BUFFER_PAD(u8, mdata_aligned, size, desc->blksz);
if (!mdata) @@ -101,7 +100,7 @@ static int gpt_read_write_mdata(struct blk_desc *desc, return -ENOENT; }
- len = sizeof(*mdata); + len = size; blkcnt = BLOCK_CNT(len, desc); if (blkcnt > info.size) { log_debug("Block count exceeds FWU metadata partition size\n"); @@ -114,7 +113,7 @@ static int gpt_read_write_mdata(struct blk_desc *desc, log_debug("Error reading FWU metadata from the device\n"); return -EIO; } - memcpy(mdata, mdata_aligned, sizeof(struct fwu_mdata)); + memcpy(mdata, mdata_aligned, size); } else { if (blk_dwrite(desc, blk_start, blkcnt, mdata) != blkcnt) { log_debug("Error writing FWU metadata to the device\n"); @@ -164,7 +163,7 @@ static int fwu_mdata_gpt_blk_probe(struct udevice *dev) }
static int fwu_gpt_read_mdata(struct udevice *dev, struct fwu_mdata *mdata, - bool primary) + bool primary, u32 size) { struct fwu_mdata_gpt_blk_priv *priv = dev_get_priv(dev); struct blk_desc *desc = dev_get_uclass_plat(priv->blk_dev); @@ -177,11 +176,13 @@ static int fwu_gpt_read_mdata(struct udevice *dev, struct fwu_mdata *mdata, }
return gpt_read_write_mdata(desc, mdata, MDATA_READ, - primary ? g_mdata_part[0] : g_mdata_part[1]); + primary ? + g_mdata_part[0] : g_mdata_part[1], + size); }
static int fwu_gpt_write_mdata(struct udevice *dev, struct fwu_mdata *mdata, - bool primary) + bool primary, u32 size) { struct fwu_mdata_gpt_blk_priv *priv = dev_get_priv(dev); struct blk_desc *desc = dev_get_uclass_plat(priv->blk_dev); @@ -194,7 +195,9 @@ static int fwu_gpt_write_mdata(struct udevice *dev, struct fwu_mdata *mdata, }
return gpt_read_write_mdata(desc, mdata, MDATA_WRITE, - primary ? g_mdata_part[0] : g_mdata_part[1]); + primary ? + g_mdata_part[0] : g_mdata_part[1], + size); }
static const struct fwu_mdata_ops fwu_gpt_blk_ops = { diff --git a/drivers/fwu-mdata/raw_mtd.c b/drivers/fwu-mdata/raw_mtd.c index 17e4517973..9f3f1dc213 100644 --- a/drivers/fwu-mdata/raw_mtd.c +++ b/drivers/fwu-mdata/raw_mtd.c @@ -97,22 +97,24 @@ lock: return ret; }
-static int fwu_mtd_read_mdata(struct udevice *dev, struct fwu_mdata *mdata, bool primary) +static int fwu_mtd_read_mdata(struct udevice *dev, struct fwu_mdata *mdata, + bool primary, u32 size) { struct fwu_mdata_mtd_priv *mtd_priv = dev_get_priv(dev); struct mtd_info *mtd = mtd_priv->mtd; u32 offs = primary ? mtd_priv->pri_offset : mtd_priv->sec_offset;
- return mtd_io_data(mtd, offs, sizeof(struct fwu_mdata), mdata, FWU_MTD_READ); + return mtd_io_data(mtd, offs, size, mdata, FWU_MTD_READ); }
-static int fwu_mtd_write_mdata(struct udevice *dev, struct fwu_mdata *mdata, bool primary) +static int fwu_mtd_write_mdata(struct udevice *dev, struct fwu_mdata *mdata, + bool primary, u32 size) { struct fwu_mdata_mtd_priv *mtd_priv = dev_get_priv(dev); struct mtd_info *mtd = mtd_priv->mtd; u32 offs = primary ? mtd_priv->pri_offset : mtd_priv->sec_offset;
- return mtd_io_data(mtd, offs, sizeof(struct fwu_mdata), mdata, FWU_MTD_WRITE); + return mtd_io_data(mtd, offs, size, mdata, FWU_MTD_WRITE); }
static int flash_partition_offset(struct udevice *dev, const char *part_name, fdt_addr_t *offset) diff --git a/include/fwu.h b/include/fwu.h index eb5638f4f3..1815bd0064 100644 --- a/include/fwu.h +++ b/include/fwu.h @@ -32,20 +32,24 @@ struct fwu_mdata_ops { * @dev: FWU metadata device * @mdata: Output FWU mdata read * @primary: If primary or secondary copy of metadata is to be read + * @size: Size in bytes of the metadata to be read * * Return: 0 if OK, -ve on error */ - int (*read_mdata)(struct udevice *dev, struct fwu_mdata *mdata, bool primary); + int (*read_mdata)(struct udevice *dev, struct fwu_mdata *mdata, + bool primary, uint32_t size);
/** * write_mdata() - Write the given FWU metadata copy * @dev: FWU metadata device * @mdata: Copy of the FWU metadata to write * @primary: If primary or secondary copy of metadata is to be written + * @size: Size in bytes of the metadata to be written * * Return: 0 if OK, -ve on error */ - int (*write_mdata)(struct udevice *dev, struct fwu_mdata *mdata, bool primary); + int (*write_mdata)(struct udevice *dev, struct fwu_mdata *mdata, + bool primary, uint32_t size); };
#define FWU_MDATA_VERSION 0x1 @@ -80,12 +84,14 @@ struct fwu_mdata_ops { /** * fwu_read_mdata() - Wrapper around fwu_mdata_ops.read_mdata() */ -int fwu_read_mdata(struct udevice *dev, struct fwu_mdata *mdata, bool primary); +int fwu_read_mdata(struct udevice *dev, struct fwu_mdata *mdata, + bool primary, uint32_t size);
/** * fwu_write_mdata() - Wrapper around fwu_mdata_ops.write_mdata() */ -int fwu_write_mdata(struct udevice *dev, struct fwu_mdata *mdata, bool primary); +int fwu_write_mdata(struct udevice *dev, struct fwu_mdata *mdata, + bool primary, uint32_t size);
/** * fwu_get_mdata() - Read, verify and return the FWU metadata

There are certain fields added in version 2 of the FWU metadata structure. Also, information like number of banks and number of images per bank are also part of the metadata structure. Add functions to access fields of the version 2 of the metadata structure.
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org --- include/fwu.h | 53 ++++++++++++++++ lib/fwu_updates/fwu.c | 142 ++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 195 insertions(+)
diff --git a/include/fwu.h b/include/fwu.h index 1815bd0064..d3e97a5360 100644 --- a/include/fwu.h +++ b/include/fwu.h @@ -104,6 +104,26 @@ int fwu_write_mdata(struct udevice *dev, struct fwu_mdata *mdata, */ int fwu_get_mdata(struct fwu_mdata *mdata);
+/** + * fwu_mdata_copies_allocate() - Allocate memory for metadata + * + * Allocate memory for storing both the copies of the FWU metadata. The + * copies are then used as a cache for storing FWU metadata contents. + * + * Return: 0 if OK, -ve on error + */ +int fwu_mdata_copies_allocate(void); + +/** + * fwu_get_mdata_size() - Get the FWU metadata size + * + * Get the size of the FWU metadata from the structure. This is later used + * to allocate memory for the structure. + * + * Return: 0 if OK, -ve on error + */ +int fwu_get_mdata_size(uint32_t *mdata_size); + /** * fwu_get_active_index() - Get active_index from the FWU metadata * @active_idxp: active_index value to be read @@ -153,6 +173,18 @@ int fwu_get_dfu_alt_num(u8 image_index, u8 *alt_num); */ int fwu_revert_boot_index(void);
+/** + * fwu_bank_state_update() - Check and update the bank_state of the metadata + * @update_index: Bank for which the bank_state needs to be updated + * + * Check that all the images for the given bank have been accepted, and if + * they are, set the status of the bank to Accepted in the bank_state field + * of the metadata. + * + * Return: 0 if OK, -ve on error + */ +int fwu_bank_state_update(uint update_index); + /** * fwu_accept_image() - Set the Acceptance bit for the image * @img_type_id: GUID of the image type for which the accepted bit is to be @@ -286,4 +318,25 @@ int fwu_gen_alt_info_from_mtd(char *buf, size_t len, struct mtd_info *mtd); */ int fwu_mtd_get_alt_num(efi_guid_t *image_guid, u8 *alt_num, const char *mtd_dev);
+/** + * fwu_get_banks_images() - Get the number of banks and images from the metadata + * @nbanks: Number of banks + * @nimages: Number of images per bank + * + * Get the values of number of banks and number of images per bank from the + * metadata. + * + * Return: 0 if OK, -ve on error + */ +__maybe_unused int fwu_get_banks_images(u8 *nbanks, u16 *nimages); + +/** + * fwu_get_dev() - Return the FWU metadata device + * + * Return the pointer to the FWU metadata device. + * + * Return: Pointer to the FWU metadata dev + */ +__maybe_unused struct udevice *fwu_get_dev(void); + #endif /* _FWU_H_ */ diff --git a/lib/fwu_updates/fwu.c b/lib/fwu_updates/fwu.c index 86518108c2..5bfa24067b 100644 --- a/lib/fwu_updates/fwu.c +++ b/lib/fwu_updates/fwu.c @@ -188,6 +188,114 @@ static inline int mdata_crc_check(struct fwu_mdata *mdata) return calc_crc32 == mdata->crc32 ? 0 : -EINVAL; }
+/** + * fwu_mdata_copies_allocate() - Allocate memory for metadata + * + * Allocate memory for storing both the copies of the FWU metadata. The + * copies are then used as a cache for storing FWU metadata contents. + * + * Return: 0 if OK, -ve on error + */ +int fwu_mdata_copies_allocate(void) +{ + int err; + uint32_t mdata_size; + + if (g_mdata) + return 0; + + err = fwu_get_mdata_size(&mdata_size); + if (err) + return err; + + /* + * Now allocate the total memory that would be needed for both + * the copies. + */ + g_mdata = calloc(2, mdata_size); + if (!g_mdata) { + log_err("Unable to allocate space for FWU metadata\n"); + return -ENOMEM; + } + + return 0; +} + +/** + * fwu_get_mdata_size() - Get the FWU metadata size + * + * Get the size of the FWU metadata from the structure. This is later used + * to allocate memory for the structure. + * + * Return: 0 if OK, -ve on error + */ +int fwu_get_mdata_size(uint32_t *mdata_size) +{ + int err = 0; + struct fwu_mdata mdata = { 0 }; + + if (g_mdata && !mdata_crc_check(g_mdata)) { + *mdata_size = g_mdata->metadata_size; + return 0; + } + + err = fwu_read_mdata(g_dev, &mdata, 1, sizeof(struct fwu_mdata)); + if (err) { + log_err("FWU metadata read failed\n"); + return err; + } + + if (mdata.version != 0x2) { + log_err("FWU metadata version %u. Expected value of 2\n", + mdata.version); + return -EINVAL; + } + + *mdata_size = mdata.metadata_size; + if (!*mdata_size) + return -EINVAL; + + return 0; +} + +/** + * fwu_get_dev() - Return the FWU metadata device + * + * Return the pointer to the FWU metadata device. + * + * Return: Pointer to the FWU metadata dev + */ +__maybe_unused struct udevice *fwu_get_dev(void) +{ + return g_dev; +} + +/** + * fwu_get_banks_images() - Get the number of banks and images from the metadata + * @nbanks: Number of banks + * @nimages: Number of images per bank + * + * Get the values of number of banks and number of images per bank from the + * metadata. + * + * Return: 0 if OK, -ve on error + */ +__maybe_unused int fwu_get_banks_images(u8 *nbanks, u16 *nimages) +{ + int ret; + + if (mdata_crc_check(g_mdata)) { + ret = fwu_get_mdata(NULL); + if (ret) + return ret; + } + + *nbanks = g_mdata->fw_desc[0].num_banks; + *nimages = g_mdata->fw_desc[0].num_images; + + return 0; +} + /** * fwu_get_mdata() - Read, verify and return the FWU metadata * @mdata: Output FWU metadata read or NULL @@ -473,6 +581,40 @@ out: return ret; }
+/** + * fwu_bank_state_update() - Check and update the bank_state of the metadata + * @update_index: Bank for which the bank_state needs to be updated + * + * Check that all the images for the given bank have been accepted, and if + * they are, set the status of the bank to Accepted in the bank_state field + * of the metadata. + * + * Return: 0 if OK, -ve on error + */ +int fwu_bank_state_update(uint update_index) +{ + int ret = 0, i; + u16 num_images; + struct fwu_mdata *mdata = g_mdata; + struct fwu_image_entry *img_entry; + struct fwu_image_bank_info *img_bank_info; + + img_entry = &mdata->fw_desc[0].img_entry[0]; + num_images = mdata->fw_desc[0].num_images; + for (i = 0; i < num_images; i++) { + img_bank_info = &img_entry[i].img_bank_info[update_index]; + if (!(img_bank_info->accepted & FWU_IMAGE_ACCEPTED)) + return 0; + } + + mdata->bank_state[update_index] = FWU_BANK_ACCEPTED; + ret = fwu_sync_mdata(mdata, BOTH_PARTS); + if (ret) + log_err("Unable to set bank_state for bank %u\n", update_index); + + return ret; +} + /** * fwu_accept_image() - Set the Acceptance bit for the image * @img_type_id: GUID of the image type for which the accepted bit is to be

Make changes to the FWU library functions which are used to access the metadata structure to support version 2 of the metadata.
At a broad level, the following are the changes made - Use a pointer g_mdata instead of a variable, and allocate space for it at runtime. - Obtain the number of banks and number of images per bank from the metadata at runtime, instead of using config values. - Get the size of the metadata from the metadata structure, instead of using build-time value.
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org --- include/fwu.h | 6 ++- lib/fwu_updates/fwu.c | 112 ++++++++++++++++++++++++------------------ 2 files changed, 68 insertions(+), 50 deletions(-)
diff --git a/include/fwu.h b/include/fwu.h index d3e97a5360..d21c8c6f93 100644 --- a/include/fwu.h +++ b/include/fwu.h @@ -52,9 +52,13 @@ struct fwu_mdata_ops { bool primary, uint32_t size); };
-#define FWU_MDATA_VERSION 0x1 +#define FWU_MDATA_VERSION 0x2 #define FWU_IMAGE_ACCEPTED 0x1
+#define FWU_BANK_INVALID 0xFF +#define FWU_BANK_VALID 0xFE +#define FWU_BANK_ACCEPTED 0xFC + /* * GUID value defined in the FWU specification for identification * of the FWU metadata partition. diff --git a/lib/fwu_updates/fwu.c b/lib/fwu_updates/fwu.c index 5bfa24067b..831ff6aa91 100644 --- a/lib/fwu_updates/fwu.c +++ b/lib/fwu_updates/fwu.c @@ -17,7 +17,7 @@
#include <u-boot/crc.h>
-static struct fwu_mdata g_mdata; /* = {0} makes uninit crc32 always invalid */ +static struct fwu_mdata *g_mdata; static struct udevice *g_dev; static u8 in_trial; static u8 boottime_check; @@ -108,21 +108,9 @@ out:
static int in_trial_state(struct fwu_mdata *mdata) { - u32 i, active_bank; - struct fwu_image_entry *img_entry; - struct fwu_image_bank_info *img_bank_info; - - active_bank = mdata->active_index; - img_entry = &mdata->img_entry[0]; - for (i = 0; i < CONFIG_FWU_NUM_IMAGES_PER_BANK; i++) { - img_bank_info = &img_entry[i].img_bank_info[active_bank]; - if (!img_bank_info->accepted) { - log_info("System booting in Trial State\n"); - return 1; - } - } + u32 active_bank = mdata->active_index;
- return 0; + return mdata->bank_state[active_bank] == FWU_BANK_VALID ? 1 : 0; }
static int fwu_get_image_type_id(u8 image_index, efi_guid_t *image_type_id) @@ -150,8 +138,9 @@ static int fwu_get_image_type_id(u8 image_index, efi_guid_t *image_type_id) */ static int fwu_sync_mdata(struct fwu_mdata *mdata, int part) { - void *buf = &mdata->version; int err; + uint32_t mdata_size; + void *buf = &mdata->version;
if (part == BOTH_PARTS) { err = fwu_sync_mdata(mdata, SECONDARY_PART); @@ -165,9 +154,10 @@ static int fwu_sync_mdata(struct fwu_mdata *mdata, int part) * and put the updated value in the FWU metadata crc32 * field */ - mdata->crc32 = crc32(0, buf, sizeof(*mdata) - sizeof(u32)); + mdata_size = mdata->metadata_size; + mdata->crc32 = crc32(0, buf, mdata_size - sizeof(u32));
- err = fwu_write_mdata(g_dev, mdata, part == PRIMARY_PART); + err = fwu_write_mdata(g_dev, mdata, part == PRIMARY_PART, mdata_size); if (err) { log_err("Unable to write %s mdata\n", part == PRIMARY_PART ? "primary" : "secondary"); @@ -175,7 +165,7 @@ static int fwu_sync_mdata(struct fwu_mdata *mdata, int part) }
/* update the cached copy of meta-data */ - memcpy(&g_mdata, mdata, sizeof(struct fwu_mdata)); + memcpy(g_mdata, mdata, mdata_size);
return 0; } @@ -183,8 +173,12 @@ static int fwu_sync_mdata(struct fwu_mdata *mdata, int part) static inline int mdata_crc_check(struct fwu_mdata *mdata) { void *buf = &mdata->version; - u32 calc_crc32 = crc32(0, buf, sizeof(*mdata) - sizeof(u32)); + u32 calc_crc32; + + if (!mdata->metadata_size) + return -EINVAL;
+ calc_crc32 = crc32(0, buf, mdata->metadata_size - sizeof(u32)); return calc_crc32 == mdata->crc32 ? 0 : -EINVAL; }
@@ -309,27 +303,32 @@ __maybe_unused int fwu_get_banks_images(u8 *nbanks, u16 *nimages) int fwu_get_mdata(struct fwu_mdata *mdata) { int err; + uint32_t mdata_size; bool parts_ok[2] = { false }; - struct fwu_mdata s, *parts_mdata[2]; + struct fwu_mdata *parts_mdata[2]; + + err = fwu_get_mdata_size(&mdata_size); + if (err) + return err;
- parts_mdata[0] = &g_mdata; - parts_mdata[1] = &s; + parts_mdata[0] = g_mdata; + parts_mdata[1] = (struct fwu_mdata *)((char *)g_mdata + mdata_size);
/* if mdata already read and ready */ - err = mdata_crc_check(parts_mdata[0]); - if (!err) + if (!mdata_crc_check(parts_mdata[0])) goto ret_mdata; - /* else read, verify and, if needed, fix mdata */
+ /* else read, verify and, if needed, fix mdata */ for (int i = 0; i < 2; i++) { parts_ok[i] = false; - err = fwu_read_mdata(g_dev, parts_mdata[i], !i); + err = fwu_read_mdata(g_dev, parts_mdata[i], !i, mdata_size); if (!err) { err = mdata_crc_check(parts_mdata[i]); if (!err) parts_ok[i] = true; else - log_debug("mdata : %s crc32 failed\n", i ? "secondary" : "primary"); + log_debug("mdata : %s crc32 failed\n", + i ? "secondary" : "primary"); } }
@@ -338,7 +337,8 @@ int fwu_get_mdata(struct fwu_mdata *mdata) * Before returning, check that both the * FWU metadata copies are the same. */ - err = memcmp(parts_mdata[0], parts_mdata[1], sizeof(struct fwu_mdata)); + err = memcmp(parts_mdata[0], parts_mdata[1], + mdata_size); if (!err) goto ret_mdata;
@@ -355,7 +355,8 @@ int fwu_get_mdata(struct fwu_mdata *mdata) if (parts_ok[i]) continue;
- memcpy(parts_mdata[i], parts_mdata[1 - i], sizeof(struct fwu_mdata)); + memcpy(parts_mdata[i], parts_mdata[1 - i], + mdata_size); err = fwu_sync_mdata(parts_mdata[i], i ? SECONDARY_PART : PRIMARY_PART); if (err) { log_debug("mdata : %s write failed\n", i ? "secondary" : "primary"); @@ -365,7 +366,7 @@ int fwu_get_mdata(struct fwu_mdata *mdata)
ret_mdata: if (!err && mdata) - memcpy(mdata, parts_mdata[0], sizeof(struct fwu_mdata)); + memcpy(mdata, parts_mdata[0], mdata_size);
return err; } @@ -383,14 +384,16 @@ ret_mdata: int fwu_get_active_index(uint *active_idx) { int ret = 0; - struct fwu_mdata *mdata = &g_mdata; + u8 num_banks; + struct fwu_mdata *mdata = g_mdata;
/* * Found the FWU metadata partition, now read the active_index * value */ *active_idx = mdata->active_index; - if (*active_idx >= CONFIG_FWU_NUM_BANKS) { + num_banks = mdata->fw_desc[0].num_banks; + if (*active_idx >= num_banks) { log_debug("Active index value read is incorrect\n"); ret = -EINVAL; } @@ -410,9 +413,11 @@ int fwu_get_active_index(uint *active_idx) int fwu_set_active_index(uint active_idx) { int ret; - struct fwu_mdata *mdata = &g_mdata; + u8 num_banks; + struct fwu_mdata *mdata = g_mdata;
- if (active_idx >= CONFIG_FWU_NUM_BANKS) { + num_banks = mdata->fw_desc[0].num_banks; + if (active_idx >= num_banks) { log_debug("Invalid active index value\n"); return -EINVAL; } @@ -452,9 +457,10 @@ int fwu_set_active_index(uint active_idx) int fwu_get_dfu_alt_num(u8 image_index, u8 *alt_num) { int ret, i; + u16 num_images; uint update_bank; efi_guid_t *image_guid, image_type_id; - struct fwu_mdata *mdata = &g_mdata; + struct fwu_mdata *mdata = g_mdata; struct fwu_image_entry *img_entry; struct fwu_image_bank_info *img_bank_info;
@@ -473,15 +479,16 @@ int fwu_get_dfu_alt_num(u8 image_index, u8 *alt_num)
ret = -EINVAL; /* - * The FWU metadata has been read. Now get the image_uuid for the + * The FWU metadata has been read. Now get the image_guid for the * image with the update_bank. */ - for (i = 0; i < CONFIG_FWU_NUM_IMAGES_PER_BANK; i++) { + num_images = mdata->fw_desc[0].num_images; + for (i = 0; i < num_images; i++) { if (!guidcmp(&image_type_id, - &mdata->img_entry[i].image_type_uuid)) { - img_entry = &mdata->img_entry[i]; + &mdata->fw_desc[0].img_entry[i].image_type_guid)) { + img_entry = &mdata->fw_desc[0].img_entry[i]; img_bank_info = &img_entry->img_bank_info[update_bank]; - image_guid = &img_bank_info->image_uuid; + image_guid = &img_bank_info->image_guid; ret = fwu_plat_get_alt_num(g_dev, image_guid, alt_num); if (ret) log_debug("alt_num not found for partition with GUID %pUs\n", @@ -515,7 +522,7 @@ int fwu_revert_boot_index(void) { int ret; u32 cur_active_index; - struct fwu_mdata *mdata = &g_mdata; + struct fwu_mdata *mdata = g_mdata;
/* * Swap the active index and previous_active_index fields @@ -556,13 +563,15 @@ int fwu_revert_boot_index(void) static int fwu_clrset_image_accept(efi_guid_t *img_type_id, u32 bank, u8 action) { int ret, i; - struct fwu_mdata *mdata = &g_mdata; + u16 num_images; + struct fwu_mdata *mdata = g_mdata; struct fwu_image_entry *img_entry; struct fwu_image_bank_info *img_bank_info;
- img_entry = &mdata->img_entry[0]; - for (i = 0; i < CONFIG_FWU_NUM_IMAGES_PER_BANK; i++) { - if (!guidcmp(&img_entry[i].image_type_uuid, img_type_id)) { + img_entry = &mdata->fw_desc[0].img_entry[0]; + num_images = mdata->fw_desc[0].num_images; + for (i = 0; i < num_images; i++) { + if (!guidcmp(&img_entry[i].image_type_guid, img_type_id)) { img_bank_info = &img_entry[i].img_bank_info[bank]; if (action == IMAGE_ACCEPT_SET) img_bank_info->accepted |= FWU_IMAGE_ACCEPTED; @@ -671,12 +680,15 @@ __weak int fwu_plat_get_update_index(uint *update_idx) { int ret; u32 active_idx; + u8 num_banks; + struct fwu_mdata *mdata = g_mdata;
ret = fwu_get_active_index(&active_idx); if (ret < 0) return -1;
- *update_idx = (active_idx + 1) % CONFIG_FWU_NUM_BANKS; + num_banks = mdata->fw_desc[0].num_banks; + *update_idx = (active_idx + 1) % num_banks;
return ret; } @@ -755,6 +767,7 @@ int fwu_trial_state_ctr_start(void) static int fwu_boottime_checks(void) { int ret; + u8 num_banks; u32 boot_idx, active_idx;
ret = uclass_first_device_err(UCLASS_FWU_MDATA, &g_dev); @@ -785,7 +798,8 @@ static int fwu_boottime_checks(void) * update the active_index. */ fwu_plat_get_bootidx(&boot_idx); - if (boot_idx >= CONFIG_FWU_NUM_BANKS) { + num_banks = g_mdata->fw_desc[0].num_banks; + if (boot_idx >= num_banks) { log_err("Received incorrect value of boot_index\n"); return 0; } @@ -807,7 +821,7 @@ static int fwu_boottime_checks(void) if (efi_init_obj_list() != EFI_SUCCESS) return 0;
- in_trial = in_trial_state(&g_mdata); + in_trial = in_trial_state(g_mdata); if (!in_trial || (ret = fwu_trial_count_update()) > 0) ret = trial_counter_update(NULL);

The FWU metadata access driver for MTD partitioned devices currently uses a statically allocated array for storing the updatable image information. This array depends on the number of banks and images per bank. With migration of the FWU metadata to version 2, these parameters are now obtained at runtime from the metadata.
Make changes to the FWU metadata access driver for MTD devices to allocate memory for the image information dynamically in the driver's probe function, after having obtained the number of banks and images per bank by reading the metadata. Move the image information as part of the driver's private structure, instead of using a global variable.
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org --- drivers/fwu-mdata/raw_mtd.c | 71 ++++++++++++++++++++++++------------- include/fwu.h | 9 +++++ 2 files changed, 55 insertions(+), 25 deletions(-)
diff --git a/drivers/fwu-mdata/raw_mtd.c b/drivers/fwu-mdata/raw_mtd.c index 9f3f1dc213..da36094644 100644 --- a/drivers/fwu-mdata/raw_mtd.c +++ b/drivers/fwu-mdata/raw_mtd.c @@ -12,22 +12,11 @@ #include <linux/errno.h> #include <linux/types.h>
-/* Internal helper structure to move data around */ -struct fwu_mdata_mtd_priv { - struct mtd_info *mtd; - char pri_label[50]; - char sec_label[50]; - u32 pri_offset; - u32 sec_offset; -}; - enum fwu_mtd_op { FWU_MTD_READ, FWU_MTD_WRITE, };
-extern struct fwu_mtd_image_info fwu_mtd_images[]; - static bool mtd_is_aligned_with_block_size(struct mtd_info *mtd, u64 size) { return !do_div(size, mtd->erasesize); @@ -134,7 +123,7 @@ static int flash_partition_offset(struct udevice *dev, const char *part_name, fd return (int)size; }
-static int fwu_mdata_mtd_of_to_plat(struct udevice *dev) +static int get_fwu_mdata_dev(struct udevice *dev) { struct fwu_mdata_mtd_priv *mtd_priv = dev_get_priv(dev); const fdt32_t *phandle_p = NULL; @@ -144,8 +133,6 @@ static int fwu_mdata_mtd_of_to_plat(struct udevice *dev) fdt_addr_t offset; int ret, size; u32 phandle; - ofnode bank; - int off_img;
/* Find the FWU mdata storage device */ phandle_p = ofnode_get_property(dev_ofnode(dev), @@ -199,8 +186,28 @@ static int fwu_mdata_mtd_of_to_plat(struct udevice *dev) return ret; mtd_priv->sec_offset = offset;
- off_img = 0; + return 0; +} + +static int fwu_mtd_image_info_populate(struct udevice *dev, u8 nbanks, + u16 nimages) +{ + struct fwu_mtd_image_info *mtd_images; + struct fwu_mdata_mtd_priv *mtd_priv = dev_get_priv(dev); + struct udevice *mtd_dev = mtd_priv->mtd->dev; + fdt_addr_t offset; + ofnode bank; + int off_img; + u32 total_images;
+ total_images = nbanks * nimages; + mtd_priv->fwu_mtd_images = malloc(sizeof(struct fwu_mtd_image_info) * + total_images); + if (!mtd_priv->fwu_mtd_images) + return -ENOMEM; + + off_img = 0; + mtd_images = mtd_priv->fwu_mtd_images; ofnode_for_each_subnode(bank, dev_ofnode(dev)) { int bank_num, bank_offset, bank_size; const char *bank_name; @@ -219,8 +226,7 @@ static int fwu_mdata_mtd_of_to_plat(struct udevice *dev) int image_num, image_offset, image_size; const char *uuid;
- if (off_img == CONFIG_FWU_NUM_BANKS * - CONFIG_FWU_NUM_IMAGES_PER_BANK) { + if (off_img == total_images) { log_err("DT provides more images than configured!\n"); break; } @@ -230,11 +236,11 @@ static int fwu_mdata_mtd_of_to_plat(struct udevice *dev) ofnode_read_u32(image, "offset", &image_offset); ofnode_read_u32(image, "size", &image_size);
- fwu_mtd_images[off_img].start = bank_offset + image_offset; - fwu_mtd_images[off_img].size = image_size; - fwu_mtd_images[off_img].bank_num = bank_num; - fwu_mtd_images[off_img].image_num = image_num; - strcpy(fwu_mtd_images[off_img].uuidbuf, uuid); + mtd_images[off_img].start = bank_offset + image_offset; + mtd_images[off_img].size = image_size; + mtd_images[off_img].bank_num = bank_num; + mtd_images[off_img].image_num = image_num; + strcpy(mtd_images[off_img].uuidbuf, uuid); log_debug("\tImage%d: %s @0x%x\n\n", image_num, uuid, bank_offset + image_offset); off_img++; @@ -246,8 +252,24 @@ static int fwu_mdata_mtd_of_to_plat(struct udevice *dev)
static int fwu_mdata_mtd_probe(struct udevice *dev) { - /* Ensure the metadata can be read. */ - return fwu_get_mdata(NULL); + u8 nbanks; + u16 nimages; + int ret; + + ret = get_fwu_mdata_dev(dev); + if (ret) + return ret; + + /* Read the metadata to get number of banks and images */ + ret = fwu_get_banks_images(&nbanks, &nimages); + if (ret) + return ret; + + ret = fwu_mtd_image_info_populate(dev, nbanks, nimages); + if (ret) + return ret; + + return 0; }
static struct fwu_mdata_ops fwu_mtd_ops = { @@ -266,6 +288,5 @@ U_BOOT_DRIVER(fwu_mdata_mtd) = { .of_match = fwu_mdata_ids, .ops = &fwu_mtd_ops, .probe = fwu_mdata_mtd_probe, - .of_to_plat = fwu_mdata_mtd_of_to_plat, .priv_auto = sizeof(struct fwu_mdata_mtd_priv), }; diff --git a/include/fwu.h b/include/fwu.h index d21c8c6f93..3764336952 100644 --- a/include/fwu.h +++ b/include/fwu.h @@ -26,6 +26,15 @@ struct fwu_mtd_image_info { char uuidbuf[UUID_STR_LEN + 1]; };
+struct fwu_mdata_mtd_priv { + struct mtd_info *mtd; + char pri_label[50]; + char sec_label[50]; + u32 pri_offset; + u32 sec_offset; + struct fwu_mtd_image_info *fwu_mtd_images; +}; + struct fwu_mdata_ops { /** * read_mdata() - Populate the asked FWU metadata copy

With migration of the FWU metadata access code to version 2, the size of the metadata is obtained at runtime. Allocate memory for both the metadata copies from the driver's probe function.
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org --- drivers/fwu-mdata/gpt_blk.c | 4 ++++ drivers/fwu-mdata/raw_mtd.c | 4 ++++ 2 files changed, 8 insertions(+)
diff --git a/drivers/fwu-mdata/gpt_blk.c b/drivers/fwu-mdata/gpt_blk.c index 97eac3611f..c2cb7ef7c3 100644 --- a/drivers/fwu-mdata/gpt_blk.c +++ b/drivers/fwu-mdata/gpt_blk.c @@ -159,6 +159,10 @@ static int fwu_mdata_gpt_blk_probe(struct udevice *dev)
priv->blk_dev = mdata_dev;
+ ret = fwu_mdata_copies_allocate(); + if (ret) + return ret; + return 0; }
diff --git a/drivers/fwu-mdata/raw_mtd.c b/drivers/fwu-mdata/raw_mtd.c index da36094644..d91518bf0a 100644 --- a/drivers/fwu-mdata/raw_mtd.c +++ b/drivers/fwu-mdata/raw_mtd.c @@ -260,6 +260,10 @@ static int fwu_mdata_mtd_probe(struct udevice *dev) if (ret) return ret;
+ ret = fwu_mdata_copies_allocate(); + if (ret) + return ret; + /* Read the metadata to get number of banks and images */ ret = fwu_get_banks_images(&nbanks, &nimages); if (ret)

The version 2 of the FWU metadata has a field in the top level structure, called bank_state. This is used to keep the state a given bank is in, either of valid(for trial state), invalid, or accepted.
Update this field when putting the platform in Trial State, in addition to starting the TrialStateCtr variable by calling the fwu_trial_state_start() function.
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org --- include/fwu.h | 12 +++++--- lib/efi_loader/efi_capsule.c | 2 +- lib/fwu_updates/fwu.c | 54 ++++++++++++++++++++++++++++++------ 3 files changed, 54 insertions(+), 14 deletions(-)
diff --git a/include/fwu.h b/include/fwu.h index 3764336952..d0b4e12190 100644 --- a/include/fwu.h +++ b/include/fwu.h @@ -297,15 +297,19 @@ u8 fwu_update_checks_pass(void); u8 fwu_empty_capsule_checks_pass(void);
/** - * fwu_trial_state_ctr_start() - Start the Trial State counter + * fwu_trial_state_start() - Put the platform in Trial State + * @update_index: Bank number to which images have been updated * - * Start the counter to identify the platform booting in the - * Trial State. The counter is implemented as an EFI variable. + * Put the platform in Trial State by starting the counter to + * identify the platform booting in the Trial State. The + * counter is implemented as an EFI variable. Secondly, set + * the bank_state in the metadata for the updated bank to Valid + * state. * * Return: 0 if OK, -ve on error * */ -int fwu_trial_state_ctr_start(void); +int fwu_trial_state_start(uint update_index);
/** * fwu_gen_alt_info_from_mtd() - Parse dfu_alt_info from metadata in mtd diff --git a/lib/efi_loader/efi_capsule.c b/lib/efi_loader/efi_capsule.c index de0d49ebeb..0e6a38b441 100644 --- a/lib/efi_loader/efi_capsule.c +++ b/lib/efi_loader/efi_capsule.c @@ -522,7 +522,7 @@ static __maybe_unused efi_status_t fwu_post_update_process(bool fw_accept_os) } else { log_debug("Successfully updated the active_index\n"); if (fw_accept_os) { - status = fwu_trial_state_ctr_start(); + status = fwu_trial_state_start(update_index); if (status < 0) ret = EFI_DEVICE_ERROR; } diff --git a/lib/fwu_updates/fwu.c b/lib/fwu_updates/fwu.c index 831ff6aa91..0f43cf63b2 100644 --- a/lib/fwu_updates/fwu.c +++ b/lib/fwu_updates/fwu.c @@ -590,6 +590,36 @@ out: return ret; }
+static int fwu_trial_state_ctr_start(void) +{ + int ret; + u16 trial_state_ctr; + + printf("%s: starting the TrialStateCtr\n", __func__); + trial_state_ctr = 0; + ret = trial_counter_update(&trial_state_ctr); + if (ret) + log_err("Unable to initialise TrialStateCtr\n"); + + return ret; +} + +static int fwu_set_bank_state_trial(uint update_index) +{ + int ret; + struct fwu_mdata *mdata = g_mdata; + + mdata->bank_state[update_index] = FWU_BANK_VALID; + + ret = fwu_sync_mdata(mdata, BOTH_PARTS); + if (ret) { + log_err("Unable to set bank_state for %d bank\n", update_index); + return ret; + } + + return 0; +} + /** * fwu_bank_state_update() - Check and update the bank_state of the metadata * @update_index: Bank for which the bank_state needs to be updated @@ -743,25 +773,31 @@ u8 fwu_empty_capsule_checks_pass(void) }
/** - * fwu_trial_state_ctr_start() - Start the Trial State counter + * fwu_trial_state_start() - Put the platform in Trial State + * @update_index: Bank number to which images have been updated * - * Start the counter to identify the platform booting in the - * Trial State. The counter is implemented as an EFI variable. + * Put the platform in Trial State by starting the counter to + * identify the platform booting in the Trial State. The + * counter is implemented as an EFI variable. Secondly, set + * the bank_state in the metadata for the updated bank to Valid + * state. * * Return: 0 if OK, -ve on error * */ -int fwu_trial_state_ctr_start(void) +int fwu_trial_state_start(uint update_index) { int ret; - u16 trial_state_ctr;
- trial_state_ctr = 0; - ret = trial_counter_update(&trial_state_ctr); + ret = fwu_trial_state_ctr_start(); if (ret) - log_err("Unable to initialise TrialStateCtr\n"); + return ret;
- return ret; + ret = fwu_set_bank_state_trial(update_index); + if (ret) + return ret; + + return 0; }
static int fwu_boottime_checks(void)

The version 2 of the FWU metadata maintains a bank_state field per bank, which keeps an aggregate status of the bank. A bank can either be in a valid, invalid, or accepted state.
Update the bank_state field of the metadata once the update has gone through successfully(when skipping Trial State), or once the images in the bank have been accepted.
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org --- lib/efi_loader/efi_capsule.c | 10 ++++++++++ 1 file changed, 10 insertions(+)
diff --git a/lib/efi_loader/efi_capsule.c b/lib/efi_loader/efi_capsule.c index 0e6a38b441..422bb11162 100644 --- a/lib/efi_loader/efi_capsule.c +++ b/lib/efi_loader/efi_capsule.c @@ -480,6 +480,12 @@ static __maybe_unused efi_status_t fwu_empty_capsule_process( if (ret != EFI_SUCCESS) log_err("Unable to set the Accept bit for the image %pUs\n", image_guid); + + status = fwu_bank_state_update(active_idx); + ret = fwu_to_efi_error(status); + if (ret != EFI_SUCCESS) + log_err("Unable to update the bank_state for bank %u\n", + active_idx); }
return ret; @@ -525,6 +531,10 @@ static __maybe_unused efi_status_t fwu_post_update_process(bool fw_accept_os) status = fwu_trial_state_start(update_index); if (status < 0) ret = EFI_DEVICE_ERROR; + } else { + status = fwu_bank_state_update(update_index); + if (status < 0) + ret = EFI_DEVICE_ERROR; } }

Make changes to the functions used for generating the DFU's alt variable so that they are aligned with changes to the metadata version 2.
These changes include getting the number of banks and images per bank at runtime from the metadata, as well as accessing the updatable image information from the FWU MTD driver's private structure.
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org --- lib/fwu_updates/fwu_mtd.c | 76 +++++++++++++++++++++++++++++---------- 1 file changed, 58 insertions(+), 18 deletions(-)
diff --git a/lib/fwu_updates/fwu_mtd.c b/lib/fwu_updates/fwu_mtd.c index 69cd3d7001..a82133de2e 100644 --- a/lib/fwu_updates/fwu_mtd.c +++ b/lib/fwu_updates/fwu_mtd.c @@ -15,16 +15,51 @@
#include <dm/ofnode.h>
-struct fwu_mtd_image_info -fwu_mtd_images[CONFIG_FWU_NUM_BANKS * CONFIG_FWU_NUM_IMAGES_PER_BANK]; +static struct fwu_mdata *mdata; + +static int read_mdata(void) +{ + int ret = 0; + u32 mdata_size; + + ret = fwu_get_mdata_size(&mdata_size); + if (ret) + return ret; + + mdata = malloc(mdata_size); + if (!mdata) + return -ENOMEM; + + ret = fwu_get_mdata(mdata); + if (ret < 0) { + log_err("Failed to get the FWU mdata\n"); + free(mdata); + mdata = NULL; + } + + return ret; +}
static struct fwu_mtd_image_info *mtd_img_by_uuid(const char *uuidbuf) { - int num_images = ARRAY_SIZE(fwu_mtd_images); + u8 nbanks; + u16 nimages; + int num_images, ret; + struct fwu_mdata_mtd_priv *mtd_priv = dev_get_priv(fwu_get_dev()); + struct fwu_mtd_image_info *image_info = mtd_priv->fwu_mtd_images; + + if (!image_info) + return NULL; + + ret = fwu_get_banks_images(&nbanks, &nimages); + if (ret) + return NULL; + + num_images = nbanks * nimages;
for (int i = 0; i < num_images; i++) - if (!strcmp(uuidbuf, fwu_mtd_images[i].uuidbuf)) - return &fwu_mtd_images[i]; + if (!strcmp(uuidbuf, image_info[i].uuidbuf)) + return &image_info[i];
return NULL; } @@ -108,7 +143,8 @@ __weak int fwu_plat_get_alt_num(struct udevice *dev, efi_guid_t *image_id, }
static int gen_image_alt_info(char *buf, size_t len, int sidx, - struct fwu_image_entry *img, struct mtd_info *mtd) + struct fwu_image_entry *img, + struct mtd_info *mtd, uint8_t num_banks) { char *p = buf, *end = buf + len; int i; @@ -123,7 +159,7 @@ static int gen_image_alt_info(char *buf, size_t len, int sidx, * List the image banks in the FWU mdata and search the corresponding * partition based on partition's uuid. */ - for (i = 0; i < CONFIG_FWU_NUM_BANKS; i++) { + for (i = 0; i < num_banks; i++) { struct fwu_mtd_image_info *mtd_img_info; struct fwu_image_bank_info *bank; char uuidbuf[UUID_STR_LEN + 1]; @@ -131,7 +167,7 @@ static int gen_image_alt_info(char *buf, size_t len, int sidx,
/* Query a partition by image UUID */ bank = &img->img_bank_info[i]; - uuid_bin_to_str(bank->image_uuid.b, uuidbuf, UUID_STR_FORMAT_STD); + uuid_bin_to_str(bank->image_guid.b, uuidbuf, UUID_STR_FORMAT_STD);
mtd_img_info = mtd_img_by_uuid(uuidbuf); if (!mtd_img_info) { @@ -150,7 +186,7 @@ static int gen_image_alt_info(char *buf, size_t len, int sidx, } }
- if (i == CONFIG_FWU_NUM_BANKS) + if (i == num_banks) return 0;
return -ENOENT; @@ -158,24 +194,28 @@ static int gen_image_alt_info(char *buf, size_t len, int sidx,
int fwu_gen_alt_info_from_mtd(char *buf, size_t len, struct mtd_info *mtd) { - struct fwu_mdata mdata; + u8 num_banks; + u16 num_images; int i, l, ret;
- ret = fwu_get_mdata(&mdata); - if (ret < 0) { - log_err("Failed to get the FWU mdata.\n"); - return ret; + if (!mdata) { + ret = read_mdata(); + if (ret) + return ret; }
- for (i = 0; i < CONFIG_FWU_NUM_IMAGES_PER_BANK; i++) { - ret = gen_image_alt_info(buf, len, i * CONFIG_FWU_NUM_BANKS, - &mdata.img_entry[i], mtd); + num_banks = mdata->fw_desc[0].num_banks; + num_images = mdata->fw_desc[0].num_images; + for (i = 0; i < num_images; i++) { + ret = gen_image_alt_info(buf, len, i * num_banks, + &mdata->fw_desc[0].img_entry[i], + mtd, num_banks); if (ret) break;
l = strlen(buf); /* Replace the last ';' with '&' if there is another image. */ - if (i != CONFIG_FWU_NUM_IMAGES_PER_BANK - 1 && l) { + if (i != num_images - 1 && l) { buf[l] = '&'; buf++; }

The FWU metadata is being read for populating the firmware image's version information. The sandbox platform does not have the FWU metadata on any of it's storage devices. Skip attempting to read the FWU metadata on the sandbox platform.
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org --- lib/efi_loader/efi_firmware.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-)
diff --git a/lib/efi_loader/efi_firmware.c b/lib/efi_loader/efi_firmware.c index 9fd13297a6..51797a169f 100644 --- a/lib/efi_loader/efi_firmware.c +++ b/lib/efi_loader/efi_firmware.c @@ -223,7 +223,8 @@ void efi_firmware_fill_version_info(struct efi_firmware_image_descriptor *image_ /* get the fw_version */ efi_create_indexed_name(varname, sizeof(varname), "FmpState", fw_array->image_index); - if (IS_ENABLED(CONFIG_FWU_MULTI_BANK_UPDATE)) { + if (!IS_ENABLED(CONFIG_SANDBOX) && + IS_ENABLED(CONFIG_FWU_MULTI_BANK_UPDATE)) { ret = fwu_get_active_index(&active_index); if (ret) return; @@ -391,7 +392,8 @@ efi_status_t efi_firmware_set_fmp_state_var(struct fmp_state *state, u8 image_in efi_create_indexed_name(varname, sizeof(varname), "FmpState", image_index);
- if (IS_ENABLED(CONFIG_FWU_MULTI_BANK_UPDATE)) { + if (!IS_ENABLED(CONFIG_SANDBOX) && + IS_ENABLED(CONFIG_FWU_MULTI_BANK_UPDATE)) { ret = fwu_plat_get_update_index(&update_bank); if (ret) return EFI_INVALID_PARAMETER;

With the migration of the FWU metadata to version 2, the number of banks are now obtained at runtime, instead of the config symbols. Make use of the API to get the number of banks in the versioning functions.
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org --- lib/efi_loader/efi_firmware.c | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-)
diff --git a/lib/efi_loader/efi_firmware.c b/lib/efi_loader/efi_firmware.c index 51797a169f..74f241015d 100644 --- a/lib/efi_loader/efi_firmware.c +++ b/lib/efi_loader/efi_firmware.c @@ -207,7 +207,8 @@ void efi_firmware_fill_version_info(struct efi_firmware_image_descriptor *image_ u16 varname[13]; /* u"FmpStateXXXX" */ efi_status_t ret; efi_uintn_t size, expected_size; - uint num_banks = 1; + u8 num_banks = 1; + u16 __maybe_unused num_images; uint active_index = 0; struct fmp_state *var_state;
@@ -229,7 +230,9 @@ void efi_firmware_fill_version_info(struct efi_firmware_image_descriptor *image_ if (ret) return;
- num_banks = CONFIG_FWU_NUM_BANKS; + ret = fwu_get_banks_images(&num_banks, &num_images); + if (ret) + return; }
size = num_banks * sizeof(*var_state); @@ -379,7 +382,8 @@ efi_status_t efi_firmware_set_fmp_state_var(struct fmp_state *state, u8 image_in { u16 varname[13]; /* u"FmpStateXXXX" */ efi_status_t ret; - uint num_banks = 1; + u8 num_banks = 1; + u16 __maybe_unused num_images; uint update_bank = 0; efi_uintn_t size; efi_guid_t *image_type_id; @@ -398,7 +402,9 @@ efi_status_t efi_firmware_set_fmp_state_var(struct fmp_state *state, u8 image_in if (ret) return EFI_INVALID_PARAMETER;
- num_banks = CONFIG_FWU_NUM_BANKS; + ret = fwu_get_banks_images(&num_banks, &num_images); + if (ret) + return EFI_INVALID_PARAMETER; }
size = num_banks * sizeof(*var_state);

Make changes to the fwu_mdata_read command to have it align with the metadata version 2.
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org --- cmd/fwu_mdata.c | 43 ++++++++++++++++++++++++++++++++++--------- 1 file changed, 34 insertions(+), 9 deletions(-)
diff --git a/cmd/fwu_mdata.c b/cmd/fwu_mdata.c index 5ecda455df..7d99b8287f 100644 --- a/cmd/fwu_mdata.c +++ b/cmd/fwu_mdata.c @@ -16,6 +16,8 @@ static void print_mdata(struct fwu_mdata *mdata) { int i, j; + uint8_t num_banks; + uint16_t num_images; struct fwu_image_entry *img_entry; struct fwu_image_bank_info *img_info;
@@ -25,15 +27,22 @@ static void print_mdata(struct fwu_mdata *mdata) printf("active_index: %#x\n", mdata->active_index); printf("previous_active_index: %#x\n", mdata->previous_active_index);
+ num_banks = mdata->fw_desc[0].num_banks; + num_images = mdata->fw_desc[0].num_images; + + for (i = 0; i < 4; i++) + printf("bank_state[%d]: %#x\n", i, mdata->bank_state[i]); + printf("\tImage Info\n"); - for (i = 0; i < CONFIG_FWU_NUM_IMAGES_PER_BANK; i++) { - img_entry = &mdata->img_entry[i]; + + for (i = 0; i < num_images; i++) { + img_entry = &mdata->fw_desc[0].img_entry[i]; printf("\nImage Type Guid: %pUL\n", - &img_entry->image_type_uuid); - printf("Location Guid: %pUL\n", &img_entry->location_uuid); - for (j = 0; j < CONFIG_FWU_NUM_BANKS; j++) { + &img_entry->image_type_guid); + printf("Location Guid: %pUL\n", &img_entry->location_guid); + for (j = 0; j < num_banks; j++) { img_info = &img_entry->img_bank_info[j]; - printf("Image Guid: %pUL\n", &img_info->image_uuid); + printf("Image Guid: %pUL\n", &img_info->image_guid); printf("Image Acceptance: %s\n", img_info->accepted == 0x1 ? "yes" : "no"); } @@ -43,19 +52,35 @@ static void print_mdata(struct fwu_mdata *mdata) int do_fwu_mdata_read(struct cmd_tbl *cmdtp, int flag, int argc, char * const argv[]) { + uint32_t mdata_size; + struct fwu_mdata *mdata = NULL; int ret = CMD_RET_SUCCESS, res; - struct fwu_mdata mdata;
- res = fwu_get_mdata(&mdata); + res = fwu_get_mdata_size(&mdata_size); + if (res) { + log_err("Unable to get FWU metadata size\n"); + ret = CMD_RET_FAILURE; + goto out; + } + + mdata = malloc(mdata_size); + if (!mdata) { + log_err("Unable to allocate memory for FWU metadata\n"); + ret = CMD_RET_FAILURE; + goto out; + } + + res = fwu_get_mdata(mdata); if (res < 0) { log_err("Unable to get valid FWU metadata\n"); ret = CMD_RET_FAILURE; goto out; }
- print_mdata(&mdata); + print_mdata(mdata);
out: + free(mdata); return ret; }

With the FWU metadata support having been migrated to version 2, make corresponding changes to the test for accessing the FWU metadata.
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org --- test/dm/fwu_mdata.c | 56 ++++++++------- test/dm/fwu_mdata_disk_image.h | 124 ++++++++++++++------------------- 2 files changed, 83 insertions(+), 97 deletions(-)
diff --git a/test/dm/fwu_mdata.c b/test/dm/fwu_mdata.c index 52018f610f..73b3382917 100644 --- a/test/dm/fwu_mdata.c +++ b/test/dm/fwu_mdata.c @@ -88,10 +88,15 @@ static int write_mmc_blk_device(struct unit_test_state *uts) return 0; }
-static int dm_test_fwu_mdata_read(struct unit_test_state *uts) +static int fwu_mdata_access_setup(struct unit_test_state *uts, + struct fwu_mdata **mdata) { + u32 mdata_size; struct udevice *dev; - struct fwu_mdata mdata = { 0 }; + + ut_assertok(setup_blk_device(uts)); + ut_assertok(populate_mmc_disk_image(uts)); + ut_assertok(write_mmc_blk_device(uts));
/* * Trigger lib/fwu_updates/fwu.c fwu_boottime_checks() @@ -100,13 +105,24 @@ static int dm_test_fwu_mdata_read(struct unit_test_state *uts) event_notify_null(EVT_MAIN_LOOP);
ut_assertok(uclass_first_device_err(UCLASS_FWU_MDATA, &dev)); - ut_assertok(setup_blk_device(uts)); - ut_assertok(populate_mmc_disk_image(uts)); - ut_assertok(write_mmc_blk_device(uts));
- ut_assertok(fwu_get_mdata(&mdata)); + ut_assertok(fwu_get_mdata_size(&mdata_size));
- ut_asserteq(mdata.version, 0x1); + *mdata = malloc(mdata_size); + ut_assertnonnull(*mdata); + + return 0; +} + +static int dm_test_fwu_mdata_read(struct unit_test_state *uts) +{ + struct fwu_mdata *mdata = NULL; + + fwu_mdata_access_setup(uts, &mdata); + + ut_assertok(fwu_get_mdata(mdata)); + + ut_asserteq(mdata->version, 0x2);
return 0; } @@ -114,29 +130,21 @@ DM_TEST(dm_test_fwu_mdata_read, UT_TESTF_SCAN_FDT);
static int dm_test_fwu_mdata_write(struct unit_test_state *uts) { + u8 num_banks; u32 active_idx; - struct udevice *dev; - struct fwu_mdata mdata = { 0 }; - - /* - * Trigger lib/fwu_updates/fwu.c fwu_boottime_checks() - * to populate g_dev global pointer in that library. - */ - event_notify_null(EVT_MAIN_LOOP); + struct fwu_mdata *mdata = NULL;
- ut_assertok(setup_blk_device(uts)); - ut_assertok(populate_mmc_disk_image(uts)); - ut_assertok(write_mmc_blk_device(uts)); - - ut_assertok(uclass_first_device_err(UCLASS_FWU_MDATA, &dev)); + fwu_mdata_access_setup(uts, &mdata);
- ut_assertok(fwu_get_mdata(&mdata)); + ut_assertok(fwu_get_mdata(mdata)); + num_banks = mdata->fw_desc[0].num_banks; + ut_asserteq(2, num_banks);
- active_idx = (mdata.active_index + 1) % CONFIG_FWU_NUM_BANKS; + active_idx = (mdata->active_index + 1) % num_banks; ut_assertok(fwu_set_active_index(active_idx));
- ut_assertok(fwu_get_mdata(&mdata)); - ut_asserteq(mdata.active_index, active_idx); + ut_assertok(fwu_get_mdata(mdata)); + ut_asserteq(mdata->active_index, active_idx);
return 0; } diff --git a/test/dm/fwu_mdata_disk_image.h b/test/dm/fwu_mdata_disk_image.h index b9803417c8..b15b06b9de 100644 --- a/test/dm/fwu_mdata_disk_image.h +++ b/test/dm/fwu_mdata_disk_image.h @@ -6,107 +6,85 @@ */
#define FWU_MDATA_DISK_IMG { 0x00010000, { \ - {0x000001c0, "\x02\x00\xee\x02\x02\x00\x01\x00"}, /* ........ */ \ + {0x000001c0, "\x02\x00\xee\xff\xff\xff\x01\x00"}, /* ........ */ \ {0x000001c8, "\x00\x00\x7f\x00\x00\x00\x00\x00"}, /* ........ */ \ {0x000001f8, "\x00\x00\x00\x00\x00\x00\x55\xaa"}, /* ......U. */ \ {0x00000200, "\x45\x46\x49\x20\x50\x41\x52\x54"}, /* EFI PART */ \ {0x00000208, "\x00\x00\x01\x00\x5c\x00\x00\x00"}, /* ....... */ \ - {0x00000210, "\xa6\xf6\x92\x20\x00\x00\x00\x00"}, /* ... .... */ \ + {0x00000210, "\x52\x5f\x3a\xa1\x00\x00\x00\x00"}, /* R_:..... */ \ {0x00000218, "\x01\x00\x00\x00\x00\x00\x00\x00"}, /* ........ */ \ {0x00000220, "\x7f\x00\x00\x00\x00\x00\x00\x00"}, /* ........ */ \ {0x00000228, "\x22\x00\x00\x00\x00\x00\x00\x00"}, /* "....... */ \ {0x00000230, "\x5e\x00\x00\x00\x00\x00\x00\x00"}, /* ^....... */ \ - {0x00000238, "\xde\x99\xa2\x7e\x46\x34\xeb\x47"}, /* ...~F4.G */ \ - {0x00000240, "\x87\xf6\x4f\x75\xe8\xd5\x7d\xc7"}, /* ..Ou..}. */ \ + {0x00000238, "\xf5\xf3\x9d\xb9\x92\xdd\x48\x60"}, /* ......H` */ \ + {0x00000240, "\x9a\x04\xe5\x2b\x11\xcb\x42\x61"}, /* ...+..Ba */ \ {0x00000248, "\x02\x00\x00\x00\x00\x00\x00\x00"}, /* ........ */ \ {0x00000250, "\x80\x00\x00\x00\x80\x00\x00\x00"}, /* ........ */ \ - {0x00000258, "\x2a\x64\x03\x83\x00\x00\x00\x00"}, /* .d...... */ \ + {0x00000258, "\xc4\x80\x68\xad\x00\x00\x00\x00"}, /* ..h..... */ \ {0x00000400, "\xa0\x84\x7a\x8a\x87\x83\xf6\x40"}, /* ..z....@ */ \ {0x00000408, "\xab\x41\xa8\xb9\xa5\xa6\x0d\x23"}, /* .A.....# */ \ - {0x00000410, "\x3d\x6c\xb9\xaa\x20\xb2\x18\x4c"}, /* =l.. ..L */ \ - {0x00000418, "\xbc\x87\x1c\x9f\xe0\x35\x9b\x73"}, /* .....5.s */ \ + {0x00000410, "\x02\xa0\xf1\x31\xc0\x4c\x42\xd1"}, /* ...1.LB. */ \ + {0x00000418, "\xbd\x0b\xa0\xa3\xd9\xe8\x4b\x64"}, /* ......Kd */ \ {0x00000420, "\x22\x00\x00\x00\x00\x00\x00\x00"}, /* "....... */ \ - {0x00000428, "\x31\x00\x00\x00\x00\x00\x00\x00"}, /* 1....... */ \ - {0x00000438, "\x55\x00\x6e\x00\x6b\x00\x6e\x00"}, /* U.n.k.n. */ \ - {0x00000440, "\x6f\x00\x77\x00\x6e\x00\x00\x00"}, /* o.w.n... */ \ + {0x00000428, "\x23\x00\x00\x00\x00\x00\x00\x00"}, /* #....... */ \ {0x00000480, "\xa0\x84\x7a\x8a\x87\x83\xf6\x40"}, /* ..z....@ */ \ {0x00000488, "\xab\x41\xa8\xb9\xa5\xa6\x0d\x23"}, /* .A.....# */ \ - {0x00000490, "\x57\x24\xf6\xe6\x0b\x6f\x66\x4e"}, /* W$...ofN */ \ - {0x00000498, "\xb3\xd5\x99\x50\xa5\xc6\x4e\xc1"}, /* ...P..N. */ \ - {0x000004a0, "\x32\x00\x00\x00\x00\x00\x00\x00"}, /* 2....... */ \ - {0x000004a8, "\x41\x00\x00\x00\x00\x00\x00\x00"}, /* A....... */ \ - {0x000004b8, "\x55\x00\x6e\x00\x6b\x00\x6e\x00"}, /* U.n.k.n. */ \ - {0x000004c0, "\x6f\x00\x77\x00\x6e\x00\x00\x00"}, /* o.w.n... */ \ - {0x00004400, "\x4e\xd5\x3f\x43\x01\x00\x00\x00"}, /* N.?C.... */ \ + {0x00000490, "\x55\x2e\xe8\x5c\x7f\x10\x4b\xe7"}, /* U....K. */ \ + {0x00000498, "\xb1\xb8\x3a\x84\xb7\x63\x1d\xcd"}, /* ..:..c.. */ \ + {0x000004a0, "\x24\x00\x00\x00\x00\x00\x00\x00"}, /* $....... */ \ + {0x000004a8, "\x25\x00\x00\x00\x00\x00\x00\x00"}, /* %....... */ \ + {0x00004400, "\x71\x30\xcf\xf7\x02\x00\x00\x00"}, /* q0...... */ \ {0x00004408, "\x00\x00\x00\x00\x01\x00\x00\x00"}, /* ........ */ \ - {0x00004410, "\x52\xcf\xd7\x09\x20\x07\x10\x47"}, /* R... ..G */ \ - {0x00004418, "\x91\xd1\x08\x46\x9b\x7f\xe9\xc8"}, /* ...F.... */ \ - {0x00004420, "\xeb\x2b\x27\x49\xd8\x8d\xdf\x46"}, /* .+'I...F */ \ - {0x00004428, "\x8d\x75\x35\x6c\x65\xef\xf4\x17"}, /* .u5le... */ \ - {0x00004430, "\x86\x7a\x05\x10\xf1\xda\x93\x4f"}, /* .z.....O */ \ - {0x00004438, "\xba\x7f\xb1\x95\xf7\xfa\x41\x70"}, /* ......Ap */ \ - {0x00004440, "\x01\x00\x00\x00\x00\x00\x00\x00"}, /* ........ */ \ - {0x00004448, "\x3e\xed\x62\xdb\x37\x62\xb4\x4f"}, /* >.b.7b.O */ \ - {0x00004450, "\x80\xc4\x1b\x74\xd8\x46\xa8\xe7"}, /* ...t.F.. */ \ + {0x00004410, "\x78\x00\x00\x00\x20\x00\x00\x00"}, /* x... ... */ \ + {0x00004418, "\xfc\xfc\xff\xff\x00\x00\x00\x00"}, /* ........ */ \ + {0x00004420, "\x02\x00\x01\x00\x50\x00\x18\x00"}, /* ....P... */ \ + {0x00004428, "\x83\xdf\xd5\x19\xb0\x11\x7b\x45"}, /* ......{E */ \ + {0x00004430, "\xbe\x2c\x75\x59\xc1\x31\x42\xa5"}, /* .,uY.1B. */ \ + {0x00004438, "\x17\xc7\xa9\x08\x4a\xb0\x6b\x45"}, /* ....J.kE */ \ + {0x00004440, "\x8c\x82\x6f\x8e\x19\x39\xc5\x8b"}, /* ..o..9.. */ \ + {0x00004448, "\xcc\x28\x74\xd5\x9a\xbb\xe0\x42"}, /* .(t....B */ \ + {0x00004450, "\xaa\x36\x3f\x5a\x13\x20\x59\xc7"}, /* .6?Z. Y. */ \ {0x00004458, "\x01\x00\x00\x00\x00\x00\x00\x00"}, /* ........ */ \ - {0x00004460, "\xf5\x21\x70\x5a\xf2\xfe\xb4\x48"}, /* .!pZ...H */ \ - {0x00004468, "\xaa\xba\x83\x2e\x77\x74\x18\xc0"}, /* ....wt.. */ \ - {0x00004470, "\xeb\x2b\x27\x49\xd8\x8d\xdf\x46"}, /* .+'I...F */ \ - {0x00004478, "\x8d\x75\x35\x6c\x65\xef\xf4\x17"}, /* .u5le... */ \ - {0x00004480, "\x3b\x0e\xd2\x0b\x9f\xab\x86\x49"}, /* ;......I */ \ - {0x00004488, "\xb7\x90\x8d\xf3\x9c\x9c\xa3\x82"}, /* ........ */ \ - {0x00004490, "\x01\x00\x00\x00\x00\x00\x00\x00"}, /* ........ */ \ - {0x00004498, "\x6d\xe4\x25\x0e\x15\xb6\xd3\x4c"}, /* m.%....L */ \ - {0x000044a0, "\x94\xda\x51\x79\x8f\xb1\x9e\xb1"}, /* ..Qy.... */ \ - {0x000044a8, "\x01\x00\x00\x00\x00\x00\x00\x00"}, /* ........ */ \ - {0x00006400, "\x4e\xd5\x3f\x43\x01\x00\x00\x00"}, /* N.?C.... */ \ - {0x00006408, "\x00\x00\x00\x00\x01\x00\x00\x00"}, /* ........ */ \ - {0x00006410, "\x52\xcf\xd7\x09\x20\x07\x10\x47"}, /* R... ..G */ \ - {0x00006418, "\x91\xd1\x08\x46\x9b\x7f\xe9\xc8"}, /* ...F.... */ \ - {0x00006420, "\xeb\x2b\x27\x49\xd8\x8d\xdf\x46"}, /* .+'I...F */ \ - {0x00006428, "\x8d\x75\x35\x6c\x65\xef\xf4\x17"}, /* .u5le... */ \ - {0x00006430, "\x86\x7a\x05\x10\xf1\xda\x93\x4f"}, /* .z.....O */ \ - {0x00006438, "\xba\x7f\xb1\x95\xf7\xfa\x41\x70"}, /* ......Ap */ \ - {0x00006440, "\x01\x00\x00\x00\x00\x00\x00\x00"}, /* ........ */ \ - {0x00006448, "\x3e\xed\x62\xdb\x37\x62\xb4\x4f"}, /* >.b.7b.O */ \ - {0x00006450, "\x80\xc4\x1b\x74\xd8\x46\xa8\xe7"}, /* ...t.F.. */ \ - {0x00006458, "\x01\x00\x00\x00\x00\x00\x00\x00"}, /* ........ */ \ - {0x00006460, "\xf5\x21\x70\x5a\xf2\xfe\xb4\x48"}, /* .!pZ...H */ \ - {0x00006468, "\xaa\xba\x83\x2e\x77\x74\x18\xc0"}, /* ....wt.. */ \ - {0x00006470, "\xeb\x2b\x27\x49\xd8\x8d\xdf\x46"}, /* .+'I...F */ \ - {0x00006478, "\x8d\x75\x35\x6c\x65\xef\xf4\x17"}, /* .u5le... */ \ - {0x00006480, "\x3b\x0e\xd2\x0b\x9f\xab\x86\x49"}, /* ;......I */ \ - {0x00006488, "\xb7\x90\x8d\xf3\x9c\x9c\xa3\x82"}, /* ........ */ \ - {0x00006490, "\x01\x00\x00\x00\x00\x00\x00\x00"}, /* ........ */ \ - {0x00006498, "\x6d\xe4\x25\x0e\x15\xb6\xd3\x4c"}, /* m.%....L */ \ - {0x000064a0, "\x94\xda\x51\x79\x8f\xb1\x9e\xb1"}, /* ..Qy.... */ \ - {0x000064a8, "\x01\x00\x00\x00\x00\x00\x00\x00"}, /* ........ */ \ + {0x00004460, "\x6d\x7d\xe3\x2b\x81\x82\x38\x49"}, /* m}.+..8I */ \ + {0x00004468, "\xbd\x7b\x9a\x5b\xbf\x80\x86\x9f"}, /* .{.[.... */ \ + {0x00004470, "\x01\x00\x00\x00\x00\x00\x00\x00"}, /* ........ */ \ + {0x00004800, "\x71\x30\xcf\xf7\x02\x00\x00\x00"}, /* q0...... */ \ + {0x00004808, "\x00\x00\x00\x00\x01\x00\x00\x00"}, /* ........ */ \ + {0x00004810, "\x78\x00\x00\x00\x20\x00\x00\x00"}, /* x... ... */ \ + {0x00004818, "\xfc\xfc\xff\xff\x00\x00\x00\x00"}, /* ........ */ \ + {0x00004820, "\x02\x00\x01\x00\x50\x00\x18\x00"}, /* ....P... */ \ + {0x00004828, "\x83\xdf\xd5\x19\xb0\x11\x7b\x45"}, /* ......{E */ \ + {0x00004830, "\xbe\x2c\x75\x59\xc1\x31\x42\xa5"}, /* .,uY.1B. */ \ + {0x00004838, "\x17\xc7\xa9\x08\x4a\xb0\x6b\x45"}, /* ....J.kE */ \ + {0x00004840, "\x8c\x82\x6f\x8e\x19\x39\xc5\x8b"}, /* ..o..9.. */ \ + {0x00004848, "\xcc\x28\x74\xd5\x9a\xbb\xe0\x42"}, /* .(t....B */ \ + {0x00004850, "\xaa\x36\x3f\x5a\x13\x20\x59\xc7"}, /* .6?Z. Y. */ \ + {0x00004858, "\x01\x00\x00\x00\x00\x00\x00\x00"}, /* ........ */ \ + {0x00004860, "\x6d\x7d\xe3\x2b\x81\x82\x38\x49"}, /* m}.+..8I */ \ + {0x00004868, "\xbd\x7b\x9a\x5b\xbf\x80\x86\x9f"}, /* .{.[.... */ \ + {0x00004870, "\x01\x00\x00\x00\x00\x00\x00\x00"}, /* ........ */ \ {0x0000be00, "\xa0\x84\x7a\x8a\x87\x83\xf6\x40"}, /* ..z....@ */ \ {0x0000be08, "\xab\x41\xa8\xb9\xa5\xa6\x0d\x23"}, /* .A.....# */ \ - {0x0000be10, "\x3d\x6c\xb9\xaa\x20\xb2\x18\x4c"}, /* =l.. ..L */ \ - {0x0000be18, "\xbc\x87\x1c\x9f\xe0\x35\x9b\x73"}, /* .....5.s */ \ + {0x0000be10, "\x02\xa0\xf1\x31\xc0\x4c\x42\xd1"}, /* ...1.LB. */ \ + {0x0000be18, "\xbd\x0b\xa0\xa3\xd9\xe8\x4b\x64"}, /* ......Kd */ \ {0x0000be20, "\x22\x00\x00\x00\x00\x00\x00\x00"}, /* "....... */ \ - {0x0000be28, "\x31\x00\x00\x00\x00\x00\x00\x00"}, /* 1....... */ \ - {0x0000be38, "\x55\x00\x6e\x00\x6b\x00\x6e\x00"}, /* U.n.k.n. */ \ - {0x0000be40, "\x6f\x00\x77\x00\x6e\x00\x00\x00"}, /* o.w.n... */ \ + {0x0000be28, "\x23\x00\x00\x00\x00\x00\x00\x00"}, /* #....... */ \ {0x0000be80, "\xa0\x84\x7a\x8a\x87\x83\xf6\x40"}, /* ..z....@ */ \ {0x0000be88, "\xab\x41\xa8\xb9\xa5\xa6\x0d\x23"}, /* .A.....# */ \ - {0x0000be90, "\x57\x24\xf6\xe6\x0b\x6f\x66\x4e"}, /* W$...ofN */ \ - {0x0000be98, "\xb3\xd5\x99\x50\xa5\xc6\x4e\xc1"}, /* ...P..N. */ \ - {0x0000bea0, "\x32\x00\x00\x00\x00\x00\x00\x00"}, /* 2....... */ \ - {0x0000bea8, "\x41\x00\x00\x00\x00\x00\x00\x00"}, /* A....... */ \ - {0x0000beb8, "\x55\x00\x6e\x00\x6b\x00\x6e\x00"}, /* U.n.k.n. */ \ - {0x0000bec0, "\x6f\x00\x77\x00\x6e\x00\x00\x00"}, /* o.w.n... */ \ + {0x0000be90, "\x55\x2e\xe8\x5c\x7f\x10\x4b\xe7"}, /* U....K. */ \ + {0x0000be98, "\xb1\xb8\x3a\x84\xb7\x63\x1d\xcd"}, /* ..:..c.. */ \ + {0x0000bea0, "\x24\x00\x00\x00\x00\x00\x00\x00"}, /* $....... */ \ + {0x0000bea8, "\x25\x00\x00\x00\x00\x00\x00\x00"}, /* %....... */ \ {0x0000fe00, "\x45\x46\x49\x20\x50\x41\x52\x54"}, /* EFI PART */ \ {0x0000fe08, "\x00\x00\x01\x00\x5c\x00\x00\x00"}, /* ....... */ \ - {0x0000fe10, "\xa2\xce\x23\xfc\x00\x00\x00\x00"}, /* ..#..... */ \ + {0x0000fe10, "\x56\x67\x8b\x7d\x00\x00\x00\x00"}, /* Vg.}.... */ \ {0x0000fe18, "\x7f\x00\x00\x00\x00\x00\x00\x00"}, /* ........ */ \ {0x0000fe20, "\x01\x00\x00\x00\x00\x00\x00\x00"}, /* ........ */ \ {0x0000fe28, "\x22\x00\x00\x00\x00\x00\x00\x00"}, /* "....... */ \ {0x0000fe30, "\x5e\x00\x00\x00\x00\x00\x00\x00"}, /* ^....... */ \ - {0x0000fe38, "\xde\x99\xa2\x7e\x46\x34\xeb\x47"}, /* ...~F4.G */ \ - {0x0000fe40, "\x87\xf6\x4f\x75\xe8\xd5\x7d\xc7"}, /* ..Ou..}. */ \ + {0x0000fe38, "\xf5\xf3\x9d\xb9\x92\xdd\x48\x60"}, /* ......H` */ \ + {0x0000fe40, "\x9a\x04\xe5\x2b\x11\xcb\x42\x61"}, /* ...+..Ba */ \ {0x0000fe48, "\x5f\x00\x00\x00\x00\x00\x00\x00"}, /* _....... */ \ {0x0000fe50, "\x80\x00\x00\x00\x80\x00\x00\x00"}, /* ........ */ \ - {0x0000fe58, "\x2a\x64\x03\x83\x00\x00\x00\x00"}, /* .d...... */ \ + {0x0000fe58, "\xc4\x80\x68\xad\x00\x00\x00\x00"}, /* ..h..... */ \ {0, NULL} } }

With the migration to the FWU metadata version 2 structure, the values of number of banks and number of images per bank are now obtained from the metadata at runtime. Remove the now superfluous config symbols.
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org --- arch/sandbox/Kconfig | 6 ------ board/armltd/corstone1000/corstone1000.c | 2 +- lib/fwu_updates/Kconfig | 11 ----------- 3 files changed, 1 insertion(+), 18 deletions(-)
diff --git a/arch/sandbox/Kconfig b/arch/sandbox/Kconfig index 0ce77de2fc..29013a5673 100644 --- a/arch/sandbox/Kconfig +++ b/arch/sandbox/Kconfig @@ -79,9 +79,3 @@ config SYS_FDT_LOAD_ADDR See `doc/arch/sandbox.rst` for more information.
endmenu - -config FWU_NUM_BANKS - default 2 - -config FWU_NUM_IMAGES_PER_BANK - default 2 diff --git a/board/armltd/corstone1000/corstone1000.c b/board/armltd/corstone1000/corstone1000.c index 01c80aaf9d..15de738154 100644 --- a/board/armltd/corstone1000/corstone1000.c +++ b/board/armltd/corstone1000/corstone1000.c @@ -109,7 +109,7 @@ void fwu_plat_get_bootidx(uint *boot_idx) */ ret = fwu_get_active_index(boot_idx); if (ret < 0) { - *boot_idx = CONFIG_FWU_NUM_BANKS; + *boot_idx = 0; log_err("corstone1000: failed to read active index\n"); } } diff --git a/lib/fwu_updates/Kconfig b/lib/fwu_updates/Kconfig index d35247d0e5..6bb94f88d3 100644 --- a/lib/fwu_updates/Kconfig +++ b/lib/fwu_updates/Kconfig @@ -12,17 +12,6 @@ menuconfig FWU_MULTI_BANK_UPDATE
if FWU_MULTI_BANK_UPDATE
-config FWU_NUM_BANKS - int "Number of Banks defined by the platform" - help - Define the number of banks of firmware images on a platform - -config FWU_NUM_IMAGES_PER_BANK - int "Number of firmware images per bank" - help - Define the number of firmware images per bank. This value - should be the same for all the banks. - config FWU_TRIAL_STATE_CNT int "Number of times system boots in Trial State" default 3

Migrate the metadata generation tool to generate the version 2 metadata.
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org --- tools/mkfwumdata.c | 43 ++++++++++++++++++++++++++++++++----------- 1 file changed, 32 insertions(+), 11 deletions(-)
diff --git a/tools/mkfwumdata.c b/tools/mkfwumdata.c index 9732a8ddc5..b43cf38457 100644 --- a/tools/mkfwumdata.c +++ b/tools/mkfwumdata.c @@ -14,12 +14,13 @@ #include <unistd.h> #include <uuid/uuid.h>
-/* This will dynamically allocate the fwu_mdata */ -#define CONFIG_FWU_NUM_BANKS 0 -#define CONFIG_FWU_NUM_IMAGES_PER_BANK 0 - /* Since we can not include fwu.h, redefine version here. */ -#define FWU_MDATA_VERSION 1 +#define FWU_MDATA_VERSION 2 + +#define MAX_BANKS 4 + +#define BANK_INVALID 0xFF +#define BANK_ACCEPTED 0xFC
typedef uint8_t u8; typedef int16_t s16; @@ -29,8 +30,6 @@ typedef uint64_t u64;
#include <fwu_mdata.h>
-/* TODO: Endianness conversion may be required for some arch. */ - static const char *opts_short = "b:i:a:p:gh";
static struct option options[] = { @@ -48,7 +47,7 @@ static void print_usage(void) fprintf(stderr, "Usage: mkfwumdata [options] <UUIDs list> <output file>\n"); fprintf(stderr, "Options:\n" "\t-i, --images <num> Number of images (mandatory)\n" - "\t-b, --banks <num> Number of banks (mandatory)\n" + "\t-b, --banks <num> Number of banks(1-4) (mandatory)\n" "\t-a, --active-bank <num> Active bank (default=0)\n" "\t-p, --previous-bank <num> Previous active bank (default=active_bank - 1)\n" "\t-g, --guid Use GUID instead of UUID\n" @@ -85,6 +84,7 @@ static struct fwu_mdata_object *fwu_alloc_mdata(size_t images, size_t banks) return NULL;
mobj->size = sizeof(struct fwu_mdata) + + sizeof(struct fwu_fw_store_desc) + (sizeof(struct fwu_image_entry) + sizeof(struct fwu_image_bank_info) * banks) * images; mobj->images = images; @@ -105,6 +105,7 @@ fwu_get_image(struct fwu_mdata_object *mobj, size_t idx) size_t offset;
offset = sizeof(struct fwu_mdata) + + sizeof(struct fwu_fw_store_desc) + (sizeof(struct fwu_image_entry) + sizeof(struct fwu_image_bank_info) * mobj->banks) * idx;
@@ -117,6 +118,7 @@ fwu_get_bank(struct fwu_mdata_object *mobj, size_t img_idx, size_t bnk_idx) size_t offset;
offset = sizeof(struct fwu_mdata) + + sizeof(struct fwu_fw_store_desc) + (sizeof(struct fwu_image_entry) + sizeof(struct fwu_image_bank_info) * mobj->banks) * img_idx + sizeof(struct fwu_image_entry) + @@ -188,7 +190,7 @@ fwu_parse_fill_image_uuid(struct fwu_mdata_object *mobj, return -EINVAL;
if (strcmp(uuid, "0") && - uuid_guid_parse(uuid, (unsigned char *)&image->location_uuid) < 0) + uuid_guid_parse(uuid, (unsigned char *)&image->location_guid) < 0) return -EINVAL;
/* Image type UUID */ @@ -196,7 +198,7 @@ fwu_parse_fill_image_uuid(struct fwu_mdata_object *mobj, if (!uuid) return -EINVAL;
- if (uuid_guid_parse(uuid, (unsigned char *)&image->image_type_uuid) < 0) + if (uuid_guid_parse(uuid, (unsigned char *)&image->image_type_guid) < 0) return -EINVAL;
/* Fill bank image-UUID */ @@ -210,7 +212,7 @@ fwu_parse_fill_image_uuid(struct fwu_mdata_object *mobj, return -EINVAL;
if (strcmp(uuid, "0") && - uuid_guid_parse(uuid, (unsigned char *)&bank->image_uuid) < 0) + uuid_guid_parse(uuid, (unsigned char *)&bank->image_guid) < 0) return -EINVAL; } return 0; @@ -225,6 +227,19 @@ static int fwu_parse_fill_uuids(struct fwu_mdata_object *mobj, char *uuids[]) mdata->version = FWU_MDATA_VERSION; mdata->active_index = active_bank; mdata->previous_active_index = previous_bank; + mdata->metadata_size = mobj->size; + mdata->desc_offset = sizeof(struct fwu_mdata); + + for (i = 0; i < MAX_BANKS; i++) + mdata->bank_state[i] = i < mobj->banks ? + BANK_ACCEPTED : BANK_INVALID; + + mdata->fw_desc[0].num_banks = mobj->banks; + mdata->fw_desc[0].num_images = mobj->images; + mdata->fw_desc[0].img_entry_size = sizeof(struct fwu_image_entry) + + (sizeof(struct fwu_image_bank_info) * mobj->banks); + mdata->fw_desc[0].bank_info_entry_size = + sizeof(struct fwu_image_bank_info);
for (i = 0; i < mobj->images; i++) { ret = fwu_parse_fill_image_uuid(mobj, i, uuids[i]); @@ -313,6 +328,12 @@ int main(int argc, char *argv[]) return -EINVAL; }
+ if (banks > MAX_BANKS) { + fprintf(stderr, "Error: The number of banks must not be more than %u.\n", + MAX_BANKS); + return -EINVAL; + } + /* This command takes UUIDs * images and output file. */ if (optind + images + 1 != argc) { fprintf(stderr, "Error: UUID list or output file is not specified or too much.\n");

Now that the migration to the FWU metadata version 2 is complete, the feature can be re-enabled on platforms which had it enabled.
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org --- configs/corstone1000_defconfig | 2 ++ configs/sandbox64_defconfig | 1 + configs/synquacer_developerbox_defconfig | 3 +++ 3 files changed, 6 insertions(+)
diff --git a/configs/corstone1000_defconfig b/configs/corstone1000_defconfig index 24b7984959..e45415b90c 100644 --- a/configs/corstone1000_defconfig +++ b/configs/corstone1000_defconfig @@ -25,6 +25,7 @@ CONFIG_BOARD_LATE_INIT=y CONFIG_SYS_PROMPT="corstone1000# " CONFIG_SYS_MAXARGS=64 # CONFIG_CMD_CONSOLE is not set +CONFIG_CMD_FWU_METADATA=y CONFIG_CMD_BOOTZ=y # CONFIG_CMD_XIMG is not set CONFIG_CMD_GPT=y @@ -66,3 +67,4 @@ CONFIG_FFA_SHARED_MM_BUF_OFFSET=0 CONFIG_FFA_SHARED_MM_BUF_ADDR=0x02000000 CONFIG_EFI_CAPSULE_ON_DISK=y CONFIG_EFI_IGNORE_OSINDICATIONS=y +CONFIG_FWU_MULTI_BANK_UPDATE=y diff --git a/configs/sandbox64_defconfig b/configs/sandbox64_defconfig index 7b5888af38..996bb7aa4f 100644 --- a/configs/sandbox64_defconfig +++ b/configs/sandbox64_defconfig @@ -274,6 +274,7 @@ CONFIG_EFI_CAPSULE_ON_DISK=y CONFIG_EFI_CAPSULE_FIRMWARE_RAW=y CONFIG_EFI_SECURE_BOOT=y CONFIG_TEST_FDTDEC=y +CONFIG_FWU_MULTI_BANK_UPDATE=y CONFIG_UNIT_TEST=y CONFIG_UT_TIME=y CONFIG_UT_DM=y diff --git a/configs/synquacer_developerbox_defconfig b/configs/synquacer_developerbox_defconfig index 616d410074..1bb55be0a7 100644 --- a/configs/synquacer_developerbox_defconfig +++ b/configs/synquacer_developerbox_defconfig @@ -17,6 +17,7 @@ CONFIG_SYS_BOOTM_LEN=0x800000 CONFIG_BOOTSTAGE_STASH_SIZE=4096 CONFIG_HUSH_PARSER=y CONFIG_SYS_MAXARGS=128 +CONFIG_CMD_FWU_METADATA=y CONFIG_CMD_IMLS=y CONFIG_CMD_ERASEENV=y CONFIG_CMD_NVEDIT_EFI=y @@ -51,6 +52,7 @@ CONFIG_DFU_TFTP=y CONFIG_DFU_MTD=y CONFIG_DFU_RAM=y CONFIG_DFU_SF=y +CONFIG_FWU_MDATA_MTD=y CONFIG_DM_I2C=y CONFIG_SYS_I2C_SYNQUACER=y CONFIG_MMC_SDHCI=y @@ -93,3 +95,4 @@ CONFIG_EFI_RUNTIME_UPDATE_CAPSULE=y CONFIG_EFI_CAPSULE_ON_DISK=y CONFIG_EFI_IGNORE_OSINDICATIONS=y CONFIG_EFI_CAPSULE_FIRMWARE_RAW=y +CONFIG_FWU_MULTI_BANK_UPDATE=y

Make changes to the FWU documentation to reflect the changes made with migration of the FWU metadata to version 2.
Signed-off-by: Sughosh Ganu sughosh.ganu@linaro.org --- doc/board/socionext/developerbox.rst | 9 +++------ doc/develop/uefi/fwu_updates.rst | 12 +++++------- doc/usage/cmd/fwu_mdata.rst | 12 ++++++++---- 3 files changed, 16 insertions(+), 17 deletions(-)
diff --git a/doc/board/socionext/developerbox.rst b/doc/board/socionext/developerbox.rst index 46712c379b..d8c1bb4986 100644 --- a/doc/board/socionext/developerbox.rst +++ b/doc/board/socionext/developerbox.rst @@ -113,8 +113,6 @@ configs/synquacer_developerbox_defconfig enables default FWU configuration :: CONFIG_FWU_MULTI_BANK_UPDATE=y CONFIG_FWU_MDATA=y CONFIG_FWU_MDATA_MTD=y - CONFIG_FWU_NUM_BANKS=2 - CONFIG_FWU_NUM_IMAGES_PER_BANK=1 CONFIG_CMD_FWU_METADATA=y
And build it:: @@ -126,10 +124,9 @@ And build it:: make -j `noproc` cd ../
-By default, the CONFIG_FWU_NUM_BANKS and CONFIG_FWU_NUM_IMAGES_PER_BANKS are -set to 2 and 1 respectively. This uses FIP (Firmware Image Package) type image -which contains TF-A, U-Boot and OP-TEE (the OP-TEE is optional). -You can use fiptool to compose the FIP image from those firmware images. +This uses FIP (Firmware Image Package) type image which contains TF-A, +U-Boot and OP-TEE (the OP-TEE is optional). You can use fiptool to +compose the FIP image from those firmware images.
Rebuild SCP firmware -------------------- diff --git a/doc/develop/uefi/fwu_updates.rst b/doc/develop/uefi/fwu_updates.rst index e4709d82b4..7911c954d9 100644 --- a/doc/develop/uefi/fwu_updates.rst +++ b/doc/develop/uefi/fwu_updates.rst @@ -43,8 +43,6 @@ The feature can be enabled by specifying the following configs:: CONFIG_FWU_MULTI_BANK_UPDATE=y CONFIG_FWU_MDATA=y CONFIG_FWU_MDATA_GPT_BLK=y - CONFIG_FWU_NUM_BANKS=<val> - CONFIG_FWU_NUM_IMAGES_PER_BANK=<val>
in the .config file
@@ -94,12 +92,12 @@ of. Each GPT partition entry in the GPT header has two GUIDs:: * UniquePartitionGUID
The PartitionTypeGUID value should correspond to the -``image_type_uuid`` field of the FWU metadata. This field is used to +``image_type_guid`` field of the FWU metadata. This field is used to identify a given type of updatable firmware image, e.g. U-Boot, OP-TEE, FIP etc. This GUID should also be used for specifying the `--guid` parameter when generating the capsule.
-The UniquePartitionGUID value should correspond to the ``image_uuid`` +The UniquePartitionGUID value should correspond to the ``image_guid`` field in the FWU metadata. This GUID is used to identify images of a given image type in different banks.
@@ -108,8 +106,8 @@ metadata partitions. This would be the PartitionTypeGUID for the metadata partitions. Similarly, the UEFI specification defines the ESP GUID to be be used.
-When generating the metadata, the ``image_type_uuid`` and the -``image_uuid`` values should match the *PartitionTypeGUID* and the +When generating the metadata, the ``image_type_guid`` and the +``image_guid`` values should match the *PartitionTypeGUID* and the *UniquePartitionGUID* values respectively.
Performing the Update @@ -181,5 +179,5 @@ empty capsule would be:: Links -----
-* [1] https://developer.arm.com/documentation/den0118/a/ - FWU Specification +* [1] https://developer.arm.com/documentation/den0118/ - FWU Specification * [2] https://git.codelinaro.org/linaro/dependable-boot/mbfw/uploads/6f7ddfe3be24e... - Dependable Boot Specification diff --git a/doc/usage/cmd/fwu_mdata.rst b/doc/usage/cmd/fwu_mdata.rst index f1bf08fde1..1804422b33 100644 --- a/doc/usage/cmd/fwu_mdata.rst +++ b/doc/usage/cmd/fwu_mdata.rst @@ -26,10 +26,14 @@ The output may look like:
=> fwu_mdata_read FWU Metadata - crc32: 0xec4fb997 - version: 0x1 - active_index: 0x0 - previous_active_index: 0x1 + crc32: 0x13c330 + version: 0x2 + active_index: 0x1 + previous_active_index: 0x0 + bank_state[0]: 0xfc + bank_state[1]: 0xfc + bank_state[2]: 0xff + bank_state[3]: 0xff Image Info
Image Type Guid: 19D5DF83-11B0-457B-BE2C-7559C13142A5

Hi Sughosh,
On Mon, Jan 22, 2024 at 05:24:21PM +0530, Sughosh Ganu wrote:
The following patches migrate the FWU metadata access code to version 2 of the structure. This is based on the structure definition as defined in the latest rev of the FWU Multi Bank Update specification [1].
Since the version 1 of the structure has currently been adopted on a couple of platforms, it was decided to have a clean migration of the metadata to version 2 only, instead of supporting both the versions of the structure. Also, based on consultations with the main author of the specification, it is expected that any further changes in the structure would be minor tweaks, and not be significant. Hence a migration to version 2.
I think this makes sense. We've already verified Socionext doesn't mind dropping v1 support. If some from ST doesn't have objections, only supporting v2 will simplify the code a lot.
Thanks /Ilias
Similar migration is also being done in TF-A, including migrating the ST platform port to support version 2 of the metadata structure [2].
The patches have been tested on STM32MP1 DK2 board and the Synquacer board from Socionext. This covers testing both the GPT and the MTD partitioned storage devices for the metadata access.
[1] - https://developer.arm.com/documentation/den0118/latest/ [2] - https://review.trustedfirmware.org/q/topic:%22topics/fwu_metadata_v2_migrati...
Sughosh Ganu (18): configs: fwu: Remove FWU configs for metadata V2 migration fwu: metadata: Migrate to version 2 of the structure drivers: fwu: Add the size parameter to the metadata access API's fwu: Add some API's for metadata version 2 access lib: fwu: Make changes to support version 2 of FWU metadata drivers: fwu: mtd: Allocate buffer for image info dynamically drivers: fwu: Allocate memory for metadata copies fwu: Add a function to put a bank in Trial State capsule: Accept a bank on a successful update fwu: mtd: Modify the DFU API's to align with metadata version 2 efi_firmware: fwu: Do not read FWU metadata on sandbox efi_firmware: fwu: Get the number of FWU banks at runtime cmd: fwu: Align the command with metadata version 2 test: fwu: Align the FWU metadata access test with version 2 fwu: Remove the config symbols for number of banks and images tools: mkfwumdata: Migrate to metadata version 2 configs: fwu: Re-enable FWU configs doc: fwu: Make changes for supporting FWU Metadata version 2
arch/sandbox/Kconfig | 6 - board/armltd/corstone1000/corstone1000.c | 2 +- cmd/fwu_mdata.c | 43 +++- configs/synquacer_developerbox_defconfig | 1 - doc/board/socionext/developerbox.rst | 9 +- doc/develop/uefi/fwu_updates.rst | 12 +- doc/usage/cmd/fwu_mdata.rst | 12 +- drivers/fwu-mdata/fwu-mdata-uclass.c | 10 +- drivers/fwu-mdata/gpt_blk.c | 27 +- drivers/fwu-mdata/raw_mtd.c | 85 ++++--- include/fwu.h | 94 ++++++- include/fwu_mdata.h | 56 +++-- lib/efi_loader/efi_capsule.c | 12 +- lib/efi_loader/efi_firmware.c | 20 +- lib/fwu_updates/Kconfig | 11 - lib/fwu_updates/fwu.c | 308 ++++++++++++++++++----- lib/fwu_updates/fwu_mtd.c | 76 ++++-- test/dm/fwu_mdata.c | 56 +++-- test/dm/fwu_mdata_disk_image.h | 124 ++++----- tools/mkfwumdata.c | 43 +++- 20 files changed, 705 insertions(+), 302 deletions(-)
-- 2.34.1

Hi Sughosh,
po 22. 1. 2024 v 12:55 odesÃlatel Sughosh Ganu sughosh.ganu@linaro.org napsal:
The following patches migrate the FWU metadata access code to version 2 of the structure. This is based on the structure definition as defined in the latest rev of the FWU Multi Bank Update specification [1].
Since the version 1 of the structure has currently been adopted on a couple of platforms, it was decided to have a clean migration of the metadata to version 2 only, instead of supporting both the versions of the structure. Also, based on consultations with the main author of the specification, it is expected that any further changes in the structure would be minor tweaks, and not be significant. Hence a migration to version 2.
Similar migration is also being done in TF-A, including migrating the ST platform port to support version 2 of the metadata structure [2].
The patches have been tested on STM32MP1 DK2 board and the Synquacer board from Socionext. This covers testing both the GPT and the MTD partitioned storage devices for the metadata access.
[1] - https://developer.arm.com/documentation/den0118/latest/ [2] - https://review.trustedfirmware.org/q/topic:%22topics/fwu_metadata_v2_migrati...
Sughosh Ganu (18): configs: fwu: Remove FWU configs for metadata V2 migration fwu: metadata: Migrate to version 2 of the structure drivers: fwu: Add the size parameter to the metadata access API's fwu: Add some API's for metadata version 2 access lib: fwu: Make changes to support version 2 of FWU metadata drivers: fwu: mtd: Allocate buffer for image info dynamically drivers: fwu: Allocate memory for metadata copies fwu: Add a function to put a bank in Trial State capsule: Accept a bank on a successful update fwu: mtd: Modify the DFU API's to align with metadata version 2 efi_firmware: fwu: Do not read FWU metadata on sandbox efi_firmware: fwu: Get the number of FWU banks at runtime cmd: fwu: Align the command with metadata version 2 test: fwu: Align the FWU metadata access test with version 2 fwu: Remove the config symbols for number of banks and images tools: mkfwumdata: Migrate to metadata version 2 configs: fwu: Re-enable FWU configs doc: fwu: Make changes for supporting FWU Metadata version 2
arch/sandbox/Kconfig | 6 - board/armltd/corstone1000/corstone1000.c | 2 +- cmd/fwu_mdata.c | 43 +++- configs/synquacer_developerbox_defconfig | 1 - doc/board/socionext/developerbox.rst | 9 +- doc/develop/uefi/fwu_updates.rst | 12 +- doc/usage/cmd/fwu_mdata.rst | 12 +- drivers/fwu-mdata/fwu-mdata-uclass.c | 10 +- drivers/fwu-mdata/gpt_blk.c | 27 +- drivers/fwu-mdata/raw_mtd.c | 85 ++++--- include/fwu.h | 94 ++++++- include/fwu_mdata.h | 56 +++-- lib/efi_loader/efi_capsule.c | 12 +- lib/efi_loader/efi_firmware.c | 20 +- lib/fwu_updates/Kconfig | 11 - lib/fwu_updates/fwu.c | 308 ++++++++++++++++++----- lib/fwu_updates/fwu_mtd.c | 76 ++++-- test/dm/fwu_mdata.c | 56 +++-- test/dm/fwu_mdata_disk_image.h | 124 ++++----- tools/mkfwumdata.c | 43 +++- 20 files changed, 705 insertions(+), 302 deletions(-)
Thanks for this work. I have tested it on kv260 and I see an issue with 2 image per location configuration. When I build mdata v2 with: ./tools/mkfwumdata -a 0 -i 2 -b 2 588aced7-2cce-ed11-81cd-d324e93ac223,e86660de-5602-ad4f-8238-e406e274c4cf,48054af6-ce2c-11ed-8f66-7bc4531cfe6b,4b819c3e-ce2c-11ed-bec8-23de4c6d2cf2 588aced7-2cce-ed11-81cd-d324e93ac223,d4cf9ecf-8b93-c541-8551-1f883ab7dc18,fb04da52-0e9d-11ee-a57f-637805837c3f,07609246-0e9e-11ee-a23a-a38980b779a1 mdata.bin
fwu command is showing up configuration for the second image
Image Type Guid: DE6066E8-0256-4FAD-8238-E406E274C4CF Location Guid: D7CE8A58-CE2C-11ED-81CD-D324E93AC223 Image Guid: F64A0548-2CCE-ED11-8F66-7BC4531CFE6B Image Acceptance: yes Image Guid: 3E9C814B-2CCE-ED11-BEC8-23DE4C6D2CF2 Image Acceptance: yes
Image Type Guid: F64A0548-2CCE-ED11-8F66-7BC4531CFE6B Location Guid: 00000001-0000-0000-4B81-9C3ECE2C11ED Image Guid: DE23C8BE-6D4C-F22C-0100-000000000000 Image Acceptance: no Image Guid: 881F5185-B73A-18DC-588A-CED72CCEED11 Image Acceptance: no
but it should be (from mdata v1) Image Type Guid: DE6066E8-0256-4FAD-8238-E406E274C4CF Location Guid: D7CE8A58-CE2C-11ED-81CD-D324E93AC223 Image Guid: F64A0548-2CCE-ED11-8F66-7BC4531CFE6B Image Acceptance: yes Image Guid: 3E9C814B-2CCE-ED11-BEC8-23DE4C6D2CF2 Image Acceptance: yes
Image Type Guid: CF9ECFD4-938B-41C5-8551-1F883AB7DC18 Location Guid: D7CE8A58-CE2C-11ED-81CD-D324E93AC223 Image Guid: 52DA04FB-9D0E-EE11-A57F-637805837C3F Image Acceptance: yes Image Guid: 46926007-9E0E-EE11-A23A-A38980B779A1 Image Acceptance: yes
And I think the issue is not with mdata v2 generation but it is with decoding inside u-boot. Which ends up in a situation that dfu_alt_info for 2 images is not generated properly.
Thanks, Michal

hi Michal,
On Fri, 26 Jan 2024 at 20:40, Michal Simek monstr@monstr.eu wrote:
Hi Sughosh,
po 22. 1. 2024 v 12:55 odesÃlatel Sughosh Ganu sughosh.ganu@linaro.org napsal:
The following patches migrate the FWU metadata access code to version 2 of the structure. This is based on the structure definition as defined in the latest rev of the FWU Multi Bank Update specification [1].
Since the version 1 of the structure has currently been adopted on a couple of platforms, it was decided to have a clean migration of the metadata to version 2 only, instead of supporting both the versions of the structure. Also, based on consultations with the main author of the specification, it is expected that any further changes in the structure would be minor tweaks, and not be significant. Hence a migration to version 2.
Similar migration is also being done in TF-A, including migrating the ST platform port to support version 2 of the metadata structure [2].
The patches have been tested on STM32MP1 DK2 board and the Synquacer board from Socionext. This covers testing both the GPT and the MTD partitioned storage devices for the metadata access.
[1] - https://developer.arm.com/documentation/den0118/latest/ [2] - https://review.trustedfirmware.org/q/topic:%22topics/fwu_metadata_v2_migrati...
Sughosh Ganu (18): configs: fwu: Remove FWU configs for metadata V2 migration fwu: metadata: Migrate to version 2 of the structure drivers: fwu: Add the size parameter to the metadata access API's fwu: Add some API's for metadata version 2 access lib: fwu: Make changes to support version 2 of FWU metadata drivers: fwu: mtd: Allocate buffer for image info dynamically drivers: fwu: Allocate memory for metadata copies fwu: Add a function to put a bank in Trial State capsule: Accept a bank on a successful update fwu: mtd: Modify the DFU API's to align with metadata version 2 efi_firmware: fwu: Do not read FWU metadata on sandbox efi_firmware: fwu: Get the number of FWU banks at runtime cmd: fwu: Align the command with metadata version 2 test: fwu: Align the FWU metadata access test with version 2 fwu: Remove the config symbols for number of banks and images tools: mkfwumdata: Migrate to metadata version 2 configs: fwu: Re-enable FWU configs doc: fwu: Make changes for supporting FWU Metadata version 2
arch/sandbox/Kconfig | 6 - board/armltd/corstone1000/corstone1000.c | 2 +- cmd/fwu_mdata.c | 43 +++- configs/synquacer_developerbox_defconfig | 1 - doc/board/socionext/developerbox.rst | 9 +- doc/develop/uefi/fwu_updates.rst | 12 +- doc/usage/cmd/fwu_mdata.rst | 12 +- drivers/fwu-mdata/fwu-mdata-uclass.c | 10 +- drivers/fwu-mdata/gpt_blk.c | 27 +- drivers/fwu-mdata/raw_mtd.c | 85 ++++--- include/fwu.h | 94 ++++++- include/fwu_mdata.h | 56 +++-- lib/efi_loader/efi_capsule.c | 12 +- lib/efi_loader/efi_firmware.c | 20 +- lib/fwu_updates/Kconfig | 11 - lib/fwu_updates/fwu.c | 308 ++++++++++++++++++----- lib/fwu_updates/fwu_mtd.c | 76 ++++-- test/dm/fwu_mdata.c | 56 +++-- test/dm/fwu_mdata_disk_image.h | 124 ++++----- tools/mkfwumdata.c | 43 +++- 20 files changed, 705 insertions(+), 302 deletions(-)
Thanks for this work. I have tested it on kv260 and I see an issue with 2 image per location configuration. When I build mdata v2 with: ./tools/mkfwumdata -a 0 -i 2 -b 2 588aced7-2cce-ed11-81cd-d324e93ac223,e86660de-5602-ad4f-8238-e406e274c4cf,48054af6-ce2c-11ed-8f66-7bc4531cfe6b,4b819c3e-ce2c-11ed-bec8-23de4c6d2cf2 588aced7-2cce-ed11-81cd-d324e93ac223,d4cf9ecf-8b93-c541-8551-1f883ab7dc18,fb04da52-0e9d-11ee-a57f-637805837c3f,07609246-0e9e-11ee-a23a-a38980b779a1 mdata.bin
fwu command is showing up configuration for the second image
Image Type Guid: DE6066E8-0256-4FAD-8238-E406E274C4CF Location Guid: D7CE8A58-CE2C-11ED-81CD-D324E93AC223 Image Guid: F64A0548-2CCE-ED11-8F66-7BC4531CFE6B Image Acceptance: yes Image Guid: 3E9C814B-2CCE-ED11-BEC8-23DE4C6D2CF2 Image Acceptance: yes
Image Type Guid: F64A0548-2CCE-ED11-8F66-7BC4531CFE6B Location Guid: 00000001-0000-0000-4B81-9C3ECE2C11ED Image Guid: DE23C8BE-6D4C-F22C-0100-000000000000 Image Acceptance: no Image Guid: 881F5185-B73A-18DC-588A-CED72CCEED11 Image Acceptance: no
but it should be (from mdata v1) Image Type Guid: DE6066E8-0256-4FAD-8238-E406E274C4CF Location Guid: D7CE8A58-CE2C-11ED-81CD-D324E93AC223 Image Guid: F64A0548-2CCE-ED11-8F66-7BC4531CFE6B Image Acceptance: yes Image Guid: 3E9C814B-2CCE-ED11-BEC8-23DE4C6D2CF2 Image Acceptance: yes
Image Type Guid: CF9ECFD4-938B-41C5-8551-1F883AB7DC18 Location Guid: D7CE8A58-CE2C-11ED-81CD-D324E93AC223 Image Guid: 52DA04FB-9D0E-EE11-A57F-637805837C3F Image Acceptance: yes Image Guid: 46926007-9E0E-EE11-A23A-A38980B779A1 Image Acceptance: yes
And I think the issue is not with mdata v2 generation but it is with decoding inside u-boot. Which ends up in a situation that dfu_alt_info for 2 images is not generated properly.
Thanks for trying this out. I will try to replicate the same setup on my end and triage this.
-sughosh
participants (3)
-
Ilias Apalodimas
-
Michal Simek
-
Sughosh Ganu