From: Uwe Kleine-König u.kleine-koenig@pengutronix.de
mainline inclusion from mainline-v6.9-rc1 commit b0cde62e4c548b2e7cb535caa6eb0df135888601 category: bugfix bugzilla: https://gitee.com/src-openeuler/kernel/issues/IACTBX CVE: CVE-2024-40965
Reference: https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?i...
--------------------------------
This allows to simplify drivers that use clk_rate_exclusive_get() in their probe routine as calling clk_rate_exclusive_put() is cared for automatically.
Signed-off-by: Uwe Kleine-König u.kleine-koenig@pengutronix.de Link: https://lore.kernel.org/r/20240104225512.1124519-2-u.kleine-koenig@pengutron... Acked-by: Russell King (Oracle) rmk+kernel@armlinux.org.uk Signed-off-by: Stephen Boyd sboyd@kernel.org Signed-off-by: dinglongwei dinglongwei1@huawei.com --- drivers/clk/clk.c | 19 +++++++++++++++++++ include/linux/clk.h | 12 ++++++++++++ 2 files changed, 31 insertions(+)
diff --git a/drivers/clk/clk.c b/drivers/clk/clk.c index f8776065ad1f..d942d62e95eb 100644 --- a/drivers/clk/clk.c +++ b/drivers/clk/clk.c @@ -1030,6 +1030,25 @@ int clk_rate_exclusive_get(struct clk *clk) } EXPORT_SYMBOL_GPL(clk_rate_exclusive_get);
+static void devm_clk_rate_exclusive_put(void *data) +{ + struct clk *clk = data; + + clk_rate_exclusive_put(clk); +} + +int devm_clk_rate_exclusive_get(struct device *dev, struct clk *clk) +{ + int ret; + + ret = clk_rate_exclusive_get(clk); + if (ret) + return ret; + + return devm_add_action_or_reset(dev, devm_clk_rate_exclusive_put, clk); +} +EXPORT_SYMBOL_GPL(devm_clk_rate_exclusive_get); + static void clk_core_unprepare(struct clk_core *core) { lockdep_assert_held(&prepare_lock); diff --git a/include/linux/clk.h b/include/linux/clk.h index 06f1b292f8a0..24c49b01c25d 100644 --- a/include/linux/clk.h +++ b/include/linux/clk.h @@ -201,6 +201,18 @@ bool clk_is_match(const struct clk *p, const struct clk *q); */ int clk_rate_exclusive_get(struct clk *clk);
+/** + * devm_clk_rate_exclusive_get - devm variant of clk_rate_exclusive_get + * @dev: device the exclusivity is bound to + * @clk: clock source + * + * Calls clk_rate_exclusive_get() on @clk and registers a devm cleanup handler + * on @dev to call clk_rate_exclusive_put(). + * + * Must not be called from within atomic context. + */ +int devm_clk_rate_exclusive_get(struct device *dev, struct clk *clk); + /** * clk_rate_exclusive_put - release exclusivity over the rate control of a * producer