diff --git a/cmd/efidebug.c b/cmd/efidebug.c index e657226254..cb152b3339 100644 --- a/cmd/efidebug.c +++ b/cmd/efidebug.c @@ -505,7 +505,8 @@ static int do_efi_boot_add(cmd_tbl_t *cmdtp, int flag, struct efi_load_option lo; void *data = NULL; efi_uintn_t size; - int ret; + efi_status_t ret; + int r = CMD_RET_SUCCESS; if (argc < 6 || argc > 7) return CMD_RET_USAGE; @@ -538,7 +539,7 @@ static int do_efi_boot_add(cmd_tbl_t *cmdtp, int flag, if (ret != EFI_SUCCESS) { printf("Cannot create device path for \"%s %s\"\n", argv[3], argv[4]); - ret = CMD_RET_FAILURE; + r = CMD_RET_FAILURE; goto out; } lo.file_path = file_path; @@ -553,7 +554,7 @@ static int do_efi_boot_add(cmd_tbl_t *cmdtp, int flag, size = efi_serialize_load_option(&lo, (u8 **)&data); if (!size) { - ret = CMD_RET_FAILURE; + r = CMD_RET_FAILURE; goto out; } @@ -562,14 +563,17 @@ static int do_efi_boot_add(cmd_tbl_t *cmdtp, int flag, EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS, size, data)); - ret = (ret == EFI_SUCCESS ? CMD_RET_SUCCESS : CMD_RET_FAILURE); + if (ret != EFI_SUCCESS) { + printf("Cannot set %ls\n", var_name16); + r = CMD_RET_FAILURE; + } out: free(data); efi_free_pool(device_path); efi_free_pool(file_path); free(lo.label); - return ret; + return r; } /** @@ -609,7 +613,7 @@ static int do_efi_boot_rm(cmd_tbl_t *cmdtp, int flag, ret = EFI_CALL(RT->set_variable(var_name16, &guid, 0, 0, NULL)); if (ret) { - printf("cannot remove Boot%04X", id); + printf("Cannot remove Boot%04X", id); return CMD_RET_FAILURE; } } @@ -896,6 +900,7 @@ static int do_efi_boot_next(cmd_tbl_t *cmdtp, int flag, char *endp; efi_guid_t guid; efi_status_t ret; + int r = CMD_RET_SUCCESS; if (argc != 2) return CMD_RET_USAGE; @@ -903,7 +908,7 @@ static int do_efi_boot_next(cmd_tbl_t *cmdtp, int flag, bootnext = (u16)simple_strtoul(argv[1], &endp, 16); if (*endp != '\0' || bootnext > 0xffff) { printf("invalid value: %s\n", argv[1]); - ret = CMD_RET_FAILURE; + r = CMD_RET_FAILURE; goto out; } @@ -914,9 +919,12 @@ static int do_efi_boot_next(cmd_tbl_t *cmdtp, int flag, EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS, size, &bootnext)); - ret = (ret == EFI_SUCCESS ? CMD_RET_SUCCESS : CMD_RET_FAILURE); + if (ret != EFI_SUCCESS) { + printf("Cannot set BootNext\n"); + r = CMD_RET_FAILURE; + } out: - return ret; + return r; } /** @@ -941,6 +949,7 @@ static int do_efi_boot_order(cmd_tbl_t *cmdtp, int flag, char *endp; efi_guid_t guid; efi_status_t ret; + int r = CMD_RET_SUCCESS; if (argc == 1) return show_efi_boot_order(); @@ -957,7 +966,7 @@ static int do_efi_boot_order(cmd_tbl_t *cmdtp, int flag, id = (int)simple_strtoul(argv[i], &endp, 16); if (*endp != '\0' || id > 0xffff) { printf("invalid value: %s\n", argv[i]); - ret = CMD_RET_FAILURE; + r = CMD_RET_FAILURE; goto out; } @@ -970,11 +979,14 @@ static int do_efi_boot_order(cmd_tbl_t *cmdtp, int flag, EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS, size, bootorder)); - ret = (ret == EFI_SUCCESS ? CMD_RET_SUCCESS : CMD_RET_FAILURE); + if (ret != EFI_SUCCESS) { + printf("Cannot set BootOrder\n"); + r = CMD_RET_FAILURE; + } out: free(bootorder); - return ret; + return r; } static cmd_tbl_t cmd_efidebug_boot_sub[] = { diff --git a/cmd/fs.c b/cmd/fs.c index aaafbf9b52..db74767b7b 100644 --- a/cmd/fs.c +++ b/cmd/fs.c @@ -8,7 +8,6 @@ #include #include #include -#include static int do_size_wrapper(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) { @@ -26,10 +25,6 @@ U_BOOT_CMD( static int do_load_wrapper(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) { -#ifdef CONFIG_CMD_BOOTEFI - efi_set_bootdev(argv[1], (argc > 2) ? argv[2] : "", - (argc > 4) ? argv[4] : ""); -#endif return do_load(cmdtp, flag, argc, argv, FS_TYPE_ANY); } diff --git a/fs/fs.c b/fs/fs.c index 736ebef4a9..48d8f1f6da 100644 --- a/fs/fs.c +++ b/fs/fs.c @@ -17,6 +17,7 @@ #include #include #include +#include DECLARE_GLOBAL_DATA_PTR; @@ -700,6 +701,10 @@ int do_load(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[], else pos = 0; +#ifdef CONFIG_CMD_BOOTEFI + efi_set_bootdev(argv[1], (argc > 2) ? argv[2] : "", + (argc > 4) ? argv[4] : ""); +#endif time = get_timer(0); ret = _fs_read(filename, addr, pos, bytes, 1, &len_read); time = get_timer(time); diff --git a/include/efi_api.h b/include/efi_api.h index d7d95edd4d..4de5d208f5 100644 --- a/include/efi_api.h +++ b/include/efi_api.h @@ -577,7 +577,9 @@ struct simple_text_output_mode { #define EFI_ATTR_BG(attr) (((attr) >> 4) & 0x7) struct efi_simple_text_output_protocol { - void *reset; + efi_status_t (EFIAPI *reset)( + struct efi_simple_text_output_protocol *this, + char extended_verification); efi_status_t (EFIAPI *output_string)( struct efi_simple_text_output_protocol *this, const efi_string_t str); diff --git a/lib/efi_loader/efi_boottime.c b/lib/efi_loader/efi_boottime.c index b26291b919..d104cc6b31 100644 --- a/lib/efi_loader/efi_boottime.c +++ b/lib/efi_loader/efi_boottime.c @@ -3620,11 +3620,11 @@ struct efi_system_table __efi_runtime_data systab = { }, .fw_vendor = firmware_vendor, .fw_revision = FW_VERSION << 16 | FW_PATCHLEVEL << 8, - .con_in = (void *)&efi_con_in, - .con_out = (void *)&efi_con_out, - .std_err = (void *)&efi_con_out, - .runtime = (void *)&efi_runtime_services, - .boottime = (void *)&efi_boot_services, + .con_in = &efi_con_in, + .con_out = &efi_con_out, + .std_err = &efi_con_out, + .runtime = &efi_runtime_services, + .boottime = &efi_boot_services, .nr_tables = 0, .tables = NULL, }; diff --git a/lib/efi_loader/efi_console.c b/lib/efi_loader/efi_console.c index 706e6ad31e..6c8229da42 100644 --- a/lib/efi_loader/efi_console.c +++ b/lib/efi_loader/efi_console.c @@ -481,10 +481,8 @@ void set_shift_mask(int mod, struct efi_key_state *key_state) key_state->key_shift_state |= EFI_LEFT_ALT_PRESSED; if (mod & 4) key_state->key_shift_state |= EFI_LEFT_CONTROL_PRESSED; - if (mod & 8) + if (!mod || (mod & 8)) key_state->key_shift_state |= EFI_LEFT_LOGO_PRESSED; - } else { - key_state->key_shift_state |= EFI_LEFT_LOGO_PRESSED; } } @@ -563,10 +561,13 @@ static efi_status_t efi_cin_read_key(struct efi_key_data *key) case cESC: /* ESC */ pressed_key.scan_code = 23; break; - case 'O': /* F1 - F4 */ + case 'O': /* F1 - F4, End */ ch = getc(); /* consider modifiers */ - if (ch < 'P') { + if (ch == 'F') { /* End */ + pressed_key.scan_code = 6; + break; + } else if (ch < 'P') { set_shift_mask(ch - '0', &key->key_state); ch = getc(); } @@ -590,17 +591,20 @@ static efi_status_t efi_cin_read_key(struct efi_key_data *key) case '1'...'5': /* F1 - F5 */ pressed_key.scan_code = ch - '1' + 11; break; - case '7'...'9': /* F6 - F8 */ - pressed_key.scan_code = ch - '7' + 16; + case '6'...'9': /* F5 - F8 */ + pressed_key.scan_code = ch - '6' + 15; break; case 'A'...'D': /* up, down right, left */ pressed_key.scan_code = ch - 'A' + 1; break; - case 'F': - pressed_key.scan_code = 6; /* End */ + case 'F': /* End */ + pressed_key.scan_code = 6; break; - case 'H': - pressed_key.scan_code = 5; /* Home */ + case 'H': /* Home */ + pressed_key.scan_code = 5; + break; + case '~': /* Home */ + pressed_key.scan_code = 5; break; } break; diff --git a/lib/efi_loader/efi_file.c b/lib/efi_loader/efi_file.c index 182d735e6b..36ca719a82 100644 --- a/lib/efi_loader/efi_file.c +++ b/lib/efi_loader/efi_file.c @@ -307,16 +307,10 @@ static efi_status_t EFIAPI efi_file_delete(struct efi_file_handle *file) EFI_ENTRY("%p", file); - if (set_blk_dev(fh)) { - ret = EFI_DEVICE_ERROR; - goto error; - } + if (set_blk_dev(fh) || fs_unlink(fh->path)) + ret = EFI_WARN_DELETE_FAILURE; - if (fs_unlink(fh->path)) - ret = EFI_DEVICE_ERROR; file_close(fh); - -error: return EFI_EXIT(ret); } diff --git a/lib/efi_loader/efi_gop.c b/lib/efi_loader/efi_gop.c index e003823b60..cad509bfea 100644 --- a/lib/efi_loader/efi_gop.c +++ b/lib/efi_loader/efi_gop.c @@ -41,24 +41,25 @@ static efi_status_t EFIAPI gop_query_mode(struct efi_gop *this, u32 mode_number, struct efi_gop_mode_info **info) { struct efi_gop_obj *gopobj; + efi_status_t ret = EFI_SUCCESS; EFI_ENTRY("%p, %x, %p, %p", this, mode_number, size_of_info, info); + if (!this || !size_of_info || !info || mode_number) { + ret = EFI_INVALID_PARAMETER; + goto out; + } + gopobj = container_of(this, struct efi_gop_obj, ops); + ret = efi_allocate_pool(EFI_BOOT_SERVICES_DATA, sizeof(gopobj->info), + (void **)info); + if (ret != EFI_SUCCESS) + goto out; *size_of_info = sizeof(gopobj->info); - *info = &gopobj->info; + memcpy(*info, &gopobj->info, sizeof(gopobj->info)); - return EFI_EXIT(EFI_SUCCESS); -} - -static efi_status_t EFIAPI gop_set_mode(struct efi_gop *this, u32 mode_number) -{ - EFI_ENTRY("%p, %x", this, mode_number); - - if (mode_number != 0) - return EFI_EXIT(EFI_INVALID_PARAMETER); - - return EFI_EXIT(EFI_SUCCESS); +out: + return EFI_EXIT(ret); } static __always_inline struct efi_gop_pixel efi_vid16_to_blt_col(u16 vid) @@ -309,6 +310,44 @@ static efi_status_t gop_blt_vid_to_buf(struct efi_gop *this, dx, dy, width, height, delta, vid_bpp); } +/** + * gop_set_mode() - set graphical output mode + * + * This function implements the SetMode() service. + * + * See the Unified Extensible Firmware Interface (UEFI) specification for + * details. + * + * @this: the graphical output protocol + * @model_number: the mode to be set + * Return: status code + */ +static efi_status_t EFIAPI gop_set_mode(struct efi_gop *this, u32 mode_number) +{ + struct efi_gop_obj *gopobj; + struct efi_gop_pixel buffer = {0, 0, 0, 0}; + efi_uintn_t vid_bpp; + efi_status_t ret = EFI_SUCCESS; + + EFI_ENTRY("%p, %x", this, mode_number); + + if (!this) { + ret = EFI_INVALID_PARAMETER; + goto out; + } + if (mode_number) { + ret = EFI_UNSUPPORTED; + goto out; + } + gopobj = container_of(this, struct efi_gop_obj, ops); + vid_bpp = gop_get_bpp(this); + ret = gop_blt_video_fill(this, &buffer, EFI_BLT_VIDEO_FILL, 0, 0, 0, 0, + gopobj->info.width, gopobj->info.height, 0, + vid_bpp); +out: + return EFI_EXIT(ret); +} + /* * Copy rectangle. * @@ -367,7 +406,7 @@ efi_status_t EFIAPI gop_blt(struct efi_gop *this, struct efi_gop_pixel *buffer, dy, width, height, delta, vid_bpp); break; default: - ret = EFI_UNSUPPORTED; + ret = EFI_INVALID_PARAMETER; } if (ret != EFI_SUCCESS) @@ -464,26 +503,26 @@ efi_status_t efi_gop_register(void) gopobj->mode.info = &gopobj->info; gopobj->mode.info_size = sizeof(gopobj->info); + gopobj->mode.fb_base = fb_base; + gopobj->mode.fb_size = fb_size; + + gopobj->info.version = 0; + gopobj->info.width = col; + gopobj->info.height = row; #ifdef CONFIG_DM_VIDEO if (bpix == VIDEO_BPP32) #else if (bpix == LCD_COLOR32) #endif { - /* - * With 32bit color space we can directly expose the frame - * buffer - */ - gopobj->mode.fb_base = fb_base; - gopobj->mode.fb_size = fb_size; + gopobj->info.pixel_format = EFI_GOT_BGRA8; + } else { + gopobj->info.pixel_format = EFI_GOT_BITMASK; + gopobj->info.pixel_bitmask[0] = 0xf800; /* red */ + gopobj->info.pixel_bitmask[1] = 0x07e0; /* green */ + gopobj->info.pixel_bitmask[2] = 0x001f; /* blue */ } - - gopobj->info.version = 0; - gopobj->info.width = col; - gopobj->info.height = row; - gopobj->info.pixel_format = EFI_GOT_BGRA8; gopobj->info.pixels_per_scanline = col; - gopobj->bpix = bpix; gopobj->fb = fb; diff --git a/lib/efi_loader/efi_hii.c b/lib/efi_loader/efi_hii.c index 61b71dec62..77e330285a 100644 --- a/lib/efi_loader/efi_hii.c +++ b/lib/efi_loader/efi_hii.c @@ -581,18 +581,22 @@ list_package_lists(const struct efi_hii_database_protocol *this, struct efi_hii_packagelist *hii = (struct efi_hii_packagelist *)handle; int package_cnt, package_max; - efi_status_t ret = EFI_SUCCESS; + efi_status_t ret = EFI_NOT_FOUND; EFI_ENTRY("%p, %u, %pUl, %p, %p", this, package_type, package_guid, handle_buffer_length, handle); if (!handle_buffer_length || - (*handle_buffer_length && !handle)) - return EFI_EXIT(EFI_INVALID_PARAMETER); + (*handle_buffer_length && !handle)) { + ret = EFI_INVALID_PARAMETER; + goto out; + } if ((package_type != EFI_HII_PACKAGE_TYPE_GUID && package_guid) || - (package_type == EFI_HII_PACKAGE_TYPE_GUID && !package_guid)) - return EFI_EXIT(EFI_INVALID_PARAMETER); + (package_type == EFI_HII_PACKAGE_TYPE_GUID && !package_guid)) { + ret = EFI_INVALID_PARAMETER; + goto out; + } EFI_PRINT("package type=%x, guid=%pUl, length=%zu\n", (int)package_type, package_guid, *handle_buffer_length); @@ -607,53 +611,28 @@ list_package_lists(const struct efi_hii_database_protocol *this, if (!list_empty(&hii->guid_list)) break; continue; - case EFI_HII_PACKAGE_FORMS: - EFI_PRINT("Form package not supported\n"); - ret = EFI_INVALID_PARAMETER; - continue; case EFI_HII_PACKAGE_STRINGS: if (!list_empty(&hii->string_tables)) break; continue; - case EFI_HII_PACKAGE_FONTS: - EFI_PRINT("Font package not supported\n"); - ret = EFI_INVALID_PARAMETER; - continue; - case EFI_HII_PACKAGE_IMAGES: - EFI_PRINT("Image package not supported\n"); - ret = EFI_INVALID_PARAMETER; - continue; - case EFI_HII_PACKAGE_SIMPLE_FONTS: - EFI_PRINT("Simple font package not supported\n"); - ret = EFI_INVALID_PARAMETER; - continue; - case EFI_HII_PACKAGE_DEVICE_PATH: - EFI_PRINT("Device path package not supported\n"); - ret = EFI_INVALID_PARAMETER; - continue; case EFI_HII_PACKAGE_KEYBOARD_LAYOUT: if (!list_empty(&hii->keyboard_packages)) break; continue; - case EFI_HII_PACKAGE_ANIMATIONS: - EFI_PRINT("Animation package not supported\n"); - ret = EFI_INVALID_PARAMETER; - continue; - case EFI_HII_PACKAGE_END: - case EFI_HII_PACKAGE_TYPE_SYSTEM_BEGIN: - case EFI_HII_PACKAGE_TYPE_SYSTEM_END: default: continue; } package_cnt++; - if (package_cnt <= package_max) + if (package_cnt <= package_max) { *handle++ = hii; - else + ret = EFI_SUCCESS; + } else { ret = EFI_BUFFER_TOO_SMALL; + } } *handle_buffer_length = package_cnt * sizeof(*handle); - +out: return EFI_EXIT(ret); } diff --git a/lib/efi_loader/efi_variable.c b/lib/efi_loader/efi_variable.c index 1d1b23b0e5..d6b75ca02e 100644 --- a/lib/efi_loader/efi_variable.c +++ b/lib/efi_loader/efi_variable.c @@ -148,7 +148,7 @@ static const char *parse_attr(const char *str, u32 *attrp) } /** - * efi_efi_get_variable() - retrieve value of a UEFI variable + * efi_get_variable() - retrieve value of a UEFI variable * * This function implements the GetVariable runtime service. * @@ -404,7 +404,7 @@ efi_status_t EFIAPI efi_get_next_variable_name(efi_uintn_t *variable_name_size, } /** - * efi_efi_set_variable() - set value of a UEFI variable + * efi_set_variable() - set value of a UEFI variable * * This function implements the SetVariable runtime service. * diff --git a/lib/efi_selftest/efi_selftest_gop.c b/lib/efi_selftest/efi_selftest_gop.c index 4ad043c597..d64294ac79 100644 --- a/lib/efi_selftest/efi_selftest_gop.c +++ b/lib/efi_selftest/efi_selftest_gop.c @@ -80,6 +80,11 @@ static int execute(void) } efi_st_printf("Mode %u: %u x %u\n", i, info->width, info->height); + ret = boottime->free_pool(info); + if (ret != EFI_SUCCESS) { + efi_st_printf("FreePool failed"); + return EFI_ST_FAILURE; + } } return EFI_ST_SUCCESS;