iio: adc: rzg2l_adc: Use adc-helpers

The new devm_iio_adc_device_alloc_chaninfo_se() -helper is intended to
help drivers avoid open-coding the for_each_node -loop for getting the
channel IDs. The helper provides standard way to detect the ADC channel
nodes (by the node name), and a standard way to convert the "reg"
-properties to channel identification numbers, used in the struct
iio_chan_spec. Furthermore, the helper can optionally check the found
channel IDs are smaller than given maximum. This is useful for callers
which later use the IDs for example for indexing a channel data array.

The original driver treated all found child nodes as channel nodes. The
new helper requires channel nodes to be named channel[@N]. This should
help avoid problems with devices which may contain also other but ADC
child nodes. Quick grep from arch/* with the rzg2l_adc's compatible
string didn't reveal any in-tree .dts with channel nodes named
otherwise. Also, same grep shows all the .dts seem to have channel IDs
between 0..num of channels.

Use the new helper.

Signed-off-by: Matti Vaittinen <mazziesaccount@gmail.com>
Reviewed-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com>
Tested-by: Claudiu Beznea <claudiu.beznea.uj@bp.renesas.com>
Reviewed-by: Claudiu Beznea <claudiu.beznea.uj@bp.renesas.com>
Link: https://patch.msgid.link/e84ccff01070eaee3dd1ae2d7e109f963168f586.1742560649.git.mazziesaccount@gmail.com
Signed-off-by: Jonathan Cameron <Jonathan.Cameron@huawei.com>
This commit is contained in:
Matti Vaittinen 2025-03-24 09:13:16 +02:00 committed by Jonathan Cameron
parent f3a8f870fa
commit 2d17ed10e4
2 changed files with 17 additions and 23 deletions

View File

@ -1266,6 +1266,7 @@ config RICHTEK_RTQ6056
config RZG2L_ADC
tristate "Renesas RZ/G2L ADC driver"
depends on ARCH_RZG2L || COMPILE_TEST
select IIO_ADC_HELPER
help
Say yes here to build support for the ADC found in Renesas
RZ/G2L family.

View File

@ -11,6 +11,7 @@
#include <linux/cleanup.h>
#include <linux/completion.h>
#include <linux/delay.h>
#include <linux/iio/adc-helpers.h>
#include <linux/iio/iio.h>
#include <linux/interrupt.h>
#include <linux/io.h>
@ -324,48 +325,39 @@ static irqreturn_t rzg2l_adc_isr(int irq, void *dev_id)
return IRQ_HANDLED;
}
static const struct iio_chan_spec rzg2l_adc_chan_template = {
.indexed = 1,
.info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
};
static int rzg2l_adc_parse_properties(struct platform_device *pdev, struct rzg2l_adc *adc)
{
const struct rzg2l_adc_hw_params *hw_params = adc->hw_params;
struct iio_chan_spec *chan_array;
struct rzg2l_adc_data *data;
unsigned int channel;
int num_channels;
int ret;
u8 i;
data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL);
if (!data)
return -ENOMEM;
num_channels = device_get_child_node_count(&pdev->dev);
if (!num_channels)
return dev_err_probe(&pdev->dev, -ENODEV, "no channel children\n");
num_channels = devm_iio_adc_device_alloc_chaninfo_se(&pdev->dev,
&rzg2l_adc_chan_template,
hw_params->num_channels - 1,
&chan_array);
if (num_channels < 0)
return num_channels;
if (num_channels > hw_params->num_channels)
return dev_err_probe(&pdev->dev, -EINVAL,
"num of channel children out of range\n");
chan_array = devm_kcalloc(&pdev->dev, num_channels, sizeof(*chan_array),
GFP_KERNEL);
if (!chan_array)
return -ENOMEM;
for (i = 0; i < num_channels; i++) {
int channel = chan_array[i].channel;
i = 0;
device_for_each_child_node_scoped(&pdev->dev, fwnode) {
ret = fwnode_property_read_u32(fwnode, "reg", &channel);
if (ret)
return ret;
if (channel >= hw_params->num_channels)
return -EINVAL;
chan_array[i].type = rzg2l_adc_channels[channel].type;
chan_array[i].indexed = 1;
chan_array[i].channel = channel;
chan_array[i].info_mask_separate = BIT(IIO_CHAN_INFO_RAW);
chan_array[i].datasheet_name = rzg2l_adc_channels[channel].name;
i++;
chan_array[i].type = rzg2l_adc_channels[channel].type;
}
data->num_channels = num_channels;
@ -626,3 +618,4 @@ module_platform_driver(rzg2l_adc_driver);
MODULE_AUTHOR("Lad Prabhakar <prabhakar.mahadev-lad.rj@bp.renesas.com>");
MODULE_DESCRIPTION("Renesas RZ/G2L ADC driver");
MODULE_LICENSE("GPL v2");
MODULE_IMPORT_NS("IIO_DRIVER");