All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v4 0/2] pwm: Broadcom BCM7038 PWM controller (v4)
@ 2015-09-14 23:47 Florian Fainelli
  2015-09-14 23:47 ` [PATCH v4 1/2] Documentation: dt: add Broadcom BCM7038 PWM controller binding Florian Fainelli
                   ` (3 more replies)
  0 siblings, 4 replies; 13+ messages in thread
From: Florian Fainelli @ 2015-09-14 23:47 UTC (permalink / raw)
  To: linux-kernel
  Cc: Florian Fainelli, bcm-kernel-feedback-list, thierry.reding,
	devicetree, linux-pwm, ariel

Hi,

This patch series add PWM support for the Broadcom BCM7xxx
chips which feature one or more PWM controllers capable of
output periods from 148ns to ~622ms using a combination of
variable and fixed frequency settings.

The controller does not support setting a polarity.

This is based on Thierry's pwm/next branch.

Florian Fainelli (2):
  Documentation: dt: add Broadcom BCM7038 PWM controller binding
  pwm: Add Broadcom BCM7038 PWM controller support

 .../devicetree/bindings/pwm/brcm,bcm7038-pwm.txt   |  20 ++
 drivers/pwm/Kconfig                                |  10 +
 drivers/pwm/Makefile                               |   1 +
 drivers/pwm/pwm-brcmstb.c                          | 345 +++++++++++++++++++++
 4 files changed, 376 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/pwm/brcm,bcm7038-pwm.txt
 create mode 100644 drivers/pwm/pwm-brcmstb.c

-- 
2.1.0


^ permalink raw reply	[flat|nested] 13+ messages in thread

* [PATCH v4 1/2] Documentation: dt: add Broadcom BCM7038 PWM controller binding
  2015-09-14 23:47 [PATCH v4 0/2] pwm: Broadcom BCM7038 PWM controller (v4) Florian Fainelli
@ 2015-09-14 23:47 ` Florian Fainelli
  2015-09-14 23:47   ` Florian Fainelli
                   ` (2 subsequent siblings)
  3 siblings, 0 replies; 13+ messages in thread
From: Florian Fainelli @ 2015-09-14 23:47 UTC (permalink / raw)
  To: linux-kernel
  Cc: Florian Fainelli, bcm-kernel-feedback-list, thierry.reding,
	devicetree, linux-pwm, ariel

Add a binding documentation for the Broadcom BCM7038 PWM controller found in
BCM7xxx chips.

Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
---
Changes in v3:

- list 'clocks' property as mandatory

 .../devicetree/bindings/pwm/brcm,bcm7038-pwm.txt     | 20 ++++++++++++++++++++
 1 file changed, 20 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/pwm/brcm,bcm7038-pwm.txt

diff --git a/Documentation/devicetree/bindings/pwm/brcm,bcm7038-pwm.txt b/Documentation/devicetree/bindings/pwm/brcm,bcm7038-pwm.txt
new file mode 100644
index 000000000000..d9254a6da5ed
--- /dev/null
+++ b/Documentation/devicetree/bindings/pwm/brcm,bcm7038-pwm.txt
@@ -0,0 +1,20 @@
+Broadcom BCM7038 PWM controller (BCM7xxx Set Top Box PWM controller)
+
+Required properties:
+
+- compatible: must be "brcm,bcm7038-pwm"
+- reg: physical base address and length for this controller
+- #pwm-cells: should be 2. See pwm.txt in this directory for a description
+  of the cells format
+- clocks: a phandle to the reference clock for this block which is fed through
+  its internal variable clock frequency generator
+
+
+Example:
+
+	pwm: pwm@f0408000 {
+		compatible = "brcm,bcm7038-pwm";
+		reg = <0xf0408000 0x28>;
+		#pwm-cells = <2>;
+		clocks = <&upg_fixed>;
+	};
-- 
2.1.0


^ permalink raw reply related	[flat|nested] 13+ messages in thread

* [PATCH v4 2/2] pwm: Add Broadcom BCM7038 PWM controller support
@ 2015-09-14 23:47   ` Florian Fainelli
  0 siblings, 0 replies; 13+ messages in thread
From: Florian Fainelli @ 2015-09-14 23:47 UTC (permalink / raw)
  To: linux-kernel
  Cc: Florian Fainelli, bcm-kernel-feedback-list, thierry.reding,
	devicetree, linux-pwm, ariel

Add support for the BCM7038-style PWM controller found in all BCM7xxx STB SoCs.
This controller has a hardcoded 2 channels per controller, and cascades a
variable frequency generator on top of a fixed frequency generator which offers
a range of a 148ns period all the way to ~622ms periods.

Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
---
Changes in v4:

- address Ariel's feedback:
- add locking around HW manipulation registers
- rename I/O accessors to be less generic
- remove excessive parenthesis
- add proper error path cleanup code
- re-arrange remove function to call pwmchip_remove() first
- make the CWORD register offsets take a "ch" argument for consistency
- consistently use 'p' when referring to brcmstb_pwm_dev in code
- remove unecessary break lines

Changes in v3:

- make clock mandatory
- removed a remaining div64_u64 use

hanges in v2:

- properly format comments
- utilize do_div instead of div64_u64
- avoid using a "done" variable for the while loop
- utilize a parameterized register accessor
- remove a bunch of unnecessary assignments
- provide a module author
- update depends to build on BMIPS_GENERIC (the other user)
- removed artificial padding
- removed used only once variable: dn
- utilize devm_ioremap_resource
- do not print success message
- removed THIS_MODULE from platform_driver structure


 drivers/pwm/Kconfig       |  10 ++
 drivers/pwm/Makefile      |   1 +
 drivers/pwm/pwm-brcmstb.c | 345 ++++++++++++++++++++++++++++++++++++++++++++++
 3 files changed, 356 insertions(+)
 create mode 100644 drivers/pwm/pwm-brcmstb.c

diff --git a/drivers/pwm/Kconfig b/drivers/pwm/Kconfig
index ac8b0e968b6b..04d4817dda18 100644
--- a/drivers/pwm/Kconfig
+++ b/drivers/pwm/Kconfig
@@ -111,6 +111,16 @@ config PWM_CLPS711X
 	  To compile this driver as a module, choose M here: the module
 	  will be called pwm-clps711x.
 
+config PWM_BRCMSTB
+	tristate "Broadcom STB PWM support"
+	depends on ARCH_BRCMSTB || BMIPS_GENERIC
+	help
+	  Generic PWM framework driver for the Broadcom Set-top-Box
+	  SoCs (BCM7xxx).
+
+	  To compile this driver as a module, choose M Here: the module
+	  will be called pwm-brcmstb.c.
+
 config PWM_EP93XX
 	tristate "Cirrus Logic EP93xx PWM support"
 	depends on ARCH_EP93XX
diff --git a/drivers/pwm/Makefile b/drivers/pwm/Makefile
index cd9abef2d5b1..f03c0ed18d7a 100644
--- a/drivers/pwm/Makefile
+++ b/drivers/pwm/Makefile
@@ -7,6 +7,7 @@ obj-$(CONFIG_PWM_ATMEL_TCB)	+= pwm-atmel-tcb.o
 obj-$(CONFIG_PWM_BCM_KONA)	+= pwm-bcm-kona.o
 obj-$(CONFIG_PWM_BCM2835)	+= pwm-bcm2835.o
 obj-$(CONFIG_PWM_BFIN)		+= pwm-bfin.o
