Skip to contentSkip to conversation

iio: amplifiers: update license information

PATCH Applied Alexandru Ardelean 3 participants 11 messages May 30, 2019 – Jun 8, 2019

Subsystems (3)
lore
Share & tools
lore
#0 lore raw

PATCH 1/5 iio: amplifiers: update license information

Use the new SPDX-License-Identifier tag to specify the license. For ad8366, also update copyright years in the header part.

---
 drivers/iio/amplifiers/Kconfig  | 1 +
 drivers/iio/amplifiers/ad8366.c | 5 ++---
 2 files changed, 3 insertions(+), 3 deletions(-)
drivers/iio/amplifiers/Kconfig +1 -0
index e9c5f2cd9257..da5830da9bcf 100644
@@ -1,3 +1,4 @@
+# SPDX-License-Identifier: GPL-2.0
 #
 # Gain Amplifiers, etc.
 #
drivers/iio/amplifiers/ad8366.c +2 -3
index 4b76b61ba4be..82ac15914ff3 100644
@@ -1,9 +1,8 @@
+// SPDX-License-Identifier: GPL-2.0
 /*
  * AD8366 SPI Dual-Digital Variable Gain Amplifier (VGA)
  *
- * Copyright 2012 Analog Devices Inc.
- *
- * Licensed under the GPL-2.
+ * Copyright 2012-2019 Analog Devices Inc.
  */
 
 #include <linux/device.h>
Signature · 1 line
2.20.1
#1 lore raw

PATCH 2/5 iio: amplifiers: ad8366: use own lock to guard state

This driver is still using iio_dev's mlock to guard against inconsistent state. This has been discouraged for some time.

This change switches to using it's own mutex, defined on the state struct.

---
 drivers/iio/amplifiers/ad8366.c | 10 ++++++----
 1 file changed, 6 insertions(+), 4 deletions(-)
