Pull request for UEFI sub-system for v2019.07-rc2
This pull request provides error fixes for the handling of GPT partitions and for the UEFI subsystem. -----BEGIN PGP SIGNATURE----- iQIzBAABCAAdFiEEbcT5xx8ppvoGt20zxIHbvCwFGsQFAlzLSXQACgkQxIHbvCwF GsSdeQ/9HM7NELIDgo8lK9+v4i1oFLbfO0a/W8I1p2d8o19RKLKfDe9hE5fs5cmu Ky/qnGIfNbtv1YdJg9TNLWbdE9lrLRJVWXbDhG6rh99W8vDEhFwPMhwzmTsoyJnR H5qXgEpwqG7FYidiVWvN6J3MB9pZRn+Be6Rt28NUrM0QJWrJ9MPkN3/tHNbtYGbs jbsm/GDhTBVXLlOcOjXtJvrcC/W/fLyPEz9oR0POzOtKDAZPISfZhORwipnu3DAb WVzH1Slg7Icy7fRPJDFpQGwiefcuFngLShL6JP2tA4HcMVAhdhjDo+YYwR0vXoM5 QfvrIE2hpNrOUhHkNrcYRWynHVZHnuoxdwdQpeBs3y0G8Ig1K0xvB5nwUGZhigzY qmOWZZoNt1IJByvZdS+gVa0Mx0akRF9tJy/Kou90acPuSRAbsAaEjeuP5umYqBhl o9isRLyc+jjfpS2WyRzy4vfIhmR+FA8BU7KPUF/GppA+q0ZplGizJ+a1M5WBZWMN JIjIMuYmbbHOjcfrksDfPCfE5WyS5QZyV7jyec8xAXe/cW045uqaeWV/215sr9hr dcJS6rKfYJ1CO5OSYjZCJJLKBbSoS/RE31iLBxRvOLjR0o8kJGm7IN//sTtVL7uJ OWRpeLVQ35JFAmDzr8LlEtDdkbTrPM5AMMUCie+SU8R7b+ldnwU= =GUpA -----END PGP SIGNATURE----- Merge tag 'efi-2019-07-rc2' of git://git.denx.de/u-boot-efi Pull request for UEFI sub-system for v2019.07-rc2 This pull request provides error fixes for the handling of GPT partitions and for the UEFI subsystem.
This commit is contained in:
commit
6e25cfe9a4
@ -297,18 +297,21 @@ static efi_status_t efi_install_fdt(const char *fdt_opt)
|
||||
static efi_status_t do_bootefi_exec(efi_handle_t handle)
|
||||
{
|
||||
efi_status_t ret;
|
||||
efi_uintn_t exit_data_size = 0;
|
||||
u16 *exit_data = NULL;
|
||||
|
||||
/* Transfer environment variable as load options */
|
||||
ret = set_load_options(handle, "bootargs");
|
||||
if (ret != EFI_SUCCESS)
|
||||
return ret;
|
||||
|
||||
/* we don't support much: */
|
||||
env_set("efi_8be4df61-93ca-11d2-aa0d-00e098032b8c_OsIndicationsSupported",
|
||||
"{ro,boot}(blob)0000000000000000");
|
||||
|
||||
/* Call our payload! */
|
||||
ret = EFI_CALL(efi_start_image(handle, NULL, NULL));
|
||||
ret = EFI_CALL(efi_start_image(handle, &exit_data_size, &exit_data));
|
||||
printf("## Application terminated, r = %lu\n", ret & ~EFI_ERROR_MASK);
|
||||
if (ret && exit_data) {
|
||||
printf("## %ls\n", exit_data);
|
||||
efi_free_pool(exit_data);
|
||||
}
|
||||
|
||||
efi_restore_gd();
|
||||
|
||||
@ -361,7 +364,6 @@ static int do_efibootmgr(const char *fdt_opt)
|
||||
}
|
||||
|
||||
ret = do_bootefi_exec(handle);
|
||||
printf("## Application terminated, r = %lu\n", ret & ~EFI_ERROR_MASK);
|
||||
|
||||
if (ret != EFI_SUCCESS)
|
||||
return CMD_RET_FAILURE;
|
||||
@ -476,7 +478,6 @@ static int do_bootefi_image(const char *image_opt, const char *fdt_opt)
|
||||
goto out;
|
||||
|
||||
ret = do_bootefi_exec(handle);
|
||||
printf("## Application terminated, r = %lu\n", ret & ~EFI_ERROR_MASK);
|
||||
|
||||
out:
|
||||
if (mem_handle)
|
||||
|
106
cmd/efidebug.c
106
cmd/efidebug.c
@ -11,6 +11,7 @@
|
||||
#include <efi_loader.h>
|
||||
#include <environment.h>
|
||||
#include <exports.h>
|
||||
#include <hexdump.h>
|
||||
#include <malloc.h>
|
||||
#include <search.h>
|
||||
#include <linux/ctype.h>
|
||||
@ -545,7 +546,10 @@ static int do_efi_boot_add(cmd_tbl_t *cmdtp, int flag,
|
||||
+ sizeof(struct efi_device_path); /* for END */
|
||||
|
||||
/* optional data */
|
||||
lo.optional_data = (u8 *)(argc == 6 ? "" : argv[6]);
|
||||
if (argc < 6)
|
||||
lo.optional_data = NULL;
|
||||
else
|
||||
lo.optional_data = (const u8 *)argv[6];
|
||||
|
||||
size = efi_serialize_load_option(&lo, (u8 **)&data);
|
||||
if (!size) {
|
||||
@ -615,12 +619,13 @@ static int do_efi_boot_rm(cmd_tbl_t *cmdtp, int flag,
|
||||
/**
|
||||
* show_efi_boot_opt_data() - dump UEFI load option
|
||||
*
|
||||
* @id: Load option number
|
||||
* @data: Value of UEFI load option variable
|
||||
* @id: load option number
|
||||
* @data: value of UEFI load option variable
|
||||
* @size: size of the boot option
|
||||
*
|
||||
* Decode the value of UEFI load option variable and print information.
|
||||
*/
|
||||
static void show_efi_boot_opt_data(int id, void *data)
|
||||
static void show_efi_boot_opt_data(int id, void *data, size_t size)
|
||||
{
|
||||
struct efi_load_option lo;
|
||||
char *label, *p;
|
||||
@ -638,7 +643,7 @@ static void show_efi_boot_opt_data(int id, void *data)
|
||||
utf16_utf8_strncpy(&p, lo.label, label_len16);
|
||||
|
||||
printf("Boot%04X:\n", id);
|
||||
printf("\tattributes: %c%c%c (0x%08x)\n",
|
||||
printf(" attributes: %c%c%c (0x%08x)\n",
|
||||
/* ACTIVE */
|
||||
lo.attributes & LOAD_OPTION_ACTIVE ? 'A' : '-',
|
||||
/* FORCE RECONNECT */
|
||||
@ -646,14 +651,16 @@ static void show_efi_boot_opt_data(int id, void *data)
|
||||
/* HIDDEN */
|
||||
lo.attributes & LOAD_OPTION_HIDDEN ? 'H' : '-',
|
||||
lo.attributes);
|
||||
printf("\tlabel: %s\n", label);
|
||||
printf(" label: %s\n", label);
|
||||
|
||||
dp_str = efi_dp_str(lo.file_path);
|
||||
printf("\tfile_path: %ls\n", dp_str);
|
||||
printf(" file_path: %ls\n", dp_str);
|
||||
efi_free_pool(dp_str);
|
||||
|
||||
printf("\tdata: %s\n", lo.optional_data);
|
||||
|
||||
printf(" data:\n");
|
||||
print_hex_dump(" ", DUMP_PREFIX_OFFSET, 16, 1,
|
||||
lo.optional_data, size + (u8 *)data -
|
||||
(u8 *)lo.optional_data, true);
|
||||
free(label);
|
||||
}
|
||||
|
||||
@ -686,13 +693,24 @@ static void show_efi_boot_opt(int id)
|
||||
data));
|
||||
}
|
||||
if (ret == EFI_SUCCESS)
|
||||
show_efi_boot_opt_data(id, data);
|
||||
show_efi_boot_opt_data(id, data, size);
|
||||
else if (ret == EFI_NOT_FOUND)
|
||||
printf("Boot%04X: not found\n", id);
|
||||
|
||||
free(data);
|
||||
}
|
||||
|
||||
static int u16_tohex(u16 c)
|
||||
{
|
||||
if (c >= '0' && c <= '9')
|
||||
return c - '0';
|
||||
if (c >= 'A' && c <= 'F')
|
||||
return c - 'A' + 10;
|
||||
|
||||
/* not hexadecimal */
|
||||
return -1;
|
||||
}
|
||||
|
||||
/**
|
||||
* show_efi_boot_dump() - dump all UEFI load options
|
||||
*
|
||||
@ -709,38 +727,58 @@ static void show_efi_boot_opt(int id)
|
||||
static int do_efi_boot_dump(cmd_tbl_t *cmdtp, int flag,
|
||||
int argc, char * const argv[])
|
||||
{
|
||||
char regex[256];
|
||||
char * const regexlist[] = {regex};
|
||||
char *variables = NULL, *boot, *value;
|
||||
int len;
|
||||
int id;
|
||||
u16 *var_name16, *p;
|
||||
efi_uintn_t buf_size, size;
|
||||
efi_guid_t guid;
|
||||
int id, i, digit;
|
||||
efi_status_t ret;
|
||||
|
||||
if (argc > 1)
|
||||
return CMD_RET_USAGE;
|
||||
|
||||
snprintf(regex, 256, "efi_.*-.*-.*-.*-.*_Boot[0-9A-F]+");
|
||||
|
||||
/* TODO: use GetNextVariableName? */
|
||||
len = hexport_r(&env_htab, '\n', H_MATCH_REGEX | H_MATCH_KEY,
|
||||
&variables, 0, 1, regexlist);
|
||||
|
||||
if (!len)
|
||||
return CMD_RET_SUCCESS;
|
||||
|
||||
if (len < 0)
|
||||
buf_size = 128;
|
||||
var_name16 = malloc(buf_size);
|
||||
if (!var_name16)
|
||||
return CMD_RET_FAILURE;
|
||||
|
||||
boot = variables;
|
||||
while (*boot) {
|
||||
value = strstr(boot, "Boot") + 4;
|
||||
id = (int)simple_strtoul(value, NULL, 16);
|
||||
show_efi_boot_opt(id);
|
||||
boot = strchr(boot, '\n');
|
||||
if (!*boot)
|
||||
var_name16[0] = 0;
|
||||
for (;;) {
|
||||
size = buf_size;
|
||||
ret = EFI_CALL(efi_get_next_variable_name(&size, var_name16,
|
||||
&guid));
|
||||
if (ret == EFI_NOT_FOUND)
|
||||
break;
|
||||
boot++;
|
||||
if (ret == EFI_BUFFER_TOO_SMALL) {
|
||||
buf_size = size;
|
||||
p = realloc(var_name16, buf_size);
|
||||
if (!p) {
|
||||
free(var_name16);
|
||||
return CMD_RET_FAILURE;
|
||||
}
|
||||
var_name16 = p;
|
||||
ret = EFI_CALL(efi_get_next_variable_name(&size,
|
||||
var_name16,
|
||||
&guid));
|
||||
}
|
||||
if (ret != EFI_SUCCESS) {
|
||||
free(var_name16);
|
||||
return CMD_RET_FAILURE;
|
||||
}
|
||||
|
||||
if (memcmp(var_name16, L"Boot", 8))
|
||||
continue;
|
||||
|
||||
for (id = 0, i = 0; i < 4; i++) {
|
||||
digit = u16_tohex(var_name16[4 + i]);
|
||||
if (digit < 0)
|
||||
break;
|
||||
id = (id << 4) + digit;
|
||||
}
|
||||
if (i == 4 && !var_name16[8])
|
||||
show_efi_boot_opt(id);
|
||||
}
|
||||
free(variables);
|
||||
|
||||
free(var_name16);
|
||||
|
||||
return CMD_RET_SUCCESS;
|
||||
}
|
||||
|
12
cmd/gpt.c
12
cmd/gpt.c
@ -876,21 +876,21 @@ U_BOOT_CMD(gpt, CONFIG_SYS_MAXARGS, 1, do_gpt,
|
||||
" Example usage:\n"
|
||||
" gpt write mmc 0 $partitions\n"
|
||||
" gpt verify mmc 0 $partitions\n"
|
||||
" read <interface> <dev>\n"
|
||||
" - read GPT into a data structure for manipulation\n"
|
||||
" guid <interface> <dev>\n"
|
||||
" gpt guid <interface> <dev>\n"
|
||||
" - print disk GUID\n"
|
||||
" guid <interface> <dev> <varname>\n"
|
||||
" gpt guid <interface> <dev> <varname>\n"
|
||||
" - set environment variable to disk GUID\n"
|
||||
" Example usage:\n"
|
||||
" gpt guid mmc 0\n"
|
||||
" gpt guid mmc 0 varname\n"
|
||||
#ifdef CONFIG_CMD_GPT_RENAME
|
||||
"gpt partition renaming commands:\n"
|
||||
"gpt swap <interface> <dev> <name1> <name2>\n"
|
||||
" gpt read <interface> <dev>\n"
|
||||
" - read GPT into a data structure for manipulation\n"
|
||||
" gpt swap <interface> <dev> <name1> <name2>\n"
|
||||
" - change all partitions named name1 to name2\n"
|
||||
" and vice-versa\n"
|
||||
"gpt rename <interface> <dev> <part> <name>\n"
|
||||
" gpt rename <interface> <dev> <part> <name>\n"
|
||||
" - rename the specified partition\n"
|
||||
" Example usage:\n"
|
||||
" gpt swap mmc 0 foo bar\n"
|
||||
|
@ -291,8 +291,11 @@ static int append_value(char **bufp, size_t *sizep, char *data)
|
||||
if (!tmp_buf)
|
||||
return -1;
|
||||
|
||||
if (hex2bin((u8 *)tmp_buf, data, len) < 0)
|
||||
if (hex2bin((u8 *)tmp_buf, data, len) < 0) {
|
||||
printf("Error: illegal hexadecimal string\n");
|
||||
free(tmp_buf);
|
||||
return -1;
|
||||
}
|
||||
|
||||
value = tmp_buf;
|
||||
} else { /* string */
|
||||
|
@ -209,6 +209,8 @@ int get_disk_guid(struct blk_desc * dev_desc, char *guid)
|
||||
guid_bin = gpt_head->disk_guid.b;
|
||||
uuid_bin_to_str(guid_bin, guid, UUID_STR_FORMAT_GUID);
|
||||
|
||||
/* Remember to free pte */
|
||||
free(gpt_pte);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -696,6 +698,10 @@ int gpt_verify_headers(struct blk_desc *dev_desc, gpt_header *gpt_head,
|
||||
__func__);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Free pte before allocating again */
|
||||
free(*gpt_pte);
|
||||
|
||||
if (is_gpt_valid(dev_desc, (dev_desc->lba - 1),
|
||||
gpt_head, gpt_pte) != 1) {
|
||||
printf("%s: *** ERROR: Invalid Backup GPT ***\n",
|
||||
|
@ -207,12 +207,17 @@ struct efi_object {
|
||||
* struct efi_loaded_image_obj - handle of a loaded image
|
||||
*
|
||||
* @header: EFI object header
|
||||
* @exit_status: exit status passed to Exit()
|
||||
* @exit_data_size: exit data size passed to Exit()
|
||||
* @exit_data: exit data passed to Exit()
|
||||
* @exit_jmp: long jump buffer for returning form started image
|
||||
* @entry: entry address of the relocated image
|
||||
*/
|
||||
struct efi_loaded_image_obj {
|
||||
struct efi_object header;
|
||||
efi_status_t exit_status;
|
||||
efi_uintn_t *exit_data_size;
|
||||
u16 **exit_data;
|
||||
struct jmp_buf_data exit_jmp;
|
||||
EFIAPI efi_status_t (*entry)(efi_handle_t image_handle,
|
||||
struct efi_system_table *st);
|
||||
@ -560,7 +565,7 @@ struct efi_load_option {
|
||||
u16 file_path_length;
|
||||
u16 *label;
|
||||
struct efi_device_path *file_path;
|
||||
u8 *optional_data;
|
||||
const u8 *optional_data;
|
||||
};
|
||||
|
||||
void efi_deserialize_load_option(struct efi_load_option *lo, u8 *data);
|
||||
|
@ -16,7 +16,7 @@
|
||||
|
||||
#define EFI_ST_SUCCESS 0
|
||||
#define EFI_ST_FAILURE 1
|
||||
|
||||
#define EFI_ST_SUCCESS_STR L"SUCCESS"
|
||||
/*
|
||||
* Prints a message.
|
||||
*/
|
||||
|
@ -53,19 +53,20 @@ void efi_deserialize_load_option(struct efi_load_option *lo, u8 *data)
|
||||
*/
|
||||
unsigned long efi_serialize_load_option(struct efi_load_option *lo, u8 **data)
|
||||
{
|
||||
unsigned long label_len, option_len;
|
||||
unsigned long label_len;
|
||||
unsigned long size;
|
||||
u8 *p;
|
||||
|
||||
label_len = (u16_strlen(lo->label) + 1) * sizeof(u16);
|
||||
option_len = strlen((char *)lo->optional_data);
|
||||
|
||||
/* total size */
|
||||
size = sizeof(lo->attributes);
|
||||
size += sizeof(lo->file_path_length);
|
||||
size += label_len;
|
||||
size += lo->file_path_length;
|
||||
size += option_len + 1;
|
||||
if (lo->optional_data)
|
||||
size += (utf8_utf16_strlen((const char *)lo->optional_data)
|
||||
+ 1) * sizeof(u16);
|
||||
p = malloc(size);
|
||||
if (!p)
|
||||
return 0;
|
||||
@ -84,10 +85,10 @@ unsigned long efi_serialize_load_option(struct efi_load_option *lo, u8 **data)
|
||||
memcpy(p, lo->file_path, lo->file_path_length);
|
||||
p += lo->file_path_length;
|
||||
|
||||
memcpy(p, lo->optional_data, option_len);
|
||||
p += option_len;
|
||||
*(char *)p = '\0';
|
||||
|
||||
if (lo->optional_data) {
|
||||
utf8_utf16_strcpy((u16 **)&p, (const char *)lo->optional_data);
|
||||
p += sizeof(u16); /* size of trailing \0 */
|
||||
}
|
||||
return size;
|
||||
}
|
||||
|
||||
|
@ -423,10 +423,12 @@ static efi_status_t EFIAPI efi_free_pool_ext(void *buffer)
|
||||
}
|
||||
|
||||
/**
|
||||
* efi_add_handle() - add a new object to the object list
|
||||
* @obj: object to be added
|
||||
* efi_add_handle() - add a new handle to the object list
|
||||
*
|
||||
* The protocols list is initialized. The object handle is set.
|
||||
* @handle: handle to be added
|
||||
*
|
||||
* The protocols list is initialized. The handle is added to the list of known
|
||||
* UEFI objects.
|
||||
*/
|
||||
void efi_add_handle(efi_handle_t handle)
|
||||
{
|
||||
@ -618,7 +620,7 @@ efi_status_t efi_create_event(uint32_t type, efi_uintn_t notify_tpl,
|
||||
}
|
||||
|
||||
if ((type & (EVT_NOTIFY_WAIT | EVT_NOTIFY_SIGNAL)) &&
|
||||
(is_valid_tpl(notify_tpl) != EFI_SUCCESS))
|
||||
(!notify_function || is_valid_tpl(notify_tpl) != EFI_SUCCESS))
|
||||
return EFI_INVALID_PARAMETER;
|
||||
|
||||
evt = calloc(1, sizeof(struct efi_event));
|
||||
@ -2626,6 +2628,9 @@ efi_status_t EFIAPI efi_start_image(efi_handle_t image_handle,
|
||||
|
||||
efi_is_direct_boot = false;
|
||||
|
||||
image_obj->exit_data_size = exit_data_size;
|
||||
image_obj->exit_data = exit_data;
|
||||
|
||||
/* call the image! */
|
||||
if (setjmp(&image_obj->exit_jmp)) {
|
||||
/*
|
||||
@ -2669,6 +2674,41 @@ efi_status_t EFIAPI efi_start_image(efi_handle_t image_handle,
|
||||
return EFI_CALL(systab.boottime->exit(image_handle, ret, 0, NULL));
|
||||
}
|
||||
|
||||
/**
|
||||
* efi_update_exit_data() - fill exit data parameters of StartImage()
|
||||
*
|
||||
* @image_obj image handle
|
||||
* @exit_data_size size of the exit data buffer
|
||||
* @exit_data buffer with data returned by UEFI payload
|
||||
* Return: status code
|
||||
*/
|
||||
static efi_status_t efi_update_exit_data(struct efi_loaded_image_obj *image_obj,
|
||||
efi_uintn_t exit_data_size,
|
||||
u16 *exit_data)
|
||||
{
|
||||
efi_status_t ret;
|
||||
|
||||
/*
|
||||
* If exit_data is not provided to StartImage(), exit_data_size must be
|
||||
* ignored.
|
||||
*/
|
||||
if (!image_obj->exit_data)
|
||||
return EFI_SUCCESS;
|
||||
if (image_obj->exit_data_size)
|
||||
*image_obj->exit_data_size = exit_data_size;
|
||||
if (exit_data_size && exit_data) {
|
||||
ret = efi_allocate_pool(EFI_BOOT_SERVICES_DATA,
|
||||
exit_data_size,
|
||||
(void **)image_obj->exit_data);
|
||||
if (ret != EFI_SUCCESS)
|
||||
return ret;
|
||||
memcpy(*image_obj->exit_data, exit_data, exit_data_size);
|
||||
} else {
|
||||
image_obj->exit_data = NULL;
|
||||
}
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
|
||||
/**
|
||||
* efi_exit() - leave an EFI application or driver
|
||||
* @image_handle: handle of the application or driver that is exiting
|
||||
@ -2709,6 +2749,15 @@ static efi_status_t EFIAPI efi_exit(efi_handle_t image_handle,
|
||||
if (ret != EFI_SUCCESS)
|
||||
goto out;
|
||||
|
||||
/* Exit data is only foreseen in case of failure. */
|
||||
if (exit_status != EFI_SUCCESS) {
|
||||
ret = efi_update_exit_data(image_obj, exit_data_size,
|
||||
exit_data);
|
||||
/* Exiting has priority. Don't return error to caller. */
|
||||
if (ret != EFI_SUCCESS)
|
||||
EFI_PRINT("%s: out of memory\n", __func__);
|
||||
}
|
||||
|
||||
/* Make sure entry/exit counts for EFI world cross-overs match */
|
||||
EFI_EXIT(exit_status);
|
||||
|
||||
|
@ -452,7 +452,7 @@ efi_status_t efi_free_pages(uint64_t memory, efi_uintn_t pages)
|
||||
uint64_t r = 0;
|
||||
|
||||
/* Sanity check */
|
||||
if (!memory || (memory & EFI_PAGE_MASK)) {
|
||||
if (!memory || (memory & EFI_PAGE_MASK) || !pages) {
|
||||
printf("%s: illegal free 0x%llx, 0x%zx\n", __func__,
|
||||
memory, pages);
|
||||
return EFI_INVALID_PARAMETER;
|
||||
|
@ -79,6 +79,7 @@ out:
|
||||
*/
|
||||
efi_status_t efi_init_obj_list(void)
|
||||
{
|
||||
u64 os_indications_supported = 0; /* None */
|
||||
efi_status_t ret = EFI_SUCCESS;
|
||||
|
||||
/* Initialize once only */
|
||||
@ -90,6 +91,16 @@ efi_status_t efi_init_obj_list(void)
|
||||
if (ret != EFI_SUCCESS)
|
||||
goto out;
|
||||
|
||||
/* Indicate supported features */
|
||||
ret = EFI_CALL(efi_set_variable(L"OsIndicationsSupported",
|
||||
&efi_global_variable_guid,
|
||||
EFI_VARIABLE_BOOTSERVICE_ACCESS |
|
||||
EFI_VARIABLE_RUNTIME_ACCESS,
|
||||
sizeof(os_indications_supported),
|
||||
&os_indications_supported));
|
||||
if (ret != EFI_SUCCESS)
|
||||
goto out;
|
||||
|
||||
/* Initialize system table */
|
||||
ret = efi_initialize_system_table();
|
||||
if (ret != EFI_SUCCESS)
|
||||
|
@ -9,7 +9,7 @@
|
||||
*/
|
||||
|
||||
#include <common.h>
|
||||
#include <efi_api.h>
|
||||
#include <efi_selftest.h>
|
||||
|
||||
static efi_guid_t loaded_image_protocol_guid = EFI_LOADED_IMAGE_PROTOCOL_GUID;
|
||||
|
||||
@ -66,15 +66,22 @@ efi_status_t EFIAPI efi_main(efi_handle_t handle,
|
||||
struct efi_system_table *systable)
|
||||
{
|
||||
struct efi_simple_text_output_protocol *con_out = systable->con_out;
|
||||
efi_status_t ret = EFI_UNSUPPORTED;
|
||||
efi_status_t ret;
|
||||
u16 text[] = EFI_ST_SUCCESS_STR;
|
||||
|
||||
con_out->output_string(con_out, L"EFI application calling Exit\n");
|
||||
|
||||
if (check_loaded_image_protocol(handle, systable) != EFI_SUCCESS)
|
||||
if (check_loaded_image_protocol(handle, systable) != EFI_SUCCESS) {
|
||||
con_out->output_string(con_out,
|
||||
L"Loaded image protocol missing\n");
|
||||
ret = EFI_NOT_FOUND;
|
||||
goto out;
|
||||
}
|
||||
|
||||
/* The return value is checked by the calling test */
|
||||
systable->boottime->exit(handle, ret, 0, NULL);
|
||||
/* This return value is expected by the calling test */
|
||||
ret = EFI_UNSUPPORTED;
|
||||
out:
|
||||
systable->boottime->exit(handle, ret, sizeof(text), text);
|
||||
|
||||
/*
|
||||
* This statement should not be reached.
|
||||
|
@ -123,6 +123,9 @@ static int execute(void)
|
||||
{
|
||||
efi_status_t ret;
|
||||
efi_handle_t handle;
|
||||
efi_uintn_t exit_data_size = 0;
|
||||
u16 *exit_data = NULL;
|
||||
u16 expected_text[] = EFI_ST_SUCCESS_STR;
|
||||
|
||||
ret = boottime->load_image(false, image_handle, NULL, image,
|
||||
img.length, &handle);
|
||||
@ -130,11 +133,21 @@ static int execute(void)
|
||||
efi_st_error("Failed to load image\n");
|
||||
return EFI_ST_FAILURE;
|
||||
}
|
||||
ret = boottime->start_image(handle, NULL, NULL);
|
||||
ret = boottime->start_image(handle, &exit_data_size, &exit_data);
|
||||
if (ret != EFI_UNSUPPORTED) {
|
||||
efi_st_error("Wrong return value from application\n");
|
||||
return EFI_ST_FAILURE;
|
||||
}
|
||||
if (!exit_data || exit_data_size != sizeof(expected_text) ||
|
||||
efi_st_memcmp(exit_data, expected_text, sizeof(expected_text))) {
|
||||
efi_st_error("Incorrect exit data\n");
|
||||
return EFI_ST_FAILURE;
|
||||
}
|
||||
ret = boottime->free_pool(exit_data);
|
||||
if (ret != EFI_SUCCESS) {
|
||||
efi_st_error("Failed to free exit data\n");
|
||||
return EFI_ST_FAILURE;
|
||||
}
|
||||
|
||||
return EFI_ST_SUCCESS;
|
||||
}
|
||||
|
@ -238,6 +238,8 @@ void gen_rand_uuid(unsigned char *uuid_bin)
|
||||
unsigned int *ptr = (unsigned int *)&uuid;
|
||||
int i;
|
||||
|
||||
srand(get_ticks() + rand());
|
||||
|
||||
/* Set all fields randomly */
|
||||
for (i = 0; i < sizeof(struct uuid) / sizeof(*ptr); i++)
|
||||
*(ptr + i) = cpu_to_be32(rand());
|
||||
|
Loading…
Reference in New Issue
Block a user