From: Yang QU <yang...@stericsson.com> Add some GPIOs used as interrupt on ab8540 and modify the setting strategy of the interrupt line.
Signed-off-by: Lee Jones <lee.jo...@linaro.org> Signed-off-by: Yang QU <yang...@stericsson.com> Reviewed-by: Rabin VINCENT <rabin.vinc...@stericsson.com> Reviewed-by: Xiao Mei ZHANG <xiaomei.zh...@stericsson.com> Tested-by: Yang QU <yang...@stericsson.com> --- drivers/gpio/gpio-ab8500.c | 50 +++++++++++++++++++++++++++++++++----------- 1 file changed, 38 insertions(+), 12 deletions(-) diff --git a/drivers/gpio/gpio-ab8500.c b/drivers/gpio/gpio-ab8500.c index 833d4c2..edc3037 100644 --- a/drivers/gpio/gpio-ab8500.c +++ b/drivers/gpio/gpio-ab8500.c @@ -98,6 +98,7 @@ enum ab8500_gpio_action { struct ab8500_gpio_irq_cluster { int start; int end; + int offset; }; struct ab8500_gpio { @@ -155,10 +156,12 @@ static struct ab8500_gpio_irq_cluster ab8505_irq_clusters[] = { /* * For AB8540 Only some GPIOs are interrupt capable: + * GPIO43 to GPIO44 * GPIO51 to GPIO54 */ static struct ab8500_gpio_irq_cluster ab8540_irq_clusters[] = { - {.start = 50, .end = 53}, /* GPIO numbers start from 1 */ + {.start = 42, .end = 43, .offset = 2}, /* GPIO numbers start from 1 */ + {.start = 50, .end = 53}, }; @@ -253,7 +256,7 @@ static int ab8500_gpio_to_irq(struct gpio_chip *chip, unsigned offset) return base + offset - cluster->start; /* Advance by the number of gpios in this cluster */ - base += cluster->end - cluster->start + 1; + base += cluster->end + cluster->offset - cluster->start + 1; } return -EINVAL; @@ -273,7 +276,12 @@ static unsigned int irq_to_rising(unsigned int irq) { struct ab8500_gpio *ab8500_gpio = irq_get_chip_data(irq); int offset = irq - ab8500_gpio->irq_base; - int new_irq = offset + AB8500_INT_GPIO6R + int new_irq; + if (is_ab8540(ab8500_gpio->parent)) { + new_irq = offset * 2 + AB8540_INT_GPIO43R + + ab8500_gpio->parent->irq_base; + } else + new_irq = offset + AB8500_INT_GPIO6R + ab8500_gpio->parent->irq_base; return new_irq; } @@ -282,8 +290,13 @@ static unsigned int irq_to_falling(unsigned int irq) { struct ab8500_gpio *ab8500_gpio = irq_get_chip_data(irq); int offset = irq - ab8500_gpio->irq_base; - int new_irq = offset + AB8500_INT_GPIO6F - + ab8500_gpio->parent->irq_base; + int new_irq; + if (is_ab8540(ab8500_gpio->parent)) { + new_irq = offset * 2 + AB8540_INT_GPIO43F + + ab8500_gpio->parent->irq_base; + } else + new_irq = offset + AB8500_INT_GPIO6F + + ab8500_gpio->parent->irq_base; return new_irq; } @@ -291,20 +304,33 @@ static unsigned int irq_to_falling(unsigned int irq) static unsigned int rising_to_irq(unsigned int irq, void *dev) { struct ab8500_gpio *ab8500_gpio = dev; - int offset = irq - AB8500_INT_GPIO6R - - ab8500_gpio->parent->irq_base ; - int new_irq = offset + ab8500_gpio->irq_base; + int offset, new_irq; + if (is_ab8540(ab8500_gpio->parent)) { + offset = irq - AB8540_INT_GPIO43R + - ab8500_gpio->parent->irq_base; + new_irq = (offset >> 1) + ab8500_gpio->irq_base; + } else { + offset = irq - AB8500_INT_GPIO6R + - ab8500_gpio->parent->irq_base; + new_irq = offset + ab8500_gpio->irq_base; + } return new_irq; } static unsigned int falling_to_irq(unsigned int irq, void *dev) { struct ab8500_gpio *ab8500_gpio = dev; - int offset = irq - AB8500_INT_GPIO6F - - ab8500_gpio->parent->irq_base ; - int new_irq = offset + ab8500_gpio->irq_base; + int offset, new_irq; + if (is_ab8540(ab8500_gpio->parent)) { + offset = irq - AB8540_INT_GPIO43F + - ab8500_gpio->parent->irq_base; + new_irq = (offset >> 1) + ab8500_gpio->irq_base; + } else { + offset = irq - AB8500_INT_GPIO6F + - ab8500_gpio->parent->irq_base; + new_irq = offset + ab8500_gpio->irq_base; + } return new_irq; - } /* -- 1.7.9.5 -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/