Allow 'fwupdmgr install' to install a specified firmware version

This also moves the 'local-install' action to a new verb, although we
fall back for compatibility.

Fixes https://github.com/fwupd/fwupd/issues/4514
This commit is contained in:
Richard Hughes 2022-04-12 11:22:00 +01:00
parent 55605a0d5e
commit 63f2e9ee28
2 changed files with 89 additions and 2 deletions

View File

@ -20,6 +20,7 @@ _fwupdmgr_cmd_list=(
'get-upgrades'
'get-plugins'
'install'
'local-install'
'modify-config'
'modify-remote'
'reinstall'
@ -82,6 +83,16 @@ _show_device_ids()
COMPREPLY+=( $(compgen -W "${description}" -- "$cur") )
}
_show_release_versions()
{
if ! command -v jq &> /dev/null; then
return 0
fi
local description
description="$(command fwupdmgr get-releases "$1" --json 2>/dev/null | jq '.Releases[].Version')"
COMPREPLY+=( $(compgen -W "${description}" -- "$cur") )
}
_show_remotes()
{
local remotes
@ -131,6 +142,18 @@ _fwupdmgr()
fi
;;
install)
#device ID
if [[ "$prev" = "${COMP_WORDS[2]}" ]]; then
_show_device_ids
#version
elif [[ "$prev" = "${COMP_WORDS[3]}" ]]; then
_show_release_versions "$prev"
#modifiers
else
_show_modifiers
fi
;;
local-install)
#find files
if [[ "$prev" = "$command" ]]; then
_filedir

View File

@ -1079,7 +1079,7 @@ fu_util_download(FuUtilPrivate *priv, gchar **values, GError **error)
}
static gboolean
fu_util_install(FuUtilPrivate *priv, gchar **values, GError **error)
fu_util_local_install(FuUtilPrivate *priv, gchar **values, GError **error)
{
const gchar *id;
g_autofree gchar *filename = NULL;
@ -2699,6 +2699,63 @@ fu_util_reinstall(FuUtilPrivate *priv, gchar **values, GError **error)
return fu_util_prompt_complete(priv->completion_flags, TRUE, error);
}
static gboolean
fu_util_install(FuUtilPrivate *priv, gchar **values, GError **error)
{
g_autoptr(FwupdDevice) dev = NULL;
g_autoptr(FwupdRelease) rel = NULL;
/* fall back for CLI compatibility */
if (g_strv_length(values) >= 1) {
if (g_file_test(values[0], G_FILE_TEST_EXISTS))
return fu_util_local_install(priv, values, error);
}
/* find device */
priv->filter_include |= FWUPD_DEVICE_FLAG_SUPPORTED;
dev = fu_util_get_device_or_prompt(priv, values, error);
if (dev == NULL)
return FALSE;
/* find release */
if (g_strv_length(values) >= 2) {
rel = fu_util_get_release_for_device_version(priv, dev, values[1], error);
if (rel == NULL)
return FALSE;
} else {
g_autoptr(GPtrArray) rels = NULL;
rels = fwupd_client_get_releases(priv->client,
fwupd_device_get_id(dev),
priv->cancellable,
error);
if (rels == NULL)
return FALSE;
rel = fu_util_prompt_for_release(priv, rels, error);
if (rel == NULL)
return FALSE;
}
/* allow all actions */
priv->current_operation = FU_UTIL_OPERATION_INSTALL;
priv->flags |= FWUPD_INSTALL_FLAG_ALLOW_REINSTALL;
priv->flags |= FWUPD_INSTALL_FLAG_ALLOW_OLDER;
if (!fu_util_update_device_with_release(priv, dev, rel, error))
return FALSE;
fu_util_display_current_message(priv);
/* send report if we're supposed to */
if (!fu_util_maybe_send_reports(priv, rel, error))
return FALSE;
/* we don't want to ask anything */
if (priv->no_reboot_check) {
g_debug("skipping reboot check");
return TRUE;
}
return fu_util_prompt_complete(priv->completion_flags, TRUE, error);
}
static gboolean
_g_str_equal0(gconstpointer str1, gconstpointer str2)
{
@ -3994,10 +4051,17 @@ main(int argc, char *argv[])
fu_util_cmd_array_add(cmd_array,
"install",
/* TRANSLATORS: command argument: uppercase, spaces->dashes */
_("[DEVICE-ID|GUID] [VERSION]"),
/* TRANSLATORS: command description */
_("Install a specific firmware version on a device"),
fu_util_install);
fu_util_cmd_array_add(cmd_array,
"local-install",
/* TRANSLATORS: command argument: uppercase, spaces->dashes */
_("FILE [DEVICE-ID|GUID]"),
/* TRANSLATORS: command description */
_("Install a firmware file on this hardware"),
fu_util_install);
fu_util_local_install);
fu_util_cmd_array_add(cmd_array,
"get-details",
/* TRANSLATORS: command argument: uppercase, spaces->dashes */