+obj-$(CONFIG_PWM_BRCMSTB)	+= pwm-brcmstb.o
 obj-$(CONFIG_PWM_CLPS711X)	+= pwm-clps711x.o
 obj-$(CONFIG_PWM_EP93XX)	+= pwm-ep93xx.o
 obj-$(CONFIG_PWM_FSL_FTM)	+= pwm-fsl-ftm.o
diff --git a/drivers/pwm/pwm-brcmstb.c b/drivers/pwm/pwm-brcmstb.c
new file mode 100644
index 000000000000..86ab6a5025a0
--- /dev/null
+++ b/drivers/pwm/pwm-brcmstb.c
@@ -0,0 +1,345 @@
+/*
+ * Broadcom BCM7038 PWM driver
+ * Author: Florian Fainelli
+ *
+ * Copyright (C) 2015 Broadcom Corporation
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ */
+
+#define pr_fmt(fmt)	KBUILD_MODNAME ": " fmt
+
+#include <linux/clk.h>
+#include <linux/export.h>
+#include <linux/init.h>
+#include <linux/io.h>
+#include <linux/kernel.h>
+#include <linux/module.h>
+#include <linux/of.h>
+#include <linux/platform_device.h>
+#include <linux/pwm.h>
+#include <linux/spinlock.h>
+
+#define PWM_CTRL		0x00
+#define  CTRL_START		BIT(0)
+#define  CTRL_OEB		BIT(1)
+#define  CTRL_FORCE_HIGH	BIT(2)
+#define  CTRL_OPENDRAIN		BIT(3)
+#define  CTRL_CHAN_OFFS		4
+
+#define PWM_CTRL2		0x04
+#define  CTRL2_OUT_SELECT	BIT(0)
+
+#define PWM_CH_SIZE		0x8
+
+#define PWM_CWORD_MSB(ch)	(0x08 + ((ch) * PWM_CH_SIZE))
+#define PWM_CWORD_LSB(ch)	(0x0C + ((ch) * PWM_CH_SIZE))
+
+/* Number of bits for the CWORD value */
+#define CWORD_BIT_SIZE		16
+
+/*
+ * Maximum control word value allowed when variable-frequency PWM is used as a
+ * clock for the constant-frequency PMW.
+ */
+#define CONST_VAR_F_MAX		32768
+#define CONST_VAR_F_MIN		1
+
+#define PWM_ON(ch)		(0x18 + ((ch) * PWM_CH_SIZE))
+#define  PWM_ON_MIN		1
+#define PWM_PERIOD(ch)		(0x1C + ((ch) * PWM_CH_SIZE))
+#define  PWM_PERIOD_MIN		0
+
+#define PWM_ON_PERIOD_MAX	0xff
+
+struct brcmstb_pwm_dev {
+	void __iomem *base;
+	spinlock_t lock;
+	struct clk *clk;
+	struct pwm_chip chip;
+};
+
+static inline u32 brcmstb_pwm_readl(struct brcmstb_pwm_dev *p, u32 off)
+{
+	if (IS_ENABLED(CONFIG_MIPS) && IS_ENABLED(CONFIG_CPU_BIG_ENDIAN))
+		return __raw_readl(p->base + off);
+	else
+		return readl_relaxed(p->base + off);
+}
+
+static inline void brcmstb_pwm_writel(struct brcmstb_pwm_dev *p,
+				      u32 val, u32 off)
+{
+	if (IS_ENABLED(CONFIG_MIPS) && IS_ENABLED(CONFIG_CPU_BIG_ENDIAN))
+		__raw_writel(val, p->base + off);
+	else
+		writel_relaxed(val, p->base + off);
+}
+
+static inline struct brcmstb_pwm_dev *to_brcmstb_pwm(struct pwm_chip *ch)
+{
+	return container_of(ch, struct brcmstb_pwm_dev, chip);
+}
+
+/*
+ * Fv is derived from the variable frequency output. The variable frequency
+ * output is configured using this formula:
+ *
+ * W = cword, if cword < 2 ^ 15 else 16-bit 2's complement of cword
+ *
+ * Fv = W x 2 ^ -16 x 27Mhz (reference clock)
+ *
+ * The period is: (period + 1) / Fv and "on" time is on / (period + 1)
+ *
+ * The PWM core framework specifies that the "duty_ns" parameter is in fact the
+ * "on" time, so this translates directly into our HW programming here.
+ */
+static int brcmstb_pwm_config(struct pwm_chip *chip, struct pwm_device *pwm,
+			      int duty_ns, int period_ns)
+{
+	struct brcmstb_pwm_dev *p = to_brcmstb_pwm(chip);
+	unsigned long pc, dc, cword = CONST_VAR_F_MAX;
+	unsigned int ch = pwm->hwpwm;
+	u64 val, rate;
+	u32 reg;
+
+	/*
+	 * If asking for a duty_ns equal to period_ns, we need to substract
+	 * the period value by 1 to make it shorter than the "on" time and
+	 * produce a flat 100% duty cycle signal, and max out the "on" time
+	 */
+	if (duty_ns == period_ns) {
+		dc = PWM_ON_PERIOD_MAX;
+		pc = PWM_ON_PERIOD_MAX - 1;
+		goto done;
+	}
+
+	while (1) {
+		/*
+		 * Calculate the base rate from base frequency and current
+		 * cword
+		 */
+		rate = (u64)clk_get_rate(p->clk) * (u64)cword;
+		do_div(rate, 1 << CWORD_BIT_SIZE);
+
+		val = period_ns * rate;
+		do_div(val, NSEC_PER_SEC);
+		pc = val;
+
+		val = (duty_ns + 1) * rate;
+		do_div(val, NSEC_PER_SEC);
+		dc = val;
+
+		/*
+		 * We can be called with separate duty and period updates,
+		 * so do not reject dc == 0 right away
+		 */
+		if (pc == PWM_PERIOD_MIN || (dc < PWM_ON_MIN && duty_ns))
+			return -EINVAL;
+
+		/* We converged on a calculation */
+		if (pc <= PWM_ON_PERIOD_MAX && dc <= PWM_ON_PERIOD_MAX)
+			break;
+
+		/*
+		 * The cword needs to be a power of 2 for the variable
+		 * frequency generator to output a 50% duty cycle variable
+		 * frequency which is used as input clock to the fixed
+		 * frequency generator.
+		 */
+		cword >>= 1;
+
+		/*
+		 * Desired periods are too large, we do not have a divider
+		 * for them
+		 */
+		if (cword < CONST_VAR_F_MIN)
+			return -EINVAL;
+	}
+
+done:
+	/*
+	 * Configure the defined "cword" value to have the variable frequency
+	 * generator output a base frequency for the constant frequency
+	 * generator to derive from.
+	 */
+	spin_lock(&p->lock);
+	brcmstb_pwm_writel(p, cword >> 8, PWM_CWORD_MSB(ch));
+	brcmstb_pwm_writel(p, cword & 0xff, PWM_CWORD_LSB(ch));
+
+	/* Select constant frequency signal output */
+	reg = brcmstb_pwm_readl(p, PWM_CTRL2);
+	reg |= CTRL2_OUT_SELECT << (ch * CTRL_CHAN_OFFS);
+	brcmstb_pwm_writel(p, reg, PWM_CTRL2);
+
+	/* Configure on and period value */
+	brcmstb_pwm_writel(p, pc, PWM_PERIOD(ch));
+	brcmstb_pwm_writel(p, dc, PWM_ON(ch));
+	spin_unlock(&p->lock);
+
+	return 0;
+}
+
+static inline void brcmstb_pwm_enable_set(struct brcmstb_pwm_dev *p,
+					  unsigned int ch, bool enable)
+{
+	unsigned int ofs = ch * CTRL_CHAN_OFFS;
+	u32 reg;
+
+	spin_lock(&p->lock);
+	reg = brcmstb_pwm_readl(p, PWM_CTRL);
+	if (enable) {
+		reg &= ~(CTRL_OEB << ofs);
+		reg |= (CTRL_START | CTRL_OPENDRAIN) << ofs;
+	} else {
+		reg &= ~((CTRL_START | CTRL_OPENDRAIN) << ofs);
+		reg |= CTRL_OEB << ofs;
+	}
+	brcmstb_pwm_writel(p, reg, PWM_CTRL);
+	spin_unlock(&p->lock);
+}
+
+static int brcmstb_pwm_enable(struct pwm_chip *chip, struct pwm_device *pwm)
+{
+	struct brcmstb_pwm_dev *p = to_brcmstb_pwm(chip);
+
+	brcmstb_pwm_enable_set(p, pwm->hwpwm, true);
+
+	return 0;
+}
+
+static void brcmstb_pwm_disable(struct pwm_chip *chip, struct pwm_device *pwm)
+{
+	struct brcmstb_pwm_dev *p = to_brcmstb_pwm(chip);
+
+	brcmstb_pwm_enable_set(p, pwm->hwpwm, false);
+}
+
+static const struct pwm_ops brcmstb_pwm_ops = {
+	.config	= brcmstb_pwm_config,
+	.enable	= brcmstb_pwm_enable,
+	.disable = brcmstb_pwm_disable,
+	.owner = THIS_MODULE,
+};
+
+static const struct of_device_id brcmstb_pwm_of_match[] = {
+	{ .compatible = "brcm,bcm7038-pwm", },
+	{ /* sentinel */ }
+};
+
+static int brcmstb_pwm_probe(struct platform_device *pdev)
+{
+	struct brcmstb_pwm_dev *p;
+	struct resource *r;
+	int ret;
+
+	p = devm_kzalloc(&pdev->dev, sizeof(*p), GFP_KERNEL);
+	if (!p)
+		return -ENOMEM;
+
+	spin_lock_init(&p->lock);
+
+	/*
+	 * Try to grab the clock and its rate, if not available, default
+	 * to the base 27Mhz clock domain this block comes from.
+	 */
+	p->clk = devm_clk_get(&pdev->dev, NULL);
+	if (IS_ERR(p->clk)) {
+		dev_err(&pdev->dev, "fail to obtain clock\n");
+		return PTR_ERR(p->clk);
+	}
+
+	clk_prepare_enable(p->clk);
+
+	platform_set_drvdata(pdev, p);
+
+	p->chip.dev = &pdev->dev;
+	p->chip.ops = &brcmstb_pwm_ops;
+	/* Dynamically assign a PWM base */
+	p->chip.base = -1;
+	/* Static number of PWM channels for this controller */
+	p->chip.npwm = 2;
+	p->chip.can_sleep = true;
+
+	r = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+	p->base = devm_ioremap_resource(&pdev->dev, r);
+	if (!p->base) {
+		ret = -ENOMEM;
+		goto out_clk;
+	}
+
+	ret = pwmchip_add(&p->chip);
+	if (ret) {
+		dev_err(&pdev->dev, "failed to add PWM chip %d\n", ret);
+		goto out_clk;
+	}
+
+	return ret;
+
+out_clk:
+	clk_disable_unprepare(p->clk);
+	return ret;
+}
+
+static int brcmstb_pwm_remove(struct platform_device *pdev)
+{
+	struct brcmstb_pwm_dev *p = platform_get_drvdata(pdev);
+	int ret;
+
+	ret = pwmchip_remove(&p->chip);
+	if (ret)
+		return ret;
+
+	clk_disable_unprepare(p->clk);
+
+	return 0;
+}
+
+#ifdef CONFIG_PM_SLEEP
+static int brcmstb_pwm_suspend(struct device *d)
+{
+	struct platform_device *pdev = to_platform_device(d);
+	struct brcmstb_pwm_dev *p = platform_get_drvdata(pdev);
+
+	clk_disable(p->clk);
+
+	return 0;
+}
+
+static int brcmstb_pwm_resume(struct device *d)
+{
+	struct platform_device *pdev = to_platform_device(d);
+	struct brcmstb_pwm_dev *p = platform_get_drvdata(pdev);
+
+	clk_enable(p->clk);
+
+	return 0;
+}
+#endif
+
+static SIMPLE_DEV_PM_OPS(brcmstb_pwm_pm_ops,
+			 brcmstb_pwm_suspend, brcmstb_pwm_resume);
+
+static struct platform_driver brcmstb_pwm_driver = {
+	.probe	= brcmstb_pwm_probe,
+	.remove	= brcmstb_pwm_remove,
+	.driver	= {
+		.name = "pwm-brcmstb",
+		.of_match_table = brcmstb_pwm_of_match,
+		.pm = &brcmstb_pwm_pm_ops,
+	},
+};
+module_platform_driver(brcmstb_pwm_driver);
+
+MODULE_AUTHOR("Florian Fainelli <f.fainelli@gmail.com>");
+MODULE_DESCRIPTION("Broadcom STB PWM driver");
+MODULE_ALIAS("platform:pwm-brcmstb");
+MODULE_LICENSE("GPL");
-- 
2.1.0


