From 3794f9f94a9363d618ed9bad4ba22b0a37b5bea2 Mon Sep 17 00:00:00 2001 From: Sergii Dmytruk Date: Mon, 23 Sep 2024 21:10:57 +0300 Subject: [PATCH] drivers/efi/capsules.c: fix recording capsule size As mentioned in comments on CB:83422, size of the current data block (which is also the last block of a capsule) was incorrectly used in place of the capsule size: - when publishing a capsule in CBMEM (this worked in practice because CapsuleApp.efi allocates a continuous physical memory) - when aligning target address (which could move output pointer past previously allocated buffer by up to 7 bytes per capsule block) Change-Id: I97a528e2611fcd711c555d0f01e9aadcd2031217 Signed-off-by: Sergii Dmytruk Reviewed-on: https://review.coreboot.org/c/coreboot/+/84542 Reviewed-by: Nico Huber Tested-by: build bot (Jenkins) --- src/drivers/efi/capsules.c | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/src/drivers/efi/capsules.c b/src/drivers/efi/capsules.c index 38178c618e..e8078bbd48 100644 --- a/src/drivers/efi/capsules.c +++ b/src/drivers/efi/capsules.c @@ -596,6 +596,7 @@ static void coalesce_capsules(struct block_descr block_chain, uint8_t *target) { struct block_descr block = block_chain; uint8_t *capsule_start = NULL; + uint32_t capsule_size = 0; uint32_t size_left = 0; /* No safety checks in this function, as all of them were done earlier. */ @@ -610,8 +611,10 @@ static void coalesce_capsules(struct block_descr block_chain, uint8_t *target) if (size_left == 0) { const EFI_CAPSULE_HEADER *capsule_hdr = map_range(block.addr, sizeof(*capsule_hdr)); - size_left = capsule_hdr->CapsuleImageSize; + capsule_size = capsule_hdr->CapsuleImageSize; capsule_start = target; + + size_left = capsule_size; } uint64_t addr = block.addr; @@ -641,13 +644,14 @@ static void coalesce_capsules(struct block_descr block_chain, uint8_t *target) } uefi_capsules[uefi_capsule_count].base = (uintptr_t)capsule_start; - uefi_capsules[uefi_capsule_count].len = block.len; + uefi_capsules[uefi_capsule_count].len = capsule_size; uefi_capsule_count++; /* This is to align start of the next capsule (assumes that initial value of target was suitably aligned). */ - if (!IS_ALIGNED(block.len, CAPSULE_ALIGNMENT)) - target += ALIGN_UP(block.len, CAPSULE_ALIGNMENT) - block.len; + if (!IS_ALIGNED(capsule_size, CAPSULE_ALIGNMENT)) + target += ALIGN_UP(capsule_size, CAPSULE_ALIGNMENT) - + capsule_size; } }