diff mbox

[3/3] ARM: OMAP3: fix dpll4_m3_ck and dpll4_m4_ck dividers

Message ID 1381324359-28825-3-git-send-email-tomi.valkeinen@ti.com (mailing list archive)
State New, archived
Headers show

Commit Message

Tomi Valkeinen Oct. 9, 2013, 1:12 p.m. UTC
dpll4_m3_ck and dpll4_m4_ck have divider bit fields which are 6 bits
wide. However, only values from 1 to 32 are allowed. This means we have
to add a divider tables and list the dividers explicitly.

I believe the same issue is there for other dpll4_mx_ck clocks, but as
I'm not familiar with them, I didn't touch them.

Signed-off-by: Tomi Valkeinen <tomi.valkeinen@ti.com>
---
 arch/arm/mach-omap2/cclock3xxx_data.c | 44 +++++++++++++++++++++++++++++++----
 1 file changed, 40 insertions(+), 4 deletions(-)

Comments

Tero Kristo Oct. 9, 2013, 1:22 p.m. UTC | #1
On 10/09/2013 04:12 PM, Tomi Valkeinen wrote:
> dpll4_m3_ck and dpll4_m4_ck have divider bit fields which are 6 bits
> wide. However, only values from 1 to 32 are allowed. This means we have
> to add a divider tables and list the dividers explicitly.
>
> I believe the same issue is there for other dpll4_mx_ck clocks, but as
> I'm not familiar with them, I didn't touch them.

I think you can limit the max value with a mask only, no need to define 
new tables.

Also similar comment regarding dts vs legacy clock data as for patch #1.

-Tero