^ permalink raw reply related	[flat|nested] 13+ messages in thread

* [PATCH v4 2/2] pwm: Add Broadcom BCM7038 PWM controller support
@ 2015-09-14 23:47   ` Florian Fainelli
  0 siblings, 0 replies; 13+ messages in thread
From: Florian Fainelli @ 2015-09-14 23:47 UTC (permalink / raw)
  To: linux-kernel-u79uwXL29TY76Z2rM5mHXA
  Cc: Florian Fainelli,
	bcm-kernel-feedback-list-dY08KVG/lbpWk0Htik3J/w,
	thierry.reding-Re5JQEeQqe8AvxtiuMwx3w,
	devicetree-u79uwXL29TY76Z2rM5mHXA,
	linux-pwm-u79uwXL29TY76Z2rM5mHXA,
	ariel-30ULvvUtt6G51wMPkGsGjgyUoB5FGQPZ

Add support for the BCM7038-style PWM controller found in all BCM7xxx STB SoCs.
This controller has a hardcoded 2 channels per controller, and cascades a
variable frequency generator on top of a fixed frequency generator which offers
a range of a 148ns period all the way to ~622ms periods.

Signed-off-by: Florian Fainelli <f.fainelli-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org>
---
Changes in v4:

- address Ariel's feedback:
- add locking around HW manipulation registers
- rename I/O accessors to be less generic
- remove excessive parenthesis
- add proper error path cleanup code
- re-arrange remove function to call pwmchip_remove() first
- make the CWORD register offsets take a "ch" argument for consistency
- consistently use 'p' when referring to brcmstb_pwm_dev in code
- remove unecessary break lines

Changes in v3:

- make clock mandatory
- removed a remaining div64_u64 use

hanges in v2:

- properly format comments
- utilize do_div instead of div64_u64
- avoid using a "done" variable for the while loop
- utilize a parameterized register accessor
- remove a bunch of unnecessary assignments
- provide a module author
- update depends to build on BMIPS_GENERIC (the other user)
- removed artificial padding
- removed used only once variable: dn
- utilize devm_ioremap_resource
- do not print success message
- removed THIS_MODULE from platform_driver structure


 drivers/pwm/Kconfig       |  10 ++
 drivers/pwm/Makefile      |   1 +
 drivers/pwm/pwm-brcmstb.c | 345 ++++++++++++++++++++++++++++++++++++++++++++++
 3 files changed, 356 insertions(+)
 create mode 100644 drivers/pwm/pwm-brcmstb.c

diff --git a/drivers/pwm/Kconfig b/drivers/pwm/Kconfig
index ac8b0e968b6b..04d4817dda18 100644
--- a/drivers/pwm/Kconfig
+++ b/drivers/pwm/Kconfig
@@ -111,6 +111,16 @@ config PWM_CLPS711X
 	  To compile this driver as a module, choose M here: the module
 	  will be called pwm-clps711x.
 
+config PWM_BRCMSTB
+	tristate "Broadcom STB PWM support"
+	depends on ARCH_BRCMSTB || BMIPS_GENERIC
+	help
+	  Generic PWM framework driver for the Broadcom Set-top-Box
+	  SoCs (BCM7xxx).
+
+	  To compile this driver as a module, choose M Here: the module
+	  will be called pwm-brcmstb.c.
+
 config PWM_EP93XX
 	tristate "Cirrus Logic EP93xx PWM support"
 	depends on ARCH_EP93XX
diff --git a/drivers/pwm/Makefile b/drivers/pwm/Makefile
index cd9abef2d5b1..f03c0ed18d7a 100644
--- a/drivers/pwm/Makefile
+++ b/drivers/pwm/Makefile
@@ -7,6 +7,7 @@ obj-$(CONFIG_PWM_ATMEL_TCB)	+= pwm-atmel-tcb.o
 obj-$(CONFIG_PWM_BCM_KONA)	+= pwm-bcm-kona.o
 obj-$(CONFIG_PWM_BCM2835)	+= pwm-bcm2835.o
 obj-$(CONFIG_PWM_BFIN)		+= pwm-bfin.o
+obj-$(CONFIG_PWM_BRCMSTB)	+= pwm-brcmstb.o
 obj-$(CONFIG_PWM_CLPS711X)	+= pwm-clps711x.o
 obj-$(CONFIG_PWM_EP93XX)	+= pwm-ep93xx.o
 obj-$(CONFIG_PWM_FSL_FTM)	+= pwm-fsl-ftm.o
diff --git a/drivers/pwm/pwm-brcmstb.c b/drivers/pwm/pwm-brcmstb.c
new file mode 100644
index 000000000000..86ab6a5025a0
--- /dev/null
+++ b/drivers/pwm/pwm-brcmstb.c
@@ -0,0 +1,345 @@
+/*
+ * Broadcom BCM7038 PWM driver
+ * Author: Florian Fainelli
+ *
+ * Copyright (C) 2015 Broadcom Corporation
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ */
+
+#define pr_fmt(fmt)	KBUILD_MODNAME ": " fmt
+
+#include <linux/clk.h>
+#include <linux/export.h>
+#include <linux/init.h>
+#include <linux/io.h>
+#include <linux/kernel.h>
+#include <linux/module.h>
+#include <linux/of.h>
+#include <linux/platform_device.h>
+#include <linux/pwm.h>
+#include <linux/spinlock.h>
+
+#define PWM_CTRL		0x00
+#define  CTRL_START		BIT(0)
+#define  CTRL_OEB		BIT(1)
+#define  CTRL_FORCE_HIGH	BIT(2)
+#define  CTRL_OPENDRAIN		BIT(3)
+#define  CTRL_CHAN_OFFS		4
+
+#define PWM_CTRL2		0x04
+#define  CTRL2_OUT_SELECT	BIT(0)
+
+#define PWM_CH_SIZE		0x8
+
+#define PWM_CWORD_MSB(ch)	(0x08 + ((ch) * PWM_CH_SIZE))
+#define PWM_CWORD_LSB(ch)	(0x0C + ((ch) * PWM_CH_SIZE))
+
+/* Number of bits for the CWORD value */
+#define CWORD_BIT_SIZE		16
+
+/*
+ * Maximum control word value allowed when variable-frequency PWM is used as a
+ * clock for the constant-frequency PMW.
+ */
+#define CONST_VAR_F_MAX		32768
+#define CONST_VAR_F_MIN		1
+
+#define PWM_ON(ch)		(0x18 + ((ch) * PWM_CH_SIZE))
+#define  PWM_ON_MIN		1
+#define PWM_PERIOD(ch)		(0x1C + ((ch) * PWM_CH_SIZE))
+#define  PWM_PERIOD_MIN		0
+
+#define PWM_ON_PERIOD_MAX	0xff
+
+struct brcmstb_pwm_dev {
+	void __iomem *base;
+	spinlock_t lock;
+	struct clk *clk;
+	struct pwm_chip chip;
+};
+
+static inline u32 brcmstb_pwm_readl(struct brcmstb_pwm_dev *p, u32 off)
+{
+	if (IS_ENABLED(CONFIG_MIPS) && IS_ENABLED(CONFIG_CPU_BIG_ENDIAN))
+		return __raw_readl(p->base + off);
+	else
+		return readl_relaxed(p->base + off);
+}
+
+static inline void brcmstb_pwm_writel(struct brcmstb_pwm_dev *p,
+				      u32 val, u32 off)
+{
+	if (IS_ENABLED(CONFIG_MIPS) && IS_ENABLED(CONFIG_CPU_BIG_ENDIAN))
+		__raw_writel(val, p->base + off);
+	else
+		writel_relaxed(val, p->base + off);
+}
+
+static inline struct brcmstb_pwm_dev *to_brcmstb_pwm(struct pwm_chip *ch)
+{
+	return container_of(ch, struct brcmstb_pwm_dev, chip);
+}
+
+/*
+ * Fv is derived from the variable frequency output. The variable frequency
+ * output is configured using this formula:
+ *
+ * W = cword, if cword < 2 ^ 15 else 16-bit 2's complement of cword
+ *
+ * Fv = W x 2 ^ -16 x 27Mhz (reference clock)
+ *
+ * The period is: (period + 1) / Fv and "on" time is on / (period + 1)
+ *
+ * The PWM core framework specifies that the "duty_ns" parameter is in fact the
+ * "on" time, so this translates directly into our HW programming here.
+ */
+static int brcmstb_pwm_config(struct pwm_chip *chip, struct pwm_device *pwm,
+			      int duty_ns, int period_ns)
+{
+	struct brcmstb_pwm_dev *p = to_brcmstb_pwm(chip);
+	unsigned long pc, dc, cword = CONST_VAR_F_MAX;
+	unsigned int ch = pwm->hwpwm;
+	u64 val, rate;
+	u32 reg;
+
+	/*
+	 * If asking for a duty_ns equal to period_ns, we need to substract
+	 * the period value by 1 to make it shorter than the "on" time and
+	 * produce a flat 100% duty cycle signal, and max out the "on" time
+	 */
+	if (duty_ns == period_ns) {
+		dc = PWM_ON_PERIOD_MAX;
+		pc = PWM_ON_PERIOD_MAX - 1;
+		goto done;
+	}
+
+	while (1) {
+		/*
+		 * Calculate the base rate from base frequency and current
+		 * cword
+		 */
+		rate = (u64)clk_get_rate(p->clk) * (u64)cword;
+		do_div(rate, 1 << CWORD_BIT_SIZE);
+
+		val = period_ns * rate;
+		do_div(val, NSEC_PER_SEC);
+		pc = val;
+
+		val = (duty_ns + 1) * rate;
+		do_div(val, NSEC_PER_SEC);
+		dc = val;
+
+		/*
+		 * We can be called with separate duty and period updates,
+		 * so do not reject dc == 0 right away
+		 */
+		if (pc == PWM_PERIOD_MIN || (dc < PWM_ON_MIN && duty_ns))
+			return -EINVAL;
+
+		/* We converged on a calculation */
+		if (pc <= PWM_ON_PERIOD_MAX && dc <= PWM_ON_PERIOD_MAX)
+			break;
+
+		/*
+		 * The cword needs to be a power of 2 for the variable
+		 * frequency generator to output a 50% duty cycle variable
+		 * frequency which is used as input clock to the fixed
+		 * frequency generator.
+		 */
+		cword >>= 1;
+
+		/*
+		 * Desired periods are too large, we do not have a divider
+		 * for them
+		 */
+		if (cword < CONST_VAR_F_MIN)
+			return -EINVAL;
+	}
+
+done:
+	/*
+	 * Configure the defined "cword" value to have the variable frequency
+	 * generator output a base frequency for the constant frequency
+	 * generator to derive from.
+	 */
+	spin_lock(&p->lock);
+	brcmstb_pwm_writel(p, cword >> 8, PWM_CWORD_MSB(ch));
+	brcmstb_pwm_writel(p, cword & 0xff, PWM_CWORD_LSB(ch));
+
+	/* Select constant frequency signal output */
+	reg = brcmstb_pwm_readl(p, PWM_CTRL2);
+	reg |= CTRL2_OUT_SELECT << (ch * CTRL_CHAN_OFFS);
+	brcmstb_pwm_writel(p, reg, PWM_CTRL2);
+
+	/* Configure on and period value */
+	brcmstb_pwm_writel(p, pc, PWM_PERIOD(ch));
+	brcmstb_pwm_writel(p, dc, PWM_ON(ch));
+	spin_unlock(&p->lock);
+
+	return 0;
+}
+
+static inline void brcmstb_pwm_enable_set(struct brcmstb_pwm_dev *p,
+					  unsigned int ch, bool enable)
+{
+	unsigned int ofs = ch * CTRL_CHAN_OFFS;
+	u32 reg;
+
+	spin_lock(&p->lock);
+	reg = brcmstb_pwm_readl(p, PWM_CTRL);
+	if (enable) {
+		reg &= ~(CTRL_OEB << ofs);
+		reg |= (CTRL_START | CTRL_OPENDRAIN) << ofs;
+	} else {
+		reg &= ~((CTRL_START | CTRL_OPENDRAIN) << ofs);
+		reg |= CTRL_OEB << ofs;
+	}
+	brcmstb_pwm_writel(p, reg, PWM_CTRL);
+	spin_unlock(&p->lock);
+}
+
+static int brcmstb_pwm_enable(struct pwm_chip *chip, struct pwm_device *pwm)
+{
+	struct brcmstb_pwm_dev *p = to_brcmstb_pwm(chip);
+
+	brcmstb_pwm_enable_set(p, pwm->hwpwm, true);
+
+	return 0;
+}
+
+static void brcmstb_pwm_disable(struct pwm_chip *chip, struct pwm_device *pwm)
+{
+	struct brcmstb_pwm_dev *p = to_brcmstb_pwm(chip);
+
+	brcmstb_pwm_enable_set(p, pwm->hwpwm, false);
+}
+
+static const struct pwm_ops brcmstb_pwm_ops = {
+	.config	= brcmstb_pwm_config,
+	.enable	= brcmstb_pwm_enable,
+	.disable = brcmstb_pwm_disable,
+	.owner = THIS_MODULE,
+};
+
+static const struct of_device_id brcmstb_pwm_of_match[] = {
+	{ .compatible = "brcm,bcm7038-pwm", },
+	{ /* sentinel */ }
+};
+
+static int brcmstb_pwm_probe(struct platform_device *pdev)
+{
+	struct brcmstb_pwm_dev *p;
+	struct resource *r;
+	int ret;
+
+	p = devm_kzalloc(&pdev->dev, sizeof(*p), GFP_KERNEL);
+	if (!p)
+		return -ENOMEM;
+
+	spin_lock_init(&p->lock);
+
+	/*
+	 * Try to grab the clock and its rate, if not available, default
+	 * to the base 27Mhz clock domain this block comes from.
+	 */
+	p->clk = devm_clk_get(&pdev->dev, NULL);
+	if (IS_ERR(p->clk)) {
+		dev_err(&pdev->dev, "fail to obtain clock\n");
+		return PTR_ERR(p->clk);
+	}
+
+	clk_prepare_enable(p->clk);
+
+	platform_set_drvdata(pdev, p);
+
+	p->chip.dev = &pdev->dev;
+	p->chip.ops = &brcmstb_pwm_ops;
+	/* Dynamically assign a PWM base */
+	p->chip.base = -1;
+	/* Static number of PWM channels for this controller */
+	p->chip.npwm = 2;
+	p->chip.can_sleep = true;
+
+	r = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+	p->base = devm_ioremap_resource(&pdev->dev, r);
+	if (!p->base) {
+		ret = -ENOMEM;
+		goto out_clk;
+	}
+
+	ret = pwmchip_add(&p->chip);
+	if (ret) {
+		dev_err(&pdev->dev, "failed to add PWM chip %d\n", ret);
+		goto out_clk;
+	}
+
+	return ret;
+
+out_clk:
+	clk_disable_unprepare(p->clk);
+	return ret;
+}
+
+static int brcmstb_pwm_remove(struct platform_device *pdev)
+{
+	struct brcmstb_pwm_dev *p = platform_get_drvdata(pdev);
+	int ret;
+
+	ret = pwmchip_remove(&p->chip);
+	if (ret)
+		return ret;
+
+	clk_disable_unprepare(p->clk);
+
+	return 0;
+}
+
+#ifdef CONFIG_PM_SLEEP
+static int brcmstb_pwm_suspend(struct device *d)
+{
+	struct platform_device *pdev = to_platform_device(d);
+	struct brcmstb_pwm_dev *p = platform_get_drvdata(pdev);
+
+	clk_disable(p->clk);
+
+	return 0;
+}
+
+static int brcmstb_pwm_resume(struct device *d)
+{
+	struct platform_device *pdev = to_platform_device(d);
+	struct brcmstb_pwm_dev *p = platform_get_drvdata(pdev);
+
+	clk_enable(p->clk);
+
+	return 0;
+}
+#endif
+
+static SIMPLE_DEV_PM_OPS(brcmstb_pwm_pm_ops,
+			 brcmstb_pwm_suspend, brcmstb_pwm_resume);
+
+static struct platform_driver brcmstb_pwm_driver = {
+	.probe	= brcmstb_pwm_probe,
+	.remove	= brcmstb_pwm_remove,
+	.driver	= {
+		.name = "pwm-brcmstb",
+		.of_match_table = brcmstb_pwm_of_match,
+		.pm = &brcmstb_pwm_pm_ops,
+	},
+};
+module_platform_driver(brcmstb_pwm_driver);
+
+MODULE_AUTHOR("Florian Fainelli <f.fainelli-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org>");
+MODULE_DESCRIPTION("Broadcom STB PWM driver");
+MODULE_ALIAS("platform:pwm-brcmstb");
+MODULE_LICENSE("GPL");
-- 
2.1.0

--
To unsubscribe from this list: send the line "unsubscribe devicetree" in
the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply related	[flat|nested] 13+ messages in thread

* Re: [PATCH v4 0/2] pwm: Broadcom BCM7038 PWM controller (v4)
  2015-09-14 23:47 [PATCH v4 0/2] pwm: Broadcom BCM7038 PWM controller (v4) Florian Fainelli
  2015-09-14 23:47 ` [PATCH v4 1/2] Documentation: dt: add Broadcom BCM7038 PWM controller binding Florian Fainelli
  2015-09-14 23:47   ` Florian Fainelli
@ 2015-09-25 23:05 ` Florian Fainelli
  2015-10-05 15:14   ` Thierry Reding
  3 siblings, 0 replies; 13+ messages in thread
From: Florian Fainelli @ 2015-09-25 23:05 UTC (permalink / raw)
  To: Florian Fainelli, linux-kernel
  Cc: bcm-kernel-feedback-list, thierry.reding, devicetree, linux-pwm, ariel

On 14/09/15 16:47, Florian Fainelli wrote:
> Hi,
> 
> This patch series add PWM support for the Broadcom BCM7xxx
> chips which feature one or more PWM controllers capable of
> output periods from 148ns to ~622ms using a combination of
> variable and fixed frequency settings.

Thierry, are you happy with this version of the patches? Thanks.

> 
> The controller does not support setting a polarity.
> 
> This is based on Thierry's pwm/next branch.
> 
> Florian Fainelli (2):
>   Documentation: dt: add Broadcom BCM7038 PWM controller binding
>   pwm: Add Broadcom BCM7038 PWM controller support
> 
>  .../devicetree/bindings/pwm/brcm,bcm7038-pwm.txt   |  20 ++
>  drivers/pwm/Kconfig                                |  10 +
>  drivers/pwm/Makefile                               |   1 +
>  drivers/pwm/pwm-brcmstb.c                          | 345 +++++++++++++++++++++
>  4 files changed, 376 insertions(+)
>  create mode 100644 Documentation/devicetree/bindings/pwm/brcm,bcm7038-pwm.txt
>  create mode 100644 drivers/pwm/pwm-brcmstb.c
> 


-- 
Florian

^ permalink raw reply	[flat|nested] 13+ messages in thread

* Re: [PATCH v4 0/2] pwm: Broadcom BCM7038 PWM controller (v4)
@ 2015-10-05 15:14   ` Thierry Reding
  0 siblings, 0 replies; 13+ messages in thread
