diff options
| author | João Paulo Rechi Vita <jprvita@endlessos.org> | 2019-02-15 15:55:53 -0800 |
|---|---|---|
| committer | Peter Jones <pjones@redhat.com> | 2021-09-03 16:51:19 -0400 |
| commit | 77648c5c01c79a330075824ff695ecd185514edc (patch) | |
| tree | cea3df352296b7e29ef5a08d7551de1bfa37ef0d | |
| parent | 437caecbab16b1f17bda9ee10115a0c5d7317a1d (diff) | |
| download | efi-boot-shim-77648c5c01c79a330075824ff695ecd185514edc.tar.gz efi-boot-shim-77648c5c01c79a330075824ff695ecd185514edc.zip | |
fallback: Use a dynamic buffer when list var names
Now that we are iterating over all EFI variables to look for duplicate
boot entries, we should use a dynamic buffer, so if the firmware tells
us the buffer is too small for the next variable name we can re-allocate
it to a big enough size.
Signed-off-by: João Paulo Rechi Vita <jprvita@endlessos.org>
| -rw-r--r-- | fallback.c | 22 |
1 files changed, 17 insertions, 5 deletions
@@ -415,9 +415,12 @@ find_boot_option(EFI_DEVICE_PATH *dp, EFI_DEVICE_PATH *fulldp, cursor += DevicePathSize(dp); StrCpy((CHAR16 *)cursor, arguments); - CHAR16 varname[256]; EFI_STATUS efi_status; EFI_GUID vendor_guid = NullGuid; + UINTN buffer_size = 256 * sizeof(CHAR16); + CHAR16 *varname = AllocateZeroPool(buffer_size); + if (!varname) + return EFI_OUT_OF_RESOURCES; UINTN max_candidate_size = calc_masked_boot_option_size(size); CHAR8 *candidate = AllocateZeroPool(max_candidate_size); @@ -426,14 +429,22 @@ find_boot_option(EFI_DEVICE_PATH *dp, EFI_DEVICE_PATH *fulldp, return EFI_OUT_OF_RESOURCES; } - varname[0] = 0; while (1) { - UINTN varname_size = sizeof(varname); + UINTN varname_size = buffer_size; efi_status = gRT->GetNextVariableName(&varname_size, varname, &vendor_guid); if (EFI_ERROR(efi_status)) { - if (efi_status == EFI_BUFFER_TOO_SMALL) - VerbosePrint(L"Buffer too small for next variable name\n"); + if (efi_status == EFI_BUFFER_TOO_SMALL) { + VerbosePrint(L"Buffer too small for next variable name, re-allocating it to be %d bytes and retrying\n", + varname_size); + varname = ReallocatePool(varname, + buffer_size, + varname_size); + if (!varname) + return EFI_OUT_OF_RESOURCES; + buffer_size = varname_size; + continue; + } if (efi_status == EFI_DEVICE_ERROR) VerbosePrint(L"The next variable name could not be retrieved due to a hardware error\n"); @@ -487,6 +498,7 @@ find_boot_option(EFI_DEVICE_PATH *dp, EFI_DEVICE_PATH *fulldp, } FreePool(candidate); FreePool(data); + FreePool(varname); return efi_status; } |
