drivers/iio/light/iqs621-als.c

Source file repositories/reference/linux-study-clean/drivers/iio/light/iqs621-als.c

File Facts

System
Linux kernel
Corpus path
drivers/iio/light/iqs621-als.c
Extension
.c
Size
15202 bytes
Lines
619
Domain
Driver Families
Bucket
drivers/iio
Inferred role
Driver Families: implementation source
Status
source 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 iqs621_als_private {
	struct iqs62x_core *iqs62x;
	struct iio_dev *indio_dev;
	struct notifier_block notifier;
	struct mutex lock;
	bool light_en;
	bool range_en;
	bool prox_en;
	u8 als_flags;
	u8 ir_flags_mask;
	u8 ir_flags;
	u8 thresh_light;
	u8 thresh_dark;
	u8 thresh_prox;
};

static int iqs621_als_init(struct iqs621_als_private *iqs621_als)
{
	struct iqs62x_core *iqs62x = iqs621_als->iqs62x;
	unsigned int event_mask = 0;
	int ret;

	switch (iqs621_als->ir_flags_mask) {
	case IQS622_IR_FLAGS_TOUCH:
		ret = regmap_write(iqs62x->regmap, IQS622_IR_THRESH_TOUCH,
				   iqs621_als->thresh_prox);
		break;

	case IQS622_IR_FLAGS_PROX:
		ret = regmap_write(iqs62x->regmap, IQS622_IR_THRESH_PROX,
				   iqs621_als->thresh_prox);
		break;

	default:
		ret = regmap_write(iqs62x->regmap, IQS621_ALS_THRESH_LIGHT,
				   iqs621_als->thresh_light);
		if (ret)
			return ret;

		ret = regmap_write(iqs62x->regmap, IQS621_ALS_THRESH_DARK,
				   iqs621_als->thresh_dark);
	}

	if (ret)
		return ret;

	if (iqs621_als->light_en || iqs621_als->range_en)
		event_mask |= iqs62x->dev_desc->als_mask;

	if (iqs621_als->prox_en)
		event_mask |= iqs62x->dev_desc->ir_mask;

	return regmap_clear_bits(iqs62x->regmap, IQS620_GLBL_EVENT_MASK,
				 event_mask);
}

static int iqs621_als_notifier(struct notifier_block *notifier,
			       unsigned long event_flags, void *context)
{
	struct iqs62x_event_data *event_data = context;
	struct iqs621_als_private *iqs621_als;
	struct iio_dev *indio_dev;
	bool light_new, light_old;
	bool prox_new, prox_old;
	u8 range_new, range_old;
	s64 timestamp;
	int ret;

	iqs621_als = container_of(notifier, struct iqs621_als_private,
				  notifier);
	indio_dev = iqs621_als->indio_dev;
	timestamp = iio_get_time_ns(indio_dev);

	mutex_lock(&iqs621_als->lock);

	if (event_flags & BIT(IQS62X_EVENT_SYS_RESET)) {
		ret = iqs621_als_init(iqs621_als);
		if (ret) {
			dev_err(indio_dev->dev.parent,
				"Failed to re-initialize device: %d\n", ret);
			ret = NOTIFY_BAD;
		} else {
			ret = NOTIFY_OK;
		}

		goto err_mutex;
	}

	if (!iqs621_als->light_en && !iqs621_als->range_en &&
	    !iqs621_als->prox_en) {

Annotation

Implementation Notes