diff options
Diffstat (limited to 'drivers/clk/mmp/clk-frac.c')
-rw-r--r-- | drivers/clk/mmp/clk-frac.c | 20 |
1 files changed, 12 insertions, 8 deletions
diff --git a/drivers/clk/mmp/clk-frac.c b/drivers/clk/mmp/clk-frac.c index 80c1dd15d15c..23a56f561812 100644 --- a/drivers/clk/mmp/clk-frac.c +++ b/drivers/clk/mmp/clk-frac.c @@ -40,15 +40,19 @@ static long clk_factor_round_rate(struct clk_hw *hw, unsigned long drate, for (i = 0; i < factor->ftbl_cnt; i++) { prev_rate = rate; - rate = (((*prate / 10000) * factor->ftbl[i].num) / - (factor->ftbl[i].den * factor->masks->factor)) * 10000; + rate = (((*prate / 10000) * factor->ftbl[i].den) / + (factor->ftbl[i].num * factor->masks->factor)) * 10000; if (rate > drate) break; } - if (i == 0) + if ((i == 0) || (i == factor->ftbl_cnt)) { return rate; - else - return prev_rate; + } else { + if ((drate - prev_rate) > (rate - drate)) + return rate; + else + return prev_rate; + } } static unsigned long clk_factor_recalc_rate(struct clk_hw *hw, @@ -64,7 +68,7 @@ static unsigned long clk_factor_recalc_rate(struct clk_hw *hw, num = (val >> masks->num_shift) & masks->num_mask; /* calculate denominator */ - den = (val >> masks->den_shift) & masks->num_mask; + den = (val >> masks->den_shift) & masks->den_mask; if (!den) return 0; @@ -85,8 +89,8 @@ static int clk_factor_set_rate(struct clk_hw *hw, unsigned long drate, for (i = 0; i < factor->ftbl_cnt; i++) { prev_rate = rate; - rate = (((prate / 10000) * factor->ftbl[i].num) / - (factor->ftbl[i].den * factor->masks->factor)) * 10000; + rate = (((prate / 10000) * factor->ftbl[i].den) / + (factor->ftbl[i].num * factor->masks->factor)) * 10000; if (rate > drate) break; } |