2024-03-25 15:52:58

by Luke D. Jones

[permalink] [raw]
Subject: [PATCH 0/9] asus-wmi: add new features, clean up, fixes

This patch series touches quite a few things along with adding support for some
new features.

- Add support for mini-LED on 2024 ROG lpatops
- Add support for the gpu MUX WMI call on Vivobook laptops
- Add support for the POST boot sound on ROG laptops
- Add support for MCU power-save (ROG Ally only, saves more power on suspend)
- Store written values for ppt_* features
- Small formatting cleanup
- Small fixes to cleanup struct holes found with pahole

Obsoletes:
- https://lore.kernel.org/all/[email protected]/
- https://lore.kernel.org/all/[email protected]/
- https://lore.kernel.org/all/[email protected]/
- https://lore.kernel.org/all/[email protected]/
- https://lore.kernel.org/all/[email protected]/

Luke D. Jones (9):
platform/x86: asus-wmi: add support for 2024 ROG Mini-LED
platform/x86: asus-wmi: add support for Vivobook GPU MUX
platform/x86: asus-wmi: add support variant of TUF RGB
platform/x86: asus-wmi: support toggling POST sound
platform/x86: asus-wmi: store a min default for ppt options
platform/x86: asus-wmi: adjust formatting of ppt-<name>() functions
platform/x86: asus-wmi: ROG Ally increase wait time, allow MCU
powersave
platform/x86: asus-wmi: Add support for MCU powersave
platform/x86: asus-wmi: cleanup main struct to avoid some holes

.../ABI/testing/sysfs-platform-asus-wmi | 26 ++
drivers/platform/x86/asus-wmi.c | 386 ++++++++++++++----
include/linux/platform_data/x86/asus-wmi.h | 6 +
3 files changed, 339 insertions(+), 79 deletions(-)

--
2.44.0



2024-03-25 15:56:45

by Luke D. Jones

[permalink] [raw]
Subject: [PATCH 4/9] platform/x86: asus-wmi: support toggling POST sound

Add support for toggling the BIOS POST sound on some ASUS laptops.

Signed-off-by: Luke D. Jones <[email protected]>
---
.../ABI/testing/sysfs-platform-asus-wmi | 9 ++++
drivers/platform/x86/asus-wmi.c | 51 +++++++++++++++++++
include/linux/platform_data/x86/asus-wmi.h | 3 ++
3 files changed, 63 insertions(+)

diff --git a/Documentation/ABI/testing/sysfs-platform-asus-wmi b/Documentation/ABI/testing/sysfs-platform-asus-wmi
index 61a745d2476f..5645dbac4ce8 100644
--- a/Documentation/ABI/testing/sysfs-platform-asus-wmi
+++ b/Documentation/ABI/testing/sysfs-platform-asus-wmi
@@ -194,3 +194,12 @@ Contact: "Luke Jones" <[email protected]>
Description:
Set the target temperature limit of the Nvidia dGPU:
* min=75, max=87
+
+What: /sys/devices/platform/<platform>/boot_sound
+Date: Jun 2023
+KernelVersion: 6.10
+Contact: "Luke Jones" <[email protected]>
+Description:
+ Set if the BIOS POST sound is played on boot.
+ * 0 - False,
+ * 1 - True
\ No newline at end of file
diff --git a/drivers/platform/x86/asus-wmi.c b/drivers/platform/x86/asus-wmi.c
index 094a93f24667..6cac9c3eb8b2 100644
--- a/drivers/platform/x86/asus-wmi.c
+++ b/drivers/platform/x86/asus-wmi.c
@@ -2106,6 +2106,54 @@ static ssize_t panel_od_store(struct device *dev,
}
static DEVICE_ATTR_RW(panel_od);

