All of lore.kernel.org
 help / color / mirror / Atom feed
* [RFT][PATCH 1/2] irqchip: vt8500: Fix implementation for irq_ack and irq_mask
@ 2013-07-09  0:21 Axel Lin
  2013-07-09  0:33 ` [RFT][PATCH 2/2] irqchip: vt8500: Support 'rising and falling edge' trigger mode Axel Lin
  0 siblings, 1 reply; 2+ messages in thread
From: Axel Lin @ 2013-07-09  0:21 UTC (permalink / raw)
  To: Thomas Gleixner; +Cc: Tony Prisk, Alexey Charkov, linux-kernel

Current code sets both irq_ack and irq_mask callbacks to vt8500_irq_mask().
However, vt8500_irq_mask does not clear interrupt enable bit when the interrupt
trigger mode is edge trigger.

This patch moves the code clearing Interrupt Status Register bit to irq_ack().
irq_mask() always clear interrupt enable bit for all interrupt trigger mode.

According to the datasheet, the Interrupt Status Register is written one to
clear(Write 0 has no effect). So we don't need a read-modify-write operation
for clearing a bit in interrupt status register.

Signed-off-by: Axel Lin <axel.lin@ingics.com>
---
Hi Tony,
I don't have the hardware to test, just found this issue while reading the code.
I'd appreciate if you can review and test this patch serial.

Thanks,
Axel
 drivers/irqchip/irq-vt8500.c | 31 +++++++++++++++----------------
 1 file changed, 15 insertions(+), 16 deletions(-)

diff --git a/drivers/irqchip/irq-vt8500.c b/drivers/irqchip/irq-vt8500.c
index d970595..eb6d05a 100644
--- a/drivers/irqchip/irq-vt8500.c
+++ b/drivers/irqchip/irq-vt8500.c
@@ -81,25 +81,24 @@ struct vt8500_irq_data {
 static struct vt8500_irq_data intc[VT8500_INTC_MAX];
 static u32 active_cnt = 0;
 
-static void vt8500_irq_mask(struct irq_data *d)
+static void vt8500_irq_ack(struct irq_data *d)
 {
 	struct vt8500_irq_data *priv = d->domain->host_data;
 	void __iomem *base = priv->base;
 	void __iomem *stat_reg = base + VT8500_ICIS + (d->hwirq < 32 ? 0 : 4);
-	u8 edge, dctr;
-	u32 status;
-
-	edge = readb(base + VT8500_ICDC + d->hwirq) & VT8500_EDGE;
-	if (edge) {
-		status = readl(stat_reg);
-
-		status |= (1 << (d->hwirq & 0x1f));
-		writel(status, stat_reg);
-	} else {
-		dctr = readb(base + VT8500_ICDC + d->hwirq);
-		dctr &= ~VT8500_INT_ENABLE;
-		writeb(dctr, base + VT8500_ICDC + d->hwirq);
-	}
+
+	writel(1 << (d->hwirq & 0x1f), stat_reg);
+}
+
+static void vt8500_irq_mask(struct irq_data *d)
+{
+	struct vt8500_irq_data *priv = d->domain->host_data;
+	void __iomem *base = priv->base;
+	u8 dctr;
+
+	dctr = readb(base + VT8500_ICDC + d->hwirq);
+	dctr &= ~VT8500_INT_ENABLE;
+	writeb(dctr, base + VT8500_ICDC + d->hwirq);
 }
 
 static void vt8500_irq_unmask(struct irq_data *d)
@@ -145,7 +144,7 @@ static int vt8500_irq_set_type(struct irq_data *d, unsigned int flow_type)
 
 static struct irq_chip vt8500_irq_chip = {
 	.name = "vt8500",
-	.irq_ack = vt8500_irq_mask,
+	.irq_ack = vt8500_irq_ack,
 	.irq_mask = vt8500_irq_mask,
 	.irq_unmask = vt8500_irq_unmask,
 	.irq_set_type = vt8500_irq_set_type,
-- 
1.8.1.2




^ permalink raw reply related	[flat|nested] 2+ messages in thread

* [RFT][PATCH 2/2] irqchip: vt8500: Support 'rising and falling edge' trigger mode
  2013-07-09  0:21 [RFT][PATCH 1/2] irqchip: vt8500: Fix implementation for irq_ack and irq_mask Axel Lin
@ 2013-07-09  0:33 ` Axel Lin
  0 siblings, 0 replies; 2+ messages in thread
From: Axel Lin @ 2013-07-09  0:33 UTC (permalink / raw)
  To: Thomas Gleixner; +Cc: Tony Prisk, Alexey Charkov, linux-kernel

This chip supports below interrupt request trigger mode:

Destination Control Register:
BIT[5:4] Interrupt Request Trigger Mode.
        00: High level trigger
        01: Posedge trigger
        10: Negedge trigger
        11: Both posedge and negedge trigger

This patch adds support for setting 'posedge and negedge trigger' mode.

Signed-off-by: Axel Lin <axel.lin@ingics.com>
---
Current code does not correctly handle the case if a driver request irq with
"IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING" flag.
I'm not sure if we have such use case in current code.

 drivers/irqchip/irq-vt8500.c | 4 ++++
 1 file changed, 4 insertions(+)

diff --git a/drivers/irqchip/irq-vt8500.c b/drivers/irqchip/irq-vt8500.c
index eb6d05a..e040994 100644
--- a/drivers/irqchip/irq-vt8500.c
+++ b/drivers/irqchip/irq-vt8500.c
@@ -136,6 +136,10 @@ static int vt8500_irq_set_type(struct irq_data *d, unsigned int flow_type)
 		dctr |= VT8500_TRIGGER_RISING;
 		__irq_set_handler_locked(d->irq, handle_edge_irq);
 		break;
+	case IRQF_TRIGGER_FALLING | IRQF_TRIGGER_RISING:
+		dctr |= VT8500_EDGE;
+		__irq_set_handler_locked(d->irq, handle_edge_irq);
+		break;
 	}
 	writeb(dctr, base + VT8500_ICDC + d->hwirq);
 
-- 
1.8.1.2




^ permalink raw reply related	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2013-07-09  0:33 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2013-07-09  0:21 [RFT][PATCH 1/2] irqchip: vt8500: Fix implementation for irq_ack and irq_mask Axel Lin
2013-07-09  0:33 ` [RFT][PATCH 2/2] irqchip: vt8500: Support 'rising and falling edge' trigger mode Axel Lin

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.