21 #include <linux/kernel.h>
22 #include <linux/device.h>
23 #include <linux/list.h>
24 #include <linux/errno.h>
28 #include <linux/bitops.h>
31 #include <plat/clock.h>
39 #define DPLL_AUTOIDLE_DISABLE 0x0
40 #define DPLL_AUTOIDLE_LOW_POWER_STOP 0x1
42 #define MAX_DPLL_WAIT_TRIES 1000000
47 static void _omap3_dpll_write_clken(
struct clk *
clk,
u8 clken_bits)
49 const struct dpll_data *
dd;
55 v &= ~dd->enable_mask;
56 v |= clken_bits <<
__ffs(dd->enable_mask);
63 const struct dpll_data *
dd;
71 state <<=
__ffs(dd->idlest_mask);
73 while (((
__raw_readl(dd->idlest_reg) & dd->idlest_mask) != state) &&
81 clk_name, (state) ?
"locked" :
"bypassed");
83 pr_debug(
"clock: %s transition to '%s' in %d loops\n",
84 clk_name, (state) ?
"locked" :
"bypassed", i);
93 static u16 _omap3_dpll_compute_freqsel(
struct clk *clk,
u8 n)
100 pr_debug(
"clock: fint is %lu\n", fint);
102 if (fint >= 750000 && fint <= 1000000)
104 else if (fint > 1000000 && fint <= 1250000)
106 else if (fint > 1250000 && fint <= 1500000)
108 else if (fint > 1500000 && fint <= 1750000)
110 else if (fint > 1750000 && fint <= 2100000)
112 else if (fint > 7500000 && fint <= 10000000)
114 else if (fint > 10000000 && fint <= 12500000)
116 else if (fint > 12500000 && fint <= 15000000)
118 else if (fint > 15000000 && fint <= 17500000)
120 else if (fint > 17500000 && fint <= 21000000)
123 pr_debug(
"clock: unknown freqsel setting for %d\n", n);
138 static int _omap3_noncore_dpll_lock(
struct clk *clk)
140 const struct dpll_data *
dd;
148 state <<=
__ffs(dd->idlest_mask);
151 if ((
__raw_readl(dd->idlest_reg) & dd->idlest_mask) == state)
161 r = _omap3_wait_dpll_status(clk, 1);
183 static int _omap3_noncore_dpll_bypass(
struct clk *clk)
191 pr_debug(
"clock: configuring DPLL %s for low-power bypass\n",
198 r = _omap3_wait_dpll_status(clk, 0);
215 static int _omap3_noncore_dpll_stop(
struct clk *clk)
246 static void _lookup_dco(
struct clk *clk,
u8 *dco,
u16 m,
u8 n)
248 unsigned long fint, clkinp;
251 fint = (clkinp /
n) * m;
253 if (fint < 1000000000)
271 static void _lookup_sddiv(
struct clk *clk,
u8 *sd_div,
u16 m,
u8 n)
273 unsigned long clkinp,
sd;
283 mod1 = (clkinp *
m) % (250 * n);
284 sd = (clkinp *
m) / (250 * n);
303 static int omap3_noncore_dpll_program(
struct clk *clk,
u16 m,
u8 n,
u16 freqsel)
305 struct dpll_data *dd = clk->dpll_data;
310 _omap3_noncore_dpll_bypass(clk);
318 v &= ~dd->freqsel_mask;
319 v |= freqsel <<
__ffs(dd->freqsel_mask);
325 v &= ~(dd->mult_mask | dd->div1_mask);
326 v |= m <<
__ffs(dd->mult_mask);
327 v |= (n - 1) <<
__ffs(dd->div1_mask);
331 _lookup_dco(clk, &dco, m, n);
332 v &= ~(dd->dco_mask);
333 v |= dco <<
__ffs(dd->dco_mask);
335 if (dd->sddiv_mask) {
336 _lookup_sddiv(clk, &sd_div, m, n);
337 v &= ~(dd->sddiv_mask);
338 v |= sd_div <<
__ffs(dd->sddiv_mask);
347 _omap3_noncore_dpll_lock(clk);
384 struct dpll_data *
dd;
394 WARN_ON(parent != dd->clk_bypass);
395 r = _omap3_noncore_dpll_bypass(clk);
397 WARN_ON(parent != dd->clk_ref);
398 r = _omap3_noncore_dpll_lock(clk);
420 _omap3_noncore_dpll_stop(clk);
439 struct clk *new_parent =
NULL;
440 unsigned long hw_rate, bypass_rate;
442 struct dpll_data *
dd;
465 if (bypass_rate == rate &&
467 pr_debug(
"clock: %s: set rate: entering bypass.\n", clk->
name);
469 ret = _omap3_noncore_dpll_bypass(clk);
471 new_parent = dd->clk_bypass;
473 if (dd->last_rounded_rate != rate)
476 if (dd->last_rounded_rate == 0)
481 freqsel = _omap3_dpll_compute_freqsel(clk,
487 pr_debug(
"clock: %s: set rate: locking rate to %lu.\n",
490 ret = omap3_noncore_dpll_program(clk, dd->last_rounded_m,
491 dd->last_rounded_n, freqsel);
493 new_parent = dd->clk_ref;
527 const struct dpll_data *
dd;
530 if (!clk || !clk->dpll_data)
535 if (!dd->autoidle_reg)
539 v &= dd->autoidle_mask;
540 v >>=
__ffs(dd->autoidle_mask);
556 const struct dpll_data *
dd;
559 if (!clk || !clk->dpll_data)
564 if (!dd->autoidle_reg) {
565 pr_debug(
"clock: DPLL %s: autoidle not supported\n",
576 v &= ~dd->autoidle_mask;
590 const struct dpll_data *
dd;
593 if (!clk || !clk->dpll_data)
598 if (!dd->autoidle_reg) {
599 pr_debug(
"clock: DPLL %s: autoidle not supported\n",
605 v &= ~dd->autoidle_mask;
622 const struct dpll_data *
dd;
626 unsigned long parent_rate;
630 while (pclk && !pclk->dpll_data)
639 dd = pclk->dpll_data;
644 v =
__raw_readl(dd->control_reg) & dd->enable_mask;
645 v >>=
__ffs(dd->enable_mask);
649 rate = parent_rate * 2;