Skip to contentSkip to conversation

iio: adc: ad4000: Add SPI offload support

PATCH Superseded Marcelo Schmitt 3 participants 14 messages Mar 19, 2025 – Mar 21, 2025

Subsystems (4)

v2 of 4 Superseded Latest is v4 →

lore
Share & tools
lore

Marcelo Schmitt

author maintainer
#0 lore raw

v2 cover iio: adc: ad4000: Add SPI offload support

This patch series extends the ad4000 driver to support SPI offloading. In addition to that, ad4000 IIO documentation is expanded to:
- list PulSAR parts supported by the ad4000 driver.
- describe some characteristics of AD4000 IIO device.
- describe changes when SPI offload is being used.

v2 changes were tested with ADAQ4003 on CoraZ7 setup running Linux built from IIO testing branch.

Link to v1: https://lore.kernel.org/linux-iio/[email protected]/

Change log v1 -> v2
- Fixed passing inappropriate pointer instead of ret to dev_err_probe().
- [new patch] Set transfer bits_per_word to have data in CPU endianness.
- Set iio_dev num_channels close to where channels is set.
- Complement offload message comment about first sample being invalid.
- Documented why the first buffer sample is invalid when offloading.
- Added blank line before a 'simple return'.

Instead of changing bits_per_word according to buffer endianness, I set bits_per_word for other SPI transfers and updated IIO channels to always use CPU endianness (the new patch). With that, bits_per_word no longer needs be updated according to buffer endianness or, in other words, buffer endianness is no longer related to bits_per_word.

Marcelo Schmitt (5):
iio: adc: ad400: Set transfer bits_per_word to have data in CPU
endianness
iio: adc: ad4000: Add support for SPI offload
Documentation: iio: ad4000: Add new supported parts
Documentation: iio: ad4000: Add IIO Device characteristics section
Documentation: iio: ad4000: Describe offload support

 Documentation/iio/ad4000.rst |  86 +++++-
 drivers/iio/adc/Kconfig      |   7 +-
 drivers/iio/adc/ad4000.c     | 509 +++++++++++++++++++++++++++++------
 3 files changed, 512 insertions(+), 90 deletions(-)

base-commit: af94f401e26f686f7391ce79b38a6129417c22dc
prerequisite-patch-id: 3d517eef53a799adba5922815fe684b913e36773

Signature · 1 line
2.47.2
author maintainer
#1 lore raw

PATCH v2 1/5 iio: adc: ad400: Set transfer bits_per_word to have data in CPU endianness

When SPI bits_per_word is not set, SPI transfers default 8-bit word size and ADC data gets stored in big-endian format in memory. Because of that, the IIO driver requests ADC data to be rearranged from BE to CPU endianness. However, with bits_per_word set to the number of ADC precision bits, transfers use larger word sizes that get stored in 'in-memory wordsizes' and can be read in CPU endianness.

Use proper bits_per_word size for SPI transfers thus saving the driver from requesting endianness conversions. With that, shifting the buffer data is also no longer needed. This change has no impact on IIO device functionality.

---
 drivers/iio/adc/ad4000.c | 18 ++++++++----------
 1 file changed, 8 insertions(+), 10 deletions(-)
drivers/iio/adc/ad4000.c +8 -10
index 4fe8dee48da9..19bc021e1b5d 100644
@@ -50,8 +50,7 @@
 		.sign = _sign,							\
 		.realbits = _real_bits,						\
 		.storagebits = _storage_bits,					\
-		.shift = _storage_bits - _real_bits,				\
-		.endianness = IIO_BE,						\
+		.endianness = IIO_CPU,						\
 	},									\
 }
 
@@ -79,8 +78,7 @@
 		.sign = _sign,							\
 		.realbits = _real_bits,						\
 		.storagebits = _storage_bits,					\
-		.shift = _storage_bits - _real_bits,				\
-		.endianness = IIO_BE,						\
+		.endianness = IIO_CPU,						\
 	},									\
 }
 