From: Thierry Reding @ 2015-10-05 15:14 UTC (permalink / raw)
  To: Florian Fainelli
  Cc: linux-kernel, bcm-kernel-feedback-list, devicetree, linux-pwm, ariel

[-- Attachment #1: Type: text/plain, Size: 661 bytes --]

On Mon, Sep 14, 2015 at 04:47:04PM -0700, Florian Fainelli wrote:
> Hi,
> 
> This patch series add PWM support for the Broadcom BCM7xxx
> chips which feature one or more PWM controllers capable of
> output periods from 148ns to ~622ms using a combination of
> variable and fixed frequency settings.
> 
> The controller does not support setting a polarity.
> 
> This is based on Thierry's pwm/next branch.
> 
> Florian Fainelli (2):
>   Documentation: dt: add Broadcom BCM7038 PWM controller binding
>   pwm: Add Broadcom BCM7038 PWM controller support

I've applied both of these patches with a couple of stylistic changes.

Thanks,
Thierry

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 819 bytes --]

^ permalink raw reply	[flat|nested] 13+ messages in thread

* Re: [PATCH v4 0/2] pwm: Broadcom BCM7038 PWM controller (v4)
@ 2015-10-05 15:14   ` Thierry Reding
  0 siblings, 0 replies; 13+ messages in thread
From: Thierry Reding @ 2015-10-05 15:14 UTC (permalink / raw)
  To: Florian Fainelli
  Cc: linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	bcm-kernel-feedback-list-dY08KVG/lbpWk0Htik3J/w,
	devicetree-u79uwXL29TY76Z2rM5mHXA,
	linux-pwm-u79uwXL29TY76Z2rM5mHXA,
	ariel-30ULvvUtt6G51wMPkGsGjgyUoB5FGQPZ

[-- Attachment #1: Type: text/plain, Size: 661 bytes --]

On Mon, Sep 14, 2015 at 04:47:04PM -0700, Florian Fainelli wrote:
> Hi,
> 
> This patch series add PWM support for the Broadcom BCM7xxx
> chips which feature one or more PWM controllers capable of
> output periods from 148ns to ~622ms using a combination of
> variable and fixed frequency settings.
> 
> The controller does not support setting a polarity.
> 
> This is based on Thierry's pwm/next branch.
> 
> Florian Fainelli (2):
>   Documentation: dt: add Broadcom BCM7038 PWM controller binding
>   pwm: Add Broadcom BCM7038 PWM controller support

I've applied both of these patches with a couple of stylistic changes.

Thanks,
Thierry

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 819 bytes --]

^ permalink raw reply	[flat|nested] 13+ messages in thread

* Re: [PATCH v4 0/2] pwm: Broadcom BCM7038 PWM controller (v4)
  2015-10-05 15:14   ` Thierry Reding
  (?)
