* [PATCH v4 2/2] clk: bcm2835: Minimise clock jitter for PCM clock
@ 2017-06-01 14:14 Phil Elwell
2017-06-02 22:45 ` Stephen Boyd
0 siblings, 1 reply; 2+ messages in thread
From: Phil Elwell @ 2017-06-01 14:14 UTC (permalink / raw)
To: Michael Turquette, Stephen Boyd, Eric Anholt, Stefan Wahren,
Florian Fainelli, linux-clk, linux-rpi-kernel, linux-kernel
Fractional clock dividers generate accurate average frequencies but
with jitter, particularly when the integer divisor is small.
Introduce a new metric of clock accuracy to penalise clocks with a good
average but worse jitter compared to clocks with an average which is no
better but with lower jitter. The metric is the ideal rate minus the
worse deviation from that ideal using the nearest integer divisors.
Use this metric for parent selection for clocks requiring low jitter
(currently just PCM).
Signed-off-by: Phil Elwell <phil@raspberrypi.org>
Reviewed-by: Eric Anholt <eric@anholt.net>
Acked-by: Stefan Wahren <stefan.wahren@i2se.com>
---
drivers/clk/bcm/clk-bcm2835.c | 34 +++++++++++++++++++++++++++++-----
1 file changed, 29 insertions(+), 5 deletions(-)
diff --git a/drivers/clk/bcm/clk-bcm2835.c b/drivers/clk/bcm/clk-bcm2835.c
index 49867d2..0bc56a0 100644
--- a/drivers/clk/bcm/clk-bcm2835.c
+++ b/drivers/clk/bcm/clk-bcm2835.c
@@ -530,6 +530,7 @@ struct bcm2835_clock_data {
bool is_vpu_clock;
bool is_mash_clock;
+ bool low_jitter;
u32 tcnt_mux;
};
@@ -1124,7 +1125,8 @@ static unsigned long bcm2835_clock_choose_div_and_prate(struct clk_hw *hw,
int parent_idx,
unsigned long rate,
u32 *div,
- unsigned long *prate)
+ unsigned long *prate,
+ unsigned long *avgrate)
{
struct bcm2835_clock *clock = bcm2835_clock_from_hw(hw);
struct bcm2835_cprman *cprman = clock->cprman;
@@ -1139,8 +1141,25 @@ static unsigned long bcm2835_clock_choose_div_and_prate(struct clk_hw *hw,
*prate = clk_hw_get_rate(parent);
*div = bcm2835_clock_choose_div(hw, rate, *prate, true);
- return bcm2835_clock_rate_from_divisor(clock, *prate,
- *div);
+ *avgrate = bcm2835_clock_rate_from_divisor(clock, *prate, *div);
+
+ if (data->low_jitter && (*div & CM_DIV_FRAC_MASK)) {
+ unsigned long high, low;
+ u32 int_div = *div & ~CM_DIV_FRAC_MASK;
+
+ high = bcm2835_clock_rate_from_divisor(clock, *prate,
+ int_div);
+ int_div += CM_DIV_FRAC_MASK + 1;
+ low = bcm2835_clock_rate_from_divisor(clock, *prate,
+ int_div);
+
+ /*
+ * Return a value which is the maximum deviation
+ * below the ideal rate, for use as a metric.
+ */
+ return *avgrate - max(*avgrate - low, high - *avgrate);
+ }
+ return *avgrate;
}
if (data->frac_bits)
@@ -1167,6 +1186,7 @@ static unsigned long bcm2835_clock_choose_div_and_prate(struct clk_hw *hw,
*div = curdiv << CM_DIV_FRAC_BITS;
*prate = curdiv * best_rate;
+ *avgrate = best_rate;
return best_rate;
}
@@ -1178,6 +1198,7 @@ static int bcm2835_clock_determine_rate(struct clk_hw *hw,
bool current_parent_is_pllc;
unsigned long rate, best_rate = 0;
unsigned long prate, best_prate = 0;
+ unsigned long avgrate, best_avgrate = 0;
size_t i;
u32 div;
@@ -1202,11 +1223,13 @@ static int bcm2835_clock_determine_rate(struct clk_hw *hw,
continue;
rate = bcm2835_clock_choose_div_and_prate(hw, i, req->rate,
- &div, &prate);
+ &div, &prate,
+ &avgrate);
if (rate > best_rate && rate <= req->rate) {
best_parent = parent;
best_prate = prate;
best_rate = rate;
+ best_avgrate = avgrate;
}
}
@@ -1216,7 +1239,7 @@ static int bcm2835_clock_determine_rate(struct clk_hw *hw,
req->best_parent_hw = best_parent;
req->best_parent_rate = best_prate;
- req->rate = best_rate;
+ req->rate = best_avgrate;
return 0;
}
@@ -2025,6 +2048,7 @@ struct bcm2835_clk_desc {
.int_bits = 12,
.frac_bits = 12,
.is_mash_clock = true,
+ .low_jitter = true,
.tcnt_mux = 23),
[BCM2835_CLOCK_PWM] = REGISTER_PER_CLK(
.name = "pwm",
--
1.9.1
^ permalink raw reply related [flat|nested] 2+ messages in thread
* Re: [PATCH v4 2/2] clk: bcm2835: Minimise clock jitter for PCM clock
2017-06-01 14:14 [PATCH v4 2/2] clk: bcm2835: Minimise clock jitter for PCM clock Phil Elwell
@ 2017-06-02 22:45 ` Stephen Boyd
0 siblings, 0 replies; 2+ messages in thread
From: Stephen Boyd @ 2017-06-02 22:45 UTC (permalink / raw)
To: Phil Elwell
Cc: Michael Turquette, Eric Anholt, Stefan Wahren, Florian Fainelli,
linux-clk, linux-rpi-kernel, linux-kernel
On 06/01, Phil Elwell wrote:
> Fractional clock dividers generate accurate average frequencies but
> with jitter, particularly when the integer divisor is small.
>
> Introduce a new metric of clock accuracy to penalise clocks with a good
> average but worse jitter compared to clocks with an average which is no
> better but with lower jitter. The metric is the ideal rate minus the
> worse deviation from that ideal using the nearest integer divisors.
>
> Use this metric for parent selection for clocks requiring low jitter
> (currently just PCM).
>
> Signed-off-by: Phil Elwell <phil@raspberrypi.org>
> Reviewed-by: Eric Anholt <eric@anholt.net>
> Acked-by: Stefan Wahren <stefan.wahren@i2se.com>
> ---
Applied to clk-next
--
Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum,
a Linux Foundation Collaborative Project
^ permalink raw reply [flat|nested] 2+ messages in thread
end of thread, other threads:[~2017-06-02 22:45 UTC | newest]
Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2017-06-01 14:14 [PATCH v4 2/2] clk: bcm2835: Minimise clock jitter for PCM clock Phil Elwell
2017-06-02 22:45 ` Stephen Boyd
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).