From patchwork Sun Jul 10 13:14:34 2011 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Ido Yariv X-Patchwork-Id: 961312 Received: from merlin.infradead.org (merlin.infradead.org [205.233.59.134]) by demeter2.kernel.org (8.14.4/8.14.4) with ESMTP id p6ADFupj021227 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=NO) for ; Sun, 10 Jul 2011 13:16:17 GMT Received: from canuck.infradead.org ([2001:4978:20e::1]) by merlin.infradead.org with esmtps (Exim 4.76 #1 (Red Hat Linux)) id 1Qftqe-0004q0-Cp; Sun, 10 Jul 2011 13:15:00 +0000 Received: from localhost ([127.0.0.1] helo=canuck.infradead.org) by canuck.infradead.org with esmtp (Exim 4.76 #1 (Red Hat Linux)) id 1Qftqd-0006iO-Vl; Sun, 10 Jul 2011 13:15:00 +0000 Received: from mail-wy0-f177.google.com ([74.125.82.177]) by canuck.infradead.org with esmtps (Exim 4.76 #1 (Red Hat Linux)) id 1Qftqa-0006hZ-7A for linux-arm-kernel@lists.infradead.org; Sun, 10 Jul 2011 13:14:57 +0000 Received: by wyf23 with SMTP id 23so2693126wyf.36 for ; Sun, 10 Jul 2011 06:14:52 -0700 (PDT) Received: by 10.216.79.74 with SMTP id h52mr3854105wee.33.1310303691989; Sun, 10 Jul 2011 06:14:51 -0700 (PDT) Received: from localhost.localdomain (46-116-74-128.bb.netvision.net.il [46.116.74.128]) by mx.google.com with ESMTPS id g2sm6388912weg.14.2011.07.10.06.14.49 (version=TLSv1/SSLv3 cipher=OTHER); Sun, 10 Jul 2011 06:14:51 -0700 (PDT) From: Ido Yariv To: davinci-linux-open-source@linux.davincidsp.com, linux-arm-kernel@lists.infradead.org, linux-mmc@vger.kernel.org Subject: [PATCH v2 1/6] arm: davinci: Fix low level gpio irq handlers' argument Date: Sun, 10 Jul 2011 16:14:34 +0300 Message-Id: <1310303679-17936-2-git-send-email-ido@wizery.com> X-Mailer: git-send-email 1.7.4.1 In-Reply-To: <1310303679-17936-1-git-send-email-ido@wizery.com> References: <1310303679-17936-1-git-send-email-ido@wizery.com> X-CRM114-Version: 20090807-BlameThorstenAndJenny ( TRE 0.7.6 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20110710_091456_435277_A23C3679 X-CRM114-Status: GOOD ( 15.20 ) X-Spam-Score: -0.7 (/) X-Spam-Report: SpamAssassin version 3.3.1 on canuck.infradead.org summary: Content analysis details: (-0.7 points) pts rule name description ---- ---------------------- -------------------------------------------------- -0.7 RCVD_IN_DNSWL_LOW RBL: Sender listed at http://www.dnswl.org/, low trust [74.125.82.177 listed in list.dnswl.org] Cc: Thomas Gleixner , Ido Yariv X-BeenThere: linux-arm-kernel@lists.infradead.org X-Mailman-Version: 2.1.12 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , MIME-Version: 1.0 Sender: linux-arm-kernel-bounces@lists.infradead.org Errors-To: linux-arm-kernel-bounces+patchwork-linux-arm=patchwork.kernel.org@lists.infradead.org X-Greylist: IP, sender and recipient auto-whitelisted, not delayed by milter-greylist-4.2.6 (demeter2.kernel.org [140.211.167.43]); Sun, 10 Jul 2011 13:16:17 +0000 (UTC) Commit 7416401 ("arm: davinci: Fix fallout from generic irq chip conversion") introduced a bug, causing low level interrupt handlers to get a bogus irq number as an argument. The gpio irq handler falsely assumes that the handler data is the irq base number and that is no longer true. Fix this by converting gpio_irq_handler's bank_irq argument to the corresponding irq base number. Signed-off-by: Ido Yariv CC: Thomas Gleixner --- arch/arm/mach-davinci/gpio.c | 32 ++++++++++++++++++++++++++++---- 1 files changed, 28 insertions(+), 4 deletions(-) diff --git a/arch/arm/mach-davinci/gpio.c b/arch/arm/mach-davinci/gpio.c index e722139..ff43e2a 100644 --- a/arch/arm/mach-davinci/gpio.c +++ b/arch/arm/mach-davinci/gpio.c @@ -249,16 +249,40 @@ static struct irq_chip gpio_irqchip = { .flags = IRQCHIP_SET_TYPE_MASKED, }; +static inline int bankirq_to_irqbase(unsigned int bank_irq) +{ + int gpio; + int index; + + /* Each irq bank consists of up to 16 irqs */ + gpio = 16 * (bank_irq - davinci_soc_info.gpio_irq); + + /* Each controller controls 32 GPIOs */ + index = gpio / 32; + + if (unlikely(!davinci_soc_info.gpio_ctlrs)) + return -EINVAL; + + if (unlikely(index >= davinci_soc_info.gpio_ctlrs_num)) + return -EINVAL; + + return davinci_soc_info.gpio_ctlrs[index].irq_base; +} + static void -gpio_irq_handler(unsigned irq, struct irq_desc *desc) +gpio_irq_handler(unsigned bank_irq, struct irq_desc *desc) { struct davinci_gpio_regs __iomem *g; u32 mask = 0xffff; + int irqbase = bankirq_to_irqbase(bank_irq); + + if (unlikely(irqbase < 0)) + return; g = (__force struct davinci_gpio_regs __iomem *) irq_desc_get_handler_data(desc); /* we only care about one bank */ - if (irq & 1) + if (bank_irq & 1) mask <<= 16; /* temporarily mask (level sensitive) parent IRQ */ @@ -274,11 +298,11 @@ gpio_irq_handler(unsigned irq, struct irq_desc *desc) if (!status) break; __raw_writel(status, &g->intstat); - if (irq & 1) + if (bank_irq & 1) status >>= 16; /* now demux them to the right lowlevel handler */ - n = (int)irq_get_handler_data(irq); + n = irqbase; while (status) { res = ffs(status); n += res;