@ 2015-10-06 18:14   ` Florian Fainelli
  2015-10-06 18:16       ` Florian Fainelli
  -1 siblings, 1 reply; 13+ messages in thread
From: Florian Fainelli @ 2015-10-06 18:14 UTC (permalink / raw)
  To: Thierry Reding, Florian Fainelli
  Cc: linux-kernel, bcm-kernel-feedback-list, devicetree, linux-pwm, ariel

On 05/10/15 08:14, Thierry Reding wrote:
> On Mon, Sep 14, 2015 at 04:47:04PM -0700, Florian Fainelli wrote:
>> Hi,
>>
>> This patch series add PWM support for the Broadcom BCM7xxx
>> chips which feature one or more PWM controllers capable of
>> output periods from 148ns to ~622ms using a combination of
>> variable and fixed frequency settings.
>>
>> The controller does not support setting a polarity.
>>
>> This is based on Thierry's pwm/next branch.
>>
>> Florian Fainelli (2):
>>   Documentation: dt: add Broadcom BCM7038 PWM controller binding
>>   pwm: Add Broadcom BCM7038 PWM controller support
> 
> I've applied both of these patches with a couple of stylistic changes.

Thanks but:

1) you dropped the MODULE_DEVICE_TABLE while doing so which is useful
for auto-loading OF modules
2) you introduced a build failure in the CONFIG_PM_SLEEP

