Patch "pwm: lpss: Fix off by one error in base_unit math in pwm_lpss_prepare()" has been added to the 5.9-stable tree

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



This is a note to let you know that I've just added the patch titled

    pwm: lpss: Fix off by one error in base_unit math in pwm_lpss_prepare()

to the 5.9-stable tree which can be found at:
    http://www.kernel.org/git/?p=linux/kernel/git/stable/stable-queue.git;a=summary

The filename of the patch is:
     pwm-lpss-fix-off-by-one-error-in-base_unit-math-in-p.patch
and it can be found in the queue-5.9 subdirectory.

If you, or anyone else, feels it should not be added to the stable tree,
please let <stable@xxxxxxxxxxxxxxx> know about it.



commit 26aa648b7b9f48377f80cc5e7486e9d17f57287c
Author: Hans de Goede <hdegoede@xxxxxxxxxx>
Date:   Thu Sep 3 13:23:23 2020 +0200

    pwm: lpss: Fix off by one error in base_unit math in pwm_lpss_prepare()
    
    [ Upstream commit 181f4d2f44463fe09fe4df02e03095cb87151c29 ]
    
    According to the data-sheet the way the PWM controller works is that
    each input clock-cycle the base_unit gets added to a N bit counter and
    that counter overflowing determines the PWM output frequency.
    
    So assuming e.g. a 16 bit counter this means that if base_unit is set to 1,
    after 65535 input clock-cycles the counter has been increased from 0 to
    65535 and it will overflow on the next cycle, so it will overflow after
    every 65536 clock cycles and thus the calculations done in
    pwm_lpss_prepare() should use 65536 and not 65535.
    
    This commit fixes this. Note this also aligns the calculations in
    pwm_lpss_prepare() with those in pwm_lpss_get_state().
    
    Note this effectively reverts commit 684309e5043e ("pwm: lpss: Avoid
    potential overflow of base_unit"). The next patch in this series really
    fixes the potential overflow of the base_unit value.
    
    Fixes: 684309e5043e ("pwm: lpss: Avoid potential overflow of base_unit")
    Reviewed-by: Andy Shevchenko <andriy.shevchenko@xxxxxxxxxxxxxxx>
    Acked-by: Uwe Kleine-König <u.kleine-koenig@xxxxxxxxxxxxxx>
    Acked-by: Thierry Reding <thierry.reding@xxxxxxxxx>
    Signed-off-by: Hans de Goede <hdegoede@xxxxxxxxxx>
    Link: https://patchwork.freedesktop.org/patch/msgid/20200903112337.4113-4-hdegoede@xxxxxxxxxx
    Signed-off-by: Sasha Levin <sashal@xxxxxxxxxx>

diff --git a/drivers/pwm/pwm-lpss.c b/drivers/pwm/pwm-lpss.c
index 9d965ffe66d1e..43b1fc634af1a 100644
--- a/drivers/pwm/pwm-lpss.c
+++ b/drivers/pwm/pwm-lpss.c
@@ -93,7 +93,7 @@ static void pwm_lpss_prepare(struct pwm_lpss_chip *lpwm, struct pwm_device *pwm,
 	 * The equation is:
 	 * base_unit = round(base_unit_range * freq / c)
 	 */
-	base_unit_range = BIT(lpwm->info->base_unit_bits) - 1;
+	base_unit_range = BIT(lpwm->info->base_unit_bits);
 	freq *= base_unit_range;
 
 	base_unit = DIV_ROUND_CLOSEST_ULL(freq, c);
@@ -104,8 +104,8 @@ static void pwm_lpss_prepare(struct pwm_lpss_chip *lpwm, struct pwm_device *pwm,
 
 	orig_ctrl = ctrl = pwm_lpss_read(pwm);
 	ctrl &= ~PWM_ON_TIME_DIV_MASK;
-	ctrl &= ~(base_unit_range << PWM_BASE_UNIT_SHIFT);
-	base_unit &= base_unit_range;
+	ctrl &= ~((base_unit_range - 1) << PWM_BASE_UNIT_SHIFT);
+	base_unit &= (base_unit_range - 1);
 	ctrl |= (u32) base_unit << PWM_BASE_UNIT_SHIFT;
 	ctrl |= on_time_div;
 



[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Index of Archives]     [Linux USB Devel]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]

  Powered by Linux