From: Jonathan Cameron <jic23@kernel.org>
To: Rodrigo Alencar via B4 Relay
<devnull+rodrigo.alencar.analog.com@kernel.org>
Cc: rodrigo.alencar@analog.com,
Michael Auchter <michael.auchter@ni.com>,
linux@analog.com, linux-iio@vger.kernel.org,
devicetree@vger.kernel.org, linux-kernel@vger.kernel.org,
linux-hardening@vger.kernel.org,
Michael Hennerich <Michael.Hennerich@analog.com>,
David Lechner <dlechner@baylibre.com>,
Andy Shevchenko <andy@kernel.org>, Rob Herring <robh@kernel.org>,
Krzysztof Kozlowski <krzk+dt@kernel.org>,
Conor Dooley <conor+dt@kernel.org>,
Philipp Zabel <p.zabel@pengutronix.de>,
Kees Cook <kees@kernel.org>,
"Gustavo A. R. Silva" <gustavoars@kernel.org>
Subject: Re: [PATCH 10/12] iio: dac: ad5686: add triggered buffer support
Date: Wed, 3 Jun 2026 13:41:51 +0100 [thread overview]
Message-ID: <20260603134151.7cf1654b@jic23-huawei> (raw)
In-Reply-To: <20260602-ad5686-new-features-v1-10-691e01883d27@analog.com>
On Tue, 02 Jun 2026 17:33:57 +0100
Rodrigo Alencar via B4 Relay <devnull+rodrigo.alencar.analog.com@kernel.org> wrote:
> From: Rodrigo Alencar <rodrigo.alencar@analog.com>
>
> Implement trigger handler by leveraging the LDAC gpio to update all DAC
> channels at once when it is available. Also, the multiple channel writes
> can be flushed at once with the sync() operation.
>
> Signed-off-by: Rodrigo Alencar <rodrigo.alencar@analog.com>
One passing comment inline. + some musings... I'd love to avoid
the need for lots of drivers to call iio_trigger_notify_done() manually
as it always results in ugly code paths.
> ---
> drivers/iio/dac/Kconfig | 2 ++
> drivers/iio/dac/ad5686.c | 59 ++++++++++++++++++++++++++++++++++++++++++++++++
> 2 files changed, 61 insertions(+)
>
> diff --git a/drivers/iio/dac/Kconfig b/drivers/iio/dac/Kconfig
> index 657c68e75542..5f14fcd780e2 100644
> --- a/drivers/iio/dac/Kconfig
> +++ b/drivers/iio/dac/Kconfig
> @@ -240,6 +240,8 @@ config LTC2688
>
> config AD5686
> tristate
> + select IIO_BUFFER
> + select IIO_TRIGGERED_BUFFER
>
> config AD5686_SPI
> tristate "Analog Devices AD5686 and similar multi-channel DACs (SPI)"
> diff --git a/drivers/iio/dac/ad5686.c b/drivers/iio/dac/ad5686.c
> index a4cc0f86ea54..5052df44ab1c 100644
> --- a/drivers/iio/dac/ad5686.c
> +++ b/drivers/iio/dac/ad5686.c
> @@ -19,7 +19,11 @@
> #include <linux/sysfs.h>
> #include <linux/wordpart.h>
>
> +#include <linux/iio/buffer.h>
> #include <linux/iio/iio.h>
> +#include <linux/iio/trigger.h>
> +#include <linux/iio/trigger_consumer.h>
> +#include <linux/iio/triggered_buffer.h>
>
> #include "ad5686.h"
>
> @@ -245,6 +249,7 @@ static const struct iio_chan_spec_ext_info ad5686_ext_info[] = {
> .info_mask_separate = BIT(IIO_CHAN_INFO_RAW), \
> .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE),\
> .address = addr, \
> + .scan_index = chan, \
> .scan_type = { \
> .sign = 'u', \
> .realbits = (bits), \
> @@ -469,6 +474,53 @@ const struct ad5686_chip_info ad5679r_chip_info = {
> };
> EXPORT_SYMBOL_NS_GPL(ad5679r_chip_info, "IIO_AD5686");
>
> +static irqreturn_t ad5686_trigger_handler(int irq, void *p)
> +{
> + struct iio_poll_func *pf = p;
> + struct iio_dev *indio_dev = pf->indio_dev;
> + struct iio_buffer *buffer = indio_dev->buffer;
> + struct ad5686_state *st = iio_priv(indio_dev);
> + u16 val[AD5686_MAX_CHANNELS] = { };
> + int ret, ch, i = 0;
> + bool async_update;
> + u8 cmd;
> +
> + ret = iio_pop_from_buffer(buffer, val);
> + if (ret)
> + goto out;
> +
> + mutex_lock(&st->lock);
> +
> + async_update = st->ldac_gpio && bitmap_weight(indio_dev->active_scan_mask,
> + iio_get_masklength(indio_dev)) > 1;
> + if (async_update) {
> + /* use ldac to update all channels simultaneously */
> + cmd = AD5686_CMD_WRITE_INPUT_N;
> + gpiod_set_value_cansleep(st->ldac_gpio, 0);
> + } else {
> + cmd = AD5686_CMD_WRITE_INPUT_N_UPDATE_N;
> + }
> +
> + iio_for_each_active_channel(indio_dev, ch) {
> + ret = st->ops->write(st, cmd, indio_dev->channels[ch].address, val[i++]);
> + if (ret)
> + goto cleanup;
> + }
> +
> + if (st->ops->sync)
> + ret = st->ops->sync(st); /* flush all pending transfers */
> +
> +cleanup:
> + if (async_update)
Error paths are always fun. Do we care about setting ldac_gpio to 1 if
we failed to write the channel values? That will set any that did successfully
update, but not all of them. Note I'm not sure on the right answer for this.
There may not be one!
> + gpiod_set_value_cansleep(st->ldac_gpio, 1);
> +
> + mutex_unlock(&st->lock);
> +out:
> + iio_trigger_notify_done(indio_dev->trig);
We get this pattern so often (though not always). Feels like maybe
we should put some effort into a generic opt in solution for this.
A job for another day but options that come to mind.
1) (hideous) a flag
2) Maybe an alternative callback. thread_always_complete or
something like that. Pain to wire through all the calls though
and injecting the necessary wrapper isn't great either.
Implementation wise would be a case of popping in a wrapper function
in iio_trigger_attach_poll() call to request_threaded_irq().
3) Maybe a helper macro? Bit ugly as we'd need one to generate
the wrapper function and another to use the same name for
the registration function.
Hmm. Those are all ugly (maybe 2 is ok ish). Suggestions welcome!
> +
> + return IRQ_HANDLED;
> +}
> +
> int ad5686_probe(struct device *dev,
> const struct ad5686_chip_info *chip_info,
> const char *name, const struct ad5686_bus_ops *ops,
> @@ -569,6 +621,13 @@ int ad5686_probe(struct device *dev,
> return -EINVAL;
> }
>
> + ret = devm_iio_triggered_buffer_setup_ext(dev, indio_dev, NULL,
> + &ad5686_trigger_handler,
> + IIO_BUFFER_DIRECTION_OUT,
> + NULL, NULL);
> + if (ret)
> + return ret;
> +
> return devm_iio_device_register(dev, indio_dev);
> }
> EXPORT_SYMBOL_NS_GPL(ad5686_probe, "IIO_AD5686");
>
next prev parent reply other threads:[~2026-06-03 12:42 UTC|newest]
Thread overview: 36+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-06-02 16:33 [PATCH 00/12] New features for the AD5686 IIO driver Rodrigo Alencar via B4 Relay
2026-06-02 16:33 ` [PATCH 01/12] dt-bindings: iio: dac: ad5696: add reset/ldac/gain gpio support Rodrigo Alencar via B4 Relay
2026-06-02 16:33 ` [PATCH 02/12] dt-bindings: iio: dac: ad5696: rework on power supplies Rodrigo Alencar via B4 Relay
2026-06-03 15:25 ` Conor Dooley
2026-06-02 16:33 ` [PATCH 03/12] dt-bindings: iio: dac: ad5686: add reset/ldac/gain gpio support Rodrigo Alencar via B4 Relay
2026-06-02 16:33 ` [PATCH 04/12] dt-bindings: iio: dac: ad5686: rework on power supplies Rodrigo Alencar via B4 Relay
2026-06-03 15:29 ` Conor Dooley
2026-06-02 16:33 ` [PATCH 05/12] iio: dac: ad5686: add support for missing " Rodrigo Alencar via B4 Relay
2026-06-02 19:02 ` Andy Shevchenko
2026-06-03 12:17 ` Rodrigo Alencar
2026-06-04 5:51 ` Andy Shevchenko
2026-06-02 16:33 ` [PATCH 06/12] iio: dac: ad5686: consume optional reset signal Rodrigo Alencar via B4 Relay
2026-06-02 19:03 ` Andy Shevchenko
2026-06-03 8:28 ` Nuno Sá
2026-06-03 12:08 ` Jonathan Cameron
2026-06-03 12:57 ` Philipp Zabel
2026-06-08 8:29 ` Nuno Sá
2026-06-02 16:33 ` [PATCH 07/12] iio: dac: ad5686: add ldac gpio Rodrigo Alencar via B4 Relay
2026-06-02 19:05 ` Andy Shevchenko
2026-06-02 16:33 ` [PATCH 08/12] iio: dac: ad5686: introduce sync operation Rodrigo Alencar via B4 Relay
2026-06-02 16:33 ` [PATCH 09/12] iio: dac: ad5686: implement new sync() op for the spi bus Rodrigo Alencar via B4 Relay
2026-06-02 19:14 ` Andy Shevchenko
2026-06-03 12:26 ` Rodrigo Alencar
2026-06-03 12:55 ` Jonathan Cameron
2026-06-04 19:51 ` Andy Shevchenko
2026-06-03 12:24 ` Jonathan Cameron
2026-06-02 16:33 ` [PATCH 10/12] iio: dac: ad5686: add triggered buffer support Rodrigo Alencar via B4 Relay
2026-06-02 19:18 ` Andy Shevchenko
2026-06-03 12:41 ` Jonathan Cameron [this message]
2026-06-05 11:34 ` Rodrigo Alencar
2026-06-05 14:09 ` Jonathan Cameron
2026-06-05 14:40 ` Rodrigo Alencar
2026-06-02 16:33 ` [PATCH 11/12] iio: dac: ad5686: write_raw: use guard(mutex)() Rodrigo Alencar via B4 Relay
2026-06-02 19:20 ` Andy Shevchenko
2026-06-02 16:33 ` [PATCH 12/12] iio: dac: ad5686: add gain control support Rodrigo Alencar via B4 Relay
2026-06-02 19:25 ` Andy Shevchenko
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20260603134151.7cf1654b@jic23-huawei \
--to=jic23@kernel.org \
--cc=Michael.Hennerich@analog.com \
--cc=andy@kernel.org \
--cc=conor+dt@kernel.org \
--cc=devicetree@vger.kernel.org \
--cc=devnull+rodrigo.alencar.analog.com@kernel.org \
--cc=dlechner@baylibre.com \
--cc=gustavoars@kernel.org \
--cc=kees@kernel.org \
--cc=krzk+dt@kernel.org \
--cc=linux-hardening@vger.kernel.org \
--cc=linux-iio@vger.kernel.org \
--cc=linux-kernel@vger.kernel.org \
--cc=linux@analog.com \
--cc=michael.auchter@ni.com \
--cc=p.zabel@pengutronix.de \
--cc=robh@kernel.org \
--cc=rodrigo.alencar@analog.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox