diff --git a/libfwupd/fwupd-enums.c b/libfwupd/fwupd-enums.c index 933766aeb..d6f871e7d 100644 --- a/libfwupd/fwupd-enums.c +++ b/libfwupd/fwupd-enums.c @@ -368,6 +368,8 @@ fwupd_device_problem_to_string(FwupdDeviceProblem device_problem) return "missing-license"; if (device_problem == FWUPD_DEVICE_PROBLEM_SYSTEM_INHIBIT) return "system-inhibit"; + if (device_problem == FWUPD_DEVICE_PROBLEM_UPDATE_IN_PROGRESS) + return "update-in-process"; if (device_problem == FWUPD_DEVICE_PROBLEM_UNKNOWN) return "unknown"; return NULL; @@ -406,6 +408,8 @@ fwupd_device_problem_from_string(const gchar *device_problem) return FWUPD_DEVICE_PROBLEM_MISSING_LICENSE; if (g_strcmp0(device_problem, "system-inhibit") == 0) return FWUPD_DEVICE_PROBLEM_SYSTEM_INHIBIT; + if (g_strcmp0(device_problem, "update-in-process") == 0) + return FWUPD_DEVICE_PROBLEM_UPDATE_IN_PROGRESS; return FWUPD_DEVICE_PROBLEM_UNKNOWN; } diff --git a/libfwupd/fwupd-enums.h b/libfwupd/fwupd-enums.h index af96ab6e3..dc0165e1b 100644 --- a/libfwupd/fwupd-enums.h +++ b/libfwupd/fwupd-enums.h @@ -631,6 +631,14 @@ typedef guint64 FwupdDeviceFlags; * Since 1.8.10 */ #define FWUPD_DEVICE_PROBLEM_SYSTEM_INHIBIT (1llu << 8) +/** + * FWUPD_DEVICE_PROBLEM_UPDATE_IN_PROGRESS: + * + * The device cannot be updated as it is already being updated. + * + * Since 1.8.11 + */ +#define FWUPD_DEVICE_PROBLEM_UPDATE_IN_PROGRESS (1llu << 9) /** * FWUPD_DEVICE_PROBLEM_UNKNOWN: * diff --git a/libfwupd/fwupd-self-test.c b/libfwupd/fwupd-self-test.c index 2468efbe9..64d813362 100644 --- a/libfwupd/fwupd-self-test.c +++ b/libfwupd/fwupd-self-test.c @@ -164,7 +164,7 @@ fwupd_enums_func(void) g_assert_cmpstr(tmp, !=, NULL); g_assert_cmpint(fwupd_device_flag_from_string(tmp), ==, i); } - for (guint64 i = 1; i <= FWUPD_DEVICE_PROBLEM_SYSTEM_INHIBIT; i *= 2) { + for (guint64 i = 1; i <= FWUPD_DEVICE_PROBLEM_UPDATE_IN_PROGRESS; i *= 2) { const gchar *tmp = fwupd_device_problem_to_string(i); if (tmp == NULL) g_warning("missing device problem 0x%x", (guint)i); diff --git a/libfwupdplugin/fu-device.c b/libfwupdplugin/fu-device.c index ce3dfb07d..9831e91fd 100644 --- a/libfwupdplugin/fu-device.c +++ b/libfwupdplugin/fu-device.c @@ -2926,6 +2926,8 @@ fu_device_problem_to_inhibit_reason(FuDevice *self, guint64 device_problem) return g_strdup("Device cannot be used while the lid is closed"); if (device_problem == FWUPD_DEVICE_PROBLEM_IS_EMULATED) return g_strdup("Device is emulated"); + if (device_problem == FWUPD_DEVICE_PROBLEM_UPDATE_IN_PROGRESS) + return g_strdup("An update is in progress"); if (device_problem == FWUPD_DEVICE_PROBLEM_MISSING_LICENSE) return g_strdup("Device does not have the necessary license installed"); if (device_problem == FWUPD_DEVICE_PROBLEM_SYSTEM_POWER_TOO_LOW) { diff --git a/src/fu-device-list.c b/src/fu-device-list.c index c8364e6f1..d7f4f0fb9 100644 --- a/src/fu-device-list.c +++ b/src/fu-device-list.c @@ -12,6 +12,7 @@ #include "fu-device-list.h" #include "fu-device-private.h" +#include "fu-engine.h" #include "fu-mutex.h" /** @@ -605,6 +606,16 @@ fu_device_list_clear_wait_for_replug(FuDeviceList *self, FuDeviceItem *item) } } +static void +fu_device_incorporate_problem_update_in_progress(FuDevice *self, FuDevice *donor) +{ + if (fu_device_has_inhibit(donor, "update-in-progress")) { + g_debug("moving inhibit update-in-progress to active device"); + fu_device_add_problem(self, FWUPD_DEVICE_PROBLEM_UPDATE_IN_PROGRESS); + fu_device_remove_problem(donor, FWUPD_DEVICE_PROBLEM_UPDATE_IN_PROGRESS); + } +} + static void fu_device_incorporate_update_state(FuDevice *self, FuDevice *donor) { @@ -646,6 +657,9 @@ fu_device_list_replace(FuDeviceList *self, FuDeviceItem *item, FuDevice *device) fu_device_set_private_flags(device, private_flags); } + /* copy inhibit */ + fu_device_incorporate_problem_update_in_progress(item->device, device); + /* copy over the version strings if not set */ if (fu_device_get_version(item->device) != NULL && fu_device_get_version(device) == NULL) { const gchar *version = fu_device_get_version(item->device); @@ -744,6 +758,8 @@ fu_device_list_add(FuDeviceList *self, FuDevice *device) g_debug("found existing device %s", fu_device_get_id(device)); if (device != item->device) { fu_device_uninhibit(item->device, "unconnected"); + fu_device_incorporate_problem_update_in_progress(device, + item->device); fu_device_incorporate_update_state(device, item->device); fu_device_list_item_set_device(item, device); } @@ -757,6 +773,7 @@ fu_device_list_add(FuDeviceList *self, FuDevice *device) g_strcmp0(fu_device_get_id(device), fu_device_get_id(item->device_old)) == 0) { g_debug("found old device %s, swapping", fu_device_get_id(device)); fu_device_uninhibit(item->device, "unconnected"); + fu_device_incorporate_problem_update_in_progress(device, item->device); fu_device_incorporate_update_state(device, item->device); g_set_object(&item->device_old, item->device); fu_device_list_item_set_device(item, device); diff --git a/src/fu-engine.c b/src/fu-engine.c index 5d4255b60..d3fea1420 100644 --- a/src/fu-engine.c +++ b/src/fu-engine.c @@ -3138,7 +3138,7 @@ fu_engine_prepare(FuEngine *self, g_prefix_error(error, "failed to get device before update prepare: "); return FALSE; } - fu_device_inhibit(device, "update-in-progress", "An update is in progress"); + fu_device_add_problem(device, FWUPD_DEVICE_PROBLEM_UPDATE_IN_PROGRESS); if (!fu_engine_device_check_power(self, device, flags, error)) return FALSE; @@ -3178,7 +3178,7 @@ fu_engine_cleanup(FuEngine *self, g_prefix_error(error, "failed to get device before update cleanup: "); return FALSE; } - fu_device_uninhibit(device, "update-in-progress"); + fu_device_remove_problem(device, FWUPD_DEVICE_PROBLEM_UPDATE_IN_PROGRESS); str = fu_device_to_string(device); g_debug("cleanup -> %s", str); if (!fu_engine_device_cleanup(self, device, progress, flags, error)) diff --git a/src/fu-util-common.c b/src/fu-util-common.c index 630cc16c3..9eb4913af 100644 --- a/src/fu-util-common.c +++ b/src/fu-util-common.c @@ -1410,6 +1410,10 @@ fu_util_device_problem_to_string(FwupdClient *client, FwupdDevice *dev, FwupdDev /* TRANSLATORS: an application is preventing system updates */ return g_strdup(_("All devices are prevented from update by system inhibit")); } + if (problem == FWUPD_DEVICE_PROBLEM_UPDATE_IN_PROGRESS) { + /* TRANSLATORS: another application is updating the device already */ + return g_strdup(_("An update is in progress")); + } return NULL; }