Hi,Thank you for clarification.
On Tue, Jun 7, 2022 at 10:40 AM Vijaya Krishna Nivarthi
<quic_vnivarth@xxxxxxxxxxx> wrote:
Hi,I don't see why not. You're basically just getting a resulting clock
On 6/7/2022 1:29 AM, Doug Anderson wrote:
My only concern continues to be...
Given ser_clk is the final frequency that this function is going to
return and best_div is going to be the clk_divider, is it ok if the
divider cant divide the frequency exactly?
In other words, Can this function output combinations like (402,4)
(501,5) ?
If ok, then we can go ahead with this patch or even previous perhaps.
that's not an integral "Hz", right?
So if "baud" is 9600 and sampling_rate is 16 then desired_clk is (9600
* 16) = 153600
Let's imagine that we do all the math and we finally decide that our
best bet is with the rate 922000 and a divider of 6. That means that
the actual clock we'll make is 153666.67 when we _wanted_ 153600.
There's no reason it needs to be integral, though, and 153666.67 would
still be better than making 160000.
Ok, 2% seems good.Right, except that if you just pick the first clock you find it wouldpower?)Actually power saving was the anticipation behind returning first
frequency in original patch, when we cant find exact frequency.
be _wildly_ off. I guess if you really want to do this the right way,
you need to set a maximum tolerance and pick the first rate you find
that meets that tolerance. Random web search for "uart baud rate
tolerance" makes me believe that +/- 5% deviation is OK, but to be
safe you probably want something lower. Maybe 2%? So if the desired
clock is within 2% of a clock you can make, can you just pick that
one?
Ah, sorry. Not quite 1 line, but this (untested)Apologies, I could not figure out how.Please note that we go past cases when we have an divider that canAh, good point. Luckily that's a 1-line fix, right?
exactly divide the frequency(105/1, 204/2, 303/3) and end up with one
that doesn't.
freq = clk_round_rate(clk, mult);
if (freq % desired_clk == 0) {
ser_clk = freq;
best_div = freq / desired_clk;
break;
}
candidate_div = max(1, DIV_ROUND_CLOSEST(freq, desired_clk));
candidate_freq = freq / candidate_div;
diff = abs((long)desired_clk - candidate_freq);
if (diff < best_diff) {
best_diff = diff;
ser_clk = freq;
best_div = candidate_div;
}