From patchwork Wed Jun 15 11:15:19 2011 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Shawn Guo X-Patchwork-Id: 881672 Received: from merlin.infradead.org (merlin.infradead.org [205.233.59.134]) by demeter1.kernel.org (8.14.4/8.14.4) with ESMTP id p5FBBAgZ014043 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=NO) for ; Wed, 15 Jun 2011 11:11:31 GMT Received: from canuck.infradead.org ([2001:4978:20e::1]) by merlin.infradead.org with esmtps (Exim 4.76 #1 (Red Hat Linux)) id 1QWnzk-0004XM-5P; Wed, 15 Jun 2011 11:10:50 +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 1QWnzi-0006yl-0n; Wed, 15 Jun 2011 11:10:46 +0000 Received: from tx2ehsobe004.messaging.microsoft.com ([65.55.88.14] helo=TX2EHSOBE009.bigfish.com) by canuck.infradead.org with esmtps (Exim 4.76 #1 (Red Hat Linux)) id 1QWnzH-0006t3-GG for linux-arm-kernel@lists.infradead.org; Wed, 15 Jun 2011 11:10:21 +0000 Received: from mail178-tx2-R.bigfish.com (10.9.14.241) by TX2EHSOBE009.bigfish.com (10.9.40.29) with Microsoft SMTP Server id 14.1.225.22; Wed, 15 Jun 2011 11:10:15 +0000 Received: from mail178-tx2 (localhost.localdomain [127.0.0.1]) by mail178-tx2-R.bigfish.com (Postfix) with ESMTP id 4CCC0D18397; Wed, 15 Jun 2011 11:10:15 +0000 (UTC) X-SpamScore: 0 X-BigFish: VS0(zzzz1202hzz8275bh8275dhz2dh87h2a8h668h839h63h) X-Spam-TCS-SCL: 2:0 X-Forefront-Antispam-Report: CIP:70.37.183.190; KIP:(null); UIP:(null); IPVD:NLI; H:mail.freescale.net; RD:none; EFVD:NLI X-FB-DOMAIN-IP-MATCH: fail Received: from mail178-tx2 (localhost.localdomain [127.0.0.1]) by mail178-tx2 (MessageSwitch) id 1308136200219613_13906; Wed, 15 Jun 2011 11:10:00 +0000 (UTC) Received: from TX2EHSMHS023.bigfish.com (unknown [10.9.14.245]) by mail178-tx2.bigfish.com (Postfix) with ESMTP id 177321000052; Wed, 15 Jun 2011 11:10:00 +0000 (UTC) Received: from mail.freescale.net (70.37.183.190) by TX2EHSMHS023.bigfish.com (10.9.99.123) with Microsoft SMTP Server (TLS) id 14.1.225.22; Wed, 15 Jun 2011 11:09:55 +0000 Received: from az33smr02.freescale.net (10.64.34.200) by 039-SN1MMR1-001.039d.mgd.msft.net (10.84.1.13) with Microsoft SMTP Server id 14.1.289.8; Wed, 15 Jun 2011 06:09:54 -0500 Received: from S2100-06.ap.freescale.net (S2100-06.ap.freescale.net [10.192.242.125]) by az33smr02.freescale.net (8.13.1/8.13.0) with ESMTP id p5FB9l3F013936; Wed, 15 Jun 2011 06:09:51 -0500 (CDT) From: Shawn Guo To: Subject: [PATCH v2 1/4] mmc: sdhci: fix interrupt storm from card detection Date: Wed, 15 Jun 2011 19:15:19 +0800 Message-ID: <1308136522-3403-2-git-send-email-shawn.guo@linaro.org> X-Mailer: git-send-email 1.7.4.1 In-Reply-To: <1308136522-3403-1-git-send-email-shawn.guo@linaro.org> References: <1308136522-3403-1-git-send-email-shawn.guo@linaro.org> MIME-Version: 1.0 X-OriginatorOrg: sigmatel.com X-CRM114-Version: 20090807-BlameThorstenAndJenny ( TRE 0.7.6 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20110615_071019_773984_D1F56F1E X-CRM114-Status: GOOD ( 17.23 ) X-Spam-Score: -2.3 (--) X-Spam-Report: SpamAssassin version 3.3.1 on canuck.infradead.org summary: Content analysis details: (-2.3 points) pts rule name description ---- ---------------------- -------------------------------------------------- -2.3 RCVD_IN_DNSWL_MED RBL: Sender listed at http://www.dnswl.org/, medium trust [65.55.88.14 listed in list.dnswl.org] Cc: Shawn Guo , Eric Benard , Pavel Machek , patches@linaro.org, Wolfram Sang , linux-arm-kernel@lists.infradead.org, kernel@pengutronix.de, Chris Ball , Arnaud Patard 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: , 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 (demeter1.kernel.org [140.211.167.41]); Wed, 15 Jun 2011 11:11:31 +0000 (UTC) The issue was initially found by Eric Benard as below. http://permalink.gmane.org/gmane.linux.ports.arm.kernel/108031 Not sure about other SDHCI based controller, but on Freescale eSDHC, the SDHCI_INT_CARD_INSERT bits will be immediately set again when it gets cleared, if a card is inserted. The driver need to mask the irq to prevent interrupt storm which will freeze the system. And the SDHCI_INT_CARD_REMOVE gets the same situation. The patch fixes the problem based on the initial idea from Eric Benard. Signed-off-by: Shawn Guo Cc: Eric Benard --- drivers/mmc/host/sdhci.c | 23 ++++++++++++++++++++--- 1 files changed, 20 insertions(+), 3 deletions(-) diff --git a/drivers/mmc/host/sdhci.c b/drivers/mmc/host/sdhci.c index 91d9892..0dd10e4 100644 --- a/drivers/mmc/host/sdhci.c +++ b/drivers/mmc/host/sdhci.c @@ -2154,13 +2154,30 @@ static irqreturn_t sdhci_irq(int irq, void *dev_id) mmc_hostname(host->mmc), intmask); if (intmask & (SDHCI_INT_CARD_INSERT | SDHCI_INT_CARD_REMOVE)) { + u32 present = sdhci_readl(host, SDHCI_PRESENT_STATE) & + SDHCI_CARD_PRESENT; + + /* + * There is a observation on i.mx esdhc. INSERT bit will be + * immediately set again when it gets cleared, if a card is + * inserted. We have to mask the irq to prevent interrupt + * storm which will freeze the system. And the REMOVE gets + * the same situation. + * + * More testing are needed here to ensure it works for other + * platforms though. + */ + sdhci_mask_irqs(host, present ? SDHCI_INT_CARD_INSERT : + SDHCI_INT_CARD_REMOVE); + sdhci_unmask_irqs(host, present ? SDHCI_INT_CARD_REMOVE : + SDHCI_INT_CARD_INSERT); + sdhci_writel(host, intmask & (SDHCI_INT_CARD_INSERT | - SDHCI_INT_CARD_REMOVE), SDHCI_INT_STATUS); + SDHCI_INT_CARD_REMOVE), SDHCI_INT_STATUS); + intmask &= ~(SDHCI_INT_CARD_INSERT | SDHCI_INT_CARD_REMOVE); tasklet_schedule(&host->card_tasklet); } - intmask &= ~(SDHCI_INT_CARD_INSERT | SDHCI_INT_CARD_REMOVE); - if (intmask & SDHCI_INT_CMD_MASK) { sdhci_writel(host, intmask & SDHCI_INT_CMD_MASK, SDHCI_INT_STATUS);