diff options
author | Tom Rini <trini@konsulko.com> | 2019-06-05 15:53:18 -0400 |
---|---|---|
committer | Tom Rini <trini@konsulko.com> | 2019-06-05 15:53:18 -0400 |
commit | dbbb1c43f26cb28b64df80b72fffbaf2801e8a30 (patch) | |
tree | 6f60c48458e4fb975b0e602cff637c2e65a270cf /lib/efi_loader/efi_boottime.c | |
parent | 2253e40caef5b45bcae2ccdb238f9cf037eefc0b (diff) | |
parent | 4b27a761321fd17536e02644d0ec0373150eb570 (diff) |
Merge tag 'efi-2019-07-rc4-2' of git://git.denx.de/u-boot-efi
Pull request for UEFI sub-system for v2019.07-rc4-2
Support for managing the non-volatile attribute of UEFI variables
is added though we do not have a backend for persistence yet.
Error messages for changes of UEFI variables are provided.
UEFI boottime service implementations are corrected.
Diffstat (limited to 'lib/efi_loader/efi_boottime.c')
-rw-r--r-- | lib/efi_loader/efi_boottime.c | 55 |
1 files changed, 50 insertions, 5 deletions
diff --git a/lib/efi_loader/efi_boottime.c b/lib/efi_loader/efi_boottime.c index 5c6bc691a5..7d1d6e9213 100644 --- a/lib/efi_loader/efi_boottime.c +++ b/lib/efi_loader/efi_boottime.c @@ -1153,11 +1153,15 @@ static efi_status_t efi_get_drivers(efi_handle_t handle, ++count; } } + *number_of_drivers = 0; + if (!count) { + *driver_handle_buffer = NULL; + return EFI_SUCCESS; + } /* * Create buffer. In case of duplicate driver assignments the buffer * will be too large. But that does not harm. */ - *number_of_drivers = 0; *driver_handle_buffer = calloc(count, sizeof(efi_handle_t)); if (!*driver_handle_buffer) return EFI_OUT_OF_RESOURCES; @@ -1213,7 +1217,8 @@ static efi_status_t efi_disconnect_all_drivers &driver_handle_buffer); if (ret != EFI_SUCCESS) return ret; - + if (!number_of_drivers) + return EFI_SUCCESS; ret = EFI_NOT_FOUND; while (number_of_drivers) { r = EFI_CALL(efi_disconnect_controller( @@ -1985,8 +1990,14 @@ out: */ static efi_status_t EFIAPI efi_stall(unsigned long microseconds) { + u64 end_tick; + EFI_ENTRY("%ld", microseconds); - udelay(microseconds); + + end_tick = get_ticks() + usec_to_tick(microseconds); + while (get_ticks() < end_tick) + efi_timer_check(); + return EFI_EXIT(EFI_SUCCESS); } @@ -2868,12 +2879,46 @@ efi_status_t EFIAPI efi_start_image(efi_handle_t image_handle, * @image_obj: handle of the loaded image * @loaded_image_protocol: loaded image protocol */ -static void efi_delete_image(struct efi_loaded_image_obj *image_obj, - struct efi_loaded_image *loaded_image_protocol) +static efi_status_t efi_delete_image + (struct efi_loaded_image_obj *image_obj, + struct efi_loaded_image *loaded_image_protocol) { + struct efi_object *efiobj; + efi_status_t r, ret = EFI_SUCCESS; + +close_next: + list_for_each_entry(efiobj, &efi_obj_list, link) { + struct efi_handler *protocol; + + list_for_each_entry(protocol, &efiobj->protocols, link) { + struct efi_open_protocol_info_item *info; + + list_for_each_entry(info, &protocol->open_infos, link) { + if (info->info.agent_handle != + (efi_handle_t)image_obj) + continue; + r = EFI_CALL(efi_close_protocol + (efiobj, protocol->guid, + info->info.agent_handle, + info->info.controller_handle + )); + if (r != EFI_SUCCESS) + ret = r; + /* + * Closing protocols may results in further + * items being deleted. To play it safe loop + * over all elements again. + */ + goto close_next; + } + } + } + efi_free_pages((uintptr_t)loaded_image_protocol->image_base, efi_size_in_pages(loaded_image_protocol->image_size)); efi_delete_handle(&image_obj->header); + + return ret; } /** |