1 // SPDX-License-Identifier: GPL-2.0
3 * Copyright (c) 2021 Rockchip Electronics Co., Ltd
9 #include <clk-uclass.h>
13 #include <asm/arch-rockchip/cru_rk3568.h>
14 #include <asm/arch-rockchip/clock.h>
15 #include <asm/arch-rockchip/hardware.h>
18 #include <dt-bindings/clock/rk3568-cru.h>
20 DECLARE_GLOBAL_DATA_PTR;
22 #if CONFIG_IS_ENABLED(OF_PLATDATA)
23 struct rk3568_clk_plat {
24 struct dtd_rockchip_rk3568_cru dtd;
27 struct rk3568_pmuclk_plat {
28 struct dtd_rockchip_rk3568_pmucru dtd;
32 #define RK3568_CPUCLK_RATE(_rate, _aclk_div, _pclk_div) \
35 .aclk_div = _aclk_div, \
36 .pclk_div = _pclk_div, \
39 #define DIV_TO_RATE(input_rate, div) ((input_rate) / ((div) + 1))
41 static struct rockchip_cpu_rate_table rk3568_cpu_rates[] = {
42 RK3568_CPUCLK_RATE(1416000000, 1, 5),
43 RK3568_CPUCLK_RATE(1296000000, 1, 5),
44 RK3568_CPUCLK_RATE(1200000000, 1, 3),
45 RK3568_CPUCLK_RATE(1104000000, 1, 3),
46 RK3568_CPUCLK_RATE(1008000000, 1, 3),
47 RK3568_CPUCLK_RATE(912000000, 1, 3),
48 RK3568_CPUCLK_RATE(816000000, 1, 3),
49 RK3568_CPUCLK_RATE(600000000, 1, 1),
50 RK3568_CPUCLK_RATE(408000000, 1, 1),
54 static struct rockchip_pll_rate_table rk3568_pll_rates[] = {
55 /* _mhz, _refdiv, _fbdiv, _postdiv1, _postdiv2, _dsmpd, _frac */
56 RK3036_PLL_RATE(1608000000, 1, 67, 1, 1, 1, 0),
57 RK3036_PLL_RATE(1416000000, 1, 118, 2, 1, 1, 0),
58 RK3036_PLL_RATE(1296000000, 1, 108, 2, 1, 1, 0),
59 RK3036_PLL_RATE(1200000000, 1, 100, 2, 1, 1, 0),
60 RK3036_PLL_RATE(1188000000, 1, 99, 2, 1, 1, 0),
61 RK3036_PLL_RATE(1104000000, 1, 92, 2, 1, 1, 0),
62 RK3036_PLL_RATE(1008000000, 1, 84, 2, 1, 1, 0),
63 RK3036_PLL_RATE(1000000000, 3, 250, 2, 1, 1, 0),
64 RK3036_PLL_RATE(912000000, 1, 76, 2, 1, 1, 0),
65 RK3036_PLL_RATE(816000000, 1, 68, 2, 1, 1, 0),
66 RK3036_PLL_RATE(600000000, 1, 100, 4, 1, 1, 0),
67 RK3036_PLL_RATE(594000000, 1, 99, 4, 1, 1, 0),
68 RK3036_PLL_RATE(500000000, 1, 125, 6, 1, 1, 0),
69 RK3036_PLL_RATE(408000000, 1, 68, 2, 2, 1, 0),
70 RK3036_PLL_RATE(400000000, 1, 100, 6, 1, 1, 0),
71 RK3036_PLL_RATE(200000000, 1, 100, 6, 2, 1, 0),
72 RK3036_PLL_RATE(100000000, 1, 150, 6, 6, 1, 0),
76 static struct rockchip_pll_clock rk3568_pll_clks[] = {
77 [APLL] = PLL(pll_rk3328, PLL_APLL, RK3568_PLL_CON(0),
78 RK3568_MODE_CON, 0, 10, 0, rk3568_pll_rates),
79 [DPLL] = PLL(pll_rk3328, PLL_DPLL, RK3568_PLL_CON(8),
80 RK3568_MODE_CON, 2, 10, 0, NULL),
81 [CPLL] = PLL(pll_rk3328, PLL_CPLL, RK3568_PLL_CON(24),
82 RK3568_MODE_CON, 4, 10, 0, rk3568_pll_rates),
83 [GPLL] = PLL(pll_rk3328, PLL_HPLL, RK3568_PLL_CON(16),
84 RK3568_MODE_CON, 6, 10, 0, rk3568_pll_rates),
85 [NPLL] = PLL(pll_rk3328, PLL_NPLL, RK3568_PLL_CON(32),
86 RK3568_MODE_CON, 10, 10, 0, rk3568_pll_rates),
87 [VPLL] = PLL(pll_rk3328, PLL_VPLL, RK3568_PLL_CON(40),
88 RK3568_MODE_CON, 12, 10, 0, rk3568_pll_rates),
89 [PPLL] = PLL(pll_rk3328, PLL_PPLL, RK3568_PMU_PLL_CON(0),
90 RK3568_PMU_MODE, 0, 10, 0, rk3568_pll_rates),
91 [HPLL] = PLL(pll_rk3328, PLL_HPLL, RK3568_PMU_PLL_CON(16),
92 RK3568_PMU_MODE, 2, 10, 0, rk3568_pll_rates),
95 #ifndef CONFIG_SPL_BUILD
97 rk3568_pmu_pll_set_rate(struct rk3568_clk_priv *priv,
98 ulong pll_id, ulong rate)
100 struct udevice *pmucru_dev;
101 struct rk3568_pmuclk_priv *pmu_priv;
104 ret = uclass_get_device_by_driver(UCLASS_CLK,
105 DM_DRIVER_GET(rockchip_rk3568_pmucru),
108 printf("%s: could not find pmucru device\n", __func__);
111 pmu_priv = dev_get_priv(pmucru_dev);
113 rockchip_pll_set_rate(&rk3568_pll_clks[pll_id],
114 pmu_priv->pmucru, pll_id, rate);
120 static ulong rk3568_pmu_pll_get_rate(struct rk3568_clk_priv *priv,
123 struct udevice *pmucru_dev;
124 struct rk3568_pmuclk_priv *pmu_priv;
127 ret = uclass_get_device_by_driver(UCLASS_CLK,
128 DM_DRIVER_GET(rockchip_rk3568_pmucru),
131 printf("%s: could not find pmucru device\n", __func__);
134 pmu_priv = dev_get_priv(pmucru_dev);
136 return rockchip_pll_get_rate(&rk3568_pll_clks[pll_id],
137 pmu_priv->pmucru, pll_id);
142 * rational_best_approximation(31415, 10000,
143 * (1 << 8) - 1, (1 << 5) - 1, &n, &d);
145 * you may look at given_numerator as a fixed point number,
146 * with the fractional part size described in given_denominator.
148 * for theoretical background, see:
149 * http://en.wikipedia.org/wiki/Continued_fraction
151 static void rational_best_approximation(unsigned long given_numerator,
152 unsigned long given_denominator,
153 unsigned long max_numerator,
154 unsigned long max_denominator,
155 unsigned long *best_numerator,
156 unsigned long *best_denominator)
158 unsigned long n, d, n0, d0, n1, d1;
161 d = given_denominator;
169 if (n1 > max_numerator || d1 > max_denominator) {
187 *best_numerator = n1;
188 *best_denominator = d1;
191 static ulong rk3568_rtc32k_get_pmuclk(struct rk3568_pmuclk_priv *priv)
193 struct rk3568_pmucru *pmucru = priv->pmucru;
197 fracdiv = readl(&pmucru->pmu_clksel_con[1]);
198 m = fracdiv & RTC32K_FRAC_NUMERATOR_MASK;
199 m >>= RTC32K_FRAC_NUMERATOR_SHIFT;
200 n = fracdiv & RTC32K_FRAC_DENOMINATOR_MASK;
201 n >>= RTC32K_FRAC_DENOMINATOR_SHIFT;
203 return OSC_HZ * m / n;
206 static ulong rk3568_rtc32k_set_pmuclk(struct rk3568_pmuclk_priv *priv,
209 struct rk3568_pmucru *pmucru = priv->pmucru;
210 unsigned long m, n, val;
212 rk_clrsetreg(&pmucru->pmu_clksel_con[0], RTC32K_SEL_MASK,
213 RTC32K_SEL_OSC0_DIV32K << RTC32K_SEL_SHIFT);
215 rational_best_approximation(rate, OSC_HZ,
219 val = m << RTC32K_FRAC_NUMERATOR_SHIFT | n;
220 writel(val, &pmucru->pmu_clksel_con[1]);
222 return rk3568_rtc32k_get_pmuclk(priv);
225 static ulong rk3568_i2c_get_pmuclk(struct rk3568_pmuclk_priv *priv,
228 struct rk3568_pmucru *pmucru = priv->pmucru;
233 con = readl(&pmucru->pmu_clksel_con[3]);
234 div = (con & CLK_I2C0_DIV_MASK) >> CLK_I2C0_DIV_SHIFT;
240 return DIV_TO_RATE(priv->ppll_hz, div);
243 static ulong rk3568_i2c_set_pmuclk(struct rk3568_pmuclk_priv *priv,
244 ulong clk_id, ulong rate)
246 struct rk3568_pmucru *pmucru = priv->pmucru;
249 src_clk_div = DIV_ROUND_UP(priv->ppll_hz, rate);
250 assert(src_clk_div - 1 <= 127);
254 rk_clrsetreg(&pmucru->pmu_clksel_con[3], CLK_I2C0_DIV_MASK,
255 (src_clk_div - 1) << CLK_I2C0_DIV_SHIFT);
261 return rk3568_i2c_get_pmuclk(priv, clk_id);
264 static ulong rk3568_pwm_get_pmuclk(struct rk3568_pmuclk_priv *priv,
267 struct rk3568_pmucru *pmucru = priv->pmucru;
268 u32 div, sel, con, parent;
272 con = readl(&pmucru->pmu_clksel_con[6]);
273 sel = (con & CLK_PWM0_SEL_MASK) >> CLK_PWM0_SEL_SHIFT;
274 div = (con & CLK_PWM0_DIV_MASK) >> CLK_PWM0_DIV_SHIFT;
275 if (sel == CLK_PWM0_SEL_XIN24M)
278 parent = priv->ppll_hz;
284 return DIV_TO_RATE(parent, div);
287 static ulong rk3568_pwm_set_pmuclk(struct rk3568_pmuclk_priv *priv,
288 ulong clk_id, ulong rate)
290 struct rk3568_pmucru *pmucru = priv->pmucru;
295 if (rate == OSC_HZ) {
296 rk_clrsetreg(&pmucru->pmu_clksel_con[6],
297 CLK_PWM0_SEL_MASK | CLK_PWM0_DIV_MASK,
298 (CLK_PWM0_SEL_XIN24M <<
299 CLK_PWM0_SEL_SHIFT) |
300 0 << CLK_PWM0_SEL_SHIFT);
302 src_clk_div = DIV_ROUND_UP(priv->ppll_hz, rate);
303 assert(src_clk_div - 1 <= 127);
304 rk_clrsetreg(&pmucru->pmu_clksel_con[6],
305 CLK_PWM0_DIV_MASK | CLK_PWM0_DIV_MASK,
306 (CLK_PWM0_SEL_PPLL << CLK_PWM0_SEL_SHIFT) |
307 (src_clk_div - 1) << CLK_PWM0_DIV_SHIFT);
314 return rk3568_pwm_get_pmuclk(priv, clk_id);
317 static ulong rk3568_pmu_get_pmuclk(struct rk3568_pmuclk_priv *priv)
319 struct rk3568_pmucru *pmucru = priv->pmucru;
320 u32 div, con, sel, parent;
322 con = readl(&pmucru->pmu_clksel_con[2]);
323 sel = (con & PCLK_PDPMU_SEL_MASK) >> PCLK_PDPMU_SEL_SHIFT;
324 div = (con & PCLK_PDPMU_DIV_MASK) >> PCLK_PDPMU_DIV_SHIFT;
328 parent = priv->ppll_hz;
330 return DIV_TO_RATE(parent, div);
333 static ulong rk3568_pmu_set_pmuclk(struct rk3568_pmuclk_priv *priv,
336 struct rk3568_pmucru *pmucru = priv->pmucru;
339 src_clk_div = DIV_ROUND_UP(priv->ppll_hz, rate);
340 assert(src_clk_div - 1 <= 31);
342 rk_clrsetreg(&pmucru->pmu_clksel_con[2],
343 PCLK_PDPMU_DIV_MASK | PCLK_PDPMU_SEL_MASK,
344 (PCLK_PDPMU_SEL_PPLL << PCLK_PDPMU_SEL_SHIFT) |
345 ((src_clk_div - 1) << PCLK_PDPMU_DIV_SHIFT));
347 return rk3568_pmu_get_pmuclk(priv);
350 static ulong rk3568_pmuclk_get_rate(struct clk *clk)
352 struct rk3568_pmuclk_priv *priv = dev_get_priv(clk->dev);
355 if (!priv->ppll_hz) {
356 printf("%s ppll=%lu\n", __func__, priv->ppll_hz);
360 debug("%s %ld\n", __func__, clk->id);
363 rate = rockchip_pll_get_rate(&rk3568_pll_clks[PPLL],
367 rate = rockchip_pll_get_rate(&rk3568_pll_clks[HPLL],
371 case CLK_RTC32K_FRAC:
372 rate = rk3568_rtc32k_get_pmuclk(priv);
375 rate = rk3568_i2c_get_pmuclk(priv, clk->id);
378 rate = rk3568_pwm_get_pmuclk(priv, clk->id);
381 rate = rk3568_pmu_get_pmuclk(priv);
390 static ulong rk3568_pmuclk_set_rate(struct clk *clk, ulong rate)
392 struct rk3568_pmuclk_priv *priv = dev_get_priv(clk->dev);
395 if (!priv->ppll_hz) {
396 printf("%s ppll=%lu\n", __func__, priv->ppll_hz);
400 debug("%s %ld %ld\n", __func__, clk->id, rate);
403 ret = rockchip_pll_set_rate(&rk3568_pll_clks[PPLL],
404 priv->pmucru, PPLL, rate);
405 priv->ppll_hz = rockchip_pll_get_rate(&rk3568_pll_clks[PPLL],
409 ret = rockchip_pll_set_rate(&rk3568_pll_clks[HPLL],
410 priv->pmucru, HPLL, rate);
411 priv->hpll_hz = rockchip_pll_get_rate(&rk3568_pll_clks[HPLL],
415 case CLK_RTC32K_FRAC:
416 ret = rk3568_rtc32k_set_pmuclk(priv, rate);
419 ret = rk3568_i2c_set_pmuclk(priv, clk->id, rate);
422 ret = rk3568_pwm_set_pmuclk(priv, clk->id, rate);
425 ret = rk3568_pmu_set_pmuclk(priv, rate);
434 static int rk3568_rtc32k_set_parent(struct clk *clk, struct clk *parent)
436 struct rk3568_pmuclk_priv *priv = dev_get_priv(clk->dev);
437 struct rk3568_pmucru *pmucru = priv->pmucru;
439 if (parent->id == CLK_RTC32K_FRAC)
440 rk_clrsetreg(&pmucru->pmu_clksel_con[0], RTC32K_SEL_MASK,
441 RTC32K_SEL_OSC0_DIV32K << RTC32K_SEL_SHIFT);
443 rk_clrsetreg(&pmucru->pmu_clksel_con[0], RTC32K_SEL_MASK,
444 RTC32K_SEL_OSC1_32K << RTC32K_SEL_SHIFT);
449 static int rk3568_pmuclk_set_parent(struct clk *clk, struct clk *parent)
453 return rk3568_rtc32k_set_parent(clk, parent);
459 static struct clk_ops rk3568_pmuclk_ops = {
460 .get_rate = rk3568_pmuclk_get_rate,
461 .set_rate = rk3568_pmuclk_set_rate,
462 .set_parent = rk3568_pmuclk_set_parent,
465 static int rk3568_pmuclk_probe(struct udevice *dev)
467 struct rk3568_pmuclk_priv *priv = dev_get_priv(dev);
470 if (priv->ppll_hz != PPLL_HZ) {
471 ret = rockchip_pll_set_rate(&rk3568_pll_clks[PPLL],
475 priv->ppll_hz = PPLL_HZ;
478 /* Ungate PCIe30phy refclk_m and refclk_n */
479 rk_clrsetreg(&priv->pmucru->pmu_clkgate_con[2], 0x3 << 13, 0 << 13);
483 static int rk3568_pmuclk_ofdata_to_platdata(struct udevice *dev)
485 struct rk3568_pmuclk_priv *priv = dev_get_priv(dev);
487 priv->pmucru = dev_read_addr_ptr(dev);
492 static int rk3568_pmuclk_bind(struct udevice *dev)
494 #if CONFIG_IS_ENABLED(RESET_ROCKCHIP)
497 ret = offsetof(struct rk3568_pmucru, pmu_softrst_con[0]);
498 ret = rockchip_reset_bind(dev, ret, 1);
500 debug("Warning: pmucru software reset driver bind faile\n");
506 static const struct udevice_id rk3568_pmuclk_ids[] = {
507 { .compatible = "rockchip,rk3568-pmucru" },
511 U_BOOT_DRIVER(rockchip_rk3568_pmucru) = {
512 .name = "rockchip_rk3568_pmucru",
514 .of_match = rk3568_pmuclk_ids,
515 .priv_auto = sizeof(struct rk3568_pmuclk_priv),
516 .of_to_plat = rk3568_pmuclk_ofdata_to_platdata,
517 .ops = &rk3568_pmuclk_ops,
518 .bind = rk3568_pmuclk_bind,
519 .probe = rk3568_pmuclk_probe,
520 #if CONFIG_IS_ENABLED(OF_PLATDATA)
521 .plat_auto = sizeof(struct rk3568_pmuclk_plat),
526 static int rk3568_armclk_set_clk(struct rk3568_clk_priv *priv, ulong hz)
528 struct rk3568_cru *cru = priv->cru;
529 const struct rockchip_cpu_rate_table *rate;
532 rate = rockchip_get_cpu_settings(rk3568_cpu_rates, hz);
534 printf("%s unsupported rate\n", __func__);
538 rk_clrsetreg(&cru->clksel_con[0],
539 CLK_CORE_PRE_SEL_MASK,
540 (CLK_CORE_PRE_SEL_SRC << CLK_CORE_PRE_SEL_SHIFT));
541 rk_clrsetreg(&cru->clksel_con[2],
542 SCLK_CORE_PRE_SEL_MASK |
543 SCLK_CORE_SRC_SEL_MASK |
544 SCLK_CORE_SRC_DIV_MASK,
545 (SCLK_CORE_PRE_SEL_SRC <<
546 SCLK_CORE_PRE_SEL_SHIFT) |
547 (SCLK_CORE_SRC_SEL_APLL <<
548 SCLK_CORE_SRC_SEL_SHIFT) |
549 (1 << SCLK_CORE_SRC_DIV_SHIFT));
552 * set up dependent divisors for DBG and ACLK clocks.
554 old_rate = rockchip_pll_get_rate(&rk3568_pll_clks[APLL],
557 if (rockchip_pll_set_rate(&rk3568_pll_clks[APLL],
558 priv->cru, APLL, hz))
560 rk_clrsetreg(&cru->clksel_con[3],
561 GICCLK_CORE_DIV_MASK | ATCLK_CORE_DIV_MASK,
562 rate->pclk_div << GICCLK_CORE_DIV_SHIFT |
563 rate->pclk_div << ATCLK_CORE_DIV_SHIFT);
564 rk_clrsetreg(&cru->clksel_con[4],
565 PERIPHCLK_CORE_PRE_DIV_MASK |
566 PCLK_CORE_PRE_DIV_MASK,
567 rate->pclk_div << PCLK_CORE_PRE_DIV_SHIFT |
568 rate->pclk_div << PERIPHCLK_CORE_PRE_DIV_SHIFT);
569 rk_clrsetreg(&cru->clksel_con[5],
570 ACLK_CORE_NDFT_DIV_MASK,
571 rate->aclk_div << ACLK_CORE_NDFT_DIV_SHIFT);
572 } else if (old_rate < hz) {
573 rk_clrsetreg(&cru->clksel_con[3],
574 GICCLK_CORE_DIV_MASK | ATCLK_CORE_DIV_MASK,
575 rate->pclk_div << GICCLK_CORE_DIV_SHIFT |
576 rate->pclk_div << ATCLK_CORE_DIV_SHIFT);
577 rk_clrsetreg(&cru->clksel_con[4],
578 PERIPHCLK_CORE_PRE_DIV_MASK |
579 PCLK_CORE_PRE_DIV_MASK,
580 rate->pclk_div << PCLK_CORE_PRE_DIV_SHIFT |
581 rate->pclk_div << PERIPHCLK_CORE_PRE_DIV_SHIFT);
582 rk_clrsetreg(&cru->clksel_con[5],
583 ACLK_CORE_NDFT_DIV_MASK,
584 rate->aclk_div << ACLK_CORE_NDFT_DIV_SHIFT);
585 if (rockchip_pll_set_rate(&rk3568_pll_clks[APLL],
586 priv->cru, APLL, hz))
593 static ulong rk3568_cpll_div_get_rate(struct rk3568_clk_priv *priv,
596 struct rk3568_cru *cru = priv->cru;
597 int div, mask, shift, con;
602 mask = CPLL_500M_DIV_MASK;
603 shift = CPLL_500M_DIV_SHIFT;
607 mask = CPLL_333M_DIV_MASK;
608 shift = CPLL_333M_DIV_SHIFT;
612 mask = CPLL_250M_DIV_MASK;
613 shift = CPLL_250M_DIV_SHIFT;
617 mask = CPLL_125M_DIV_MASK;
618 shift = CPLL_125M_DIV_SHIFT;
622 mask = CPLL_100M_DIV_MASK;
623 shift = CPLL_100M_DIV_SHIFT;
627 mask = CPLL_62P5M_DIV_MASK;
628 shift = CPLL_62P5M_DIV_SHIFT;
632 mask = CPLL_50M_DIV_MASK;
633 shift = CPLL_50M_DIV_SHIFT;
637 mask = CPLL_25M_DIV_MASK;
638 shift = CPLL_25M_DIV_SHIFT;
644 div = (readl(&cru->clksel_con[con]) & mask) >> shift;
645 return DIV_TO_RATE(priv->cpll_hz, div);
648 static ulong rk3568_cpll_div_set_rate(struct rk3568_clk_priv *priv,
649 ulong clk_id, ulong rate)
651 struct rk3568_cru *cru = priv->cru;
652 int div, mask, shift, con;
657 mask = CPLL_500M_DIV_MASK;
658 shift = CPLL_500M_DIV_SHIFT;
662 mask = CPLL_333M_DIV_MASK;
663 shift = CPLL_333M_DIV_SHIFT;
667 mask = CPLL_250M_DIV_MASK;
668 shift = CPLL_250M_DIV_SHIFT;
672 mask = CPLL_125M_DIV_MASK;
673 shift = CPLL_125M_DIV_SHIFT;
677 mask = CPLL_100M_DIV_MASK;
678 shift = CPLL_100M_DIV_SHIFT;
682 mask = CPLL_62P5M_DIV_MASK;
683 shift = CPLL_62P5M_DIV_SHIFT;
687 mask = CPLL_50M_DIV_MASK;
688 shift = CPLL_50M_DIV_SHIFT;
692 mask = CPLL_25M_DIV_MASK;
693 shift = CPLL_25M_DIV_SHIFT;
699 div = DIV_ROUND_UP(priv->cpll_hz, rate);
700 assert(div - 1 <= 31);
701 rk_clrsetreg(&cru->clksel_con[con],
702 mask, (div - 1) << shift);
703 return rk3568_cpll_div_get_rate(priv, clk_id);
706 static ulong rk3568_bus_get_clk(struct rk3568_clk_priv *priv, ulong clk_id)
708 struct rk3568_cru *cru = priv->cru;
713 con = readl(&cru->clksel_con[50]);
714 sel = (con & ACLK_BUS_SEL_MASK) >> ACLK_BUS_SEL_SHIFT;
715 if (sel == ACLK_BUS_SEL_200M)
717 else if (sel == ACLK_BUS_SEL_150M)
719 else if (sel == ACLK_BUS_SEL_100M)
726 con = readl(&cru->clksel_con[50]);
727 sel = (con & PCLK_BUS_SEL_MASK) >> PCLK_BUS_SEL_SHIFT;
728 if (sel == PCLK_BUS_SEL_100M)
730 else if (sel == PCLK_BUS_SEL_75M)
732 else if (sel == PCLK_BUS_SEL_50M)
744 static ulong rk3568_bus_set_clk(struct rk3568_clk_priv *priv,
745 ulong clk_id, ulong rate)
747 struct rk3568_cru *cru = priv->cru;
752 if (rate == 200 * MHz)
753 src_clk = ACLK_BUS_SEL_200M;
754 else if (rate == 150 * MHz)
755 src_clk = ACLK_BUS_SEL_150M;
756 else if (rate == 100 * MHz)
757 src_clk = ACLK_BUS_SEL_100M;
759 src_clk = ACLK_BUS_SEL_24M;
760 rk_clrsetreg(&cru->clksel_con[50],
762 src_clk << ACLK_BUS_SEL_SHIFT);
766 if (rate == 100 * MHz)
767 src_clk = PCLK_BUS_SEL_100M;
768 else if (rate == 75 * MHz)
769 src_clk = PCLK_BUS_SEL_75M;
770 else if (rate == 50 * MHz)
771 src_clk = PCLK_BUS_SEL_50M;
773 src_clk = PCLK_BUS_SEL_24M;
774 rk_clrsetreg(&cru->clksel_con[50],
776 src_clk << PCLK_BUS_SEL_SHIFT);
780 printf("do not support this bus freq\n");
784 return rk3568_bus_get_clk(priv, clk_id);
787 static ulong rk3568_perimid_get_clk(struct rk3568_clk_priv *priv, ulong clk_id)
789 struct rk3568_cru *cru = priv->cru;
794 con = readl(&cru->clksel_con[10]);
795 sel = (con & ACLK_PERIMID_SEL_MASK) >> ACLK_PERIMID_SEL_SHIFT;
796 if (sel == ACLK_PERIMID_SEL_300M)
798 else if (sel == ACLK_PERIMID_SEL_200M)
800 else if (sel == ACLK_PERIMID_SEL_100M)
806 con = readl(&cru->clksel_con[10]);
807 sel = (con & HCLK_PERIMID_SEL_MASK) >> HCLK_PERIMID_SEL_SHIFT;
808 if (sel == HCLK_PERIMID_SEL_150M)
810 else if (sel == HCLK_PERIMID_SEL_100M)
812 else if (sel == HCLK_PERIMID_SEL_75M)
824 static ulong rk3568_perimid_set_clk(struct rk3568_clk_priv *priv,
825 ulong clk_id, ulong rate)
827 struct rk3568_cru *cru = priv->cru;
832 if (rate == 300 * MHz)
833 src_clk = ACLK_PERIMID_SEL_300M;
834 else if (rate == 200 * MHz)
835 src_clk = ACLK_PERIMID_SEL_200M;
836 else if (rate == 100 * MHz)
837 src_clk = ACLK_PERIMID_SEL_100M;
839 src_clk = ACLK_PERIMID_SEL_24M;
840 rk_clrsetreg(&cru->clksel_con[10],
841 ACLK_PERIMID_SEL_MASK,
842 src_clk << ACLK_PERIMID_SEL_SHIFT);
845 if (rate == 150 * MHz)
846 src_clk = HCLK_PERIMID_SEL_150M;
847 else if (rate == 100 * MHz)
848 src_clk = HCLK_PERIMID_SEL_100M;
849 else if (rate == 75 * MHz)
850 src_clk = HCLK_PERIMID_SEL_75M;
852 src_clk = HCLK_PERIMID_SEL_24M;
853 rk_clrsetreg(&cru->clksel_con[10],
854 HCLK_PERIMID_SEL_MASK,
855 src_clk << HCLK_PERIMID_SEL_SHIFT);
859 printf("do not support this permid freq\n");
863 return rk3568_perimid_get_clk(priv, clk_id);
866 static ulong rk3568_top_get_clk(struct rk3568_clk_priv *priv, ulong clk_id)
868 struct rk3568_cru *cru = priv->cru;
873 con = readl(&cru->clksel_con[73]);
874 sel = (con & ACLK_TOP_HIGH_SEL_MASK) >> ACLK_TOP_HIGH_SEL_SHIFT;
875 if (sel == ACLK_TOP_HIGH_SEL_500M)
877 else if (sel == ACLK_TOP_HIGH_SEL_400M)
879 else if (sel == ACLK_TOP_HIGH_SEL_300M)
885 con = readl(&cru->clksel_con[73]);
886 sel = (con & ACLK_TOP_LOW_SEL_MASK) >> ACLK_TOP_LOW_SEL_SHIFT;
887 if (sel == ACLK_TOP_LOW_SEL_400M)
889 else if (sel == ACLK_TOP_LOW_SEL_300M)
891 else if (sel == ACLK_TOP_LOW_SEL_200M)
897 con = readl(&cru->clksel_con[73]);
898 sel = (con & HCLK_TOP_SEL_MASK) >> HCLK_TOP_SEL_SHIFT;
899 if (sel == HCLK_TOP_SEL_150M)
901 else if (sel == HCLK_TOP_SEL_100M)
903 else if (sel == HCLK_TOP_SEL_75M)
909 con = readl(&cru->clksel_con[73]);
910 sel = (con & PCLK_TOP_SEL_MASK) >> PCLK_TOP_SEL_SHIFT;
911 if (sel == PCLK_TOP_SEL_100M)
913 else if (sel == PCLK_TOP_SEL_75M)
915 else if (sel == PCLK_TOP_SEL_50M)
927 static ulong rk3568_top_set_clk(struct rk3568_clk_priv *priv,
928 ulong clk_id, ulong rate)
930 struct rk3568_cru *cru = priv->cru;
935 if (rate == 500 * MHz)
936 src_clk = ACLK_TOP_HIGH_SEL_500M;
937 else if (rate == 400 * MHz)
938 src_clk = ACLK_TOP_HIGH_SEL_400M;
939 else if (rate == 300 * MHz)
940 src_clk = ACLK_TOP_HIGH_SEL_300M;
942 src_clk = ACLK_TOP_HIGH_SEL_24M;
943 rk_clrsetreg(&cru->clksel_con[73],
944 ACLK_TOP_HIGH_SEL_MASK,
945 src_clk << ACLK_TOP_HIGH_SEL_SHIFT);
948 if (rate == 400 * MHz)
949 src_clk = ACLK_TOP_LOW_SEL_400M;
950 else if (rate == 300 * MHz)
951 src_clk = ACLK_TOP_LOW_SEL_300M;
952 else if (rate == 200 * MHz)
953 src_clk = ACLK_TOP_LOW_SEL_200M;
955 src_clk = ACLK_TOP_LOW_SEL_24M;
956 rk_clrsetreg(&cru->clksel_con[73],
957 ACLK_TOP_LOW_SEL_MASK,
958 src_clk << ACLK_TOP_LOW_SEL_SHIFT);
961 if (rate == 150 * MHz)
962 src_clk = HCLK_TOP_SEL_150M;
963 else if (rate == 100 * MHz)
964 src_clk = HCLK_TOP_SEL_100M;
965 else if (rate == 75 * MHz)
966 src_clk = HCLK_TOP_SEL_75M;
968 src_clk = HCLK_TOP_SEL_24M;
969 rk_clrsetreg(&cru->clksel_con[73],
971 src_clk << HCLK_TOP_SEL_SHIFT);
974 if (rate == 100 * MHz)
975 src_clk = PCLK_TOP_SEL_100M;
976 else if (rate == 75 * MHz)
977 src_clk = PCLK_TOP_SEL_75M;
978 else if (rate == 50 * MHz)
979 src_clk = PCLK_TOP_SEL_50M;
981 src_clk = PCLK_TOP_SEL_24M;
982 rk_clrsetreg(&cru->clksel_con[73],
984 src_clk << PCLK_TOP_SEL_SHIFT);
988 printf("do not support this permid freq\n");
992 return rk3568_top_get_clk(priv, clk_id);
995 static ulong rk3568_i2c_get_clk(struct rk3568_clk_priv *priv, ulong clk_id)
997 struct rk3568_cru *cru = priv->cru;
1007 con = readl(&cru->clksel_con[71]);
1008 sel = (con & CLK_I2C_SEL_MASK) >> CLK_I2C_SEL_SHIFT;
1009 if (sel == CLK_I2C_SEL_200M)
1011 else if (sel == CLK_I2C_SEL_100M)
1013 else if (sel == CLK_I2C_SEL_CPLL_100M)
1025 static ulong rk3568_i2c_set_clk(struct rk3568_clk_priv *priv, ulong clk_id,
1028 struct rk3568_cru *cru = priv->cru;
1031 if (rate == 200 * MHz)
1032 src_clk = CLK_I2C_SEL_200M;
1033 else if (rate == 100 * MHz)
1034 src_clk = CLK_I2C_SEL_100M;
1036 src_clk = CLK_I2C_SEL_24M;
1044 rk_clrsetreg(&cru->clksel_con[71], CLK_I2C_SEL_MASK,
1045 src_clk << CLK_I2C_SEL_SHIFT);
1051 return rk3568_i2c_get_clk(priv, clk_id);
1054 static ulong rk3568_spi_get_clk(struct rk3568_clk_priv *priv, ulong clk_id)
1056 struct rk3568_cru *cru = priv->cru;
1059 con = readl(&cru->clksel_con[72]);
1063 sel = (con & CLK_SPI0_SEL_MASK) >> CLK_SPI0_SEL_SHIFT;
1066 sel = (con & CLK_SPI1_SEL_MASK) >> CLK_SPI1_SEL_SHIFT;
1069 sel = (con & CLK_SPI2_SEL_MASK) >> CLK_SPI2_SEL_SHIFT;
1072 sel = (con & CLK_SPI3_SEL_MASK) >> CLK_SPI3_SEL_SHIFT;
1079 case CLK_SPI_SEL_200M:
1081 case CLK_SPI_SEL_24M:
1083 case CLK_SPI_SEL_CPLL_100M:
1090 static ulong rk3568_spi_set_clk(struct rk3568_clk_priv *priv,
1091 ulong clk_id, ulong rate)
1093 struct rk3568_cru *cru = priv->cru;
1096 if (rate == 200 * MHz)
1097 src_clk = CLK_SPI_SEL_200M;
1098 else if (rate == 100 * MHz)
1099 src_clk = CLK_SPI_SEL_CPLL_100M;
1101 src_clk = CLK_SPI_SEL_24M;
1105 rk_clrsetreg(&cru->clksel_con[72],
1107 src_clk << CLK_SPI0_SEL_SHIFT);
1110 rk_clrsetreg(&cru->clksel_con[72],
1112 src_clk << CLK_SPI1_SEL_SHIFT);
1115 rk_clrsetreg(&cru->clksel_con[72],
1117 src_clk << CLK_SPI2_SEL_SHIFT);
1120 rk_clrsetreg(&cru->clksel_con[72],
1122 src_clk << CLK_SPI3_SEL_SHIFT);
1128 return rk3568_spi_get_clk(priv, clk_id);
1131 static ulong rk3568_pwm_get_clk(struct rk3568_clk_priv *priv, ulong clk_id)
1133 struct rk3568_cru *cru = priv->cru;
1136 con = readl(&cru->clksel_con[72]);
1140 sel = (con & CLK_PWM1_SEL_MASK) >> CLK_PWM3_SEL_SHIFT;
1143 sel = (con & CLK_PWM2_SEL_MASK) >> CLK_PWM2_SEL_SHIFT;
1146 sel = (con & CLK_PWM3_SEL_MASK) >> CLK_PWM3_SEL_SHIFT;
1153 case CLK_PWM_SEL_100M:
1155 case CLK_PWM_SEL_24M:
1157 case CLK_PWM_SEL_CPLL_100M:
1164 static ulong rk3568_pwm_set_clk(struct rk3568_clk_priv *priv,
1165 ulong clk_id, ulong rate)
1167 struct rk3568_cru *cru = priv->cru;
1170 if (rate == 100 * MHz)
1171 src_clk = CLK_PWM_SEL_100M;
1173 src_clk = CLK_PWM_SEL_24M;
1177 rk_clrsetreg(&cru->clksel_con[72],
1179 src_clk << CLK_PWM1_SEL_SHIFT);
1182 rk_clrsetreg(&cru->clksel_con[72],
1184 src_clk << CLK_PWM2_SEL_SHIFT);
1187 rk_clrsetreg(&cru->clksel_con[72],
1189 src_clk << CLK_PWM3_SEL_SHIFT);
1195 return rk3568_pwm_get_clk(priv, clk_id);
1198 static ulong rk3568_adc_get_clk(struct rk3568_clk_priv *priv, ulong clk_id)
1200 struct rk3568_cru *cru = priv->cru;
1201 u32 div, sel, con, prate;
1206 case CLK_TSADC_TSEN:
1207 con = readl(&cru->clksel_con[51]);
1208 div = (con & CLK_TSADC_TSEN_DIV_MASK) >>
1209 CLK_TSADC_TSEN_DIV_SHIFT;
1210 sel = (con & CLK_TSADC_TSEN_SEL_MASK) >>
1211 CLK_TSADC_TSEN_SEL_SHIFT;
1212 if (sel == CLK_TSADC_TSEN_SEL_24M)
1216 return DIV_TO_RATE(prate, div);
1218 con = readl(&cru->clksel_con[51]);
1219 div = (con & CLK_TSADC_DIV_MASK) >> CLK_TSADC_DIV_SHIFT;
1220 prate = rk3568_adc_get_clk(priv, CLK_TSADC_TSEN);
1221 return DIV_TO_RATE(prate, div);
1227 static ulong rk3568_adc_set_clk(struct rk3568_clk_priv *priv,
1228 ulong clk_id, ulong rate)
1230 struct rk3568_cru *cru = priv->cru;
1237 case CLK_TSADC_TSEN:
1238 if (!(OSC_HZ % rate)) {
1239 src_clk_div = DIV_ROUND_UP(OSC_HZ, rate);
1240 assert(src_clk_div - 1 <= 7);
1241 rk_clrsetreg(&cru->clksel_con[51],
1242 CLK_TSADC_TSEN_SEL_MASK |
1243 CLK_TSADC_TSEN_DIV_MASK,
1244 (CLK_TSADC_TSEN_SEL_24M <<
1245 CLK_TSADC_TSEN_SEL_SHIFT) |
1246 (src_clk_div - 1) <<
1247 CLK_TSADC_TSEN_DIV_SHIFT);
1249 src_clk_div = DIV_ROUND_UP(100 * MHz, rate);
1250 assert(src_clk_div - 1 <= 7);
1251 rk_clrsetreg(&cru->clksel_con[51],
1252 CLK_TSADC_TSEN_SEL_MASK |
1253 CLK_TSADC_TSEN_DIV_MASK,
1254 (CLK_TSADC_TSEN_SEL_100M <<
1255 CLK_TSADC_TSEN_SEL_SHIFT) |
1256 (src_clk_div - 1) <<
1257 CLK_TSADC_TSEN_DIV_SHIFT);
1261 prate = rk3568_adc_get_clk(priv, CLK_TSADC_TSEN);
1262 src_clk_div = DIV_ROUND_UP(prate, rate);
1263 assert(src_clk_div - 1 <= 128);
1264 rk_clrsetreg(&cru->clksel_con[51],
1266 (src_clk_div - 1) << CLK_TSADC_DIV_SHIFT);
1271 return rk3568_adc_get_clk(priv, clk_id);
1274 static ulong rk3568_crypto_get_rate(struct rk3568_clk_priv *priv, ulong clk_id)
1276 struct rk3568_cru *cru = priv->cru;
1280 case ACLK_SECURE_FLASH:
1281 case ACLK_CRYPTO_NS:
1282 con = readl(&cru->clksel_con[27]);
1283 sel = (con & ACLK_SECURE_FLASH_SEL_MASK) >>
1284 ACLK_SECURE_FLASH_SEL_SHIFT;
1285 if (sel == ACLK_SECURE_FLASH_SEL_200M)
1287 else if (sel == ACLK_SECURE_FLASH_SEL_150M)
1289 else if (sel == ACLK_SECURE_FLASH_SEL_100M)
1293 case HCLK_SECURE_FLASH:
1294 case HCLK_CRYPTO_NS:
1295 case CLK_CRYPTO_NS_RNG:
1296 con = readl(&cru->clksel_con[27]);
1297 sel = (con & HCLK_SECURE_FLASH_SEL_MASK) >>
1298 HCLK_SECURE_FLASH_SEL_SHIFT;
1299 if (sel == HCLK_SECURE_FLASH_SEL_150M)
1301 else if (sel == HCLK_SECURE_FLASH_SEL_100M)
1303 else if (sel == HCLK_SECURE_FLASH_SEL_75M)
1307 case CLK_CRYPTO_NS_CORE:
1308 con = readl(&cru->clksel_con[27]);
1309 sel = (con & CLK_CRYPTO_CORE_SEL_MASK) >>
1310 CLK_CRYPTO_CORE_SEL_SHIFT;
1311 if (sel == CLK_CRYPTO_CORE_SEL_200M)
1313 else if (sel == CLK_CRYPTO_CORE_SEL_150M)
1317 case CLK_CRYPTO_NS_PKA:
1318 con = readl(&cru->clksel_con[27]);
1319 sel = (con & CLK_CRYPTO_PKA_SEL_MASK) >>
1320 CLK_CRYPTO_PKA_SEL_SHIFT;
1321 if (sel == CLK_CRYPTO_PKA_SEL_300M)
1323 else if (sel == CLK_CRYPTO_PKA_SEL_200M)
1332 static ulong rk3568_crypto_set_rate(struct rk3568_clk_priv *priv,
1333 ulong clk_id, ulong rate)
1335 struct rk3568_cru *cru = priv->cru;
1336 u32 src_clk, mask, shift;
1339 case ACLK_SECURE_FLASH:
1340 case ACLK_CRYPTO_NS:
1341 mask = ACLK_SECURE_FLASH_SEL_MASK;
1342 shift = ACLK_SECURE_FLASH_SEL_SHIFT;
1343 if (rate == 200 * MHz)
1344 src_clk = ACLK_SECURE_FLASH_SEL_200M;
1345 else if (rate == 150 * MHz)
1346 src_clk = ACLK_SECURE_FLASH_SEL_150M;
1347 else if (rate == 100 * MHz)
1348 src_clk = ACLK_SECURE_FLASH_SEL_100M;
1350 src_clk = ACLK_SECURE_FLASH_SEL_24M;
1352 case HCLK_SECURE_FLASH:
1353 case HCLK_CRYPTO_NS:
1354 case CLK_CRYPTO_NS_RNG:
1355 mask = HCLK_SECURE_FLASH_SEL_MASK;
1356 shift = HCLK_SECURE_FLASH_SEL_SHIFT;
1357 if (rate == 150 * MHz)
1358 src_clk = HCLK_SECURE_FLASH_SEL_150M;
1359 else if (rate == 100 * MHz)
1360 src_clk = HCLK_SECURE_FLASH_SEL_100M;
1361 else if (rate == 75 * MHz)
1362 src_clk = HCLK_SECURE_FLASH_SEL_75M;
1364 src_clk = HCLK_SECURE_FLASH_SEL_24M;
1366 case CLK_CRYPTO_NS_CORE:
1367 mask = CLK_CRYPTO_CORE_SEL_MASK;
1368 shift = CLK_CRYPTO_CORE_SEL_SHIFT;
1369 if (rate == 200 * MHz)
1370 src_clk = CLK_CRYPTO_CORE_SEL_200M;
1371 else if (rate == 150 * MHz)
1372 src_clk = CLK_CRYPTO_CORE_SEL_150M;
1374 src_clk = CLK_CRYPTO_CORE_SEL_100M;
1376 case CLK_CRYPTO_NS_PKA:
1377 mask = CLK_CRYPTO_PKA_SEL_MASK;
1378 shift = CLK_CRYPTO_PKA_SEL_SHIFT;
1379 if (rate == 300 * MHz)
1380 src_clk = CLK_CRYPTO_PKA_SEL_300M;
1381 else if (rate == 200 * MHz)
1382 src_clk = CLK_CRYPTO_PKA_SEL_200M;
1384 src_clk = CLK_CRYPTO_PKA_SEL_100M;
1390 rk_clrsetreg(&cru->clksel_con[27], mask, src_clk << shift);
1392 return rk3568_crypto_get_rate(priv, clk_id);
1395 static ulong rk3568_sdmmc_get_clk(struct rk3568_clk_priv *priv, ulong clk_id)
1397 struct rk3568_cru *cru = priv->cru;
1403 con = readl(&cru->clksel_con[30]);
1404 sel = (con & CLK_SDMMC0_SEL_MASK) >> CLK_SDMMC0_SEL_SHIFT;
1407 con = readl(&cru->clksel_con[30]);
1408 sel = (con & CLK_SDMMC1_SEL_MASK) >> CLK_SDMMC1_SEL_SHIFT;
1411 con = readl(&cru->clksel_con[32]);
1412 sel = (con & CLK_SDMMC2_SEL_MASK) >> CLK_SDMMC2_SEL_SHIFT;
1419 case CLK_SDMMC_SEL_24M:
1421 case CLK_SDMMC_SEL_400M:
1423 case CLK_SDMMC_SEL_300M:
1425 case CLK_SDMMC_SEL_100M:
1427 case CLK_SDMMC_SEL_50M:
1429 case CLK_SDMMC_SEL_750K:
1436 static ulong rk3568_sdmmc_set_clk(struct rk3568_clk_priv *priv,
1437 ulong clk_id, ulong rate)
1439 struct rk3568_cru *cru = priv->cru;
1444 src_clk = CLK_SDMMC_SEL_24M;
1447 src_clk = CLK_SDMMC_SEL_400M;
1450 src_clk = CLK_SDMMC_SEL_300M;
1453 src_clk = CLK_SDMMC_SEL_100M;
1457 src_clk = CLK_SDMMC_SEL_50M;
1461 src_clk = CLK_SDMMC_SEL_750K;
1470 rk_clrsetreg(&cru->clksel_con[30],
1471 CLK_SDMMC0_SEL_MASK,
1472 src_clk << CLK_SDMMC0_SEL_SHIFT);
1475 rk_clrsetreg(&cru->clksel_con[30],
1476 CLK_SDMMC1_SEL_MASK,
1477 src_clk << CLK_SDMMC1_SEL_SHIFT);
1480 rk_clrsetreg(&cru->clksel_con[32],
1481 CLK_SDMMC2_SEL_MASK,
1482 src_clk << CLK_SDMMC2_SEL_SHIFT);
1488 return rk3568_sdmmc_get_clk(priv, clk_id);
1491 static ulong rk3568_sfc_get_clk(struct rk3568_clk_priv *priv)
1493 struct rk3568_cru *cru = priv->cru;
1496 con = readl(&cru->clksel_con[28]);
1497 sel = (con & SCLK_SFC_SEL_MASK) >> SCLK_SFC_SEL_SHIFT;
1499 case SCLK_SFC_SEL_24M:
1501 case SCLK_SFC_SEL_50M:
1503 case SCLK_SFC_SEL_75M:
1505 case SCLK_SFC_SEL_100M:
1507 case SCLK_SFC_SEL_125M:
1509 case SCLK_SFC_SEL_150M:
1516 static ulong rk3568_sfc_set_clk(struct rk3568_clk_priv *priv, ulong rate)
1518 struct rk3568_cru *cru = priv->cru;
1523 src_clk = SCLK_SFC_SEL_24M;
1526 src_clk = SCLK_SFC_SEL_50M;
1529 src_clk = SCLK_SFC_SEL_75M;
1532 src_clk = SCLK_SFC_SEL_100M;
1535 src_clk = SCLK_SFC_SEL_125M;
1538 src_clk = SCLK_SFC_SEL_150M;
1544 rk_clrsetreg(&cru->clksel_con[28],
1546 src_clk << SCLK_SFC_SEL_SHIFT);
1548 return rk3568_sfc_get_clk(priv);
1551 static ulong rk3568_nand_get_clk(struct rk3568_clk_priv *priv)
1553 struct rk3568_cru *cru = priv->cru;
1556 con = readl(&cru->clksel_con[28]);
1557 sel = (con & NCLK_NANDC_SEL_MASK) >> NCLK_NANDC_SEL_SHIFT;
1559 case NCLK_NANDC_SEL_200M:
1561 case NCLK_NANDC_SEL_150M:
1563 case NCLK_NANDC_SEL_100M:
1565 case NCLK_NANDC_SEL_24M:
1572 static ulong rk3568_nand_set_clk(struct rk3568_clk_priv *priv, ulong rate)
1574 struct rk3568_cru *cru = priv->cru;
1579 src_clk = NCLK_NANDC_SEL_24M;
1582 src_clk = NCLK_NANDC_SEL_100M;
1585 src_clk = NCLK_NANDC_SEL_150M;
1588 src_clk = NCLK_NANDC_SEL_200M;
1594 rk_clrsetreg(&cru->clksel_con[28],
1595 NCLK_NANDC_SEL_MASK,
1596 src_clk << NCLK_NANDC_SEL_SHIFT);
1598 return rk3568_nand_get_clk(priv);
1601 static ulong rk3568_emmc_get_clk(struct rk3568_clk_priv *priv)
1603 struct rk3568_cru *cru = priv->cru;
1606 con = readl(&cru->clksel_con[28]);
1607 sel = (con & CCLK_EMMC_SEL_MASK) >> CCLK_EMMC_SEL_SHIFT;
1609 case CCLK_EMMC_SEL_200M:
1611 case CCLK_EMMC_SEL_150M:
1613 case CCLK_EMMC_SEL_100M:
1615 case CCLK_EMMC_SEL_50M:
1617 case CCLK_EMMC_SEL_375K:
1619 case CCLK_EMMC_SEL_24M:
1626 static ulong rk3568_emmc_set_clk(struct rk3568_clk_priv *priv, ulong rate)
1628 struct rk3568_cru *cru = priv->cru;
1633 src_clk = CCLK_EMMC_SEL_24M;
1637 src_clk = CCLK_EMMC_SEL_50M;
1640 src_clk = CCLK_EMMC_SEL_100M;
1643 src_clk = CCLK_EMMC_SEL_150M;
1646 src_clk = CCLK_EMMC_SEL_200M;
1650 src_clk = CCLK_EMMC_SEL_375K;
1656 rk_clrsetreg(&cru->clksel_con[28],
1658 src_clk << CCLK_EMMC_SEL_SHIFT);
1660 return rk3568_emmc_get_clk(priv);
1663 static ulong rk3568_emmc_get_bclk(struct rk3568_clk_priv *priv)
1665 struct rk3568_cru *cru = priv->cru;
1668 con = readl(&cru->clksel_con[28]);
1669 sel = (con & BCLK_EMMC_SEL_MASK) >> BCLK_EMMC_SEL_SHIFT;
1671 case BCLK_EMMC_SEL_200M:
1673 case BCLK_EMMC_SEL_150M:
1675 case BCLK_EMMC_SEL_125M:
1682 static ulong rk3568_emmc_set_bclk(struct rk3568_clk_priv *priv, ulong rate)
1684 struct rk3568_cru *cru = priv->cru;
1689 src_clk = BCLK_EMMC_SEL_200M;
1692 src_clk = BCLK_EMMC_SEL_150M;
1695 src_clk = BCLK_EMMC_SEL_125M;
1701 rk_clrsetreg(&cru->clksel_con[28],
1703 src_clk << BCLK_EMMC_SEL_SHIFT);
1705 return rk3568_emmc_get_bclk(priv);
1708 #ifndef CONFIG_SPL_BUILD
1709 static ulong rk3568_aclk_vop_get_clk(struct rk3568_clk_priv *priv)
1711 struct rk3568_cru *cru = priv->cru;
1712 u32 div, sel, con, parent;
1714 con = readl(&cru->clksel_con[38]);
1715 div = (con & ACLK_VOP_PRE_DIV_MASK) >> ACLK_VOP_PRE_DIV_SHIFT;
1716 sel = (con & ACLK_VOP_PRE_SEL_MASK) >> ACLK_VOP_PRE_SEL_SHIFT;
1717 if (sel == ACLK_VOP_PRE_SEL_GPLL)
1718 parent = priv->gpll_hz;
1719 else if (sel == ACLK_VOP_PRE_SEL_CPLL)
1720 parent = priv->cpll_hz;
1721 else if (sel == ACLK_VOP_PRE_SEL_VPLL)
1722 parent = priv->vpll_hz;
1724 parent = priv->hpll_hz;
1726 return DIV_TO_RATE(parent, div);
1729 static ulong rk3568_aclk_vop_set_clk(struct rk3568_clk_priv *priv, ulong rate)
1731 struct rk3568_cru *cru = priv->cru;
1732 int src_clk_div, src_clk_mux;
1734 if ((priv->cpll_hz % rate) == 0) {
1735 src_clk_div = DIV_ROUND_UP(priv->cpll_hz, rate);
1736 src_clk_mux = ACLK_VOP_PRE_SEL_CPLL;
1738 src_clk_div = DIV_ROUND_UP(priv->gpll_hz, rate);
1739 src_clk_mux = ACLK_VOP_PRE_SEL_GPLL;
1741 assert(src_clk_div - 1 <= 31);
1742 rk_clrsetreg(&cru->clksel_con[38],
1743 ACLK_VOP_PRE_SEL_MASK | ACLK_VOP_PRE_DIV_MASK,
1744 src_clk_mux << ACLK_VOP_PRE_SEL_SHIFT |
1745 (src_clk_div - 1) << ACLK_VOP_PRE_DIV_SHIFT);
1747 return rk3568_aclk_vop_get_clk(priv);
1750 static ulong rk3568_dclk_vop_get_clk(struct rk3568_clk_priv *priv, ulong clk_id)
1752 struct rk3568_cru *cru = priv->cru;
1753 u32 conid, div, sel, con, parent;
1769 con = readl(&cru->clksel_con[conid]);
1770 div = (con & DCLK0_VOP_DIV_MASK) >> DCLK0_VOP_DIV_SHIFT;
1771 sel = (con & DCLK0_VOP_SEL_MASK) >> DCLK0_VOP_SEL_SHIFT;
1772 if (sel == DCLK_VOP_SEL_HPLL)
1773 parent = rk3568_pmu_pll_get_rate(priv, HPLL);
1774 else if (sel == DCLK_VOP_SEL_VPLL)
1775 parent = rockchip_pll_get_rate(&rk3568_pll_clks[VPLL],
1777 else if (sel == DCLK_VOP_SEL_GPLL)
1778 parent = priv->gpll_hz;
1779 else if (sel == DCLK_VOP_SEL_CPLL)
1780 parent = priv->cpll_hz;
1784 return DIV_TO_RATE(parent, div);
1787 #define RK3568_VOP_PLL_LIMIT_FREQ 600000000
1789 static ulong rk3568_dclk_vop_set_clk(struct rk3568_clk_priv *priv,
1790 ulong clk_id, ulong rate)
1792 struct rk3568_cru *cru = priv->cru;
1793 ulong pll_rate, now, best_rate = 0;
1794 u32 i, conid, con, sel, div, best_div = 0, best_sel = 0;
1810 con = readl(&cru->clksel_con[conid]);
1811 sel = (con & DCLK0_VOP_SEL_MASK) >> DCLK0_VOP_SEL_SHIFT;
1813 if (sel == DCLK_VOP_SEL_HPLL) {
1815 rk_clrsetreg(&cru->clksel_con[conid],
1816 DCLK0_VOP_DIV_MASK | DCLK0_VOP_SEL_MASK,
1817 (DCLK_VOP_SEL_HPLL << DCLK0_VOP_SEL_SHIFT) |
1818 ((div - 1) << DCLK0_VOP_DIV_SHIFT));
1819 rk3568_pmu_pll_set_rate(priv, HPLL, div * rate);
1820 } else if (sel == DCLK_VOP_SEL_VPLL) {
1821 div = DIV_ROUND_UP(RK3568_VOP_PLL_LIMIT_FREQ, rate);
1822 rk_clrsetreg(&cru->clksel_con[conid],
1823 DCLK0_VOP_DIV_MASK | DCLK0_VOP_SEL_MASK,
1824 (DCLK_VOP_SEL_VPLL << DCLK0_VOP_SEL_SHIFT) |
1825 ((div - 1) << DCLK0_VOP_DIV_SHIFT));
1826 rockchip_pll_set_rate(&rk3568_pll_clks[VPLL],
1827 priv->cru, VPLL, div * rate);
1829 for (i = 0; i <= DCLK_VOP_SEL_CPLL; i++) {
1831 case DCLK_VOP_SEL_GPLL:
1832 pll_rate = priv->gpll_hz;
1834 case DCLK_VOP_SEL_CPLL:
1835 pll_rate = priv->cpll_hz;
1838 printf("do not support this vop pll sel\n");
1842 div = DIV_ROUND_UP(pll_rate, rate);
1845 now = pll_rate / div;
1846 if (abs(rate - now) < abs(rate - best_rate)) {
1851 debug("p_rate=%lu, best_rate=%lu, div=%u, sel=%u\n",
1852 pll_rate, best_rate, best_div, best_sel);
1856 rk_clrsetreg(&cru->clksel_con[conid],
1857 DCLK0_VOP_DIV_MASK | DCLK0_VOP_SEL_MASK,
1858 best_sel << DCLK0_VOP_SEL_SHIFT |
1859 (best_div - 1) << DCLK0_VOP_DIV_SHIFT);
1861 printf("do not support this vop freq %lu\n", rate);
1865 return rk3568_dclk_vop_get_clk(priv, clk_id);
1868 static ulong rk3568_gmac_src_get_clk(struct rk3568_clk_priv *priv,
1871 struct rk3568_cru *cru = priv->cru;
1874 con = readl(&cru->clksel_con[31 + mac_id * 2]);
1875 sel = (con & CLK_MAC0_2TOP_SEL_MASK) >> CLK_MAC0_2TOP_SEL_SHIFT;
1878 case CLK_MAC0_2TOP_SEL_125M:
1880 case CLK_MAC0_2TOP_SEL_50M:
1882 case CLK_MAC0_2TOP_SEL_25M:
1884 case CLK_MAC0_2TOP_SEL_PPLL:
1885 return rk3568_pmu_pll_get_rate(priv, HPLL);
1891 static ulong rk3568_gmac_src_set_clk(struct rk3568_clk_priv *priv,
1892 ulong mac_id, ulong rate)
1894 struct rk3568_cru *cru = priv->cru;
1899 src_clk = CLK_MAC0_2TOP_SEL_125M;
1902 src_clk = CLK_MAC0_2TOP_SEL_50M;
1905 src_clk = CLK_MAC0_2TOP_SEL_25M;
1911 rk_clrsetreg(&cru->clksel_con[31 + mac_id * 2],
1912 CLK_MAC0_2TOP_SEL_MASK,
1913 src_clk << CLK_MAC0_2TOP_SEL_SHIFT);
1915 return rk3568_gmac_src_get_clk(priv, mac_id);
1918 static ulong rk3568_gmac_out_get_clk(struct rk3568_clk_priv *priv,
1921 struct rk3568_cru *cru = priv->cru;
1924 con = readl(&cru->clksel_con[31 + mac_id * 2]);
1925 sel = (con & CLK_MAC0_OUT_SEL_MASK) >> CLK_MAC0_OUT_SEL_SHIFT;
1928 case CLK_MAC0_OUT_SEL_125M:
1930 case CLK_MAC0_OUT_SEL_50M:
1932 case CLK_MAC0_OUT_SEL_25M:
1934 case CLK_MAC0_OUT_SEL_24M:
1941 static ulong rk3568_gmac_out_set_clk(struct rk3568_clk_priv *priv,
1942 ulong mac_id, ulong rate)
1944 struct rk3568_cru *cru = priv->cru;
1949 src_clk = CLK_MAC0_OUT_SEL_125M;
1952 src_clk = CLK_MAC0_OUT_SEL_50M;
1955 src_clk = CLK_MAC0_OUT_SEL_25M;
1958 src_clk = CLK_MAC0_OUT_SEL_24M;
1964 rk_clrsetreg(&cru->clksel_con[31 + mac_id * 2],
1965 CLK_MAC0_OUT_SEL_MASK,
1966 src_clk << CLK_MAC0_OUT_SEL_SHIFT);
1968 return rk3568_gmac_out_get_clk(priv, mac_id);
1971 static ulong rk3568_gmac_ptp_ref_get_clk(struct rk3568_clk_priv *priv,
1974 struct rk3568_cru *cru = priv->cru;
1977 con = readl(&cru->clksel_con[31 + mac_id * 2]);
1978 sel = (con & CLK_GMAC0_PTP_REF_SEL_MASK) >> CLK_GMAC0_PTP_REF_SEL_SHIFT;
1981 case CLK_GMAC0_PTP_REF_SEL_62_5M:
1983 case CLK_GMAC0_PTP_REF_SEL_100M:
1985 case CLK_GMAC0_PTP_REF_SEL_50M:
1987 case CLK_GMAC0_PTP_REF_SEL_24M:
1994 static ulong rk3568_gmac_ptp_ref_set_clk(struct rk3568_clk_priv *priv,
1995 ulong mac_id, ulong rate)
1997 struct rk3568_cru *cru = priv->cru;
2002 src_clk = CLK_GMAC0_PTP_REF_SEL_62_5M;
2005 src_clk = CLK_GMAC0_PTP_REF_SEL_100M;
2008 src_clk = CLK_GMAC0_PTP_REF_SEL_50M;
2011 src_clk = CLK_GMAC0_PTP_REF_SEL_24M;
2017 rk_clrsetreg(&cru->clksel_con[31 + mac_id * 2],
2018 CLK_GMAC0_PTP_REF_SEL_MASK,
2019 src_clk << CLK_GMAC0_PTP_REF_SEL_SHIFT);
2021 return rk3568_gmac_ptp_ref_get_clk(priv, mac_id);
2024 static ulong rk3568_gmac_tx_rx_set_clk(struct rk3568_clk_priv *priv,
2025 ulong mac_id, ulong rate)
2027 struct rk3568_cru *cru = priv->cru;
2028 u32 con, sel, div_sel;
2030 con = readl(&cru->clksel_con[31 + mac_id * 2]);
2031 sel = (con & RMII0_MODE_MASK) >> RMII0_MODE_SHIFT;
2033 if (sel == RMII0_MODE_SEL_RGMII) {
2034 if (rate == 2500000)
2035 div_sel = RGMII0_CLK_SEL_2_5M;
2036 else if (rate == 25000000)
2037 div_sel = RGMII0_CLK_SEL_25M;
2039 div_sel = RGMII0_CLK_SEL_125M;
2040 rk_clrsetreg(&cru->clksel_con[31 + mac_id * 2],
2041 RGMII0_CLK_SEL_MASK,
2042 div_sel << RGMII0_CLK_SEL_SHIFT);
2043 } else if (sel == RMII0_MODE_SEL_RMII) {
2044 if (rate == 2500000)
2045 div_sel = RMII0_CLK_SEL_2_5M;
2047 div_sel = RMII0_CLK_SEL_25M;
2048 rk_clrsetreg(&cru->clksel_con[31 + mac_id * 2],
2050 div_sel << RMII0_CLK_SEL_SHIFT);
2056 static ulong rk3568_ebc_get_clk(struct rk3568_clk_priv *priv)
2058 struct rk3568_cru *cru = priv->cru;
2059 u32 con, div, p_rate;
2061 con = readl(&cru->clksel_con[79]);
2062 div = (con & CPLL_333M_DIV_MASK) >> CPLL_333M_DIV_SHIFT;
2063 p_rate = DIV_TO_RATE(priv->cpll_hz, div);
2065 con = readl(&cru->clksel_con[43]);
2066 div = (con & DCLK_EBC_SEL_MASK) >> DCLK_EBC_SEL_SHIFT;
2068 case DCLK_EBC_SEL_GPLL_400M:
2070 case DCLK_EBC_SEL_CPLL_333M:
2072 case DCLK_EBC_SEL_GPLL_200M:
2079 static ulong rk3568_ebc_set_clk(struct rk3568_clk_priv *priv, ulong rate)
2081 struct rk3568_cru *cru = priv->cru;
2084 src_clk_div = DIV_ROUND_UP(priv->cpll_hz, rate);
2085 assert(src_clk_div - 1 <= 31);
2086 rk_clrsetreg(&cru->clksel_con[79],
2088 (src_clk_div - 1) << CPLL_333M_DIV_SHIFT);
2089 rk_clrsetreg(&cru->clksel_con[43],
2091 DCLK_EBC_SEL_CPLL_333M << DCLK_EBC_SEL_SHIFT);
2093 return rk3568_ebc_get_clk(priv);
2096 static ulong rk3568_rkvdec_get_clk(struct rk3568_clk_priv *priv, ulong clk_id)
2098 struct rk3568_cru *cru = priv->cru;
2099 u32 con, div, src, p_rate;
2102 case ACLK_RKVDEC_PRE:
2104 con = readl(&cru->clksel_con[47]);
2105 src = (con & ACLK_RKVDEC_SEL_MASK) >> ACLK_RKVDEC_SEL_SHIFT;
2106 div = (con & ACLK_RKVDEC_DIV_MASK) >> ACLK_RKVDEC_DIV_SHIFT;
2107 if (src == ACLK_RKVDEC_SEL_CPLL)
2108 p_rate = priv->cpll_hz;
2110 p_rate = priv->gpll_hz;
2111 return DIV_TO_RATE(p_rate, div);
2112 case CLK_RKVDEC_CORE:
2113 con = readl(&cru->clksel_con[49]);
2114 src = (con & CLK_RKVDEC_CORE_SEL_MASK)
2115 >> CLK_RKVDEC_CORE_SEL_SHIFT;
2116 div = (con & CLK_RKVDEC_CORE_DIV_MASK)
2117 >> CLK_RKVDEC_CORE_DIV_SHIFT;
2118 if (src == CLK_RKVDEC_CORE_SEL_CPLL)
2119 p_rate = priv->cpll_hz;
2120 else if (src == CLK_RKVDEC_CORE_SEL_NPLL)
2121 p_rate = priv->npll_hz;
2122 else if (src == CLK_RKVDEC_CORE_SEL_VPLL)
2123 p_rate = priv->vpll_hz;
2125 p_rate = priv->gpll_hz;
2126 return DIV_TO_RATE(p_rate, div);
2132 static ulong rk3568_rkvdec_set_clk(struct rk3568_clk_priv *priv,
2133 ulong clk_id, ulong rate)
2135 struct rk3568_cru *cru = priv->cru;
2136 int src_clk_div, src, p_rate;
2139 case ACLK_RKVDEC_PRE:
2141 src = (readl(&cru->clksel_con[47]) & ACLK_RKVDEC_SEL_MASK)
2142 >> ACLK_RKVDEC_SEL_SHIFT;
2143 if (src == ACLK_RKVDEC_SEL_CPLL)
2144 p_rate = priv->cpll_hz;
2146 p_rate = priv->gpll_hz;
2147 src_clk_div = DIV_ROUND_UP(p_rate, rate);
2148 assert(src_clk_div - 1 <= 31);
2149 rk_clrsetreg(&cru->clksel_con[47],
2150 ACLK_RKVDEC_SEL_MASK |
2151 ACLK_RKVDEC_DIV_MASK,
2152 (src << ACLK_RKVDEC_SEL_SHIFT) |
2153 (src_clk_div - 1) << ACLK_RKVDEC_DIV_SHIFT);
2155 case CLK_RKVDEC_CORE:
2156 src = (readl(&cru->clksel_con[49]) & CLK_RKVDEC_CORE_SEL_MASK)
2157 >> CLK_RKVDEC_CORE_SEL_SHIFT;
2158 if (src == CLK_RKVDEC_CORE_SEL_CPLL)
2159 p_rate = priv->cpll_hz;
2160 else if (src == CLK_RKVDEC_CORE_SEL_NPLL)
2161 p_rate = priv->npll_hz;
2162 else if (src == CLK_RKVDEC_CORE_SEL_VPLL)
2163 p_rate = priv->vpll_hz;
2165 p_rate = priv->gpll_hz;
2166 src_clk_div = DIV_ROUND_UP(p_rate, rate);
2167 assert(src_clk_div - 1 <= 31);
2168 rk_clrsetreg(&cru->clksel_con[49],
2169 CLK_RKVDEC_CORE_SEL_MASK |
2170 CLK_RKVDEC_CORE_DIV_MASK,
2171 (src << CLK_RKVDEC_CORE_SEL_SHIFT) |
2172 (src_clk_div - 1) << CLK_RKVDEC_CORE_DIV_SHIFT);
2178 return rk3568_rkvdec_get_clk(priv, clk_id);
2181 static ulong rk3568_uart_get_rate(struct rk3568_clk_priv *priv, ulong clk_id)
2183 struct rk3568_cru *cru = priv->cru;
2184 u32 reg, con, fracdiv, div, src, p_src, p_rate;
2218 con = readl(&cru->clksel_con[reg]);
2219 src = (con & CLK_UART_SEL_MASK) >> CLK_UART_SEL_SHIFT;
2220 div = (con & CLK_UART_SRC_DIV_MASK) >> CLK_UART_SRC_DIV_SHIFT;
2221 p_src = (con & CLK_UART_SRC_SEL_MASK) >> CLK_UART_SRC_SEL_SHIFT;
2222 if (p_src == CLK_UART_SRC_SEL_GPLL)
2223 p_rate = priv->gpll_hz;
2224 else if (p_src == CLK_UART_SRC_SEL_CPLL)
2225 p_rate = priv->cpll_hz;
2228 if (src == CLK_UART_SEL_SRC) {
2229 return DIV_TO_RATE(p_rate, div);
2230 } else if (src == CLK_UART_SEL_FRAC) {
2231 fracdiv = readl(&cru->clksel_con[reg + 1]);
2232 n = fracdiv & CLK_UART_FRAC_NUMERATOR_MASK;
2233 n >>= CLK_UART_FRAC_NUMERATOR_SHIFT;
2234 m = fracdiv & CLK_UART_FRAC_DENOMINATOR_MASK;
2235 m >>= CLK_UART_FRAC_DENOMINATOR_SHIFT;
2236 return DIV_TO_RATE(p_rate, div) * n / m;
2242 static ulong rk3568_uart_set_rate(struct rk3568_clk_priv *priv,
2243 ulong clk_id, ulong rate)
2245 struct rk3568_cru *cru = priv->cru;
2246 u32 reg, clk_src, uart_src, div;
2247 unsigned long m = 0, n = 0, val;
2249 if (priv->gpll_hz % rate == 0) {
2250 clk_src = CLK_UART_SRC_SEL_GPLL;
2251 uart_src = CLK_UART_SEL_SRC;
2252 div = DIV_ROUND_UP(priv->gpll_hz, rate);
2253 } else if (priv->cpll_hz % rate == 0) {
2254 clk_src = CLK_UART_SRC_SEL_CPLL;
2255 uart_src = CLK_UART_SEL_SRC;
2256 div = DIV_ROUND_UP(priv->gpll_hz, rate);
2257 } else if (rate == OSC_HZ) {
2258 clk_src = CLK_UART_SRC_SEL_GPLL;
2259 uart_src = CLK_UART_SEL_XIN24M;
2262 clk_src = CLK_UART_SRC_SEL_GPLL;
2263 uart_src = CLK_UART_SEL_FRAC;
2265 rational_best_approximation(rate, priv->gpll_hz / div,
2302 rk_clrsetreg(&cru->clksel_con[reg],
2303 CLK_UART_SEL_MASK | CLK_UART_SRC_SEL_MASK |
2304 CLK_UART_SRC_DIV_MASK,
2305 (clk_src << CLK_UART_SRC_SEL_SHIFT) |
2306 (uart_src << CLK_UART_SEL_SHIFT) |
2307 ((div - 1) << CLK_UART_SRC_DIV_SHIFT));
2309 val = m << CLK_UART_FRAC_NUMERATOR_SHIFT | n;
2310 writel(val, &cru->clksel_con[reg + 1]);
2313 return rk3568_uart_get_rate(priv, clk_id);
2317 static ulong rk3568_clk_get_rate(struct clk *clk)
2319 struct rk3568_clk_priv *priv = dev_get_priv(clk->dev);
2322 if (!priv->gpll_hz) {
2323 printf("%s gpll=%lu\n", __func__, priv->gpll_hz);
2330 rate = rockchip_pll_get_rate(&rk3568_pll_clks[APLL], priv->cru,
2334 rate = rockchip_pll_get_rate(&rk3568_pll_clks[CPLL], priv->cru,
2338 rate = rockchip_pll_get_rate(&rk3568_pll_clks[GPLL], priv->cru,
2342 rate = rockchip_pll_get_rate(&rk3568_pll_clks[NPLL], priv->cru,
2346 rate = rockchip_pll_get_rate(&rk3568_pll_clks[VPLL], priv->cru,
2350 rate = rockchip_pll_get_rate(&rk3568_pll_clks[DPLL], priv->cru,
2356 rate = rk3568_bus_get_clk(priv, clk->id);
2360 rate = rk3568_perimid_get_clk(priv, clk->id);
2366 rate = rk3568_top_get_clk(priv, clk->id);
2373 rate = rk3568_i2c_get_clk(priv, clk->id);
2379 rate = rk3568_spi_get_clk(priv, clk->id);
2384 rate = rk3568_pwm_get_clk(priv, clk->id);
2387 case CLK_TSADC_TSEN:
2389 rate = rk3568_adc_get_clk(priv, clk->id);
2395 rate = rk3568_sdmmc_get_clk(priv, clk->id);
2398 rate = rk3568_sfc_get_clk(priv);
2401 rate = rk3568_nand_get_clk(priv);
2404 rate = rk3568_emmc_get_clk(priv);
2407 rate = rk3568_emmc_get_bclk(priv);
2409 #ifndef CONFIG_SPL_BUILD
2411 rate = rk3568_aclk_vop_get_clk(priv);
2416 rate = rk3568_dclk_vop_get_clk(priv, clk->id);
2420 case CLK_MAC0_REFOUT:
2421 rate = rk3568_gmac_src_get_clk(priv, 0);
2424 rate = rk3568_gmac_out_get_clk(priv, 0);
2426 case CLK_GMAC0_PTP_REF:
2427 rate = rk3568_gmac_ptp_ref_get_clk(priv, 0);
2431 case CLK_MAC1_REFOUT:
2432 rate = rk3568_gmac_src_get_clk(priv, 1);
2435 rate = rk3568_gmac_out_get_clk(priv, 1);
2437 case CLK_GMAC1_PTP_REF:
2438 rate = rk3568_gmac_ptp_ref_get_clk(priv, 1);
2441 rate = rk3568_ebc_get_clk(priv);
2443 case ACLK_RKVDEC_PRE:
2445 case CLK_RKVDEC_CORE:
2446 rate = rk3568_rkvdec_get_clk(priv, clk->id);
2460 rate = rk3568_uart_get_rate(priv, clk->id);
2463 case ACLK_SECURE_FLASH:
2464 case ACLK_CRYPTO_NS:
2465 case HCLK_SECURE_FLASH:
2466 case HCLK_CRYPTO_NS:
2467 case CLK_CRYPTO_NS_RNG:
2468 case CLK_CRYPTO_NS_CORE:
2469 case CLK_CRYPTO_NS_PKA:
2470 rate = rk3568_crypto_get_rate(priv, clk->id);
2480 rate = rk3568_cpll_div_get_rate(priv, clk->id);
2489 static ulong rk3568_clk_set_rate(struct clk *clk, ulong rate)
2491 struct rk3568_clk_priv *priv = dev_get_priv(clk->dev);
2494 if (!priv->gpll_hz) {
2495 printf("%s gpll=%lu\n", __func__, priv->gpll_hz);
2502 if (priv->armclk_hz)
2503 rk3568_armclk_set_clk(priv, rate);
2504 priv->armclk_hz = rate;
2507 ret = rockchip_pll_set_rate(&rk3568_pll_clks[CPLL], priv->cru,
2509 priv->cpll_hz = rockchip_pll_get_rate(&rk3568_pll_clks[CPLL],
2513 ret = rockchip_pll_set_rate(&rk3568_pll_clks[GPLL], priv->cru,
2515 priv->gpll_hz = rockchip_pll_get_rate(&rk3568_pll_clks[GPLL],
2519 ret = rockchip_pll_set_rate(&rk3568_pll_clks[NPLL], priv->cru,
2523 ret = rockchip_pll_set_rate(&rk3568_pll_clks[VPLL], priv->cru,
2525 priv->vpll_hz = rockchip_pll_get_rate(&rk3568_pll_clks[VPLL],
2532 ret = rk3568_bus_set_clk(priv, clk->id, rate);
2536 ret = rk3568_perimid_set_clk(priv, clk->id, rate);
2542 ret = rk3568_top_set_clk(priv, clk->id, rate);
2549 ret = rk3568_i2c_set_clk(priv, clk->id, rate);
2555 ret = rk3568_spi_set_clk(priv, clk->id, rate);
2560 ret = rk3568_pwm_set_clk(priv, clk->id, rate);
2563 case CLK_TSADC_TSEN:
2565 ret = rk3568_adc_set_clk(priv, clk->id, rate);
2571 ret = rk3568_sdmmc_set_clk(priv, clk->id, rate);
2574 ret = rk3568_sfc_set_clk(priv, rate);
2577 ret = rk3568_nand_set_clk(priv, rate);
2580 ret = rk3568_emmc_set_clk(priv, rate);
2583 ret = rk3568_emmc_set_bclk(priv, rate);
2585 #ifndef CONFIG_SPL_BUILD
2587 ret = rk3568_aclk_vop_set_clk(priv, rate);
2592 ret = rk3568_dclk_vop_set_clk(priv, clk->id, rate);
2596 case CLK_MAC0_REFOUT:
2597 ret = rk3568_gmac_src_set_clk(priv, 0, rate);
2600 ret = rk3568_gmac_out_set_clk(priv, 0, rate);
2602 case SCLK_GMAC0_RX_TX:
2603 ret = rk3568_gmac_tx_rx_set_clk(priv, 0, rate);
2605 case CLK_GMAC0_PTP_REF:
2606 ret = rk3568_gmac_ptp_ref_set_clk(priv, 0, rate);
2610 case CLK_MAC1_REFOUT:
2611 ret = rk3568_gmac_src_set_clk(priv, 1, rate);
2614 ret = rk3568_gmac_out_set_clk(priv, 1, rate);
2616 case SCLK_GMAC1_RX_TX:
2617 ret = rk3568_gmac_tx_rx_set_clk(priv, 1, rate);
2619 case CLK_GMAC1_PTP_REF:
2620 ret = rk3568_gmac_ptp_ref_set_clk(priv, 1, rate);
2623 ret = rk3568_ebc_set_clk(priv, rate);
2625 case ACLK_RKVDEC_PRE:
2627 case CLK_RKVDEC_CORE:
2628 ret = rk3568_rkvdec_set_clk(priv, clk->id, rate);
2642 ret = rk3568_uart_set_rate(priv, clk->id, rate);
2645 case ACLK_SECURE_FLASH:
2646 case ACLK_CRYPTO_NS:
2647 case HCLK_SECURE_FLASH:
2648 case HCLK_CRYPTO_NS:
2649 case CLK_CRYPTO_NS_RNG:
2650 case CLK_CRYPTO_NS_CORE:
2651 case CLK_CRYPTO_NS_PKA:
2652 ret = rk3568_crypto_set_rate(priv, clk->id, rate);
2662 ret = rk3568_cpll_div_set_rate(priv, clk->id, rate);
2671 #if (IS_ENABLED(OF_CONTROL)) || (!IS_ENABLED(OF_PLATDATA))
2672 static int rk3568_gmac0_src_set_parent(struct clk *clk, struct clk *parent)
2674 struct rk3568_clk_priv *priv = dev_get_priv(clk->dev);
2675 struct rk3568_cru *cru = priv->cru;
2677 if (parent->id == CLK_MAC0_2TOP)
2678 rk_clrsetreg(&cru->clksel_con[31],
2679 RMII0_EXTCLK_SEL_MASK,
2680 RMII0_EXTCLK_SEL_MAC0_TOP <<
2681 RMII0_EXTCLK_SEL_SHIFT);
2683 rk_clrsetreg(&cru->clksel_con[31],
2684 RMII0_EXTCLK_SEL_MASK,
2685 RMII0_EXTCLK_SEL_IO << RMII0_EXTCLK_SEL_SHIFT);
2689 static int rk3568_gmac1_src_set_parent(struct clk *clk, struct clk *parent)
2691 struct rk3568_clk_priv *priv = dev_get_priv(clk->dev);
2692 struct rk3568_cru *cru = priv->cru;
2694 if (parent->id == CLK_MAC1_2TOP)
2695 rk_clrsetreg(&cru->clksel_con[33],
2696 RMII0_EXTCLK_SEL_MASK,
2697 RMII0_EXTCLK_SEL_MAC0_TOP <<
2698 RMII0_EXTCLK_SEL_SHIFT);
2700 rk_clrsetreg(&cru->clksel_con[33],
2701 RMII0_EXTCLK_SEL_MASK,
2702 RMII0_EXTCLK_SEL_IO << RMII0_EXTCLK_SEL_SHIFT);
2706 static int rk3568_gmac0_tx_rx_set_parent(struct clk *clk, struct clk *parent)
2708 struct rk3568_clk_priv *priv = dev_get_priv(clk->dev);
2709 struct rk3568_cru *cru = priv->cru;
2711 if (parent->id == SCLK_GMAC0_RGMII_SPEED)
2712 rk_clrsetreg(&cru->clksel_con[31],
2714 RMII0_MODE_SEL_RGMII << RMII0_MODE_SHIFT);
2715 else if (parent->id == SCLK_GMAC0_RMII_SPEED)
2716 rk_clrsetreg(&cru->clksel_con[31],
2718 RMII0_MODE_SEL_RMII << RMII0_MODE_SHIFT);
2720 rk_clrsetreg(&cru->clksel_con[31],
2722 RMII0_MODE_SEL_GMII << RMII0_MODE_SHIFT);
2727 static int rk3568_gmac1_tx_rx_set_parent(struct clk *clk, struct clk *parent)
2729 struct rk3568_clk_priv *priv = dev_get_priv(clk->dev);
2730 struct rk3568_cru *cru = priv->cru;
2732 if (parent->id == SCLK_GMAC1_RGMII_SPEED)
2733 rk_clrsetreg(&cru->clksel_con[33],
2735 RMII0_MODE_SEL_RGMII << RMII0_MODE_SHIFT);
2736 else if (parent->id == SCLK_GMAC1_RMII_SPEED)
2737 rk_clrsetreg(&cru->clksel_con[33],
2739 RMII0_MODE_SEL_RMII << RMII0_MODE_SHIFT);
2741 rk_clrsetreg(&cru->clksel_con[33],
2743 RMII0_MODE_SEL_GMII << RMII0_MODE_SHIFT);
2748 static int rk3568_dclk_vop_set_parent(struct clk *clk, struct clk *parent)
2750 struct rk3568_clk_priv *priv = dev_get_priv(clk->dev);
2751 struct rk3568_cru *cru = priv->cru;
2767 if (parent->id == PLL_VPLL) {
2768 rk_clrsetreg(&cru->clksel_con[con_id], DCLK0_VOP_SEL_MASK,
2769 DCLK_VOP_SEL_VPLL << DCLK0_VOP_SEL_SHIFT);
2771 rk_clrsetreg(&cru->clksel_con[con_id], DCLK0_VOP_SEL_MASK,
2772 DCLK_VOP_SEL_HPLL << DCLK0_VOP_SEL_SHIFT);
2778 static int rk3568_rkvdec_set_parent(struct clk *clk, struct clk *parent)
2780 struct rk3568_clk_priv *priv = dev_get_priv(clk->dev);
2781 struct rk3568_cru *cru = priv->cru;
2782 u32 con_id, mask, shift;
2785 case ACLK_RKVDEC_PRE:
2787 mask = ACLK_RKVDEC_SEL_MASK;
2788 shift = ACLK_RKVDEC_SEL_SHIFT;
2790 case CLK_RKVDEC_CORE:
2792 mask = CLK_RKVDEC_CORE_SEL_MASK;
2793 shift = CLK_RKVDEC_CORE_SEL_SHIFT;
2798 if (parent->id == PLL_CPLL) {
2799 rk_clrsetreg(&cru->clksel_con[con_id], mask,
2800 ACLK_RKVDEC_SEL_CPLL << shift);
2802 rk_clrsetreg(&cru->clksel_con[con_id], mask,
2803 ACLK_RKVDEC_SEL_GPLL << shift);
2809 static int rk3568_clk_set_parent(struct clk *clk, struct clk *parent)
2813 return rk3568_gmac0_src_set_parent(clk, parent);
2815 return rk3568_gmac1_src_set_parent(clk, parent);
2816 case SCLK_GMAC0_RX_TX:
2817 return rk3568_gmac0_tx_rx_set_parent(clk, parent);
2818 case SCLK_GMAC1_RX_TX:
2819 return rk3568_gmac1_tx_rx_set_parent(clk, parent);
2823 return rk3568_dclk_vop_set_parent(clk, parent);
2824 case ACLK_RKVDEC_PRE:
2825 case CLK_RKVDEC_CORE:
2826 return rk3568_rkvdec_set_parent(clk, parent);
2835 static struct clk_ops rk3568_clk_ops = {
2836 .get_rate = rk3568_clk_get_rate,
2837 .set_rate = rk3568_clk_set_rate,
2838 #if (IS_ENABLED(OF_CONTROL)) || (!IS_ENABLED(OF_PLATDATA))
2839 .set_parent = rk3568_clk_set_parent,
2843 static void rk3568_clk_init(struct rk3568_clk_priv *priv)
2847 priv->sync_kernel = false;
2848 if (!priv->armclk_enter_hz) {
2849 priv->armclk_enter_hz =
2850 rockchip_pll_get_rate(&rk3568_pll_clks[APLL],
2852 priv->armclk_init_hz = priv->armclk_enter_hz;
2855 if (priv->armclk_init_hz != APLL_HZ) {
2856 ret = rk3568_armclk_set_clk(priv, APLL_HZ);
2858 priv->armclk_init_hz = APLL_HZ;
2860 if (priv->cpll_hz != CPLL_HZ) {
2861 ret = rockchip_pll_set_rate(&rk3568_pll_clks[CPLL], priv->cru,
2864 priv->cpll_hz = CPLL_HZ;
2866 if (priv->gpll_hz != GPLL_HZ) {
2867 ret = rockchip_pll_set_rate(&rk3568_pll_clks[GPLL], priv->cru,
2870 priv->gpll_hz = GPLL_HZ;
2873 #ifdef CONFIG_SPL_BUILD
2874 ret = rk3568_bus_set_clk(priv, ACLK_BUS, 150000000);
2876 printf("Fail to set the ACLK_BUS clock.\n");
2879 priv->ppll_hz = rk3568_pmu_pll_get_rate(priv, PPLL);
2880 priv->hpll_hz = rk3568_pmu_pll_get_rate(priv, HPLL);
2883 static int rk3568_clk_probe(struct udevice *dev)
2885 struct rk3568_clk_priv *priv = dev_get_priv(dev);
2888 priv->grf = syscon_get_first_range(ROCKCHIP_SYSCON_GRF);
2889 if (IS_ERR(priv->grf))
2890 return PTR_ERR(priv->grf);
2892 rk3568_clk_init(priv);
2894 /* Process 'assigned-{clocks/clock-parents/clock-rates}' properties */
2895 ret = clk_set_defaults(dev, 1);
2897 debug("%s clk_set_defaults failed %d\n", __func__, ret);
2899 priv->sync_kernel = true;
2904 static int rk3568_clk_ofdata_to_platdata(struct udevice *dev)
2906 struct rk3568_clk_priv *priv = dev_get_priv(dev);
2908 priv->cru = dev_read_addr_ptr(dev);
2913 static int rk3568_clk_bind(struct udevice *dev)
2916 struct udevice *sys_child;
2917 struct sysreset_reg *priv;
2919 /* The reset driver does not have a device node, so bind it here */
2920 ret = device_bind_driver(dev, "rockchip_sysreset", "sysreset",
2923 debug("Warning: No sysreset driver: ret=%d\n", ret);
2925 priv = malloc(sizeof(struct sysreset_reg));
2926 priv->glb_srst_fst_value = offsetof(struct rk3568_cru,
2928 priv->glb_srst_snd_value = offsetof(struct rk3568_cru,
2932 #if CONFIG_IS_ENABLED(RESET_ROCKCHIP)
2933 ret = offsetof(struct rk3568_cru, softrst_con[0]);
2934 ret = rockchip_reset_bind(dev, ret, 30);
2936 debug("Warning: software reset driver bind faile\n");
2942 static const struct udevice_id rk3568_clk_ids[] = {
2943 { .compatible = "rockchip,rk3568-cru" },
2947 U_BOOT_DRIVER(rockchip_rk3568_cru) = {
2948 .name = "rockchip_rk3568_cru",
2950 .of_match = rk3568_clk_ids,
2951 .priv_auto = sizeof(struct rk3568_clk_priv),
2952 .of_to_plat = rk3568_clk_ofdata_to_platdata,
2953 .ops = &rk3568_clk_ops,
2954 .bind = rk3568_clk_bind,
2955 .probe = rk3568_clk_probe,
2956 #if CONFIG_IS_ENABLED(OF_PLATDATA)
2957 .plat_auto = sizeof(struct rk3568_clk_plat),