>
> Signed-off-by: Tomi Valkeinen <tomi.valkeinen@ti.com>
> ---
>   arch/arm/mach-omap2/cclock3xxx_data.c | 44 +++++++++++++++++++++++++++++++----
>   1 file changed, 40 insertions(+), 4 deletions(-)
>
> diff --git a/arch/arm/mach-omap2/cclock3xxx_data.c b/arch/arm/mach-omap2/cclock3xxx_data.c
> index a51dd75..e94d635 100644
> --- a/arch/arm/mach-omap2/cclock3xxx_data.c
> +++ b/arch/arm/mach-omap2/cclock3xxx_data.c
> @@ -381,6 +381,42 @@ static struct clk_hw_omap dpll4_ck_hw = {
>
>   DEFINE_STRUCT_CLK(dpll4_ck, dpll3_ck_parent_names, dpll4_ck_ops);
>
> +static const struct clk_div_table dpll4_mx_ck_div_table[] = {
> +	{ .div = 1, .val = 1 },
> +	{ .div = 2, .val = 2 },
> +	{ .div = 3, .val = 3 },
> +	{ .div = 4, .val = 4 },
> +	{ .div = 5, .val = 5 },
> +	{ .div = 6, .val = 6 },
> +	{ .div = 7, .val = 7 },
> +	{ .div = 8, .val = 8 },
> +	{ .div = 9, .val = 9 },
> +	{ .div = 10, .val = 10 },
> +	{ .div = 11, .val = 11 },
> +	{ .div = 12, .val = 12 },
> +	{ .div = 13, .val = 13 },
> +	{ .div = 14, .val = 14 },
> +	{ .div = 15, .val = 15 },
> +	{ .div = 16, .val = 16 },
> +	{ .div = 17, .val = 17 },
> +	{ .div = 18, .val = 18 },
> +	{ .div = 19, .val = 19 },
> +	{ .div = 20, .val = 20 },
> +	{ .div = 21, .val = 21 },
> +	{ .div = 22, .val = 22 },
> +	{ .div = 23, .val = 23 },
> +	{ .div = 24, .val = 24 },
> +	{ .div = 25, .val = 25 },
> +	{ .div = 26, .val = 26 },
> +	{ .div = 27, .val = 27 },
> +	{ .div = 28, .val = 28 },
> +	{ .div = 29, .val = 29 },
> +	{ .div = 30, .val = 30 },
> +	{ .div = 31, .val = 31 },
> +	{ .div = 32, .val = 32 },
> +	{ .div = 0 },
> +};
> +
>   DEFINE_CLK_DIVIDER(dpll4_m5_ck, "dpll4_ck", &dpll4_ck, 0x0,
>   		   OMAP_CM_REGADDR(OMAP3430_CAM_MOD, CM_CLKSEL),
>   		   OMAP3430_CLKSEL_CAM_SHIFT, OMAP3630_CLKSEL_CAM_WIDTH,
> @@ -524,10 +560,10 @@ static const struct clksel_rate clkout2_src_54m_rates[] = {
>   	{ .div = 0 }
>   };
>
> -DEFINE_CLK_DIVIDER(dpll4_m3_ck, "dpll4_ck", &dpll4_ck, 0x0,
> +DEFINE_CLK_DIVIDER_TABLE(dpll4_m3_ck, "dpll4_ck", &dpll4_ck, 0x0,
>   		   OMAP_CM_REGADDR(OMAP3430_DSS_MOD, CM_CLKSEL),
>   		   OMAP3430_CLKSEL_TV_SHIFT, OMAP3630_CLKSEL_TV_WIDTH,
> -		   CLK_DIVIDER_ONE_BASED, NULL);
> +		   0, dpll4_mx_ck_div_table, NULL);
>
>   static struct clk dpll4_m3x2_ck;
>
> @@ -847,10 +883,10 @@ static struct clk dpll3_m3x2_ck_3630 = {
>
>   DEFINE_CLK_FIXED_FACTOR(dpll3_x2_ck, "dpll3_ck", &dpll3_ck, 0x0, 2, 1);
>
> -DEFINE_CLK_DIVIDER(dpll4_m4_ck, "dpll4_ck", &dpll4_ck, 0x0,
> +DEFINE_CLK_DIVIDER_TABLE(dpll4_m4_ck, "dpll4_ck", &dpll4_ck, 0x0,
>   		   OMAP_CM_REGADDR(OMAP3430_DSS_MOD, CM_CLKSEL),
>   		   OMAP3430_CLKSEL_DSS1_SHIFT, OMAP3630_CLKSEL_DSS1_WIDTH,
> -		   CLK_DIVIDER_ONE_BASED, NULL);
> +		   0, dpll4_mx_ck_div_table, NULL);
>
>   static struct clk dpll4_m4x2_ck;
>
>
Tomi Valkeinen Oct. 9, 2013, 1:33 p.m. UTC | #2
On 09/10/13 16:22, Tero Kristo wrote:
> On 10/09/2013 04:12 PM, Tomi Valkeinen wrote:
>> dpll4_m3_ck and dpll4_m4_ck have divider bit fields which are 6 bits
>> wide. However, only values from 1 to 32 are allowed. This means we have
>> to add a divider tables and list the dividers explicitly.
>>
>> I believe the same issue is there for other dpll4_mx_ck clocks, but as
>> I'm not familiar with them, I didn't touch them.
> 
> I think you can limit the max value with a mask only, no need to define
> new tables.

The bit field is 6 bits wide, so the mask is correct. It's just that the
biggest allowed value is 32, which takes 6 bits, not 63.

Changing the mask to 5 bits would limit the divider to 31, wouldn't it?

 Tomi
Tero Kristo Oct. 9, 2013, 1:43 p.m. UTC | #3
On 10/09/2013 04:33 PM, Tomi Valkeinen wrote:
> On 09/10/13 16:22, Tero Kristo wrote:
>> On 10/09/2013 04:12 PM, Tomi Valkeinen wrote:
>>> dpll4_m3_ck and dpll4_m4_ck have divider bit fields which are 6 bits
>>> wide. However, only values from 1 to 32 are allowed. This means we have
>>> to add a divider tables and list the dividers explicitly.
>>>
>>> I believe the same issue is there for other dpll4_mx_ck clocks, but as
>>> I'm not familiar with them, I didn't touch them.
>>
>> I think you can limit the max value with a mask only, no need to define
>> new tables.
>
> The bit field is 6 bits wide, so the mask is correct. It's just that the
> biggest allowed value is 32, which takes 6 bits, not 63.
>
> Changing the mask to 5 bits would limit the divider to 31, wouldn't it?

Oh true. Sucks with legacy clocks then.

For dt clocks, you should be able to declare max / min divider values 
for ti,divider-clock type which would take care of this case. Just 
change the ti,max-div = <63>; field to ... = <32>;

-Tero
Paul Walmsley Oct. 24, 2013, 3:14 p.m. UTC | #4
On Wed, 9 Oct 2013, Tomi Valkeinen wrote:

> dpll4_m3_ck and dpll4_m4_ck have divider bit fields which are 6 bits
> wide. However, only values from 1 to 32 are allowed. This means we have
> to add a divider tables and list the dividers explicitly.
> 
> I believe the same issue is there for other dpll4_mx_ck clocks, but as
> I'm not familiar with them, I didn't touch them.
> 
> Signed-off-by: Tomi Valkeinen <tomi.valkeinen@ti.com>

Thanks, queued.  Does anyone out there want to take care of patching the 
remaining DPLL output clocks that suffer from the same problem?


- Paul
diff mbox

Patch

diff --git a/arch/arm/mach-omap2/cclock3xxx_data.c b/arch/arm/mach-omap2/cclock3xxx_data.c
index a51dd75..e94d635 100644
--- a/arch/arm/mach-omap2/cclock3xxx_data.c
+++ b/arch/arm/mach-omap2/cclock3xxx_data.c
@@ -381,6 +381,42 @@  static struct clk_hw_omap dpll4_ck_hw = {
 
 DEFINE_STRUCT_CLK(dpll4_ck, dpll3_ck_parent_names, dpll4_ck_ops);
 
+static const struct clk_div_table dpll4_mx_ck_div_table[] = {
+	{ .div = 1, .val = 1 },
+	{ .div = 2, .val = 2 },
+	{ .div = 3, .val = 3 },
+	{ .div = 4, .val = 4 },
+	{ .div = 5, .val = 5 },
+	{ .div = 6, .val = 6 },
+	{ .div = 7, .val = 7 },
+	{ .div = 8, .val = 8 },
+	{ .div = 9, .val = 9 },
+	{ .div = 10, .val = 10 },
+	{ .div = 11, .val = 11 },
+	{ .div = 12, .val = 12 },
+	{ .div = 13, .val = 13 },
+	{ .div = 14, .val = 14 },
+	{ .div = 15, .val = 15 },
+	{ .div = 16, .val = 16 },
+	{ .div = 17, .val = 17 },
+	{ .div = 18, .val = 18 },
+	{ .div = 19, .val = 19 },
+	{ .div = 20, .val = 20 },
+	{ .div = 21, .val = 21 },
+	{ .div = 22, .val = 22 },
+	{ .div = 23, .val = 23 },
+	{ .div = 24, .val = 24 },
+	{ .div = 25, .val = 25 },
+	{ .div = 26, .val = 26 },
+	{ .div = 27, .val = 27 },
+	{ .div = 28, .val = 28 },
+	{ .div = 29, .val = 29 },
+	{ .div = 30, .val = 30 },
+	{ .div = 31, .val = 31 },
+	{ .div = 32, .val = 32 },
+	{ .div = 0 },
+};
+
 DEFINE_CLK_DIVIDER(dpll4_m5_ck, "dpll4_ck", &dpll4_ck, 0x0,
 		   OMAP_CM_REGADDR(OMAP3430_CAM_MOD, CM_CLKSEL),
 		   OMAP3430_CLKSEL_CAM_SHIFT, OMAP3630_CLKSEL_CAM_WIDTH,
@@ -524,10 +560,10 @@  static const struct clksel_rate clkout2_src_54m_rates[] = {
 	{ .div = 0 }
 };
 
-DEFINE_CLK_DIVIDER(dpll4_m3_ck, "dpll4_ck", &dpll4_ck, 0x0,
+DEFINE_CLK_DIVIDER_TABLE(dpll4_m3_ck, "dpll4_ck", &dpll4_ck, 0x0,
 		   OMAP_CM_REGADDR(OMAP3430_DSS_MOD, CM_CLKSEL),
 		   OMAP3430_CLKSEL_TV_SHIFT, OMAP3630_CLKSEL_TV_WIDTH,
-		   CLK_DIVIDER_ONE_BASED, NULL);
+		   0, dpll4_mx_ck_div_table, NULL);
 
 static struct clk dpll4_m3x2_ck;
 
@@ -847,10 +883,10 @@  static struct clk dpll3_m3x2_ck_3630 = {
 
 DEFINE_CLK_FIXED_FACTOR(dpll3_x2_ck, "dpll3_ck", &dpll3_ck, 0x0, 2, 1);
 
-DEFINE_CLK_DIVIDER(dpll4_m4_ck, "dpll4_ck", &dpll4_ck, 0x0,
+DEFINE_CLK_DIVIDER_TABLE(dpll4_m4_ck, "dpll4_ck", &dpll4_ck, 0x0,
 		   OMAP_CM_REGADDR(OMAP3430_DSS_MOD, CM_CLKSEL),
 		   OMAP3430_CLKSEL_DSS1_SHIFT, OMAP3630_CLKSEL_DSS1_WIDTH,
-		   CLK_DIVIDER_ONE_BASED, NULL);
+		   0, dpll4_mx_ck_div_table, NULL);
 
 static struct clk dpll4_m4x2_ck;