drivers/iio/inkern.c

Source file repositories/reference/linux-study-clean/drivers/iio/inkern.c

File Facts

System
Linux kernel
Corpus path
drivers/iio/inkern.c
Extension
.c
Size
25504 bytes
Lines
1046
Domain
Driver Families
Bucket
drivers/iio
Inferred role
Driver Families: exported/initcall integration point
Status
integration implementation candidate

Why This File Exists

Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.

Dependency Surface

Detected Declarations

Annotated Snippet

struct iio_map_internal {
	struct iio_dev *indio_dev;
	const struct iio_map *map;
	struct list_head l;
};

static LIST_HEAD(iio_map_list);
static DEFINE_MUTEX(iio_map_list_lock);

static int iio_map_array_unregister_locked(struct iio_dev *indio_dev)
{
	int ret = -ENODEV;
	struct iio_map_internal *mapi, *next;

	list_for_each_entry_safe(mapi, next, &iio_map_list, l) {
		if (indio_dev == mapi->indio_dev) {
			list_del(&mapi->l);
			kfree(mapi);
			ret = 0;
		}
	}
	return ret;
}

int iio_map_array_register(struct iio_dev *indio_dev, const struct iio_map *maps)
{
	struct iio_map_internal *mapi;
	int i = 0;
	int ret;

	if (!maps)
		return 0;

	guard(mutex)(&iio_map_list_lock);
	while (maps[i].consumer_dev_name) {
		mapi = kzalloc_obj(*mapi);
		if (!mapi) {
			ret = -ENOMEM;
			goto error_ret;
		}
		mapi->map = &maps[i];
		mapi->indio_dev = indio_dev;
		list_add_tail(&mapi->l, &iio_map_list);
		i++;
	}

	return 0;
error_ret:
	iio_map_array_unregister_locked(indio_dev);
	return ret;
}
EXPORT_SYMBOL_GPL(iio_map_array_register);

/*
 * Remove all map entries associated with the given iio device
 */
int iio_map_array_unregister(struct iio_dev *indio_dev)
{
	guard(mutex)(&iio_map_list_lock);
	return iio_map_array_unregister_locked(indio_dev);
}
EXPORT_SYMBOL_GPL(iio_map_array_unregister);

static void iio_map_array_unregister_cb(void *indio_dev)
{
	iio_map_array_unregister(indio_dev);
}

int devm_iio_map_array_register(struct device *dev, struct iio_dev *indio_dev,
				const struct iio_map *maps)
{
	int ret;

	ret = iio_map_array_register(indio_dev, maps);
	if (ret)
		return ret;

	return devm_add_action_or_reset(dev, iio_map_array_unregister_cb, indio_dev);
}
EXPORT_SYMBOL_GPL(devm_iio_map_array_register);

static const struct iio_chan_spec
*iio_chan_spec_from_name(const struct iio_dev *indio_dev, const char *name)
{
	int i;
	const struct iio_chan_spec *chan = NULL;

	for (i = 0; i < indio_dev->num_channels; i++)
		if (indio_dev->channels[i].datasheet_name &&
		    strcmp(name, indio_dev->channels[i].datasheet_name) == 0) {

Annotation

Implementation Notes