[PATCH 1/2] gpio: xgene: add support to configure GPIO line as input, output or external IRQ pin

Y Vo yvo at apm.com
Fri Sep 11 02:22:11 PDT 2015


Add support to configure GPIO line as input, output or external IRQ pin.

Signed-off-by: Y Vo <yvo at apm.com>
---
 drivers/gpio/gpio-xgene-sb.c |   33 ++++++++++++++++++++++++++-------
 1 files changed, 26 insertions(+), 7 deletions(-)

diff --git a/drivers/gpio/gpio-xgene-sb.c b/drivers/gpio/gpio-xgene-sb.c
index d57068b..76b15e0 100644
--- a/drivers/gpio/gpio-xgene-sb.c
+++ b/drivers/gpio/gpio-xgene-sb.c
@@ -32,6 +32,8 @@
 
 #define XGENE_MAX_GPIO_DS		22
 #define XGENE_MAX_GPIO_DS_IRQ		6
+#define XGENE_GPIO8_HWIRQ		0x48
+#define XGENE_GPIO8_IDX			8
 
 #define GPIO_MASK(x)			(1U << ((x) % 32))
 
@@ -82,11 +84,19 @@ static int apm_gpio_sb_to_irq(struct gpio_chip *gc, u32 gpio)
 	return -ENXIO;
 }
 
+static int xgene_irq_to_line(u32 irq)
+{
+	u32 offset = irq_get_irq_data(irq)->hwirq - XGENE_GPIO8_HWIRQ;
+
+	return (offset < XGENE_MAX_GPIO_DS_IRQ) ?
+			(offset + XGENE_GPIO8_IDX) : -EINVAL;
+}
+
 static int xgene_gpio_sb_probe(struct platform_device *pdev)
 {
 	struct xgene_gpio_sb *priv;
 	u32 ret, i;
-	u32 default_lines[] = {0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D};
+	int virq, line;
 	struct resource *res;
 	void __iomem *regs;
 
@@ -109,20 +119,29 @@ static int xgene_gpio_sb_probe(struct platform_device *pdev)
 	priv->bgc.gc.to_irq = apm_gpio_sb_to_irq;
 	priv->bgc.gc.ngpio = XGENE_MAX_GPIO_DS;
 
-	priv->nirq = XGENE_MAX_GPIO_DS_IRQ;
-
 	priv->irq = devm_kzalloc(&pdev->dev, sizeof(u32) * XGENE_MAX_GPIO_DS,
 				   GFP_KERNEL);
 	if (!priv->irq)
 		return -ENOMEM;
 
-	for (i = 0; i < priv->nirq; i++) {
-		priv->irq[default_lines[i]] = platform_get_irq(pdev, i);
+	for (i = 0; i < XGENE_MAX_GPIO_DS_IRQ; i++) {
+		virq = platform_get_irq(pdev, i);
+		if (virq < 0)
+			break;
+		line = xgene_irq_to_line(virq);
+		if (line < XGENE_GPIO8_IDX)
+			break;
+		priv->irq[line] = virq;
 		xgene_gpio_set_bit(&priv->bgc, regs + MPA_GPIO_SEL_LO,
-                                   default_lines[i] * 2, 1);
-		xgene_gpio_set_bit(&priv->bgc, regs + MPA_GPIO_INT_LVL, i, 1);
+						line * 2, 1);
+		xgene_gpio_set_bit(&priv->bgc, regs + MPA_GPIO_INT_LVL,
+						(line - XGENE_GPIO8_IDX), 1);
+		dev_dbg(&pdev->dev,
+			"gpio line %d mapped as external irq pin\n", line);
 	}
 
+	priv->nirq = i;
+
 	platform_set_drvdata(pdev, priv);
 
 	ret = gpiochip_add(&priv->bgc.gc);
-- 
1.7.1




More information about the linux-arm-kernel mailing list