+/* Bootup sound ***************************************************************/
+
+static ssize_t boot_sound_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct asus_wmi *asus = dev_get_drvdata(dev);
+ int result;
+
+ result = asus_wmi_get_devstate_simple(asus, ASUS_WMI_DEVID_BOOT_SOUND);
+ if (result < 0)
+ return result;
+
+ return sysfs_emit(buf, "%d\n", result);
+}
+
+static ssize_t boot_sound_store(struct device *dev,
+ struct device_attribute *attr,
+ const char *buf, size_t count)
+{
+ int result, err;
+ u32 snd;
+
+ struct asus_wmi *asus = dev_get_drvdata(dev);
+
+ result = kstrtou32(buf, 10, &snd);
+ if (result)
+ return result;
+
+ if (snd > 1)
+ return -EINVAL;
+
+ err = asus_wmi_set_devstate(ASUS_WMI_DEVID_BOOT_SOUND, snd, &result);
+ if (err) {
+ pr_warn("Failed to set boot sound: %d\n", err);
+ return err;
+ }
+
+ if (result > 1) {
+ pr_warn("Failed to set panel boot sound (result): 0x%x\n", result);
+ return -EIO;
+ }
+
+ sysfs_notify(&asus->platform_device->dev.kobj, NULL, "boot_sound");
+
+ return count;
+}
+static DEVICE_ATTR_RW(boot_sound);
+
/* Mini-LED mode **************************************************************/
static ssize_t mini_led_mode_show(struct device *dev,
struct device_attribute *attr, char *buf)
@@ -4227,6 +4275,7 @@ static struct attribute *platform_attributes[] = {
&dev_attr_ppt_platform_sppt.attr,
&dev_attr_nv_dynamic_boost.attr,
&dev_attr_nv_temp_target.attr,
+ &dev_attr_boot_sound.attr,
&dev_attr_panel_od.attr,
&dev_attr_mini_led_mode.attr,
&dev_attr_available_mini_led_mode.attr,
@@ -4279,6 +4328,8 @@ static umode_t asus_sysfs_is_visible(struct kobject *kobj,
ok = asus->nv_dyn_boost_available;
else if (attr == &dev_attr_nv_temp_target.attr)
ok = asus->nv_temp_tgt_available;
+ else if (attr == &dev_attr_boot_sound.attr)
+ devid = ASUS_WMI_DEVID_BOOT_SOUND;
else if (attr == &dev_attr_panel_od.attr)
ok = asus->panel_overdrive_available;
else if (attr == &dev_attr_mini_led_mode.attr)
diff --git a/include/linux/platform_data/x86/asus-wmi.h b/include/linux/platform_data/x86/asus-wmi.h
index 3e9a01467c67..3eb5cd6773ad 100644
--- a/include/linux/platform_data/x86/asus-wmi.h
+++ b/include/linux/platform_data/x86/asus-wmi.h
@@ -137,6 +137,9 @@
/* TUF laptop RGB power/state */
#define ASUS_WMI_DEVID_TUF_RGB_STATE 0x00100057

+/* Bootup sound control */
+#define ASUS_WMI_DEVID_BOOT_SOUND 0x00130022
+
/* DSTS masks */
#define ASUS_WMI_DSTS_STATUS_BIT 0x00000001
#define ASUS_WMI_DSTS_UNKNOWN_BIT 0x00000002
--
2.44.0


2024-03-25 16:10:32

by Luke D. Jones

[permalink] [raw]
Subject: [PATCH 5/9] platform/x86: asus-wmi: store a min default for ppt options

Laptops with any of the ppt or nv tunables default to the minimum setting
on boot so we can safely assume a stored value is correct.

This patch adds storing of those values in the local struct, and enables
reading of those values back. To prevent creating a series of byte holes
in the struct the "<name>_available" bool is removed and
`asus_sysfs_is_visible()` uses the `ASUS_WMI_DEVID_<name>` directly.

Signed-off-by: Luke D. Jones <[email protected]>
---
drivers/platform/x86/asus-wmi.c | 127 +++++++++++++++++++++++++-------
1 file changed, 99 insertions(+), 28 deletions(-)

diff --git a/drivers/platform/x86/asus-wmi.c b/drivers/platform/x86/asus-wmi.c
index 6cac9c3eb8b2..1e369b673a72 100644
--- a/drivers/platform/x86/asus-wmi.c
+++ b/drivers/platform/x86/asus-wmi.c
@@ -271,13 +271,13 @@ struct asus_wmi {
u32 gpu_mux_dev;

/* Tunables provided by ASUS for gaming laptops */
- bool ppt_pl2_sppt_available;
- bool ppt_pl1_spl_available;
- bool ppt_apu_sppt_available;
- bool ppt_plat_sppt_available;
- bool ppt_fppt_available;
- bool nv_dyn_boost_available;
- bool nv_temp_tgt_available;
+ u32 ppt_pl2_sppt;
+ u32 ppt_pl1_spl;
+ u32 ppt_apu_sppt;
+ u32 ppt_platform_sppt;
+ u32 ppt_fppt;
+ u32 nv_dynamic_boost;
+ u32 nv_temp_target;

bool kbd_rgb_mode_available;
u32 kbd_rgb_dev;
@@ -1021,11 +1021,21 @@ static ssize_t ppt_pl2_sppt_store(struct device *dev,
return -EIO;
}

+ asus->ppt_pl2_sppt = value;
sysfs_notify(&asus->platform_device->dev.kobj, NULL, "ppt_pl2_sppt");

return count;
}
-static DEVICE_ATTR_WO(ppt_pl2_sppt);
+
+static ssize_t ppt_pl2_sppt_show(struct device *dev,
+ struct device_attribute *attr,
+ char *buf)
+{
+ struct asus_wmi *asus = dev_get_drvdata(dev);
+
+ return sysfs_emit(buf, "%d\n", asus->ppt_pl2_sppt);
+}
+static DEVICE_ATTR_RW(ppt_pl2_sppt);

/* Tunable: PPT, Intel=PL1, AMD=SPL ******************************************/
static ssize_t ppt_pl1_spl_store(struct device *dev,
@@ -1055,11 +1065,20 @@ static ssize_t ppt_pl1_spl_store(struct device *dev,
return -EIO;
}

+ asus->ppt_pl1_spl = value;
sysfs_notify(&asus->platform_device->dev.kobj, NULL, "ppt_pl1_spl");

return count;
}
-static DEVICE_ATTR_WO(ppt_pl1_spl);
+static ssize_t ppt_pl1_spl_show(struct device *dev,
+ struct device_attribute *attr,
+ char *buf)
+{
+ struct asus_wmi *asus = dev_get_drvdata(dev);
+
+ return sysfs_emit(buf, "%d\n", asus->ppt_pl1_spl);
+}
+static DEVICE_ATTR_RW(ppt_pl1_spl);

/* Tunable: PPT APU FPPT ******************************************************/
static ssize_t ppt_fppt_store(struct device *dev,
@@ -1089,11 +1108,21 @@ static ssize_t ppt_fppt_store(struct device *dev,
return -EIO;
}

+ asus->ppt_fppt = value;
sysfs_notify(&asus->platform_device->dev.kobj, NULL, "ppt_fpu_sppt");

return count;
}
-static DEVICE_ATTR_WO(ppt_fppt);
+
+static ssize_t ppt_fppt_show(struct device *dev,
+ struct device_attribute *attr,
+ char *buf)
+{
+ struct asus_wmi *asus = dev_get_drvdata(dev);
+
+ return sysfs_emit(buf, "%d\n", asus->ppt_fppt);
+}
+static DEVICE_ATTR_RW(ppt_fppt);

/* Tunable: PPT APU SPPT *****************************************************/
static ssize_t ppt_apu_sppt_store(struct device *dev,
@@ -1123,11 +1152,21 @@ static ssize_t ppt_apu_sppt_store(struct device *dev,
return -EIO;
}

+ asus->ppt_apu_sppt = value;
sysfs_notify(&asus->platform_device->dev.kobj, NULL, "ppt_apu_sppt");

return count;
}
-static DEVICE_ATTR_WO(ppt_apu_sppt);
+
+static ssize_t ppt_apu_sppt_show(struct device *dev,
+ struct device_attribute *attr,
+ char *buf)
+{
+ struct asus_wmi *asus = dev_get_drvdata(dev);
+
+ return sysfs_emit(buf, "%d\n", asus->ppt_apu_sppt);
+}
+static DEVICE_ATTR_RW(ppt_apu_sppt);

/* Tunable: PPT platform SPPT ************************************************/
static ssize_t ppt_platform_sppt_store(struct device *dev,
@@ -1157,11 +1196,21 @@ static ssize_t ppt_platform_sppt_store(struct device *dev,
return -EIO;
}

+ asus->ppt_platform_sppt = value;
sysfs_notify(&asus->platform_device->dev.kobj, NULL, "ppt_platform_sppt");

return count;
}
-static DEVICE_ATTR_WO(ppt_platform_sppt);
+
+static ssize_t ppt_platform_sppt_show(struct device *dev,
+ struct device_attribute *attr,
+ char *buf)
+{
+ struct asus_wmi *asus = dev_get_drvdata(dev);
+
+ return sysfs_emit(buf, "%d\n", asus->ppt_platform_sppt);
+}
+static DEVICE_ATTR_RW(ppt_platform_sppt);

/* Tunable: NVIDIA dynamic boost *********************************************/
static ssize_t nv_dynamic_boost_store(struct device *dev,
@@ -1191,11 +1240,21 @@ static ssize_t nv_dynamic_boost_store(struct device *dev,
return -EIO;
}

+ asus->nv_dynamic_boost = value;
sysfs_notify(&asus->platform_device->dev.kobj, NULL, "nv_dynamic_boost");

return count;
}
-static DEVICE_ATTR_WO(nv_dynamic_boost);
+
+static ssize_t nv_dynamic_boost_show(struct device *dev,
+ struct device_attribute *attr,
+ char *buf)
+{
+ struct asus_wmi *asus = dev_get_drvdata(dev);
+
+ return sysfs_emit(buf, "%d\n", asus->nv_dynamic_boost);
+}
+static DEVICE_ATTR_RW(nv_dynamic_boost);

/* Tunable: NVIDIA temperature target ****************************************/
static ssize_t nv_temp_target_store(struct device *dev,
@@ -1225,11 +1284,21 @@ static ssize_t nv_temp_target_store(struct device *dev,
return -EIO;
}

+ asus->nv_temp_target = value;
sysfs_notify(&asus->platform_device->dev.kobj, NULL, "nv_temp_target");

return count;
}
-static DEVICE_ATTR_WO(nv_temp_target);
+
+static ssize_t nv_temp_target_show(struct device *dev,
+ struct device_attribute *attr,
+ char *buf)
+{
+ struct asus_wmi *asus = dev_get_drvdata(dev);
+
+ return sysfs_emit(buf, "%d\n", asus->nv_temp_target);
+}
+static DEVICE_ATTR_RW(nv_temp_target);

/* Battery ********************************************************************/

@@ -4315,19 +4384,19 @@ static umode_t asus_sysfs_is_visible(struct kobject *kobj,
else if (attr == &dev_attr_throttle_thermal_policy.attr)
ok = asus->throttle_thermal_policy_available;
else if (attr == &dev_attr_ppt_pl2_sppt.attr)
- ok = asus->ppt_pl2_sppt_available;
+ devid = ASUS_WMI_DEVID_PPT_PL2_SPPT;
else if (attr == &dev_attr_ppt_pl1_spl.attr)
- ok = asus->ppt_pl1_spl_available;
+ devid = ASUS_WMI_DEVID_PPT_PL1_SPL;
else if (attr == &dev_attr_ppt_fppt.attr)
- ok = asus->ppt_fppt_available;
+ devid = ASUS_WMI_DEVID_PPT_FPPT;
else if (attr == &dev_attr_ppt_apu_sppt.attr)
- ok = asus->ppt_apu_sppt_available;
+ devid = ASUS_WMI_DEVID_PPT_APU_SPPT;
else if (attr == &dev_attr_ppt_platform_sppt.attr)
- ok = asus->ppt_plat_sppt_available;
+ devid = ASUS_WMI_DEVID_PPT_PLAT_SPPT;
else if (attr == &dev_attr_nv_dynamic_boost.attr)
- ok = asus->nv_dyn_boost_available;
+ devid = ASUS_WMI_DEVID_NV_DYN_BOOST;
else if (attr == &dev_attr_nv_temp_target.attr)
- ok = asus->nv_temp_tgt_available;
+ devid = ASUS_WMI_DEVID_NV_THERM_TARGET;
else if (attr == &dev_attr_boot_sound.attr)
devid = ASUS_WMI_DEVID_BOOT_SOUND;
else if (attr == &dev_attr_panel_od.attr)
@@ -4588,18 +4657,20 @@ static int asus_wmi_add(struct platform_device *pdev)
if (err)
goto fail_platform;

+ /* ensure defaults for tunables */
+ asus->ppt_pl2_sppt = 5;
+ asus->ppt_pl1_spl = 5;
+ asus->ppt_apu_sppt = 5;
+ asus->ppt_platform_sppt = 5;
+ asus->ppt_fppt = 5;
+ asus->nv_dynamic_boost = 5;
+ asus->nv_temp_target = 75;
+
asus->charge_mode_available = asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_CHARGE_MODE);
asus->egpu_enable_available = asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_EGPU);
asus->egpu_connect_available = asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_EGPU_CONNECTED);
asus->dgpu_disable_available = asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_DGPU);
asus->kbd_rgb_state_available = asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_TUF_RGB_STATE);
- asus->ppt_pl2_sppt_available = asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_PPT_PL2_SPPT);
- asus->ppt_pl1_spl_available = asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_PPT_PL1_SPL);
- asus->ppt_fppt_available = asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_PPT_FPPT);
- asus->ppt_apu_sppt_available = asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_PPT_APU_SPPT);
- asus->ppt_plat_sppt_available = asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_PPT_PLAT_SPPT);
- asus->nv_dyn_boost_available = asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_NV_DYN_BOOST);
- asus->nv_temp_tgt_available = asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_NV_THERM_TARGET);
asus->panel_overdrive_available = asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_PANEL_OD);
asus->ally_mcu_usb_switch = acpi_has_method(NULL, ASUS_USB0_PWR_EC0_CSEE)
&& dmi_match(DMI_BOARD_NAME, "RC71L");
--
2.44.0


