From patchwork Fri May 25 19:25:23 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Evan Green X-Patchwork-Id: 10428365 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id 2774E601D5 for ; Fri, 25 May 2018 19:26:00 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 12698297B1 for ; Fri, 25 May 2018 19:26:00 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 070E8297C2; Fri, 25 May 2018 19:26:00 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-7.8 required=2.0 tests=BAYES_00,DKIM_SIGNED, MAILING_LIST_MULTI, RCVD_IN_DNSWL_HI, T_DKIM_INVALID autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 65E9C297B1 for ; Fri, 25 May 2018 19:25:59 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S967811AbeEYTZ6 (ORCPT ); Fri, 25 May 2018 15:25:58 -0400 Received: from mail-pf0-f194.google.com ([209.85.192.194]:41976 "EHLO mail-pf0-f194.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S967587AbeEYTZ5 (ORCPT ); Fri, 25 May 2018 15:25:57 -0400 Received: by mail-pf0-f194.google.com with SMTP id v63-v6so3016922pfk.8 for ; Fri, 25 May 2018 12:25:57 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=chromium.org; s=google; h=from:to:cc:subject:date:message-id; bh=V7KAjF5Y29AdmMqspPtz0qPOYpkHa3DpWJFeEJBhifo=; b=BZ32yBCqNVbFijrqvuLV/LYCFW7boFDTTBnuZ2nfhwnS60qQmzKd3GVquPZHyW3f+8 GsoUVxhOuaNRpTSKUwOalnhp6oeziqm4YlTL0j68wV8KMgJ/RACoy5ZBuRr7ZepEvY4C Rumdm1v+4h1cZIShSaNfNrmDktpNvlfxMulOA= X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id; bh=V7KAjF5Y29AdmMqspPtz0qPOYpkHa3DpWJFeEJBhifo=; b=I/YgxCGfuholGEsfuriIqurh+yWsRGq8002W8CQOh/pgWHPUVVuVdw2qevr3vzWFD2 YXvFiLVtbrTVk90pAG/ZJjVWyhDGV5tFJC7ZsRwIQp93RIt0y7lMF0DHOHooV2NbMGzb gWvbBbPzppX4rEjhkpD+HIX6usm5muslInfXjL1XIaPSwNE+vn5LxWpNQDHxdv6eMF6d TwwaLlfQ1jgh/3gDa1ofza15DZm9/3iO0gTZmEoMJlcvnYO2iNhsQdFs56CivJMvPoVr wNJa4zh9BWWXI94TaFofeXsgFZ4GwAF/q5NlF5iRc5Ts8VdzKTlZL+341ZJdXKrD5EHz KVlA== X-Gm-Message-State: ALKqPwc7PkwlnTvsrW6DybSbKz1no1lU1aLCLjgvGNjl7lseEzoFznPE NcBoQ9GG6FMbj2mleQ89fmXnjqospSo= X-Google-Smtp-Source: AB8JxZo6B+lf04ygux7zQqT9fp8hVKGMxkqxxISMebrbhjZVHFF6bDLbIC7It+C7AmuMFoZ2oiq9pQ== X-Received: by 2002:a62:7105:: with SMTP id m5-v6mr3714519pfc.167.1527276356847; Fri, 25 May 2018 12:25:56 -0700 (PDT) Received: from evgreen2.mtv.corp.google.com ([2620:0:1000:1511:116f:8bf3:133b:f7fd]) by smtp.gmail.com with ESMTPSA id b3-v6sm43639540pff.132.2018.05.25.12.25.55 (version=TLS1_2 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Fri, 25 May 2018 12:25:55 -0700 (PDT) From: Evan Green To: Ulf Hansson , Adrian Hunter , Andy Shevchenko , Douglas Anderson , linux-mmc@vger.kernel.org, linux-kernel@vger.kernel.org Cc: Evan Green Subject: [PATCH v2] mmc: Allow non-sleeping GPIO cd Date: Fri, 25 May 2018 12:25:23 -0700 Message-Id: <20180525192523.204873-1-evgreen@chromium.org> X-Mailer: git-send-email 2.13.5 Sender: linux-mmc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-mmc@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP This change uses the appropriate _cansleep or non-sleeping API for reading GPIO card detect state. This allows users with GPIOs that never sleep to avoid a warning when certain quirks are present. The sdhci controller has an SDHCI_QUIRK_NO_CARD_NO_RESET, which indicates that a controller will not reset properly if no card is inserted. With this quirk enabled, mmc_get_cd_gpio is called in several places with a spinlock held and interrupts disabled. gpiod_get_raw_value_cansleep is not happy with this situation, and throws out a warning. For boards that a) use controllers that have this quirk, and b) wire card detect up to a GPIO that doesn't sleep, this is a spurious warning. This change silences that warning, at the cost of pushing this problem down to users that have sleeping GPIOs and controllers with this quirk. Signed-off-by: Evan Green --- Changes since v1: - Style fixups as suggested by Andy This is my initial solution to the warning I was trying to face down in my previous RFC [1]. Upsides of this solution is it manages to avoid the warning in places where the warning doesn't apply, and is low-risk. Other approaches I considered: 1. Changing sdhci_get_cd to reach through mmc and get the GPIO value directly (without sleeping) rather than calling mmc_gpio_get_cd, which uses the cansleep functions. I didn't love this because a) it seemed ugly to be reaching into mmc_host like that and b) I'd have to duplicate the logic in mmc_gpio_get_cd, which seemed brittle. 2. Using mmc_gpio_set_cd_isr to record when the card detect pin changes, and then in sdhci_do_reset we wouldn't actually need to get CD state, just look at the cached value. This seemed risky to me since it would affect all sdhci controllers, and I don't know that everybody using gpio-cd can do interrupts on their pins. 3. Adding mmc_gpio_get_cd_nosleep(). That one's still doable if preferred, but I'd have to give some thought to when sdhci wires up to which one. I'm up for other suggestions. This one most just seemed like the best first stab of minimally addressing the warning without rocking the boat otherwise. [1] https://patchwork.kernel.org/patch/10374633/ --- drivers/mmc/core/slot-gpio.c | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-) diff --git a/drivers/mmc/core/slot-gpio.c b/drivers/mmc/core/slot-gpio.c index 31f7dbb15668..1ca8220690f2 100644 --- a/drivers/mmc/core/slot-gpio.c +++ b/drivers/mmc/core/slot-gpio.c @@ -76,15 +76,22 @@ EXPORT_SYMBOL(mmc_gpio_get_ro); int mmc_gpio_get_cd(struct mmc_host *host) { struct mmc_gpio *ctx = host->slot.handler_priv; + int cansleep; if (!ctx || !ctx->cd_gpio) return -ENOSYS; - if (ctx->override_cd_active_level) - return !gpiod_get_raw_value_cansleep(ctx->cd_gpio) ^ - !!(host->caps2 & MMC_CAP2_CD_ACTIVE_HIGH); + cansleep = gpiod_cansleep(ctx->cd_gpio); + if (ctx->override_cd_active_level) { + int value = cansleep ? + gpiod_get_raw_value_cansleep(ctx->cd_gpio) : + gpiod_get_raw_value(ctx->cd_gpio); + return !value ^ !!(host->caps2 & MMC_CAP2_CD_ACTIVE_HIGH); + } - return gpiod_get_value_cansleep(ctx->cd_gpio); + return cansleep ? + gpiod_get_value_cansleep(ctx->cd_gpio) : + gpiod_get_value(ctx->cd_gpio); } EXPORT_SYMBOL(mmc_gpio_get_cd);