From: AKASHI Takahiro <takahiro.akashi@linaro.org>
To: u-boot@lists.denx.de
Subject: [RFC PATCH 3/3] efidebug: add multiple device path instances on Boot####
Date: Thu, 14 Jan 2021 14:11:33 +0900 [thread overview]
Message-ID: <20210114051133.GC25252@laputa> (raw)
In-Reply-To: <20210113111149.64567-4-ilias.apalodimas@linaro.org>
Ilias,
On Wed, Jan 13, 2021 at 01:11:49PM +0200, Ilias Apalodimas wrote:
> The UEFI spec allow a packed array of UEFI device paths in the
> FilePathList[] of an EFI_LOAD_OPTION. The first file path must
> describe the laoded image but the rest are OS specific.
> Previous patches parse the device path and try to use the second
> member of the array as an initrd. So let's modify efidebug slightly
> and install the second file described in the command line as the
> initrd device path.
I have a concern about your proposed command line syntax.
It takes a lot of parameters as a whole which makes it
hard to understand it at a glance, easily overflowing
the width of terminal window.
It will even get worse if we want to take dtb as a third
device path, and what if we want to specify dtb, but not initrd?
Moreover, if we want to add support for non-linux executabes which
utilize extra device paths (neither initrd nor dtb) in a boot
load option, the syntax will be problematic.
> Signed-off-by: Ilias Apalodimas <ilias.apalodimas@linaro.org>
> ---
> cmd/efidebug.c | 89 +++++++++++++++++++++++++++++++++++++++++++++-----
> 1 file changed, 81 insertions(+), 8 deletions(-)
>
> diff --git a/cmd/efidebug.c b/cmd/efidebug.c
> index 5fb7b1e3c6a9..8d62981aca92 100644
> --- a/cmd/efidebug.c
> +++ b/cmd/efidebug.c
> @@ -8,6 +8,7 @@
> #include <charset.h>
> #include <common.h>
> #include <command.h>
> +#include <efi_helper.h>
> #include <efi_loader.h>
> #include <efi_rng.h>
> #include <exports.h>
> @@ -17,6 +18,7 @@
> #include <mapmem.h>
> #include <search.h>
> #include <linux/ctype.h>
> +#include <linux/err.h>
>
> #define BS systab.boottime
> #define RT systab.runtime
> @@ -782,6 +784,42 @@ static int do_efi_show_tables(struct cmd_tbl *cmdtp, int flag,
> return CMD_RET_SUCCESS;
> }
>
> +/**
> + * add_initrd_instance() - Append a device path to load_options pointing to an
> + * inirtd
> + *
> + * @argc: Number of arguments
> + * @argv: Argument array
> + * @file_path Existing device path, the new instance will be appended
> + * Return: Pointer to the device path or ERR_PTR
> + *
> + */
> +static struct efi_device_path *add_initrd_instance(int argc, char *const argv[],
> + struct efi_device_path *file_path)
> +{
> + struct efi_device_path *tmp_dp = NULL, *tmp_fp = NULL;
> + struct efi_device_path *final_fp = NULL;
> + efi_status_t ret;
> +
> + if (argc < 8)
> + return ERR_PTR(-EINVAL);
> +
> + ret = efi_dp_from_name(argv[6], argv[7], argv[8], &tmp_dp,
> + &tmp_fp);
> + if (ret != EFI_SUCCESS) {
> + printf("Cannot create device path for \"%s %s\"\n",
> + argv[6], argv[7]);
> + goto out;
> + }
> +
> + final_fp = efi_dp_append_instance(file_path, tmp_fp);
> +
> +out:
> + efi_free_pool(tmp_dp);
> + efi_free_pool(tmp_fp);
> + return final_fp ? final_fp : ERR_PTR(-EINVAL);
> +}
> +
> /**
> * do_efi_boot_add() - set UEFI load option
> *
> @@ -794,7 +832,11 @@ static int do_efi_show_tables(struct cmd_tbl *cmdtp, int flag,
> *
> * Implement efidebug "boot add" sub-command. Create or change UEFI load option.
> *
> - * efidebug boot add <id> <label> <interface> <devnum>[:<part>] <file> <options>
> + * Without initrd:
> + * efidebug boot add <id> <label> <interface> <devnum>[:<part>] <file> <options>
> + *
> + * With initrd:
> + * efidebug boot add <id> <label> <interface> <devnum>[:<part>] <file> <interface2> <devnum2>[:<part>] <initrd> <options>
> */
> static int do_efi_boot_add(struct cmd_tbl *cmdtp, int flag,
> int argc, char *const argv[])
> @@ -807,13 +849,14 @@ static int do_efi_boot_add(struct cmd_tbl *cmdtp, int flag,
> size_t label_len, label_len16;
> u16 *label;
> struct efi_device_path *device_path = NULL, *file_path = NULL;
> + struct efi_device_path *final_fp = NULL;
> struct efi_load_option lo;
> void *data = NULL;
> efi_uintn_t size;
> efi_status_t ret;
> int r = CMD_RET_SUCCESS;
>
> - if (argc < 6 || argc > 7)
> + if (argc < 6 || argc > 9)
> return CMD_RET_USAGE;
>
> id = (int)simple_strtoul(argv[1], &endp, 16);
> @@ -829,6 +872,12 @@ static int do_efi_boot_add(struct cmd_tbl *cmdtp, int flag,
> /* attributes */
> lo.attributes = LOAD_OPTION_ACTIVE; /* always ACTIVE */
>
> + /* optional data */
> + if (argc == 6)
> + lo.optional_data = NULL;
> + else
> + lo.optional_data = (const u8 *)argv[6];
> +
> /* label */
> label_len = strlen(argv[2]);
> label_len16 = utf8_utf16_strnlen(argv[2], label_len);
> @@ -847,15 +896,30 @@ static int do_efi_boot_add(struct cmd_tbl *cmdtp, int flag,
> r = CMD_RET_FAILURE;
> goto out;
> }
> +
> + /* add initrd instance in device path */
> + if (argc >= 9) {
> + final_fp = add_initrd_instance(argc, argv, file_path);
We'd better pass argv[6], argv[7] and argv[8] explicitly here,
which will make the code readable and easily extended to support
dtb in the future.
then,
argc -= 3;
argv += 3;
> + if (IS_ERR(final_fp)) {
> + r = CMD_RET_FAILURE;
> + goto out;
> + }
> +
> + /* add_initrd_instance allocates a new device path */
> + efi_free_pool(file_path);
> + file_path = final_fp;
> +
> + /* update optional data */
Then, the code should be moved out of this 'if' clause.
> + if (argc == 9)
> + lo.optional_data = NULL;
> + else
> + lo.optional_data = (const u8 *)argv[9];
> + }
> +
> lo.file_path = file_path;
> lo.file_path_length = efi_dp_size(file_path)
> + sizeof(struct efi_device_path); /* for END */
>
> - /* optional data */
> - if (argc == 6)
> - lo.optional_data = NULL;
> - else
> - lo.optional_data = (const u8 *)argv[6];
The code should remain here for non-initrd case.
-Takahiro Akashi
>
> size = efi_serialize_load_option(&lo, (u8 **)&data);
> if (!size) {
> @@ -939,11 +1003,13 @@ static int do_efi_boot_rm(struct cmd_tbl *cmdtp, int flag,
> */
> static void show_efi_boot_opt_data(u16 *varname16, void *data, size_t *size)
> {
> + struct efi_device_path *initrd_path = NULL;
> struct efi_load_option lo;
> char *label, *p;
> size_t label_len16, label_len;
> u16 *dp_str;
> efi_status_t ret;
> + efi_uintn_t initrd_dp_size;
>
> ret = efi_deserialize_load_option(&lo, data, size);
> if (ret != EFI_SUCCESS) {
> @@ -973,6 +1039,13 @@ static void show_efi_boot_opt_data(u16 *varname16, void *data, size_t *size)
> dp_str = efi_dp_str(lo.file_path);
> printf(" file_path: %ls\n", dp_str);
> efi_free_pool(dp_str);
> + initrd_path = efi_dp_instance_by_idx(lo.file_path, &initrd_dp_size, INITRD_DP);
> + if (initrd_path) {
> + dp_str = efi_dp_str(initrd_path);
> + printf(" initrd_path: %ls\n", dp_str);
> + efi_free_pool(dp_str);
> + efi_free_pool(initrd_path);
> + }
>
> printf(" data:\n");
> print_hex_dump(" ", DUMP_PREFIX_OFFSET, 16, 1,
> @@ -1583,7 +1656,7 @@ static char efidebug_help_text[] =
> #endif
>
> U_BOOT_CMD(
> - efidebug, 10, 0, do_efidebug,
> + efidebug, CONFIG_SYS_MAXARGS, 0, do_efidebug,
> "Configure UEFI environment",
> efidebug_help_text
> );
> --
> 2.30.0.rc2
>
next prev parent reply other threads:[~2021-01-14 5:11 UTC|newest]
Thread overview: 21+ messages / expand[flat|nested] mbox.gz Atom feed top
2021-01-13 11:11 [RFC 0/3] Change logic of EFI LoadFile2 protocol for initrd loading Ilias Apalodimas
2021-01-13 11:11 ` [RFC PATCH 1/3] efi_loader: Introduce helper functions for EFI Ilias Apalodimas
2021-01-13 12:41 ` Heinrich Schuchardt
2021-01-13 13:30 ` Ilias Apalodimas
2021-01-14 4:48 ` AKASHI Takahiro
2021-01-14 4:57 ` Heinrich Schuchardt
2021-01-14 10:54 ` Ilias Apalodimas
2021-01-14 9:46 ` Ilias Apalodimas
2021-01-13 11:11 ` [RFC PATCH 2/3] efi_loader: efi_loader: Replace config option for initrd loading Ilias Apalodimas
2021-01-13 13:08 ` Heinrich Schuchardt
2021-01-13 13:23 ` Ilias Apalodimas
2021-01-14 4:23 ` AKASHI Takahiro
2021-01-14 9:40 ` Ilias Apalodimas
2021-01-13 11:11 ` [RFC PATCH 3/3] efidebug: add multiple device path instances on Boot#### Ilias Apalodimas
2021-01-13 13:13 ` Heinrich Schuchardt
2021-01-13 13:21 ` Ilias Apalodimas
2021-01-14 5:11 ` AKASHI Takahiro [this message]
2021-01-14 9:55 ` Ilias Apalodimas
2021-01-14 12:07 ` Heinrich Schuchardt
2021-01-14 12:36 ` Ilias Apalodimas
2021-01-15 2:16 ` AKASHI Takahiro
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20210114051133.GC25252@laputa \
--to=takahiro.akashi@linaro.org \
--cc=u-boot@lists.denx.de \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.