2024-03-25 16:19:36

by Ilpo Järvinen

[permalink] [raw]
Subject: Re: [PATCH 4/9] platform/x86: asus-wmi: support toggling POST sound

On Mon, 25 Mar 2024, Luke D. Jones wrote:

> Add support for toggling the BIOS POST sound on some ASUS laptops.
>
> Signed-off-by: Luke D. Jones <[email protected]>
> ---
> .../ABI/testing/sysfs-platform-asus-wmi | 9 ++++
> drivers/platform/x86/asus-wmi.c | 51 +++++++++++++++++++
> include/linux/platform_data/x86/asus-wmi.h | 3 ++
> 3 files changed, 63 insertions(+)
>
> diff --git a/Documentation/ABI/testing/sysfs-platform-asus-wmi b/Documentation/ABI/testing/sysfs-platform-asus-wmi
> index 61a745d2476f..5645dbac4ce8 100644
> --- a/Documentation/ABI/testing/sysfs-platform-asus-wmi
> +++ b/Documentation/ABI/testing/sysfs-platform-asus-wmi
> @@ -194,3 +194,12 @@ Contact: "Luke Jones" <[email protected]>
> Description:
> Set the target temperature limit of the Nvidia dGPU:
> * min=75, max=87
> +
> +What: /sys/devices/platform/<platform>/boot_sound
> +Date: Jun 2023
> +KernelVersion: 6.10
> +Contact: "Luke Jones" <[email protected]>
> +Description:
> + Set if the BIOS POST sound is played on boot.
> + * 0 - False,
> + * 1 - True
> \ No newline at end of file
> diff --git a/drivers/platform/x86/asus-wmi.c b/drivers/platform/x86/asus-wmi.c
> index 094a93f24667..6cac9c3eb8b2 100644
> --- a/drivers/platform/x86/asus-wmi.c
> +++ b/drivers/platform/x86/asus-wmi.c
> @@ -2106,6 +2106,54 @@ static ssize_t panel_od_store(struct device *dev,
> }
> static DEVICE_ATTR_RW(panel_od);
>
> +/* Bootup sound ***************************************************************/
> +
> +static ssize_t boot_sound_show(struct device *dev,
> + struct device_attribute *attr, char *buf)
> +{
> + struct asus_wmi *asus = dev_get_drvdata(dev);
> + int result;
> +
> + result = asus_wmi_get_devstate_simple(asus, ASUS_WMI_DEVID_BOOT_SOUND);
> + if (result < 0)
> + return result;
> +
> + return sysfs_emit(buf, "%d\n", result);
> +}
> +
> +static ssize_t boot_sound_store(struct device *dev,
> + struct device_attribute *attr,
> + const char *buf, size_t count)
> +{
> + int result, err;
> + u32 snd;
> +
> + struct asus_wmi *asus = dev_get_drvdata(dev);
> +
> + result = kstrtou32(buf, 10, &snd);
> + if (result)
> + return result;
> +
> + if (snd > 1)
> + return -EINVAL;
> +
> + err = asus_wmi_set_devstate(ASUS_WMI_DEVID_BOOT_SOUND, snd, &result);
> + if (err) {
> + pr_warn("Failed to set boot sound: %d\n", err);
> + return err;
> + }
> +
> + if (result > 1) {
> + pr_warn("Failed to set panel boot sound (result): 0x%x\n", result);
> + return -EIO;
> + }
> +
> + sysfs_notify(&asus->platform_device->dev.kobj, NULL, "boot_sound");
> +
> + return count;
> +}
> +static DEVICE_ATTR_RW(boot_sound);