There was a patch just submitted for 2), but I can submit an incremental
for 1) maybe?
-- 
Florian

^ permalink raw reply	[flat|nested] 13+ messages in thread

* Re: [PATCH v4 0/2] pwm: Broadcom BCM7038 PWM controller (v4)
  2015-10-06 18:14   ` Florian Fainelli
@ 2015-10-06 18:16       ` Florian Fainelli
  0 siblings, 0 replies; 13+ messages in thread
From: Florian Fainelli @ 2015-10-06 18:16 UTC (permalink / raw)
  To: Florian Fainelli, Thierry Reding
  Cc: linux-kernel, bcm-kernel-feedback-list, devicetree, linux-pwm, ariel

On 06/10/15 11:14, Florian Fainelli wrote:
> On 05/10/15 08:14, Thierry Reding wrote:
>> On Mon, Sep 14, 2015 at 04:47:04PM -0700, Florian Fainelli wrote:
>>> Hi,
>>>
>>> This patch series add PWM support for the Broadcom BCM7xxx
>>> chips which feature one or more PWM controllers capable of
>>> output periods from 148ns to ~622ms using a combination of
>>> variable and fixed frequency settings.
>>>
>>> The controller does not support setting a polarity.
>>>
>>> This is based on Thierry's pwm/next branch.
>>>
>>> Florian Fainelli (2):
>>>   Documentation: dt: add Broadcom BCM7038 PWM controller binding
>>>   pwm: Add Broadcom BCM7038 PWM controller support
>>
>> I've applied both of these patches with a couple of stylistic changes.
> 
> Thanks but:
> 
> 1) you dropped the MODULE_DEVICE_TABLE while doing so which is useful
> for auto-loading OF modules
> 2) you introduced a build failure in the CONFIG_PM_SLEEP
> 
> There was a patch just submitted for 2), but I can submit an incremental
> for 1) maybe?

