From patchwork Thu Apr 6 14:40:10 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: William Breathitt Gray X-Patchwork-Id: 13203545 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id 53BE6C761A6 for ; Thu, 6 Apr 2023 14:42:29 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S238544AbjDFOm1 (ORCPT ); Thu, 6 Apr 2023 10:42:27 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:43154 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S238150AbjDFOmG (ORCPT ); Thu, 6 Apr 2023 10:42:06 -0400 Received: from mail-oi1-x22b.google.com (mail-oi1-x22b.google.com [IPv6:2607:f8b0:4864:20::22b]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 67133B768 for ; Thu, 6 Apr 2023 07:40:34 -0700 (PDT) Received: by mail-oi1-x22b.google.com with SMTP id r16so29137122oij.5 for ; Thu, 06 Apr 2023 07:40:34 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; t=1680792033; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=QwrW8zLdNa13eS+GI7R48Yjhq4tM8k3jsY8GnpkuSw0=; b=ET29C6Lpq8H1bupcLWpddJ6+WJMTZH14dq8GvOLwp89jjim1Y3wOQbN1KqFe/QpqPy be/SeTJYazGAwS7ghu4jp7LrOVKD2d4AaCEbEbnVH9aC9Id6cSyePAk+O3pWcwkdtGP8 hX9A1/oeThB47yf06fReeoYujLwL7my+G/S3t/vAOcU1Pko10MoIJGQib395m8yK5eVv JwxDASIU3jjLNyC3fRyxpePBnqpQkss9KO3phn1JTpZXqrFxg6p5h6hc2Nb8FaBvel6A gDTkiNq38ls117KNKCBhztRm5K9vpZQg/Cb/tVj08vooFX9lr00x3FhUWE8llk50q2zc wqrA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; t=1680792033; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=QwrW8zLdNa13eS+GI7R48Yjhq4tM8k3jsY8GnpkuSw0=; b=xVW1DaCxOsjTjg01COKLh1PAaPw6ZvusgQAnf2TWHtFirz06Lg3Ztxan7wzQZL06UH /yry34GcO5hi2f5zAie4KB5viVuIO4/XPnVVeqkwSrF6knQmZwWAaaYIFp5vEHLtpV/i HS1KzXAQqLx/4lTO0VmTf4NdY19X1tzIgVW8H5kJMb+K7Qg8hcjxQ/yO3Xo/p1Xio3hD SdU4j9QWk/I6OynkQBg6OieZyVZCBrqmKMieUmkd+0qzONFBZWDjmizvZ49r1Qbm+GBB c6Wm4XPkt8qr4qvtrE++yxOhG9fiD8bvX0Kuy+KQQ9WtWyZv7ntc9o/JFJz+2LYNvBeV 05qQ== X-Gm-Message-State: AAQBX9fzhP5jhQ+gpSdzKLreBidrfNcClXU4tXQbpr3ej6VARrXsRrCI Rwbn1ZssnuJY93D6RVgDNq9+eQ== X-Google-Smtp-Source: AKy350bCG0vtWtwYel0t3Kxrv4Y3pHI0ty1lJDbA7pUA7EgHrAAKXj9ot3YBX1+UPSmWRV0LbsvSuA== X-Received: by 2002:a05:6808:614:b0:387:715e:56b8 with SMTP id y20-20020a056808061400b00387715e56b8mr4773349oih.56.1680792033707; Thu, 06 Apr 2023 07:40:33 -0700 (PDT) Received: from fedora.attlocal.net (69-109-179-158.lightspeed.dybhfl.sbcglobal.net. [69.109.179.158]) by smtp.gmail.com with ESMTPSA id q7-20020acaf207000000b0037d7f4eb7e8sm726209oih.31.2023.04.06.07.40.32 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Thu, 06 Apr 2023 07:40:33 -0700 (PDT) From: William Breathitt Gray To: Jonathan Cameron , Lars-Peter Clausen Cc: linux-iio@vger.kernel.org, linux-kernel@vger.kernel.org, Andy Shevchenko , William Breathitt Gray Subject: [PATCH v5 1/6] iio: addac: stx104: Fix race condition for stx104_write_raw() Date: Thu, 6 Apr 2023 10:40:10 -0400 Message-Id: X-Mailer: git-send-email 2.39.2 In-Reply-To: References: MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-iio@vger.kernel.org The priv->chan_out_states array and actual DAC value can become mismatched if stx104_write_raw() is called concurrently. Prevent such a race condition by utilizing a mutex. Fixes: 97a445dad37a ("iio: Add IIO support for the DAC on the Apex Embedded Systems STX104") Signed-off-by: William Breathitt Gray --- Changes in v5: none drivers/iio/addac/stx104.c | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/drivers/iio/addac/stx104.c b/drivers/iio/addac/stx104.c index e45b70aa5bb7..4239aafe42fc 100644 --- a/drivers/iio/addac/stx104.c +++ b/drivers/iio/addac/stx104.c @@ -15,6 +15,7 @@ #include #include #include +#include #include #include @@ -69,10 +70,12 @@ struct stx104_reg { /** * struct stx104_iio - IIO device private data structure + * @lock: synchronization lock to prevent I/O race conditions * @chan_out_states: channels' output states * @reg: I/O address offset for the device registers */ struct stx104_iio { + struct mutex lock; unsigned int chan_out_states[STX104_NUM_OUT_CHAN]; struct stx104_reg __iomem *reg; }; @@ -178,9 +181,12 @@ static int stx104_write_raw(struct iio_dev *indio_dev, if ((unsigned int)val > 65535) return -EINVAL; + mutex_lock(&priv->lock); + priv->chan_out_states[chan->channel] = val; iowrite16(val, &priv->reg->dac[chan->channel]); + mutex_unlock(&priv->lock); return 0; } return -EINVAL; @@ -351,6 +357,8 @@ static int stx104_probe(struct device *dev, unsigned int id) indio_dev->name = dev_name(dev); + mutex_init(&priv->lock); + /* configure device for software trigger operation */ iowrite8(0, &priv->reg->acr); From patchwork Thu Apr 6 14:40:11 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: William Breathitt Gray X-Patchwork-Id: 13203546 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id 32678C77B6F for ; Thu, 6 Apr 2023 14:42:31 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S239377AbjDFOma (ORCPT ); Thu, 6 Apr 2023 10:42:30 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:42480 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S236627AbjDFOmJ (ORCPT ); Thu, 6 Apr 2023 10:42:09 -0400 Received: from mail-oi1-x232.google.com (mail-oi1-x232.google.com [IPv6:2607:f8b0:4864:20::232]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 73F8BB456 for ; Thu, 6 Apr 2023 07:40:35 -0700 (PDT) Received: by mail-oi1-x232.google.com with SMTP id w133so29220382oib.1 for ; Thu, 06 Apr 2023 07:40:35 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; t=1680792034; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=/VAaI37UUMqujz98kbcVgbWBFxRUSTxumyIYUkuTwcc=; b=uJVnn/Jfr+TJwzOL9C4qjEv/Uo0+lzKmZ2RFC2vCBh+UeCVjgKNJpI3Mjs9o4xtWtC Kk5X4jO3NKGFNLq2fLzyVmA8etXFiLM/IX+RZ654JQ2GujskNzmlWXUyYKat5OIU+gGy +7xpaWVI0Y6X2O3kG/St+h0N8ofi/2Ml1jSm7fKbIxAoy1hzfsabAFTxoLjUV49pvUiE GW6R3Oc2rv/gtIM5fDbrA1yFeATw5BXz95Lat99blrO2FI4HHMLUcVRXlGhYKnJkoIuD GxJIWxIKuMToCHFe7ngjNaNigsoaHapTzN6pCUfS3IPwNFzTKAGhAfS9/3+Z5yWXgMqk 67mg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; t=1680792034; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=/VAaI37UUMqujz98kbcVgbWBFxRUSTxumyIYUkuTwcc=; b=mY5YYabvGVzMndb583MmS8BS8zozvpxt6sGI529iQgKfS7F9RSikMGPl9J7I3y07y6 /e7dw4AwUUzLtpurOp70HtQnFqaw8RJnXyuYE2VqmKrZ7CPxiHN0DOUOJ9hk7HfISu2D un0fA9ZlAtJjCy9O2qnrtMswD3y9LJ1kU6ICesr73bQPP6/I+o47lIknI3zVHap+PuOx ETf2HHrnXOlC8GjR3kmxq0Kgq9MgicikAe+nVAITLDn1574YqVISHGNINlXmqYZ4yxLQ om93H7oukRNYGyoztgOSiaGg4Jm94L2z+UnlGjqTvTzqRvjByHD8iJrNkADXipayYQ/q Hkng== X-Gm-Message-State: AAQBX9eCi5B/yMzzgErM0m+uLJ7qpvqvg4+jViA1QivzdDvcFjZ+ePgl wgXd3etPPgTYPC0A8kE9/U8GPQ== X-Google-Smtp-Source: AKy350b7bQVcppxgdKHQbyzF/mFoW8VEbJHgqp0obT7UjSjkp9f1/A810fJ2G0K0IFYxXUW5yw+PJw== X-Received: by 2002:a05:6808:1912:b0:387:1e85:d1ae with SMTP id bf18-20020a056808191200b003871e85d1aemr5819223oib.18.1680792034597; Thu, 06 Apr 2023 07:40:34 -0700 (PDT) Received: from fedora.attlocal.net (69-109-179-158.lightspeed.dybhfl.sbcglobal.net. [69.109.179.158]) by smtp.gmail.com with ESMTPSA id q7-20020acaf207000000b0037d7f4eb7e8sm726209oih.31.2023.04.06.07.40.33 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Thu, 06 Apr 2023 07:40:34 -0700 (PDT) From: William Breathitt Gray To: Jonathan Cameron , Lars-Peter Clausen Cc: linux-iio@vger.kernel.org, linux-kernel@vger.kernel.org, Andy Shevchenko , William Breathitt Gray Subject: [PATCH v5 2/6] iio: addac: stx104: Fix race condition when converting analog-to-digital Date: Thu, 6 Apr 2023 10:40:11 -0400 Message-Id: <2ae5e40eed5006ca735e4c12181a9ff5ced65547.1680790580.git.william.gray@linaro.org> X-Mailer: git-send-email 2.39.2 In-Reply-To: References: MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-iio@vger.kernel.org The ADC conversion procedure requires several device I/O operations performed in a particular sequence. If stx104_read_raw() is called concurrently, the ADC conversion procedure could be clobbered. Prevent such a race condition by utilizing a mutex. Fixes: 4075a283ae83 ("iio: stx104: Add IIO support for the ADC channels") Signed-off-by: William Breathitt Gray --- Changes in v5: none drivers/iio/addac/stx104.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/drivers/iio/addac/stx104.c b/drivers/iio/addac/stx104.c index 4239aafe42fc..8730b79e921c 100644 --- a/drivers/iio/addac/stx104.c +++ b/drivers/iio/addac/stx104.c @@ -117,6 +117,8 @@ static int stx104_read_raw(struct iio_dev *indio_dev, return IIO_VAL_INT; } + mutex_lock(&priv->lock); + /* select ADC channel */ iowrite8(chan->channel | (chan->channel << 4), ®->achan); @@ -127,6 +129,8 @@ static int stx104_read_raw(struct iio_dev *indio_dev, while (ioread8(®->cir_asr) & BIT(7)); *val = ioread16(®->ssr_ad); + + mutex_unlock(&priv->lock); return IIO_VAL_INT; case IIO_CHAN_INFO_OFFSET: /* get ADC bipolar/unipolar configuration */ From patchwork Thu Apr 6 14:40:12 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: William Breathitt Gray X-Patchwork-Id: 13203547 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id C6496C76196 for ; Thu, 6 Apr 2023 14:42:32 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S237148AbjDFOmb (ORCPT ); Thu, 6 Apr 2023 10:42:31 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:43100 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S239025AbjDFOmJ (ORCPT ); Thu, 6 Apr 2023 10:42:09 -0400 Received: from mail-oo1-xc33.google.com (mail-oo1-xc33.google.com [IPv6:2607:f8b0:4864:20::c33]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 7D6F3BB94 for ; Thu, 6 Apr 2023 07:40:36 -0700 (PDT) Received: by mail-oo1-xc33.google.com with SMTP id f7-20020a4ab647000000b0054101f316c7so2775114ooo.13 for ; Thu, 06 Apr 2023 07:40:36 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; t=1680792035; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=T77DZLgcuvZGhTCXvpAiez5W7bAjrquGewZGCvMql+g=; b=YwIEBxMVzAo6ze8vKzbjcXJdJTuZ047xC9x1gnqtINolu0BWghermplLZ32osLEoEt obEby0llRPohdk4+U+BhveUYpj6WFZ7xQ0RbMgUaI4y7+uohndddh+vPJJ9O3poK7Rpl aiHiswTYiKGbv15cmieOo9kdxW6DnlCd9ojK9lH9xXM7avTPqnv6wK2j7zYY0xHevp/T x7E6e57R1qQoE14eL+yNcKNJcgqgxFwyz3aCnPqkKbU0yXKekPNtfzYyUjmP4uBTLoDi Nx6rLgiUzM7WF/oNmZcQXzxHXMWC8SvlpkvYD/fb7EZxXxuoP/PV6XFUWx4wK+caCln8 zlKg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; t=1680792035; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=T77DZLgcuvZGhTCXvpAiez5W7bAjrquGewZGCvMql+g=; b=El2fMrTg/y3F2CDVb8Gd3c/t3UX9N37zfF0D/QYe/S48WoMNCdJBgFQZOzaqiiQiVR FWpAn4Sh/x4EZCewwvigw13Ie1IbdBOlek56HNedBN8fvSeo7hNS0zU7maYjeyrQFLRe x2p94+0O8opqGuS62XBP63n1RLQzvR5j8lefGMrcv3VdIalU7J+uhDEVIvxJuNvGn8nT F9ESH3P7ps9jrsZGLOpBFrwFiXQ3879It5n6gI/30/uuevqPM4YQRjpLgo/lH3uB0Gx9 puW86OQtajBw/5kP+lyzGwJG1cN1jPxwYp6d9ERDl9DgnD5izRE3pqBzEYYTGV2vSNy5 EBeA== X-Gm-Message-State: AAQBX9cehB4FVqwEXbseyKrlyxc6JQeKaBlqu5tNIevO7d5ZTpwrMQft 8UfHJQKUPSXKdAE+/hL5/UugvQ== X-Google-Smtp-Source: AKy350akILD0OhGKfUUaCFpXEw+5BRBBcj8pfP0bB7fbj9sbK9VTS5qG5SCeZpVqb602yozzLWg/0w== X-Received: by 2002:a4a:3383:0:b0:525:4058:2fcd with SMTP id q125-20020a4a3383000000b0052540582fcdmr882877ooq.1.1680792035728; Thu, 06 Apr 2023 07:40:35 -0700 (PDT) Received: from fedora.attlocal.net (69-109-179-158.lightspeed.dybhfl.sbcglobal.net. [69.109.179.158]) by smtp.gmail.com with ESMTPSA id q7-20020acaf207000000b0037d7f4eb7e8sm726209oih.31.2023.04.06.07.40.34 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Thu, 06 Apr 2023 07:40:35 -0700 (PDT) From: William Breathitt Gray To: Jonathan Cameron , Lars-Peter Clausen Cc: linux-iio@vger.kernel.org, linux-kernel@vger.kernel.org, Andy Shevchenko , William Breathitt Gray Subject: [PATCH v5 3/6] iio: addac: stx104: Use define rather than hardcoded limit for write val Date: Thu, 6 Apr 2023 10:40:12 -0400 Message-Id: <4c9f4f1b4a270d133be70c82a091351b531b5e3e.1680790580.git.william.gray@linaro.org> X-Mailer: git-send-email 2.39.2 In-Reply-To: References: MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-iio@vger.kernel.org The DAC register is 16 bits wide, so the value passed by write_raw() should be checked against that limit. Rather than hardcoding the 16-bit maximum value limit, use a define to improve readability and make the intention of the code clearer. The explicit cast is also avoided by instead explicitly checking for negative values. Suggested-by: Andy Shevchenko Signed-off-by: William Breathitt Gray --- drivers/iio/addac/stx104.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/iio/addac/stx104.c b/drivers/iio/addac/stx104.c index 8730b79e921c..0ed5f71b18cb 100644 --- a/drivers/iio/addac/stx104.c +++ b/drivers/iio/addac/stx104.c @@ -13,6 +13,7 @@ #include #include #include +#include #include #include #include @@ -181,8 +182,7 @@ static int stx104_write_raw(struct iio_dev *indio_dev, return 0; case IIO_CHAN_INFO_RAW: if (chan->output) { - /* DAC can only accept up to a 16-bit value */ - if ((unsigned int)val > 65535) + if (val < 0 || val > U16_MAX) return -EINVAL; mutex_lock(&priv->lock); From patchwork Thu Apr 6 14:40:13 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: William Breathitt Gray X-Patchwork-Id: 13203548 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id 89D46C77B70 for ; Thu, 6 Apr 2023 14:42:33 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S239148AbjDFOmb (ORCPT ); Thu, 6 Apr 2023 10:42:31 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:42190 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S239124AbjDFOmR (ORCPT ); Thu, 6 Apr 2023 10:42:17 -0400 Received: from mail-oi1-x22f.google.com (mail-oi1-x22f.google.com [IPv6:2607:f8b0:4864:20::22f]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id ED902BB93 for ; Thu, 6 Apr 2023 07:40:37 -0700 (PDT) Received: by mail-oi1-x22f.google.com with SMTP id y184so29201938oiy.8 for ; Thu, 06 Apr 2023 07:40:37 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; t=1680792037; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=U5QEeXDXo+8Slk68c7cxRCftpIfRluY8LXkH8WgnI7Y=; b=SK/NklCaaBaTM/Glz90edPtzaUc6wm8CheJFHJgxB8egsFyIDt2Uvlk7xVY4DH/N60 Xw8We6CFUka6LZHvkAmbJKtbDzNt6QAlYNLNDqKpjl9TmYLz6572rYsyj7XXiA4j2huU Xz8ZRRPP5tfvmrV/Ce7cHv19ONC+txfVah0vXoAvUHHq3Ja3Vii+yJvncPhW+ruhT1kG RBJvzn9m3rE8N5b2lvHF7tDG2iUi7h0MraW/l6fbhv+9RVcVOW3RueTVEmn1p7DOWIGy kUiWGMzcL8R3zUCCdwlOb2yPG0qmbJPcVRruLB5U1Ep3w6OwRAJMCB7aOt/oqFK5miXM iCeg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; t=1680792037; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=U5QEeXDXo+8Slk68c7cxRCftpIfRluY8LXkH8WgnI7Y=; b=4NEXzP3S1ZeisK2aiVFRI2lCCW9L4x3oeovc/iPZnstrVzxuK0zVUn3dE+Om1bd5iI aR7xnQcGPo+XFmsy52U/zgy+++ODyl53de4Zf8Txcll9VdyBeXQSDAWi+BIhTxcj4ywo etmwrpON993l9nSTM48aPzsFh8yk8MNzvFN8/+/AkSkU4Oclw6eXVtmw3S3O0Y1t759c JE+QQ5oWDm8wmD0gMNB9mej7+18sfJCoWGuaQ65iC3RkDhbhnvBdIOBV+1N6heW0/eTX 5/dYYFIQye+AVHzU3NG+IkLev4kbwSk81IJAn87z301rWkJpqMK/HZfTlYlZEAXrEmSu rBRw== X-Gm-Message-State: AAQBX9dZ9FQ0OMbG0ifxzcr7LODnzDdWdr8C9vLBAuMWoWIal0efi03x Wr+Wv3I6kCeLpoZ1Q9FfP+j8ug== X-Google-Smtp-Source: AKy350Z4NesDaNZ6svLg943zXrdWqiqQrl3C+lM0UCfe+MlQeUzwbcQUQpigKabEFPi1BbuXIWWbSA== X-Received: by 2002:a05:6808:285:b0:384:2b1d:45a with SMTP id z5-20020a056808028500b003842b1d045amr4430203oic.30.1680792036750; Thu, 06 Apr 2023 07:40:36 -0700 (PDT) Received: from fedora.attlocal.net (69-109-179-158.lightspeed.dybhfl.sbcglobal.net. [69.109.179.158]) by smtp.gmail.com with ESMTPSA id q7-20020acaf207000000b0037d7f4eb7e8sm726209oih.31.2023.04.06.07.40.35 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Thu, 06 Apr 2023 07:40:36 -0700 (PDT) From: William Breathitt Gray To: Jonathan Cameron , Lars-Peter Clausen Cc: linux-iio@vger.kernel.org, linux-kernel@vger.kernel.org, Andy Shevchenko , William Breathitt Gray Subject: [PATCH v5 4/6] iio: addac: stx104: Improve indentation in stx104_write_raw() Date: Thu, 6 Apr 2023 10:40:13 -0400 Message-Id: <487d17da9e2612f3e6b2bd1c3def2fa1b955db9b.1680790580.git.william.gray@linaro.org> X-Mailer: git-send-email 2.39.2 In-Reply-To: References: MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-iio@vger.kernel.org By bailing out early if chan->output is false for the IIO_CHAN_INFO_RAW, indentation can be decreased by a tab and code readability improved. Suggested-by: Andy Shevchenko Signed-off-by: William Breathitt Gray --- Changes in v5: none drivers/iio/addac/stx104.c | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/drivers/iio/addac/stx104.c b/drivers/iio/addac/stx104.c index 0ed5f71b18cb..81020b710195 100644 --- a/drivers/iio/addac/stx104.c +++ b/drivers/iio/addac/stx104.c @@ -181,19 +181,19 @@ static int stx104_write_raw(struct iio_dev *indio_dev, return 0; case IIO_CHAN_INFO_RAW: - if (chan->output) { - if (val < 0 || val > U16_MAX) - return -EINVAL; + if (!chan->output) + return -EINVAL; - mutex_lock(&priv->lock); + if (val < 0 || val > U16_MAX) + return -EINVAL; - priv->chan_out_states[chan->channel] = val; - iowrite16(val, &priv->reg->dac[chan->channel]); + mutex_lock(&priv->lock); - mutex_unlock(&priv->lock); - return 0; - } - return -EINVAL; + priv->chan_out_states[chan->channel] = val; + iowrite16(val, &priv->reg->dac[chan->channel]); + + mutex_unlock(&priv->lock); + return 0; } return -EINVAL; From patchwork Thu Apr 6 14:40:14 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: William Breathitt Gray X-Patchwork-Id: 13203550 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id 2947CC76196 for ; Thu, 6 Apr 2023 14:42:46 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S239224AbjDFOmo (ORCPT ); Thu, 6 Apr 2023 10:42:44 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:42856 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S239212AbjDFOmU (ORCPT ); Thu, 6 Apr 2023 10:42:20 -0400 Received: from mail-oi1-x22a.google.com (mail-oi1-x22a.google.com [IPv6:2607:f8b0:4864:20::22a]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 307EABBA0 for ; Thu, 6 Apr 2023 07:40:39 -0700 (PDT) Received: by mail-oi1-x22a.google.com with SMTP id bl22so15214887oib.11 for ; Thu, 06 Apr 2023 07:40:39 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; t=1680792038; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=5yd2yVxoqIsDwTMXS2T+HZEAI9D83RI3BoDA5xaKfBE=; b=jtclRHPP5+lJZo9EBwwK1pZZFGC6dToXe2TyW5nNy5HVecAtbIlh/Rfnqd77oMbOzz 6cc345VEEpP3eeXWnTMebBVLNo84sY9QhB3s50HVOo2ZdYC5504EaKkl6JxOh5JJXaZ6 6H73eFKohOwWu5uex72u2AmLhanIemGuU49cPfbzrSaLrb2InzKCmgJtEKBo2SpsBe+5 UQ4TgI7Ze8QI16rYD86n7eLAFoQWb/O2hPbj/g3LDNdy/gQBi0GtDO5AnZuutm1NItBy d4bomTjT3OS5PfyuaW+RlfJinm0fGjhwTlx8Hq+VUAbIg4/ucVkcD6J7fEC7wiNvyH7i 0hNg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; t=1680792038; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=5yd2yVxoqIsDwTMXS2T+HZEAI9D83RI3BoDA5xaKfBE=; b=CPqrl7wPU6C8qET+bIh5WlnVSvjR5khQiZjIqJ+z/wVXWJTH8VuhvvCsrgb5Fb4OxU FMUrgfeWAUrZ+PkQwJkctpl7PjIOyVYJ67rlMXr1OaeTQFv0JqBj+GbLz7UpLCgoH5iq CjHYaqEa2Ug52tzVXc9ku6/H3bKaGwSnt9jWWCeezqoPsdm9eSN29YSZhoh997lsz4LQ rWOIuD0OPtFjapTx4kjyqxrkppRUtjpeG0RBcpxV17/07+t7g+Z49Am9sPUdYLNaCKIS d6qKJuDhvZxOFHgoOYcqicqry207Qsax7lEcYea4q+xR44feYLRzMiWDYCtgOM0ljoS3 hzcA== X-Gm-Message-State: AAQBX9fRlZw9yxOtsdU4DkfkgkEncLiNNbZQAurEo2ZD8YV9k2VgZf4V 4FqfznrpKORwCgzxI1c0JPg11g== X-Google-Smtp-Source: AKy350boRhk831n7uM/oGwGMSDoOnGxltKCbM/S3odFkPmPDtOQI5khsKqh21rhHiUk4RR7Y85y6Rg== X-Received: by 2002:a05:6808:20f:b0:389:5104:84db with SMTP id l15-20020a056808020f00b00389510484dbmr4351821oie.35.1680792037861; Thu, 06 Apr 2023 07:40:37 -0700 (PDT) Received: from fedora.attlocal.net (69-109-179-158.lightspeed.dybhfl.sbcglobal.net. [69.109.179.158]) by smtp.gmail.com with ESMTPSA id q7-20020acaf207000000b0037d7f4eb7e8sm726209oih.31.2023.04.06.07.40.36 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Thu, 06 Apr 2023 07:40:37 -0700 (PDT) From: William Breathitt Gray To: Jonathan Cameron , Lars-Peter Clausen Cc: linux-iio@vger.kernel.org, linux-kernel@vger.kernel.org, Andy Shevchenko , William Breathitt Gray Subject: [PATCH v5 5/6] iio: addac: stx104: Migrate to the regmap API Date: Thu, 6 Apr 2023 10:40:14 -0400 Message-Id: <0bcdfc4738cc019fb2ff83f61eb46a3488bc166d.1680790580.git.william.gray@linaro.org> X-Mailer: git-send-email 2.39.2 In-Reply-To: References: MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-iio@vger.kernel.org The regmap API supports IO port accessors so we can take advantage of regmap abstractions rather than handling access to the device registers directly in the driver. In addition, to improve code organization in stx104_probe(), the devm_iio_device_register() call is moved above GPIO configuration in order to keep relevant code closer together. Suggested-by: Andy Shevchenko Signed-off-by: William Breathitt Gray --- Changes in v5: none Changes in v4: - Remove regmap_config max_register lines as superfluous - Utilize BIT() for gain calculation in stx104_read_raw() Changes in v3: - Add STX104_ prefixes to defines to avoid potential name classes - Rename SAME_CHANNEL() to STX104_SINGLE_CHANNEL() to convey intention better - Utilize u8_encode_bits() to define STX104_SOFTWARE_TRIGGER - Adjust to utilize reg_base members in regmap_config structures - Fix off-by-one errors in aio_data_wr_ranges[], aio_data_rd_ranges[], and aio_data_regmap_config max_register - Inline gpio_config initialization to avoid zeroing it at declaration - Add blank lines between register map init blocks for clarity Changes in v2: - Relocate struct stx104_iio for the sake of a clearer patch diff - Replace FIELD_PREP() and FIELD_GET() with u8_encode_bits() and u8_get_bits() drivers/iio/addac/Kconfig | 2 + drivers/iio/addac/stx104.c | 438 ++++++++++++++++++++----------------- 2 files changed, 245 insertions(+), 195 deletions(-) diff --git a/drivers/iio/addac/Kconfig b/drivers/iio/addac/Kconfig index 2843fcb70e24..877f9124803c 100644 --- a/drivers/iio/addac/Kconfig +++ b/drivers/iio/addac/Kconfig @@ -35,7 +35,9 @@ config STX104 tristate "Apex Embedded Systems STX104 driver" depends on PC104 && X86 select ISA_BUS_API + select REGMAP_MMIO select GPIOLIB + select GPIO_REGMAP help Say yes here to build support for the Apex Embedded Systems STX104 integrated analog PC/104 card. diff --git a/drivers/iio/addac/stx104.c b/drivers/iio/addac/stx104.c index 81020b710195..798f98a8872e 100644 --- a/drivers/iio/addac/stx104.c +++ b/drivers/iio/addac/stx104.c @@ -3,21 +3,20 @@ * IIO driver for the Apex Embedded Systems STX104 * Copyright (C) 2016 William Breathitt Gray */ +#include #include #include -#include -#include +#include +#include #include #include -#include -#include #include #include #include #include #include #include -#include +#include #include #define STX104_OUT_CHAN(chan) { \ @@ -47,107 +46,207 @@ static unsigned int num_stx104; module_param_hw_array(base, uint, ioport, &num_stx104, 0); MODULE_PARM_DESC(base, "Apex Embedded Systems STX104 base addresses"); -/** - * struct stx104_reg - device register structure - * @ssr_ad: Software Strobe Register and ADC Data - * @achan: ADC Channel - * @dio: Digital I/O - * @dac: DAC Channels - * @cir_asr: Clear Interrupts and ADC Status - * @acr: ADC Control - * @pccr_fsh: Pacer Clock Control and FIFO Status MSB - * @acfg: ADC Configuration - */ -struct stx104_reg { - u16 ssr_ad; - u8 achan; - u8 dio; - u16 dac[2]; - u8 cir_asr; - u8 acr; - u8 pccr_fsh; - u8 acfg; -}; +#define STX104_AIO_BASE 0x0 +#define STX104_SOFTWARE_STROBE STX104_AIO_BASE +#define STX104_ADC_DATA STX104_AIO_BASE +#define STX104_ADC_CHANNEL (STX104_AIO_BASE + 0x2) +#define STX104_DIO_REG (STX104_AIO_BASE + 0x3) +#define STX104_DAC_BASE (STX104_AIO_BASE + 0x4) +#define STX104_ADC_STATUS (STX104_AIO_BASE + 0x8) +#define STX104_ADC_CONTROL (STX104_AIO_BASE + 0x9) +#define STX104_ADC_CONFIGURATION (STX104_AIO_BASE + 0x11) + +#define STX104_AIO_DATA_STRIDE 2 +#define STX104_DAC_OFFSET(_channel) (STX104_DAC_BASE + STX104_AIO_DATA_STRIDE * (_channel)) + +/* ADC Channel */ +#define STX104_FC GENMASK(3, 0) +#define STX104_LC GENMASK(7, 4) +#define STX104_SINGLE_CHANNEL(_channel) \ + (u8_encode_bits(_channel, STX104_FC) | u8_encode_bits(_channel, STX104_LC)) + +/* ADC Status */ +#define STX104_SD BIT(5) +#define STX104_CNV BIT(7) +#define STX104_DIFFERENTIAL 1 + +/* ADC Control */ +#define STX104_ALSS GENMASK(1, 0) +#define STX104_SOFTWARE_TRIGGER u8_encode_bits(0x0, STX104_ALSS) + +/* ADC Configuration */ +#define STX104_GAIN GENMASK(1, 0) +#define STX104_ADBU BIT(2) +#define STX104_BIPOLAR 0 +#define STX104_GAIN_X1 0 +#define STX104_GAIN_X2 1 +#define STX104_GAIN_X4 2 +#define STX104_GAIN_X8 3 /** * struct stx104_iio - IIO device private data structure * @lock: synchronization lock to prevent I/O race conditions - * @chan_out_states: channels' output states - * @reg: I/O address offset for the device registers + * @aio_data_map: Regmap for analog I/O data + * @aio_ctl_map: Regmap for analog I/O control */ struct stx104_iio { struct mutex lock; - unsigned int chan_out_states[STX104_NUM_OUT_CHAN]; - struct stx104_reg __iomem *reg; + struct regmap *aio_data_map; + struct regmap *aio_ctl_map; }; -/** - * struct stx104_gpio - GPIO device private data structure - * @chip: instance of the gpio_chip - * @lock: synchronization lock to prevent I/O race conditions - * @base: base port address of the GPIO device - * @out_state: output bits state - */ -struct stx104_gpio { - struct gpio_chip chip; - spinlock_t lock; - u8 __iomem *base; - unsigned int out_state; +static const struct regmap_range aio_ctl_wr_ranges[] = { + regmap_reg_range(0x0, 0x0), regmap_reg_range(0x2, 0x2), regmap_reg_range(0x9, 0x9), + regmap_reg_range(0x11, 0x11), +}; +static const struct regmap_range aio_ctl_rd_ranges[] = { + regmap_reg_range(0x2, 0x2), regmap_reg_range(0x8, 0x9), regmap_reg_range(0x11, 0x11), +}; +static const struct regmap_range aio_ctl_volatile_ranges[] = { + regmap_reg_range(0x8, 0x8), +}; +static const struct regmap_access_table aio_ctl_wr_table = { + .yes_ranges = aio_ctl_wr_ranges, + .n_yes_ranges = ARRAY_SIZE(aio_ctl_wr_ranges), +}; +static const struct regmap_access_table aio_ctl_rd_table = { + .yes_ranges = aio_ctl_rd_ranges, + .n_yes_ranges = ARRAY_SIZE(aio_ctl_rd_ranges), +}; +static const struct regmap_access_table aio_ctl_volatile_table = { + .yes_ranges = aio_ctl_volatile_ranges, + .n_yes_ranges = ARRAY_SIZE(aio_ctl_volatile_ranges), +}; + +static const struct regmap_config aio_ctl_regmap_config = { + .name = "aio_ctl", + .reg_bits = 8, + .reg_stride = 1, + .reg_base = STX104_AIO_BASE, + .val_bits = 8, + .io_port = true, + .wr_table = &aio_ctl_wr_table, + .rd_table = &aio_ctl_rd_table, + .volatile_table = &aio_ctl_volatile_table, + .cache_type = REGCACHE_FLAT, +}; + +static const struct regmap_range aio_data_wr_ranges[] = { + regmap_reg_range(0x4, 0x6), +}; +static const struct regmap_range aio_data_rd_ranges[] = { + regmap_reg_range(0x0, 0x0), +}; +static const struct regmap_access_table aio_data_wr_table = { + .yes_ranges = aio_data_wr_ranges, + .n_yes_ranges = ARRAY_SIZE(aio_data_wr_ranges), +}; +static const struct regmap_access_table aio_data_rd_table = { + .yes_ranges = aio_data_rd_ranges, + .n_yes_ranges = ARRAY_SIZE(aio_data_rd_ranges), +}; + +static const struct regmap_config aio_data_regmap_config = { + .name = "aio_data", + .reg_bits = 16, + .reg_stride = STX104_AIO_DATA_STRIDE, + .reg_base = STX104_AIO_BASE, + .val_bits = 16, + .io_port = true, + .wr_table = &aio_data_wr_table, + .rd_table = &aio_data_rd_table, + .volatile_table = &aio_data_rd_table, + .cache_type = REGCACHE_FLAT, +}; + +static const struct regmap_config dio_regmap_config = { + .name = "dio", + .reg_bits = 8, + .reg_stride = 1, + .reg_base = STX104_DIO_REG, + .val_bits = 8, + .io_port = true, }; static int stx104_read_raw(struct iio_dev *indio_dev, struct iio_chan_spec const *chan, int *val, int *val2, long mask) { struct stx104_iio *const priv = iio_priv(indio_dev); - struct stx104_reg __iomem *const reg = priv->reg; + int err; unsigned int adc_config; - int adbu; - int gain; + unsigned int value; + unsigned int adc_status; switch (mask) { case IIO_CHAN_INFO_HARDWAREGAIN: - /* get gain configuration */ - adc_config = ioread8(®->acfg); - gain = adc_config & 0x3; + err = regmap_read(priv->aio_ctl_map, STX104_ADC_CONFIGURATION, &adc_config); + if (err) + return err; - *val = 1 << gain; + *val = BIT(u8_get_bits(adc_config, STX104_GAIN)); return IIO_VAL_INT; case IIO_CHAN_INFO_RAW: if (chan->output) { - *val = priv->chan_out_states[chan->channel]; + err = regmap_read(priv->aio_data_map, STX104_DAC_OFFSET(chan->channel), + &value); + if (err) + return err; + *val = value; return IIO_VAL_INT; } mutex_lock(&priv->lock); /* select ADC channel */ - iowrite8(chan->channel | (chan->channel << 4), ®->achan); + err = regmap_write(priv->aio_ctl_map, STX104_ADC_CHANNEL, + STX104_SINGLE_CHANNEL(chan->channel)); + if (err) { + mutex_unlock(&priv->lock); + return err; + } /* trigger ADC sample capture by writing to the 8-bit * Software Strobe Register and wait for completion */ - iowrite8(0, ®->ssr_ad); - while (ioread8(®->cir_asr) & BIT(7)); - - *val = ioread16(®->ssr_ad); + err = regmap_write(priv->aio_ctl_map, STX104_SOFTWARE_STROBE, 0); + if (err) { + mutex_unlock(&priv->lock); + return err; + } + do { + err = regmap_read(priv->aio_ctl_map, STX104_ADC_STATUS, &adc_status); + if (err) { + mutex_unlock(&priv->lock); + return err; + } + } while (u8_get_bits(adc_status, STX104_CNV)); + + err = regmap_read(priv->aio_data_map, STX104_ADC_DATA, &value); + if (err) { + mutex_unlock(&priv->lock); + return err; + } + *val = value; mutex_unlock(&priv->lock); return IIO_VAL_INT; case IIO_CHAN_INFO_OFFSET: /* get ADC bipolar/unipolar configuration */ - adc_config = ioread8(®->acfg); - adbu = !(adc_config & BIT(2)); + err = regmap_read(priv->aio_ctl_map, STX104_ADC_CONFIGURATION, &adc_config); + if (err) + return err; - *val = -32768 * adbu; + *val = (u8_get_bits(adc_config, STX104_ADBU) == STX104_BIPOLAR) ? -32768 : 0; return IIO_VAL_INT; case IIO_CHAN_INFO_SCALE: /* get ADC bipolar/unipolar and gain configuration */ - adc_config = ioread8(®->acfg); - adbu = !(adc_config & BIT(2)); - gain = adc_config & 0x3; + err = regmap_read(priv->aio_ctl_map, STX104_ADC_CONFIGURATION, &adc_config); + if (err) + return err; *val = 5; - *val2 = 15 - adbu + gain; + *val2 = (u8_get_bits(adc_config, STX104_ADBU) == STX104_BIPOLAR) ? 14 : 15; + *val2 += u8_get_bits(adc_config, STX104_GAIN); return IIO_VAL_FRACTIONAL_LOG2; } @@ -158,28 +257,29 @@ static int stx104_write_raw(struct iio_dev *indio_dev, struct iio_chan_spec const *chan, int val, int val2, long mask) { struct stx104_iio *const priv = iio_priv(indio_dev); + u8 gain; switch (mask) { case IIO_CHAN_INFO_HARDWAREGAIN: /* Only four gain states (x1, x2, x4, x8) */ switch (val) { case 1: - iowrite8(0, &priv->reg->acfg); + gain = STX104_GAIN_X1; break; case 2: - iowrite8(1, &priv->reg->acfg); + gain = STX104_GAIN_X2; break; case 4: - iowrite8(2, &priv->reg->acfg); + gain = STX104_GAIN_X4; break; case 8: - iowrite8(3, &priv->reg->acfg); + gain = STX104_GAIN_X8; break; default: return -EINVAL; } - return 0; + return regmap_write(priv->aio_ctl_map, STX104_ADC_CONFIGURATION, gain); case IIO_CHAN_INFO_RAW: if (!chan->output) return -EINVAL; @@ -187,13 +287,7 @@ static int stx104_write_raw(struct iio_dev *indio_dev, if (val < 0 || val > U16_MAX) return -EINVAL; - mutex_lock(&priv->lock); - - priv->chan_out_states[chan->channel] = val; - iowrite16(val, &priv->reg->dac[chan->channel]); - - mutex_unlock(&priv->lock); - return 0; + return regmap_write(priv->aio_data_map, STX104_DAC_OFFSET(chan->channel), val); } return -EINVAL; @@ -222,119 +316,66 @@ static const struct iio_chan_spec stx104_channels_diff[] = { STX104_IN_CHAN(6, 1), STX104_IN_CHAN(7, 1) }; -static int stx104_gpio_get_direction(struct gpio_chip *chip, - unsigned int offset) -{ - /* GPIO 0-3 are input only, while the rest are output only */ - if (offset < 4) - return 1; - - return 0; -} - -static int stx104_gpio_direction_input(struct gpio_chip *chip, - unsigned int offset) -{ - if (offset >= 4) - return -EINVAL; - - return 0; -} - -static int stx104_gpio_direction_output(struct gpio_chip *chip, - unsigned int offset, int value) +static int stx104_reg_mask_xlate(struct gpio_regmap *const gpio, const unsigned int base, + unsigned int offset, unsigned int *const reg, + unsigned int *const mask) { - if (offset < 4) - return -EINVAL; - - chip->set(chip, offset, value); - return 0; -} - -static int stx104_gpio_get(struct gpio_chip *chip, unsigned int offset) -{ - struct stx104_gpio *const stx104gpio = gpiochip_get_data(chip); - + /* Output lines are located at same register bit offsets as input lines */ if (offset >= 4) - return -EINVAL; + offset -= 4; - return !!(ioread8(stx104gpio->base) & BIT(offset)); -} - -static int stx104_gpio_get_multiple(struct gpio_chip *chip, unsigned long *mask, - unsigned long *bits) -{ - struct stx104_gpio *const stx104gpio = gpiochip_get_data(chip); - - *bits = ioread8(stx104gpio->base); + *reg = base; + *mask = BIT(offset); return 0; } -static void stx104_gpio_set(struct gpio_chip *chip, unsigned int offset, - int value) -{ - struct stx104_gpio *const stx104gpio = gpiochip_get_data(chip); - const unsigned int mask = BIT(offset) >> 4; - unsigned long flags; - - if (offset < 4) - return; - - spin_lock_irqsave(&stx104gpio->lock, flags); - - if (value) - stx104gpio->out_state |= mask; - else - stx104gpio->out_state &= ~mask; - - iowrite8(stx104gpio->out_state, stx104gpio->base); - - spin_unlock_irqrestore(&stx104gpio->lock, flags); -} - #define STX104_NGPIO 8 static const char *stx104_names[STX104_NGPIO] = { "DIN0", "DIN1", "DIN2", "DIN3", "DOUT0", "DOUT1", "DOUT2", "DOUT3" }; -static void stx104_gpio_set_multiple(struct gpio_chip *chip, - unsigned long *mask, unsigned long *bits) +static int stx104_init_hw(struct stx104_iio *const priv) { - struct stx104_gpio *const stx104gpio = gpiochip_get_data(chip); - unsigned long flags; - - /* verify masked GPIO are output */ - if (!(*mask & 0xF0)) - return; + int err; - *mask >>= 4; - *bits >>= 4; + /* configure device for software trigger operation */ + err = regmap_write(priv->aio_ctl_map, STX104_ADC_CONTROL, STX104_SOFTWARE_TRIGGER); + if (err) + return err; - spin_lock_irqsave(&stx104gpio->lock, flags); + /* initialize gain setting to x1 */ + err = regmap_write(priv->aio_ctl_map, STX104_ADC_CONFIGURATION, STX104_GAIN_X1); + if (err) + return err; - stx104gpio->out_state &= ~*mask; - stx104gpio->out_state |= *mask & *bits; - iowrite8(stx104gpio->out_state, stx104gpio->base); + /* initialize DAC outputs to 0V */ + err = regmap_write(priv->aio_data_map, STX104_DAC_BASE, 0); + if (err) + return err; + err = regmap_write(priv->aio_data_map, STX104_DAC_BASE + STX104_AIO_DATA_STRIDE, 0); + if (err) + return err; - spin_unlock_irqrestore(&stx104gpio->lock, flags); + return 0; } static int stx104_probe(struct device *dev, unsigned int id) { struct iio_dev *indio_dev; struct stx104_iio *priv; - struct stx104_gpio *stx104gpio; + struct gpio_regmap_config gpio_config; + void __iomem *stx104_base; + struct regmap *aio_ctl_map; + struct regmap *aio_data_map; + struct regmap *dio_map; int err; + unsigned int adc_status; indio_dev = devm_iio_device_alloc(dev, sizeof(*priv)); if (!indio_dev) return -ENOMEM; - stx104gpio = devm_kzalloc(dev, sizeof(*stx104gpio), GFP_KERNEL); - if (!stx104gpio) - return -ENOMEM; - if (!devm_request_region(dev, base[id], STX104_EXTENT, dev_name(dev))) { dev_err(dev, "Unable to lock port addresses (0x%X-0x%X)\n", @@ -342,16 +383,37 @@ static int stx104_probe(struct device *dev, unsigned int id) return -EBUSY; } - priv = iio_priv(indio_dev); - priv->reg = devm_ioport_map(dev, base[id], STX104_EXTENT); - if (!priv->reg) + stx104_base = devm_ioport_map(dev, base[id], STX104_EXTENT); + if (!stx104_base) return -ENOMEM; + aio_ctl_map = devm_regmap_init_mmio(dev, stx104_base, &aio_ctl_regmap_config); + if (IS_ERR(aio_ctl_map)) + return dev_err_probe(dev, PTR_ERR(aio_ctl_map), + "Unable to initialize aio_ctl register map\n"); + + aio_data_map = devm_regmap_init_mmio(dev, stx104_base, &aio_data_regmap_config); + if (IS_ERR(aio_data_map)) + return dev_err_probe(dev, PTR_ERR(aio_data_map), + "Unable to initialize aio_data register map\n"); + + dio_map = devm_regmap_init_mmio(dev, stx104_base, &dio_regmap_config); + if (IS_ERR(dio_map)) + return dev_err_probe(dev, PTR_ERR(dio_map), + "Unable to initialize dio register map\n"); + + priv = iio_priv(indio_dev); + priv->aio_ctl_map = aio_ctl_map; + priv->aio_data_map = aio_data_map; + indio_dev->info = &stx104_info; indio_dev->modes = INDIO_DIRECT_MODE; - /* determine if differential inputs */ - if (ioread8(&priv->reg->cir_asr) & BIT(5)) { + err = regmap_read(aio_ctl_map, STX104_ADC_STATUS, &adc_status); + if (err) + return err; + + if (u8_get_bits(adc_status, STX104_SD) == STX104_DIFFERENTIAL) { indio_dev->num_channels = ARRAY_SIZE(stx104_channels_diff); indio_dev->channels = stx104_channels_diff; } else { @@ -363,41 +425,27 @@ static int stx104_probe(struct device *dev, unsigned int id) mutex_init(&priv->lock); - /* configure device for software trigger operation */ - iowrite8(0, &priv->reg->acr); + err = stx104_init_hw(priv); + if (err) + return err; - /* initialize gain setting to x1 */ - iowrite8(0, &priv->reg->acfg); - - /* initialize DAC output to 0V */ - iowrite16(0, &priv->reg->dac[0]); - iowrite16(0, &priv->reg->dac[1]); - - stx104gpio->chip.label = dev_name(dev); - stx104gpio->chip.parent = dev; - stx104gpio->chip.owner = THIS_MODULE; - stx104gpio->chip.base = -1; - stx104gpio->chip.ngpio = STX104_NGPIO; - stx104gpio->chip.names = stx104_names; - stx104gpio->chip.get_direction = stx104_gpio_get_direction; - stx104gpio->chip.direction_input = stx104_gpio_direction_input; - stx104gpio->chip.direction_output = stx104_gpio_direction_output; - stx104gpio->chip.get = stx104_gpio_get; - stx104gpio->chip.get_multiple = stx104_gpio_get_multiple; - stx104gpio->chip.set = stx104_gpio_set; - stx104gpio->chip.set_multiple = stx104_gpio_set_multiple; - stx104gpio->base = &priv->reg->dio; - stx104gpio->out_state = 0x0; - - spin_lock_init(&stx104gpio->lock); - - err = devm_gpiochip_add_data(dev, &stx104gpio->chip, stx104gpio); - if (err) { - dev_err(dev, "GPIO registering failed (%d)\n", err); + err = devm_iio_device_register(dev, indio_dev); + if (err) return err; - } - return devm_iio_device_register(dev, indio_dev); + gpio_config = (struct gpio_regmap_config) { + .parent = dev, + .regmap = dio_map, + .ngpio = STX104_NGPIO, + .names = stx104_names, + .reg_dat_base = GPIO_REGMAP_ADDR(STX104_DIO_REG), + .reg_set_base = GPIO_REGMAP_ADDR(STX104_DIO_REG), + .ngpio_per_reg = STX104_NGPIO, + .reg_mask_xlate = stx104_reg_mask_xlate, + .drvdata = dio_map, + }; + + return PTR_ERR_OR_ZERO(devm_gpio_regmap_register(dev, &gpio_config)); } static struct isa_driver stx104_driver = { From patchwork Thu Apr 6 14:40:15 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: William Breathitt Gray X-Patchwork-Id: 13203549 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id 0C5A5C7618D for ; Thu, 6 Apr 2023 14:42:44 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S239402AbjDFOmm (ORCPT ); Thu, 6 Apr 2023 10:42:42 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:43166 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S239185AbjDFOmT (ORCPT ); Thu, 6 Apr 2023 10:42:19 -0400 Received: from mail-oi1-x231.google.com (mail-oi1-x231.google.com [IPv6:2607:f8b0:4864:20::231]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id E7E13BBA3 for ; Thu, 6 Apr 2023 07:40:39 -0700 (PDT) Received: by mail-oi1-x231.google.com with SMTP id f14so15650773oiw.10 for ; Thu, 06 Apr 2023 07:40:39 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; t=1680792039; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=OFjEsgotUCqG/Q9AAJkwtGeznbu0uxLBMZfxP03HZSU=; b=dm0NPDE41iKMFj+9B6Oo+4IxfPmFQMlB4O7g0/RrSd1IqLw56L3OGQK9UGtqWUEXhV LijwBLp0kng8rZtcWFkk+h6X+d3ggUw2QxWyRpC9Yec/gaK+aWn5iHPs1tO8+nS8fR0a vOShwOPuhMjVgDXTP+wTXUMpjnBHURxJ6yUQ3zWPghXSdToNmz6c20oucq7vkWIO09nm LGRPiMoWxE2Eh96ywqsawuj/YEkxSRcVvsOqJs4ZmRU8jXhBrH+N8ZFYMXa8yD5hUJR2 W2ITcc9n3/RnYPWycNhvyk5A38cVFKRIebGJbBHd5wDVnXISKd42PkJ/UQPrzm4sfdY4 kl5A== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; t=1680792039; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=OFjEsgotUCqG/Q9AAJkwtGeznbu0uxLBMZfxP03HZSU=; b=MkE+7CTBRZ+prz36mxAgltDggDMnNHJ1Nu1Z7ORWtofzzGYk79AbKfFr57+fLb7h+m Alu9R9CpsuMidUeyw+yiPnz/5kpUmmGqF86B6h3l5Y/wvAg6tbV5HrIuD1rUWXpfPtr0 czFcQ08+0AxNWAxhbx0Uzam0ORZ/OuoqppFccjjL7jMsmz49bHc8h0//Nt2gqk+aVbKm lHGYj0vA10kKgKyKNOxZTliR9eTrF0forn0mK6moWRNSRmQXdYfpIOCZKkHkPKJGQybj tM/cuJDinKuGe1lm2glFMrvYf1tf/vIvUw1wa9HshUxqVDg5vmPgoMzlLDQX5HJwKl+/ A+WQ== X-Gm-Message-State: AAQBX9cjYLLLXUR7FFKxMFN2CK6iZ2JrF83kPV2o7gzq12FEvHFHykUs trKLciBeq247RML1YNue7CPcrw== X-Google-Smtp-Source: AKy350Z59V90K5rlPYbC8tfLr2K8aOiRiJjKIgsM24opnyT30WreZ2c3+OmAZehvTXpbk9767pqgow== X-Received: by 2002:a54:440e:0:b0:38b:7347:1f62 with SMTP id k14-20020a54440e000000b0038b73471f62mr1644786oiw.22.1680792039246; Thu, 06 Apr 2023 07:40:39 -0700 (PDT) Received: from fedora.attlocal.net (69-109-179-158.lightspeed.dybhfl.sbcglobal.net. [69.109.179.158]) by smtp.gmail.com with ESMTPSA id q7-20020acaf207000000b0037d7f4eb7e8sm726209oih.31.2023.04.06.07.40.38 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Thu, 06 Apr 2023 07:40:38 -0700 (PDT) From: William Breathitt Gray To: Jonathan Cameron , Lars-Peter Clausen Cc: linux-iio@vger.kernel.org, linux-kernel@vger.kernel.org, Andy Shevchenko , William Breathitt Gray Subject: [PATCH v5 6/6] iio: addac: stx104: Use regmap_read_poll_timeout() for conversion poll Date: Thu, 6 Apr 2023 10:40:15 -0400 Message-Id: <9ef433f107afd1d4dcd2d97ef0e932d7045c2bbd.1680790580.git.william.gray@linaro.org> X-Mailer: git-send-email 2.39.2 In-Reply-To: References: MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-iio@vger.kernel.org ADC sample captures take a certain amount of time to complete after initiated; this conversion time range can be anywhere from 5 microseconds to 53.68 seconds depending on the configuration of the Analog Input Frame Timer register. When the conversion is in progress, the ADC Status register CNV bit is high. Call regmap_read_poll_timeout() to poll until the ADC conversion is completed (or timeout if more than 53.68 seconds passes). Suggested-by: Jonathan Cameron Signed-off-by: William Breathitt Gray --- Changes in v5: - Improve ADC conversion comment format and use proper SI units format Changes in v4: none drivers/iio/addac/stx104.c | 22 +++++++++++++--------- 1 file changed, 13 insertions(+), 9 deletions(-) diff --git a/drivers/iio/addac/stx104.c b/drivers/iio/addac/stx104.c index 798f98a8872e..d1f7ce033b46 100644 --- a/drivers/iio/addac/stx104.c +++ b/drivers/iio/addac/stx104.c @@ -205,21 +205,25 @@ static int stx104_read_raw(struct iio_dev *indio_dev, return err; } - /* trigger ADC sample capture by writing to the 8-bit - * Software Strobe Register and wait for completion + /* + * Trigger ADC sample capture by writing to the 8-bit Software Strobe Register and + * wait for completion; the conversion time range is 5 microseconds to 53.68 seconds + * in steps of 25 nanoseconds. The actual Analog Input Frame Timer time interval is + * calculated as: + * ai_time_frame_ns = ( AIFT + 1 ) * ( 25 nanoseconds ). + * Where 0 <= AIFT <= 2147483648. */ err = regmap_write(priv->aio_ctl_map, STX104_SOFTWARE_STROBE, 0); if (err) { mutex_unlock(&priv->lock); return err; } - do { - err = regmap_read(priv->aio_ctl_map, STX104_ADC_STATUS, &adc_status); - if (err) { - mutex_unlock(&priv->lock); - return err; - } - } while (u8_get_bits(adc_status, STX104_CNV)); + err = regmap_read_poll_timeout(priv->aio_ctl_map, STX104_ADC_STATUS, adc_status, + !u8_get_bits(adc_status, STX104_CNV), 0, 53687092); + if (err) { + mutex_unlock(&priv->lock); + return err; + } err = regmap_read(priv->aio_data_map, STX104_ADC_DATA, &value); if (err) {