1. 05 11月, 2018 3 次提交
  2. 04 10月, 2018 2 次提交
    • D
      PM / OPP: _of_add_opp_table_v2(): increment count only if OPP is added · deac8703
      Dave Gerlach 提交于
      Currently the _of_add_opp_table_v2 call loops through the OPP nodes in
      the operating-points-v2 table in the device tree and calls
      _opp_add_static_v2 for each to add them to the table. It counts each
      iteration through this loop as an added OPP, however there are cases
      where _opp_add_static_v2() returns 0 but no new OPP is added to the
      list.
      
      This can happen while adding duplicate OPP or if the OPP isn't supported
      by hardware.
      
      Because of this the count variable will contain the number of OPP nodes
      in the table in device tree but not necessarily the ones that are
      actually added.
      
      As this count value is what is checked to determine if there are any
      valid OPPs, if a platform has an operating-points-v2 table with all OPP
      nodes containing opp-supported-hw values that are not currently
      supported, then _of_add_opp_table_v2 will fail to abort as it should due
      to an empty table.
      
      Additionally, since commit 3ba98324 ("PM / OPP: Get
      performance state using genpd helper"), the same count variable is
      compared against the number of OPPs containing performance states and
      requires that either all or none have pstates set, however in the case
      of any opp table that has any entries that do not get added by
      _opp_add_static_v2 due to incompatible opp-supported-hw fields, these
      numbers will not match and _of_add_opp_table_v2 will incorrectly fail.
      
      We need to clearly identify all the three cases (success, failure,
      unsupported/duplicate OPPs) and then increment count only on success
      case. Change return type of _opp_add_static_v2() to return the pointer
      to the newly added OPP instead of an integer. This routine now returns a
      valid pointer if the OPP is really added, NULL for unsupported or
      duplicate OPPs, and error value cased as a pointer on errors.
      
      Ideally the fixes tag in this commit should point back to the commit
      that introduced OPP v2 initially, as that's where we started incorrectly
      accounting for duplicate OPPs:
      
      commit 27465902 ("PM / OPP: Add support to parse "operating-points-v2" bindings")
      
      But it wasn't a real problem until recently as the count was only used
      to check if any OPPs are added or not. And so this commit points to a
      rather recent commit where we added more code that depends on the value
      of "count".
      
      Fixes: 3ba98324 ("PM / OPP: Get performance state using genpd helper")
      Reported-by: NDave Gerlach <d-gerlach@ti.com>
      Reported-by: NNiklas Cassel <niklas.cassel@linaro.org>
      Tested-by: NNiklas Cassel <niklas.cassel@linaro.org>
      Signed-off-by: NDave Gerlach <d-gerlach@ti.com>
      Signed-off-by: NViresh Kumar <viresh.kumar@linaro.org>
      deac8703
    • V
      OPP: Improve error handling in dev_pm_opp_of_cpumask_add_table() · 50b6b87c
      Viresh Kumar 提交于
      The error handling wasn't appropriate in
      dev_pm_opp_of_cpumask_add_table(). For example it returns 0 on success
      and also for the case where cpumask is empty or cpu_device wasn't found
      for any of the CPUs.
      
      It should really return error on such cases, so that the callers can be
      aware of the outcome.
      
      Fix it.
      Signed-off-by: NViresh Kumar <viresh.kumar@linaro.org>
      50b6b87c
  3. 01 10月, 2018 2 次提交
    • V
      OPP: Pass OPP table to _of_add_opp_table_v{1|2}() · 5ed4cecd
      Viresh Kumar 提交于
      Both _of_add_opp_table_v1() and _of_add_opp_table_v2() contain similar
      code to get the OPP table and their parent routine also parses the DT to
      find the OPP table's node pointer. This can be simplified by getting the
      OPP table in advance and then passing it as argument to these routines.
      Tested-by: NNiklas Cassel <niklas.cassel@linaro.org>
      Signed-off-by: NViresh Kumar <viresh.kumar@linaro.org>
      5ed4cecd
    • V
      OPP: Prevent creating multiple OPP tables for devices sharing OPP nodes · 283d55e6
      Viresh Kumar 提交于
      When two or more devices are sharing their clock and voltage rails, they
      share the same OPP table. But there are some corner cases where the OPP
      core incorrectly creates separate OPP tables for them.
      
      For example, CPU 0 and 1 share clock/voltage rails. The platform
      specific code calls dev_pm_opp_set_regulators() for CPU0 and the OPP
      core creates an OPP table for it (the individual OPPs aren't initialized
      as of now). The same is repeated for CPU1 then. Because
      _opp_get_opp_table() doesn't compare DT node pointers currently, it
      fails to find the link between CPU0 and CPU1 and so creates a new OPP
      table.
      
      Fix this by calling _managed_opp() from _opp_get_opp_table().
      _managed_opp() gain an additional argument (index) to get the right node
      pointer. This resulted in simplifying code in _of_add_opp_table_v2() as
      well.
      Tested-by: NNiklas Cassel <niklas.cassel@linaro.org>
      Signed-off-by: NViresh Kumar <viresh.kumar@linaro.org>
      283d55e6
  4. 20 9月, 2018 7 次提交
    • V
      OPP: Use a single mechanism to free the OPP table · cdd6ed90
      Viresh Kumar 提交于
      Currently there are two separate ways to free the OPP table based on how
      it is created in the first place.
      
      We call _dev_pm_opp_remove_table() to free the static and/or dynamic
      OPP, OPP list devices, etc. This is done for the case where the OPP
      table is added while initializing the OPPs, like via the path
      dev_pm_opp_of_add_table().
      
      We also call dev_pm_opp_put_opp_table() in some cases which eventually
      frees the OPP table structure once the reference count reaches 0. This
      is used by the first case as well as other cases like
      dev_pm_opp_set_regulators() where the OPPs aren't necessarily
      initialized at this point.
      
      This whole thing is a bit unclear and messy and obstruct any further
      cleanup/fixup of OPP core.
      
      This patch tries to streamline this by keeping a single path for OPP
      table destruction, i.e. dev_pm_opp_put_opp_table().
      
      All the cleanup happens in _opp_table_kref_release() now after the
      reference count reaches 0. _dev_pm_opp_remove_table() is removed as it
      isn't required anymore.
      
      We don't drop the reference to the OPP table after creating it from
      _of_add_opp_table_v{1|2}() anymore and the same is dropped only when we
      try to remove them.
      Tested-by: NNiklas Cassel <niklas.cassel@linaro.org>
      Signed-off-by: NViresh Kumar <viresh.kumar@linaro.org>
      cdd6ed90
    • V
      OPP: Don't remove dynamic OPPs from _dev_pm_opp_remove_table() · 2a4eb735
      Viresh Kumar 提交于
      Only one platform was depending on this feature and it is already
      updated now. Stop removing dynamic OPPs from _dev_pm_opp_remove_table().
      This simplifies lot of paths and removes unnecessary parameters.
      Tested-by: NNiklas Cassel <niklas.cassel@linaro.org>
      Signed-off-by: NViresh Kumar <viresh.kumar@linaro.org>
      2a4eb735
    • V
      OPP: Create separate kref for static OPPs list · d0e8ae6c
      Viresh Kumar 提交于
      The static OPPs don't always get freed with the OPP table, it can happen
      before that as well. For example, if the OPP table is first created
      using helpers like dev_pm_opp_set_supported_hw() and the OPPs are
      created at a later point. Now when the OPPs are removed, the OPP table
      stays until the time dev_pm_opp_put_supported_hw() is called.
      
      Later patches will streamline the freeing of OPP table and that requires
      the static OPPs to get freed with help of a separate kernel reference.
      This patch prepares for that by creating a separate kref for static OPPs
      list.
      Tested-by: NNiklas Cassel <niklas.cassel@linaro.org>
      Signed-off-by: NViresh Kumar <viresh.kumar@linaro.org>
      d0e8ae6c
    • V
      OPP: Parse OPP table's DT properties from _of_init_opp_table() · f06ed90e
      Viresh Kumar 提交于
      Parse the DT properties present in the OPP table from
      _of_init_opp_table(), which is a dedicated routine for DT parsing.
      
      Minor relocation of helpers is required for this.
      
      It is possible now for _managed_opp() to return a partially initialized
      OPP table if the OPP table is created via the helpers like
      dev_pm_opp_set_supported_hw() and we need another flag to indicate if
      the static OPP are already parsed or not to make sure we don't
      incorrectly skip initializing the static OPPs.
      Tested-by: NNiklas Cassel <niklas.cassel@linaro.org>
      Signed-off-by: NViresh Kumar <viresh.kumar@linaro.org>
      f06ed90e
    • V
      OPP: Pass index to _of_init_opp_table() · eb7c8743
      Viresh Kumar 提交于
      This is a preparatory patch required for the next commit which will
      start using OPP table's node pointer in _of_init_opp_table(), which
      requires the index in order to read the OPP table's phandle.
      
      This commit adds the index argument in the call chains in order to get
      it delivered to _of_init_opp_table().
      Tested-by: NNiklas Cassel <niklas.cassel@linaro.org>
      Signed-off-by: NViresh Kumar <viresh.kumar@linaro.org>
      eb7c8743
    • V
      OPP: Don't try to remove all OPP tables on failure · 404b1369
      Viresh Kumar 提交于
      dev_pm_opp_of_cpumask_add_table() creates the OPP table for all CPUs
      present in the cpumask and on errors it should revert all changes it has
      done.
      
      It actually is doing a bit more than that. On errors, it tries to free
      all the OPP tables, even the one it hasn't created yet. This may also
      end up freeing the OPP tables which were created from separate path,
      like dev_pm_opp_set_supported_hw().
      Reported-and-tested-by: NNiklas Cassel <niklas.cassel@linaro.org>
      Signed-off-by: NViresh Kumar <viresh.kumar@linaro.org>
      404b1369
    • V
      OPP: Free OPP table properly on performance state irregularities · 2fbb8670
      Viresh Kumar 提交于
      The OPP table was freed, but not the individual OPPs which is done from
      _dev_pm_opp_remove_table(). Fix it by calling _dev_pm_opp_remove_table()
      as well.
      
      Cc: 4.18 <stable@vger.kernel.org> # v4.18
      Fixes: 3ba98324 ("PM / OPP: Get performance state using genpd helper")
      Tested-by: NNiklas Cassel <niklas.cassel@linaro.org>
      Signed-off-by: NViresh Kumar <viresh.kumar@linaro.org>
      2fbb8670
  5. 30 5月, 2018 1 次提交
    • V
      OPP: Allow same OPP table to be used for multiple genpd · 8a352fd8
      Viresh Kumar 提交于
      The OPP binding says:
      
      	Property: operating-points-v2
      
      	...
      
      	This can contain more than one phandle for power domain
      	providers that provide multiple power domains. That is, one
      	phandle for each power domain. If only one phandle is available,
      	then the same OPP table will be used for all power domains
      	provided by the power domain provider.
      
      But the OPP core isn't allowing the same OPP table to be used for
      multiple domains. Update dev_pm_opp_of_add_table_indexed() to allow
      that.
      Signed-off-by: NViresh Kumar <viresh.kumar@linaro.org>
      Tested-by: NRajendra Nayak <rnayak@codeaurora.org>
      8a352fd8
  6. 16 5月, 2018 1 次提交
  7. 09 5月, 2018 5 次提交
  8. 14 10月, 2017 1 次提交
  9. 11 10月, 2017 1 次提交
  10. 03 10月, 2017 1 次提交
  11. 01 8月, 2017 1 次提交
  12. 16 7月, 2017 1 次提交
  13. 22 6月, 2017 1 次提交
  14. 10 2月, 2017 1 次提交
  15. 30 1月, 2017 2 次提交
    • V
      PM / OPP: Move away from RCU locking · 052c6f19
      Viresh Kumar 提交于
      The RCU locking isn't well suited for the OPP core. The RCU locking fits
      better for reader heavy stuff, while the OPP core have at max one or two
      readers only at a time.
      
      Over that, it was getting very confusing the way RCU locking was used
      with the OPP core. The individual OPPs are mostly well handled, i.e. for
      an update a new structure was created and then that replaced the older
      one. But the OPP tables were updated directly all the time from various
      parts of the core. Though they were mostly used from within RCU locked
      region, they didn't had much to do with RCU and were governed by the
      mutex instead.
      
      And that mixed with the 'opp_table_lock' has made the core even more
      confusing.
      
      Now that we are already managing the OPPs and the OPP tables with kernel
      reference infrastructure, we can get rid of RCU locking completely and
      simplify the code a lot.
      
      Remove all RCU references from code and comments.
      
      Acquire opp_table->lock while parsing the list of OPPs though.
      Signed-off-by: NViresh Kumar <viresh.kumar@linaro.org>
      Reviewed-by: NStephen Boyd <sboyd@codeaurora.org>
      Signed-off-by: NRafael J. Wysocki <rafael.j.wysocki@intel.com>
      052c6f19
    • V
      PM / OPP: Use dev_pm_opp_get_opp_table() instead of _add_opp_table() · b83c1899
      Viresh Kumar 提交于
      Migrate all users of _add_opp_table() to use dev_pm_opp_get_opp_table()
      to guarantee that the OPP table doesn't get freed while being used.
      
      Also update _managed_opp() to get the reference to the OPP table.
      
      Now that the OPP table wouldn't get freed while these routines are
      executing after dev_pm_opp_get_opp_table() is called, there is no need
      to take opp_table_lock. Drop them as well.
      
      Now that _add_opp_table(), _remove_opp_table() and the unlocked release
      routines aren't used anymore, remove them.
      Signed-off-by: NViresh Kumar <viresh.kumar@linaro.org>
      Reviewed-by: NStephen Boyd <sboyd@codeaurora.org>
      Signed-off-by: NRafael J. Wysocki <rafael.j.wysocki@intel.com>
      b83c1899
  16. 27 1月, 2017 7 次提交
  17. 06 12月, 2016 2 次提交
  18. 21 10月, 2016 1 次提交