All of lore.kernel.org
 help / color / mirror / Atom feed
From: <gregkh@linuxfoundation.org>
To: drivshin@allworx.com, aford173@gmail.com,
	gregkh@linuxfoundation.org, narmstrong@baylibre.com,
	thierry.reding@gmail.com
Cc: <stable@vger.kernel.org>, <stable-commits@vger.kernel.org>
Subject: Patch "pwm: omap-dmtimer: Fix inaccurate period and duty cycle calculations" has been added to the 4.5-stable tree
Date: Fri, 06 May 2016 12:30:44 -0400	[thread overview]
Message-ID: <1462552244248131@kroah.com> (raw)


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

    pwm: omap-dmtimer: Fix inaccurate period and duty cycle calculations

to the 4.5-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-omap-dmtimer-fix-inaccurate-period-and-duty-cycle-calculations.patch
and it can be found in the queue-4.5 subdirectory.

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


>From f8caa792261c0edded20eba2b8fcc899a1b91819 Mon Sep 17 00:00:00 2001
From: David Rivshin <drivshin@allworx.com>
Date: Fri, 29 Jan 2016 23:26:51 -0500
Subject: pwm: omap-dmtimer: Fix inaccurate period and duty cycle calculations

From: David Rivshin <drivshin@allworx.com>

commit f8caa792261c0edded20eba2b8fcc899a1b91819 upstream.

Fix the calculation of load_value and match_value. Currently they
are slightly too low, which produces a noticeably wrong PWM rate with
sufficiently short periods (i.e. when 1/period approaches clk_rate/2).

Example:
 clk_rate=32768Hz, period=122070ns, duty_cycle=61035ns (8192Hz/50% PWM)
 Correct values: load = 0xfffffffc, match = 0xfffffffd
 Current values: load = 0xfffffffa, match = 0xfffffffc
 effective PWM: period=183105ns, duty_cycle=91553ns (5461Hz/50% PWM)

Fixes: 6604c6556db9 ("pwm: Add PWM driver for OMAP using dual-mode timers")
Signed-off-by: David Rivshin <drivshin@allworx.com>
Acked-by: Neil Armstrong <narmstrong@baylibre.com>
Tested-by: Adam Ford <aford173@gmail.com>
Signed-off-by: Thierry Reding <thierry.reding@gmail.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>

---
 drivers/pwm/pwm-omap-dmtimer.c |   27 ++++++++++++++++++++-------
 1 file changed, 20 insertions(+), 7 deletions(-)

--- a/drivers/pwm/pwm-omap-dmtimer.c
+++ b/drivers/pwm/pwm-omap-dmtimer.c
@@ -31,6 +31,7 @@
 #include <linux/time.h>
 
 #define DM_TIMER_LOAD_MIN 0xfffffffe
+#define DM_TIMER_MAX      0xffffffff
 
 struct pwm_omap_dmtimer_chip {
 	struct pwm_chip chip;
@@ -46,13 +47,13 @@ to_pwm_omap_dmtimer_chip(struct pwm_chip
 	return container_of(chip, struct pwm_omap_dmtimer_chip, chip);
 }
 
-static int pwm_omap_dmtimer_calc_value(unsigned long clk_rate, int ns)
+static u32 pwm_omap_dmtimer_get_clock_cycles(unsigned long clk_rate, int ns)
 {
 	u64 c = (u64)clk_rate * ns;
 
 	do_div(c, NSEC_PER_SEC);
 
-	return DM_TIMER_LOAD_MIN - c;
+	return c;
 }
 
 static void pwm_omap_dmtimer_start(struct pwm_omap_dmtimer_chip *omap)
@@ -99,7 +100,8 @@ static int pwm_omap_dmtimer_config(struc
 				   int duty_ns, int period_ns)
 {
 	struct pwm_omap_dmtimer_chip *omap = to_pwm_omap_dmtimer_chip(chip);
-	int load_value, match_value;
+	u32 period_cycles, duty_cycles;
+	u32 load_value, match_value;
 	struct clk *fclk;
 	unsigned long clk_rate;
 	bool timer_active;
@@ -133,11 +135,22 @@ static int pwm_omap_dmtimer_config(struc
 	/*
 	 * Calculate the appropriate load and match values based on the
 	 * specified period and duty cycle. The load value determines the
-	 * cycle time and the match value determines the duty cycle.
+	 * period time and the match value determines the duty time.
+	 *
+	 * The period lasts for (DM_TIMER_MAX-load_value+1) clock cycles.
+	 * Similarly, the active time lasts (match_value-load_value+1) cycles.
+	 * The non-active time is the remainder: (DM_TIMER_MAX-match_value)
+	 * clock cycles.
+	 *
+	 * References:
+	 *   OMAP4430/60/70 TRM sections 22.2.4.10 and 22.2.4.11
+	 *   AM335x Sitara TRM sections 20.1.3.5 and 20.1.3.6
 	 */
-	load_value = pwm_omap_dmtimer_calc_value(clk_rate, period_ns);
-	match_value = pwm_omap_dmtimer_calc_value(clk_rate,
-						  period_ns - duty_ns);
+	period_cycles = pwm_omap_dmtimer_get_clock_cycles(clk_rate, period_ns);
+	duty_cycles = pwm_omap_dmtimer_get_clock_cycles(clk_rate, duty_ns);
+
+	load_value = (DM_TIMER_MAX - period_cycles) + 1;
+	match_value = load_value + duty_cycles - 1;
 
 	/*
 	 * We MUST stop the associated dual-mode timer before attempting to


Patches currently in stable-queue which might be from drivshin@allworx.com are

queue-4.5/pwm-omap-dmtimer-fix-inaccurate-period-and-duty-cycle-calculations.patch
queue-4.5/pwm-omap-dmtimer-add-sanity-checking-for-load-and-match-values.patch
queue-4.5/pwm-omap-dmtimer-round-load-and-match-values-rather-than-truncate.patch

                 reply	other threads:[~2016-05-06 17:31 UTC|newest]

Thread overview: [no followups] expand[flat|nested]  mbox.gz  Atom feed

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=1462552244248131@kroah.com \
    --to=gregkh@linuxfoundation.org \
    --cc=aford173@gmail.com \
    --cc=drivshin@allworx.com \
    --cc=narmstrong@baylibre.com \
    --cc=stable-commits@vger.kernel.org \
    --cc=stable@vger.kernel.org \
    --cc=thierry.reding@gmail.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.