Commit Graph

299 Commits

Author SHA1 Message Date
Viresh Kumar 28330ceb95 OPP: debugfs: Fix warning around icc_get_name()
If the kernel isn't built with interconnect support, icc_get_name()
returns NULL and we get following warning:

drivers/opp/debugfs.c: In function 'bw_name_read':
drivers/opp/debugfs.c:43:42: error: '%.62s' directive argument is null [-Werror=format-overflow=]
         i = scnprintf(buf, sizeof(buf), "%.62s\n", icc_get_name(path));

Fix it.

Reported-by: kernel test robot <lkp@intel.com>
Closes: https://lore.kernel.org/oe-kbuild-all/202402141313.81ltVF5g-lkp@intel.com/
Fixes: 0430b1d570 ("opp: Expose bandwidth information via debugfs")
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Reviewed-by: Dhruva Gole <d-gole@ti.com>
2024-03-11 10:39:24 +05:30
Viresh Kumar 992e883359 OPP: debugfs: Fix warning with W=1 builds
We currently get the following warning:

debugfs.c:105:54: error: '%d' directive output may be truncated writing between 1 and 11 bytes into a region of size 8 [-Werror=format-truncation=]
                 snprintf(name, sizeof(name), "supply-%d", i);
                                                      ^~
debugfs.c:105:46: note: directive argument in the range [-2147483644, 2147483646]
                 snprintf(name, sizeof(name), "supply-%d", i);
                                              ^~~~~~~~~~~
debugfs.c:105:17: note: 'snprintf' output between 9 and 19 bytes into a destination of size 15
                 snprintf(name, sizeof(name), "supply-%d", i);

Fix this and other potential issues it by allocating larger arrays.
Use the exact string format to allocate the arrays without getting into
these issues again.

Reported-by: kernel test robot <lkp@intel.com>
Closes: https://lore.kernel.org/oe-kbuild-all/202402141313.81ltVF5g-lkp@intel.com/
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Reviewed-by: Dhruva Gole <d-gole@ti.com>
2024-03-11 10:39:24 +05:30
Sibi Sankar abb3f9717a OPP: Extend dev_pm_opp_data with turbo support
Let's extend the dev_pm_opp_data with a turbo variable, to allow users to
specify if it's a boost frequency for a dynamically added OPP.

Signed-off-by: Sibi Sankar <quic_sibis@quicinc.com>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2024-03-11 10:39:24 +05:30
Viresh Kumar dcfec12b67 OPP: Rename 'rate_clk_single'
The field's name isn't clear enough. Rename it.

Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2024-01-05 15:55:41 +05:30
Viresh Kumar 7269c250db OPP: Pass rounded rate to _set_opp()
The OPP core finds the eventual frequency to set with the help of
clk_round_rate() and the same was earlier getting passed to _set_opp()
and that's what would get configured.

