diff options
Diffstat (limited to 'drivers/clk/ti')
-rw-r--r-- | drivers/clk/ti/apll.c | 2 | ||||
-rw-r--r-- | drivers/clk/ti/clk-816x.c | 2 | ||||
-rw-r--r-- | drivers/clk/ti/clkt_dpll.c | 4 | ||||
-rw-r--r-- | drivers/clk/ti/divider.c | 16 | ||||
-rw-r--r-- | drivers/clk/ti/dpll3xxx.c | 25 | ||||
-rw-r--r-- | drivers/clk/ti/fapll.c | 4 | ||||
-rw-r--r-- | drivers/clk/ti/mux.c | 15 |
7 files changed, 37 insertions, 31 deletions
diff --git a/drivers/clk/ti/apll.c b/drivers/clk/ti/apll.c index f3eab6e79027..b336a8c11e2a 100644 --- a/drivers/clk/ti/apll.c +++ b/drivers/clk/ti/apll.c @@ -323,7 +323,7 @@ static void omap2_apll_deny_idle(struct clk_hw_omap *clk) omap2_apll_set_autoidle(clk, OMAP2_APLL_AUTOIDLE_DISABLE); } -static struct clk_hw_omap_ops omap2_apll_hwops = { +static const struct clk_hw_omap_ops omap2_apll_hwops = { .allow_idle = &omap2_apll_allow_idle, .deny_idle = &omap2_apll_deny_idle, }; diff --git a/drivers/clk/ti/clk-816x.c b/drivers/clk/ti/clk-816x.c index 1dfad0c712cd..2a5d84fdddc5 100644 --- a/drivers/clk/ti/clk-816x.c +++ b/drivers/clk/ti/clk-816x.c @@ -20,6 +20,8 @@ static struct ti_dt_clk dm816x_clks[] = { DT_CLK(NULL, "sys_clkin", "sys_clkin_ck"), DT_CLK(NULL, "timer_sys_ck", "sys_clkin_ck"), DT_CLK(NULL, "sys_32k_ck", "sys_32k_ck"), + DT_CLK(NULL, "timer_32k_ck", "sysclk18_ck"), + DT_CLK(NULL, "timer_ext_ck", "tclkin_ck"), DT_CLK(NULL, "mpu_ck", "mpu_ck"), DT_CLK(NULL, "timer1_fck", "timer1_fck"), DT_CLK(NULL, "timer2_fck", "timer2_fck"), diff --git a/drivers/clk/ti/clkt_dpll.c b/drivers/clk/ti/clkt_dpll.c index 9023ca9caf84..b5cc6f66ae5d 100644 --- a/drivers/clk/ti/clkt_dpll.c +++ b/drivers/clk/ti/clkt_dpll.c @@ -240,7 +240,7 @@ u8 omap2_init_dpll_parent(struct clk_hw *hw) */ unsigned long omap2_get_dpll_rate(struct clk_hw_omap *clk) { - long long dpll_clk; + u64 dpll_clk; u32 dpll_mult, dpll_div, v; struct dpll_data *dd; @@ -262,7 +262,7 @@ unsigned long omap2_get_dpll_rate(struct clk_hw_omap *clk) dpll_div = v & dd->div1_mask; dpll_div >>= __ffs(dd->div1_mask); - dpll_clk = (long long)clk_get_rate(dd->clk_ref) * dpll_mult; + dpll_clk = (u64)clk_get_rate(dd->clk_ref) * dpll_mult; do_div(dpll_clk, dpll_div + 1); return dpll_clk; diff --git a/drivers/clk/ti/divider.c b/drivers/clk/ti/divider.c index 5b1726829e6d..df2558350fc1 100644 --- a/drivers/clk/ti/divider.c +++ b/drivers/clk/ti/divider.c @@ -214,7 +214,6 @@ static int ti_clk_divider_set_rate(struct clk_hw *hw, unsigned long rate, { struct clk_divider *divider; unsigned int div, value; - unsigned long flags = 0; u32 val; if (!hw || !rate) @@ -228,9 +227,6 @@ static int ti_clk_divider_set_rate(struct clk_hw *hw, unsigned long rate, if (value > div_mask(divider)) value = div_mask(divider); - if (divider->lock) - spin_lock_irqsave(divider->lock, flags); - if (divider->flags & CLK_DIVIDER_HIWORD_MASK) { val = div_mask(divider) << (divider->shift + 16); } else { @@ -240,9 +236,6 @@ static int ti_clk_divider_set_rate(struct clk_hw *hw, unsigned long rate, val |= value << divider->shift; ti_clk_ll_ops->clk_writel(val, divider->reg); - if (divider->lock) - spin_unlock_irqrestore(divider->lock, flags); - return 0; } @@ -256,8 +249,7 @@ static struct clk *_register_divider(struct device *dev, const char *name, const char *parent_name, unsigned long flags, void __iomem *reg, u8 shift, u8 width, u8 clk_divider_flags, - const struct clk_div_table *table, - spinlock_t *lock) + const struct clk_div_table *table) { struct clk_divider *div; struct clk *clk; @@ -288,7 +280,6 @@ static struct clk *_register_divider(struct device *dev, const char *name, div->shift = shift; div->width = width; div->flags = clk_divider_flags; - div->lock = lock; div->hw.init = &init; div->table = table; @@ -421,7 +412,7 @@ struct clk *ti_clk_register_divider(struct ti_clk *setup) clk = _register_divider(NULL, setup->name, div->parent, flags, (void __iomem *)reg, div->bit_shift, - width, div_flags, table, NULL); + width, div_flags, table); if (IS_ERR(clk)) kfree(table); @@ -584,8 +575,7 @@ static void __init of_ti_divider_clk_setup(struct device_node *node) goto cleanup; clk = _register_divider(NULL, node->name, parent_name, flags, reg, - shift, width, clk_divider_flags, table, - NULL); + shift, width, clk_divider_flags, table); if (!IS_ERR(clk)) { of_clk_add_provider(node, of_clk_src_simple_get, clk); diff --git a/drivers/clk/ti/dpll3xxx.c b/drivers/clk/ti/dpll3xxx.c index f4dec00fb684..1c300388782b 100644 --- a/drivers/clk/ti/dpll3xxx.c +++ b/drivers/clk/ti/dpll3xxx.c @@ -305,8 +305,9 @@ static void _lookup_sddiv(struct clk_hw_omap *clk, u8 *sd_div, u16 m, u8 n) static int omap3_noncore_dpll_program(struct clk_hw_omap *clk, u16 freqsel) { struct dpll_data *dd = clk->dpll_data; - u8 dco, sd_div; + u8 dco, sd_div, ai = 0; u32 v; + bool errata_i810; /* 3430 ES2 TRM: 4.7.6.9 DPLL Programming Sequence */ _omap3_noncore_dpll_bypass(clk); @@ -350,6 +351,25 @@ static int omap3_noncore_dpll_program(struct clk_hw_omap *clk, u16 freqsel) v |= sd_div << __ffs(dd->sddiv_mask); } + /* + * Errata i810 - DPLL controller can get stuck while transitioning + * to a power saving state. Software must ensure the DPLL can not + * transition to a low power state while changing M/N values. + * Easiest way to accomplish this is to prevent DPLL autoidle + * before doing the M/N re-program. + */ + errata_i810 = ti_clk_get_features()->flags & TI_CLK_ERRATA_I810; + + if (errata_i810) { + ai = omap3_dpll_autoidle_read(clk); + if (ai) { + omap3_dpll_deny_idle(clk); + + /* OCP barrier */ + omap3_dpll_autoidle_read(clk); + } + } + ti_clk_ll_ops->clk_writel(v, dd->mult_div1_reg); /* Set 4X multiplier and low-power mode */ @@ -379,6 +399,9 @@ static int omap3_noncore_dpll_program(struct clk_hw_omap *clk, u16 freqsel) _omap3_noncore_dpll_lock(clk); + if (errata_i810 && ai) + omap3_dpll_allow_idle(clk); + return 0; } diff --git a/drivers/clk/ti/fapll.c b/drivers/clk/ti/fapll.c index f4b2e9888bdf..66a0d0ed8b55 100644 --- a/drivers/clk/ti/fapll.c +++ b/drivers/clk/ti/fapll.c @@ -168,7 +168,7 @@ static unsigned long ti_fapll_recalc_rate(struct clk_hw *hw, { struct fapll_data *fd = to_fapll(hw); u32 fapll_n, fapll_p, v; - long long rate; + u64 rate; if (ti_fapll_clock_is_bypass(fd)) return parent_rate; @@ -314,7 +314,7 @@ static unsigned long ti_fapll_synth_recalc_rate(struct clk_hw *hw, { struct fapll_synth *synth = to_synth(hw); u32 synth_div_m; - long long rate; + u64 rate; /* The audio_pll_clk1 is hardwired to produce 32.768KiHz clock */ if (!synth->div) diff --git a/drivers/clk/ti/mux.c b/drivers/clk/ti/mux.c index 69f08a1d047d..dab9ba88b9d6 100644 --- a/drivers/clk/ti/mux.c +++ b/drivers/clk/ti/mux.c @@ -69,7 +69,6 @@ static int ti_clk_mux_set_parent(struct clk_hw *hw, u8 index) { struct clk_mux *mux = to_clk_mux(hw); u32 val; - unsigned long flags = 0; if (mux->table) { index = mux->table[index]; @@ -81,9 +80,6 @@ static int ti_clk_mux_set_parent(struct clk_hw *hw, u8 index) index++; } - if (mux->lock) - spin_lock_irqsave(mux->lock, flags); - if (mux->flags & CLK_MUX_HIWORD_MASK) { val = mux->mask << (mux->shift + 16); } else { @@ -93,9 +89,6 @@ static int ti_clk_mux_set_parent(struct clk_hw *hw, u8 index) val |= index << mux->shift; ti_clk_ll_ops->clk_writel(val, mux->reg); - if (mux->lock) - spin_unlock_irqrestore(mux->lock, flags); - return 0; } @@ -109,7 +102,7 @@ static struct clk *_register_mux(struct device *dev, const char *name, const char **parent_names, u8 num_parents, unsigned long flags, void __iomem *reg, u8 shift, u32 mask, u8 clk_mux_flags, - u32 *table, spinlock_t *lock) + u32 *table) { struct clk_mux *mux; struct clk *clk; @@ -133,7 +126,6 @@ static struct clk *_register_mux(struct device *dev, const char *name, mux->shift = shift; mux->mask = mask; mux->flags = clk_mux_flags; - mux->lock = lock; mux->table = table; mux->hw.init = &init; @@ -175,7 +167,7 @@ struct clk *ti_clk_register_mux(struct ti_clk *setup) return _register_mux(NULL, setup->name, mux->parents, mux->num_parents, flags, (void __iomem *)reg, mux->bit_shift, mask, - mux_flags, NULL, NULL); + mux_flags, NULL); } /** @@ -227,8 +219,7 @@ static void of_mux_clk_setup(struct device_node *node) mask = (1 << fls(mask)) - 1; clk = _register_mux(NULL, node->name, parent_names, num_parents, - flags, reg, shift, mask, clk_mux_flags, NULL, - NULL); + flags, reg, shift, mask, clk_mux_flags, NULL); if (!IS_ERR(clk)) of_clk_add_provider(node, of_clk_src_simple_get, clk); |