From patchwork Mon Feb 24 19:50:57 2025 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Antheas Kapenekakis X-Patchwork-Id: 13988866 Received: from linux1587.grserver.gr (linux1587.grserver.gr [185.138.42.100]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id D9E0D1DB346; Mon, 24 Feb 2025 19:51:11 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=185.138.42.100 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1740426674; cv=none; b=MuJHPPpKlpAVWA1VggGaq2senSqcY+dGK8TaAZHqwmfSwrpeAbaQh6uRZjNsHz09eCLFOmJwgnKoZiXF2Fusn5tjIJ5m7TM53tWKjVoAVOZgiEix4dhRTA+0gwd+RwcETQkdLTA8ntt5sOHWvZM78n6yPlQlJklJKVymOCd3HEs= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1740426674; c=relaxed/simple; bh=2YTWcc0RCWcvCxkwLHCXfMZ1V9B6DXDFvKiWKCbalHI=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=WMBu42vntghoOjqSRMzvchJhcIKj0/fEgIk+PMQlambVbLujsTc08ct+o8DtTJnaFfjqa0Cn7DEz4XTRYGYsp1qb41Jx9gUvqspDAK1ev/ffF1mAfeCVor2GDH0vDZcCvN/d7EsIVfAeL6+geCRwwEWlIWYl2d072wOQHTV+gAU= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=antheas.dev; spf=pass smtp.mailfrom=antheas.dev; dkim=pass (1024-bit key) header.d=antheas.dev header.i=@antheas.dev header.b=srfon7C2; arc=none smtp.client-ip=185.138.42.100 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=antheas.dev Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=antheas.dev Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=antheas.dev header.i=@antheas.dev header.b="srfon7C2" Received: from localhost.localdomain (unknown [IPv6:2a05:f6c2:511b:0:8d8a:5967:d692:ea4e]) by linux1587.grserver.gr (Postfix) with ESMTPSA id 4A5E12E02886; Mon, 24 Feb 2025 21:51:08 +0200 (EET) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=antheas.dev; s=default; t=1740426669; bh=E2QSzTezztxd6Ef0cZ8WmAoDrND7y6XUuooP7fVEXFI=; h=From:To:Subject; b=srfon7C2dPVlgEmPjo4bh/l1JXO2AJi38/c+s1goJbfqmTgXTX8GR0cNqfqIrbdyQ pFV5VJ0K/TR+rlVZyxLJhSfKI2SkW11uicKryckICiSEgXIw1efzpddx3qiArOSh5e vL+3UGJ8rJTWW0hGWQrYSZtYOuTrz81d9Qj6+Qic= Authentication-Results: linux1587.grserver.gr; spf=pass (sender IP is 2a05:f6c2:511b:0:8d8a:5967:d692:ea4e) smtp.mailfrom=lkml@antheas.dev smtp.helo=localhost.localdomain Received-SPF: pass (linux1587.grserver.gr: connection is authenticated) From: Antheas Kapenekakis To: mario.limonciello@amd.com, mpearson-lenovo@squebb.ca Cc: ilpo.jarvinen@linux.intel.com, lenb@kernel.org, linux-acpi@vger.kernel.org, linux-kernel@vger.kernel.org, platform-driver-x86@vger.kernel.org, rafael@kernel.org, hdegoede@redhat.com, me@kylegospodneti.ch, Antheas Kapenekakis Subject: [PATCH 1/3] ACPI: platform_profile: Add support for secondary handlers Date: Mon, 24 Feb 2025 20:50:57 +0100 Message-ID: <20250224195059.10185-2-lkml@antheas.dev> X-Mailer: git-send-email 2.48.1 In-Reply-To: <20250224195059.10185-1-lkml@antheas.dev> References: <20250224195059.10185-1-lkml@antheas.dev> Precedence: bulk X-Mailing-List: linux-acpi@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-PPP-Message-ID: <174042666945.466.7712161454235914871@linux1587.grserver.gr> X-PPP-Vhost: antheas.dev X-Virus-Scanned: clamav-milter 0.103.11 at linux1587.grserver.gr X-Virus-Status: Clean Currently, only the subset of supported profiles are exposed when using platform profile. This is a big problem when e.g., asus-wmi and amd-pmf are loaded together, as they have conflicting low power options. This causes ppd and tuned to miss the low power option increasing power consumption. Therefore, add the secondary variable. Profile handlers with it should accept all profile options always. Only when they are the sole handler, their probe function will be used to expose available profiles. Signed-off-by: Antheas Kapenekakis --- drivers/platform/x86/amd/pmf/sps.c | 1 + include/linux/platform_profile.h | 7 +++++++ 2 files changed, 8 insertions(+) diff --git a/drivers/platform/x86/amd/pmf/sps.c b/drivers/platform/x86/amd/pmf/sps.c index e6cf0b22dac3..424b146d3574 100644 --- a/drivers/platform/x86/amd/pmf/sps.c +++ b/drivers/platform/x86/amd/pmf/sps.c @@ -397,6 +397,7 @@ static int amd_pmf_profile_probe(void *drvdata, unsigned long *choices) } static const struct platform_profile_ops amd_pmf_profile_ops = { + .secondary = true, .probe = amd_pmf_profile_probe, .profile_get = amd_pmf_profile_get, .profile_set = amd_pmf_profile_set, diff --git a/include/linux/platform_profile.h b/include/linux/platform_profile.h index 8ab5b0e8eb2c..fef5f2404e9f 100644 --- a/include/linux/platform_profile.h +++ b/include/linux/platform_profile.h @@ -30,6 +30,12 @@ enum platform_profile_option { /** * struct platform_profile_ops - platform profile operations + * @secondary: Set the platform handler as a secondary. Secondary handlers + * should be able to accept all profile options. This way, they do + * not obscure the primary handler's profile options (such as amdpmf + * having cool and asus-wmi having quiet). When a secondary handler + * is the only handler available, its probe function is still used + * to avoid showing all profiles. * @probe: Callback to setup choices available to the new class device. These * choices will only be enforced when setting a new profile, not when * getting the current one. @@ -39,6 +45,7 @@ enum platform_profile_option { * profile in sysfs. */ struct platform_profile_ops { + bool secondary; int (*probe)(void *drvdata, unsigned long *choices); int (*profile_get)(struct device *dev, enum platform_profile_option *profile); int (*profile_set)(struct device *dev, enum platform_profile_option profile); From patchwork Mon Feb 24 19:50:58 2025 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Antheas Kapenekakis X-Patchwork-Id: 13988867 Received: from linux1587.grserver.gr (linux1587.grserver.gr [185.138.42.100]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id F0AAC1C6FE4; Mon, 24 Feb 2025 19:51:13 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=185.138.42.100 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1740426676; cv=none; b=iaFNI11fBqxtKL1gmfKSDq1SQ2aBOd4ghwYBDhOUfhQ5Ymue7zRdwJcJyjFJDjQv3NapUIaMTdkIx8z6tbal6F4KHB4sXnF6vMvckwle1k/xykwekCUdCMTcekkYrtroVm/VI4iJsKmWWFKBETaIFd2JonZ5AN7ktGpXAOP+aME= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1740426676; c=relaxed/simple; bh=pQIZI3RhskIemMuOi4mkO2phoUfcs3mClPk3IXZvoiM=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=I5n4+ItMZM/mGpDh1llrEr21d8zArqHnJaAdK7NClHP+wU+WsNcGqQJrinn0vQvPEFvCxwgjap3B75lcwzJfe9kKJOH1pOf0eKXR3anvIGRZeyUaehk+/5zwwyw8xSXKWD0/MAqtTFXu0eUtt2FqnpjGYOdTbbpwbUbgVFHjYNI= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=antheas.dev; spf=pass smtp.mailfrom=antheas.dev; dkim=pass (1024-bit key) header.d=antheas.dev header.i=@antheas.dev header.b=Ya/WmKqu; arc=none smtp.client-ip=185.138.42.100 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=antheas.dev Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=antheas.dev Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=antheas.dev header.i=@antheas.dev header.b="Ya/WmKqu" Received: from localhost.localdomain (unknown [IPv6:2a05:f6c2:511b:0:8d8a:5967:d692:ea4e]) by linux1587.grserver.gr (Postfix) with ESMTPSA id 0BECC2E09300; Mon, 24 Feb 2025 21:51:09 +0200 (EET) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=antheas.dev; s=default; t=1740426671; bh=+SO3o/KnLjaW2qevFdQUm8FDaUvLmpOi1YiDgAfUgBU=; h=From:To:Subject; b=Ya/WmKquGTu3gCnXsYLGsrr7JTqfN9U/WD+pgGQiVnsS3qu9ULoB48WGMic7xLN7P R/pRIMg3iCNx5ioK1yj4SKbWbzEVeg5saaNVy2cGG1qs5HDQ+QuL3H+dPbDs8iKev/ +YmW5rjtLKAnyQmtvj5scXZZfMzAXwXVZSEXYPH4= Authentication-Results: linux1587.grserver.gr; spf=pass (sender IP is 2a05:f6c2:511b:0:8d8a:5967:d692:ea4e) smtp.mailfrom=lkml@antheas.dev smtp.helo=localhost.localdomain Received-SPF: pass (linux1587.grserver.gr: connection is authenticated) From: Antheas Kapenekakis To: mario.limonciello@amd.com, mpearson-lenovo@squebb.ca Cc: ilpo.jarvinen@linux.intel.com, lenb@kernel.org, linux-acpi@vger.kernel.org, linux-kernel@vger.kernel.org, platform-driver-x86@vger.kernel.org, rafael@kernel.org, hdegoede@redhat.com, me@kylegospodneti.ch, Antheas Kapenekakis Subject: [PATCH 2/3] ACPI: platform_profile: add all options to amd-pmf as a secondary handler Date: Mon, 24 Feb 2025 20:50:58 +0100 Message-ID: <20250224195059.10185-3-lkml@antheas.dev> X-Mailer: git-send-email 2.48.1 In-Reply-To: <20250224195059.10185-1-lkml@antheas.dev> References: <20250224195059.10185-1-lkml@antheas.dev> Precedence: bulk X-Mailing-List: linux-acpi@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-PPP-Message-ID: <174042667123.532.11352273453287996101@linux1587.grserver.gr> X-PPP-Vhost: antheas.dev X-Virus-Scanned: clamav-milter 0.103.11 at linux1587.grserver.gr X-Virus-Status: Clean As a secondary handler, the amd-pmf module should be able to accept all platform profiles. In the case of a custom profile, it should NOOP without an error to allow primary handlers to receive a custom profile. The sysfs endpoint will still report custom, after all. Signed-off-by: Antheas Kapenekakis --- drivers/platform/x86/amd/pmf/spc.c | 3 +++ drivers/platform/x86/amd/pmf/sps.c | 7 +++++++ 2 files changed, 10 insertions(+) diff --git a/drivers/platform/x86/amd/pmf/spc.c b/drivers/platform/x86/amd/pmf/spc.c index f34f3130c330..99c48378f943 100644 --- a/drivers/platform/x86/amd/pmf/spc.c +++ b/drivers/platform/x86/amd/pmf/spc.c @@ -219,12 +219,15 @@ static int amd_pmf_get_slider_info(struct amd_pmf_dev *dev, struct ta_pmf_enact_ switch (dev->current_profile) { case PLATFORM_PROFILE_PERFORMANCE: + case PLATFORM_PROFILE_BALANCED_PERFORMANCE: val = TA_BEST_PERFORMANCE; break; case PLATFORM_PROFILE_BALANCED: val = TA_BETTER_PERFORMANCE; break; case PLATFORM_PROFILE_LOW_POWER: + case PLATFORM_PROFILE_COOL: + case PLATFORM_PROFILE_QUIET: val = TA_BEST_BATTERY; break; default: diff --git a/drivers/platform/x86/amd/pmf/sps.c b/drivers/platform/x86/amd/pmf/sps.c index 424b146d3574..f284ebc495ee 100644 --- a/drivers/platform/x86/amd/pmf/sps.c +++ b/drivers/platform/x86/amd/pmf/sps.c @@ -297,12 +297,15 @@ int amd_pmf_get_pprof_modes(struct amd_pmf_dev *pmf) switch (pmf->current_profile) { case PLATFORM_PROFILE_PERFORMANCE: + case PLATFORM_PROFILE_BALANCED_PERFORMANCE: mode = POWER_MODE_PERFORMANCE; break; case PLATFORM_PROFILE_BALANCED: mode = POWER_MODE_BALANCED_POWER; break; case PLATFORM_PROFILE_LOW_POWER: + case PLATFORM_PROFILE_COOL: + case PLATFORM_PROFILE_QUIET: mode = POWER_MODE_POWER_SAVER; break; default: @@ -369,6 +372,10 @@ static int amd_pmf_profile_set(struct device *dev, struct amd_pmf_dev *pmf = dev_get_drvdata(dev); int ret = 0; + /* If the profile is custom, bail without an error. */ + if (profile == PLATFORM_PROFILE_CUSTOM) + return 0; + pmf->current_profile = profile; /* Notify EC about the slider position change */ From patchwork Mon Feb 24 19:50:59 2025 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Antheas Kapenekakis X-Patchwork-Id: 13988868 Received: from linux1587.grserver.gr (linux1587.grserver.gr [185.138.42.100]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 3E13024169A; Mon, 24 Feb 2025 19:51:14 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=185.138.42.100 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1740426679; cv=none; b=HFkq4vl6IrSlYXDazVxWI3hj+uOQlZIACx6PdfDgOWKGOFPSQQRv+VCtleMewuyZQEE+wfRWwzonBT92D6zrukbAZM28Xb2zgshJWBh6aZOUaUFt5PJPnaoeJlTtamp+lCzspuDqhllP2GCkPBesYqkAoO96p/nhPjUbhGwUzms= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1740426679; c=relaxed/simple; bh=WQ/xqCJrJ+Z98inVNsT+Yk88ZSVVjeBUaBvkDVXIYKU=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=HW5Firm06lkPlG3nuIQvCxDnC674bIpuzsGDqO8I2A29gi7O4gdpycG1I5Liivk+qjOhob9GaIEScyjELzuNpvhSCcWuvBR8CkG3Mvr3ox74VnnDUkGzFj107krBJBPmlaahmGVsje6J6+hK2kdDZ39lGDM/OYZ9gop8Jrz2L80= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=antheas.dev; spf=pass smtp.mailfrom=antheas.dev; dkim=pass (1024-bit key) header.d=antheas.dev header.i=@antheas.dev header.b=NJzWSczu; arc=none smtp.client-ip=185.138.42.100 Authentication-Results: smtp.subspace.kernel.org; dmarc=none (p=none dis=none) header.from=antheas.dev Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=antheas.dev Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=antheas.dev header.i=@antheas.dev header.b="NJzWSczu" Received: from localhost.localdomain (unknown [IPv6:2a05:f6c2:511b:0:8d8a:5967:d692:ea4e]) by linux1587.grserver.gr (Postfix) with ESMTPSA id A99B32E09301; Mon, 24 Feb 2025 21:51:11 +0200 (EET) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=antheas.dev; s=default; t=1740426673; bh=w21vgSbxYFIeo/DD3sVkH8EjXyQtZFxNGcN92C3rAwc=; h=From:To:Subject; b=NJzWSczu9TzaPMKs+qgAIL4s46Avc4fBhY2CzIriBsfIYgtbqc2Jty2t/C0kcW8/8 W3tKCUTHhr1VyX6+QL4wizUS1+P8uLslmsINuNeHKqjqw/up9cMEq421i1pkG12IAu 4o8do9qAe4F6qXng4Yi4iQYK/dj5Vs9woKJjmriM= Authentication-Results: linux1587.grserver.gr; spf=pass (sender IP is 2a05:f6c2:511b:0:8d8a:5967:d692:ea4e) smtp.mailfrom=lkml@antheas.dev smtp.helo=localhost.localdomain Received-SPF: pass (linux1587.grserver.gr: connection is authenticated) From: Antheas Kapenekakis To: mario.limonciello@amd.com, mpearson-lenovo@squebb.ca Cc: ilpo.jarvinen@linux.intel.com, lenb@kernel.org, linux-acpi@vger.kernel.org, linux-kernel@vger.kernel.org, platform-driver-x86@vger.kernel.org, rafael@kernel.org, hdegoede@redhat.com, me@kylegospodneti.ch, Antheas Kapenekakis Subject: [PATCH 3/3] ACPI: platform_profile: Do not hide options missing in secondary handlers Date: Mon, 24 Feb 2025 20:50:59 +0100 Message-ID: <20250224195059.10185-4-lkml@antheas.dev> X-Mailer: git-send-email 2.48.1 In-Reply-To: <20250224195059.10185-1-lkml@antheas.dev> References: <20250224195059.10185-1-lkml@antheas.dev> Precedence: bulk X-Mailing-List: linux-acpi@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-PPP-Message-ID: <174042667280.621.1070105492077902020@linux1587.grserver.gr> X-PPP-Vhost: antheas.dev X-Virus-Scanned: clamav-milter 0.103.11 at linux1587.grserver.gr X-Virus-Status: Clean In the legacy endpoint, previously, only the options common to all handlers were exposed. This causes an issue when the primary handler of the device has its options hidden, as it results in a performance degradation. Therefore, this commit introduces the concept of secondary handlers. These are handlers that are able to accept all options and do not partake in the process of selecting which profiles are visible. These handlers still have a probe function which is used for their endpoint and their endpoint works normally and will block other options. However, when called from the legacy endpoint, all options will be sent to them. It is the expectation that secondary handlers will pick the closest profile they have to what was sent. In the absence of a primary handler, the options shown in the legacy endpoint will be the union of all options of all secondary handlers. Signed-off-by: Antheas Kapenekakis --- drivers/acpi/platform_profile.c | 57 ++++++++++++++++++++++++++++----- 1 file changed, 49 insertions(+), 8 deletions(-) diff --git a/drivers/acpi/platform_profile.c b/drivers/acpi/platform_profile.c index 2ad53cc6aae5..55e8bb6adf8e 100644 --- a/drivers/acpi/platform_profile.c +++ b/drivers/acpi/platform_profile.c @@ -63,17 +63,18 @@ static ssize_t _commmon_choices_show(unsigned long *choices, char *buf) * _store_class_profile - Set the profile for a class device * @dev: The class device * @data: The profile to set + * @enforce_valid: For secondary handlers, enforce that the profile is valid * * Return: 0 on success, -errno on failure */ -static int _store_class_profile(struct device *dev, void *data) +static int _store_class_profile(struct device *dev, void *data, bool enforce_valid) { struct platform_profile_handler *handler; int *bit = (int *)data; lockdep_assert_held(&profile_lock); handler = to_pprof_handler(dev); - if (!test_bit(*bit, handler->choices)) + if ((enforce_valid || !handler->ops->secondary) && !test_bit(*bit, handler->choices)) return -EOPNOTSUPP; return handler->ops->profile_set(dev, *bit); @@ -204,7 +205,7 @@ static ssize_t profile_store(struct device *dev, return -EINVAL; scoped_cond_guard(mutex_intr, return -ERESTARTSYS, &profile_lock) { - ret = _store_class_profile(dev, &index); + ret = _store_class_profile(dev, &index, true); if (ret) return ret; } @@ -243,21 +244,37 @@ static const struct class platform_profile_class = { * * Return: 0 on success, -errno on failure */ -static int _aggregate_choices(struct device *dev, void *data) +static int _aggregate_choices(struct device *dev, void *data, bool secondary) { struct platform_profile_handler *handler; unsigned long *aggregate = data; lockdep_assert_held(&profile_lock); handler = to_pprof_handler(dev); + + if (handler->ops->secondary != secondary) + return 0; + if (test_bit(PLATFORM_PROFILE_LAST, aggregate)) bitmap_copy(aggregate, handler->choices, PLATFORM_PROFILE_LAST); + else if (handler->ops->secondary) + bitmap_or(aggregate, handler->choices, aggregate, PLATFORM_PROFILE_LAST); else bitmap_and(aggregate, handler->choices, aggregate, PLATFORM_PROFILE_LAST); return 0; } +static int _aggregate_choices_primary(struct device *dev, void *data) +{ + return _aggregate_choices(dev, data, false); +} + +static int _aggregate_choices_secondary(struct device *dev, void *data) +{ + return _aggregate_choices(dev, data, true); +} + /** * platform_profile_choices_show - Show the available profile choices for legacy sysfs interface * @dev: The device @@ -276,9 +293,16 @@ static ssize_t platform_profile_choices_show(struct device *dev, set_bit(PLATFORM_PROFILE_LAST, aggregate); scoped_cond_guard(mutex_intr, return -ERESTARTSYS, &profile_lock) { err = class_for_each_device(&platform_profile_class, NULL, - aggregate, _aggregate_choices); + aggregate, _aggregate_choices_primary); if (err) return err; + + if (test_bit(PLATFORM_PROFILE_LAST, aggregate)) { + err = class_for_each_device(&platform_profile_class, NULL, + aggregate, _aggregate_choices_secondary); + if (err) + return err; + } } /* no profile handler registered any more */ @@ -325,7 +349,7 @@ static int _store_and_notify(struct device *dev, void *data) enum platform_profile_option *profile = data; int err; - err = _store_class_profile(dev, profile); + err = _store_class_profile(dev, profile, false); if (err) return err; return _notify_class_profile(dev, NULL); @@ -384,9 +408,18 @@ static ssize_t platform_profile_store(struct device *dev, set_bit(PLATFORM_PROFILE_LAST, choices); scoped_cond_guard(mutex_intr, return -ERESTARTSYS, &profile_lock) { ret = class_for_each_device(&platform_profile_class, NULL, - choices, _aggregate_choices); + choices, _aggregate_choices_primary); if (ret) return ret; + + if (test_bit(PLATFORM_PROFILE_LAST, choices)) { + ret = class_for_each_device( + &platform_profile_class, NULL, choices, + _aggregate_choices_secondary); + if (ret) + return ret; + } + if (!test_bit(i, choices)) return -EOPNOTSUPP; @@ -470,10 +503,18 @@ int platform_profile_cycle(void) return -EINVAL; err = class_for_each_device(&platform_profile_class, NULL, - choices, _aggregate_choices); + choices, _aggregate_choices_primary); if (err) return err; + if (test_bit(PLATFORM_PROFILE_LAST, choices)) { + err = class_for_each_device( + &platform_profile_class, NULL, choices, + _aggregate_choices_secondary); + if (err) + return err; + } + /* never iterate into a custom if all drivers supported it */ clear_bit(PLATFORM_PROFILE_CUSTOM, choices);