I started to think that perhaps these would be a way to create helper for
these sysfs functions to call as they are quite similar, only the wmi id,
strings and the range check change (the GPU functions do a few extra
checks and could remain standalone functions but the rest look very
similar to each other).

--
i.


2024-03-25 17:45:42

by Luke D. Jones

[permalink] [raw]
Subject: [PATCH 1/9] platform/x86: asus-wmi: add support for 2024 ROG Mini-LED

Support the 2024 mini-led backlight and adjust the related functions
to select the relevant dev-id. Also add `available_mini_led_mode` to the
platform sysfs since the available mini-led levels can be different.

Signed-off-by: Luke D. Jones <[email protected]>
---
.../ABI/testing/sysfs-platform-asus-wmi | 8 ++
drivers/platform/x86/asus-wmi.c | 74 +++++++++++++++++--
include/linux/platform_data/x86/asus-wmi.h | 1 +
3 files changed, 76 insertions(+), 7 deletions(-)

diff --git a/Documentation/ABI/testing/sysfs-platform-asus-wmi b/Documentation/ABI/testing/sysfs-platform-asus-wmi
index 8a7e25bde085..61a745d2476f 100644
--- a/Documentation/ABI/testing/sysfs-platform-asus-wmi
+++ b/Documentation/ABI/testing/sysfs-platform-asus-wmi
@@ -126,6 +126,14 @@ Description:
Change the mini-LED mode:
* 0 - Single-zone,
* 1 - Multi-zone
+ * 2 - Multi-zone strong (available on newer generation mini-led)
+
+What: /sys/devices/platform/<platform>/available_mini_led_mode
+Date: Jun 2023
+KernelVersion: 6.10
+Contact: "Luke Jones" <[email protected]>
+Description:
+ List the available mini-led modes.

