diff options
author | Mike Turquette <mturquette@linaro.org> | 2013-12-30 19:58:22 +0100 |
---|---|---|
committer | Mike Turquette <mturquette@linaro.org> | 2013-12-30 19:58:22 +0100 |
commit | 391e3903e63781debc52a0de73f2e922dcc3f602 (patch) | |
tree | 0f06e9555dc43090f265cbe726eb6051bf7a0d51 /drivers/clk | |
parent | Merge tag 'sunxi-clk-3.14-for-mike' of https://bitbucket.org/emiliolopez/linu... (diff) | |
parent | clk: keystone: gate: fix error handling on init (diff) | |
download | linux-391e3903e63781debc52a0de73f2e922dcc3f602.tar.xz linux-391e3903e63781debc52a0de73f2e922dcc3f602.zip |
Merge branch 'for_3.14/keystone-clk' of git://git.kernel.org/pub/scm/linux/kernel/git/ssantosh/linux-keystone into clk-next-keystone
Diffstat (limited to 'drivers/clk')
-rw-r--r-- | drivers/clk/keystone/gate.c | 12 | ||||
-rw-r--r-- | drivers/clk/keystone/pll.c | 24 |
2 files changed, 28 insertions, 8 deletions
diff --git a/drivers/clk/keystone/gate.c b/drivers/clk/keystone/gate.c index 1f333bcfc22e..17a598398a53 100644 --- a/drivers/clk/keystone/gate.c +++ b/drivers/clk/keystone/gate.c @@ -223,8 +223,7 @@ static void __init of_psc_clk_init(struct device_node *node, spinlock_t *lock) data->domain_base = of_iomap(node, i); if (!data->domain_base) { pr_err("%s: domain ioremap failed\n", __func__); - iounmap(data->control_base); - goto out; + goto unmap_ctrl; } of_property_read_u32(node, "domain-id", &data->domain_id); @@ -237,16 +236,21 @@ static void __init of_psc_clk_init(struct device_node *node, spinlock_t *lock) parent_name = of_clk_get_parent_name(node, 0); if (!parent_name) { pr_err("%s: Parent clock not found\n", __func__); - goto out; + goto unmap_domain; } clk = clk_register_psc(NULL, clk_name, parent_name, data, lock); - if (clk) { + if (!IS_ERR(clk)) { of_clk_add_provider(node, of_clk_src_simple_get, clk); return; } pr_err("%s: error registering clk %s\n", __func__, node->name); + +unmap_domain: + iounmap(data->domain_base); +unmap_ctrl: + iounmap(data->control_base); out: kfree(data); return; diff --git a/drivers/clk/keystone/pll.c b/drivers/clk/keystone/pll.c index 47a1bd9f1726..0dd8a4b12747 100644 --- a/drivers/clk/keystone/pll.c +++ b/drivers/clk/keystone/pll.c @@ -24,6 +24,8 @@ #define MAIN_PLLM_HIGH_MASK 0x7f000 #define PLLM_HIGH_SHIFT 6 #define PLLD_MASK 0x3f +#define CLKOD_MASK 0x780000 +#define CLKOD_SHIFT 19 /** * struct clk_pll_data - pll data structure @@ -41,7 +43,10 @@ * @pllm_upper_mask: multiplier upper mask * @pllm_upper_shift: multiplier upper shift * @plld_mask: divider mask - * @postdiv: Post divider + * @clkod_mask: output divider mask + * @clkod_shift: output divider shift + * @plld_mask: divider mask + * @postdiv: Fixed post divider */ struct clk_pll_data { bool has_pllctrl; @@ -53,6 +58,8 @@ struct clk_pll_data { u32 pllm_upper_mask; u32 pllm_upper_shift; u32 plld_mask; + u32 clkod_mask; + u32 clkod_shift; u32 postdiv; }; @@ -90,7 +97,13 @@ static unsigned long clk_pllclk_recalc(struct clk_hw *hw, mult |= ((val & pll_data->pllm_upper_mask) >> pll_data->pllm_upper_shift); prediv = (val & pll_data->plld_mask); - postdiv = pll_data->postdiv; + + if (!pll_data->has_pllctrl) + /* read post divider from od bits*/ + postdiv = ((val & pll_data->clkod_mask) >> + pll_data->clkod_shift) + 1; + else + postdiv = pll_data->postdiv; rate /= (prediv + 1); rate = (rate * (mult + 1)); @@ -155,8 +168,11 @@ static void __init _of_pll_clk_init(struct device_node *node, bool pllctrl) } parent_name = of_clk_get_parent_name(node, 0); - if (of_property_read_u32(node, "fixed-postdiv", &pll_data->postdiv)) - goto out; + if (of_property_read_u32(node, "fixed-postdiv", &pll_data->postdiv)) { + /* assume the PLL has output divider register bits */ + pll_data->clkod_mask = CLKOD_MASK; + pll_data->clkod_shift = CLKOD_SHIFT; + } i = of_property_match_string(node, "reg-names", "control"); pll_data->pll_ctl0 = of_iomap(node, i); |