drivers/iio/amplifiers/ad8366.c +6 -4
index 82ac15914ff3..24ff5475d9f2 100644
@@ -21,6 +21,7 @@
 struct ad8366_state {
 	struct spi_device	*spi;
 	struct regulator	*reg;
+	struct mutex            lock; /* protect sensor state */
 	unsigned char		ch[2];
 	/*
 	 * DMA (thus cache coherency maintenance) requires the
@@ -58,7 +59,7 @@ static int ad8366_read_raw(struct iio_dev *indio_dev,
 	int ret;
 	unsigned code;
 
-	mutex_lock(&indio_dev->mlock);
+	mutex_lock(&st->lock);
 	switch (m) {
 	case IIO_CHAN_INFO_HARDWAREGAIN:
 		code = st->ch[chan->channel];
@@ -73,7 +74,7 @@ static int ad8366_read_raw(struct iio_dev *indio_dev,
 	default:
 		ret = -EINVAL;
 	}
-	mutex_unlock(&indio_dev->mlock);
+	mutex_unlock(&st->lock);
 
 	return ret;
 };
@@ -99,7 +100,7 @@ static int ad8366_write_raw(struct iio_dev *indio_dev,
 
 	code = (code - 4500) / 253;
 
-	mutex_lock(&indio_dev->mlock);
+	mutex_lock(&st->lock);
 	switch (mask) {
 	case IIO_CHAN_INFO_HARDWAREGAIN:
 		st->ch[chan->channel] = code;
@@ -108,7 +109,7 @@ static int ad8366_write_raw(struct iio_dev *indio_dev,
 	default:
 		ret = -EINVAL;
 	}
-	mutex_unlock(&indio_dev->mlock);
+	mutex_unlock(&st->lock);
 
 	return ret;
 }
@@ -151,6 +152,7 @@ static int ad8366_probe(struct spi_device *spi)
 	}
 
 	spi_set_drvdata(spi, indio_dev);
+	mutex_init(&st->lock);
 	st->spi = spi;
 
 	indio_dev->dev.parent = &spi->dev;
Signature · 1 line
2.20.1
#2 lore raw

Re: [PATCH 2/5] iio: amplifiers: ad8366: use own lock to guard state

Quoted 6 lines · On Thu, 30 May 2019 16:18:09 +0300 Alexandru Ardelean…

This driver is still using iio_dev's mlock to guard against inconsistent state. This has been discouraged for some time.

This change switches to using it's own mutex, defined on the state struct.

Applied,

Thanks,

Jonathan

Quoted 60 lines
---
 drivers/iio/amplifiers/ad8366.c | 10 ++++++----
 1 file changed, 6 insertions(+), 4 deletions(-)
drivers/iio/amplifiers/ad8366.c +6 -4
index 82ac15914ff3..24ff5475d9f2 100644
@@ -21,6 +21,7 @@
 struct ad8366_state {
 	struct spi_device	*spi;
 	struct regulator	*reg;
+	struct mutex            lock; /* protect sensor state */
 	unsigned char		ch[2];
 	/*
 	 * DMA (thus cache coherency maintenance) requires the
@@ -58,7 +59,7 @@ static int ad8366_read_raw(struct iio_dev *indio_dev,
 	int ret;
 	unsigned code;
 
-	mutex_lock(&indio_dev->mlock);
+	mutex_lock(&st->lock);
 	switch (m) {
 	case IIO_CHAN_INFO_HARDWAREGAIN:
 		code = st->ch[chan->channel];
@@ -73,7 +74,7 @@ static int ad8366_read_raw(struct iio_dev *indio_dev,
 	default:
 		ret = -EINVAL;
 	}
-	mutex_unlock(&indio_dev->mlock);
+	mutex_unlock(&st->lock);
 
 	return ret;
 };
@@ -99,7 +100,7 @@ static int ad8366_write_raw(struct iio_dev *indio_dev,
 
 	code = (code - 4500) / 253;
 
-	mutex_lock(&indio_dev->mlock);
+	mutex_lock(&st->lock);
 	switch (mask) {
 	case IIO_CHAN_INFO_HARDWAREGAIN:
 		st->ch[chan->channel] = code;
@@ -108,7 +109,7 @@ static int ad8366_write_raw(struct iio_dev *indio_dev,
 	default:
 		ret = -EINVAL;
 	}
-	mutex_unlock(&indio_dev->mlock);
+	mutex_unlock(&st->lock);
 
 	return ret;
 }
@@ -151,6 +152,7 @@ static int ad8366_probe(struct spi_device *spi)
 	}
 
 	spi_set_drvdata(spi, indio_dev);
+	mutex_init(&st->lock);
 	st->spi = spi;
 
 	indio_dev->dev.parent = &spi->dev;
#3 lore raw

PATCH 3/5 iio: amplifiers: ad8366: rework driver to allow other chips

In reply to Alexandru Ardelean

The SPI gain amplifiers are simple devices, with 1 or 2 channels, to which are read-from/written-to.

The gain computation in ad8366_write_raw() has been updated to compute gain in dB for negative values.

This driver will be extended to support other chips as well. To do that, this rework handles the AD8366 device as a special-case (via switch-statements). This will make things easier when adding new chips.

---
 drivers/iio/amplifiers/ad8366.c | 81 +++++++++++++++++++++++++--------
 1 file changed, 62 insertions(+), 19 deletions(-)
drivers/iio/amplifiers/ad8366.c +62 -19
index 24ff5475d9f2..1beda6409301 100644
@@ -18,11 +18,22 @@
 #include <linux/iio/iio.h>
 #include <linux/iio/sysfs.h>
 
+enum ad8366_type {
+	ID_AD8366,
+};
+
+struct ad8366_info {
+	int gain_min;
+	int gain_max;
+};
+
 struct ad8366_state {
 	struct spi_device	*spi;
 	struct regulator	*reg;
 	struct mutex            lock; /* protect sensor state */
 	unsigned char		ch[2];
+	enum ad8366_type	type;
+	struct ad8366_info	*info;
 	/*
 	 * DMA (thus cache coherency maintenance) requires the
 	 * transfer buffers to live in their own cache lines.
@@ -30,19 +41,30 @@ struct ad8366_state {
 	unsigned char		data[2] ____cacheline_aligned;
 };
 
+static struct ad8366_info ad8366_infos[] = {
+	[ID_AD8366] = {
+		.gain_min = 4500,
+		.gain_max = 20500,
+	},
+};
+
 static int ad8366_write(struct iio_dev *indio_dev,
 			unsigned char ch_a, unsigned char ch_b)
 {
 	struct ad8366_state *st = iio_priv(indio_dev);
 	int ret;
 
-	ch_a = bitrev8(ch_a & 0x3F);
-	ch_b = bitrev8(ch_b & 0x3F);
+	switch (st->type) {
+	case ID_AD8366:
+		ch_a = bitrev8(ch_a & 0x3F);
+		ch_b = bitrev8(ch_b & 0x3F);
 
-	st->data[0] = ch_b >> 4;
-	st->data[1] = (ch_b << 4) | (ch_a >> 2);
+		st->data[0] = ch_b >> 4;
+		st->data[1] = (ch_b << 4) | (ch_a >> 2);
+		break;
+	}
 
-	ret = spi_write(st->spi, st->data, ARRAY_SIZE(st->data));
+	ret = spi_write(st->spi, st->data, indio_dev->num_channels);
 	if (ret < 0)
 		dev_err(&indio_dev->dev, "write failed (%d)", ret);
 
@@ -57,17 +79,22 @@ static int ad8366_read_raw(struct iio_dev *indio_dev,
 {
 	struct ad8366_state *st = iio_priv(indio_dev);
 	int ret;
-	unsigned code;
+	int code, gain = 0;
 
 	mutex_lock(&st->lock);
 	switch (m) {
 	case IIO_CHAN_INFO_HARDWAREGAIN:
 		code = st->ch[chan->channel];
 
+		switch (st->type) {
+		case ID_AD8366:
+			gain = code * 253 + 4500;
+			break;
+		}
+
 		/* Values in dB */
-		code = code * 253 + 4500;
-		*val = code / 1000;
-		*val2 = (code % 1000) * 1000;
+		*val = gain / 1000;
+		*val2 = (gain % 1000) * 1000;
 
 		ret = IIO_VAL_INT_PLUS_MICRO_DB;
 		break;
@@ -86,19 +113,24 @@ static int ad8366_write_raw(struct iio_dev *indio_dev,
 			    long mask)
 {
 	struct ad8366_state *st = iio_priv(indio_dev);
-	unsigned code;
+	struct ad8366_info *inf = st->info;
+	int code = 0, gain;
 	int ret;
 
-	if (val < 0 || val2 < 0)
-		return -EINVAL;
-
 	/* Values in dB */
-	code = (((u8)val * 1000) + ((u32)val2 / 1000));
+	if (val < 0)
+		gain = (val * 1000) - (val2 / 1000);
+	else
+		gain = (val * 1000) + (val2 / 1000);
 
-	if (code > 20500 || code < 4500)
+	if (gain > inf->gain_max || gain < inf->gain_min)
 		return -EINVAL;
 
-	code = (code - 4500) / 253;
+	switch (st->type) {
+	case ID_AD8366:
+		code = (gain - 4500) / 253;
+		break;
+	}
 
 	mutex_lock(&st->lock);
 	switch (mask) {
@@ -154,13 +186,24 @@ static int ad8366_probe(struct spi_device *spi)
 	spi_set_drvdata(spi, indio_dev);
 	mutex_init(&st->lock);
 	st->spi = spi;
+	st->type = spi_get_device_id(spi)->driver_data;
+
+	switch (st->type) {
+	case ID_AD8366:
+		indio_dev->channels = ad8366_channels;
+		indio_dev->num_channels = ARRAY_SIZE(ad8366_channels);
+		break;
+	default:
+		dev_err(&spi->dev, "Invalid device ID\n");
+		ret = -EINVAL;
+		goto error_disable_reg;
+	}
 
+	st->info = &ad8366_infos[st->type];
 	indio_dev->dev.parent = &spi->dev;
 	indio_dev->name = spi_get_device_id(spi)->name;
 	indio_dev->info = &ad8366_info;
 	indio_dev->modes = INDIO_DIRECT_MODE;
-	indio_dev->channels = ad8366_channels;
-	indio_dev->num_channels = ARRAY_SIZE(ad8366_channels);
 
 	ret = ad8366_write(indio_dev, 0 , 0);
 	if (ret < 0)
@@ -194,7 +237,7 @@ static int ad8366_remove(struct spi_device *spi)
 }
 
 static const struct spi_device_id ad8366_id[] = {
-	{"ad8366", 0},
+	{"ad8366",  ID_AD8366},
 	{}
 };
 MODULE_DEVICE_TABLE(spi, ad8366_id);
Signature · 1 line
2.20.1
#4 lore raw

Re: [PATCH 3/5] iio: amplifiers: ad8366: rework driver to allow other chips

Quoted 11 lines · On Thu, 30 May 2019 16:18:10 +0300 Alexandru Ardelean…

The SPI gain amplifiers are simple devices, with 1 or 2 channels, to which are read-from/written-to.

The gain computation in ad8366_write_raw() has been updated to compute gain in dB for negative values.

This driver will be extended to support other chips as well. To do that, this rework handles the AD8366 device as a special-case (via switch-statements). This will make things easier when adding new chips.

Looks good to me.

Applied to the togreg branch of iio.git and pushed out as testing for the autobuilders to play with it.

thanks,

Jonathan

Quoted 162 lines
---
 drivers/iio/amplifiers/ad8366.c | 81 +++++++++++++++++++++++++--------
 1 file changed, 62 insertions(+), 19 deletions(-)
drivers/iio/amplifiers/ad8366.c +62 -19
index 24ff5475d9f2..1beda6409301 100644
@@ -18,11 +18,22 @@
 #include <linux/iio/iio.h>
 #include <linux/iio/sysfs.h>
 
+enum ad8366_type {
+	ID_AD8366,
+};
+
+struct ad8366_info {
+	int gain_min;
+	int gain_max;
+};
+
 struct ad8366_state {
 	struct spi_device	*spi;
 	struct regulator	*reg;
 	struct mutex            lock; /* protect sensor state */
 	unsigned char		ch[2];
+	enum ad8366_type	type;
+	struct ad8366_info	*info;
 	/*
 	 * DMA (thus cache coherency maintenance) requires the
 	 * transfer buffers to live in their own cache lines.
@@ -30,19 +41,30 @@ struct ad8366_state {
 	unsigned char		data[2] ____cacheline_aligned;
 };
 
+static struct ad8366_info ad8366_infos[] = {
+	[ID_AD8366] = {
+		.gain_min = 4500,
+		.gain_max = 20500,
+	},
+};
+
 static int ad8366_write(struct iio_dev *indio_dev,
 			unsigned char ch_a, unsigned char ch_b)
 {
 	struct ad8366_state *st = iio_priv(indio_dev);
 	int ret;
 
-	ch_a = bitrev8(ch_a & 0x3F);
-	ch_b = bitrev8(ch_b & 0x3F);
+	switch (st->type) {
+	case ID_AD8366:
+		ch_a = bitrev8(ch_a & 0x3F);
+		ch_b = bitrev8(ch_b & 0x3F);
 
-	st->data[0] = ch_b >> 4;
-	st->data[1] = (ch_b << 4) | (ch_a >> 2);
+		st->data[0] = ch_b >> 4;
+		st->data[1] = (ch_b << 4) | (ch_a >> 2);
+		break;
+	}
 
-	ret = spi_write(st->spi, st->data, ARRAY_SIZE(st->data));
+	ret = spi_write(st->spi, st->data, indio_dev->num_channels);
 	if (ret < 0)
 		dev_err(&indio_dev->dev, "write failed (%d)", ret);
 
@@ -57,17 +79,22 @@ static int ad8366_read_raw(struct iio_dev *indio_dev,
 {
 	struct ad8366_state *st = iio_priv(indio_dev);
 	int ret;
-	unsigned code;
+	int code, gain = 0;
 
 	mutex_lock(&st->lock);
 	switch (m) {
 	case IIO_CHAN_INFO_HARDWAREGAIN:
 		code = st->ch[chan->channel];
 
+		switch (st->type) {
+		case ID_AD8366:
+			gain = code * 253 + 4500;
+			break;
+		}
+
 		/* Values in dB */
-		code = code * 253 + 4500;
-		*val = code / 1000;
-		*val2 = (code % 1000) * 1000;
+		*val = gain / 1000;
+		*val2 = (gain % 1000) * 1000;
 
 		ret = IIO_VAL_INT_PLUS_MICRO_DB;
 		break;
@@ -86,19 +113,24 @@ static int ad8366_write_raw(struct iio_dev *indio_dev,
 			    long mask)
 {
 	struct ad8366_state *st = iio_priv(indio_dev);
-	unsigned code;
+	struct ad8366_info *inf = st->info;
+	int code = 0, gain;
 	int ret;
 
-	if (val < 0 || val2 < 0)
-		return -EINVAL;
-
 	/* Values in dB */
-	code = (((u8)val * 1000) + ((u32)val2 / 1000));
+	if (val < 0)
+		gain = (val * 1000) - (val2 / 1000);
+	else
+		gain = (val * 1000) + (val2 / 1000);
 
-	if (code > 20500 || code < 4500)
+	if (gain > inf->gain_max || gain < inf->gain_min)
 		return -EINVAL;
 
-	code = (code - 4500) / 253;
+	switch (st->type) {
+	case ID_AD8366:
+		code = (gain - 4500) / 253;
+		break;
+	}
 
 	mutex_lock(&st->lock);
 	switch (mask) {
@@ -154,13 +186,24 @@ static int ad8366_probe(struct spi_device *spi)
 	spi_set_drvdata(spi, indio_dev);
 	mutex_init(&st->lock);
 	st->spi = spi;
+	st->type = spi_get_device_id(spi)->driver_data;
+
+	switch (st->type) {
+	case ID_AD8366:
+		indio_dev->channels = ad8366_channels;
+		indio_dev->num_channels = ARRAY_SIZE(ad8366_channels);
+		break;
+	default:
+		dev_err(&spi->dev, "Invalid device ID\n");
+		ret = -EINVAL;
+		goto error_disable_reg;
+	}
 
+	st->info = &ad8366_infos[st->type];
 	indio_dev->dev.parent = &spi->dev;
 	indio_dev->name = spi_get_device_id(spi)->name;
 	indio_dev->info = &ad8366_info;
 	indio_dev->modes = INDIO_DIRECT_MODE;
-	indio_dev->channels = ad8366_channels;
-	indio_dev->num_channels = ARRAY_SIZE(ad8366_channels);
 
 	ret = ad8366_write(indio_dev, 0 , 0);
 	if (ret < 0)
@@ -194,7 +237,7 @@ static int ad8366_remove(struct spi_device *spi)
 }
 
 static const struct spi_device_id ad8366_id[] = {
-	{"ad8366", 0},
+	{"ad8366",  ID_AD8366},
 	{}
 };
 MODULE_DEVICE_TABLE(spi, ad8366_id);
#5 lore raw

PATCH 4/5 iio: amplifiers: ad8366: Add support for the ADA4961 DGA

In reply to Alexandru Ardelean

From: Paul Cercueil <[email protected]>

This change adds support for the ADA4961 BiCMOS RF Digital Gain Amplifier, (DGA), which is optimized for driving heavy loads out 2.0 GHz and beyond. The device typically achieves -90 dBc IMD3 performance at 500 MHz and -85 dBc at 1.5 GHz.

Datasheet link:
http://www.analog.com/media/en/technical-documentation/data-sheets/ADA4961.pdf

This change re-uses the existing ad8366 driver, as most logic is similar. Also, this chip has a reset pin which is initialized during probe.

---
 drivers/iio/amplifiers/Kconfig  |  9 ++++++---
 drivers/iio/amplifiers/ad8366.c | 34 +++++++++++++++++++++++++++++++--
 2 files changed, 38 insertions(+), 5 deletions(-)
drivers/iio/amplifiers/Kconfig +6 -3
index da5830da9bcf..259058da8811 100644
@@ -7,12 +7,15 @@
 menu "Amplifiers"
 
 config AD8366
-	tristate "Analog Devices AD8366 VGA"
+	tristate "Analog Devices AD8366 and similar Gain Amplifiers"
 	depends on SPI
 	select BITREVERSE
 	help
-	  Say yes here to build support for Analog Devices AD8366
-	  SPI Dual-Digital Variable Gain Amplifier (VGA).
+	  Say yes here to build support for Analog Devices AD8366 and similar
+	  gain amplifiers. This driver supports the following gain amplifiers
+	  from Analog Devices:
+	    AD8366 Dual-Digital Variable Gain Amplifier (VGA)
+	    ADA4961 BiCMOS RF Digital Gain Amplifier (DGA)
 
 	  To compile this driver as a module, choose M here: the
 	  module will be called ad8366.
drivers/iio/amplifiers/ad8366.c +32 -2
index 1beda6409301..0a9883e8eb2e 100644
@@ -1,6 +1,9 @@
 // SPDX-License-Identifier: GPL-2.0
 /*
- * AD8366 SPI Dual-Digital Variable Gain Amplifier (VGA)
+ * AD8366 and similar Gain Amplifiers
+ * This driver supports the following gain amplifiers:
+ *   AD8366 Dual-Digital Variable Gain Amplifier (VGA)
+ *   ADA4961 BiCMOS RF Digital Gain Amplifier (DGA)
  *
  * Copyright 2012-2019 Analog Devices Inc.
  */
@@ -11,6 +14,7 @@
 #include <linux/sysfs.h>
 #include <linux/spi/spi.h>
 #include <linux/regulator/consumer.h>
+#include <linux/gpio/consumer.h>
 #include <linux/err.h>
 #include <linux/module.h>
 #include <linux/bitrev.h>
@@ -20,6 +24,7 @@
 
 enum ad8366_type {
 	ID_AD8366,
+	ID_ADA4961,
 };
 
 struct ad8366_info {
@@ -31,6 +36,7 @@ struct ad8366_state {
 	struct spi_device	*spi;
 	struct regulator	*reg;
 	struct mutex            lock; /* protect sensor state */
+	struct gpio_desc	*reset_gpio;
 	unsigned char		ch[2];
 	enum ad8366_type	type;
 	struct ad8366_info	*info;
@@ -46,6 +52,10 @@ static struct ad8366_info ad8366_infos[] = {
 		.gain_min = 4500,
 		.gain_max = 20500,
 	},
+	[ID_ADA4961] = {
+		.gain_min = -6000,
+		.gain_max = 15000,
+	},
 };
 
 static int ad8366_write(struct iio_dev *indio_dev,
@@ -62,6 +72,9 @@ static int ad8366_write(struct iio_dev *indio_dev,
 		st->data[0] = ch_b >> 4;
 		st->data[1] = (ch_b << 4) | (ch_a >> 2);
 		break;
+	case ID_ADA4961:
+		st->data[0] = ch_a & 0x1F;
+		break;
 	}
 
 	ret = spi_write(st->spi, st->data, indio_dev->num_channels);
@@ -90,6 +103,9 @@ static int ad8366_read_raw(struct iio_dev *indio_dev,
 		case ID_AD8366:
 			gain = code * 253 + 4500;
 			break;
+		case ID_ADA4961:
+			gain = 15000 - code * 1000;
+			break;
 		}
 
 		/* Values in dB */
@@ -130,6 +146,9 @@ static int ad8366_write_raw(struct iio_dev *indio_dev,
 	case ID_AD8366:
 		code = (gain - 4500) / 253;
 		break;
+	case ID_ADA4961:
+		code = (15000 - gain) / 1000;
+		break;
 	}
 
 	mutex_lock(&st->lock);
@@ -164,6 +183,10 @@ static const struct iio_chan_spec ad8366_channels[] = {
 	AD8366_CHAN(1),
 };
 
+static const struct iio_chan_spec ada4961_channels[] = {
+	AD8366_CHAN(0),
+};
+
 static int ad8366_probe(struct spi_device *spi)
 {
 	struct iio_dev *indio_dev;
@@ -193,6 +216,12 @@ static int ad8366_probe(struct spi_device *spi)
 		indio_dev->channels = ad8366_channels;
 		indio_dev->num_channels = ARRAY_SIZE(ad8366_channels);
 		break;
+	case ID_ADA4961:
+		st->reset_gpio = devm_gpiod_get(&spi->dev, "reset",
+			GPIOD_OUT_HIGH);
+		indio_dev->channels = ada4961_channels;
+		indio_dev->num_channels = ARRAY_SIZE(ada4961_channels);
+		break;
 	default:
 		dev_err(&spi->dev, "Invalid device ID\n");
 		ret = -EINVAL;
@@ -238,6 +267,7 @@ static int ad8366_remove(struct spi_device *spi)
 
 static const struct spi_device_id ad8366_id[] = {
 	{"ad8366",  ID_AD8366},
+	{"ada4961", ID_ADA4961},
 	{}
 };
 MODULE_DEVICE_TABLE(spi, ad8366_id);
@@ -254,5 +284,5 @@ static struct spi_driver ad8366_driver = {
 module_spi_driver(ad8366_driver);
 
 MODULE_AUTHOR("Michael Hennerich <[email protected]>");
-MODULE_DESCRIPTION("Analog Devices AD8366 VGA");
+MODULE_DESCRIPTION("Analog Devices AD8366 and similar Gain Amplifiers");
 MODULE_LICENSE("GPL v2");
Signature · 1 line
2.20.1
#6 lore raw

Re: [PATCH 4/5] iio: amplifiers: ad8366: Add support for the ADA4961 DGA

Quoted 10 lines · On Thu, 30 May 2019 16:18:11 +0300 Alexandru Ardelean…

From: Paul Cercueil <[email protected]>

This change adds support for the ADA4961 BiCMOS RF Digital Gain Amplifier, (DGA), which is optimized for driving heavy loads out 2.0 GHz and beyond. The device typically achieves -90 dBc IMD3 performance at 500 MHz and -85 dBc at 1.5 GHz.

Datasheet link:
http://www.analog.com/media/en/technical-documentation/data-sheets/ADA4961.pdf

Quoted 6 lines

This change re-uses the existing ad8366 driver, as most logic is similar. Also, this chip has a reset pin which is initialized during probe.

I'm fairly sure you want a GPIOLIB kconfig dependency. I've added it rather than going for a v2 for just that. Give me a shout if it's not actually required!

Applied to the togreg branch of iio.git and pushed out as testing for the autobuilders to play with it.

Thanks,

Jonathan

Quoted 44 lines
---
 drivers/iio/amplifiers/Kconfig  |  9 ++++++---
 drivers/iio/amplifiers/ad8366.c | 34 +++++++++++++++++++++++++++++++--
 2 files changed, 38 insertions(+), 5 deletions(-)
drivers/iio/amplifiers/Kconfig +6 -3
index da5830da9bcf..259058da8811 100644
@@ -7,12 +7,15 @@
 menu "Amplifiers"
 
 config AD8366
-	tristate "Analog Devices AD8366 VGA"
+	tristate "Analog Devices AD8366 and similar Gain Amplifiers"
 	depends on SPI
 	select BITREVERSE
 	help
-	  Say yes here to build support for Analog Devices AD8366
-	  SPI Dual-Digital Variable Gain Amplifier (VGA).
+	  Say yes here to build support for Analog Devices AD8366 and similar
+	  gain amplifiers. This driver supports the following gain amplifiers
+	  from Analog Devices:
+	    AD8366 Dual-Digital Variable Gain Amplifier (VGA)
+	    ADA4961 BiCMOS RF Digital Gain Amplifier (DGA)
 
 	  To compile this driver as a module, choose M here: the
 	  module will be called ad8366.
drivers/iio/amplifiers/ad8366.c +4 -1
index 1beda6409301..0a9883e8eb2e 100644
@@ -1,6 +1,9 @@
 // SPDX-License-Identifier: GPL-2.0
 /*
- * AD8366 SPI Dual-Digital Variable Gain Amplifier (VGA)
+ * AD8366 and similar Gain Amplifiers
+ * This driver supports the following gain amplifiers:
+ *   AD8366 Dual-Digital Variable Gain Amplifier (VGA)
+ *   ADA4961 BiCMOS RF Digital Gain Amplifier (DGA)
  *
  * Copyright 2012-2019 Analog Devices Inc.
  */

drivers/iio/amplifiers/ad8366.c line 17

Quoted 4 lines
drivers/iio/amplifiers/ad8366.c +1 -0
@@ -11,6 +14,7 @@
 #include <linux/sysfs.h>
 #include <linux/spi/spi.h>
 #include <linux/regulator/consumer.h>
+#include <linux/gpio/consumer.h>

I'd be highly surprised if this didn't need a KCONFIG dependency change...

Quoted 99 lines
drivers/iio/amplifiers/ad8366.c +27 -1
 #include <linux/err.h>
 #include <linux/module.h>
 #include <linux/bitrev.h>
@@ -20,6 +24,7 @@
 
 enum ad8366_type {
 	ID_AD8366,
+	ID_ADA4961,
 };
 
 struct ad8366_info {
@@ -31,6 +36,7 @@ struct ad8366_state {
 	struct spi_device	*spi;
 	struct regulator	*reg;
 	struct mutex            lock; /* protect sensor state */
+	struct gpio_desc	*reset_gpio;
 	unsigned char		ch[2];
 	enum ad8366_type	type;
 	struct ad8366_info	*info;
@@ -46,6 +52,10 @@ static struct ad8366_info ad8366_infos[] = {
 		.gain_min = 4500,
 		.gain_max = 20500,
 	},
+	[ID_ADA4961] = {
+		.gain_min = -6000,
+		.gain_max = 15000,
+	},
 };
 
 static int ad8366_write(struct iio_dev *indio_dev,
@@ -62,6 +72,9 @@ static int ad8366_write(struct iio_dev *indio_dev,
 		st->data[0] = ch_b >> 4;
 		st->data[1] = (ch_b << 4) | (ch_a >> 2);
 		break;
+	case ID_ADA4961:
+		st->data[0] = ch_a & 0x1F;
+		break;
 	}
 
 	ret = spi_write(st->spi, st->data, indio_dev->num_channels);
@@ -90,6 +103,9 @@ static int ad8366_read_raw(struct iio_dev *indio_dev,
 		case ID_AD8366:
 			gain = code * 253 + 4500;
 			break;
+		case ID_ADA4961:
+			gain = 15000 - code * 1000;
+			break;
 		}
 
 		/* Values in dB */
@@ -130,6 +146,9 @@ static int ad8366_write_raw(struct iio_dev *indio_dev,
 	case ID_AD8366:
 		code = (gain - 4500) / 253;
 		break;
+	case ID_ADA4961:
+		code = (15000 - gain) / 1000;
+		break;
 	}
 
 	mutex_lock(&st->lock);
@@ -164,6 +183,10 @@ static const struct iio_chan_spec ad8366_channels[] = {
 	AD8366_CHAN(1),
 };
 
+static const struct iio_chan_spec ada4961_channels[] = {
+	AD8366_CHAN(0),
+};
+
 static int ad8366_probe(struct spi_device *spi)
 {
 	struct iio_dev *indio_dev;
@@ -193,6 +216,12 @@ static int ad8366_probe(struct spi_device *spi)
 		indio_dev->channels = ad8366_channels;
 		indio_dev->num_channels = ARRAY_SIZE(ad8366_channels);
 		break;
+	case ID_ADA4961:
+		st->reset_gpio = devm_gpiod_get(&spi->dev, "reset",
+			GPIOD_OUT_HIGH);
+		indio_dev->channels = ada4961_channels;
+		indio_dev->num_channels = ARRAY_SIZE(ada4961_channels);
+		break;
 	default:
 		dev_err(&spi->dev, "Invalid device ID\n");
 		ret = -EINVAL;
@@ -238,6 +267,7 @@ static int ad8366_remove(struct spi_device *spi)
 
 static const struct spi_device_id ad8366_id[] = {
 	{"ad8366",  ID_AD8366},
+	{"ada4961", ID_ADA4961},
 	{}
 };
 MODULE_DEVICE_TABLE(spi, ad8366_id);
@@ -254,5 +284,5 @@ static struct spi_driver ad8366_driver = {
 module_spi_driver(ad8366_driver);
 
 MODULE_AUTHOR("Michael Hennerich <[email protected]>");
-MODULE_DESCRIPTION("Analog Devices AD8366 VGA");
+MODULE_DESCRIPTION("Analog Devices AD8366 and similar Gain Amplifiers");
 MODULE_LICENSE("GPL v2");
#7 lore raw

Re: [PATCH 4/5] iio: amplifiers: ad8366: Add support for the ADA4961 DGA

Quoted 21 lines · Jonathan Cameron
Quoted 10 lines · On Thu, 30 May 2019 16:18:11 +0300 Alexandru Ardelean…

From: Paul Cercueil <[email protected]>

This change adds support for the ADA4961 BiCMOS RF Digital Gain Amplifier, (DGA), which is optimized for driving heavy loads out 2.0 GHz and beyond. The device typically achieves -90 dBc IMD3 performance at 500 MHz and -85 dBc at 1.5 GHz.

Datasheet link:
http://www.analog.com/media/en/technical-documentation/data-sheets/ADA4961.pdf

Quoted 6 lines

This change re-uses the existing ad8366 driver, as most logic is similar. Also, this chip has a reset pin which is initialized during probe.

Quoted 7 lines

I'm fairly sure you want a GPIOLIB kconfig dependency. I've added it rather than going for a v2 for just that. Give me a shout if it's not actually required!

Applied to the togreg branch of iio.git and pushed out as testing for the autobuilders to play with it.

oops
thanks for catching this

Alex

Quoted 155 lines

Thanks,

Jonathan

Quoted 44 lines
---
 drivers/iio/amplifiers/Kconfig  |  9 ++++++---
 drivers/iio/amplifiers/ad8366.c | 34 +++++++++++++++++++++++++++++++--
 2 files changed, 38 insertions(+), 5 deletions(-)
drivers/iio/amplifiers/Kconfig +6 -3
index da5830da9bcf..259058da8811 100644
@@ -7,12 +7,15 @@
 menu "Amplifiers"
 
 config AD8366
-     tristate "Analog Devices AD8366 VGA"
+     tristate "Analog Devices AD8366 and similar Gain Amplifiers"
      depends on SPI
      select BITREVERSE
      help
-       Say yes here to build support for Analog Devices AD8366
-       SPI Dual-Digital Variable Gain Amplifier (VGA).
+       Say yes here to build support for Analog Devices AD8366 and similar
+       gain amplifiers. This driver supports the following gain amplifiers
+       from Analog Devices:
+         AD8366 Dual-Digital Variable Gain Amplifier (VGA)
+         ADA4961 BiCMOS RF Digital Gain Amplifier (DGA)
 
        To compile this driver as a module, choose M here: the
        module will be called ad8366.
drivers/iio/amplifiers/ad8366.c +4 -1
index 1beda6409301..0a9883e8eb2e 100644
@@ -1,6 +1,9 @@
 // SPDX-License-Identifier: GPL-2.0
 /*
- * AD8366 SPI Dual-Digital Variable Gain Amplifier (VGA)
+ * AD8366 and similar Gain Amplifiers
+ * This driver supports the following gain amplifiers:
+ *   AD8366 Dual-Digital Variable Gain Amplifier (VGA)
+ *   ADA4961 BiCMOS RF Digital Gain Amplifier (DGA)
  *
  * Copyright 2012-2019 Analog Devices Inc.
  */

drivers/iio/amplifiers/ad8366.c line 17

Quoted 4 lines
drivers/iio/amplifiers/ad8366.c +1 -0
@@ -11,6 +14,7 @@
 #include <linux/sysfs.h>
 #include <linux/spi/spi.h>
 #include <linux/regulator/consumer.h>
+#include <linux/gpio/consumer.h>

I'd be highly surprised if this didn't need a KCONFIG dependency change...

Quoted 99 lines
drivers/iio/amplifiers/ad8366.c +27 -1
 #include <linux/err.h>
 #include <linux/module.h>
 #include <linux/bitrev.h>
@@ -20,6 +24,7 @@
 
 enum ad8366_type {
      ID_AD8366,
+     ID_ADA4961,
 };
 
 struct ad8366_info {
@@ -31,6 +36,7 @@ struct ad8366_state {
      struct spi_device       *spi;
      struct regulator        *reg;
      struct mutex            lock; /* protect sensor state */
+     struct gpio_desc        *reset_gpio;
      unsigned char           ch[2];
      enum ad8366_type        type;
      struct ad8366_info      *info;
@@ -46,6 +52,10 @@ static struct ad8366_info ad8366_infos[] = {
              .gain_min = 4500,
              .gain_max = 20500,
      },
+     [ID_ADA4961] = {
+             .gain_min = -6000,
+             .gain_max = 15000,
+     },
 };
 
 static int ad8366_write(struct iio_dev *indio_dev,
@@ -62,6 +72,9 @@ static int ad8366_write(struct iio_dev *indio_dev,
              st->data[0] = ch_b >> 4;
              st->data[1] = (ch_b << 4) | (ch_a >> 2);
              break;
+     case ID_ADA4961:
+             st->data[0] = ch_a & 0x1F;
+             break;
      }
 
      ret = spi_write(st->spi, st->data, indio_dev->num_channels);
@@ -90,6 +103,9 @@ static int ad8366_read_raw(struct iio_dev *indio_dev,
              case ID_AD8366:
                      gain = code * 253 + 4500;
                      break;
+             case ID_ADA4961:
+                     gain = 15000 - code * 1000;
+                     break;
              }
 
              /* Values in dB */
@@ -130,6 +146,9 @@ static int ad8366_write_raw(struct iio_dev *indio_dev,
      case ID_AD8366:
              code = (gain - 4500) / 253;
              break;
+     case ID_ADA4961:
+             code = (15000 - gain) / 1000;
+             break;
      }
 
      mutex_lock(&st->lock);
@@ -164,6 +183,10 @@ static const struct iio_chan_spec ad8366_channels[] = {
      AD8366_CHAN(1),
 };
 
+static const struct iio_chan_spec ada4961_channels[] = {
+     AD8366_CHAN(0),
+};
+
 static int ad8366_probe(struct spi_device *spi)
 {
      struct iio_dev *indio_dev;
@@ -193,6 +216,12 @@ static int ad8366_probe(struct spi_device *spi)
              indio_dev->channels = ad8366_channels;
              indio_dev->num_channels = ARRAY_SIZE(ad8366_channels);
              break;
+     case ID_ADA4961:
+             st->reset_gpio = devm_gpiod_get(&spi->dev, "reset",
+                     GPIOD_OUT_HIGH);
+             indio_dev->channels = ada4961_channels;
+             indio_dev->num_channels = ARRAY_SIZE(ada4961_channels);
+             break;
      default:
              dev_err(&spi->dev, "Invalid device ID\n");
              ret = -EINVAL;
@@ -238,6 +267,7 @@ static int ad8366_remove(struct spi_device *spi)
 
 static const struct spi_device_id ad8366_id[] = {
      {"ad8366",  ID_AD8366},
+     {"ada4961", ID_ADA4961},
      {}
 };
 MODULE_DEVICE_TABLE(spi, ad8366_id);
@@ -254,5 +284,5 @@ static struct spi_driver ad8366_driver = {
 module_spi_driver(ad8366_driver);
 
 MODULE_AUTHOR("Michael Hennerich <[email protected]>");
-MODULE_DESCRIPTION("Analog Devices AD8366 VGA");
+MODULE_DESCRIPTION("Analog Devices AD8366 and similar Gain Amplifiers");
 MODULE_LICENSE("GPL v2");
#8 lore raw

PATCH 5/5 iio: amplifiers: ad8366: Add support for ADL5240 VGA

In reply to Alexandru Ardelean

The ADL5240 is a high performance, digitally controlled variable gain amplifier (VGA) operating from 100 MHz to 4000 MHz. The VGA integrates a high performance, 20 dB gain, internally matched amplifier (AMP) with a 6-bit digital step attenuator (DSA) that has a gain control range of 31.5 dB in 0.5 dB steps with ±0.25 dB step accuracy.

Datasheet link:
https://www.analog.com/media/en/technical-documentation/data-sheets/adl5240.pdf

---
 drivers/iio/amplifiers/Kconfig  |  1 +
 drivers/iio/amplifiers/ad8366.c | 17 +++++++++++++++++
 2 files changed, 18 insertions(+)
drivers/iio/amplifiers/Kconfig +1 -0
index 259058da8811..871e8060d996 100644
@@ -16,6 +16,7 @@ config AD8366
 	  from Analog Devices:
 	    AD8366 Dual-Digital Variable Gain Amplifier (VGA)
 	    ADA4961 BiCMOS RF Digital Gain Amplifier (DGA)
+	    ADL5240 Digitally controlled variable gain amplifier (VGA)
 
 	  To compile this driver as a module, choose M here: the
 	  module will be called ad8366.
drivers/iio/amplifiers/ad8366.c +17 -0
index 0a9883e8eb2e..0176d3d8cc9c 100644
@@ -4,6 +4,7 @@
  * This driver supports the following gain amplifiers:
  *   AD8366 Dual-Digital Variable Gain Amplifier (VGA)
  *   ADA4961 BiCMOS RF Digital Gain Amplifier (DGA)
+ *   ADL5240 Digitally controlled variable gain amplifier (VGA)
  *
  * Copyright 2012-2019 Analog Devices Inc.
  */
@@ -25,6 +26,7 @@
 enum ad8366_type {
 	ID_AD8366,
 	ID_ADA4961,
+	ID_ADL5240,
 };
 
 struct ad8366_info {
@@ -56,6 +58,10 @@ static struct ad8366_info ad8366_infos[] = {
 		.gain_min = -6000,
 		.gain_max = 15000,
 	},
+	[ID_ADL5240] = {
+		.gain_min = -11500,
+		.gain_max = 20000,
+	},
 };
 
 static int ad8366_write(struct iio_dev *indio_dev,
@@ -75,6 +81,9 @@ static int ad8366_write(struct iio_dev *indio_dev,
 	case ID_ADA4961:
 		st->data[0] = ch_a & 0x1F;
 		break;
+	case ID_ADL5240:
+		st->data[0] = (ch_a & 0x3F);
+		break;
 	}
 
 	ret = spi_write(st->spi, st->data, indio_dev->num_channels);
@@ -106,6 +115,9 @@ static int ad8366_read_raw(struct iio_dev *indio_dev,
 		case ID_ADA4961:
 			gain = 15000 - code * 1000;
 			break;
+		case ID_ADL5240:
+			gain = 20000 - 31500 + code * 500;
+			break;
 		}
 
 		/* Values in dB */
@@ -149,6 +161,9 @@ static int ad8366_write_raw(struct iio_dev *indio_dev,
 	case ID_ADA4961:
 		code = (15000 - gain) / 1000;
 		break;
+	case ID_ADL5240:
+		code = ((gain - 500 - 20000) / 500) & 0x3F;
+		break;
 	}
 
 	mutex_lock(&st->lock);
@@ -217,6 +232,7 @@ static int ad8366_probe(struct spi_device *spi)
 		indio_dev->num_channels = ARRAY_SIZE(ad8366_channels);
 		break;
 	case ID_ADA4961:
+	case ID_ADL5240:
 		st->reset_gpio = devm_gpiod_get(&spi->dev, "reset",
 			GPIOD_OUT_HIGH);
 		indio_dev->channels = ada4961_channels;
@@ -268,6 +284,7 @@ static int ad8366_remove(struct spi_device *spi)
 static const struct spi_device_id ad8366_id[] = {
 	{"ad8366",  ID_AD8366},
 	{"ada4961", ID_ADA4961},
+	{"adl5240", ID_ADL5240},
 	{}
 };
 MODULE_DEVICE_TABLE(spi, ad8366_id);
Signature · 1 line
2.20.1
#9 lore raw

Re: [PATCH 5/5] iio: amplifiers: ad8366: Add support for ADL5240 VGA

Quoted 10 lines · On Thu, 30 May 2019 16:18:12 +0300 Alexandru Ardelean…

The ADL5240 is a high performance, digitally controlled variable gain amplifier (VGA) operating from 100 MHz to 4000 MHz. The VGA integrates a high performance, 20 dB gain, internally matched amplifier (AMP) with a 6-bit digital step attenuator (DSA) that has a gain control range of 31.5 dB in 0.5 dB steps with ±0.25 dB step accuracy.

Datasheet link:
https://www.analog.com/media/en/technical-documentation/data-sheets/adl5240.pdf

Applied to the togreg branch of iio.git and pushed out as testing for the autobuilders to play with it.

Thanks,

Jonathan

Quoted 94 lines
---
 drivers/iio/amplifiers/Kconfig  |  1 +
 drivers/iio/amplifiers/ad8366.c | 17 +++++++++++++++++
 2 files changed, 18 insertions(+)
drivers/iio/amplifiers/Kconfig +1 -0
index 259058da8811..871e8060d996 100644
@@ -16,6 +16,7 @@ config AD8366
 	  from Analog Devices:
 	    AD8366 Dual-Digital Variable Gain Amplifier (VGA)
 	    ADA4961 BiCMOS RF Digital Gain Amplifier (DGA)
+	    ADL5240 Digitally controlled variable gain amplifier (VGA)
 
 	  To compile this driver as a module, choose M here: the
 	  module will be called ad8366.
drivers/iio/amplifiers/ad8366.c +17 -0
index 0a9883e8eb2e..0176d3d8cc9c 100644
@@ -4,6 +4,7 @@
  * This driver supports the following gain amplifiers:
  *   AD8366 Dual-Digital Variable Gain Amplifier (VGA)
  *   ADA4961 BiCMOS RF Digital Gain Amplifier (DGA)
+ *   ADL5240 Digitally controlled variable gain amplifier (VGA)
  *
  * Copyright 2012-2019 Analog Devices Inc.
  */
@@ -25,6 +26,7 @@
 enum ad8366_type {
 	ID_AD8366,
 	ID_ADA4961,
+	ID_ADL5240,
 };
 
 struct ad8366_info {
@@ -56,6 +58,10 @@ static struct ad8366_info ad8366_infos[] = {
 		.gain_min = -6000,
 		.gain_max = 15000,
 	},
+	[ID_ADL5240] = {
+		.gain_min = -11500,
+		.gain_max = 20000,
+	},
 };
 
 static int ad8366_write(struct iio_dev *indio_dev,
@@ -75,6 +81,9 @@ static int ad8366_write(struct iio_dev *indio_dev,
 	case ID_ADA4961:
 		st->data[0] = ch_a & 0x1F;
 		break;
+	case ID_ADL5240:
+		st->data[0] = (ch_a & 0x3F);
+		break;
 	}
 
 	ret = spi_write(st->spi, st->data, indio_dev->num_channels);
@@ -106,6 +115,9 @@ static int ad8366_read_raw(struct iio_dev *indio_dev,
 		case ID_ADA4961:
 			gain = 15000 - code * 1000;
 			break;
+		case ID_ADL5240:
+			gain = 20000 - 31500 + code * 500;
+			break;
 		}
 
 		/* Values in dB */
@@ -149,6 +161,9 @@ static int ad8366_write_raw(struct iio_dev *indio_dev,
 	case ID_ADA4961:
 		code = (15000 - gain) / 1000;
 		break;
+	case ID_ADL5240:
+		code = ((gain - 500 - 20000) / 500) & 0x3F;
+		break;
 	}
 
 	mutex_lock(&st->lock);
@@ -217,6 +232,7 @@ static int ad8366_probe(struct spi_device *spi)
 		indio_dev->num_channels = ARRAY_SIZE(ad8366_channels);
 		break;
 	case ID_ADA4961:
+	case ID_ADL5240:
 		st->reset_gpio = devm_gpiod_get(&spi->dev, "reset",
 			GPIOD_OUT_HIGH);
 		indio_dev->channels = ada4961_channels;
@@ -268,6 +284,7 @@ static int ad8366_remove(struct spi_device *spi)
 static const struct spi_device_id ad8366_id[] = {
 	{"ad8366",  ID_AD8366},
 	{"ada4961", ID_ADA4961},
+	{"adl5240", ID_ADL5240},
 	{}
 };
 MODULE_DEVICE_TABLE(spi, ad8366_id);
#10 lore raw
In reply to Alexandru Ardelean
Quoted 4 lines · On Thu, 30 May 2019 16:18:08 +0300 Alexandru Ardelean…

Use the new SPDX-License-Identifier tag to specify the license. For ad8366, also update copyright years in the header part.

Applied to the togreg branch of iio.git and pushed out as testing for the autobuilders to ignore

Thanks,

Jonathan

Quoted 30 lines
---
 drivers/iio/amplifiers/Kconfig  | 1 +
 drivers/iio/amplifiers/ad8366.c | 5 ++---
 2 files changed, 3 insertions(+), 3 deletions(-)
drivers/iio/amplifiers/Kconfig +1 -0
index e9c5f2cd9257..da5830da9bcf 100644
@@ -1,3 +1,4 @@
+# SPDX-License-Identifier: GPL-2.0
 #
 # Gain Amplifiers, etc.
 #
drivers/iio/amplifiers/ad8366.c +2 -3
index 4b76b61ba4be..82ac15914ff3 100644
@@ -1,9 +1,8 @@
+// SPDX-License-Identifier: GPL-2.0
 /*
  * AD8366 SPI Dual-Digital Variable Gain Amplifier (VGA)
  *
- * Copyright 2012 Analog Devices Inc.
- *
- * Licensed under the GPL-2.
+ * Copyright 2012-2019 Analog Devices Inc.
  */
 
 #include <linux/device.h>