diff options
author | Linus Walleij <linus.walleij@linaro.org> | 2015-12-04 14:02:58 +0100 |
---|---|---|
committer | Linus Walleij <linus.walleij@linaro.org> | 2016-01-05 11:21:00 +0100 |
commit | 0f4630f3720e7e6e921bf525c8357fea7ef3dbab (patch) | |
tree | 61c1904593d1ee424464c2d57668ba0fd2fbcbb4 /drivers/gpio/gpio-dwapb.c | |
parent | gpio: of: provide optional of_mm_gpiochip_add_data() function (diff) | |
download | linux-0f4630f3720e7e6e921bf525c8357fea7ef3dbab.tar.xz linux-0f4630f3720e7e6e921bf525c8357fea7ef3dbab.zip |
gpio: generic: factor into gpio_chip struct
The separate struct bgpio_chip has been a pain to handle, both
by being confusingly similar in name to struct gpio_chip and
for being contained inside a struct so that struct gpio_chip
is contained in a struct contained in a struct, making several
steps of dereferencing necessary.
Make things simpler: include the fields directly into
<linux/gpio/driver.h>, #ifdef:ed for CONFIG_GENERIC_GPIO, and
get rid of the <linux/basic_mmio_gpio.h> altogether. Prefix
some of the member variables with bgpio_* and add proper
kerneldoc while we're at it.
Modify all users to handle the change and use a struct
gpio_chip directly. And while we're at it: replace all
container_of() dereferencing by gpiochip_get_data() and
registering the gpio_chip with gpiochip_add_data().
Cc: arm@kernel.org
Cc: Alexander Shiyan <shc_work@mail.ru>
Cc: Shawn Guo <shawnguo@kernel.org>
Cc: Sascha Hauer <kernel@pengutronix.de>
Cc: Kukjin Kim <kgene@kernel.org>
Cc: Alexandre Courbot <gnurou@gmail.com>
Cc: Brian Norris <computersforpeace@gmail.com>
Cc: Florian Fainelli <f.fainelli@gmail.com>
Cc: Sudeep Holla <sudeep.holla@arm.com>
Cc: Lorenzo Pieralisi <lorenzo.pieralisi@arm.com>
Cc: Nicolas Pitre <nicolas.pitre@linaro.org>
Cc: Olof Johansson <olof@lixom.net>
Cc: Vladimir Zapolskiy <vladimir_zapolskiy@mentor.com>
Cc: Rabin Vincent <rabin@rab.in>
Cc: linux-arm-kernel@lists.infradead.org
Cc: linux-omap@vger.kernel.org
Cc: linux-samsung-soc@vger.kernel.org
Cc: bcm-kernel-feedback-list@broadcom.com
Acked-by: Gregory Fong <gregory.0xf0@gmail.com>
Acked-by: Liviu Dudau <Liviu.Dudau@arm.com>
Acked-by: H Hartley Sweeten <hsweeten@visionengravers.com>
Acked-by: Tony Lindgren <tony@atomide.com>
Acked-by: Krzysztof Kozlowski <k.kozlowski@samsung.com>
Acked-by: Lee Jones <lee.jones@linaro.org>
Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
Diffstat (limited to 'drivers/gpio/gpio-dwapb.c')
-rw-r--r-- | drivers/gpio/gpio-dwapb.c | 92 |
1 files changed, 43 insertions, 49 deletions
diff --git a/drivers/gpio/gpio-dwapb.c b/drivers/gpio/gpio-dwapb.c index fcd5b0acfc72..597de1ef497b 100644 --- a/drivers/gpio/gpio-dwapb.c +++ b/drivers/gpio/gpio-dwapb.c @@ -7,7 +7,9 @@ * * All enquiries to support@picochip.com */ -#include <linux/basic_mmio_gpio.h> +#include <linux/gpio/driver.h> +/* FIXME: for gpio_get_value(), replace this with direct register read */ +#include <linux/gpio.h> #include <linux/err.h> #include <linux/init.h> #include <linux/interrupt.h> @@ -66,7 +68,7 @@ struct dwapb_context { #endif struct dwapb_gpio_port { - struct bgpio_chip bgc; + struct gpio_chip gc; bool is_registered; struct dwapb_gpio *gpio; #ifdef CONFIG_PM_SLEEP @@ -83,33 +85,26 @@ struct dwapb_gpio { struct irq_domain *domain; }; -static inline struct dwapb_gpio_port * -to_dwapb_gpio_port(struct bgpio_chip *bgc) -{ - return container_of(bgc, struct dwapb_gpio_port, bgc); -} - static inline u32 dwapb_read(struct dwapb_gpio *gpio, unsigned int offset) { - struct bgpio_chip *bgc = &gpio->ports[0].bgc; + struct gpio_chip *gc = &gpio->ports[0].gc; void __iomem *reg_base = gpio->regs; - return bgc->read_reg(reg_base + offset); + return gc->read_reg(reg_base + offset); } static inline void dwapb_write(struct dwapb_gpio *gpio, unsigned int offset, u32 val) { - struct bgpio_chip *bgc = &gpio->ports[0].bgc; + struct gpio_chip *gc = &gpio->ports[0].gc; void __iomem *reg_base = gpio->regs; - bgc->write_reg(reg_base + offset, val); + gc->write_reg(reg_base + offset, val); } static int dwapb_gpio_to_irq(struct gpio_chip *gc, unsigned offset) { - struct bgpio_chip *bgc = to_bgpio_chip(gc); - struct dwapb_gpio_port *port = to_dwapb_gpio_port(bgc); + struct dwapb_gpio_port *port = gpiochip_get_data(gc); struct dwapb_gpio *gpio = port->gpio; return irq_find_mapping(gpio->domain, offset); @@ -119,7 +114,7 @@ static void dwapb_toggle_trigger(struct dwapb_gpio *gpio, unsigned int offs) { u32 v = dwapb_read(gpio, GPIO_INT_POLARITY); - if (gpio_get_value(gpio->ports[0].bgc.gc.base + offs)) + if (gpio_get_value(gpio->ports[0].gc.base + offs)) v &= ~BIT(offs); else v |= BIT(offs); @@ -162,39 +157,39 @@ static void dwapb_irq_enable(struct irq_data *d) { struct irq_chip_generic *igc = irq_data_get_irq_chip_data(d); struct dwapb_gpio *gpio = igc->private; - struct bgpio_chip *bgc = &gpio->ports[0].bgc; + struct gpio_chip *gc = &gpio->ports[0].gc; unsigned long flags; u32 val; - spin_lock_irqsave(&bgc->lock, flags); + spin_lock_irqsave(&gc->bgpio_lock, flags); val = dwapb_read(gpio, GPIO_INTEN); val |= BIT(d->hwirq); dwapb_write(gpio, GPIO_INTEN, val); - spin_unlock_irqrestore(&bgc->lock, flags); + spin_unlock_irqrestore(&gc->bgpio_lock, flags); } static void dwapb_irq_disable(struct irq_data *d) { struct irq_chip_generic *igc = irq_data_get_irq_chip_data(d); struct dwapb_gpio *gpio = igc->private; - struct bgpio_chip *bgc = &gpio->ports[0].bgc; + struct gpio_chip *gc = &gpio->ports[0].gc; unsigned long flags; u32 val; - spin_lock_irqsave(&bgc->lock, flags); + spin_lock_irqsave(&gc->bgpio_lock, flags); val = dwapb_read(gpio, GPIO_INTEN); val &= ~BIT(d->hwirq); dwapb_write(gpio, GPIO_INTEN, val); - spin_unlock_irqrestore(&bgc->lock, flags); + spin_unlock_irqrestore(&gc->bgpio_lock, flags); } static int dwapb_irq_reqres(struct irq_data *d) { struct irq_chip_generic *igc = irq_data_get_irq_chip_data(d); struct dwapb_gpio *gpio = igc->private; - struct bgpio_chip *bgc = &gpio->ports[0].bgc; + struct gpio_chip *gc = &gpio->ports[0].gc; - if (gpiochip_lock_as_irq(&bgc->gc, irqd_to_hwirq(d))) { + if (gpiochip_lock_as_irq(gc, irqd_to_hwirq(d))) { dev_err(gpio->dev, "unable to lock HW IRQ %lu for IRQ\n", irqd_to_hwirq(d)); return -EINVAL; @@ -206,16 +201,16 @@ static void dwapb_irq_relres(struct irq_data *d) { struct irq_chip_generic *igc = irq_data_get_irq_chip_data(d); struct dwapb_gpio *gpio = igc->private; - struct bgpio_chip *bgc = &gpio->ports[0].bgc; + struct gpio_chip *gc = &gpio->ports[0].gc; - gpiochip_unlock_as_irq(&bgc->gc, irqd_to_hwirq(d)); + gpiochip_unlock_as_irq(gc, irqd_to_hwirq(d)); } static int dwapb_irq_set_type(struct irq_data *d, u32 type) { struct irq_chip_generic *igc = irq_data_get_irq_chip_data(d); struct dwapb_gpio *gpio = igc->private; - struct bgpio_chip *bgc = &gpio->ports[0].bgc; + struct gpio_chip *gc = &gpio->ports[0].gc; int bit = d->hwirq; unsigned long level, polarity, flags; @@ -223,7 +218,7 @@ static int dwapb_irq_set_type(struct irq_data *d, u32 type) IRQ_TYPE_LEVEL_HIGH | IRQ_TYPE_LEVEL_LOW)) return -EINVAL; - spin_lock_irqsave(&bgc->lock, flags); + spin_lock_irqsave(&gc->bgpio_lock, flags); level = dwapb_read(gpio, GPIO_INTTYPE_LEVEL); polarity = dwapb_read(gpio, GPIO_INT_POLARITY); @@ -254,7 +249,7 @@ static int dwapb_irq_set_type(struct irq_data *d, u32 type) dwapb_write(gpio, GPIO_INTTYPE_LEVEL, level); dwapb_write(gpio, GPIO_INT_POLARITY, polarity); - spin_unlock_irqrestore(&bgc->lock, flags); + spin_unlock_irqrestore(&gc->bgpio_lock, flags); return 0; } @@ -262,13 +257,12 @@ static int dwapb_irq_set_type(struct irq_data *d, u32 type) static int dwapb_gpio_set_debounce(struct gpio_chip *gc, unsigned offset, unsigned debounce) { - struct bgpio_chip *bgc = to_bgpio_chip(gc); - struct dwapb_gpio_port *port = to_dwapb_gpio_port(bgc); + struct dwapb_gpio_port *port = gpiochip_get_data(gc); struct dwapb_gpio *gpio = port->gpio; unsigned long flags, val_deb; - unsigned long mask = bgc->pin2mask(bgc, offset); + unsigned long mask = gc->pin2mask(gc, offset); - spin_lock_irqsave(&bgc->lock, flags); + spin_lock_irqsave(&gc->bgpio_lock, flags); val_deb = dwapb_read(gpio, GPIO_PORTA_DEBOUNCE); if (debounce) @@ -276,7 +270,7 @@ static int dwapb_gpio_set_debounce(struct gpio_chip *gc, else dwapb_write(gpio, GPIO_PORTA_DEBOUNCE, val_deb & ~mask); - spin_unlock_irqrestore(&bgc->lock, flags); + spin_unlock_irqrestore(&gc->bgpio_lock, flags); return 0; } @@ -295,7 +289,7 @@ static void dwapb_configure_irqs(struct dwapb_gpio *gpio, struct dwapb_gpio_port *port, struct dwapb_port_property *pp) { - struct gpio_chip *gc = &port->bgc.gc; + struct gpio_chip *gc = &port->gc; struct device_node *node = pp->node; struct irq_chip_generic *irq_gc = NULL; unsigned int hwirq, ngpio = gc->ngpio; @@ -369,13 +363,13 @@ static void dwapb_configure_irqs(struct dwapb_gpio *gpio, for (hwirq = 0 ; hwirq < ngpio ; hwirq++) irq_create_mapping(gpio->domain, hwirq); - port->bgc.gc.to_irq = dwapb_gpio_to_irq; + port->gc.to_irq = dwapb_gpio_to_irq; } static void dwapb_irq_teardown(struct dwapb_gpio *gpio) { struct dwapb_gpio_port *port = &gpio->ports[0]; - struct gpio_chip *gc = &port->bgc.gc; + struct gpio_chip *gc = &port->gc; unsigned int ngpio = gc->ngpio; irq_hw_number_t hwirq; @@ -412,7 +406,7 @@ static int dwapb_gpio_add_port(struct dwapb_gpio *gpio, dirout = gpio->regs + GPIO_SWPORTA_DDR + (pp->idx * GPIO_SWPORT_DDR_SIZE); - err = bgpio_init(&port->bgc, gpio->dev, 4, dat, set, NULL, dirout, + err = bgpio_init(&port->gc, gpio->dev, 4, dat, set, NULL, dirout, NULL, false); if (err) { dev_err(gpio->dev, "failed to init gpio chip for %s\n", @@ -421,19 +415,19 @@ static int dwapb_gpio_add_port(struct dwapb_gpio *gpio, } #ifdef CONFIG_OF_GPIO - port->bgc.gc.of_node = pp->node; + port->gc.of_node = pp->node; #endif - port->bgc.gc.ngpio = pp->ngpio; - port->bgc.gc.base = pp->gpio_base; + port->gc.ngpio = pp->ngpio; + port->gc.base = pp->gpio_base; /* Only port A support debounce */ if (pp->idx == 0) - port->bgc.gc.set_debounce = dwapb_gpio_set_debounce; + port->gc.set_debounce = dwapb_gpio_set_debounce; if (pp->irq) dwapb_configure_irqs(gpio, port, pp); - err = gpiochip_add(&port->bgc.gc); + err = gpiochip_add_data(&port->gc, port); if (err) dev_err(gpio->dev, "failed to register gpiochip for %s\n", pp->name); @@ -449,7 +443,7 @@ static void dwapb_gpio_unregister(struct dwapb_gpio *gpio) for (m = 0; m < gpio->nr_ports; ++m) if (gpio->ports[m].is_registered) - gpiochip_remove(&gpio->ports[m].bgc.gc); + gpiochip_remove(&gpio->ports[m].gc); } static struct dwapb_platform_data * @@ -591,11 +585,11 @@ static int dwapb_gpio_suspend(struct device *dev) { struct platform_device *pdev = to_platform_device(dev); struct dwapb_gpio *gpio = platform_get_drvdata(pdev); - struct bgpio_chip *bgc = &gpio->ports[0].bgc; + struct gpio_chip *gc = &gpio->ports[0].gc; unsigned long flags; int i; - spin_lock_irqsave(&bgc->lock, flags); + spin_lock_irqsave(&gc->bgpio_lock, flags); for (i = 0; i < gpio->nr_ports; i++) { unsigned int offset; unsigned int idx = gpio->ports[i].idx; @@ -624,7 +618,7 @@ static int dwapb_gpio_suspend(struct device *dev) dwapb_write(gpio, GPIO_INTMASK, 0xffffffff); } } - spin_unlock_irqrestore(&bgc->lock, flags); + spin_unlock_irqrestore(&gc->bgpio_lock, flags); return 0; } @@ -633,11 +627,11 @@ static int dwapb_gpio_resume(struct device *dev) { struct platform_device *pdev = to_platform_device(dev); struct dwapb_gpio *gpio = platform_get_drvdata(pdev); - struct bgpio_chip *bgc = &gpio->ports[0].bgc; + struct gpio_chip *gc = &gpio->ports[0].gc; unsigned long flags; int i; - spin_lock_irqsave(&bgc->lock, flags); + spin_lock_irqsave(&gc->bgpio_lock, flags); for (i = 0; i < gpio->nr_ports; i++) { unsigned int offset; unsigned int idx = gpio->ports[i].idx; @@ -666,7 +660,7 @@ static int dwapb_gpio_resume(struct device *dev) dwapb_write(gpio, GPIO_PORTA_EOI, 0xffffffff); } } - spin_unlock_irqrestore(&bgc->lock, flags); + spin_unlock_irqrestore(&gc->bgpio_lock, flags); return 0; } |