From: Mark Pearson Date: Mon, 28 Jun 2021 22:28:46 +0000 (-0400) Subject: platform/x86: think-lmi: Add pending_reboot support X-Git-Url: http://git.maquefel.me/?a=commitdiff_plain;h=95d429206c97cf109591009fa386004191c62c47;p=linux.git platform/x86: think-lmi: Add pending_reboot support The Think-lmi driver was missing pending_reboot support as it wasn't available from the BIOS. Turns out this is really useful to have from user space so implementing from a purely SW point of view. Thanks to Mario Limonciello for guidance on how fwupd would use this. Suggested-by: Mario Limonciello Signed-off-by: Mark Pearson Reviewed-by: Hans de Goede Link: https://lore.kernel.org/r/20210628222846.8830-1-markpearson@lenovo.com Signed-off-by: Hans de Goede --- diff --git a/drivers/platform/x86/think-lmi.c b/drivers/platform/x86/think-lmi.c index 3671b5d206132..64dcec53a7a05 100644 --- a/drivers/platform/x86/think-lmi.c +++ b/drivers/platform/x86/think-lmi.c @@ -571,6 +571,11 @@ static ssize_t current_value_store(struct kobject *kobj, else ret = tlmi_save_bios_settings(""); + if (!ret && !tlmi_priv.pending_changes) { + tlmi_priv.pending_changes = true; + /* let userland know it may need to check reboot pending again */ + kobject_uevent(&tlmi_priv.class_dev->kobj, KOBJ_CHANGE); + } out: kfree(auth_str); kfree(set_str); @@ -647,6 +652,14 @@ static struct kobj_type tlmi_pwd_setting_ktype = { .sysfs_ops = &tlmi_kobj_sysfs_ops, }; +static ssize_t pending_reboot_show(struct kobject *kobj, struct kobj_attribute *attr, + char *buf) +{ + return sprintf(buf, "%d\n", tlmi_priv.pending_changes); +} + +static struct kobj_attribute pending_reboot = __ATTR_RO(pending_reboot); + /* ---- Initialisation --------------------------------------------------------- */ static void tlmi_release_attr(void) { @@ -667,6 +680,7 @@ static void tlmi_release_attr(void) sysfs_remove_group(&tlmi_priv.pwd_power->kobj, &auth_attr_group); kobject_put(&tlmi_priv.pwd_power->kobj); kset_unregister(tlmi_priv.authentication_kset); + sysfs_remove_file(&tlmi_priv.class_dev->kobj, &pending_reboot.attr); } static int tlmi_sysfs_init(void) @@ -746,6 +760,11 @@ static int tlmi_sysfs_init(void) if (ret) goto fail_create_attr; + /* Create global sysfs files */ + ret = sysfs_create_file(&tlmi_priv.class_dev->kobj, &pending_reboot.attr); + if (ret) + goto fail_create_attr; + return ret; fail_create_attr: diff --git a/drivers/platform/x86/think-lmi.h b/drivers/platform/x86/think-lmi.h index 6fa8da7af6c78..eb598846628a6 100644 --- a/drivers/platform/x86/think-lmi.h +++ b/drivers/platform/x86/think-lmi.h @@ -60,6 +60,7 @@ struct think_lmi { bool can_get_bios_selections; bool can_set_bios_password; bool can_get_password_settings; + bool pending_changes; struct tlmi_attr_setting *setting[TLMI_SETTINGS_COUNT]; struct device *class_dev;