The commit 1efae8d2e7 ("OPP: Make dev_pm_opp_set_opp() independent of
frequency") mistakenly changed that. Fix it.

Fixes: 1efae8d2e7 ("OPP: Make dev_pm_opp_set_opp() independent of frequency")
Cc: v5.18+ <stable@vger.kernel.org> # v6.0+
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2024-01-05 15:53:28 +05:30
Viresh Kumar 0b40dd3bcf OPP: Relocate dev_pm_opp_sync_regulators()
Move this to a more relevant place in the file. No functional changes.

Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2024-01-05 15:52:33 +05:30
Viresh Kumar 3b82024c5b OPP: Move dev_pm_opp_icc_bw to internal opp.h
It isn't used by any driver or API, privatize it.

Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2024-01-03 16:21:42 +05:30
Bryan O'Donoghue ab7a781fd6 OPP: Fix _set_required_opps when opp is NULL
_set_required_opps can be called with opp NULL in _disable_opp_table().

commit e37440e7e2 ("OPP: Call dev_pm_opp_set_opp() for required OPPs")
requires the opp pointer to be non-NULL to function.

[   81.253439] Unable to handle kernel NULL pointer dereference at virtual address 0000000000000048
[   81.438407] Hardware name: Qualcomm Technologies, Inc. Robotics RB5 (DT)
[   81.445296] Workqueue: pm pm_runtime_work
[   81.449446] pstate: 60400005 (nZCv daif +PAN -UAO -TCO -DIT -SSBS BTYPE=--)
[   81.456609] pc : _set_required_opps+0x178/0x28c
[   81.461288] lr : _set_required_opps+0x178/0x28c
[   81.465962] sp : ffff80008078bb00
[   81.469375] x29: ffff80008078bb00 x28: ffffd1cd71bfe308 x27: 0000000000000000
[   81.476730] x26: ffffd1cd70ebc578 x25: ffffd1cd70a08710 x24: 00000000ffffffff
[   81.484083] x23: 00000000ffffffff x22: 0000000000000000 x21: ffff56ff892b3c48
[   81.491435] x20: ffff56f1071c10 x19: 0000000000000000 x18: ffffffffffffffff
[   81.498788] x17: 2030207865646e69 x16: 2030303131207370 x15: 706f5f6465726975
[   81.506141] x14: 7165725f7465735f x13: ffff5700f5c00000 x12: 00000000000008ac
[   81.513495] x11: 00000000000002e4 x10: ffff5700f6700000 x9 : ffff5700f5c00000
[   81.520848] x8 : 00000000fffdffff x7 : ffff5700f6700000 x6 : 80000000fffe0000
[   81.528200] x5 : ffff5700fef40d08 x4 : 0000000000000000 x3 : 0000000000000000
[   81.535551] x2 : 0000000000000000 x1 : 0000000000000000 x0 : ffff56ff81298f80
[   81.542904] Call trace:
[   81.545437]  _set_required_opps+0x178/0x28c
[   81.549754]  _set_opp+0x3fc/0x5c0
[   81.553181]  dev_pm_opp_set_rate+0x90/0x26c
[   81.557498]  core_power_v4+0x44/0x15c [venus_core]
[   81.562509]  venus_runtime_suspend+0x40/0xd0 [venus_core]
[   81.568135]  pm_generic_runtime_suspend+0x2c/0x44
[   81.572983]  __rpm_callback+0x48/0x1d8
[   81.576852]  rpm_callback+0x6c/0x78
[   81.580453]  rpm_suspend+0x10c/0x570
[   81.584143]  pm_runtime_work+0xc4/0xc8
[   81.588011]  process_one_work+0x138/0x244
[   81.592153]  worker_thread+0x320/0x438
[   81.596021]  kthread+0x110/0x114
[   81.599355]  ret_from_fork+0x10/0x20
[   81.603052] Code: f10000ff fa5410e0 54fffbe1 97f05ae8 (f94026c5)
[   81.609317] ---[ end trace 0000000000000000 ]---

Fix it.

Fixes: e37440e7e2 ("OPP: Call dev_pm_opp_set_opp() for required OPPs")
Signed-off-by: Bryan O'Donoghue <bryan.odonoghue@linaro.org>
[ Viresh: Implemented the fix differently ]
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Reviewed-by: Bryan O'Donoghue <bryan.odonoghue@linaro.org>
Tested-by: Bryan O'Donoghue <bryan.odonoghue@linaro.org>
2023-12-28 10:55:27 +05:30
Viresh Kumar ba367479c7 OPP: The level field is always of unsigned int type
By mistake, dev_pm_opp_find_level_floor() used the level parameter as
unsigned long instead of unsigned int. Fix it.

Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-12-27 13:27:30 +05:30
Viresh Kumar 19cc8b1819 OPP: Check for invalid OPP in dev_pm_opp_find_level_ceil()
_find_key_ceil() may return an error and that must be checked before
passing the same to dev_pm_opp_put().

Fixes: 41907aa4ae37 ("OPP: Level zero is valid")
Reported-by: Dan Carpenter <dan.carpenter@linaro.org>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-11-28 16:03:37 +05:30
Viresh Kumar 925141432f OPP: Don't set OPP recursively for a parent genpd
Like other frameworks (clk, regulator, etc.) genpd core too takes care
of propagation to performance state to parent genpds. The OPP core
shouldn't attempt the same, or it may result in undefined behavior.

Add checks at various places to take care of the same.

Reviewed-by: Ulf Hansson <ulf.hansson@linaro.org>
Tested-by: Stephan Gerhold <stephan.gerhold@kernkonzept.com>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-11-28 16:03:25 +05:30
Viresh Kumar e37440e7e2 OPP: Call dev_pm_opp_set_opp() for required OPPs
Configuring the required OPP was never properly implemented, we just
took an exception for genpds and configured them directly, while leaving
out all other required OPP types.

Now that a standard call to dev_pm_opp_set_opp() takes care of
configuring the opp->level too, the special handling for genpds can be
avoided by simply calling dev_pm_opp_set_opp() for the required OPPs,
which shall eventually configure the corresponding level for genpds.

This also makes it possible for us to configure other type of required
OPPs (no concrete users yet though), via the same path. This is how
other frameworks take care of parent nodes, like clock, regulators, etc,
where we recursively call the same helper.

In order to call dev_pm_opp_set_opp() for the virtual genpd devices,
they must share the OPP table of the genpd. Call _add_opp_dev() for them
to get that done.

This commit also extends the struct dev_pm_opp_config to pass required
devices, for non-genpd cases, which can be used to call
dev_pm_opp_set_opp() for the non-genpd required devices.

Reviewed-by: Ulf Hansson <ulf.hansson@linaro.org>
Tested-by: Stephan Gerhold <stephan.gerhold@kernkonzept.com>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-11-28 16:03:19 +05:30
Viresh Kumar 6d366d0e54 OPP: Use _set_opp_level() for single genpd case
There are two genpd (as required-opp) cases that we need to handle,
devices with a single genpd and ones with multiple genpds.

The multiple genpds case is clear, where the OPP core calls
dev_pm_domain_attach_by_name() for them and uses the virtual devices
returned by this helper to call dev_pm_domain_set_performance_state()
later to change the performance state.

The single genpd case however requires special handling as we need to
use the same `dev` structure (instead of a virtual one provided by genpd
core) for setting the performance state via
dev_pm_domain_set_performance_state().

As we move towards more generic code to take care of the required OPPs,
where we will recursively call dev_pm_opp_set_opp() for all the required
OPPs, the above special case becomes a problem.

It doesn't make sense for a device's DT entry to have both "opp-level"
and single "required-opps" entry pointing to a genpd's OPP, as that
would make the OPP core call dev_pm_domain_set_performance_state() for
two different values for the same device structure. And so we can reuse
the 'opp->level" field in such a case and call _set_opp_level() for the
device.

Reviewed-by: Ulf Hansson <ulf.hansson@linaro.org>
Tested-by: Stephan Gerhold <stephan.gerhold@kernkonzept.com>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-11-28 16:03:15 +05:30
Viresh Kumar 073d3d2ca7 OPP: Level zero is valid
The level zero can be used by some OPPs to drop performance state vote
for the device. It is perfectly fine to allow the same.

_set_opp_level() considers it as an invalid value currently and returns
early.

In order to support this properly, initialize the level field with
U32_MAX, which denotes unused level field.

Reported-by: Stephan Gerhold <stephan.gerhold@kernkonzept.com>
Reviewed-by: Ulf Hansson <ulf.hansson@linaro.org>
Tested-by: Stephan Gerhold <stephan.gerhold@kernkonzept.com>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-11-28 16:03:04 +05:30
Rob Herring 4c58e9d85c opp: ti: Use device_get_match_data()
Use preferred device_get_match_data() instead of of_match_device() to
get the driver match data. With this, adjust the includes to explicitly
include the correct headers.

As this driver only does DT based matching, of_match_device() will never
return NULL if we've gotten to probe(). Therefore, the NULL check and
error return for it can be dropped.

Signed-off-by: Rob Herring <robh@kernel.org>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-11-23 11:28:46 +05:30
Viresh Kumar 5ea4911359 OPP: No need to defer probe from _opp_attach_genpd()
When the new interface for attaching genpd's via the OPP core was added,
it was possible for required_opp_count to be zero, but not anymore.

Remove the unused check.

Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Reviewed-by: Ulf Hansson <ulf.hansson@linaro.org>
2023-10-17 11:11:28 +05:30
Viresh Kumar 48b5aaec59 OPP: Remove genpd_virt_dev_lock
All the config operations for OPP tables share common code paths now and
none of the other ones have such protection in place. Either all should
have it or none.

The understanding here is that user won't clear the OPP configs while
still using them and so such a case won't happen. We can always come
back and use a wider lock for all resource types if required.

Also fix the error on failing to allocate memory.

Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Reviewed-by: Ulf Hansson <ulf.hansson@linaro.org>
2023-10-17 11:11:28 +05:30
Viresh Kumar c2bebf9804 OPP: Reorder code in _opp_set_required_opps_genpd()
Reorder code in _opp_set_required_opps_genpd() to reduce duplicate code.

Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Reviewed-by: Ulf Hansson <ulf.hansson@linaro.org>
2023-10-17 11:11:23 +05:30
Viresh Kumar 96104046d1 OPP: Add _link_required_opps() to avoid code duplication
Factor out _link_required_opps() to remove duplicate code. No functional
change.

Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Reviewed-by: Ulf Hansson <ulf.hansson@linaro.org>
2023-10-16 16:06:09 +05:30
Viresh Kumar 8e6db129eb OPP: Fix formatting of if/else block
Add {} to both if else blocks or none.

Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Reviewed-by: Ulf Hansson <ulf.hansson@linaro.org>
2023-10-16 16:05:51 +05:30
Nathan Chancellor 184ff4f721 OPP: Fix -Wunsequenced in _of_add_opp_table_v1()
Clang warns (or errors with CONFIG_WERROR=y):

  drivers/opp/of.c:1081:28: error: multiple unsequenced modifications to 'val' [-Werror,-Wunsequenced]
   1081 |                         .freq = be32_to_cpup(val++) * 1000,
        |                                                 ^
   1082 |                         .u_volt = be32_to_cpup(val++),
        |                                                   ~~
  1 error generated.

There is no sequence point in a designated initializer. Move back to
separate variables for the creation of the values, so that there are
sequence points between each evaluation and increment of val.

Fixes: 75bbc92c09d8 ("OPP: Add dev_pm_opp_add_dynamic() to allow more flexibility")
Signed-off-by: Nathan Chancellor <nathan@kernel.org>
Reviewed-by: Nick Desaulniers <ndesaulniers@google.com>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-10-06 12:49:29 +05:30
Viresh Kumar 3aa8725467 OPP: debugfs: Fix warning with W=1 builds
We currently get the following warning:

debugfs.c: In function ‘opp_debug_create_one’:
debugfs.c:63:42: warning: ‘%.1d’ directive output may be truncated writing between 1 and 10 bytes into a region of size 2 [-Wformat-truncation=]
   snprintf(name, sizeof(name), "icc-path-%.1d", i);
                                          ^~~~
debugfs.c:63:32: note: directive argument in the range [0, 2147483647]
   snprintf(name, sizeof(name), "icc-path-%.1d", i);
                                ^~~~~~~~~~~~~~~
debugfs.c:63:3: note: ‘snprintf’ output between 11 and 20 bytes into a destination of size 11
   snprintf(name, sizeof(name), "icc-path-%.1d", i);

Fix it by increasing size of the `name` array.

Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-10-06 12:37:34 +05:30
Viresh Kumar cca14de569 OPP: Remove doc style comments for internal routines
These were previously exposed outside of the OPP core and needed doc
style commenting. They aren't public now and don't need the same.

This fixes warnings generated for builds with `W=1`:

core.c:2105: warning: Function parameter or member 'opp_table' not described in '_opp_set_supported_hw'
core.c:2105: warning: Excess function parameter 'dev' description in '_opp_set_supported_hw'
core.c:2148: warning: Function parameter or member 'opp_table' not described in '_opp_set_prop_name'
core.c:2148: warning: Excess function parameter 'dev' description in '_opp_set_prop_name'
core.c:2189: warning: Function parameter or member 'opp_table' not described in '_opp_set_regulators'
core.c:2189: warning: Excess function parameter 'count' description in '_opp_set_regulators'
core.c:2293: warning: Function parameter or member 'opp_table' not described in '_opp_set_clknames'
core.c:2293: warning: Function parameter or member 'config_clks' not described in '_opp_set_clknames'
core.c:2391: warning: Function parameter or member 'opp_table' not described in '_opp_set_config_regulators_helper'
core.c:2455: warning: Function parameter or member 'opp_table' not described in '_opp_attach_genpd'
core.c:2682: warning: Function parameter or member 'token' not described in 'dev_pm_opp_clear_config'
core.c:2682: warning: Excess function parameter 'opp_table' description in 'dev_pm_opp_clear_config'

Reported-by: kernel test robot <lkp@intel.com>
Closes: https://lore.kernel.org/oe-kbuild-all/202309091558.x3JJrxFI-lkp@intel.com/
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-10-06 12:37:34 +05:30
Krishna chaitanya chundru a0242c81bb OPP: Add dev_pm_opp_find_level_floor()
Add dev_pm_opp_find_level_floor(), as is done for frequency and
bandwidth.

Signed-off-by: Krishna chaitanya chundru <quic_krichai@quicinc.com>
[ Viresh: Updated commit log and rearranged code ]
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-10-06 12:37:34 +05:30
Ulf Hansson 0025ff64ff OPP: Extend support for the opp-level beyond required-opps
At this point the level (performance state) for an OPP is currently limited
to be requested for a device that is attached to a PM domain.  Moreover,
the device needs to have the so called required-opps assigned to it, which
are based upon OPP tables being described in DT.

To extend the support beyond required-opps and DT, let's enable the level
to be set for all OPPs. More precisely, if the requested OPP has a valid
level let's try to request it through the device's optional PM domain, via
calling dev_pm_domain_set_performance_state().

Signed-off-by: Ulf Hansson <ulf.hansson@linaro.org>
[ Viresh: Handle NULL opp in _set_opp_level() ]
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-10-06 12:37:34 +05:30
Ulf Hansson 892c60c6b4 OPP: Switch to use dev_pm_domain_set_performance_state()
To support performance scaling for any kinds of PM domains, let's move away
from using the genpd specific API, dev_pm_genpd_set_performance_state(), to
the common dev_pm_domain_set_performance_state().

No intended functional impact at this point.

Signed-off-by: Ulf Hansson <ulf.hansson@linaro.org>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-10-06 12:37:34 +05:30
Ulf Hansson 3166383da0 OPP: Extend dev_pm_opp_data with a level
Let's extend the dev_pm_opp_data with a level variable, to allow users to
specify a corresponding level (performance state) for a dynamically added
OPP.

Signed-off-by: Ulf Hansson <ulf.hansson@linaro.org>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-10-06 12:37:34 +05:30
Ulf Hansson 248a38d5cc OPP: Add dev_pm_opp_add_dynamic() to allow more flexibility
The dev_pm_opp_add() API is limited to add dynamic OPPs with a frequency
and a voltage level. To enable more flexibility, let's add a new API,
dev_pm_opp_add_dynamic() that's takes a struct dev_pm_opp_data* instead of
a list of in-parameters.

Signed-off-by: Ulf Hansson <ulf.hansson@linaro.org>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-10-06 12:37:33 +05:30
Viresh Kumar a5a297918a OPP: Fix argument name in doc comment
The name of the argument is "opp_table" and not "table", fix the
comment.

Reported-by: kernel test robot <lkp@intel.com>
Closes: https://lore.kernel.org/oe-kbuild-all/202308172310.FzcidE4c-lkp@intel.com/
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-08-18 10:55:49 +05:30
Manivannan Sadhasivam d920920f85 OPP: Fix passing 0 to PTR_ERR in _opp_attach_genpd()
If dev_pm_domain_attach_by_name() returns NULL, then 0 will be passed to
PTR_ERR() as reported by the smatch warning below:

drivers/opp/core.c:2456 _opp_attach_genpd() warn: passing zero to 'PTR_ERR'

Fix it by checking for the non-NULL virt_dev pointer before passing it to
PTR_ERR. Otherwise return -ENODEV.

Fixes: 4ea9496cbc ("opp: Fix error check in dev_pm_opp_attach_genpd()")
Signed-off-by: Manivannan Sadhasivam <manivannan.sadhasivam@linaro.org>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-07-24 13:31:25 +05:30
Manivannan Sadhasivam 7ddd8deb1c OPP: Fix potential null ptr dereference in dev_pm_opp_get_required_pstate()
"opp" pointer is dereferenced before the IS_ERR_OR_NULL() check. Fix it by
removing the dereference to cache opp_table and dereference it directly
where opp_table is used.

This fixes the following smatch warning:

drivers/opp/core.c:232 dev_pm_opp_get_required_pstate() warn: variable
dereferenced before IS_ERR check 'opp' (see line 230)

Fixes: 84cb7ff35f ("OPP: pstate is only valid for genpd OPP tables")
Signed-off-by: Manivannan Sadhasivam <manivannan.sadhasivam@linaro.org>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-07-24 13:31:17 +05:30
Viresh Kumar 746de82550 OPP: Reuse dev_pm_opp_get_freq_indexed()
Reuse dev_pm_opp_get_freq_indexed() from dev_pm_opp_get_freq().

Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Acked-by: Manivannan Sadhasivam <manivannan.sadhasivam@linaro.org>
2023-07-24 13:27:12 +05:30
Viresh Kumar 034d6aac21 OPP: Update _read_freq() to return the correct frequency
Now that we support finding indexed frequencies, lets update
_read_freq() to return the right one.

Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Acked-by: Manivannan Sadhasivam <manivannan.sadhasivam@linaro.org>
2023-07-24 13:27:03 +05:30
Viresh Kumar a5893928bb OPP: Add dev_pm_opp_find_freq_exact_indexed()
The indexed version of the API is added for other floor and ceil, add
the same for exact as well for completeness.

Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-07-24 13:22:39 +05:30
Manivannan Sadhasivam 5f756d03e2 OPP: Introduce dev_pm_opp_get_freq_indexed() API
In the case of devices with multiple clocks, drivers need to specify the
frequency index for the OPP framework to get the specific frequency within
the required OPP. So let's introduce the dev_pm_opp_get_freq_indexed() API
accepting the frequency index as an argument.

Signed-off-by: Manivannan Sadhasivam <manivannan.sadhasivam@linaro.org>
[ Viresh: Fixed potential access to NULL opp pointer ]
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-07-24 13:22:39 +05:30
Manivannan Sadhasivam 142e17c1c2 OPP: Introduce dev_pm_opp_find_freq_{ceil/floor}_indexed() APIs
In the case of devices with multiple clocks, drivers need to specify the
clock index for the OPP framework to find the OPP corresponding to the
floor/ceil of the supplied frequency. So let's introduce the two new APIs
accepting the clock index as an argument.

These APIs use the exising _find_key_ceil() helper by supplying the clock
index to it.

Signed-off-by: Manivannan Sadhasivam <manivannan.sadhasivam@linaro.org>
[ Viresh: Rearranged definitions in pm_opp.h ]
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-07-21 15:08:27 +05:30
Andrew Halaney 5fb2864cbd OPP: Properly propagate error along when failing to get icc_path
fa155f4f83 ("OPP: Use dev_err_probe() when failing to get icc_path")
failed to actually use the error it was trying to log:

    smatch warnings:
    drivers/opp/of.c:516 dev_pm_opp_of_find_icc_paths() warn: passing zero to 'dev_err_probe'

Make sure to use the right error and pass it along.

Fixes: fa155f4f83 ("OPP: Use dev_err_probe() when failing to get icc_path")
Reported-by: kernel test robot <lkp@intel.com>
Reported-by: Dan Carpenter <dan.carpenter@linaro.org>
Closes: https://lore.kernel.org/r/202306262008.guNLgjt6-lkp@intel.com/
Signed-off-by: Andrew Halaney <ahalaney@redhat.com>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-06-27 07:35:14 +05:30
Andrew Halaney fa155f4f83 OPP: Use dev_err_probe() when failing to get icc_path
This, in tandem with dynamic debug, can print useful information about
-EPROBE_DEFFER like below, and keeps similar behavior for other errors:

    [   16.561072] cpu cpu0: error -EPROBE_DEFER: dev_pm_opp_of_find_icc_paths: Unable to get path0
    [   16.575777] platform 18591000.cpufreq: deferred probe pending

Signed-off-by: Andrew Halaney <ahalaney@redhat.com>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-06-26 12:10:26 +05:30
Viresh Kumar 7c41cdcd3b OPP: Simplify the over-designed pstate <-> level dance
While adding support for "performance states" in the OPP and genpd core,
it was decided to set the `pstate` field via genpd's
pm_genpd_opp_to_performance_state() helper, to allow platforms to set
`pstate` even if they don't have a corresponding `level` field in the DT
OPP tables (More details are present in commit 6e41766a6a ("PM /
Domain: Implement of_genpd_opp_to_performance_state()")).

Revisiting that five years later clearly suggests that it was
over-designed as all current users are eventually using the `level`
value only.

The previous commit already added necessary checks to make sure pstate
is only used for genpd tables. Lets now simplify this a little, and use
`level` directly and remove `pstate` field altogether.

Suggested-by: Ulf Hansson <ulf.hansson@linaro.org>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Reviewed-by: Ulf Hansson <ulf.hansson@linaro.org>
2023-06-19 09:50:09 +05:30
Viresh Kumar 84cb7ff35f OPP: pstate is only valid for genpd OPP tables
It is not very clear right now that the `pstate` field is only valid for
genpd OPP tables and not consumer tables. And there is no checking for
the same at various places.

Add checks in place to verify that and make it clear to the reader.

Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Reviewed-by: Ulf Hansson <ulf.hansson@linaro.org>
Reviewed-by: Bjorn Andersson <quic_bjorande@quicinc.com>
Tested-by: Bjorn Andersson <quic_bjorande@quicinc.com>
2023-06-19 09:50:02 +05:30
Viresh Kumar 04bd2eafee OPP: don't drop performance constraint on OPP table removal
This code was added (long back) by commit 009acd196f ("PM / OPP:
Support updating performance state of device's power domain") and at
that time the `opp->pstate` field was used to store the performance
state required by a device's OPP.

Over time that changed and the `->pstate` field is now used only for
genpd devices and consumer devices access that via the required-opps
instead.

Because of all these changes, _opp_table_kref_release() now drops the
constraint only when the genpd's OPP table gets freed and not the
device's. Which is definitely not what we wanted. And dropping the
constraint doesn't have much meaning as the genpd itself is going away.

Moreover, if we want to drop constraints here, then just dropping the
performance constraint alone isn't sufficient as there are other
resource constraints like clk, regulator, etc. too, which must be
handled.

Probably the right thing to do here is to leave this decision to the
consumers, which can call `dev_pm_opp_set_rate(dev, 0)` or similar APIs
to drop all constraints properly. Which many of the consumers already
do.

Remove the special code, which is broken anyway.

Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Reviewed-by: Ulf Hansson <ulf.hansson@linaro.org>
2023-06-14 14:54:01 +05:30
Viresh Kumar 64aaeb7082 OPP: Protect `lazy_opp_tables` list with `opp_table_lock`
The `opp_table_lock` lock is already used to protect the list elsewhere,
use it while adding or removing entries from it.

Reported-by: Stephan Gerhold <stephan.gerhold@kernkonzept.com>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Tested-by: Stephan Gerhold <stephan.gerhold@kernkonzept.com>
2023-06-14 09:20:50 +05:30
Viresh Kumar 167eb2bd94 OPP: Staticize `lazy_opp_tables` in of.c
`lazy_opp_tables` is only used in of.c, move it there and mark it
`static`.

Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-06-08 12:55:07 +05:30
Stephan Gerhold b2a2ab039b opp: Fix use-after-free in lazy_opp_tables after probe deferral
When dev_pm_opp_of_find_icc_paths() in _allocate_opp_table() returns
-EPROBE_DEFER, the opp_table is freed again, to wait until all the
interconnect paths are available.

However, if the OPP table is using required-opps then it may already
have been added to the global lazy_opp_tables list. The error path
does not remove the opp_table from the list again.

This can cause crashes later when the provider of the required-opps
is added, since we will iterate over OPP tables that have already been
freed. E.g.:

  Unable to handle kernel NULL pointer dereference when read
  CPU: 0 PID: 7 Comm: kworker/0:0 Not tainted 6.4.0-rc3
  PC is at _of_add_opp_table_v2 (include/linux/of.h:949
  drivers/opp/of.c:98 drivers/opp/of.c:344 drivers/opp/of.c:404
  drivers/opp/of.c:1032) -> lazy_link_required_opp_table()

Fix this by calling _of_clear_opp_table() to remove the opp_table from
the list and clear other allocated resources. While at it, also add the
missing mutex_destroy() calls in the error path.

Cc: stable@vger.kernel.org
Suggested-by: Viresh Kumar <viresh.kumar@linaro.org>
Fixes: 7eba0c7641 ("opp: Allow lazy-linking of required-opps")
Signed-off-by: Stephan Gerhold <stephan.gerhold@kernkonzept.com>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-05-31 09:21:41 +05:30
Adrián Larumbe 9e28f7a745 OPP: rate-limit debug messages when no change in OPP is required
Otherwise, when enabling a debug build and dynamic debug in the kernel, it
quickly floods the kernel ring buffer and makes debugging of other
subsystems almost impossible, unless manually disabled.

Signed-off-by: Adrián Larumbe <adrian.larumbe@collabora.com>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-05-22 09:11:40 +05:30
Linus Torvalds cb6fe2ceb6 Devicetree updates for v6.4, part 2:
- First part of DT header detangling dropping cpu.h from of_device.h
   and replacing some includes with forward declarations. A handful of
   drivers needed some adjustment to their includes as a result.
 
 - Refactor of_device.h to be used by bus drivers rather than various
   device drivers. This moves non-bus related functions out of
   of_device.h. The end goal is for of_platform.h and of_device.h to stop
   including each other.
 
 - Refactor open coded parsing of "ranges" in some bus drivers to use DT
   address parsing functions
 
 - Add some new address parsing functions of_property_read_reg(),
   of_range_count(), and of_range_to_resource() in preparation to convert
   more open coded parsing of DT addresses to use them.
 
 - Treewide clean-ups to use of_property_read_bool() and
   of_property_present() as appropriate. The ones here are the ones
   that didn't get picked up elsewhere.
 -----BEGIN PGP SIGNATURE-----
 
 iQIzBAABCgAdFiEEktVUI4SxYhzZyEuo+vtdtY28YcMFAmRIOrkACgkQ+vtdtY28
 YcN9WA//R+QrmSPExhfgio5y+aOJDWucqnAcyAusPctLcF7h7j0CdzpwaSRkdaH4
 KiLjeyt6tKn8wt8w7m/+SmCsSYXPn81GH/Y5I2F40x6QMrY3cVOXUsulKQA+6ZjZ
 PmW3bMcz0Dw9IhUK3R/WX96+9UdoytKg5qoTzNzPTKpvKA1yHa/ogl2FnHJS5W+8
 Rxz+1oJ70VMIWGpBOc0acHuB2S0RHZ46kPKkPTBgFYEwtmJ8qobvV3r3uQapNaIP
 2jnamPu0tAaQoSaJKKSulToziT+sd1sNB+9oyu/kP+t3PXzq4qwp2Gr4jzUYKs4A
 ZF3DPhMR3YLLN41g/L3rtB0T/YIS287sZRuaLhCqldNpRerSDk4b0HRAksGk1XrI
 HqYXjWPbRxqYiIUWkInfregSTYJfGPxeLfLKrawNO34/eEV4JrkSKy8d0AJn04EK
 jTRqI3L7o23ZPxs29uH/3+KK90J3emPZkF7GWVJTEAMsM8jYZduGh7EpsttJLaz/
 QnxbTBm9295ahIdCfo/OQhqjWnaNhpbTzf31pyrBZ/itXV7gQ0xjwqPwiyFwI+o/
 F/r81xqdwQ3Ni8MKt2c7zLyVA95JHPe95KQ3GrDXR68aByJr4RuhKG8Y2Pj1VOb3
 V+Hsu5uhwKrK7Yqe+rHDnJBO00OCO8nwbWhMy2xVxoTkSFCjDmo=
 =89Zj
 -----END PGP SIGNATURE-----

Merge tag 'devicetree-for-6.4-2' of git://git.kernel.org/pub/scm/linux/kernel/git/robh/linux

Pull more devicetree updates from Rob Herring:

 - First part of DT header detangling dropping cpu.h from of_device.h
   and replacing some includes with forward declarations. A handful of
   drivers needed some adjustment to their includes as a result.

 - Refactor of_device.h to be used by bus drivers rather than various
   device drivers. This moves non-bus related functions out of
   of_device.h. The end goal is for of_platform.h and of_device.h to
   stop including each other.

 - Refactor open coded parsing of "ranges" in some bus drivers to use DT
   address parsing functions

 - Add some new address parsing functions of_property_read_reg(),
   of_range_count(), and of_range_to_resource() in preparation to
   convert more open coded parsing of DT addresses to use them.

 - Treewide clean-ups to use of_property_read_bool() and
   of_property_present() as appropriate. The ones here are the ones that
   didn't get picked up elsewhere.

* tag 'devicetree-for-6.4-2' of git://git.kernel.org/pub/scm/linux/kernel/git/robh/linux: (34 commits)
  bus: tegra-gmi: Replace of_platform.h with explicit includes
  hte: Use of_property_present() for testing DT property presence
  w1: w1-gpio: Use of_property_read_bool() for boolean properties
  virt: fsl: Use of_property_present() for testing DT property presence
  soc: fsl: Use of_property_present() for testing DT property presence
  sbus: display7seg: Use of_property_read_bool() for boolean properties
  sparc: Use of_property_read_bool() for boolean properties
  sparc: Use of_property_present() for testing DT property presence
  bus: mvebu-mbus: Remove open coded "ranges" parsing
  of/address: Add of_property_read_reg() helper
  of/address: Add of_range_count() helper
  of/address: Add support for 3 address cell bus
  of/address: Add of_range_to_resource() helper
  of: unittest: Add bus address range parsing tests
  of: Drop cpu.h include from of_device.h
  OPP: Adjust includes to remove of_device.h
  irqchip: loongson-eiointc: Add explicit include for cpuhotplug.h
  cpuidle: Adjust includes to remove of_device.h
  cpufreq: sun50i: Add explicit include for cpu.h
  cpufreq: Adjust includes to remove of_device.h
  ...
2023-04-27 10:09:05 -07:00
Rob Herring cd6f0f5176 OPP: Adjust includes to remove of_device.h
Now that of_cpu_device_node_get() is defined in of.h, of_device.h is just
implicitly including other includes, and is no longer needed. Adjust the
include files with what was implicitly included by of_device.h (cpu.h and
of.h) and drop including of_device.h.

Acked-by: Viresh Kumar <viresh.kumar@linaro.org>
Link: https://lore.kernel.org/r/20230329-dt-cpu-header-cleanups-v1-18-581e2605fe47@kernel.org
Signed-off-by: Rob Herring <robh@kernel.org>
2023-04-13 17:46:35 -05:00
Viresh Kumar 528f2d8d54 OPP: Move required opps configuration to specialized callback
The required-opps configuration is closely tied to genpd and performance
states at the moment and it is not very obvious that required-opps can
live without genpds. Though we don't support configuring required-opps
for non-genpd cases currently.

This commit aims at separating these parts, where configuring genpds
would be a special case of configuring the required-opps.

Add a specialized callback, set_required_opps(), to the opp table and
set it to different callbacks accordingly.

This shouldn't result in any functional changes for now.

Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Reviewed-by: Ulf Hansson <ulf.hansson@linaro.org>
2023-04-03 09:45:09 +05:30
Viresh Kumar 29b1a92e5e OPP: Handle all genpd cases together in _set_required_opps()
There is no real need of keeping separate code for single genpd case, it
can be made to work with a simple change.

Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Reviewed-by: Ulf Hansson <ulf.hansson@linaro.org>
2023-04-03 09:45:09 +05:30
Rob Herring e9eadc2827 opp: Use of_property_present() for testing DT property presence
It is preferred to use typed property access functions (i.e.
of_property_read_<type> functions) rather than low-level
of_get_property/of_find_property functions for reading properties. As
part of this, convert of_get_property/of_find_property calls to the
recently added of_property_present() helper when we just want to test
for presence of a property and nothing more.

Signed-off-by: Rob Herring <robh@kernel.org>
Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
2023-03-13 09:59:41 +05:30