summaryrefslogtreecommitdiff
path: root/drivers/clk
diff options
context:
space:
mode:
authorTero Kristo <t-kristo@ti.com>2021-06-11 11:45:12 +0300
committerLokesh Vutla <lokeshvutla@ti.com>2021-06-11 14:04:52 +0300
commit6b7fd3128f71e8c1fa847c18be4b9a322f341ba7 (patch)
tree3a96a0d96848af27bc626ba3b334b09b1f3d828b /drivers/clk
parent1e1fab0be59217aff9378e24f94f2340fbe2c3f7 (diff)
downloadu-boot-6b7fd3128f71e8c1fa847c18be4b9a322f341ba7.tar.xz
clk: fix set_rate to clean up cached rates for the hierarchy
Clock rates are cached within the individual clock nodes, and right now if one changes a clock rate somewhere in the middle of the tree, none of its child clocks notice the change. To fix this, clear up all the cached rates for us and our child clocks. Signed-off-by: Tero Kristo <t-kristo@ti.com> Signed-off-by: Tero Kristo <kristo@kernel.org>
Diffstat (limited to 'drivers/clk')
-rw-r--r--drivers/clk/clk-uclass.c19
1 files changed, 19 insertions, 0 deletions
diff --git a/drivers/clk/clk-uclass.c b/drivers/clk/clk-uclass.c
index 815f7bfe98..3d2344f009 100644
--- a/drivers/clk/clk-uclass.c
+++ b/drivers/clk/clk-uclass.c
@@ -568,6 +568,22 @@ ulong clk_round_rate(struct clk *clk, ulong rate)
return ops->round_rate(clk, rate);
}
+static void clk_clean_rate_cache(struct clk *clk)
+{
+ struct udevice *child_dev;
+ struct clk *clkp;
+
+ if (!clk)
+ return;
+
+ clk->rate = 0;
+
+ list_for_each_entry(child_dev, &clk->dev->child_head, sibling_node) {
+ clkp = dev_get_clk_ptr(child_dev);
+ clk_clean_rate_cache(clkp);
+ }
+}
+
ulong clk_set_rate(struct clk *clk, ulong rate)
{
const struct clk_ops *ops;
@@ -580,6 +596,9 @@ ulong clk_set_rate(struct clk *clk, ulong rate)
if (!ops->set_rate)
return -ENOSYS;
+ /* Clean up cached rates for us and all child clocks */
+ clk_clean_rate_cache(clk);
+
return ops->set_rate(clk, rate);
}