This is a resend of the series posted on 22 October, now with the patches inline: the first posting carried them as attachments, which b4 and Patchwork cannot use. The patches are unchanged and still apply to main.
The capsule update code takes several lengths and offsets from a capsule and uses them without checking them against the size of the capsule. On the capsule on disk path this happens before the image is authenticated, so a capsule file in \EFI\UpdateCapsule on the ESP makes U-Boot read outside the capsule buffer the next time capsule on disk runs, even where CONFIG_EFI_CAPSULE_AUTHENTICATE rejects the capsule afterwards. Patches 1-4 check the capsule file size, the capsule header size, the FMP capsule layout (header, item offset list, item offsets, image and vendor code sizes) and the certificate length of an image, each against the size of the capsule. Patch 5 checks the FMP payload header size; with CONFIG_EFI_CAPSULE_AUTHENTICATE that header is part of the signed image, so there it is hardening. Patch 6 adds unit tests for the FMP and certificate checks: without patches 1-5 four of them fail and the certificate one ends in the crash described below; with them all five pass, as does the rest of "ut lib". The capsule file check, the FWU accept capsule and the FMP payload header have no unit test, as they need a file system, FWU or a signed capsule. I checked patches 1-4 on sandbox_defconfig with CONFIG_VALGRIND instead, by placing malformed capsule files in \EFI\UpdateCapsule and running "efidebug capsule disk-update". Without the series valgrind reports reads past the capsule buffer in efi_capsule_read_file(), efi_capsule_update_firmware() and efi_parse_pkcs7_header(), and a capsule ending inside its FMP header is reported as applied; with the series each one is rejected and none of those reads remains. On that MbedTLS build a malformed certificate of valid length still crashes sandbox in efi_signature_verify(), with or without this series: pkcs7_parse_message() returns ERR_PTR() of an MbedTLS error code, which IS_ERR() does not catch. Vsevolod Kozlov's "lib/mbedtls: Do not use ERR_PTR with mbedTLS error values" fixes that. Ana Bobillo (6): efi_loader: capsule: check the size of a capsule file efi_loader: capsule: check the capsule header size efi_loader: capsule: check the FMP capsule against its size efi_loader: capsule: check the certificate length of an image efi_loader: firmware: check the FMP payload header size test: lib: add tests for the capsule size checks lib/efi_loader/efi_capsule.c | 63 ++++++++--- lib/efi_loader/efi_firmware.c | 20 +++- test/lib/Makefile | 1 + test/lib/efi_capsule.c | 193 ++++++++++++++++++++++++++++++++++ 4 files changed, 259 insertions(+), 18 deletions(-) create mode 100644 test/lib/efi_capsule.c base-commit: acc808479730e13e74199119eb9b2b9113999244
