Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

clk: keystone: use clkod register bits for postdiv

DDR3A/B, ARM and PA PLL controllers have clkod register bits for
configuring postdiv values. So use it instead of using fixed
post dividers for these pll controllers. Assume that if fixed-postdiv
attribute is not present, use clkod register value for pistdiv.

Also update the Documentation of bindings to reflect the same.

Cc: Mike Turquette <mturquette@linaro.org
Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
Signed-off-by: Santosh Shilimkar <santosh.shilimkar@ti.com>

authored by

Murali Karicheri and committed by
Santosh Shilimkar
dbb4e67f 6ce4eac1

+24 -8
+4 -4
Documentation/devicetree/bindings/clock/keystone-pll.txt
··· 17 17 - reg - pll control0 and pll multipler registers 18 18 - reg-names : control and multiplier. The multiplier is applicable only for 19 19 main pll clock 20 - - fixed-postdiv : fixed post divider value 20 + - fixed-postdiv : fixed post divider value. If absent, use clkod register bits 21 + for postdiv 21 22 22 23 Example: 23 24 mainpllclk: mainpllclk@2310110 { 24 25 #clock-cells = <0>; 25 26 compatible = "ti,keystone,main-pll-clock"; 26 - clocks = <&refclkmain>; 27 + clocks = <&refclksys>; 27 28 reg = <0x02620350 4>, <0x02310110 4>; 28 29 reg-names = "control", "multiplier"; 29 30 fixed-postdiv = <2>; ··· 33 32 papllclk: papllclk@2620358 { 34 33 #clock-cells = <0>; 35 34 compatible = "ti,keystone,pll-clock"; 36 - clocks = <&refclkmain>; 35 + clocks = <&refclkpass>; 37 36 clock-output-names = "pa-pll-clk"; 38 37 reg = <0x02620358 4>; 39 38 reg-names = "control"; 40 - fixed-postdiv = <6>; 41 39 }; 42 40 43 41 Required properties:
+20 -4
drivers/clk/keystone/pll.c
··· 24 24 #define MAIN_PLLM_HIGH_MASK 0x7f000 25 25 #define PLLM_HIGH_SHIFT 6 26 26 #define PLLD_MASK 0x3f 27 + #define CLKOD_MASK 0x780000 28 + #define CLKOD_SHIFT 19 27 29 28 30 /** 29 31 * struct clk_pll_data - pll data structure ··· 43 41 * @pllm_upper_mask: multiplier upper mask 44 42 * @pllm_upper_shift: multiplier upper shift 45 43 * @plld_mask: divider mask 46 - * @postdiv: Post divider 44 + * @clkod_mask: output divider mask 45 + * @clkod_shift: output divider shift 46 + * @plld_mask: divider mask 47 + * @postdiv: Fixed post divider 47 48 */ 48 49 struct clk_pll_data { 49 50 bool has_pllctrl; ··· 58 53 u32 pllm_upper_mask; 59 54 u32 pllm_upper_shift; 60 55 u32 plld_mask; 56 + u32 clkod_mask; 57 + u32 clkod_shift; 61 58 u32 postdiv; 62 59 }; 63 60 ··· 97 90 mult |= ((val & pll_data->pllm_upper_mask) 98 91 >> pll_data->pllm_upper_shift); 99 92 prediv = (val & pll_data->plld_mask); 100 - postdiv = pll_data->postdiv; 93 + 94 + if (!pll_data->has_pllctrl) 95 + /* read post divider from od bits*/ 96 + postdiv = ((val & pll_data->clkod_mask) >> 97 + pll_data->clkod_shift) + 1; 98 + else 99 + postdiv = pll_data->postdiv; 101 100 102 101 rate /= (prediv + 1); 103 102 rate = (rate * (mult + 1)); ··· 168 155 } 169 156 170 157 parent_name = of_clk_get_parent_name(node, 0); 171 - if (of_property_read_u32(node, "fixed-postdiv", &pll_data->postdiv)) 172 - goto out; 158 + if (of_property_read_u32(node, "fixed-postdiv", &pll_data->postdiv)) { 159 + /* assume the PLL has output divider register bits */ 160 + pll_data->clkod_mask = CLKOD_MASK; 161 + pll_data->clkod_shift = CLKOD_SHIFT; 162 + } 173 163 174 164 i = of_property_match_string(node, "reg-names", "control"); 175 165 pll_data->pll_ctl0 = of_iomap(node, i);