What: /sys/devices/platform/<platform>/ppt_pl1_spl
Date: Jun 2023
diff --git a/drivers/platform/x86/asus-wmi.c b/drivers/platform/x86/asus-wmi.c
index 18be35fdb381..54ce0fb26f42 100644
--- a/drivers/platform/x86/asus-wmi.c
+++ b/drivers/platform/x86/asus-wmi.c
@@ -297,6 +297,7 @@ struct asus_wmi {

bool panel_overdrive_available;
bool mini_led_mode_available;
+ u32 mini_led_dev_id;

struct hotplug_slot hotplug_slot;
struct mutex hotplug_lock;
@@ -2109,10 +2110,27 @@ static ssize_t mini_led_mode_show(struct device *dev,
struct asus_wmi *asus = dev_get_drvdata(dev);
int result;

- result = asus_wmi_get_devstate_simple(asus, ASUS_WMI_DEVID_MINI_LED_MODE);
- if (result < 0)
- return result;
+ result = asus_wmi_get_devstate_simple(asus, asus->mini_led_dev_id);

+ /* Remap the mode values to match previous generation mini-led.
+ * Some BIOSes return -19 instead of 2, which is "mini-LED off", this
+ * appears to be a BIOS bug.
+ */
+ if (asus->mini_led_dev_id == ASUS_WMI_DEVID_MINI_LED_MODE2) {
+ switch (result) {
+ case 0:
+ result = 1;
+ break;
+ case 1:
+ result = 2;
+ break;
+ case 2:
+ case -19:
+ result = 0;
+ }
+ } else if (result < 0) {
+ return result;
+ }
return sysfs_emit(buf, "%d\n", result);
}

@@ -2129,11 +2147,28 @@ static ssize_t mini_led_mode_store(struct device *dev,
if (result)
return result;

- if (mode > 1)
+ if (mode > 1 && asus->mini_led_dev_id == ASUS_WMI_DEVID_MINI_LED_MODE)
return -EINVAL;
+ if (mode > 2 && asus->mini_led_dev_id == ASUS_WMI_DEVID_MINI_LED_MODE2)
+ return -EINVAL;
+ /*
+ * Remap the mode values so expected behaviour is the same as the last
+ * generation of mini-LED
+ */
+ if (asus->mini_led_dev_id == ASUS_WMI_DEVID_MINI_LED_MODE2) {
+ switch (mode) {
+ case 0:
+ mode = 2;
+ break;
+ case 1:
+ mode = 0;
+ break;
+ case 2:
+ mode = 1;
+ }
+ }

- err = asus_wmi_set_devstate(ASUS_WMI_DEVID_MINI_LED_MODE, mode, &result);
-
+ err = asus_wmi_set_devstate(asus->mini_led_dev_id, mode, &result);
if (err) {
pr_warn("Failed to set mini-LED: %d\n", err);
return err;
@@ -2150,6 +2185,23 @@ static ssize_t mini_led_mode_store(struct device *dev,
}
static DEVICE_ATTR_RW(mini_led_mode);

+static ssize_t available_mini_led_mode_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct asus_wmi *asus = dev_get_drvdata(dev);
+
+ switch (asus->mini_led_dev_id) {
+ case ASUS_WMI_DEVID_MINI_LED_MODE:
+ return sysfs_emit(buf, "0 1\n");
+ case ASUS_WMI_DEVID_MINI_LED_MODE2:
+ return sysfs_emit(buf, "0 1 2\n");
+ }
+
+ return sysfs_emit(buf, "0\n");
+}
+
+static DEVICE_ATTR_RO(available_mini_led_mode);
+
/* Quirks *********************************************************************/

static void asus_wmi_set_xusb2pr(struct asus_wmi *asus)
@@ -4174,6 +4226,7 @@ static struct attribute *platform_attributes[] = {
&dev_attr_nv_temp_target.attr,
&dev_attr_panel_od.attr,
&dev_attr_mini_led_mode.attr,
+ &dev_attr_available_mini_led_mode.attr,
NULL
};

@@ -4496,10 +4549,17 @@ static int asus_wmi_add(struct platform_device *pdev)
asus->nv_dyn_boost_available = asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_NV_DYN_BOOST);
asus->nv_temp_tgt_available = asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_NV_THERM_TARGET);
asus->panel_overdrive_available = asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_PANEL_OD);
- asus->mini_led_mode_available = asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_MINI_LED_MODE);
asus->ally_mcu_usb_switch = acpi_has_method(NULL, ASUS_USB0_PWR_EC0_CSEE)
&& dmi_match(DMI_BOARD_NAME, "RC71L");

+ if (asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_MINI_LED_MODE)) {
+ asus->mini_led_mode_available = true;
+ asus->mini_led_dev_id = ASUS_WMI_DEVID_MINI_LED_MODE;
+ } else if (asus_wmi_dev_is_present(asus, ASUS_WMI_DEVID_MINI_LED_MODE2)) {
+ asus->mini_led_mode_available = true;
+ asus->mini_led_dev_id = ASUS_WMI_DEVID_MINI_LED_MODE2;
+ }
+
err = fan_boost_mode_check_present(asus);
if (err)
goto fail_fan_boost_mode;
diff --git a/include/linux/platform_data/x86/asus-wmi.h b/include/linux/platform_data/x86/asus-wmi.h
index ab1c7deff118..9cadce10ad9a 100644
--- a/include/linux/platform_data/x86/asus-wmi.h
+++ b/include/linux/platform_data/x86/asus-wmi.h
@@ -71,6 +71,7 @@
#define ASUS_WMI_DEVID_LID_FLIP 0x00060062
#define ASUS_WMI_DEVID_LID_FLIP_ROG 0x00060077
#define ASUS_WMI_DEVID_MINI_LED_MODE 0x0005001E
+#define ASUS_WMI_DEVID_MINI_LED_MODE2 0x0005002E

/* Storage */
#define ASUS_WMI_DEVID_CARDREADER 0x00080013
--
2.44.0


2024-03-25 18:02:18

by Ilpo Järvinen

[permalink] [raw]
Subject: Re: [PATCH 4/9] platform/x86: asus-wmi: support toggling POST sound

On Mon, 25 Mar 2024, Luke D. Jones wrote:

> Add support for toggling the BIOS POST sound on some ASUS laptops.
>
> Signed-off-by: Luke D. Jones <[email protected]>
> ---
> .../ABI/testing/sysfs-platform-asus-wmi | 9 ++++
> drivers/platform/x86/asus-wmi.c | 51 +++++++++++++++++++
> include/linux/platform_data/x86/asus-wmi.h | 3 ++
> 3 files changed, 63 insertions(+)
>
> diff --git a/Documentation/ABI/testing/sysfs-platform-asus-wmi b/Documentation/ABI/testing/sysfs-platform-asus-wmi
> index 61a745d2476f..5645dbac4ce8 100644
> --- a/Documentation/ABI/testing/sysfs-platform-asus-wmi
> +++ b/Documentation/ABI/testing/sysfs-platform-asus-wmi
> @@ -194,3 +194,12 @@ Contact: "Luke Jones" <[email protected]>
> Description:
> Set the target temperature limit of the Nvidia dGPU:
> * min=75, max=87
> +
> +What: /sys/devices/platform/<platform>/boot_sound
> +Date: Jun 2023

2024? :-)

> +KernelVersion: 6.10
> +Contact: "Luke Jones" <[email protected]>
> +Description:
> + Set if the BIOS POST sound is played on boot.
> + * 0 - False,
> + * 1 - True
> \ No newline at end of file

Please add the new line.

Once those are fixed:

Reviewed-by: Ilpo J?rvinen <[email protected]>

--
i.

2024-03-25 20:07:27

by Ilpo Järvinen

[permalink] [raw]
Subject: Re: [PATCH 1/9] platform/x86: asus-wmi: add support for 2024 ROG Mini-LED