Disregard that, brainfart on my side, was diffing branches backwards...
oh well.
-- 
Florian

^ permalink raw reply	[flat|nested] 13+ messages in thread

* Re: [PATCH v4 0/2] pwm: Broadcom BCM7038 PWM controller (v4)
@ 2015-10-06 18:16       ` Florian Fainelli
  0 siblings, 0 replies; 13+ messages in thread
From: Florian Fainelli @ 2015-10-06 18:16 UTC (permalink / raw)
  To: Florian Fainelli, Thierry Reding
  Cc: linux-kernel, bcm-kernel-feedback-list, devicetree, linux-pwm, ariel

On 06/10/15 11:14, Florian Fainelli wrote:
> On 05/10/15 08:14, Thierry Reding wrote:
>> On Mon, Sep 14, 2015 at 04:47:04PM -0700, Florian Fainelli wrote:
>>> Hi,
>>>
>>> This patch series add PWM support for the Broadcom BCM7xxx
>>> chips which feature one or more PWM controllers capable of
>>> output periods from 148ns to ~622ms using a combination of
>>> variable and fixed frequency settings.
>>>
>>> The controller does not support setting a polarity.
>>>
>>> This is based on Thierry's pwm/next branch.
>>>
>>> Florian Fainelli (2):
>>>   Documentation: dt: add Broadcom BCM7038 PWM controller binding
>>>   pwm: Add Broadcom BCM7038 PWM controller support
>>
>> I've applied both of these patches with a couple of stylistic changes.
> 
> Thanks but:
> 
> 1) you dropped the MODULE_DEVICE_TABLE while doing so which is useful
> for auto-loading OF modules
> 2) you introduced a build failure in the CONFIG_PM_SLEEP
> 
> There was a patch just submitted for 2), but I can submit an incremental
> for 1) maybe?

Disregard that, brainfart on my side, was diffing branches backwards...
oh well.
-- 
Florian

^ permalink raw reply	[flat|nested] 13+ messages in thread

* [PATCH] pwm: fix Broadcom BCM7038 PWM driver
  2015-10-05 15:14   ` Thierry Reding
  (?)
  (?)
@ 2015-10-06 19:59   ` Arnd Bergmann
  2015-10-07  0:51     ` Florian Fainelli
  -1 siblings, 1 reply; 13+ messages in thread
From: Arnd Bergmann @ 2015-10-06 19:59 UTC (permalink / raw)
  To: Thierry Reding
  Cc: Florian Fainelli, linux-kernel, bcm-kernel-feedback-list,
	devicetree, linux-pwm, ariel

The newly added pwm-brcmstb driver fails to build if CONFIG_PM_SLEEP
is enabled:

drivers/pwm/pwm-brcmstb.c: In function 'brcmstb_pwm_suspend':
drivers/pwm/pwm-brcmstb.c:309:42: error: 'dev' undeclared (first use in this function)
  struct brcmstb_pwm *p = dev_get_drvdata(dev);

This changes the name of the function argument to match its user.

Signed-off-by: Arnd Bergmann <arnd@arndb.de>
---
On Monday 05 October 2015 17:14:15 Thierry Reding wrote:
> On Mon, Sep 14, 2015 at 04:47:04PM -0700, Florian Fainelli wrote:
> > Florian Fainelli (2):
> >   Documentation: dt: add Broadcom BCM7038 PWM controller binding
> >   pwm: Add Broadcom BCM7038 PWM controller support
> 
> I've applied both of these patches with a couple of stylistic changes.

As in the pwm-berlin driver, one of the fixups was broken.

diff --git a/drivers/pwm/pwm-brcmstb.c b/drivers/pwm/pwm-brcmstb.c
index 083e3ef5b8e5..423ce087cd9c 100644
--- a/drivers/pwm/pwm-brcmstb.c
+++ b/drivers/pwm/pwm-brcmstb.c
@@ -304,7 +304,7 @@ static int brcmstb_pwm_remove(struct platform_device *pdev)
 }
 
 #ifdef CONFIG_PM_SLEEP
