With the plethora of new command-line options, it is starting to get difficult to remember them all. This commit introduces shell completions for bash and zsh for the convenience of the user.
Instead of writing the completion files by hand (a tedious task), the files are generated automatically from a Python spec using shtab [1]. The latter is stored as a git submodule, making it possible to generate the completion files at build time without having to install shtab (which is typically not available in package managers). [1] https://github.com/iterative/shtab Signed-off-by: Michael Adler <[email protected]> --- .gitmodules | 3 ++ Makefile.am | 39 +++++++++++++++++++++++++- completion/.gitignore | 2 ++ completion/bg_printenv/cli.py | 31 +++++++++++++++++++++ completion/bg_printenv/common.py | 1 + completion/bg_setenv/cli.py | 47 ++++++++++++++++++++++++++++++++ completion/bg_setenv/common.py | 1 + completion/common.py | 23 ++++++++++++++++ completion/shtab | 1 + tools/bg_envtools.h | 1 + tools/bg_printenv.c | 1 + tools/bg_setenv.c | 1 + 12 files changed, 150 insertions(+), 1 deletion(-) create mode 100644 completion/.gitignore create mode 100644 completion/bg_printenv/cli.py create mode 120000 completion/bg_printenv/common.py create mode 100644 completion/bg_setenv/cli.py create mode 120000 completion/bg_setenv/common.py create mode 100644 completion/common.py create mode 160000 completion/shtab diff --git a/.gitmodules b/.gitmodules index 80ad11c..143b8cb 100644 --- a/.gitmodules +++ b/.gitmodules @@ -1,3 +1,6 @@ [submodule "tests/fff"] path = tests/fff url = https://github.com/meekrosoft/fff +[submodule "completion/shtab"] + path = completion/shtab + url = https://github.com/iterative/shtab.git diff --git a/Makefile.am b/Makefile.am index 8081839..385d326 100644 --- a/Makefile.am +++ b/Makefile.am @@ -38,6 +38,8 @@ ARFLAGS = cr EXTRA_DIST = autogen.sh README LICENSE CLEANFILES = +PYTHON ?= python3 + define filechk $(AM_V_at)set -e; \ echo ' CHK $@'; \ @@ -253,7 +255,42 @@ bg_printenvdir = $(top_srcdir) bg_printenv: $(bg_setenv) $(AM_V_at)$(LN_S) -f bg_setenv bg_printenv -all-local: bg_printenv +BASH_COMPLETION_FILES := $(top_builddir)/completion/bash/bg_setenv.bash $(top_builddir)/completion/bash/bg_printenv.bash +ZSH_COMPLETION_FILES := $(top_builddir)/completion/zsh/_bg_setenv $(top_builddir)/completion/zsh/_bg_printenv + +bashcompletiondir = ${datarootdir}/efibootguard/completion/bash +bashcompletion_DATA = $(BASH_COMPLETION_FILES) + +zshcompletiondir = ${datarootdir}/efibootguard/completion/zsh +zshcompletion_DATA = $(ZSH_COMPLETION_FILES) + +.PHONY: bash-completion +bash-completion: $(BASH_COMPLETION_FILES) + +.PHONY: zsh-completion +zsh-completion: $(ZSH_COMPLETION_FILES) + +$(top_builddir)/completion/bash/bg_setenv.bash: ${top_srcdir}/completion/bg_setenv/cli.py + @mkdir -p $(@D) + -env PYTHONPATH=${top_srcdir}/completion/shtab:${top_srcdir}/completion \ + $(PYTHON) -m shtab --shell=bash -u "bg_setenv.cli.bg_setenv" >$@ + +$(top_builddir)/completion/bash/bg_printenv.bash: ${top_srcdir}/completion/bg_printenv/cli.py + @mkdir -p $(@D) + -env PYTHONPATH=${top_srcdir}/completion/shtab:${top_srcdir}/completion \ + $(PYTHON) -m shtab --shell=bash "bg_printenv.cli.bg_printenv" >$@ + +$(top_builddir)/completion/zsh/_bg_setenv: ${top_srcdir}/completion/bg_setenv/cli.py + @mkdir -p $(@D) + -env PYTHONPATH=${top_srcdir}/completion/shtab:${top_srcdir}/completion \ + $(PYTHON) -m shtab --shell=zsh -u "bg_setenv.cli.bg_setenv" >$@ + +$(top_builddir)/completion/zsh/_bg_printenv: ${top_srcdir}/completion/bg_printenv/cli.py + @mkdir -p $(@D) + -env PYTHONPATH=${top_srcdir}/completion/shtab:${top_srcdir}/completion \ + $(PYTHON) -m shtab --shell=zsh -u "bg_printenv.cli.bg_printenv" >$@ + +all-local: bg_printenv bash-completion zsh-completion CLEANFILES += bg_printenv diff --git a/completion/.gitignore b/completion/.gitignore new file mode 100644 index 0000000..b731cd1 --- /dev/null +++ b/completion/.gitignore @@ -0,0 +1,2 @@ +!bg_printenv +!bg_setenv diff --git a/completion/bg_printenv/cli.py b/completion/bg_printenv/cli.py new file mode 100644 index 0000000..570faf9 --- /dev/null +++ b/completion/bg_printenv/cli.py @@ -0,0 +1,31 @@ +# +# Copyright (c) Siemens AG, 2021 +# +# Authors: +# Michael Adler <[email protected]> +# +# This work is licensed under the terms of the GNU GPL, version 2. See +# the COPYING file in the top-level directory. +# +# SPDX-License-Identifier: GPL-2.0 + +import argparse + +from .common import add_common_opts + + +def bg_printenv(): + parser = argparse.ArgumentParser(prog="bg_printenv", add_help=False) + add_common_opts(parser) + parser.add_argument("-c", "--current", action="store_true", help="Only print values from the current environment") + parser.add_argument( + "-o", + "--output", + choices=["in_progress", "revision", "kernel", "kernelargs", "watchdog_timeout", "ustate", "user"], + help="Comma-separated list of fields which are printed", + ) + parser.add_argument("-r", "--raw", action="store_true", help="Raw output mode") + parser.add_argument("--usage", action="store_true", help="Give a short usage message") + return parser + + diff --git a/completion/bg_printenv/common.py b/completion/bg_printenv/common.py new file mode 120000 index 0000000..a11703e --- /dev/null +++ b/completion/bg_printenv/common.py @@ -0,0 +1 @@ +../common.py \ No newline at end of file diff --git a/completion/bg_setenv/cli.py b/completion/bg_setenv/cli.py new file mode 100644 index 0000000..9698882 --- /dev/null +++ b/completion/bg_setenv/cli.py @@ -0,0 +1,47 @@ +# +# Copyright (c) Siemens AG, 2021 +# +# Authors: +# Michael Adler <[email protected]> +# +# This work is licensed under the terms of the GNU GPL, version 2. See +# the COPYING file in the top-level directory. +# +# SPDX-License-Identifier: GPL-2.0 + +import argparse + +from .common import add_common_opts + + +def bg_setenv(): + parser = argparse.ArgumentParser(prog="bg_setenv", add_help=False) + add_common_opts(parser) + parser.add_argument("-P", "--preserve", action="store_true", help="Preserve existing entries") + parser.add_argument("-k", "--kernel", metavar="KERNEL", help="Set kernel to load") + parser.add_argument("-a", "--args", metavar="KERNEL_ARGS", help="Set kernel arguments") + parser.add_argument("-r", "--revision", metavar="REVISION", help="Set revision value") + parser.add_argument( + "-s", + "--ustate", + choices=["OK", "INSTALLED", "TESTING", "FAILED", "UNKNOWN"], + metavar="USTATE", + help="Set update status for environment", + ) + parser.add_argument("-w", "--watchdog", metavar="WATCHDOG_TIMEOUT", help="Watchdog timeout in seconds") + parser.add_argument("-c", "--confirm", action="store_true", help="Confirm working environment") + parser.add_argument("-u", "--update", action="store_true", help="Automatically update oldest revision") + parser.add_argument( + "-x", + "--uservar", + metavar="KEY=VAL", + help="Set user-defined string variable. For setting multiple variables, use this option multiple times.", + ) + parser.add_argument( + "-i", + "--in_progress", + metavar="IN_PROGRESS", + choices=["0", "1"], + help="Set in_progress variable to simulate a running update process.", + ) + return parser diff --git a/completion/bg_setenv/common.py b/completion/bg_setenv/common.py new file mode 120000 index 0000000..a11703e --- /dev/null +++ b/completion/bg_setenv/common.py @@ -0,0 +1 @@ +../common.py \ No newline at end of file diff --git a/completion/common.py b/completion/common.py new file mode 100644 index 0000000..8134aef --- /dev/null +++ b/completion/common.py @@ -0,0 +1,23 @@ +# +# Copyright (c) Siemens AG, 2021 +# +# Authors: +# Michael Adler <[email protected]> +# +# This work is licensed under the terms of the GNU GPL, version 2. See +# the COPYING file in the top-level directory. +# +# SPDX-License-Identifier: GPL-2.0 + +import shtab + + +def add_common_opts(parser): + parser.add_argument( + "-f", "--filepath", metavar="ENVFILE", help="Environment to use. Expects a file name, usually called BGENV.DAT." + ).complete = shtab.FILE + parser.add_argument("-p", "--part", metavar="ENV_PART", type=int, help="Set environment partition to update") + parser.add_argument("-v", "--verbose", action="store_true", help="Be verbose") + parser.add_argument("-V", "--version", action="store_true", help="Print version") + # there is a bug in shtab which currently prohibits "-?" + parser.add_argument("--help", action="store_true", help="Show help") diff --git a/completion/shtab b/completion/shtab new file mode 160000 index 0000000..5af77eb --- /dev/null +++ b/completion/shtab @@ -0,0 +1 @@ +Subproject commit 5af77eb7ead3fa55346887ada65097b03c359c28 diff --git a/tools/bg_envtools.h b/tools/bg_envtools.h index a397ca4..c7d42e5 100644 --- a/tools/bg_envtools.h +++ b/tools/bg_envtools.h @@ -23,6 +23,7 @@ name, key, arg, flags, doc \ } +/* if you change these, do not forget to update completion/common.py */ #define BG_CLI_OPTIONS_COMMON \ OPT("filepath", 'f', "ENVFILE", 0, \ "Environment to use. Expects a file name, " \ diff --git a/tools/bg_printenv.c b/tools/bg_printenv.c index 61152dc..40dd893 100644 --- a/tools/bg_printenv.c +++ b/tools/bg_printenv.c @@ -21,6 +21,7 @@ static char tool_doc[] = "bg_printenv - Environment tool for the EFI Boot Guard"; +/* if you change these, do not forget to update completion/bg_printenv/cli.py */ static struct argp_option options_printenv[] = { BG_CLI_OPTIONS_COMMON, OPT("current", 'c', 0, 0, diff --git a/tools/bg_setenv.c b/tools/bg_setenv.c index ab9673e..c789fcc 100644 --- a/tools/bg_setenv.c +++ b/tools/bg_setenv.c @@ -25,6 +25,7 @@ static char tool_doc[] = "bg_setenv - Environment tool for the EFI Boot Guard"; + /* if you change these, do not forget to update completion/bg_setenv/cli.py */ static struct argp_option options_setenv[] = { BG_CLI_OPTIONS_COMMON, OPT("preserve", 'P', 0, 0, "Preserve existing entries"), -- 2.33.1 -- You received this message because you are subscribed to the Google Groups "EFI Boot Guard" group. To unsubscribe from this group and stop receiving emails from it, send an email to [email protected]. To view this discussion on the web visit https://groups.google.com/d/msgid/efibootguard-dev/20211112102803.391261-1-michael.adler%40siemens.com.
