ASoC: tlv320aic32x4: Fix the divide by zero
The value of register(NDAC,MDAC,NADC,MADC,BCLKN) maybe zero lead to divide by zero in clk_aic32x4_div_recalc_rate().And the rate should be divide by 128 if the value was zero in this function according to the datasheet. Add the macro AIC32X4_DIV_MAX to present the 128 and return 0 if failing to read the value of register. Signed-off-by: Guiting Shen <aarongt.shen@gmail.com> Link: https://lore.kernel.org/r/20230813125520.11067-1-aarongt.shen@gmail.com Signed-off-by: Mark Brown <broonie@kernel.org>
This commit is contained in:
parent
b39eee2754
commit
11e756cc85
|
@ -321,7 +321,7 @@ static int clk_aic32x4_div_set_rate(struct clk_hw *hw, unsigned long rate,
|
|||
u8 divisor;
|
||||
|
||||
divisor = DIV_ROUND_UP(parent_rate, rate);
|
||||
if (divisor > 128)
|
||||
if (divisor > AIC32X4_DIV_MAX)
|
||||
return -EINVAL;
|
||||
|
||||
return regmap_update_bits(div->regmap, div->reg,
|
||||
|
@ -334,7 +334,7 @@ static int clk_aic32x4_div_determine_rate(struct clk_hw *hw,
|
|||
unsigned long divisor;
|
||||
|
||||
divisor = DIV_ROUND_UP(req->best_parent_rate, req->rate);
|
||||
if (divisor > 128)
|
||||
if (divisor > AIC32X4_DIV_MAX)
|
||||
return -EINVAL;
|
||||
|
||||
req->rate = DIV_ROUND_UP(req->best_parent_rate, divisor);
|
||||
|
@ -345,12 +345,18 @@ static unsigned long clk_aic32x4_div_recalc_rate(struct clk_hw *hw,
|
|||
unsigned long parent_rate)
|
||||
{
|
||||
struct clk_aic32x4 *div = to_clk_aic32x4(hw);
|
||||
|
||||
unsigned int val;
|
||||
int err;
|
||||
|
||||
regmap_read(div->regmap, div->reg, &val);
|
||||
err = regmap_read(div->regmap, div->reg, &val);
|
||||
if (err)
|
||||
return 0;
|
||||
|
||||
return DIV_ROUND_UP(parent_rate, val & AIC32X4_DIV_MASK);
|
||||
val &= AIC32X4_DIV_MASK;
|
||||
if (!val)
|
||||
val = AIC32X4_DIV_MAX;
|
||||
|
||||
return DIV_ROUND_UP(parent_rate, val);
|
||||
}
|
||||
|
||||
static const struct clk_ops aic32x4_div_ops = {
|
||||
|
|
|
@ -223,8 +223,9 @@ int aic32x4_register_clocks(struct device *dev, const char *mclk_name);
|
|||
#define AIC32X4_REFPOWERUP_120MS 0x07
|
||||
|
||||
/* Common mask and enable for all of the dividers */
|
||||
#define AIC32X4_DIVEN BIT(7)
|
||||
#define AIC32X4_DIV_MASK GENMASK(6, 0)
|
||||
#define AIC32X4_DIVEN BIT(7)
|
||||
#define AIC32X4_DIV_MASK GENMASK(6, 0)
|
||||
#define AIC32X4_DIV_MAX 128
|
||||
|
||||
/* Clock Limits */
|
||||
#define AIC32X4_MAX_DOSR_FREQ 6200000
|
||||
|
|
Loading…
Reference in New Issue