@@ -411,8 +409,8 @@ struct ad4000_state {
 	 */
 	struct {
 		union {
-			__be16 sample_buf16;
-			__be32 sample_buf32;
+			u16 sample_buf16;
+			u32 sample_buf32;
 		} data;
 		aligned_s64 timestamp;
 	} scan __aligned(IIO_DMA_MINALIGN);
@@ -516,11 +514,9 @@ static int ad4000_single_conversion(struct iio_dev *indio_dev,
 		return ret;
 
 	if (chan->scan_type.storagebits > 16)
-		sample = be32_to_cpu(st->scan.data.sample_buf32);
+		sample = st->scan.data.sample_buf32;
 	else
-		sample = be16_to_cpu(st->scan.data.sample_buf16);
-
-	sample >>= chan->scan_type.shift;
+		sample = st->scan.data.sample_buf16;
 
 	if (chan->scan_type.sign == 's')
 		*val = sign_extend32(sample, chan->scan_type.realbits - 1);
@@ -689,6 +685,7 @@ static int ad4000_prepare_3wire_mode_message(struct ad4000_state *st,
 	xfers[0].cs_change_delay.unit = SPI_DELAY_UNIT_NSECS;
 
 	xfers[1].rx_buf = &st->scan.data;
+	xfers[1].bits_per_word = chan->scan_type.realbits;
 	xfers[1].len = BITS_TO_BYTES(chan->scan_type.storagebits);
 	xfers[1].delay.value = st->time_spec->t_quiet2_ns;
 	xfers[1].delay.unit = SPI_DELAY_UNIT_NSECS;
@@ -719,6 +716,7 @@ static int ad4000_prepare_4wire_mode_message(struct ad4000_state *st,
 	xfers[0].delay.unit = SPI_DELAY_UNIT_NSECS;
 
 	xfers[1].rx_buf = &st->scan.data;
+	xfers[1].bits_per_word = chan->scan_type.realbits;
 	xfers[1].len = BITS_TO_BYTES(chan->scan_type.storagebits);
 
 	spi_message_init_with_transfers(&st->msg, st->xfers, 2);
Signature · 1 line
2.47.2
reviewer
#2 lore raw

Re: [PATCH v2 1/5] iio: adc: ad400: Set transfer bits_per_word to have data in CPU endianness

Quoted 7 lines · Marcelo Schmitt

When SPI bits_per_word is not set, SPI transfers default 8-bit word size and ADC data gets stored in big-endian format in memory. Because of that, the IIO driver requests ADC data to be rearranged from BE to CPU endianness. However, with bits_per_word set to the number of ADC precision bits, transfers use larger word sizes that get stored in 'in-memory wordsizes' and can be read in CPU endianness.

Quoted 7 lines

Use proper bits_per_word size for SPI transfers thus saving the driver from requesting endianness conversions. With that, shifting the buffer data is also no longer needed. This change has no impact on IIO device functionality.

---

This is a breaking change. Some SPI controllers, like RPi can only do 8-bit transfers, so this driver would stop working on those platforms. Also, if anyone made software already that depended on the big-endian ordering without checking the scan_type attribute, it would break that software.

I would leave this as-is (drop this patch) and just make it:

.endianness = _offl ? IIO_CPU : IIO_BE,

in the next patch.

#3 lore raw

Re: [PATCH v2 1/5] iio: adc: ad400: Set transfer bits_per_word to have data in CPU endianness

Quoted 13 lines · David Lechner
Quoted 12 lines · Marcelo Schmitt

When SPI bits_per_word is not set, SPI transfers default 8-bit word size and ADC data gets stored in big-endian format in memory. Because of that, the IIO driver requests ADC data to be rearranged from BE to CPU endianness. However, with bits_per_word set to the number of ADC precision bits, transfers use larger word sizes that get stored in 'in-memory wordsizes' and can be read in CPU endianness.

Use proper bits_per_word size for SPI transfers thus saving the driver from requesting endianness conversions. With that, shifting the buffer data is also no longer needed. This change has no impact on IIO device functionality.

Quoted 7 lines
Quoted 2 lines

---

This is a breaking change. Some SPI controllers, like RPi can only do 8-bit transfers, so this driver would stop working on those platforms. Also, if anyone made software already that depended on the big-endian ordering without checking the scan_type attribute, it would break that software.

Hmm, if user space software doesn't check deviceX/scan_elements/in_<channel_type>_type, nor deviceX/bufferY/in_<channel_type>Y_type, then I'd say that's already somewhat broken since at least buffer scan_element type attributes are documented
https://web.git.kernel.org/pub/scm/linux/kernel/git/jic23/iio.git/tree/Documentation/ABI/testing/sysfs-bus-iio?h=testing#n1470.

Anyway, this patch it indeed broke RPi support so I'll revert buffer endianness and SPI transfer bits_per_word configurations the way it was in v1.

Adding possible failure due to controller not supporting specific bits_per_word size to my list of peculiarities related to that field.

Quoted 6 lines

I would leave this as-is (drop this patch) and just make it:

.endianness = _offl ? IIO_CPU : IIO_BE,

in the next patch.

author maintainer
#4 lore raw

PATCH v2 2/5 iio: adc: ad4000: Add support for SPI offload

In reply to Marcelo Schmitt

FPGA HDL projects can include a PWM generator in addition to SPI-Engine. The PWM IP is used to trigger SPI-Engine offload modules that in turn set SPI-Engine to execute transfers to poll data from the ADC. That allows data to be read at the maximum sample rates. Also, it is possible to set a specific sample rate by setting the proper PWM duty cycle and related state parameters, thus allowing an adjustable ADC sample rate when a PWM (offload trigger) is used in combination with SPI-Engine.

Add support for SPI offload.

---
Instead of changing bits_per_word according to buffer endianness, I set bits_per_word for other SPI transfers and updated IIO channels to always use CPU endianness (the first patch in the series). With that, bits_per_word no longer needs be updated according to buffer endianness or, in other words, buffer endianness is no longer related to bits_per_word.

 drivers/iio/adc/Kconfig  |   7 +-
 drivers/iio/adc/ad4000.c | 491 ++++++++++++++++++++++++++++++++-------
 2 files changed, 419 insertions(+), 79 deletions(-)
drivers/iio/adc/Kconfig +6 -1
index b7ae6e0ae0df..1cfa3a32f3a7 100644
@@ -25,10 +25,15 @@ config AD4000
 	tristate "Analog Devices AD4000 ADC Driver"
 	depends on SPI
 	select IIO_BUFFER
+	select IIO_BUFFER_DMAENGINE
 	select IIO_TRIGGERED_BUFFER
+	select SPI_OFFLOAD
 	help
 	  Say yes here to build support for Analog Devices AD4000 high speed
-	  SPI analog to digital converters (ADC).
+	  SPI analog to digital converters (ADC). If intended to use with
+	  SPI offloading support, it is recommended to enable
+	  CONFIG_SPI_AXI_SPI_ENGINE, CONFIG_PWM_AXI_PWMGEN, and
+	  CONFIG_SPI_OFFLOAD_TRIGGER_PWM.
 
 	  To compile this driver as a module, choose M here: the module will be
 	  called ad4000.
drivers/iio/adc/ad4000.c +413 -78

821 lines not on this page · raw message

Signature · 1 line
2.47.2
reviewer
#5 lore raw

Re: [PATCH v2 2/5] iio: adc: ad4000: Add support for SPI offload

Quoted 8 lines · Marcelo Schmitt

FPGA HDL projects can include a PWM generator in addition to SPI-Engine. The PWM IP is used to trigger SPI-Engine offload modules that in turn set SPI-Engine to execute transfers to poll data from the ADC. That allows data to be read at the maximum sample rates. Also, it is possible to set a specific sample rate by setting the proper PWM duty cycle and related state parameters, thus allowing an adjustable ADC sample rate when a PWM (offload trigger) is used in combination with SPI-Engine.

Quoted 4 lines

Add support for SPI offload.

---

I'm surprised I'm not on the CC for this series. scripts/get_maintainer.pl should have picked me up due to K: spi_offload which matches this patch.

Quoted 5 lines

Instead of changing bits_per_word according to buffer endianness, I set bits_per_word for other SPI transfers and updated IIO channels to always use CPU endianness (the first patch in the series). With that, bits_per_word no longer needs be updated according to buffer endianness or, in other words, buffer endianness is no longer related to bits_per_word.

As mentioned in my reply to the previous patch, this is a breaking change, so probably not the best choice.

Quoted 13 lines
 drivers/iio/adc/Kconfig  |   7 +-
 drivers/iio/adc/ad4000.c | 491 ++++++++++++++++++++++++++++++++-------
 2 files changed, 419 insertions(+), 79 deletions(-)
drivers/iio/adc/Kconfig +0 -0
index b7ae6e0ae0df..1cfa3a32f3a7 100644
@@ -25,10 +25,15 @@ config AD4000
 	tristate "Analog Devices AD4000 ADC Driver"
 	depends on SPI
 	select IIO_BUFFER

drivers/iio/adc/Kconfig config AD4000 · line 36

Quoted 10 lines
drivers/iio/adc/Kconfig +6 -1
+	select IIO_BUFFER_DMAENGINE
 	select IIO_TRIGGERED_BUFFER
+	select SPI_OFFLOAD
 	help
 	  Say yes here to build support for Analog Devices AD4000 high speed
-	  SPI analog to digital converters (ADC).
+	  SPI analog to digital converters (ADC). If intended to use with
+	  SPI offloading support, it is recommended to enable
+	  CONFIG_SPI_AXI_SPI_ENGINE, CONFIG_PWM_AXI_PWMGEN, and
+	  CONFIG_SPI_OFFLOAD_TRIGGER_PWM.

I guess this is fine here, but people might be more likely to see it on the ADI wiki where the HDL project that has these requirements is described.

Quoted 8 lines
drivers/iio/adc/Kconfig +0 -0
 	  To compile this driver as a module, choose M here: the module will be
 	  called ad4000.
drivers/iio/adc/ad4000.c +0 -0
index 19bc021e1b5d..b3f4d215cad4 100644

drivers/iio/adc/ad4000.c line 28

Quoted 8 lines
drivers/iio/adc/ad4000.c +2 -0
@@ -21,9 +21,12 @@
 #include <linux/iio/iio.h>
 
 #include <linux/iio/buffer.h>
+#include <linux/iio/buffer-dmaengine.h>
 #include <linux/iio/triggered_buffer.h>
 #include <linux/iio/trigger_consumer.h>
 
+#include <linux/spi/offload/consumer.h>

Why not before #include <linux/spi/spi.h> ?

Quoted 6 lines
drivers/iio/adc/ad4000.c +1 -0
+
 #define AD4000_READ_COMMAND	0x54
 #define AD4000_WRITE_COMMAND	0x14
 
@@ -32,10 +35,15 @@
 /* AD4000 Configuration Register programmable bits */

drivers/iio/adc/ad4000.c line 44

Quoted 10 lines
drivers/iio/adc/ad4000.c +4 -1
 #define AD4000_CFG_SPAN_COMP		BIT(3) /* Input span compression  */
 #define AD4000_CFG_HIGHZ		BIT(2) /* High impedance mode  */
+#define AD4000_CFG_TURBO		BIT(1) /* Turbo mode */
 
 #define AD4000_SCALE_OPTIONS		2
 
-#define __AD4000_DIFF_CHANNEL(_sign, _real_bits, _storage_bits, _reg_access)	\
+#define AD4000_TQUIET1_NS		190
+#define AD4000_TQUIET2_NS		60
+#define AD4000_TCONV_NS			320

Does this actually work for every single chip? For example, the AD7983 datasheet give the max as 500 ns for this timing parameter. Might need to put this in the chip_info to account for differences.

Also AD7983 doesn't have any quite time in the datasheet, so those might not be needed in some cases?

Quoted 20 lines
drivers/iio/adc/ad4000.c +5 -2
+
+#define __AD4000_DIFF_CHANNEL(_sign, _real_bits, _storage_bits, _reg_access, _offl)\
 {										\
 	.type = IIO_VOLTAGE,							\
 	.indexed = 1,								\
@@ -43,8 +51,9 @@
 	.channel = 0,								\
 	.channel2 = 1,								\
 	.info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |				\
-			      BIT(IIO_CHAN_INFO_SCALE),				\
-	.info_mask_separate_available = _reg_access ? BIT(IIO_CHAN_INFO_SCALE) : 0,\
+			      BIT(IIO_CHAN_INFO_SCALE) |			\
+			      (_offl ? BIT(IIO_CHAN_INFO_SAMP_FREQ) : 0),	\
+	.info_mask_separate_available = (_reg_access ? BIT(IIO_CHAN_INFO_SCALE) : 0),\
 	.scan_index = 0,							\
 	.scan_type = {								\
 		.sign = _sign,							\
@@ -54,25 +63,28 @@
 	},									\
 }

drivers/iio/adc/ad4000.c line 71

Quoted 10 lines
drivers/iio/adc/ad4000.c +4 -3
 
-#define AD4000_DIFF_CHANNEL(_sign, _real_bits, _reg_access)			\
+#define AD4000_DIFF_CHANNEL(_sign, _real_bits, _reg_access, _offl)		\
 	__AD4000_DIFF_CHANNEL((_sign), (_real_bits),				\
-				     ((_real_bits) > 16 ? 32 : 16), (_reg_access))
+			      (((_offl) || ((_real_bits) > 16)) ? 32 : 16),	\
+			      (_reg_access), (_offl))
 
-#define AD4000_DIFF_CHANNELS(_sign, _real_bits, _reg_access)			\
+#define AD4000_DIFF_CHANNELS(_sign, _real_bits, _reg_access, _offl)		\

We always pass 0 to _offl here, so we can leave out this parameter and just hard-code the 0 below. We will never have a case with offload + soft timestamp.

Quoted 10 lines
drivers/iio/adc/ad4000.c +3 -2
 {										\
-	AD4000_DIFF_CHANNEL(_sign, _real_bits, _reg_access),			\
+	AD4000_DIFF_CHANNEL(_sign, _real_bits, _reg_access, _offl),		\
 	IIO_CHAN_SOFT_TIMESTAMP(1),						\
 }
 
-#define __AD4000_PSEUDO_DIFF_CHANNEL(_sign, _real_bits, _storage_bits, _reg_access)\
+#define __AD4000_PSEUDO_DIFF_CHANNEL(_sign, _real_bits, _storage_bits,		\
+				     _reg_access, _offl)			\
 {										\

drivers/iio/adc/ad4000.c line 87

Quoted 10 lines
drivers/iio/adc/ad4000.c +3 -2
 	.type = IIO_VOLTAGE,							\
 	.indexed = 1,								\
 	.channel = 0,								\
 	.info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |				\
 			      BIT(IIO_CHAN_INFO_SCALE) |			\
-			      BIT(IIO_CHAN_INFO_OFFSET),			\
-	.info_mask_separate_available = _reg_access ? BIT(IIO_CHAN_INFO_SCALE) : 0,\
+			      BIT(IIO_CHAN_INFO_OFFSET) |			\
+			      (_offl ? BIT(IIO_CHAN_INFO_SAMP_FREQ) : 0),	\
+	.info_mask_separate_available = (_reg_access ? BIT(IIO_CHAN_INFO_SCALE) : 0),\

Unrelated change (adding braces)?

Also, could be nice to have sampling_frequency_available so that userspace can discover the max sample rate.

Quoted 6 lines
drivers/iio/adc/ad4000.c +0 -0
 	.scan_index = 0,							\
 	.scan_type = {								\
 		.sign = _sign,							\
@@ -82,13 +94,14 @@
 	},									\
 }

drivers/iio/adc/ad4000.c line 102

Quoted 10 lines
drivers/iio/adc/ad4000.c +4 -3
 
-#define AD4000_PSEUDO_DIFF_CHANNEL(_sign, _real_bits, _reg_access)		\
+#define AD4000_PSEUDO_DIFF_CHANNEL(_sign, _real_bits, _reg_access, _offl)	\
 	__AD4000_PSEUDO_DIFF_CHANNEL((_sign), (_real_bits),			\
-				     ((_real_bits) > 16 ? 32 : 16), (_reg_access))
+				     (((_offl) || ((_real_bits) > 16)) ? 32 : 16),\
+				     (_reg_access), (_offl))
 
-#define AD4000_PSEUDO_DIFF_CHANNELS(_sign, _real_bits, _reg_access)		\
+#define AD4000_PSEUDO_DIFF_CHANNELS(_sign, _real_bits, _reg_access, _offl)	\

ditto about hard-coding _offl here

Quoted 5 lines
drivers/iio/adc/ad4000.c +1 -1
 {										\
-	AD4000_PSEUDO_DIFF_CHANNEL(_sign, _real_bits, _reg_access),		\
+	AD4000_PSEUDO_DIFF_CHANNEL(_sign, _real_bits, _reg_access, _offl),	\
 	IIO_CHAN_SOFT_TIMESTAMP(1),						\
 }

...

drivers/iio/adc/ad4000.c struct ad4000_chip_info { · line 460

Quoted 7 lines

static const struct ad4000_chip_info ad7983_chip_info = {

drivers/iio/adc/ad4000.c +3 -1
 	.dev_name = "ad7983",
-	.chan_spec = AD4000_PSEUDO_DIFF_CHANNELS('u', 16, 0),
+	.chan_spec = AD4000_PSEUDO_DIFF_CHANNELS('u', 16, 0, 0),
+	.offload_chan_spec = AD4000_PSEUDO_DIFF_CHANNEL('u', 16, 0, 1),
 	.time_spec = &ad7983_t_spec,
+	.max_rate_hz = 1330 * KILO,

This is actually 752 ns period when 750 is allowed. Could make it 1 * MEGA + 333
* KILO + 333 or 1333333.

drivers/iio/adc/ad4000.c struct ad4000_chip_info { · line 468

Quoted 9 lines

};

static const struct ad4000_chip_info ad7984_chip_info = {

drivers/iio/adc/ad4000.c +3 -1
 	.dev_name = "ad7984",
-	.chan_spec = AD4000_DIFF_CHANNELS('s', 18, 0),
+	.chan_spec = AD4000_DIFF_CHANNELS('s', 18, 0, 0),
+	.offload_chan_spec = AD4000_DIFF_CHANNEL('s', 18, 0, 1),
 	.time_spec = &ad7983_t_spec,
+	.max_rate_hz = 1330 * KILO,

ditto

Quoted 2 lines

};

...

drivers/iio/adc/ad4000.c static const struct iio_info ad4000_reg_access_info = { · line 831

Quoted 12 lines
drivers/iio/adc/ad4000.c +12 -0
+static int ad4000_offload_buffer_postdisable(struct iio_dev *indio_dev)
+{
+	struct ad4000_state *st = iio_priv(indio_dev);
+
+	spi_offload_trigger_disable(st->offload, st->offload_trigger);
+
+	return 0;
+}
+
+static const struct iio_buffer_setup_ops ad4000_offload_buffer_setup_ops = {
+	.postenable = &ad4000_offload_buffer_postenable,
+	.postdisable = &ad4000_offload_buffer_postdisable,

Needs to be predisable to correctly balance postenable.

Quoted 53 lines
drivers/iio/adc/ad4000.c +53 -0
+};
+
+static int ad4000_spi_offload_setup(struct iio_dev *indio_dev,
+				    struct ad4000_state *st)
+{
+	struct spi_device *spi = st->spi;
+	struct device *dev = &spi->dev;
+	struct dma_chan *rx_dma;
+	int ret;
+
+	st->offload_trigger = devm_spi_offload_trigger_get(dev, st->offload,
+							   SPI_OFFLOAD_TRIGGER_PERIODIC);
+	if (IS_ERR(st->offload_trigger))
+		return dev_err_probe(dev, PTR_ERR(st->offload_trigger),
+				     "Failed to get offload trigger\n");
+
+	ret = ad4000_set_sampling_freq(st, st->max_rate_hz);
+	if (ret)
+		return dev_err_probe(dev, ret,
+				     "Failed to set sampling frequency\n");
+
+	rx_dma = devm_spi_offload_rx_stream_request_dma_chan(dev, st->offload);
+	if (IS_ERR(rx_dma))
+		return dev_err_probe(dev, PTR_ERR(rx_dma),
+				     "Failed to get offload RX DMA\n");
+
+	ret = devm_iio_dmaengine_buffer_setup_with_handle(dev, indio_dev, rx_dma,
+							  IIO_BUFFER_DIRECTION_IN);
+	if (ret)
+		return dev_err_probe(dev, ret, "Failed to setup DMA buffer\n");
+
+	return 0;
+}
+
+/*
+ * This executes a data sample transfer when using SPI offloading for when the
+ * device connections are in "3-wire" mode, selected when the adi,sdi-pin device
+ * tree property is absent. In this connection mode, the ADC SDI pin is
+ * connected to MOSI or to VIO and ADC CNV pin is connected to a SPI controller
+ * CS (it can't be connected to a GPIO).
+ *
+ * In order to achieve the maximum sample rate, we only do one transfer per
+ * SPI offload trigger. Because the ADC output has a one sample latency (delay)
+ * when the device is wired in "3-wire" mode and only one transfer per sample is
+ * being made in turbo mode, the first data sample is not valid because it
+ * contains the output of an earlier conversion result. We also set transfer
+ * `bits_per_word` to achieve higher throughput by using the minimum number of
+ * SCLK cycles. Also, a delay is added to make sure we meet the minimum quiet
+ * time before releasing the CS line. Plus the CS change delay is set to ensure
+ * that we meet the minimum quiet time before asserting CS again.
+ *
+ * This timing is only valid if turbo mode is enabled (reading during conversion).
+ */

drivers/iio/adc/ad4000.c static const struct iio_info ad4000_reg_access_info = { · line 894

Quoted 10 lines
drivers/iio/adc/ad4000.c +10 -0
+static int ad4000_prepare_offload_turbo_message(struct ad4000_state *st,
+						const struct iio_chan_spec *chan)
+{
+	struct spi_transfer *xfers = st->offload_xfers;
+
+	/* Have to do a short CS toggle to trigger conversion. */
+	xfers[0].cs_change = 1;
+	xfers[0].cs_change_delay.value = AD4000_TQUIET1_NS;
+	xfers[0].cs_change_delay.unit = SPI_DELAY_UNIT_NSECS;
+	xfers[0].offload_flags = SPI_OFFLOAD_XFER_RX_STREAM;

There is no data transferred in this xfer, so we don't need to set this flag.

Quoted 13 lines
drivers/iio/adc/ad4000.c +13 -0
+
+	xfers[1].offload_flags = SPI_OFFLOAD_XFER_RX_STREAM;
+	xfers[1].bits_per_word = chan->scan_type.realbits;
+	xfers[1].len = chan->scan_type.realbits > 16 ? 4 : 2;
+	xfers[1].delay.value = AD4000_TQUIET2_NS;
+	xfers[1].delay.unit = SPI_DELAY_UNIT_NSECS;
+
+	spi_message_init_with_transfers(&st->offload_msg, xfers, 2);
+	st->offload_msg.offload = st->offload;
+
+	return devm_spi_optimize_message(&st->spi->dev, st->spi, &st->offload_msg);
+}
+

...

drivers/iio/adc/ad4000.c static int ad4000_probe(struct spi_device *spi) · line 1134

Quoted 13 lines
drivers/iio/adc/ad4000.c +7 -2
@@ -804,19 +1125,39 @@ static int ad4000_probe(struct spi_device *spi)
 
 		break;
 	case AD4000_SDI_VIO:
-		indio_dev->info = &ad4000_info;
-		indio_dev->channels = chip->chan_spec;
+		if (st->using_offload) {
+			indio_dev->info = &ad4000_offload_info;
+			indio_dev->channels = &chip->offload_chan_spec;
+			indio_dev->num_channels = 1;
+
+			spi->cs_hold.value = AD4000_TCONV_NS;
+			spi->cs_hold.unit = SPI_DELAY_UNIT_NSECS;

Modifying spi is suspicious. Normally, this would come from the devicetree. And this isn't used by all SPI drivers - notably the AXI SPI Engine ignores it. Better to just handle this in individual spi xfer structs.

drivers/iio/adc/ad4000.c static int ad4000_probe(struct spi_device *spi) · line 1143

Quoted 9 lines
drivers/iio/adc/ad4000.c +9 -0
+			ret = ad4000_prepare_offload_message(st, indio_dev->channels);
+			if (ret)
+				return dev_err_probe(dev, ret,
+						     "Failed to optimize SPI msg\n");
+		} else {
+			indio_dev->info = &ad4000_info;
+			indio_dev->channels = chip->chan_spec;
+			indio_dev->num_channels = ARRAY_SIZE(chip->chan_spec);
+		}

nit: add extra blank line here

Quoted 7 lines
drivers/iio/adc/ad4000.c +2 -1
 		ret = ad4000_prepare_3wire_mode_message(st, &indio_dev->channels[0]);
 		if (ret)
-			return ret;
+			return dev_err_probe(dev, ret,
+					     "Failed to optimize SPI msg\n");
 
 		break;
#6 lore raw

Re: [PATCH v2 2/5] iio: adc: ad4000: Add support for SPI offload

Quoted 9 lines · David Lechner
Quoted 8 lines · Marcelo Schmitt

FPGA HDL projects can include a PWM generator in addition to SPI-Engine. The PWM IP is used to trigger SPI-Engine offload modules that in turn set SPI-Engine to execute transfers to poll data from the ADC. That allows data to be read at the maximum sample rates. Also, it is possible to set a specific sample rate by setting the proper PWM duty cycle and related state parameters, thus allowing an adjustable ADC sample rate when a PWM (offload trigger) is used in combination with SPI-Engine.

Quoted 7 lines
Quoted 4 lines

Add support for SPI offload.

---

I'm surprised I'm not on the CC for this series. scripts/get_maintainer.pl should have picked me up due to K: spi_offload which matches this patch.

get_maintainers doesn't list you if run over ad4000.c.
If run over the patch file, get_maintainers lists many developers. Some of them don't seem to be related to this series, so I cropped the list to avoid churn. Will CC you on the next versions.

Quoted 9 lines
Quoted 6 lines

Instead of changing bits_per_word according to buffer endianness, I set bits_per_word for other SPI transfers and updated IIO channels to always use CPU endianness (the first patch in the series). With that, bits_per_word no longer needs be updated according to buffer endianness or, in other words, buffer endianness is no longer related to bits_per_word.

As mentioned in my reply to the previous patch, this is a breaking change, so probably not the best choice.

Ack

Quoted 19 lines
Quoted 19 lines

 drivers/iio/adc/Kconfig  |   7 +-
 drivers/iio/adc/ad4000.c | 491 ++++++++++++++++++++++++++++++++-------
 2 files changed, 419 insertions(+), 79 deletions(-)
drivers/iio/adc/Kconfig +2 -0
index b7ae6e0ae0df..1cfa3a32f3a7 100644
@@ -25,10 +25,15 @@ config AD4000
 	tristate "Analog Devices AD4000 ADC Driver"
 	depends on SPI
 	select IIO_BUFFER
+	select IIO_BUFFER_DMAENGINE
 	select IIO_TRIGGERED_BUFFER
+	select SPI_OFFLOAD
 	help
 	  Say yes here to build support for Analog Devices AD4000 high speed
Quoted 8 lines

drivers/iio/adc/Kconfig config AD4000 · line 36

Quoted 5 lines
drivers/iio/adc/Kconfig +4 -1
-	  SPI analog to digital converters (ADC).
+	  SPI analog to digital converters (ADC). If intended to use with
+	  SPI offloading support, it is recommended to enable
+	  CONFIG_SPI_AXI_SPI_ENGINE, CONFIG_PWM_AXI_PWMGEN, and
+	  CONFIG_SPI_OFFLOAD_TRIGGER_PWM.

I guess this is fine here, but people might be more likely to see it on the ADI wiki where the HDL project that has these requirements is described.

I don't see any word about that at
https://analogdevicesinc.github.io/hdl/projects/pulsar_adc/index.html
If no one opposes to that, I'd like to keep the piece of advice.

Quoted 11 lines
Quoted 11 lines
drivers/iio/adc/Kconfig +0 -0
 	  To compile this driver as a module, choose M here: the module will be
 	  called ad4000.
drivers/iio/adc/ad4000.c +0 -0
index 19bc021e1b5d..b3f4d215cad4 100644
@@ -21,9 +21,12 @@
 #include <linux/iio/iio.h>
 
Quoted 8 lines

drivers/iio/adc/ad4000.c line 28

Quoted 6 lines
drivers/iio/adc/ad4000.c +2 -0
 #include <linux/iio/buffer.h>
+#include <linux/iio/buffer-dmaengine.h>
 #include <linux/iio/triggered_buffer.h>
 #include <linux/iio/trigger_consumer.h>
 
+#include <linux/spi/offload/consumer.h>

Why not before #include <linux/spi/spi.h> ?

Okay, will put it there.

Quoted 1 line

...

Quoted 10 lines

drivers/iio/adc/ad4000.c line 44

Quoted 5 lines
drivers/iio/adc/ad4000.c +3 -1
-#define __AD4000_DIFF_CHANNEL(_sign, _real_bits, _storage_bits, _reg_access)	\
+#define AD4000_TQUIET1_NS		190
+#define AD4000_TQUIET2_NS		60
+#define AD4000_TCONV_NS			320

Does this actually work for every single chip? For example, the AD7983 datasheet give the max as 500 ns for this timing parameter. Might need to put this in the chip_info to account for differences.

Quoted 2 lines

Also AD7983 doesn't have any quite time in the datasheet, so those might not be needed in some cases?

I've tested the series with AD7687 and ADAQ4003 and got good readings. I'll check the timing specifications again and provide a delay long enough for AD7983 and any other device with longer TCONV.

Quoted 1 line

...

Quoted 5 lines

drivers/iio/adc/ad4000.c line 71

Quoted 2 lines
drivers/iio/adc/ad4000.c +1 -1
-#define AD4000_DIFF_CHANNELS(_sign, _real_bits, _reg_access)			\
+#define AD4000_DIFF_CHANNELS(_sign, _real_bits, _reg_access, _offl)		\

We always pass 0 to _offl here, so we can leave out this parameter and just hard-code the 0 below. We will never have a case with offload + soft timestamp.

Good catch. Will apply the simplification.

Quoted 1 line

...

Quoted 8 lines
Quoted 8 lines
drivers/iio/adc/ad4000.c +2 -1
-#define __AD4000_PSEUDO_DIFF_CHANNEL(_sign, _real_bits, _storage_bits, _reg_access)\
+#define __AD4000_PSEUDO_DIFF_CHANNEL(_sign, _real_bits, _storage_bits,		\
+				     _reg_access, _offl)			\
 {										\
 	.type = IIO_VOLTAGE,							\
 	.indexed = 1,								\
 	.channel = 0,								\
 	.info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |				\
Quoted 8 lines

drivers/iio/adc/ad4000.c line 87

Quoted 6 lines
drivers/iio/adc/ad4000.c +3 -2
 			      BIT(IIO_CHAN_INFO_SCALE) |			\
-			      BIT(IIO_CHAN_INFO_OFFSET),			\
-	.info_mask_separate_available = _reg_access ? BIT(IIO_CHAN_INFO_SCALE) : 0,\
+			      BIT(IIO_CHAN_INFO_OFFSET) |			\
+			      (_offl ? BIT(IIO_CHAN_INFO_SAMP_FREQ) : 0),	\
+	.info_mask_separate_available = (_reg_access ? BIT(IIO_CHAN_INFO_SCALE) : 0),\

Unrelated change (adding braces)?

Oops, will undo.

Quoted 3 lines

Also, could be nice to have sampling_frequency_available so that userspace can discover the max sample rate.

I don't think we should have sampling_frequency_available in this case because there is no clear list of sample frequency values nor they can always be expressed as "[min step max]" triad.
https://web.git.kernel.org/pub/scm/linux/kernel/git/jic23/iio.git/tree/Documentation/ABI/testing/sysfs-bus-iio?h=testing#n121

Quoted 1 line

...

Quoted 4 lines

drivers/iio/adc/ad4000.c line 102

Quoted 2 lines
drivers/iio/adc/ad4000.c +1 -1
-#define AD4000_PSEUDO_DIFF_CHANNELS(_sign, _real_bits, _reg_access)		\
+#define AD4000_PSEUDO_DIFF_CHANNELS(_sign, _real_bits, _reg_access, _offl)	\

ditto about hard-coding _offl here

Ack

Quoted 1 line

...

Quoted 10 lines

drivers/iio/adc/ad4000.c struct ad4000_chip_info { · line 460

Quoted 7 lines

static const struct ad4000_chip_info ad7983_chip_info = {

drivers/iio/adc/ad4000.c +3 -1
 	.dev_name = "ad7983",
-	.chan_spec = AD4000_PSEUDO_DIFF_CHANNELS('u', 16, 0),
+	.chan_spec = AD4000_PSEUDO_DIFF_CHANNELS('u', 16, 0, 0),
+	.offload_chan_spec = AD4000_PSEUDO_DIFF_CHANNEL('u', 16, 0, 1),
 	.time_spec = &ad7983_t_spec,
+	.max_rate_hz = 1330 * KILO,

This is actually 752 ns period when 750 is allowed. Could make it 1 * MEGA + 333
* KILO + 333 or 1333333.

Ack

Quoted 12 lines

drivers/iio/adc/ad4000.c struct ad4000_chip_info { · line 468

Quoted 10 lines

};

static const struct ad4000_chip_info ad7984_chip_info = {

drivers/iio/adc/ad4000.c +3 -1
 	.dev_name = "ad7984",
-	.chan_spec = AD4000_DIFF_CHANNELS('s', 18, 0),
+	.chan_spec = AD4000_DIFF_CHANNELS('s', 18, 0, 0),
+	.offload_chan_spec = AD4000_DIFF_CHANNEL('s', 18, 0, 1),
 	.time_spec = &ad7983_t_spec,
+	.max_rate_hz = 1330 * KILO,

ditto

Ack

Quoted 1 line

...

Quoted 5 lines

drivers/iio/adc/ad4000.c static const struct iio_info ad4000_reg_access_info = { · line 831

Quoted 3 lines
drivers/iio/adc/ad4000.c +3 -0
+static const struct iio_buffer_setup_ops ad4000_offload_buffer_setup_ops = {
+	.postenable = &ad4000_offload_buffer_postenable,
+	.postdisable = &ad4000_offload_buffer_postdisable,

Needs to be predisable to correctly balance postenable.

Ack

Quoted 1 line

...

Quoted 4 lines
Quoted 4 lines
drivers/iio/adc/ad4000.c +4 -0
+static int ad4000_prepare_offload_turbo_message(struct ad4000_state *st,
+						const struct iio_chan_spec *chan)
+{
+	struct spi_transfer *xfers = st->offload_xfers;
Quoted 8 lines

drivers/iio/adc/ad4000.c static const struct iio_info ad4000_reg_access_info = { · line 894

Quoted 6 lines
drivers/iio/adc/ad4000.c +6 -0
+
+	/* Have to do a short CS toggle to trigger conversion. */
+	xfers[0].cs_change = 1;
+	xfers[0].cs_change_delay.value = AD4000_TQUIET1_NS;
+	xfers[0].cs_change_delay.unit = SPI_DELAY_UNIT_NSECS;
+	xfers[0].offload_flags = SPI_OFFLOAD_XFER_RX_STREAM;

There is no data transferred in this xfer, so we don't need to set this flag.

Ack

Quoted 1 line

...

Quoted 6 lines
Quoted 6 lines
drivers/iio/adc/ad4000.c +3 -2
 	case AD4000_SDI_VIO:
-		indio_dev->info = &ad4000_info;
-		indio_dev->channels = chip->chan_spec;
+		if (st->using_offload) {
+			indio_dev->info = &ad4000_offload_info;
+			indio_dev->channels = &chip->offload_chan_spec;
Quoted 8 lines

drivers/iio/adc/ad4000.c static int ad4000_probe(struct spi_device *spi) · line 1134

Quoted 4 lines
drivers/iio/adc/ad4000.c +4 -0
+			indio_dev->num_channels = 1;
+
+			spi->cs_hold.value = AD4000_TCONV_NS;
+			spi->cs_hold.unit = SPI_DELAY_UNIT_NSECS;

Modifying spi is suspicious. Normally, this would come from the devicetree. And this isn't used by all SPI drivers - notably the AXI SPI Engine ignores it. Better to just handle this in individual spi xfer structs.

Will try that.

Quoted 12 lines

drivers/iio/adc/ad4000.c static int ad4000_probe(struct spi_device *spi) · line 1143

Quoted 10 lines
drivers/iio/adc/ad4000.c +9 -0
+			ret = ad4000_prepare_offload_message(st, indio_dev->channels);
+			if (ret)
+				return dev_err_probe(dev, ret,
+						     "Failed to optimize SPI msg\n");
+		} else {
+			indio_dev->info = &ad4000_info;
+			indio_dev->channels = chip->chan_spec;
+			indio_dev->num_channels = ARRAY_SIZE(chip->chan_spec);
+		}

nit: add extra blank line here

Ack

Quoted 9 lines
Quoted 8 lines
drivers/iio/adc/ad4000.c +2 -1
 		ret = ad4000_prepare_3wire_mode_message(st, &indio_dev->channels[0]);
 		if (ret)
-			return ret;
+			return dev_err_probe(dev, ret,
+					     "Failed to optimize SPI msg\n");
 
 		break;
reviewer
#7 lore raw

Re: [PATCH v2 2/5] iio: adc: ad4000: Add support for SPI offload

Quoted 15 lines · Marcelo Schmitt
Quoted 14 lines · David Lechner
Quoted 12 lines · Marcelo Schmitt

FPGA HDL projects can include a PWM generator in addition to SPI-Engine. The PWM IP is used to trigger SPI-Engine offload modules that in turn set SPI-Engine to execute transfers to poll data from the ADC. That allows data to be read at the maximum sample rates. Also, it is possible to set a specific sample rate by setting the proper PWM duty cycle and related state parameters, thus allowing an adjustable ADC sample rate when a PWM (offload trigger) is used in combination with SPI-Engine.

Add support for SPI offload.

---

Quoted 8 lines
Quoted 2 lines

I'm surprised I'm not on the CC for this series. scripts/get_maintainer.pl should have picked me up due to K: spi_offload which matches this patch.

get_maintainers doesn't list you if run over ad4000.c.
If run over the patch file, get_maintainers lists many developers. Some of them don't seem to be related to this series, so I cropped the list to avoid churn. Will CC you on the next versions.

I use b4 these days, but IIRC, I used to use the --no-git-fallback option of get_maintainer.pl to prune the list while keeping actual matches from the MAINTAINERS file that shouldn't be pruned.

author maintainer
#8 lore raw

PATCH v2 3/5 Documentation: iio: ad4000: Add new supported parts

In reply to Marcelo Schmitt

Commit <c3948d090080> ("iio: adc: ad4000: Add support for PulSAR devices"), extended the ad4000 driver supports many single-channel PulSAR devices.

Update IIO ad4000 documentation with the extra list of supported devices.

---
 Documentation/iio/ad4000.rst | 17 ++++++++++++++++-
 1 file changed, 16 insertions(+), 1 deletion(-)
Documentation/iio/ad4000.rst +16 -1
index de8fd3ae6e62..5578a9cfd9d5 100644
@@ -4,7 +4,7 @@
 AD4000 driver
 =============
 
-Device driver for Analog Devices Inc. AD4000 series of ADCs.
+Device driver for Analog Devices Inc. AD4000 series of ADCs and similar devices.
 
 Supported devices
 =================
@@ -25,6 +25,21 @@ Supported devices
 * `AD4022 <https://www.analog.com/AD4022>`_
 * `ADAQ4001 <https://www.analog.com/ADAQ4001>`_
 * `ADAQ4003 <https://www.analog.com/ADAQ4003>`_
+* `AD7685 <https://www.analog.com/AD7685>`_
+* `AD7686 <https://www.analog.com/AD7686>`_
+* `AD7687 <https://www.analog.com/AD7687>`_
+* `AD7688 <https://www.analog.com/AD7688>`_
+* `AD7690 <https://www.analog.com/AD7690>`_
+* `AD7691 <https://www.analog.com/AD7691>`_
+* `AD7693 <https://www.analog.com/AD7693>`_
+* `AD7942 <https://www.analog.com/AD7942>`_
+* `AD7946 <https://www.analog.com/AD7946>`_
+* `AD7980 <https://www.analog.com/AD7980>`_
+* `AD7982 <https://www.analog.com/AD7982>`_
+* `AD7983 <https://www.analog.com/AD7983>`_
+* `AD7984 <https://www.analog.com/AD7984>`_
+* `AD7988-1 <https://www.analog.com/AD7988-1>`_
+* `AD7988-5 <https://www.analog.com/AD7988-5>`_
 
 Wiring connections
 ------------------
Signature · 1 line
2.47.2
reviewer Reviewed-by on v2 3/5
#9 lore raw

Re: [PATCH v2 3/5] Documentation: iio: ad4000: Add new supported parts

Quoted 7 lines · Marcelo Schmitt

Commit <c3948d090080> ("iio: adc: ad4000: Add support for PulSAR devices"), extended the ad4000 driver supports many single-channel PulSAR devices.

Update IIO ad4000 documentation with the extra list of supported devices.

---

author maintainer
#10 lore raw

PATCH v2 4/5 Documentation: iio: ad4000: Add IIO Device characteristics section

In reply to Marcelo Schmitt

Complement ad4000 IIO driver documentation with considerations about ``_scale_available`` attribute and table of typical channel attributes.

---
 Documentation/iio/ad4000.rst | 47 ++++++++++++++++++++++++++++++++++++
 1 file changed, 47 insertions(+)
Documentation/iio/ad4000.rst +47 -0
index 5578a9cfd9d5..468d30dc9214 100644
@@ -144,3 +144,50 @@ Set ``adi,sdi-pin`` to ``"cs"`` to select this mode.
                     ^                    |             |
                     +--------------------| SCLK        |
                                          +-------------+
+
+IIO Device characteristics
+==========================
+
+The AD4000 series driver supports differential and pseudo-differential ADCs.
+
+The span compression feature available in AD4000 series devices can be
+enabled/disabled by changing the ``_scale_available`` attribute of the voltage
+channel. Note that span compression configuration requires writing to AD4000
+configuration register, which is only possible when the ADC is wired in 3-wire
+turbo mode, and the SPI controller is ``SPI_MOSI_IDLE_HIGH`` capable. If those
+conditions are not met, no ``_scale_available`` attribute is provided.
+
+Besides that, differential and pseudo-differential voltage channels present
+slightly different sysfs interfaces.
+
+Pseudo-differential ADCs
+------------------------
+
+Typical voltage channel attributes of a pseudo-differential AD4000 series device:
+
++-------------------------------------------+------------------------------------------+
+| Voltage Channel Attributes                | Description                              |
++===========================================+==========================================+
+| ``in_voltage0_raw``                       | Raw ADC output code.                     |
++-------------------------------------------+------------------------------------------+
+| ``in_voltage0_offset``                    | Offset to convert raw value to mV.       |
++-------------------------------------------+------------------------------------------+
+| ``in_voltage0_scale``                     | Scale factor to convert raw value to mV. |
++-------------------------------------------+------------------------------------------+
+| ``in_voltage0_scale_available``           | Toggles input span compression           |
++-------------------------------------------+------------------------------------------+
+
+Differential ADCs
+-----------------
+
+Typical voltage channel attributes of a differential AD4000 series device:
+
++-------------------------------------------+------------------------------------------+
+| Voltage Channel Attributes                | Description                              |
++===========================================+==========================================+
+| ``in_voltage0-voltage1_raw``              | Raw ADC output code.                     |
++-------------------------------------------+------------------------------------------+
+| ``in_voltage0-voltage1_scale``            | Scale factor to convert raw value to mV. |
++-------------------------------------------+------------------------------------------+
+| ``in_voltage0-voltage1_scale_available``  | Toggles input span compression           |
++-------------------------------------------+------------------------------------------+
Signature · 1 line
2.47.2
reviewer Reviewed-by on v2 4/5
#11 lore raw

Re: [PATCH v2 4/5] Documentation: iio: ad4000: Add IIO Device characteristics section

Quoted 5 lines · Marcelo Schmitt

Complement ad4000 IIO driver documentation with considerations about ``_scale_available`` attribute and table of typical channel attributes.

---

With or without the suggested change:

Quoted 2 lines

+Differential ADCs
+-----------------

Could say Fully or True differential here to be less ambiguous if you like.

author maintainer
#12 lore raw

PATCH v2 5/5 Documentation: iio: ad4000: Describe offload support

In reply to Marcelo Schmitt

When SPI offloading is supported, the IIO device provides different sysfs interfaces to allow using the adjusting the sample rate. Document SPI offload support for AD4000 and similar devices.

---
 Documentation/iio/ad4000.rst | 22 ++++++++++++++++++++++
 1 file changed, 22 insertions(+)
Documentation/iio/ad4000.rst +22 -0
index 468d30dc9214..e490f9604b94 100644
@@ -191,3 +191,25 @@ Typical voltage channel attributes of a differential AD4000 series device:
 +-------------------------------------------+------------------------------------------+
 | ``in_voltage0-voltage1_scale_available``  | Toggles input span compression           |
 +-------------------------------------------+------------------------------------------+
+
+SPI offload support
+-------------------
+
+To be able to achieve the maximum sample rate, the driver can be used with the
+`AXI SPI Engine`_ to provide SPI offload support.
+
+.. _AXI SPI Engine: http://analogdevicesinc.github.io/hdl/projects/pulsar_adc/index.html
+
+When set for SPI offload support, the IIO device will provide different
+interfaces.
+
+* Either ``in_voltage0_sampling_frequency`` or
+  ``in_voltage0-voltage1_sampling_frequency`` file is provided to allow setting
+  the sample rate.
+* IIO trigger device is not provided (no ``trigger`` directory).
+* ``timestamp`` channel is not provided.
+
+Also, because the ADC output has a one sample latency (delay) when the device is
+wired in "3-wire" mode and only one transfer per sample is done when using SPI
+offloading, the first data sample in the buffer is not valid because it contains
+the output of an earlier conversion result.
Signature · 1 line
2.47.2
reviewer Reviewed-by on v2 5/5
#13 lore raw

Re: [PATCH v2 5/5] Documentation: iio: ad4000: Describe offload support

Quoted 6 lines · Marcelo Schmitt

When SPI offloading is supported, the IIO device provides different sysfs interfaces to allow using the adjusting the sample rate. Document SPI offload support for AD4000 and similar devices.

---