Skip to content

Commit

Permalink
pwm: stm32: Calculate prescaler with a division instead of a loop
Browse files Browse the repository at this point in the history
Instead of looping over increasing values for the prescaler and testing
if it's big enough, calculate the value using a single division.

Link: https://lore.kernel.org/r/498a44b313a6c0a84ccddd03cd67aadaaaf7daf2.1710711976.git.u.kleine-koenig@pengutronix.de
Signed-off-by: Uwe Kleine-König <u.kleine-koenig@pengutronix.de>
  • Loading branch information
Uwe Kleine-König committed Apr 30, 2024
1 parent d44d635 commit 8002fbe
Showing 1 changed file with 17 additions and 13 deletions.
30 changes: 17 additions & 13 deletions drivers/pwm/pwm-stm32.c
Original file line number Diff line number Diff line change
Expand Up @@ -311,29 +311,33 @@ static int stm32_pwm_capture(struct pwm_chip *chip, struct pwm_device *pwm,
static int stm32_pwm_config(struct stm32_pwm *priv, unsigned int ch,
u64 duty_ns, u64 period_ns)
{
unsigned long long prd, div, dty;
unsigned int prescaler = 0;
unsigned long long prd, dty;
unsigned long long prescaler;
u32 ccmr, mask, shift;

/*
* .probe() asserted that clk_get_rate() is not bigger than 1 GHz, so
* this won't overflow.
* the calculations here won't overflow.
* First we need to find the minimal value for prescaler such that
*
* period_ns * clkrate
* ------------------------------
* NSEC_PER_SEC * (prescaler + 1)
*
* isn't bigger than max_arr.
*/
div = mul_u64_u64_div_u64(period_ns, clk_get_rate(priv->clk),
NSEC_PER_SEC);
prd = div;

while (div > priv->max_arr) {
prescaler++;
div = prd;
do_div(div, prescaler + 1);
}

prd = div;
prescaler = mul_u64_u64_div_u64(period_ns, clk_get_rate(priv->clk),
(u64)NSEC_PER_SEC * priv->max_arr);
if (prescaler > 0)
prescaler -= 1;

if (prescaler > MAX_TIM_PSC)
return -EINVAL;

prd = mul_u64_u64_div_u64(period_ns, clk_get_rate(priv->clk),
(u64)NSEC_PER_SEC * (prescaler + 1));

/*
* All channels share the same prescaler and counter so when two
* channels are active at the same time we can't change them
Expand Down

0 comments on commit 8002fbe

Please sign in to comment.