For interrupt controller that doesn't support irq_disable and hardware with level interrupt, an extra interrupt can be pending. This patch fixes the issue by setting IRQ_DISABLE_UNLAZY flag for the interrupt line. Reference: http://git.kernel.org/tip/e9849777d0e27cdd2902805be51da73e7c79578c
Unified · Split
| @@ -29,6 +29,7 @@ · 28 unmodified lines | |||
| 29 | #include <linux/dmapool.h> | 29 | #include <linux/dmapool.h> |
| 30 | #include <linux/interrupt.h> | 30 | #include <linux/interrupt.h> |
| 31 | #include <linux/io.h> | 31 | #include <linux/io.h> |
| 32 | #include <linux/irq.h> | ||
| 32 | #include <linux/module.h> | 33 | #include <linux/module.h> |
| 33 | #include <linux/of_device.h> | 34 | #include <linux/of_device.h> |
| 34 | 35 | ||
| @@ -1610,6 +1611,7 @@ static int xgene_dma_request_irqs(struct xgene_dma *pdma) · 1575 unmodified lines | |||
| 1610 | /* Register DMA channel rx irq */ | 1611 | /* Register DMA channel rx irq */ |
| 1611 | for (i = 0; i < XGENE_DMA_MAX_CHANNEL; i++) { | 1612 | for (i = 0; i < XGENE_DMA_MAX_CHANNEL; i++) { |
| 1612 | chan = &pdma->chan[i]; | 1613 | chan = &pdma->chan[i]; |
| 1614 | irq_set_status_flags(chan->rx_irq, IRQ_DISABLE_UNLAZY); | ||
| 1613 | ret = devm_request_irq(chan->dev, chan->rx_irq, | 1615 | ret = devm_request_irq(chan->dev, chan->rx_irq, |
| 1614 | xgene_dma_chan_ring_isr, | 1616 | xgene_dma_chan_ring_isr, |
| 1615 | 0, chan->name, chan); | 1617 | 0, chan->name, chan); |
| @@ -1620,6 +1622,7 @@ static int xgene_dma_request_irqs(struct xgene_dma *pdma) · 4 unmodified lines | |||
| 1620 | 1622 | ||
| 1621 | for (j = 0; j < i; j++) { | 1623 | for (j = 0; j < i; j++) { |
| 1622 | chan = &pdma->chan[i]; | 1624 | chan = &pdma->chan[i]; |
| 1625 | irq_clear_status_flags(chan->rx_irq, IRQ_DISABLE_UNLAZY); | ||
| 1623 | devm_free_irq(chan->dev, chan->rx_irq, chan); | 1626 | devm_free_irq(chan->dev, chan->rx_irq, chan); |
| 1624 | } | 1627 | } |
| 1625 | 1628 | ||
| @@ -1640,6 +1643,7 @@ static void xgene_dma_free_irqs(struct xgene_dma *pdma) · 14 unmodified lines | |||
| 1640 | 1643 | ||
| 1641 | for (i = 0; i < XGENE_DMA_MAX_CHANNEL; i++) { | 1644 | for (i = 0; i < XGENE_DMA_MAX_CHANNEL; i++) { |
| 1642 | chan = &pdma->chan[i]; | 1645 | chan = &pdma->chan[i]; |
| 1646 | irq_clear_status_flags(chan->rx_irq, IRQ_DISABLE_UNLAZY); | ||
| 1643 | devm_free_irq(chan->dev, chan->rx_irq, chan); | 1647 | devm_free_irq(chan->dev, chan->rx_irq, chan); |
| 1644 | } | 1648 | } |
| 1645 | } | 1649 | } |