Return an error when the user does not select an OS, so we know whether
to boot or not.
Move calling of bootflow_menu_run() into a separate function so we can
call it from other places.
Expand the test to cover these cases.
Add some documentation also, while we are here.
Signed-off-by: Simon Glass
---
Changes in v3:
- Add missing word 'function' in the commit message
Changes in v2:
- Add new patch to add a return code to bootflow menu
cmd/bootflow.c | 53 +++---
doc/usage/cmd/bootflow.rst | 67 ++
test/boot/bootflow.c | 15 +
3 files changed, 123 insertions(+), 12 deletions(-)
diff --git a/cmd/bootflow.c b/cmd/bootflow.c
index 300ad3aaa760..1516f8a4193b 100644
--- a/cmd/bootflow.c
+++ b/cmd/bootflow.c
@@ -89,6 +89,44 @@ static void show_footer(int count, int num_valid)
num_valid);
}
+/**
+ * bootflow_handle_menu() - Handle running the menu and updating cur bootflow
+ *
+ * This shows the menu, allows the user to select something and then prints
+ * what happened
+ *
+ * @std: bootstd information
+ * @text_mode: true to run the menu in text mode
+ * @bflowp: Returns selected bootflow, on success
+ * Return: 0 on success (a bootflow was selected), -EAGAIN if nothing was
+ * chosen, other -ve value on other error
+ */
+__maybe_unused static int bootflow_handle_menu(struct bootstd_priv *std,
+ bool text_mode,
+ struct bootflow **bflowp)
+{
+ struct bootflow *bflow;
+ int ret;
+
+ ret = bootflow_menu_run(std, text_mode, );
+ if (ret) {
+ if (ret == -EAGAIN) {
+ printf("Nothing chosen\n");
+ std->cur_bootflow = NULL;
+ } else {
+ printf("Menu failed (err=%d)\n", ret);
+ }
+
+ return ret;
+ }
+
+ printf("Selected: %s\n", bflow->os_name ? bflow->os_name : bflow->name);
+ std->cur_bootflow = bflow;
+ *bflowp = bflow;
+
+ return 0;
+}
+
static int do_bootflow_scan(struct cmd_tbl *cmdtp, int flag, int argc,
char *const argv[])
{
@@ -455,18 +493,9 @@ static int do_bootflow_menu(struct cmd_tbl *cmdtp, int
flag, int argc,
if (ret)
return CMD_RET_FAILURE;
- ret = bootflow_menu_run(std, text_mode, );
- if (ret) {
- if (ret == -EAGAIN)
- printf("Nothing chosen\n");
- else {
- printf("Menu failed (err=%d)\n", ret);
- return CMD_RET_FAILURE;
- }
- }
-
- printf("Selected: %s\n", bflow->os_name ? bflow->os_name : bflow->name);
- std->cur_bootflow = bflow;
+ ret = bootflow_handle_menu(std, text_mode, );
+ if (ret)
+ return CMD_RET_FAILURE;
return 0;
}
diff --git a/doc/usage/cmd/bootflow.rst b/doc/usage/cmd/bootflow.rst
index ead493d0aaf8..6a0645c28d07 100644
--- a/doc/usage/cmd/bootflow.rst
+++ b/doc/usage/cmd/bootflow.rst
@@ -15,6 +15,7 @@ Synopis
bootflow read
bootflow boot
bootflow cmdline [set|get|clear|delete|auto] []
+bootfloe menu [-t]
Description
---
@@ -24,6 +25,9 @@ locate bootflows, list them and boot them.
See :doc:`../../develop/bootstd` for more information.
+Note that `CONFIG_BOOTSTD_FULL` (which enables `CONFIG_CMD_BOOTFLOW_FULL) must
+be enabled to obtain full functionality with this command. Otherwise, it only
+supports `bootflow scan` which scans and boots the first available bootflow.
bootflow scan
~
@@ -247,6 +251,16 @@ can be used to set the early console (or console) to a
suitable value so that
output appears on the serial port. This is only supported by the 16550 serial
driver so far.
+bootflow menu
+~
+
+This shows a menu with available bootflows. The user can select a particular
+bootflow, which then becomes the current one.
+
+The `-t` flag requests a text menu. Otherwise, if a display is available, a
+graphical menu is shown.
+
+
Example
---
@@ -658,6 +672,56 @@ Now the buffer can be accessed::
77b7e4e0: 320fc000 08e8ba0f c031300f b8df ...2.01.
77b7e4f0: 0020 6ad8000f 00858d10 5002 ..j...P
+This shows using a text menu to boot an OS::
+
+=> bootflow scan
+=> bootfl list
+=> bootfl menu -t
+U-Boot:Boot Menu
+
+UP and DOWN to choose, ENTER to select
+
+ >0 mmc1mmc1.bootdev.whole
+ 1 mmc1Fedora-Workstation-armhfp-31-1.9
(5.3.7-301.fc31.armv7hl)
+ 2 mmc1mmc1.bootdev.part_1
+ 3 mmc4mmc4.bootdev.whole
+ 4 mmc4Armbian
+ 5 mmc4mmc4.bootdev.part_1
+ 6 mmc5mmc5.bootdev.whole
+ 7 mmc5ChromeOS
+ 8