From f78709a5d4114edc21a5d86586ed5e56e284f2bd Mon Sep 17 00:00:00 2001 From: Dmitry Osipenko Date: Tue, 17 Jul 2018 19:10:38 +0300 Subject: gpio: tegra: Fix tegra_gpio_irq_set_type() Commit 36b312792b97 ("gpiolib: Respect error code of ->get_direction()") broke tegra_gpio_irq_set_type() because requesting of GPIO direction must be done after enabling GPIO function for a pin. This patch fixes drivers probe failure like this: gpio gpiochip0: (tegra-gpio): gpiochip_lock_as_irq: cannot get GPIO direction tegra-gpio 6000d000.gpio: unable to lock Tegra GPIO 144 as IRQ Fixes: 36b312792b97 ("gpiolib: Respect error code of ->get_direction()") Signed-off-by: Dmitry Osipenko Acked-by: Jon Hunter Tested-by: Jon Hunter Signed-off-by: Linus Walleij --- drivers/gpio/gpio-tegra.c | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) (limited to 'drivers/gpio/gpio-tegra.c') diff --git a/drivers/gpio/gpio-tegra.c b/drivers/gpio/gpio-tegra.c index 94396caaca75..22e7c99ed69e 100644 --- a/drivers/gpio/gpio-tegra.c +++ b/drivers/gpio/gpio-tegra.c @@ -323,13 +323,6 @@ static int tegra_gpio_irq_set_type(struct irq_data *d, unsigned int type) return -EINVAL; } - ret = gpiochip_lock_as_irq(&tgi->gc, gpio); - if (ret) { - dev_err(tgi->dev, - "unable to lock Tegra GPIO %u as IRQ\n", gpio); - return ret; - } - spin_lock_irqsave(&bank->lvl_lock[port], flags); val = tegra_gpio_readl(tgi, GPIO_INT_LVL(tgi, gpio)); @@ -342,6 +335,14 @@ static int tegra_gpio_irq_set_type(struct irq_data *d, unsigned int type) tegra_gpio_mask_write(tgi, GPIO_MSK_OE(tgi, gpio), gpio, 0); tegra_gpio_enable(tgi, gpio); + ret = gpiochip_lock_as_irq(&tgi->gc, gpio); + if (ret) { + dev_err(tgi->dev, + "unable to lock Tegra GPIO %u as IRQ\n", gpio); + tegra_gpio_disable(tgi, gpio); + return ret; + } + if (type & (IRQ_TYPE_LEVEL_LOW | IRQ_TYPE_LEVEL_HIGH)) irq_set_handler_locked(d, handle_level_irq); else if (type & (IRQ_TYPE_EDGE_FALLING | IRQ_TYPE_EDGE_RISING)) -- cgit v1.2.2 From 0b07609ccd48a23103881a161e49eb7a282170e7 Mon Sep 17 00:00:00 2001 From: Stefan Agner Date: Thu, 26 Jul 2018 17:42:52 +0200 Subject: gpio: tegra: drop tegra specific GPIO lockdep classes Since commit e45d1c80c0ee ("gpio: put GPIO IRQs into their own lock class") and commit a0a8bcf4670c ("gpiolib: irqchip: use different lockdep class for each gpio irqchip") GPIO lib takes care of lockdep classes. In fact, gpiochip_irq_map() overwrites the class anyway, so the lockdep class set by the driver is useless. Remove it. Signed-off-by: Stefan Agner Signed-off-by: Linus Walleij --- drivers/gpio/gpio-tegra.c | 9 --------- 1 file changed, 9 deletions(-) (limited to 'drivers/gpio/gpio-tegra.c') diff --git a/drivers/gpio/gpio-tegra.c b/drivers/gpio/gpio-tegra.c index 22e7c99ed69e..2d940785bad0 100644 --- a/drivers/gpio/gpio-tegra.c +++ b/drivers/gpio/gpio-tegra.c @@ -551,13 +551,6 @@ static const struct dev_pm_ops tegra_gpio_pm_ops = { SET_SYSTEM_SLEEP_PM_OPS(tegra_gpio_suspend, tegra_gpio_resume) }; -/* - * This lock class tells lockdep that GPIO irqs are in a different category - * than their parents, so it won't report false recursion. - */ -static struct lock_class_key gpio_lock_class; -static struct lock_class_key gpio_request_class; - static int tegra_gpio_probe(struct platform_device *pdev) { struct tegra_gpio_info *tgi; @@ -662,8 +655,6 @@ static int tegra_gpio_probe(struct platform_device *pdev) bank = &tgi->bank_info[GPIO_BANK(gpio)]; - irq_set_lockdep_class(irq, &gpio_lock_class, - &gpio_request_class); irq_set_chip_data(irq, bank); irq_set_chip_and_handler(irq, &tgi->ic, handle_simple_irq); } -- cgit v1.2.2 From 21041daba2300c88f0da538b3480a9fae37430ea Mon Sep 17 00:00:00 2001 From: Linus Walleij Date: Mon, 6 Aug 2018 17:38:33 +0200 Subject: gpio: tegra: Include the right header This is a GPIO driver so include only . Drop the use of GPIOF_* flags: these are for consumers, not drivers. Just return 0/1. Cc: Stefan Agner Cc: Thierry Reding Reviewed-by: Dmitry Osipenko Signed-off-by: Linus Walleij --- drivers/gpio/gpio-tegra.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'drivers/gpio/gpio-tegra.c') diff --git a/drivers/gpio/gpio-tegra.c b/drivers/gpio/gpio-tegra.c index 2d940785bad0..8e5f3150c6af 100644 --- a/drivers/gpio/gpio-tegra.c +++ b/drivers/gpio/gpio-tegra.c @@ -22,7 +22,7 @@ #include #include #include -#include +#include #include #include #include @@ -207,7 +207,7 @@ static int tegra_gpio_get_direction(struct gpio_chip *chip, oe = tegra_gpio_readl(tgi, GPIO_OE(tgi, offset)); - return (oe & pin_mask) ? GPIOF_DIR_OUT : GPIOF_DIR_IN; + return !(oe & pin_mask); } static int tegra_gpio_set_debounce(struct gpio_chip *chip, unsigned int offset, -- cgit v1.2.2