commit: 01f58153aefc158fd690b337d29ad140e963959d
From: Ryo Tsutsui <[email protected]>
Date: Sun, 3 Feb 2013 17:18:00 +0900
Subject: ASoC: arizona: Fixed a bug in FLL fractional calculation

Previously arizona_calc_fll() was checking if the target frequency is
exactly divisible by reference frequency, but should have been product
of the ratio and the reference frequency.

Also scale down the Lamba and Theta coefficients be under 16-bits in
order to match the registers.

Signed-off-by: Ryo Tsutsui <[email protected]>
Signed-off-by: Charles Keepax <[email protected]>
Signed-off-by: Mark Brown <[email protected]>
Cc: [email protected]
---
 sound/soc/codecs/arizona.c |   11 ++++++++++-
 1 file changed, 10 insertions(+), 1 deletion(-)

diff --git a/sound/soc/codecs/arizona.c b/sound/soc/codecs/arizona.c
index ef62c43..2899cb9 100644
--- a/sound/soc/codecs/arizona.c
+++ b/sound/soc/codecs/arizona.c
@@ -910,7 +910,7 @@ static int arizona_calc_fll(struct arizona_fll *fll,
 
        cfg->n = target / (ratio * Fref);
 
-       if (target % Fref) {
+       if (target % (ratio * Fref)) {
                gcd_fll = gcd(target, ratio * Fref);
                arizona_fll_dbg(fll, "GCD=%u\n", gcd_fll);
 
@@ -922,6 +922,15 @@ static int arizona_calc_fll(struct arizona_fll *fll,
                cfg->lambda = 0;
        }
 
+       /* Round down to 16bit range with cost of accuracy lost.
+        * Denominator must be bigger than numerator so we only
+        * take care of it.
+        */
+       while (cfg->lambda >= (1 << 16)) {
+               cfg->theta >>= 1;
+               cfg->lambda >>= 1;
+       }
+
        arizona_fll_dbg(fll, "N=%x THETA=%x LAMBDA=%x\n",
                        cfg->n, cfg->theta, cfg->lambda);
        arizona_fll_dbg(fll, "FRATIO=%x(%d) OUTDIV=%x REFCLK_DIV=%x\n",
-- 
1.7.10.4
--
To unsubscribe from this list: send the line "unsubscribe stable" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html

Reply via email to