-static int brcmstb_pwm_suspend(struct device *d)
+static int brcmstb_pwm_suspend(struct device *dev)
 {
 	struct brcmstb_pwm *p = dev_get_drvdata(dev);
 
@@ -313,7 +313,7 @@ static int brcmstb_pwm_suspend(struct device *d)
 	return 0;
 }
 
-static int brcmstb_pwm_resume(struct device *d)
+static int brcmstb_pwm_resume(struct device *dev)
 {
 	struct brcmstb_pwm *p = dev_get_drvdata(dev);
 


^ permalink raw reply related	[flat|nested] 13+ messages in thread

* Re: [PATCH] pwm: fix Broadcom BCM7038 PWM driver
  2015-10-06 19:59   ` [PATCH] pwm: fix Broadcom BCM7038 PWM driver Arnd Bergmann
@ 2015-10-07  0:51     ` Florian Fainelli
  2015-10-07 13:31       ` Arnd Bergmann
  0 siblings, 1 reply; 13+ messages in thread
From: Florian Fainelli @ 2015-10-07  0:51 UTC (permalink / raw)
  To: Arnd Bergmann, Thierry Reding
  Cc: Florian Fainelli, linux-kernel, bcm-kernel-feedback-list,
	devicetree, linux-pwm, ariel

On 06/10/15 12:59, Arnd Bergmann wrote:
> The newly added pwm-brcmstb driver fails to build if CONFIG_PM_SLEEP
> is enabled:
> 
> drivers/pwm/pwm-brcmstb.c: In function 'brcmstb_pwm_suspend':
> drivers/pwm/pwm-brcmstb.c:309:42: error: 'dev' undeclared (first use in this function)
>   struct brcmstb_pwm *p = dev_get_drvdata(dev);
> 
> This changes the name of the function argument to match its user.

Thanks, maybe, to avoid similar issues in the future, we should start
removing the ifdef CONFIG_PM_SLEEP and instead annotate such functions
with __maybe_unused. I wonder if we could magically make that happen
with a coccinelle script that looks for SIMPLE_DEV_PM_OPS to know which
functions to annotate... humm.

> 
> Signed-off-by: Arnd Bergmann <arnd@arndb.de>
> ---
> On Monday 05 October 2015 17:14:15 Thierry Reding wrote:
>> On Mon, Sep 14, 2015 at 04:47:04PM -0700, Florian Fainelli wrote:
>>> Florian Fainelli (2):
>>>   Documentation: dt: add Broadcom BCM7038 PWM controller binding
>>>   pwm: Add Broadcom BCM7038 PWM controller support
>>
>> I've applied both of these patches with a couple of stylistic changes.
> 
> As in the pwm-berlin driver, one of the fixups was broken.
> 
> diff --git a/drivers/pwm/pwm-brcmstb.c b/drivers/pwm/pwm-brcmstb.c
> index 083e3ef5b8e5..423ce087cd9c 100644
> --- a/drivers/pwm/pwm-brcmstb.c
> +++ b/drivers/pwm/pwm-brcmstb.c
> @@ -304,7 +304,7 @@ static int brcmstb_pwm_remove(struct platform_device *pdev)
>  }
>  
>  #ifdef CONFIG_PM_SLEEP
> -static int brcmstb_pwm_suspend(struct device *d)
> +static int brcmstb_pwm_suspend(struct device *dev)
>  {
>  	struct brcmstb_pwm *p = dev_get_drvdata(dev);
>  
> @@ -313,7 +313,7 @@ static int brcmstb_pwm_suspend(struct device *d)
>  	return 0;
>  }
>  
> -static int brcmstb_pwm_resume(struct device *d)
> +static int brcmstb_pwm_resume(struct device *dev)
>  {
>  	struct brcmstb_pwm *p = dev_get_drvdata(dev);
>  
> 


-- 
Florian

^ permalink raw reply	[flat|nested] 13+ messages in thread

* Re: [PATCH] pwm: fix Broadcom BCM7038 PWM driver
  2015-10-07  0:51     ` Florian Fainelli
@ 2015-10-07 13:31       ` Arnd Bergmann
  0 siblings, 0 replies; 13+ messages in thread
From: Arnd Bergmann @ 2015-10-07 13:31 UTC (permalink / raw)
  To: Florian Fainelli
  Cc: Thierry Reding, linux-kernel, bcm-kernel-feedback-list,
	devicetree, linux-pwm, ariel

On Tuesday 06 October 2015 17:51:30 Florian Fainelli wrote:
> On 06/10/15 12:59, Arnd Bergmann wrote:
> > The newly added pwm-brcmstb driver fails to build if CONFIG_PM_SLEEP
> > is enabled:
> > 
> > drivers/pwm/pwm-brcmstb.c: In function 'brcmstb_pwm_suspend':
> > drivers/pwm/pwm-brcmstb.c:309:42: error: 'dev' undeclared (first use in this function)
> >   struct brcmstb_pwm *p = dev_get_drvdata(dev);
> > 
> > This changes the name of the function argument to match its user.
> 
> Thanks, maybe, to avoid similar issues in the future, we should start
> removing the ifdef CONFIG_PM_SLEEP and instead annotate such functions
> with __maybe_unused. I wonder if we could magically make that happen
> with a coccinelle script that looks for SIMPLE_DEV_PM_OPS to know which
> functions to annotate... humm.

I think the best solution would be to replace SIMPLE_DEV_PM_OPS with
a macro that creates an unused reference to the functions. That
way, we could remove all the #ifdef CONFIG_PM_SLEEP from the kernel,
but we'd still have to use coccinelle to replace all the current
instances with the new macro.

	Arnd

^ permalink raw reply	[flat|nested] 13+ messages in thread

end of thread, other threads:[~2015-10-07 13:31 UTC | newest]

Thread overview: 13+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2015-09-14 23:47 [PATCH v4 0/2] pwm: Broadcom BCM7038 PWM controller (v4) Florian Fainelli
2015-09-14 23:47 ` [PATCH v4 1/2] Documentation: dt: add Broadcom BCM7038 PWM controller binding Florian Fainelli
2015-09-14 23:47 ` [PATCH v4 2/2] pwm: Add Broadcom BCM7038 PWM controller support Florian Fainelli
2015-09-14 23:47   ` Florian Fainelli
2015-09-25 23:05 ` [PATCH v4 0/2] pwm: Broadcom BCM7038 PWM controller (v4) Florian Fainelli
2015-10-05 15:14 ` Thierry Reding
2015-10-05 15:14   ` Thierry Reding
2015-10-06 18:14   ` Florian Fainelli
2015-10-06 18:16     ` Florian Fainelli
2015-10-06 18:16       ` Florian Fainelli
2015-10-06 19:59   ` [PATCH] pwm: fix Broadcom BCM7038 PWM driver Arnd Bergmann
2015-10-07  0:51     ` Florian Fainelli
2015-10-07 13:31       ` Arnd Bergmann

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.