drivers/iio/industrialio-trigger.c

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

File Facts

System
Linux kernel
Corpus path
drivers/iio/industrialio-trigger.c
Extension
.c
Size
21197 bytes
Lines
797
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

ret = device_add(&trig_info->dev);
	if (ret)
		goto error_unregister_id;

	/* Add to list of available triggers held by the IIO core */
	scoped_guard(mutex, &iio_trigger_list_lock) {
		if (__iio_trigger_find_by_name(trig_info->name)) {
			pr_err("Duplicate trigger name '%s'\n", trig_info->name);
			ret = -EEXIST;
			goto error_device_del;
		}
		list_add_tail(&trig_info->list, &iio_trigger_list);
	}

	return 0;

error_device_del:
	device_del(&trig_info->dev);
error_unregister_id:
	ida_free(&iio_trigger_ida, trig_info->id);
	return ret;
}
EXPORT_SYMBOL(iio_trigger_register);

void iio_trigger_unregister(struct iio_trigger *trig_info)
{
	scoped_guard(mutex, &iio_trigger_list_lock)
		list_del(&trig_info->list);

	ida_free(&iio_trigger_ida, trig_info->id);
	/* Possible issue in here */
	device_del(&trig_info->dev);
}
EXPORT_SYMBOL(iio_trigger_unregister);

int iio_trigger_set_immutable(struct iio_dev *indio_dev, struct iio_trigger *trig)
{
	struct iio_dev_opaque *iio_dev_opaque;

	if (!indio_dev || !trig)
		return -EINVAL;

	iio_dev_opaque = to_iio_dev_opaque(indio_dev);
	guard(mutex)(&iio_dev_opaque->mlock);
	WARN_ON(iio_dev_opaque->trig_readonly);

	indio_dev->trig = iio_trigger_get(trig);
	iio_dev_opaque->trig_readonly = true;

	return 0;
}
EXPORT_SYMBOL(iio_trigger_set_immutable);

/* Search for trigger by name, assuming iio_trigger_list_lock held */
static struct iio_trigger *__iio_trigger_find_by_name(const char *name)
{
	struct iio_trigger *iter;

	list_for_each_entry(iter, &iio_trigger_list, list)
		if (!strcmp(iter->name, name))
			return iter;

	return NULL;
}

static struct iio_trigger *iio_trigger_acquire_by_name(const char *name)
{
	struct iio_trigger *iter;

	guard(mutex)(&iio_trigger_list_lock);
	list_for_each_entry(iter, &iio_trigger_list, list)
		if (sysfs_streq(iter->name, name))
			return iio_trigger_get(iter);

	return NULL;
}

static void iio_reenable_work_fn(struct work_struct *work)
{
	struct iio_trigger *trig = container_of(work, struct iio_trigger,
						reenable_work);

	/*
	 * This 'might' occur after the trigger state is set to disabled -
	 * in that case the driver should skip reenabling.
	 */
	trig->ops->reenable(trig);
}

/*

Annotation

Implementation Notes