diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2017-10-11 12:16:38 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2017-10-11 12:16:38 -0400 |
commit | a0db28909ecfcb9e581f567f688929ed38ef3f56 (patch) | |
tree | 34f32a596f971a62387173d52e5cbd89ceaa8981 | |
parent | cc74613b13c95c842b47251c7b8788781a967503 (diff) | |
parent | 80ac93c274411a55ae731f259f75e4ca5e499e8b (diff) |
Merge tag 'gpio-v4.14-2' of git://git.kernel.org/pub/scm/linux/kernel/git/linusw/linux-gpio
Pull GPIO fixes from Linus Walleij:
"Here are some smallish GPIO fixes for v4.14. Like with pin control:
some build/Kconfig noise and one serious bug in a specific driver.
- Three Kconfig/build warning fixes
- A fix for lost edge IRQs in the OMAP driver"
* tag 'gpio-v4.14-2' of git://git.kernel.org/pub/scm/linux/kernel/git/linusw/linux-gpio:
gpio: omap: Fix lost edge interrupts
gpio: omap: omap_gpio_show_rev is not __init
gpio: acpi: work around false-positive -Wstring-overflow warning
gpio: thunderx: select IRQ_DOMAIN_HIERARCHY instead of depends on
-rw-r--r-- | drivers/gpio/Kconfig | 3 | ||||
-rw-r--r-- | drivers/gpio/gpio-omap.c | 24 | ||||
-rw-r--r-- | drivers/gpio/gpiolib-acpi.c | 2 |
3 files changed, 17 insertions, 12 deletions
diff --git a/drivers/gpio/Kconfig b/drivers/gpio/Kconfig index 3388d54ba114..3f80f167ed56 100644 --- a/drivers/gpio/Kconfig +++ b/drivers/gpio/Kconfig | |||
@@ -453,7 +453,8 @@ config GPIO_TS4800 | |||
453 | config GPIO_THUNDERX | 453 | config GPIO_THUNDERX |
454 | tristate "Cavium ThunderX/OCTEON-TX GPIO" | 454 | tristate "Cavium ThunderX/OCTEON-TX GPIO" |
455 | depends on ARCH_THUNDER || (64BIT && COMPILE_TEST) | 455 | depends on ARCH_THUNDER || (64BIT && COMPILE_TEST) |
456 | depends on PCI_MSI && IRQ_DOMAIN_HIERARCHY | 456 | depends on PCI_MSI |
457 | select IRQ_DOMAIN_HIERARCHY | ||
457 | select IRQ_FASTEOI_HIERARCHY_HANDLERS | 458 | select IRQ_FASTEOI_HIERARCHY_HANDLERS |
458 | help | 459 | help |
459 | Say yes here to support the on-chip GPIO lines on the ThunderX | 460 | Say yes here to support the on-chip GPIO lines on the ThunderX |
diff --git a/drivers/gpio/gpio-omap.c b/drivers/gpio/gpio-omap.c index dbf869fb63ce..3233b72b6828 100644 --- a/drivers/gpio/gpio-omap.c +++ b/drivers/gpio/gpio-omap.c | |||
@@ -518,7 +518,13 @@ static int omap_gpio_irq_type(struct irq_data *d, unsigned type) | |||
518 | if (type & (IRQ_TYPE_LEVEL_LOW | IRQ_TYPE_LEVEL_HIGH)) | 518 | if (type & (IRQ_TYPE_LEVEL_LOW | IRQ_TYPE_LEVEL_HIGH)) |
519 | irq_set_handler_locked(d, handle_level_irq); | 519 | irq_set_handler_locked(d, handle_level_irq); |
520 | else if (type & (IRQ_TYPE_EDGE_FALLING | IRQ_TYPE_EDGE_RISING)) | 520 | else if (type & (IRQ_TYPE_EDGE_FALLING | IRQ_TYPE_EDGE_RISING)) |
521 | irq_set_handler_locked(d, handle_edge_irq); | 521 | /* |
522 | * Edge IRQs are already cleared/acked in irq_handler and | ||
523 | * not need to be masked, as result handle_edge_irq() | ||
524 | * logic is excessed here and may cause lose of interrupts. | ||
525 | * So just use handle_simple_irq. | ||
526 | */ | ||
527 | irq_set_handler_locked(d, handle_simple_irq); | ||
522 | 528 | ||
523 | return 0; | 529 | return 0; |
524 | 530 | ||
@@ -678,7 +684,7 @@ static void omap_gpio_free(struct gpio_chip *chip, unsigned offset) | |||
678 | static irqreturn_t omap_gpio_irq_handler(int irq, void *gpiobank) | 684 | static irqreturn_t omap_gpio_irq_handler(int irq, void *gpiobank) |
679 | { | 685 | { |
680 | void __iomem *isr_reg = NULL; | 686 | void __iomem *isr_reg = NULL; |
681 | u32 isr; | 687 | u32 enabled, isr, level_mask; |
682 | unsigned int bit; | 688 | unsigned int bit; |
683 | struct gpio_bank *bank = gpiobank; | 689 | struct gpio_bank *bank = gpiobank; |
684 | unsigned long wa_lock_flags; | 690 | unsigned long wa_lock_flags; |
@@ -691,23 +697,21 @@ static irqreturn_t omap_gpio_irq_handler(int irq, void *gpiobank) | |||
691 | pm_runtime_get_sync(bank->chip.parent); | 697 | pm_runtime_get_sync(bank->chip.parent); |
692 | 698 | ||
693 | while (1) { | 699 | while (1) { |
694 | u32 isr_saved, level_mask = 0; | ||
695 | u32 enabled; | ||
696 | |||
697 | raw_spin_lock_irqsave(&bank->lock, lock_flags); | 700 | raw_spin_lock_irqsave(&bank->lock, lock_flags); |
698 | 701 | ||
699 | enabled = omap_get_gpio_irqbank_mask(bank); | 702 | enabled = omap_get_gpio_irqbank_mask(bank); |
700 | isr_saved = isr = readl_relaxed(isr_reg) & enabled; | 703 | isr = readl_relaxed(isr_reg) & enabled; |
701 | 704 | ||
702 | if (bank->level_mask) | 705 | if (bank->level_mask) |
703 | level_mask = bank->level_mask & enabled; | 706 | level_mask = bank->level_mask & enabled; |
707 | else | ||
708 | level_mask = 0; | ||
704 | 709 | ||
705 | /* clear edge sensitive interrupts before handler(s) are | 710 | /* clear edge sensitive interrupts before handler(s) are |
706 | called so that we don't miss any interrupt occurred while | 711 | called so that we don't miss any interrupt occurred while |
707 | executing them */ | 712 | executing them */ |
708 | omap_disable_gpio_irqbank(bank, isr_saved & ~level_mask); | 713 | if (isr & ~level_mask) |
709 | omap_clear_gpio_irqbank(bank, isr_saved & ~level_mask); | 714 | omap_clear_gpio_irqbank(bank, isr & ~level_mask); |
710 | omap_enable_gpio_irqbank(bank, isr_saved & ~level_mask); | ||
711 | 715 | ||
712 | raw_spin_unlock_irqrestore(&bank->lock, lock_flags); | 716 | raw_spin_unlock_irqrestore(&bank->lock, lock_flags); |
713 | 717 | ||
@@ -1010,7 +1014,7 @@ static void omap_gpio_set(struct gpio_chip *chip, unsigned offset, int value) | |||
1010 | 1014 | ||
1011 | /*---------------------------------------------------------------------*/ | 1015 | /*---------------------------------------------------------------------*/ |
1012 | 1016 | ||
1013 | static void __init omap_gpio_show_rev(struct gpio_bank *bank) | 1017 | static void omap_gpio_show_rev(struct gpio_bank *bank) |
1014 | { | 1018 | { |
1015 | static bool called; | 1019 | static bool called; |
1016 | u32 rev; | 1020 | u32 rev; |
diff --git a/drivers/gpio/gpiolib-acpi.c b/drivers/gpio/gpiolib-acpi.c index 4d2113530735..eb4528c87c0b 100644 --- a/drivers/gpio/gpiolib-acpi.c +++ b/drivers/gpio/gpiolib-acpi.c | |||
@@ -203,7 +203,7 @@ static acpi_status acpi_gpiochip_request_interrupt(struct acpi_resource *ares, | |||
203 | 203 | ||
204 | if (pin <= 255) { | 204 | if (pin <= 255) { |
205 | char ev_name[5]; | 205 | char ev_name[5]; |
206 | sprintf(ev_name, "_%c%02X", | 206 | sprintf(ev_name, "_%c%02hhX", |
207 | agpio->triggering == ACPI_EDGE_SENSITIVE ? 'E' : 'L', | 207 | agpio->triggering == ACPI_EDGE_SENSITIVE ? 'E' : 'L', |
208 | pin); | 208 | pin); |
209 | if (ACPI_SUCCESS(acpi_get_handle(handle, ev_name, &evt_handle))) | 209 | if (ACPI_SUCCESS(acpi_get_handle(handle, ev_name, &evt_handle))) |