On Mon, 25 Mar 2024, Luke D. Jones wrote:

> Support the 2024 mini-led backlight and adjust the related functions
> to select the relevant dev-id. Also add `available_mini_led_mode` to the
> platform sysfs since the available mini-led levels can be different.
>
> Signed-off-by: Luke D. Jones <[email protected]>
> ---
> .../ABI/testing/sysfs-platform-asus-wmi | 8 ++
> drivers/platform/x86/asus-wmi.c | 74 +++++++++++++++++--
> include/linux/platform_data/x86/asus-wmi.h | 1 +
> 3 files changed, 76 insertions(+), 7 deletions(-)
>
> diff --git a/Documentation/ABI/testing/sysfs-platform-asus-wmi b/Documentation/ABI/testing/sysfs-platform-asus-wmi
> index 8a7e25bde085..61a745d2476f 100644
> --- a/Documentation/ABI/testing/sysfs-platform-asus-wmi
> +++ b/Documentation/ABI/testing/sysfs-platform-asus-wmi
> @@ -126,6 +126,14 @@ Description:
> Change the mini-LED mode:
> * 0 - Single-zone,
> * 1 - Multi-zone
> + * 2 - Multi-zone strong (available on newer generation mini-led)
> +
> +What: /sys/devices/platform/<platform>/available_mini_led_mode
> +Date: Jun 2023
> +KernelVersion: 6.10
> +Contact: "Luke Jones" <[email protected]>
> +Description:
> + List the available mini-led modes.
>
> What: /sys/devices/platform/<platform>/ppt_pl1_spl
> Date: Jun 2023
> diff --git a/drivers/platform/x86/asus-wmi.c b/drivers/platform/x86/asus-wmi.c
> index 18be35fdb381..54ce0fb26f42 100644
> --- a/drivers/platform/x86/asus-wmi.c
> +++ b/drivers/platform/x86/asus-wmi.c
> @@ -297,6 +297,7 @@ struct asus_wmi {
>
> bool panel_overdrive_available;
> bool mini_led_mode_available;
> + u32 mini_led_dev_id;
>
> struct hotplug_slot hotplug_slot;
> struct mutex hotplug_lock;
> @@ -2109,10 +2110,27 @@ static ssize_t mini_led_mode_show(struct device *dev,
> struct asus_wmi *asus = dev_get_drvdata(dev);
> int result;
>
> - result = asus_wmi_get_devstate_simple(asus, ASUS_WMI_DEVID_MINI_LED_MODE);
> - if (result < 0)
> - return result;
> + result = asus_wmi_get_devstate_simple(asus, asus->mini_led_dev_id);
>
> + /* Remap the mode values to match previous generation mini-led.
> + * Some BIOSes return -19 instead of 2, which is "mini-LED off", this
> + * appears to be a BIOS bug.
> + */
> + if (asus->mini_led_dev_id == ASUS_WMI_DEVID_MINI_LED_MODE2) {
> + switch (result) {
> + case 0:
> + result = 1;
> + break;
> + case 1:
> + result = 2;
> + break;
> + case 2:
> + case -19:

Can you confirm this -19 really does come from BIOS? Because I suspect
it's -ENODEV error code from from one of the functions on the driver side
(which is why I asked you to change it into -ENODEV).


--
i.


2024-03-25 20:36:28

by Luke D. Jones

[permalink] [raw]
Subject: Re: [PATCH 1/9] platform/x86: asus-wmi: add support for 2024 ROG Mini-LED



On Tue, 26 Mar 2024, at 2:47 AM, Ilpo Järvinen wrote:
> On Mon, 25 Mar 2024, Luke D. Jones wrote:
>
> > Support the 2024 mini-led backlight and adjust the related functions
> > to select the relevant dev-id. Also add `available_mini_led_mode` to the
> > platform sysfs since the available mini-led levels can be different.
> >
> > Signed-off-by: Luke D. Jones <[email protected]>
> > ---
> > .../ABI/testing/sysfs-platform-asus-wmi | 8 ++
> > drivers/platform/x86/asus-wmi.c | 74 +++++++++++++++++--
> > include/linux/platform_data/x86/asus-wmi.h | 1 +
> > 3 files changed, 76 insertions(+), 7 deletions(-)
> >
> > diff --git a/Documentation/ABI/testing/sysfs-platform-asus-wmi b/Documentation/ABI/testing/sysfs-platform-asus-wmi
> > index 8a7e25bde085..61a745d2476f 100644
> > --- a/Documentation/ABI/testing/sysfs-platform-asus-wmi
> > +++ b/Documentation/ABI/testing/sysfs-platform-asus-wmi
> > @@ -126,6 +126,14 @@ Description:
> > Change the mini-LED mode:
> > * 0 - Single-zone,
> > * 1 - Multi-zone
> > + * 2 - Multi-zone strong (available on newer generation mini-led)
> > +
> > +What: /sys/devices/platform/<platform>/available_mini_led_mode
> > +Date: Jun 2023
> > +KernelVersion: 6.10
> > +Contact: "Luke Jones" <[email protected]>
> > +Description:
> > + List the available mini-led modes.
> >
> > What: /sys/devices/platform/<platform>/ppt_pl1_spl
> > Date: Jun 2023
> > diff --git a/drivers/platform/x86/asus-wmi.c b/drivers/platform/x86/asus-wmi.c
> > index 18be35fdb381..54ce0fb26f42 100644
> > --- a/drivers/platform/x86/asus-wmi.c
> > +++ b/drivers/platform/x86/asus-wmi.c
> > @@ -297,6 +297,7 @@ struct asus_wmi {
> >
> > bool panel_overdrive_available;
> > bool mini_led_mode_available;
> > + u32 mini_led_dev_id;
> >
> > struct hotplug_slot hotplug_slot;
> > struct mutex hotplug_lock;
> > @@ -2109,10 +2110,27 @@ static ssize_t mini_led_mode_show(struct device *dev,
> > struct asus_wmi *asus = dev_get_drvdata(dev);
> > int result;
> >
> > - result = asus_wmi_get_devstate_simple(asus, ASUS_WMI_DEVID_MINI_LED_MODE);
> > - if (result < 0)
> > - return result;
> > + result = asus_wmi_get_devstate_simple(asus, asus->mini_led_dev_id);
> >
> > + /* Remap the mode values to match previous generation mini-led.
> > + * Some BIOSes return -19 instead of 2, which is "mini-LED off", this
> > + * appears to be a BIOS bug.
> > + */
> > + if (asus->mini_led_dev_id == ASUS_WMI_DEVID_MINI_LED_MODE2) {
> > + switch (result) {
> > + case 0:
> > + result = 1;
> > + break;
> > + case 1:
> > + result = 2;
> > + break;
> > + case 2:
> > + case -19:
>
> Can you confirm this -19 really does come from BIOS? Because I suspect
> it's -ENODEV error code from from one of the functions on the driver side
> (which is why I asked you to change it into -ENODEV).

Yes it does. It is rather annoying. What happens in this case is that `2` is written to the WMI endpoint to turn off the MINI-Led feature, this works fine and it is turned off, there are no errors from the write at all - verifying the accepted limits in dsdt also shows it is correct.

However, after that, the read fails once. And only if that `2` was written. `0` and `1` write fine, and read fine also. I hope I've managed to describe and clarify what I'm seeing here.

I'm happy to change -ENODEV. No problem, queued on my todo list.

Cheers,
Luke.

2024-03-25 20:41:26

by Luke D. Jones

[permalink] [raw]
Subject: Re: [PATCH 4/9] platform/x86: asus-wmi: support toggling POST sound

On Tue, 26 Mar 2024, at 3:02 AM, Ilpo Järvinen wrote:
> On Mon, 25 Mar 2024, Luke D. Jones wrote:
>
> > Add support for toggling the BIOS POST sound on some ASUS laptops.
> >
> > Signed-off-by: Luke D. Jones <[email protected]>
> > ---
> > .../ABI/testing/sysfs-platform-asus-wmi | 9 ++++
> > drivers/platform/x86/asus-wmi.c | 51 +++++++++++++++++++
> > include/linux/platform_data/x86/asus-wmi.h | 3 ++
> > 3 files changed, 63 insertions(+)
> >
> > diff --git a/Documentation/ABI/testing/sysfs-platform-asus-wmi b/Documentation/ABI/testing/sysfs-platform-asus-wmi
> > index 61a745d2476f..5645dbac4ce8 100644
> > --- a/Documentation/ABI/testing/sysfs-platform-asus-wmi
> > +++ b/Documentation/ABI/testing/sysfs-platform-asus-wmi
> > @@ -194,3 +194,12 @@ Contact: "Luke Jones" <[email protected]>
> > Description:
> > Set the target temperature limit of the Nvidia dGPU:
> > * min=75, max=87
> > +
> > +What: /sys/devices/platform/<platform>/boot_sound
> > +Date: Jun 2023
> > +KernelVersion: 6.10
> > +Contact: "Luke Jones" <[email protected]>
> > +Description:
> > + Set if the BIOS POST sound is played on boot.
> > + * 0 - False,
> > + * 1 - True
> > \ No newline at end of file
> > diff --git a/drivers/platform/x86/asus-wmi.c b/drivers/platform/x86/asus-wmi.c
> > index 094a93f24667..6cac9c3eb8b2 100644
> > --- a/drivers/platform/x86/asus-wmi.c
> > +++ b/drivers/platform/x86/asus-wmi.c
> > @@ -2106,6 +2106,54 @@ static ssize_t panel_od_store(struct device *dev,
> > }
> > static DEVICE_ATTR_RW(panel_od);
> >
> > +/* Bootup sound ***************************************************************/
> > +
> > +static ssize_t boot_sound_show(struct device *dev,
> > + struct device_attribute *attr, char *buf)
> > +{
> > + struct asus_wmi *asus = dev_get_drvdata(dev);
> > + int result;
> > +
> > + result = asus_wmi_get_devstate_simple(asus, ASUS_WMI_DEVID_BOOT_SOUND);
> > + if (result < 0)
> > + return result;
> > +
> > + return sysfs_emit(buf, "%d\n", result);
> > +}
> > +
> > +static ssize_t boot_sound_store(struct device *dev,
> > + struct device_attribute *attr,
> > + const char *buf, size_t count)
> > +{
> > + int result, err;
> > + u32 snd;
> > +
> > + struct asus_wmi *asus = dev_get_drvdata(dev);
> > +
> > + result = kstrtou32(buf, 10, &snd);
> > + if (result)
> > + return result;
> > +
> > + if (snd > 1)
> > + return -EINVAL;
> > +
> > + err = asus_wmi_set_devstate(ASUS_WMI_DEVID_BOOT_SOUND, snd, &result);
> > + if (err) {
> > + pr_warn("Failed to set boot sound: %d\n", err);
> > + return err;
> > + }
> > +
> > + if (result > 1) {
> > + pr_warn("Failed to set panel boot sound (result): 0x%x\n", result);
> > + return -EIO;
> > + }
> > +
> > + sysfs_notify(&asus->platform_device->dev.kobj, NULL, "boot_sound");
> > +
> > + return count;
> > +}
> > +static DEVICE_ATTR_RW(boot_sound);
>
> I started to think that perhaps these would be a way to create helper for
> these sysfs functions to call as they are quite similar, only the wmi id,
> strings and the range check change (the GPU functions do a few extra
> checks and could remain standalone functions but the rest look very
> similar to each other).

I absolutely agree. In rust I would have written function or macro by now. I'm working on this but won't submit until we've been through the existing chain and applied.

Looks like the entire asus-wmi could use some maintenance tbh, I'll do what I can.

Cheers,
Luke.

2024-03-26 11:49:33

by Ilpo Järvinen

[permalink] [raw]
Subject: Re: [PATCH 1/9] platform/x86: asus-wmi: add support for 2024 ROG Mini-LED

On Tue, 26 Mar 2024, Luke Jones wrote:
> On Tue, 26 Mar 2024, at 2:47 AM, Ilpo J?rvinen wrote:
> > On Mon, 25 Mar 2024, Luke D. Jones wrote:
> >
> > > Support the 2024 mini-led backlight and adjust the related functions
> > > to select the relevant dev-id. Also add `available_mini_led_mode` to the
> > > platform sysfs since the available mini-led levels can be different.
> > >
> > > Signed-off-by: Luke D. Jones <[email protected]>
> > > ---

> > > @@ -2109,10 +2110,27 @@ static ssize_t mini_led_mode_show(struct device *dev,
> > > struct asus_wmi *asus = dev_get_drvdata(dev);
> > > int result;
> > >
> > > - result = asus_wmi_get_devstate_simple(asus, ASUS_WMI_DEVID_MINI_LED_MODE);
> > > - if (result < 0)
> > > - return result;
> > > + result = asus_wmi_get_devstate_simple(asus, asus->mini_led_dev_id);
> > >
> > > + /* Remap the mode values to match previous generation mini-led.
> > > + * Some BIOSes return -19 instead of 2, which is "mini-LED off", this
> > > + * appears to be a BIOS bug.
> > > + */
> > > + if (asus->mini_led_dev_id == ASUS_WMI_DEVID_MINI_LED_MODE2) {
> > > + switch (result) {
> > > + case 0:
> > > + result = 1;
> > > + break;
> > > + case 1:
> > > + result = 2;
> > > + break;
> > > + case 2:
> > > + case -19:
> >
> > Can you confirm this -19 really does come from BIOS? Because I suspect
> > it's -ENODEV error code from from one of the functions on the driver side
> > (which is why I asked you to change it into -ENODEV).
>
> Yes it does. It is rather annoying. What happens in this case is that
> `2` is written to the WMI endpoint to turn off the MINI-Led feature,
> this works fine and it is turned off, there are no errors from the write
> at all - verifying the accepted limits in dsdt also shows it is correct.
>
> However, after that, the read fails once.

Hi,

I'm left a bit unsure how to interpret your response. If "read fails", it
would indicate that -ENODEV originates from asus_wmi_evaluate_method3(),
asus_wmi_get_devstate() or asus_wmi_get_devstate_bits(), not from BIOS? So
which way it is?

After reading some more code, I think I figured out the answer myself.
However, that raises another question... So lets now take a step back and
walk through the code:

Your patch does:
result = asus_wmi_get_devstate_simple(asus, asus->mini_led_dev_id);

asus_wmi_get_devstate_simple() calls asus_wmi_get_devstate_bits() with
ASUS_WMI_DSTS_STATUS_BIT mask that is 0x00000001.

If there's no error, retval is masked with that ASUS_WMI_DSTS_STATUS_BIT
forcing the return value to 0-1 range so:

a) I don't think -19 can originate from BIOS but comes from kernel side.
b) How can it ever return 2 (mini-LED off) ?????

> And only if that `2` was
> written. `0` and `1` write fine, and read fine also. I hope I've managed
> to describe and clarify what I'm seeing here.
>
> I'm happy to change -ENODEV. No problem, queued on my todo list.


--
i.

2024-03-27 03:01:53

by Luke D. Jones

[permalink] [raw]
Subject: Re: [PATCH 1/9] platform/x86: asus-wmi: add support for 2024 ROG Mini-LED

On Wed, 27 Mar 2024, at 12:49 AM, Ilpo Järvinen wrote:
> On Tue, 26 Mar 2024, Luke Jones wrote:
> > On Tue, 26 Mar 2024, at 2:47 AM, Ilpo Järvinen wrote:
> > > On Mon, 25 Mar 2024, Luke D. Jones wrote:
> > >
> > > > Support the 2024 mini-led backlight and adjust the related functions
> > > > to select the relevant dev-id. Also add `available_mini_led_mode` to the
> > > > platform sysfs since the available mini-led levels can be different.
> > > >
> > > > Signed-off-by: Luke D. Jones <[email protected]>
> > > > ---
>
> > > > @@ -2109,10 +2110,27 @@ static ssize_t mini_led_mode_show(struct device *dev,
> > > > struct asus_wmi *asus = dev_get_drvdata(dev);
> > > > int result;
> > > >
> > > > - result = asus_wmi_get_devstate_simple(asus, ASUS_WMI_DEVID_MINI_LED_MODE);
> > > > - if (result < 0)
> > > > - return result;
> > > > + result = asus_wmi_get_devstate_simple(asus, asus->mini_led_dev_id);
> > > >
> > > > + /* Remap the mode values to match previous generation mini-led.
> > > > + * Some BIOSes return -19 instead of 2, which is "mini-LED off", this
> > > > + * appears to be a BIOS bug.
> > > > + */
> > > > + if (asus->mini_led_dev_id == ASUS_WMI_DEVID_MINI_LED_MODE2) {
> > > > + switch (result) {
> > > > + case 0:
> > > > + result = 1;
> > > > + break;
> > > > + case 1:
> > > > + result = 2;
> > > > + break;
> > > > + case 2:
> > > > + case -19:
> > >
> > > Can you confirm this -19 really does come from BIOS? Because I suspect
> > > it's -ENODEV error code from from one of the functions on the driver side
> > > (which is why I asked you to change it into -ENODEV).
> >
> > Yes it does. It is rather annoying. What happens in this case is that
> > `2` is written to the WMI endpoint to turn off the MINI-Led feature,
> > this works fine and it is turned off, there are no errors from the write
> > at all - verifying the accepted limits in dsdt also shows it is correct.
> >
> > However, after that, the read fails once.
>
> Hi,
>
> I'm left a bit unsure how to interpret your response. If "read fails", it
> would indicate that -ENODEV originates from asus_wmi_evaluate_method3(),
> asus_wmi_get_devstate() or asus_wmi_get_devstate_bits(), not from BIOS? So
> which way it is?
>
> After reading some more code, I think I figured out the answer myself.
> However, that raises another question... So lets now take a step back and
> walk through the code:
>
> Your patch does:
> result = asus_wmi_get_devstate_simple(asus, asus->mini_led_dev_id);
>
> asus_wmi_get_devstate_simple() calls asus_wmi_get_devstate_bits() with
> ASUS_WMI_DSTS_STATUS_BIT mask that is 0x00000001.
>
> If there's no error, retval is masked with that ASUS_WMI_DSTS_STATUS_BIT
> forcing the return value to 0-1 range so:
>
> a) I don't think -19 can originate from BIOS but comes from kernel side.
> b) How can it ever return 2 (mini-LED off) ?????

You're right. *facepalm* *grumble*. Honestly if I were getting paid for this work I'd invest a bit more time in it and catch these silly little things myself.

I'll update the code with all feedback, including using a more appropriate WMI function whcih I really should have seen on my own.

Thank you for your time so far.