Linux Audio

Check our new training course

Loading...
Note: File does not exist in v3.1.
   1// SPDX-License-Identifier: GPL-2.0-only
   2/*
   3 * vcnl4000.c - Support for Vishay VCNL4000/4010/4020/4040/4200 combined ambient
   4 * light and proximity sensor
   5 *
   6 * Copyright 2012 Peter Meerwald <pmeerw@pmeerw.net>
   7 * Copyright 2019 Pursim SPC
   8 * Copyright 2020 Mathieu Othacehe <m.othacehe@gmail.com>
   9 *
  10 * IIO driver for:
  11 *   VCNL4000/10/20 (7-bit I2C slave address 0x13)
  12 *   VCNL4040 (7-bit I2C slave address 0x60)
  13 *   VCNL4200 (7-bit I2C slave address 0x51)
  14 *
  15 * TODO:
  16 *   allow to adjust IR current
  17 *   interrupts (VCNL4040, VCNL4200)
  18 */
  19
  20#include <linux/bitfield.h>
  21#include <linux/module.h>
  22#include <linux/i2c.h>
  23#include <linux/err.h>
  24#include <linux/delay.h>
  25#include <linux/pm_runtime.h>
  26#include <linux/interrupt.h>
  27#include <linux/units.h>
  28
  29#include <linux/iio/buffer.h>
  30#include <linux/iio/events.h>
  31#include <linux/iio/iio.h>
  32#include <linux/iio/sysfs.h>
  33#include <linux/iio/trigger.h>
  34#include <linux/iio/trigger_consumer.h>
  35#include <linux/iio/triggered_buffer.h>
  36
  37#define VCNL4000_DRV_NAME "vcnl4000"
  38#define VCNL4000_PROD_ID	0x01
  39#define VCNL4010_PROD_ID	0x02 /* for VCNL4020, VCNL4010 */
  40#define VCNL4040_PROD_ID	0x86
  41#define VCNL4200_PROD_ID	0x58
  42
  43#define VCNL4000_COMMAND	0x80 /* Command register */
  44#define VCNL4000_PROD_REV	0x81 /* Product ID and Revision ID */
  45#define VCNL4010_PROX_RATE      0x82 /* Proximity rate */
  46#define VCNL4000_LED_CURRENT	0x83 /* IR LED current for proximity mode */
  47#define VCNL4000_AL_PARAM	0x84 /* Ambient light parameter register */
  48#define VCNL4010_ALS_PARAM      0x84 /* ALS rate */
  49#define VCNL4000_AL_RESULT_HI	0x85 /* Ambient light result register, MSB */
  50#define VCNL4000_AL_RESULT_LO	0x86 /* Ambient light result register, LSB */
  51#define VCNL4000_PS_RESULT_HI	0x87 /* Proximity result register, MSB */
  52#define VCNL4000_PS_RESULT_LO	0x88 /* Proximity result register, LSB */
  53#define VCNL4000_PS_MEAS_FREQ	0x89 /* Proximity test signal frequency */
  54#define VCNL4010_INT_CTRL	0x89 /* Interrupt control */
  55#define VCNL4000_PS_MOD_ADJ	0x8a /* Proximity modulator timing adjustment */
  56#define VCNL4010_LOW_THR_HI     0x8a /* Low threshold, MSB */
  57#define VCNL4010_LOW_THR_LO     0x8b /* Low threshold, LSB */
  58#define VCNL4010_HIGH_THR_HI    0x8c /* High threshold, MSB */
  59#define VCNL4010_HIGH_THR_LO    0x8d /* High threshold, LSB */
  60#define VCNL4010_ISR		0x8e /* Interrupt status */
  61
  62#define VCNL4200_AL_CONF	0x00 /* Ambient light configuration */
  63#define VCNL4200_PS_CONF1	0x03 /* Proximity configuration */
  64#define VCNL4200_PS_CONF3	0x04 /* Proximity configuration */
  65#define VCNL4040_PS_THDL_LM	0x06 /* Proximity threshold low */
  66#define VCNL4040_PS_THDH_LM	0x07 /* Proximity threshold high */
  67#define VCNL4040_ALS_THDL_LM	0x02 /* Ambient light threshold low */
  68#define VCNL4040_ALS_THDH_LM	0x01 /* Ambient light threshold high */
  69#define VCNL4200_PS_DATA	0x08 /* Proximity data */
  70#define VCNL4200_AL_DATA	0x09 /* Ambient light data */
  71#define VCNL4040_INT_FLAGS	0x0b /* Interrupt register */
  72#define VCNL4200_INT_FLAGS	0x0d /* Interrupt register */
  73#define VCNL4200_DEV_ID		0x0e /* Device ID, slave address and version */
  74
  75#define VCNL4040_DEV_ID		0x0c /* Device ID and version */
  76
  77/* Bit masks for COMMAND register */
  78#define VCNL4000_AL_RDY		BIT(6) /* ALS data ready? */
  79#define VCNL4000_PS_RDY		BIT(5) /* proximity data ready? */
  80#define VCNL4000_AL_OD		BIT(4) /* start on-demand ALS measurement */
  81#define VCNL4000_PS_OD		BIT(3) /* start on-demand proximity measurement */
  82#define VCNL4000_ALS_EN		BIT(2) /* start ALS measurement */
  83#define VCNL4000_PROX_EN	BIT(1) /* start proximity measurement */
  84#define VCNL4000_SELF_TIMED_EN	BIT(0) /* start self-timed measurement */
  85
  86#define VCNL4040_ALS_CONF_ALS_SHUTDOWN	BIT(0)
  87#define VCNL4040_ALS_CONF_IT		GENMASK(7, 6) /* Ambient integration time */
  88#define VCNL4040_ALS_CONF_INT_EN	BIT(1) /* Ambient light Interrupt enable */
  89#define VCNL4040_ALS_CONF_PERS	GENMASK(3, 2) /* Ambient interrupt persistence setting */
  90#define VCNL4040_PS_CONF1_PS_SHUTDOWN	BIT(0)
  91#define VCNL4040_PS_CONF2_PS_IT	GENMASK(3, 1) /* Proximity integration time */
  92#define VCNL4040_CONF1_PS_PERS	GENMASK(5, 4) /* Proximity interrupt persistence setting */
  93#define VCNL4040_PS_CONF2_PS_HD		BIT(11)	/* Proximity high definition */
  94#define VCNL4040_PS_CONF2_PS_INT	GENMASK(9, 8) /* Proximity interrupt mode */
  95#define VCNL4040_PS_CONF3_MPS		GENMASK(6, 5) /* Proximity multi pulse number */
  96#define VCNL4040_PS_MS_LED_I		GENMASK(10, 8) /* Proximity current */
  97#define VCNL4040_PS_IF_AWAY		BIT(8) /* Proximity event cross low threshold */
  98#define VCNL4040_PS_IF_CLOSE		BIT(9) /* Proximity event cross high threshold */
  99#define VCNL4040_ALS_RISING		BIT(12) /* Ambient Light cross high threshold */
 100#define VCNL4040_ALS_FALLING		BIT(13) /* Ambient Light cross low threshold */
 101
 102/* Bit masks for interrupt registers. */
 103#define VCNL4010_INT_THR_SEL	BIT(0) /* Select threshold interrupt source */
 104#define VCNL4010_INT_THR_EN	BIT(1) /* Threshold interrupt type */
 105#define VCNL4010_INT_ALS_EN	BIT(2) /* Enable on ALS data ready */
 106#define VCNL4010_INT_PROX_EN	BIT(3) /* Enable on proximity data ready */
 107
 108#define VCNL4010_INT_THR_HIGH	0 /* High threshold exceeded */
 109#define VCNL4010_INT_THR_LOW	1 /* Low threshold exceeded */
 110#define VCNL4010_INT_ALS	2 /* ALS data ready */
 111#define VCNL4010_INT_PROXIMITY	3 /* Proximity data ready */
 112
 113#define VCNL4010_INT_THR \
 114	(BIT(VCNL4010_INT_THR_LOW) | BIT(VCNL4010_INT_THR_HIGH))
 115#define VCNL4010_INT_DRDY \
 116	(BIT(VCNL4010_INT_PROXIMITY) | BIT(VCNL4010_INT_ALS))
 117
 118#define VCNL4040_CONF3_PS_MPS_16BITS	3	/* 8 multi pulses */
 119#define VCNL4040_CONF3_PS_LED_I_16BITS	3	/* 120 mA */
 120
 121#define VCNL4040_CONF3_PS_SAMPLE_16BITS \
 122	(FIELD_PREP(VCNL4040_PS_CONF3_MPS, VCNL4040_CONF3_PS_MPS_16BITS) | \
 123	 FIELD_PREP(VCNL4040_PS_MS_LED_I, VCNL4040_CONF3_PS_LED_I_16BITS))
 124
 125static const int vcnl4010_prox_sampling_frequency[][2] = {
 126	{1, 950000},
 127	{3, 906250},
 128	{7, 812500},
 129	{16, 625000},
 130	{31, 250000},
 131	{62, 500000},
 132	{125, 0},
 133	{250, 0},
 134};
 135
 136static const int vcnl4040_ps_it_times[][2] = {
 137	{0, 100},
 138	{0, 150},
 139	{0, 200},
 140	{0, 250},
 141	{0, 300},
 142	{0, 350},
 143	{0, 400},
 144	{0, 800},
 145};
 146
 147static const int vcnl4200_ps_it_times[][2] = {
 148	{0, 96},
 149	{0, 144},
 150	{0, 192},
 151	{0, 384},
 152	{0, 768},
 153	{0, 864},
 154};
 155
 156static const int vcnl4040_als_it_times[][2] = {
 157	{0, 80000},
 158	{0, 160000},
 159	{0, 320000},
 160	{0, 640000},
 161};
 162
 163static const int vcnl4200_als_it_times[][2] = {
 164	{0, 50000},
 165	{0, 100000},
 166	{0, 200000},
 167	{0, 400000},
 168};
 169
 170static const int vcnl4040_ps_calibbias_ua[][2] = {
 171	{0, 50000},
 172	{0, 75000},
 173	{0, 100000},
 174	{0, 120000},
 175	{0, 140000},
 176	{0, 160000},
 177	{0, 180000},
 178	{0, 200000},
 179};
 180
 181static const int vcnl4040_als_persistence[] = {1, 2, 4, 8};
 182static const int vcnl4040_ps_persistence[] = {1, 2, 3, 4};
 183static const int vcnl4040_ps_oversampling_ratio[] = {1, 2, 4, 8};
 184
 185#define VCNL4000_SLEEP_DELAY_MS	2000 /* before we enter pm_runtime_suspend */
 186
 187enum vcnl4000_device_ids {
 188	VCNL4000,
 189	VCNL4010,
 190	VCNL4040,
 191	VCNL4200,
 192};
 193
 194struct vcnl4200_channel {
 195	u8 reg;
 196	ktime_t last_measurement;
 197	ktime_t sampling_rate;
 198	struct mutex lock;
 199};
 200
 201struct vcnl4000_data {
 202	struct i2c_client *client;
 203	enum vcnl4000_device_ids id;
 204	int rev;
 205	int al_scale;
 206	int ps_scale;
 207	u8 ps_int;		/* proximity interrupt mode */
 208	u8 als_int;		/* ambient light interrupt mode*/
 209	const struct vcnl4000_chip_spec *chip_spec;
 210	struct mutex vcnl4000_lock;
 211	struct vcnl4200_channel vcnl4200_al;
 212	struct vcnl4200_channel vcnl4200_ps;
 213	uint32_t near_level;
 214};
 215
 216struct vcnl4000_chip_spec {
 217	const char *prod;
 218	struct iio_chan_spec const *channels;
 219	const int num_channels;
 220	const struct iio_info *info;
 221	const struct iio_buffer_setup_ops *buffer_setup_ops;
 222	int (*init)(struct vcnl4000_data *data);
 223	int (*measure_light)(struct vcnl4000_data *data, int *val);
 224	int (*measure_proximity)(struct vcnl4000_data *data, int *val);
 225	int (*set_power_state)(struct vcnl4000_data *data, bool on);
 226	irqreturn_t (*irq_thread)(int irq, void *priv);
 227	irqreturn_t (*trig_buffer_func)(int irq, void *priv);
 228
 229	u8 int_reg;
 230	const int(*ps_it_times)[][2];
 231	const int num_ps_it_times;
 232	const int(*als_it_times)[][2];
 233	const int num_als_it_times;
 234	const unsigned int ulux_step;
 235};
 236
 237static const struct i2c_device_id vcnl4000_id[] = {
 238	{ "vcnl4000", VCNL4000 },
 239	{ "vcnl4010", VCNL4010 },
 240	{ "vcnl4020", VCNL4010 },
 241	{ "vcnl4040", VCNL4040 },
 242	{ "vcnl4200", VCNL4200 },
 243	{ }
 244};
 245MODULE_DEVICE_TABLE(i2c, vcnl4000_id);
 246
 247static int vcnl4000_set_power_state(struct vcnl4000_data *data, bool on)
 248{
 249	/* no suspend op */
 250	return 0;
 251}
 252
 253static int vcnl4000_init(struct vcnl4000_data *data)
 254{
 255	int ret, prod_id;
 256
 257	ret = i2c_smbus_read_byte_data(data->client, VCNL4000_PROD_REV);
 258	if (ret < 0)
 259		return ret;
 260
 261	prod_id = ret >> 4;
 262	switch (prod_id) {
 263	case VCNL4000_PROD_ID:
 264		if (data->id != VCNL4000)
 265			dev_warn(&data->client->dev,
 266					"wrong device id, use vcnl4000");
 267		break;
 268	case VCNL4010_PROD_ID:
 269		if (data->id != VCNL4010)
 270			dev_warn(&data->client->dev,
 271					"wrong device id, use vcnl4010/4020");
 272		break;
 273	default:
 274		return -ENODEV;
 275	}
 276
 277	data->rev = ret & 0xf;
 278	data->al_scale = 250000;
 279
 280	return data->chip_spec->set_power_state(data, true);
 281};
 282
 283static ssize_t vcnl4000_write_als_enable(struct vcnl4000_data *data, bool en)
 284{
 285	int ret;
 286
 287	mutex_lock(&data->vcnl4000_lock);
 288
 289	ret = i2c_smbus_read_word_data(data->client, VCNL4200_AL_CONF);
 290	if (ret < 0)
 291		goto out;
 292
 293	if (en)
 294		ret &= ~VCNL4040_ALS_CONF_ALS_SHUTDOWN;
 295	else
 296		ret |= VCNL4040_ALS_CONF_ALS_SHUTDOWN;
 297
 298	ret = i2c_smbus_write_word_data(data->client, VCNL4200_AL_CONF, ret);
 299
 300out:
 301	mutex_unlock(&data->vcnl4000_lock);
 302
 303	return ret;
 304}
 305
 306static ssize_t vcnl4000_write_ps_enable(struct vcnl4000_data *data, bool en)
 307{
 308	int ret;
 309
 310	mutex_lock(&data->vcnl4000_lock);
 311
 312	ret = i2c_smbus_read_word_data(data->client, VCNL4200_PS_CONF1);
 313	if (ret < 0)
 314		goto out;
 315
 316	if (en)
 317		ret &= ~VCNL4040_PS_CONF1_PS_SHUTDOWN;
 318	else
 319		ret |= VCNL4040_PS_CONF1_PS_SHUTDOWN;
 320
 321	ret = i2c_smbus_write_word_data(data->client, VCNL4200_PS_CONF1, ret);
 322
 323out:
 324	mutex_unlock(&data->vcnl4000_lock);
 325
 326	return ret;
 327}
 328
 329static int vcnl4200_set_power_state(struct vcnl4000_data *data, bool on)
 330{
 331	int ret;
 332
 333	/* Do not power down if interrupts are enabled */
 334	if (!on && (data->ps_int || data->als_int))
 335		return 0;
 336
 337	ret = vcnl4000_write_als_enable(data, on);
 338	if (ret < 0)
 339		return ret;
 340
 341	ret = vcnl4000_write_ps_enable(data, on);
 342	if (ret < 0)
 343		return ret;
 344
 345	if (on) {
 346		/* Wait at least one integration cycle before fetching data */
 347		data->vcnl4200_al.last_measurement = ktime_get();
 348		data->vcnl4200_ps.last_measurement = ktime_get();
 349	}
 350
 351	return 0;
 352}
 353
 354static int vcnl4200_init(struct vcnl4000_data *data)
 355{
 356	int ret, id;
 357	u16 regval;
 358
 359	ret = i2c_smbus_read_word_data(data->client, VCNL4200_DEV_ID);
 360	if (ret < 0)
 361		return ret;
 362
 363	id = ret & 0xff;
 364
 365	if (id != VCNL4200_PROD_ID) {
 366		ret = i2c_smbus_read_word_data(data->client, VCNL4040_DEV_ID);
 367		if (ret < 0)
 368			return ret;
 369
 370		id = ret & 0xff;
 371
 372		if (id != VCNL4040_PROD_ID)
 373			return -ENODEV;
 374	}
 375
 376	dev_dbg(&data->client->dev, "device id 0x%x", id);
 377
 378	data->rev = (ret >> 8) & 0xf;
 379	data->ps_int = 0;
 380	data->als_int = 0;
 381
 382	data->vcnl4200_al.reg = VCNL4200_AL_DATA;
 383	data->vcnl4200_ps.reg = VCNL4200_PS_DATA;
 384	switch (id) {
 385	case VCNL4200_PROD_ID:
 386		/* Default wait time is 50ms, add 20% tolerance. */
 387		data->vcnl4200_al.sampling_rate = ktime_set(0, 60000 * 1000);
 388		/* Default wait time is 4.8ms, add 20% tolerance. */
 389		data->vcnl4200_ps.sampling_rate = ktime_set(0, 5760 * 1000);
 390		break;
 391	case VCNL4040_PROD_ID:
 392		/* Default wait time is 80ms, add 20% tolerance. */
 393		data->vcnl4200_al.sampling_rate = ktime_set(0, 96000 * 1000);
 394		/* Default wait time is 5ms, add 20% tolerance. */
 395		data->vcnl4200_ps.sampling_rate = ktime_set(0, 6000 * 1000);
 396		break;
 397	}
 398	data->al_scale = data->chip_spec->ulux_step;
 399	data->ps_scale = 16;
 400	mutex_init(&data->vcnl4200_al.lock);
 401	mutex_init(&data->vcnl4200_ps.lock);
 402
 403	/* Use 16 bits proximity sensor readings */
 404	ret = i2c_smbus_read_word_data(data->client, VCNL4200_PS_CONF1);
 405	if (ret < 0)
 406		return ret;
 407
 408	regval = ret | VCNL4040_PS_CONF2_PS_HD;
 409	ret = i2c_smbus_write_word_data(data->client, VCNL4200_PS_CONF1,
 410					regval);
 411	if (ret < 0)
 412		return ret;
 413
 414	/* Align proximity sensor sample rate to 16 bits data width */
 415	ret = i2c_smbus_read_word_data(data->client, VCNL4200_PS_CONF3);
 416	if (ret < 0)
 417		return ret;
 418
 419	regval = ret | VCNL4040_CONF3_PS_SAMPLE_16BITS;
 420	ret = i2c_smbus_write_word_data(data->client, VCNL4200_PS_CONF3,
 421					regval);
 422	if (ret < 0)
 423		return ret;
 424
 425	ret = data->chip_spec->set_power_state(data, true);
 426	if (ret < 0)
 427		return ret;
 428
 429	return 0;
 430};
 431
 432static int vcnl4000_read_data(struct vcnl4000_data *data, u8 data_reg, int *val)
 433{
 434	s32 ret;
 435
 436	ret = i2c_smbus_read_word_swapped(data->client, data_reg);
 437	if (ret < 0)
 438		return ret;
 439
 440	*val = ret;
 441	return 0;
 442}
 443
 444static int vcnl4000_write_data(struct vcnl4000_data *data, u8 data_reg, int val)
 445{
 446	if (val > U16_MAX)
 447		return -ERANGE;
 448
 449	return i2c_smbus_write_word_swapped(data->client, data_reg, val);
 450}
 451
 452
 453static int vcnl4000_measure(struct vcnl4000_data *data, u8 req_mask,
 454				u8 rdy_mask, u8 data_reg, int *val)
 455{
 456	int tries = 20;
 457	int ret;
 458
 459	mutex_lock(&data->vcnl4000_lock);
 460
 461	ret = i2c_smbus_write_byte_data(data->client, VCNL4000_COMMAND,
 462					req_mask);
 463	if (ret < 0)
 464		goto fail;
 465
 466	/* wait for data to become ready */
 467	while (tries--) {
 468		ret = i2c_smbus_read_byte_data(data->client, VCNL4000_COMMAND);
 469		if (ret < 0)
 470			goto fail;
 471		if (ret & rdy_mask)
 472			break;
 473		msleep(20); /* measurement takes up to 100 ms */
 474	}
 475
 476	if (tries < 0) {
 477		dev_err(&data->client->dev,
 478			"vcnl4000_measure() failed, data not ready\n");
 479		ret = -EIO;
 480		goto fail;
 481	}
 482
 483	ret = vcnl4000_read_data(data, data_reg, val);
 484	if (ret < 0)
 485		goto fail;
 486
 487	mutex_unlock(&data->vcnl4000_lock);
 488
 489	return 0;
 490
 491fail:
 492	mutex_unlock(&data->vcnl4000_lock);
 493	return ret;
 494}
 495
 496static int vcnl4200_measure(struct vcnl4000_data *data,
 497		struct vcnl4200_channel *chan, int *val)
 498{
 499	int ret;
 500	s64 delta;
 501	ktime_t next_measurement;
 502
 503	mutex_lock(&chan->lock);
 504
 505	next_measurement = ktime_add(chan->last_measurement,
 506			chan->sampling_rate);
 507	delta = ktime_us_delta(next_measurement, ktime_get());
 508	if (delta > 0)
 509		usleep_range(delta, delta + 500);
 510	chan->last_measurement = ktime_get();
 511
 512	mutex_unlock(&chan->lock);
 513
 514	ret = i2c_smbus_read_word_data(data->client, chan->reg);
 515	if (ret < 0)
 516		return ret;
 517
 518	*val = ret;
 519
 520	return 0;
 521}
 522
 523static int vcnl4000_measure_light(struct vcnl4000_data *data, int *val)
 524{
 525	return vcnl4000_measure(data,
 526			VCNL4000_AL_OD, VCNL4000_AL_RDY,
 527			VCNL4000_AL_RESULT_HI, val);
 528}
 529
 530static int vcnl4200_measure_light(struct vcnl4000_data *data, int *val)
 531{
 532	return vcnl4200_measure(data, &data->vcnl4200_al, val);
 533}
 534
 535static int vcnl4000_measure_proximity(struct vcnl4000_data *data, int *val)
 536{
 537	return vcnl4000_measure(data,
 538			VCNL4000_PS_OD, VCNL4000_PS_RDY,
 539			VCNL4000_PS_RESULT_HI, val);
 540}
 541
 542static int vcnl4200_measure_proximity(struct vcnl4000_data *data, int *val)
 543{
 544	return vcnl4200_measure(data, &data->vcnl4200_ps, val);
 545}
 546
 547static int vcnl4010_read_proxy_samp_freq(struct vcnl4000_data *data, int *val,
 548					 int *val2)
 549{
 550	int ret;
 551
 552	ret = i2c_smbus_read_byte_data(data->client, VCNL4010_PROX_RATE);
 553	if (ret < 0)
 554		return ret;
 555
 556	if (ret >= ARRAY_SIZE(vcnl4010_prox_sampling_frequency))
 557		return -EINVAL;
 558
 559	*val = vcnl4010_prox_sampling_frequency[ret][0];
 560	*val2 = vcnl4010_prox_sampling_frequency[ret][1];
 561
 562	return 0;
 563}
 564
 565static bool vcnl4010_is_in_periodic_mode(struct vcnl4000_data *data)
 566{
 567	int ret;
 568
 569	ret = i2c_smbus_read_byte_data(data->client, VCNL4000_COMMAND);
 570	if (ret < 0)
 571		return false;
 572
 573	return !!(ret & VCNL4000_SELF_TIMED_EN);
 574}
 575
 576static int vcnl4000_set_pm_runtime_state(struct vcnl4000_data *data, bool on)
 577{
 578	struct device *dev = &data->client->dev;
 579	int ret;
 580
 581	if (on) {
 582		ret = pm_runtime_resume_and_get(dev);
 583	} else {
 584		pm_runtime_mark_last_busy(dev);
 585		ret = pm_runtime_put_autosuspend(dev);
 586	}
 587
 588	return ret;
 589}
 590
 591static int vcnl4040_read_als_it(struct vcnl4000_data *data, int *val, int *val2)
 592{
 593	int ret;
 594
 595	ret = i2c_smbus_read_word_data(data->client, VCNL4200_AL_CONF);
 596	if (ret < 0)
 597		return ret;
 598
 599	ret = FIELD_GET(VCNL4040_ALS_CONF_IT, ret);
 600	if (ret >= data->chip_spec->num_als_it_times)
 601		return -EINVAL;
 602
 603	*val = (*data->chip_spec->als_it_times)[ret][0];
 604	*val2 = (*data->chip_spec->als_it_times)[ret][1];
 605
 606	return 0;
 607}
 608
 609static ssize_t vcnl4040_write_als_it(struct vcnl4000_data *data, int val)
 610{
 611	unsigned int i;
 612	int ret;
 613	u16 regval;
 614
 615	for (i = 0; i < data->chip_spec->num_als_it_times; i++) {
 616		if (val == (*data->chip_spec->als_it_times)[i][1])
 617			break;
 618	}
 619
 620	if (i == data->chip_spec->num_als_it_times)
 621		return -EINVAL;
 622
 623	data->vcnl4200_al.sampling_rate = ktime_set(0, val * 1200);
 624	data->al_scale = div_u64(mul_u32_u32(data->chip_spec->ulux_step,
 625			 (*data->chip_spec->als_it_times)[0][1]),
 626			 val);
 627
 628	mutex_lock(&data->vcnl4000_lock);
 629
 630	ret = i2c_smbus_read_word_data(data->client, VCNL4200_AL_CONF);
 631	if (ret < 0)
 632		goto out_unlock;
 633
 634	regval = FIELD_PREP(VCNL4040_ALS_CONF_IT, i);
 635	regval |= (ret & ~VCNL4040_ALS_CONF_IT);
 636	ret = i2c_smbus_write_word_data(data->client,
 637					VCNL4200_AL_CONF,
 638					regval);
 639
 640out_unlock:
 641	mutex_unlock(&data->vcnl4000_lock);
 642	return ret;
 643}
 644
 645static int vcnl4040_read_ps_it(struct vcnl4000_data *data, int *val, int *val2)
 646{
 647	int ret;
 648
 649	ret = i2c_smbus_read_word_data(data->client, VCNL4200_PS_CONF1);
 650	if (ret < 0)
 651		return ret;
 652
 653	ret = FIELD_GET(VCNL4040_PS_CONF2_PS_IT, ret);
 654
 655	if (ret >= data->chip_spec->num_ps_it_times)
 656		return -EINVAL;
 657
 658	*val = (*data->chip_spec->ps_it_times)[ret][0];
 659	*val2 = (*data->chip_spec->ps_it_times)[ret][1];
 660
 661	return 0;
 662}
 663
 664static ssize_t vcnl4040_write_ps_it(struct vcnl4000_data *data, int val)
 665{
 666	unsigned int i;
 667	int ret, index = -1;
 668	u16 regval;
 669
 670	for (i = 0; i < data->chip_spec->num_ps_it_times; i++) {
 671		if (val == (*data->chip_spec->ps_it_times)[i][1]) {
 672			index = i;
 673			break;
 674		}
 675	}
 676
 677	if (index < 0)
 678		return -EINVAL;
 679
 680	data->vcnl4200_ps.sampling_rate = ktime_set(0, val * 60 * NSEC_PER_USEC);
 681
 682	mutex_lock(&data->vcnl4000_lock);
 683
 684	ret = i2c_smbus_read_word_data(data->client, VCNL4200_PS_CONF1);
 685	if (ret < 0)
 686		goto out;
 687
 688	regval = (ret & ~VCNL4040_PS_CONF2_PS_IT) |
 689	    FIELD_PREP(VCNL4040_PS_CONF2_PS_IT, index);
 690	ret = i2c_smbus_write_word_data(data->client, VCNL4200_PS_CONF1,
 691					regval);
 692
 693out:
 694	mutex_unlock(&data->vcnl4000_lock);
 695	return ret;
 696}
 697
 698static ssize_t vcnl4040_read_als_period(struct vcnl4000_data *data, int *val, int *val2)
 699{
 700	int ret, ret_pers, it;
 701	int64_t val_c;
 702
 703	ret = i2c_smbus_read_word_data(data->client, VCNL4200_AL_CONF);
 704	if (ret < 0)
 705		return ret;
 706
 707	ret_pers = FIELD_GET(VCNL4040_ALS_CONF_PERS, ret);
 708	if (ret_pers >= ARRAY_SIZE(vcnl4040_als_persistence))
 709		return -EINVAL;
 710
 711	it = FIELD_GET(VCNL4040_ALS_CONF_IT, ret);
 712	if (it >= data->chip_spec->num_als_it_times)
 713		return -EINVAL;
 714
 715	val_c = mul_u32_u32((*data->chip_spec->als_it_times)[it][1],
 716			    vcnl4040_als_persistence[ret_pers]);
 717	*val = div_u64_rem(val_c, MICRO, val2);
 718
 719	return IIO_VAL_INT_PLUS_MICRO;
 720}
 721
 722static ssize_t vcnl4040_write_als_period(struct vcnl4000_data *data, int val, int val2)
 723{
 724	unsigned int i;
 725	int ret, it;
 726	u16 regval;
 727	u64 val_n = mul_u32_u32(val, MICRO) + val2;
 728
 729	ret = i2c_smbus_read_word_data(data->client, VCNL4200_AL_CONF);
 730	if (ret < 0)
 731		return ret;
 732
 733	it = FIELD_GET(VCNL4040_ALS_CONF_IT, ret);
 734	if (it >= data->chip_spec->num_als_it_times)
 735		return -EINVAL;
 736
 737	for (i = 0; i < ARRAY_SIZE(vcnl4040_als_persistence) - 1; i++) {
 738		if (val_n < mul_u32_u32(vcnl4040_als_persistence[i],
 739					(*data->chip_spec->als_it_times)[it][1]))
 740			break;
 741	}
 742
 743	mutex_lock(&data->vcnl4000_lock);
 744
 745	ret = i2c_smbus_read_word_data(data->client, VCNL4200_AL_CONF);
 746	if (ret < 0)
 747		goto out_unlock;
 748
 749	regval = FIELD_PREP(VCNL4040_ALS_CONF_PERS, i);
 750	regval |= (ret & ~VCNL4040_ALS_CONF_PERS);
 751	ret = i2c_smbus_write_word_data(data->client, VCNL4200_AL_CONF,
 752					regval);
 753
 754out_unlock:
 755	mutex_unlock(&data->vcnl4000_lock);
 756	return ret;
 757}
 758
 759static ssize_t vcnl4040_read_ps_period(struct vcnl4000_data *data, int *val, int *val2)
 760{
 761	int ret, ret_pers, it;
 762
 763	ret = i2c_smbus_read_word_data(data->client, VCNL4200_PS_CONF1);
 764	if (ret < 0)
 765		return ret;
 766
 767	ret_pers = FIELD_GET(VCNL4040_CONF1_PS_PERS, ret);
 768	if (ret_pers >= ARRAY_SIZE(vcnl4040_ps_persistence))
 769		return -EINVAL;
 770
 771	it = FIELD_GET(VCNL4040_PS_CONF2_PS_IT, ret);
 772	if (it >= data->chip_spec->num_ps_it_times)
 773		return -EINVAL;
 774
 775	*val = (*data->chip_spec->ps_it_times)[it][0];
 776	*val2 = (*data->chip_spec->ps_it_times)[it][1] *
 777		vcnl4040_ps_persistence[ret_pers];
 778
 779	return IIO_VAL_INT_PLUS_MICRO;
 780}
 781
 782static ssize_t vcnl4040_write_ps_period(struct vcnl4000_data *data, int val, int val2)
 783{
 784	int ret, it, i;
 785	u16 regval;
 786
 787	ret = i2c_smbus_read_word_data(data->client, VCNL4200_PS_CONF1);
 788	if (ret < 0)
 789		return ret;
 790
 791	it = FIELD_GET(VCNL4040_PS_CONF2_PS_IT, ret);
 792	if (it >= data->chip_spec->num_ps_it_times)
 793		return -EINVAL;
 794
 795	if (val > 0)
 796		i = ARRAY_SIZE(vcnl4040_ps_persistence) - 1;
 797	else {
 798		for (i = 0; i < ARRAY_SIZE(vcnl4040_ps_persistence) - 1; i++) {
 799			if (val2 <= vcnl4040_ps_persistence[i] *
 800					(*data->chip_spec->ps_it_times)[it][1])
 801				break;
 802		}
 803	}
 804
 805	mutex_lock(&data->vcnl4000_lock);
 806
 807	ret = i2c_smbus_read_word_data(data->client, VCNL4200_PS_CONF1);
 808	if (ret < 0)
 809		goto out_unlock;
 810
 811	regval = FIELD_PREP(VCNL4040_CONF1_PS_PERS, i);
 812	regval |= (ret & ~VCNL4040_CONF1_PS_PERS);
 813	ret = i2c_smbus_write_word_data(data->client, VCNL4200_PS_CONF1,
 814					regval);
 815
 816out_unlock:
 817	mutex_unlock(&data->vcnl4000_lock);
 818	return ret;
 819}
 820
 821static ssize_t vcnl4040_read_ps_oversampling_ratio(struct vcnl4000_data *data, int *val)
 822{
 823	int ret;
 824
 825	ret = i2c_smbus_read_word_data(data->client, VCNL4200_PS_CONF3);
 826	if (ret < 0)
 827		return ret;
 828
 829	ret = FIELD_GET(VCNL4040_PS_CONF3_MPS, ret);
 830	if (ret >= ARRAY_SIZE(vcnl4040_ps_oversampling_ratio))
 831		return -EINVAL;
 832
 833	*val = vcnl4040_ps_oversampling_ratio[ret];
 834
 835	return ret;
 836}
 837
 838static ssize_t vcnl4040_write_ps_oversampling_ratio(struct vcnl4000_data *data, int val)
 839{
 840	unsigned int i;
 841	int ret;
 842	u16 regval;
 843
 844	for (i = 0; i < ARRAY_SIZE(vcnl4040_ps_oversampling_ratio); i++) {
 845		if (val == vcnl4040_ps_oversampling_ratio[i])
 846			break;
 847	}
 848
 849	if (i >= ARRAY_SIZE(vcnl4040_ps_oversampling_ratio))
 850		return -EINVAL;
 851
 852	mutex_lock(&data->vcnl4000_lock);
 853
 854	ret = i2c_smbus_read_word_data(data->client, VCNL4200_PS_CONF3);
 855	if (ret < 0)
 856		goto out_unlock;
 857
 858	regval = FIELD_PREP(VCNL4040_PS_CONF3_MPS, i);
 859	regval |= (ret & ~VCNL4040_PS_CONF3_MPS);
 860	ret = i2c_smbus_write_word_data(data->client, VCNL4200_PS_CONF3,
 861					regval);
 862
 863out_unlock:
 864	mutex_unlock(&data->vcnl4000_lock);
 865	return ret;
 866}
 867
 868static ssize_t vcnl4040_read_ps_calibbias(struct vcnl4000_data *data, int *val, int *val2)
 869{
 870	int ret;
 871
 872	ret = i2c_smbus_read_word_data(data->client, VCNL4200_PS_CONF3);
 873	if (ret < 0)
 874		return ret;
 875
 876	ret = FIELD_GET(VCNL4040_PS_MS_LED_I, ret);
 877	if (ret >= ARRAY_SIZE(vcnl4040_ps_calibbias_ua))
 878		return -EINVAL;
 879
 880	*val = vcnl4040_ps_calibbias_ua[ret][0];
 881	*val2 = vcnl4040_ps_calibbias_ua[ret][1];
 882
 883	return ret;
 884}
 885
 886static ssize_t vcnl4040_write_ps_calibbias(struct vcnl4000_data *data, int val)
 887{
 888	unsigned int i;
 889	int ret;
 890	u16 regval;
 891
 892	for (i = 0; i < ARRAY_SIZE(vcnl4040_ps_calibbias_ua); i++) {
 893		if (val == vcnl4040_ps_calibbias_ua[i][1])
 894			break;
 895	}
 896
 897	if (i >= ARRAY_SIZE(vcnl4040_ps_calibbias_ua))
 898		return -EINVAL;
 899
 900	mutex_lock(&data->vcnl4000_lock);
 901
 902	ret = i2c_smbus_read_word_data(data->client, VCNL4200_PS_CONF3);
 903	if (ret < 0)
 904		goto out_unlock;
 905
 906	regval = (ret & ~VCNL4040_PS_MS_LED_I);
 907	regval |= FIELD_PREP(VCNL4040_PS_MS_LED_I, i);
 908	ret = i2c_smbus_write_word_data(data->client, VCNL4200_PS_CONF3,
 909					regval);
 910
 911out_unlock:
 912	mutex_unlock(&data->vcnl4000_lock);
 913	return ret;
 914}
 915
 916static int vcnl4000_read_raw(struct iio_dev *indio_dev,
 917				struct iio_chan_spec const *chan,
 918				int *val, int *val2, long mask)
 919{
 920	int ret;
 921	struct vcnl4000_data *data = iio_priv(indio_dev);
 922
 923	switch (mask) {
 924	case IIO_CHAN_INFO_RAW:
 925		ret = vcnl4000_set_pm_runtime_state(data, true);
 926		if  (ret < 0)
 927			return ret;
 928
 929		switch (chan->type) {
 930		case IIO_LIGHT:
 931			ret = data->chip_spec->measure_light(data, val);
 932			if (!ret)
 933				ret = IIO_VAL_INT;
 934			break;
 935		case IIO_PROXIMITY:
 936			ret = data->chip_spec->measure_proximity(data, val);
 937			*val2 = data->ps_scale;
 938			if (!ret)
 939				ret = IIO_VAL_FRACTIONAL;
 940			break;
 941		default:
 942			ret = -EINVAL;
 943		}
 944		vcnl4000_set_pm_runtime_state(data, false);
 945		return ret;
 946	case IIO_CHAN_INFO_SCALE:
 947		if (chan->type != IIO_LIGHT)
 948			return -EINVAL;
 949
 950		*val = 0;
 951		*val2 = data->al_scale;
 952		return IIO_VAL_INT_PLUS_MICRO;
 953	case IIO_CHAN_INFO_INT_TIME:
 954		switch (chan->type) {
 955		case IIO_LIGHT:
 956			ret = vcnl4040_read_als_it(data, val, val2);
 957			break;
 958		case IIO_PROXIMITY:
 959			ret = vcnl4040_read_ps_it(data, val, val2);
 960			break;
 961		default:
 962			return -EINVAL;
 963		}
 964		if (ret < 0)
 965			return ret;
 966		return IIO_VAL_INT_PLUS_MICRO;
 967	case IIO_CHAN_INFO_OVERSAMPLING_RATIO:
 968		switch (chan->type) {
 969		case IIO_PROXIMITY:
 970			ret = vcnl4040_read_ps_oversampling_ratio(data, val);
 971			if (ret < 0)
 972				return ret;
 973			return IIO_VAL_INT;
 974		default:
 975			return -EINVAL;
 976		}
 977	case IIO_CHAN_INFO_CALIBBIAS:
 978		switch (chan->type) {
 979		case IIO_PROXIMITY:
 980			ret = vcnl4040_read_ps_calibbias(data, val, val2);
 981			if (ret < 0)
 982				return ret;
 983			return IIO_VAL_INT_PLUS_MICRO;
 984		default:
 985			return -EINVAL;
 986		}
 987	default:
 988		return -EINVAL;
 989	}
 990}
 991
 992static int vcnl4040_write_raw(struct iio_dev *indio_dev,
 993			      struct iio_chan_spec const *chan,
 994			      int val, int val2, long mask)
 995{
 996	struct vcnl4000_data *data = iio_priv(indio_dev);
 997
 998	switch (mask) {
 999	case IIO_CHAN_INFO_INT_TIME:
1000		if (val != 0)
1001			return -EINVAL;
1002		switch (chan->type) {
1003		case IIO_LIGHT:
1004			return vcnl4040_write_als_it(data, val2);
1005		case IIO_PROXIMITY:
1006			return vcnl4040_write_ps_it(data, val2);
1007		default:
1008			return -EINVAL;
1009		}
1010	case IIO_CHAN_INFO_OVERSAMPLING_RATIO:
1011		switch (chan->type) {
1012		case IIO_PROXIMITY:
1013			return vcnl4040_write_ps_oversampling_ratio(data, val);
1014		default:
1015			return -EINVAL;
1016		}
1017	case IIO_CHAN_INFO_CALIBBIAS:
1018		switch (chan->type) {
1019		case IIO_PROXIMITY:
1020			return vcnl4040_write_ps_calibbias(data, val2);
1021		default:
1022			return -EINVAL;
1023		}
1024	default:
1025		return -EINVAL;
1026	}
1027}
1028
1029static int vcnl4040_read_avail(struct iio_dev *indio_dev,
1030			       struct iio_chan_spec const *chan,
1031			       const int **vals, int *type, int *length,
1032			       long mask)
1033{
1034	struct vcnl4000_data *data = iio_priv(indio_dev);
1035
1036	switch (mask) {
1037	case IIO_CHAN_INFO_INT_TIME:
1038		switch (chan->type) {
1039		case IIO_LIGHT:
1040			*vals = (int *)(*data->chip_spec->als_it_times);
1041			*length = 2 * data->chip_spec->num_als_it_times;
1042			break;
1043		case IIO_PROXIMITY:
1044			*vals = (int *)(*data->chip_spec->ps_it_times);
1045			*length = 2 * data->chip_spec->num_ps_it_times;
1046			break;
1047		default:
1048			return -EINVAL;
1049		}
1050		*type = IIO_VAL_INT_PLUS_MICRO;
1051		return IIO_AVAIL_LIST;
1052	case IIO_CHAN_INFO_OVERSAMPLING_RATIO:
1053		switch (chan->type) {
1054		case IIO_PROXIMITY:
1055			*vals = (int *)vcnl4040_ps_oversampling_ratio;
1056			*length = ARRAY_SIZE(vcnl4040_ps_oversampling_ratio);
1057			*type = IIO_VAL_INT;
1058			return IIO_AVAIL_LIST;
1059		default:
1060			return -EINVAL;
1061		}
1062	case IIO_CHAN_INFO_CALIBBIAS:
1063		switch (chan->type) {
1064		case IIO_PROXIMITY:
1065			*vals = (int *)vcnl4040_ps_calibbias_ua;
1066			*length = 2 * ARRAY_SIZE(vcnl4040_ps_calibbias_ua);
1067			*type = IIO_VAL_INT_PLUS_MICRO;
1068			return IIO_AVAIL_LIST;
1069		default:
1070			return -EINVAL;
1071		}
1072	default:
1073		return -EINVAL;
1074	}
1075}
1076
1077static int vcnl4010_read_raw(struct iio_dev *indio_dev,
1078			     struct iio_chan_spec const *chan,
1079			     int *val, int *val2, long mask)
1080{
1081	int ret;
1082	struct vcnl4000_data *data = iio_priv(indio_dev);
1083
1084	switch (mask) {
1085	case IIO_CHAN_INFO_RAW:
1086	case IIO_CHAN_INFO_SCALE:
1087		ret = iio_device_claim_direct_mode(indio_dev);
1088		if (ret)
1089			return ret;
1090
1091		/* Protect against event capture. */
1092		if (vcnl4010_is_in_periodic_mode(data)) {
1093			ret = -EBUSY;
1094		} else {
1095			ret = vcnl4000_read_raw(indio_dev, chan, val, val2,
1096						mask);
1097		}
1098
1099		iio_device_release_direct_mode(indio_dev);
1100		return ret;
1101	case IIO_CHAN_INFO_SAMP_FREQ:
1102		switch (chan->type) {
1103		case IIO_PROXIMITY:
1104			ret = vcnl4010_read_proxy_samp_freq(data, val, val2);
1105			if (ret < 0)
1106				return ret;
1107			return IIO_VAL_INT_PLUS_MICRO;
1108		default:
1109			return -EINVAL;
1110		}
1111	default:
1112		return -EINVAL;
1113	}
1114}
1115
1116static int vcnl4010_read_avail(struct iio_dev *indio_dev,
1117			       struct iio_chan_spec const *chan,
1118			       const int **vals, int *type, int *length,
1119			       long mask)
1120{
1121	switch (mask) {
1122	case IIO_CHAN_INFO_SAMP_FREQ:
1123		*vals = (int *)vcnl4010_prox_sampling_frequency;
1124		*type = IIO_VAL_INT_PLUS_MICRO;
1125		*length = 2 * ARRAY_SIZE(vcnl4010_prox_sampling_frequency);
1126		return IIO_AVAIL_LIST;
1127	default:
1128		return -EINVAL;
1129	}
1130}
1131
1132static int vcnl4010_write_proxy_samp_freq(struct vcnl4000_data *data, int val,
1133					  int val2)
1134{
1135	unsigned int i;
1136	int index = -1;
1137
1138	for (i = 0; i < ARRAY_SIZE(vcnl4010_prox_sampling_frequency); i++) {
1139		if (val == vcnl4010_prox_sampling_frequency[i][0] &&
1140		    val2 == vcnl4010_prox_sampling_frequency[i][1]) {
1141			index = i;
1142			break;
1143		}
1144	}
1145
1146	if (index < 0)
1147		return -EINVAL;
1148
1149	return i2c_smbus_write_byte_data(data->client, VCNL4010_PROX_RATE,
1150					 index);
1151}
1152
1153static int vcnl4010_write_raw(struct iio_dev *indio_dev,
1154			      struct iio_chan_spec const *chan,
1155			      int val, int val2, long mask)
1156{
1157	int ret;
1158	struct vcnl4000_data *data = iio_priv(indio_dev);
1159
1160	ret = iio_device_claim_direct_mode(indio_dev);
1161	if (ret)
1162		return ret;
1163
1164	/* Protect against event capture. */
1165	if (vcnl4010_is_in_periodic_mode(data)) {
1166		ret = -EBUSY;
1167		goto end;
1168	}
1169
1170	switch (mask) {
1171	case IIO_CHAN_INFO_SAMP_FREQ:
1172		switch (chan->type) {
1173		case IIO_PROXIMITY:
1174			ret = vcnl4010_write_proxy_samp_freq(data, val, val2);
1175			goto end;
1176		default:
1177			ret = -EINVAL;
1178			goto end;
1179		}
1180	default:
1181		ret = -EINVAL;
1182		goto end;
1183	}
1184
1185end:
1186	iio_device_release_direct_mode(indio_dev);
1187	return ret;
1188}
1189
1190static int vcnl4010_read_event(struct iio_dev *indio_dev,
1191			       const struct iio_chan_spec *chan,
1192			       enum iio_event_type type,
1193			       enum iio_event_direction dir,
1194			       enum iio_event_info info,
1195			       int *val, int *val2)
1196{
1197	int ret;
1198	struct vcnl4000_data *data = iio_priv(indio_dev);
1199
1200	switch (info) {
1201	case IIO_EV_INFO_VALUE:
1202		switch (dir) {
1203		case IIO_EV_DIR_RISING:
1204			ret = vcnl4000_read_data(data, VCNL4010_HIGH_THR_HI,
1205						 val);
1206			if (ret < 0)
1207				return ret;
1208			return IIO_VAL_INT;
1209		case IIO_EV_DIR_FALLING:
1210			ret = vcnl4000_read_data(data, VCNL4010_LOW_THR_HI,
1211						 val);
1212			if (ret < 0)
1213				return ret;
1214			return IIO_VAL_INT;
1215		default:
1216			return -EINVAL;
1217		}
1218	default:
1219		return -EINVAL;
1220	}
1221}
1222
1223static int vcnl4010_write_event(struct iio_dev *indio_dev,
1224				const struct iio_chan_spec *chan,
1225				enum iio_event_type type,
1226				enum iio_event_direction dir,
1227				enum iio_event_info info,
1228				int val, int val2)
1229{
1230	int ret;
1231	struct vcnl4000_data *data = iio_priv(indio_dev);
1232
1233	switch (info) {
1234	case IIO_EV_INFO_VALUE:
1235		switch (dir) {
1236		case IIO_EV_DIR_RISING:
1237			ret = vcnl4000_write_data(data, VCNL4010_HIGH_THR_HI,
1238						  val);
1239			if (ret < 0)
1240				return ret;
1241			return IIO_VAL_INT;
1242		case IIO_EV_DIR_FALLING:
1243			ret = vcnl4000_write_data(data, VCNL4010_LOW_THR_HI,
1244						  val);
1245			if (ret < 0)
1246				return ret;
1247			return IIO_VAL_INT;
1248		default:
1249			return -EINVAL;
1250		}
1251	default:
1252		return -EINVAL;
1253	}
1254}
1255
1256static int vcnl4040_read_event(struct iio_dev *indio_dev,
1257			       const struct iio_chan_spec *chan,
1258			       enum iio_event_type type,
1259			       enum iio_event_direction dir,
1260			       enum iio_event_info info,
1261			       int *val, int *val2)
1262{
1263	int ret;
1264	struct vcnl4000_data *data = iio_priv(indio_dev);
1265
1266	switch (chan->type) {
1267	case IIO_LIGHT:
1268		switch (info) {
1269		case IIO_EV_INFO_PERIOD:
1270			return vcnl4040_read_als_period(data, val, val2);
1271		case IIO_EV_INFO_VALUE:
1272			switch (dir) {
1273			case IIO_EV_DIR_RISING:
1274				ret = i2c_smbus_read_word_data(data->client,
1275							       VCNL4040_ALS_THDH_LM);
1276				break;
1277			case IIO_EV_DIR_FALLING:
1278				ret = i2c_smbus_read_word_data(data->client,
1279							       VCNL4040_ALS_THDL_LM);
1280				break;
1281			default:
1282				return -EINVAL;
1283			}
1284			break;
1285		default:
1286			return -EINVAL;
1287		}
1288		break;
1289	case IIO_PROXIMITY:
1290		switch (info) {
1291		case IIO_EV_INFO_PERIOD:
1292			return vcnl4040_read_ps_period(data, val, val2);
1293		case IIO_EV_INFO_VALUE:
1294			switch (dir) {
1295			case IIO_EV_DIR_RISING:
1296				ret = i2c_smbus_read_word_data(data->client,
1297							       VCNL4040_PS_THDH_LM);
1298				break;
1299			case IIO_EV_DIR_FALLING:
1300				ret = i2c_smbus_read_word_data(data->client,
1301							       VCNL4040_PS_THDL_LM);
1302				break;
1303			default:
1304				return -EINVAL;
1305			}
1306			break;
1307		default:
1308			return -EINVAL;
1309		}
1310		break;
1311	default:
1312		return -EINVAL;
1313	}
1314	if (ret < 0)
1315		return ret;
1316	*val = ret;
1317	return IIO_VAL_INT;
1318}
1319
1320static int vcnl4040_write_event(struct iio_dev *indio_dev,
1321				const struct iio_chan_spec *chan,
1322				enum iio_event_type type,
1323				enum iio_event_direction dir,
1324				enum iio_event_info info,
1325				int val, int val2)
1326{
1327	int ret;
1328	struct vcnl4000_data *data = iio_priv(indio_dev);
1329
1330	switch (chan->type) {
1331	case IIO_LIGHT:
1332		switch (info) {
1333		case IIO_EV_INFO_PERIOD:
1334			return vcnl4040_write_als_period(data, val, val2);
1335		case IIO_EV_INFO_VALUE:
1336			switch (dir) {
1337			case IIO_EV_DIR_RISING:
1338				ret = i2c_smbus_write_word_data(data->client,
1339								VCNL4040_ALS_THDH_LM,
1340								val);
1341				break;
1342			case IIO_EV_DIR_FALLING:
1343				ret = i2c_smbus_write_word_data(data->client,
1344								VCNL4040_ALS_THDL_LM,
1345								val);
1346				break;
1347			default:
1348				return -EINVAL;
1349			}
1350			break;
1351		default:
1352			return -EINVAL;
1353		}
1354		break;
1355	case IIO_PROXIMITY:
1356		switch (info) {
1357		case IIO_EV_INFO_PERIOD:
1358			return vcnl4040_write_ps_period(data, val, val2);
1359		case IIO_EV_INFO_VALUE:
1360			switch (dir) {
1361			case IIO_EV_DIR_RISING:
1362				ret = i2c_smbus_write_word_data(data->client,
1363								VCNL4040_PS_THDH_LM,
1364								val);
1365				break;
1366			case IIO_EV_DIR_FALLING:
1367				ret = i2c_smbus_write_word_data(data->client,
1368								VCNL4040_PS_THDL_LM,
1369								val);
1370				break;
1371			default:
1372				return -EINVAL;
1373			}
1374			break;
1375		default:
1376			return -EINVAL;
1377		}
1378		break;
1379	default:
1380		return -EINVAL;
1381	}
1382	if (ret < 0)
1383		return ret;
1384	return IIO_VAL_INT;
1385}
1386
1387static bool vcnl4010_is_thr_enabled(struct vcnl4000_data *data)
1388{
1389	int ret;
1390
1391	ret = i2c_smbus_read_byte_data(data->client, VCNL4010_INT_CTRL);
1392	if (ret < 0)
1393		return false;
1394
1395	return !!(ret & VCNL4010_INT_THR_EN);
1396}
1397
1398static int vcnl4010_read_event_config(struct iio_dev *indio_dev,
1399				      const struct iio_chan_spec *chan,
1400				      enum iio_event_type type,
1401				      enum iio_event_direction dir)
1402{
1403	struct vcnl4000_data *data = iio_priv(indio_dev);
1404
1405	switch (chan->type) {
1406	case IIO_PROXIMITY:
1407		return vcnl4010_is_thr_enabled(data);
1408	default:
1409		return -EINVAL;
1410	}
1411}
1412
1413static int vcnl4010_config_threshold(struct iio_dev *indio_dev, bool state)
1414{
1415	struct vcnl4000_data *data = iio_priv(indio_dev);
1416	int ret;
1417	int icr;
1418	int command;
1419
1420	if (state) {
1421		ret = iio_device_claim_direct_mode(indio_dev);
1422		if (ret)
1423			return ret;
1424
1425		/* Enable periodic measurement of proximity data. */
1426		command = VCNL4000_SELF_TIMED_EN | VCNL4000_PROX_EN;
1427
1428		/*
1429		 * Enable interrupts on threshold, for proximity data by
1430		 * default.
1431		 */
1432		icr = VCNL4010_INT_THR_EN;
1433	} else {
1434		if (!vcnl4010_is_thr_enabled(data))
1435			return 0;
1436
1437		command = 0;
1438		icr = 0;
1439	}
1440
1441	ret = i2c_smbus_write_byte_data(data->client, VCNL4000_COMMAND,
1442					command);
1443	if (ret < 0)
1444		goto end;
1445
1446	ret = i2c_smbus_write_byte_data(data->client, VCNL4010_INT_CTRL, icr);
1447
1448end:
1449	if (state)
1450		iio_device_release_direct_mode(indio_dev);
1451
1452	return ret;
1453}
1454
1455static int vcnl4010_write_event_config(struct iio_dev *indio_dev,
1456				       const struct iio_chan_spec *chan,
1457				       enum iio_event_type type,
1458				       enum iio_event_direction dir,
1459				       bool state)
1460{
1461	switch (chan->type) {
1462	case IIO_PROXIMITY:
1463		return vcnl4010_config_threshold(indio_dev, state);
1464	default:
1465		return -EINVAL;
1466	}
1467}
1468
1469static int vcnl4040_read_event_config(struct iio_dev *indio_dev,
1470				      const struct iio_chan_spec *chan,
1471				      enum iio_event_type type,
1472				      enum iio_event_direction dir)
1473{
1474	int ret;
1475	struct vcnl4000_data *data = iio_priv(indio_dev);
1476
1477	switch (chan->type) {
1478	case IIO_LIGHT:
1479		ret = i2c_smbus_read_word_data(data->client, VCNL4200_AL_CONF);
1480		if (ret < 0)
1481			return ret;
1482
1483		data->als_int = FIELD_GET(VCNL4040_ALS_CONF_INT_EN, ret);
1484
1485		return data->als_int;
1486	case IIO_PROXIMITY:
1487		ret = i2c_smbus_read_word_data(data->client, VCNL4200_PS_CONF1);
1488		if (ret < 0)
1489			return ret;
1490
1491		data->ps_int = FIELD_GET(VCNL4040_PS_CONF2_PS_INT, ret);
1492
1493		return (dir == IIO_EV_DIR_RISING) ?
1494			FIELD_GET(VCNL4040_PS_IF_AWAY, ret) :
1495			FIELD_GET(VCNL4040_PS_IF_CLOSE, ret);
1496	default:
1497		return -EINVAL;
1498	}
1499}
1500
1501static int vcnl4040_write_event_config(struct iio_dev *indio_dev,
1502				       const struct iio_chan_spec *chan,
1503				       enum iio_event_type type,
1504				       enum iio_event_direction dir,
1505				       bool state)
1506{
1507	int ret = -EINVAL;
1508	u16 val, mask;
1509	struct vcnl4000_data *data = iio_priv(indio_dev);
1510
1511	mutex_lock(&data->vcnl4000_lock);
1512
1513	switch (chan->type) {
1514	case IIO_LIGHT:
1515		ret = i2c_smbus_read_word_data(data->client, VCNL4200_AL_CONF);
1516		if (ret < 0)
1517			goto out;
1518
1519		mask = VCNL4040_ALS_CONF_INT_EN;
1520		if (state)
1521			val = (ret | mask);
1522		else
1523			val = (ret & ~mask);
1524
1525		data->als_int = FIELD_GET(VCNL4040_ALS_CONF_INT_EN, val);
1526		ret = i2c_smbus_write_word_data(data->client, VCNL4200_AL_CONF,
1527						val);
1528		break;
1529	case IIO_PROXIMITY:
1530		ret = i2c_smbus_read_word_data(data->client, VCNL4200_PS_CONF1);
1531		if (ret < 0)
1532			goto out;
1533
1534		if (dir == IIO_EV_DIR_RISING)
1535			mask = VCNL4040_PS_IF_AWAY;
1536		else
1537			mask = VCNL4040_PS_IF_CLOSE;
1538
1539		val = state ? (ret | mask) : (ret & ~mask);
1540
1541		data->ps_int = FIELD_GET(VCNL4040_PS_CONF2_PS_INT, val);
1542		ret = i2c_smbus_write_word_data(data->client, VCNL4200_PS_CONF1,
1543						val);
1544		break;
1545	default:
1546		break;
1547	}
1548
1549out:
1550	mutex_unlock(&data->vcnl4000_lock);
1551
1552	return ret;
1553}
1554
1555static irqreturn_t vcnl4040_irq_thread(int irq, void *p)
1556{
1557	struct iio_dev *indio_dev = p;
1558	struct vcnl4000_data *data = iio_priv(indio_dev);
1559	int ret;
1560
1561	ret = i2c_smbus_read_word_data(data->client, data->chip_spec->int_reg);
1562	if (ret < 0)
1563		return IRQ_HANDLED;
1564
1565	if (ret & VCNL4040_PS_IF_CLOSE) {
1566		iio_push_event(indio_dev,
1567			       IIO_UNMOD_EVENT_CODE(IIO_PROXIMITY, 0,
1568						    IIO_EV_TYPE_THRESH,
1569						    IIO_EV_DIR_RISING),
1570			       iio_get_time_ns(indio_dev));
1571	}
1572
1573	if (ret & VCNL4040_PS_IF_AWAY) {
1574		iio_push_event(indio_dev,
1575			       IIO_UNMOD_EVENT_CODE(IIO_PROXIMITY, 0,
1576						    IIO_EV_TYPE_THRESH,
1577						    IIO_EV_DIR_FALLING),
1578			       iio_get_time_ns(indio_dev));
1579	}
1580
1581	if (ret & VCNL4040_ALS_FALLING) {
1582		iio_push_event(indio_dev,
1583			       IIO_UNMOD_EVENT_CODE(IIO_LIGHT, 0,
1584						    IIO_EV_TYPE_THRESH,
1585						    IIO_EV_DIR_FALLING),
1586			       iio_get_time_ns(indio_dev));
1587	}
1588
1589	if (ret & VCNL4040_ALS_RISING) {
1590		iio_push_event(indio_dev,
1591			       IIO_UNMOD_EVENT_CODE(IIO_LIGHT, 0,
1592						    IIO_EV_TYPE_THRESH,
1593						    IIO_EV_DIR_RISING),
1594			       iio_get_time_ns(indio_dev));
1595	}
1596
1597	return IRQ_HANDLED;
1598}
1599
1600static ssize_t vcnl4000_read_near_level(struct iio_dev *indio_dev,
1601					uintptr_t priv,
1602					const struct iio_chan_spec *chan,
1603					char *buf)
1604{
1605	struct vcnl4000_data *data = iio_priv(indio_dev);
1606
1607	return sprintf(buf, "%u\n", data->near_level);
1608}
1609
1610static irqreturn_t vcnl4010_irq_thread(int irq, void *p)
1611{
1612	struct iio_dev *indio_dev = p;
1613	struct vcnl4000_data *data = iio_priv(indio_dev);
1614	unsigned long isr;
1615	int ret;
1616
1617	ret = i2c_smbus_read_byte_data(data->client, VCNL4010_ISR);
1618	if (ret < 0)
1619		goto end;
1620
1621	isr = ret;
1622
1623	if (isr & VCNL4010_INT_THR) {
1624		if (test_bit(VCNL4010_INT_THR_LOW, &isr)) {
1625			iio_push_event(indio_dev,
1626				       IIO_UNMOD_EVENT_CODE(
1627					       IIO_PROXIMITY,
1628					       1,
1629					       IIO_EV_TYPE_THRESH,
1630					       IIO_EV_DIR_FALLING),
1631				       iio_get_time_ns(indio_dev));
1632		}
1633
1634		if (test_bit(VCNL4010_INT_THR_HIGH, &isr)) {
1635			iio_push_event(indio_dev,
1636				       IIO_UNMOD_EVENT_CODE(
1637					       IIO_PROXIMITY,
1638					       1,
1639					       IIO_EV_TYPE_THRESH,
1640					       IIO_EV_DIR_RISING),
1641				       iio_get_time_ns(indio_dev));
1642		}
1643
1644		i2c_smbus_write_byte_data(data->client, VCNL4010_ISR,
1645					  isr & VCNL4010_INT_THR);
1646	}
1647
1648	if (isr & VCNL4010_INT_DRDY && iio_buffer_enabled(indio_dev))
1649		iio_trigger_poll_nested(indio_dev->trig);
1650
1651end:
1652	return IRQ_HANDLED;
1653}
1654
1655static irqreturn_t vcnl4010_trigger_handler(int irq, void *p)
1656{
1657	struct iio_poll_func *pf = p;
1658	struct iio_dev *indio_dev = pf->indio_dev;
1659	struct vcnl4000_data *data = iio_priv(indio_dev);
1660	const unsigned long *active_scan_mask = indio_dev->active_scan_mask;
1661	u16 buffer[8] __aligned(8) = {0}; /* 1x16-bit + naturally aligned ts */
1662	bool data_read = false;
1663	unsigned long isr;
1664	int val = 0;
1665	int ret;
1666
1667	ret = i2c_smbus_read_byte_data(data->client, VCNL4010_ISR);
1668	if (ret < 0)
1669		goto end;
1670
1671	isr = ret;
1672
1673	if (test_bit(0, active_scan_mask)) {
1674		if (test_bit(VCNL4010_INT_PROXIMITY, &isr)) {
1675			ret = vcnl4000_read_data(data,
1676						 VCNL4000_PS_RESULT_HI,
1677						 &val);
1678			if (ret < 0)
1679				goto end;
1680
1681			buffer[0] = val;
1682			data_read = true;
1683		}
1684	}
1685
1686	ret = i2c_smbus_write_byte_data(data->client, VCNL4010_ISR,
1687					isr & VCNL4010_INT_DRDY);
1688	if (ret < 0)
1689		goto end;
1690
1691	if (!data_read)
1692		goto end;
1693
1694	iio_push_to_buffers_with_timestamp(indio_dev, buffer,
1695					   iio_get_time_ns(indio_dev));
1696
1697end:
1698	iio_trigger_notify_done(indio_dev->trig);
1699	return IRQ_HANDLED;
1700}
1701
1702static int vcnl4010_buffer_postenable(struct iio_dev *indio_dev)
1703{
1704	struct vcnl4000_data *data = iio_priv(indio_dev);
1705	int ret;
1706	int cmd;
1707
1708	/* Do not enable the buffer if we are already capturing events. */
1709	if (vcnl4010_is_in_periodic_mode(data))
1710		return -EBUSY;
1711
1712	ret = i2c_smbus_write_byte_data(data->client, VCNL4010_INT_CTRL,
1713					VCNL4010_INT_PROX_EN);
1714	if (ret < 0)
1715		return ret;
1716
1717	cmd = VCNL4000_SELF_TIMED_EN | VCNL4000_PROX_EN;
1718	return i2c_smbus_write_byte_data(data->client, VCNL4000_COMMAND, cmd);
1719}
1720
1721static int vcnl4010_buffer_predisable(struct iio_dev *indio_dev)
1722{
1723	struct vcnl4000_data *data = iio_priv(indio_dev);
1724	int ret;
1725
1726	ret = i2c_smbus_write_byte_data(data->client, VCNL4010_INT_CTRL, 0);
1727	if (ret < 0)
1728		return ret;
1729
1730	return i2c_smbus_write_byte_data(data->client, VCNL4000_COMMAND, 0);
1731}
1732
1733static const struct iio_buffer_setup_ops vcnl4010_buffer_ops = {
1734	.postenable = &vcnl4010_buffer_postenable,
1735	.predisable = &vcnl4010_buffer_predisable,
1736};
1737
1738static const struct iio_chan_spec_ext_info vcnl4000_ext_info[] = {
1739	{
1740		.name = "nearlevel",
1741		.shared = IIO_SEPARATE,
1742		.read = vcnl4000_read_near_level,
1743	},
1744	{ /* sentinel */ }
1745};
1746
1747static const struct iio_event_spec vcnl4000_event_spec[] = {
1748	{
1749		.type = IIO_EV_TYPE_THRESH,
1750		.dir = IIO_EV_DIR_RISING,
1751		.mask_separate = BIT(IIO_EV_INFO_VALUE),
1752	}, {
1753		.type = IIO_EV_TYPE_THRESH,
1754		.dir = IIO_EV_DIR_FALLING,
1755		.mask_separate = BIT(IIO_EV_INFO_VALUE),
1756	}, {
1757		.type = IIO_EV_TYPE_THRESH,
1758		.dir = IIO_EV_DIR_EITHER,
1759		.mask_separate = BIT(IIO_EV_INFO_ENABLE),
1760	}
1761};
1762
1763static const struct iio_event_spec vcnl4040_als_event_spec[] = {
1764	{
1765		.type = IIO_EV_TYPE_THRESH,
1766		.dir = IIO_EV_DIR_RISING,
1767		.mask_separate = BIT(IIO_EV_INFO_VALUE),
1768	}, {
1769		.type = IIO_EV_TYPE_THRESH,
1770		.dir = IIO_EV_DIR_FALLING,
1771		.mask_separate = BIT(IIO_EV_INFO_VALUE),
1772	}, {
1773		.type = IIO_EV_TYPE_THRESH,
1774		.dir = IIO_EV_DIR_EITHER,
1775		.mask_separate = BIT(IIO_EV_INFO_ENABLE) | BIT(IIO_EV_INFO_PERIOD),
1776	},
1777};
1778
1779static const struct iio_event_spec vcnl4040_event_spec[] = {
1780	{
1781		.type = IIO_EV_TYPE_THRESH,
1782		.dir = IIO_EV_DIR_RISING,
1783		.mask_separate = BIT(IIO_EV_INFO_VALUE) | BIT(IIO_EV_INFO_ENABLE),
1784	}, {
1785		.type = IIO_EV_TYPE_THRESH,
1786		.dir = IIO_EV_DIR_FALLING,
1787		.mask_separate = BIT(IIO_EV_INFO_VALUE) | BIT(IIO_EV_INFO_ENABLE),
1788	}, {
1789		.type = IIO_EV_TYPE_THRESH,
1790		.dir = IIO_EV_DIR_EITHER,
1791		.mask_separate = BIT(IIO_EV_INFO_PERIOD),
1792	},
1793};
1794
1795static const struct iio_chan_spec vcnl4000_channels[] = {
1796	{
1797		.type = IIO_LIGHT,
1798		.info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1799			BIT(IIO_CHAN_INFO_SCALE),
1800	}, {
1801		.type = IIO_PROXIMITY,
1802		.info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
1803		.ext_info = vcnl4000_ext_info,
1804	}
1805};
1806
1807static const struct iio_chan_spec vcnl4010_channels[] = {
1808	{
1809		.type = IIO_LIGHT,
1810		.scan_index = -1,
1811		.info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1812			BIT(IIO_CHAN_INFO_SCALE),
1813	}, {
1814		.type = IIO_PROXIMITY,
1815		.scan_index = 0,
1816		.info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1817			BIT(IIO_CHAN_INFO_SAMP_FREQ),
1818		.info_mask_separate_available = BIT(IIO_CHAN_INFO_SAMP_FREQ),
1819		.event_spec = vcnl4000_event_spec,
1820		.num_event_specs = ARRAY_SIZE(vcnl4000_event_spec),
1821		.ext_info = vcnl4000_ext_info,
1822		.scan_type = {
1823			.sign = 'u',
1824			.realbits = 16,
1825			.storagebits = 16,
1826			.endianness = IIO_CPU,
1827		},
1828	},
1829	IIO_CHAN_SOFT_TIMESTAMP(1),
1830};
1831
1832static const struct iio_chan_spec vcnl4040_channels[] = {
1833	{
1834		.type = IIO_LIGHT,
1835		.info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1836			BIT(IIO_CHAN_INFO_SCALE) |
1837			BIT(IIO_CHAN_INFO_INT_TIME),
1838		.info_mask_separate_available = BIT(IIO_CHAN_INFO_INT_TIME),
1839		.event_spec = vcnl4040_als_event_spec,
1840		.num_event_specs = ARRAY_SIZE(vcnl4040_als_event_spec),
1841	}, {
1842		.type = IIO_PROXIMITY,
1843		.info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
1844			BIT(IIO_CHAN_INFO_INT_TIME) |
1845			BIT(IIO_CHAN_INFO_OVERSAMPLING_RATIO) |
1846			BIT(IIO_CHAN_INFO_CALIBBIAS),
1847		.info_mask_separate_available = BIT(IIO_CHAN_INFO_INT_TIME) |
1848			BIT(IIO_CHAN_INFO_OVERSAMPLING_RATIO) |
1849			BIT(IIO_CHAN_INFO_CALIBBIAS),
1850		.ext_info = vcnl4000_ext_info,
1851		.event_spec = vcnl4040_event_spec,
1852		.num_event_specs = ARRAY_SIZE(vcnl4040_event_spec),
1853	}
1854};
1855
1856static const struct iio_info vcnl4000_info = {
1857	.read_raw = vcnl4000_read_raw,
1858};
1859
1860static const struct iio_info vcnl4010_info = {
1861	.read_raw = vcnl4010_read_raw,
1862	.read_avail = vcnl4010_read_avail,
1863	.write_raw = vcnl4010_write_raw,
1864	.read_event_value = vcnl4010_read_event,
1865	.write_event_value = vcnl4010_write_event,
1866	.read_event_config = vcnl4010_read_event_config,
1867	.write_event_config = vcnl4010_write_event_config,
1868};
1869
1870static const struct iio_info vcnl4040_info = {
1871	.read_raw = vcnl4000_read_raw,
1872	.write_raw = vcnl4040_write_raw,
1873	.read_event_value = vcnl4040_read_event,
1874	.write_event_value = vcnl4040_write_event,
1875	.read_event_config = vcnl4040_read_event_config,
1876	.write_event_config = vcnl4040_write_event_config,
1877	.read_avail = vcnl4040_read_avail,
1878};
1879
1880static const struct vcnl4000_chip_spec vcnl4000_chip_spec_cfg[] = {
1881	[VCNL4000] = {
1882		.prod = "VCNL4000",
1883		.init = vcnl4000_init,
1884		.measure_light = vcnl4000_measure_light,
1885		.measure_proximity = vcnl4000_measure_proximity,
1886		.set_power_state = vcnl4000_set_power_state,
1887		.channels = vcnl4000_channels,
1888		.num_channels = ARRAY_SIZE(vcnl4000_channels),
1889		.info = &vcnl4000_info,
1890	},
1891	[VCNL4010] = {
1892		.prod = "VCNL4010/4020",
1893		.init = vcnl4000_init,
1894		.measure_light = vcnl4000_measure_light,
1895		.measure_proximity = vcnl4000_measure_proximity,
1896		.set_power_state = vcnl4000_set_power_state,
1897		.channels = vcnl4010_channels,
1898		.num_channels = ARRAY_SIZE(vcnl4010_channels),
1899		.info = &vcnl4010_info,
1900		.irq_thread = vcnl4010_irq_thread,
1901		.trig_buffer_func = vcnl4010_trigger_handler,
1902		.buffer_setup_ops = &vcnl4010_buffer_ops,
1903	},
1904	[VCNL4040] = {
1905		.prod = "VCNL4040",
1906		.init = vcnl4200_init,
1907		.measure_light = vcnl4200_measure_light,
1908		.measure_proximity = vcnl4200_measure_proximity,
1909		.set_power_state = vcnl4200_set_power_state,
1910		.channels = vcnl4040_channels,
1911		.num_channels = ARRAY_SIZE(vcnl4040_channels),
1912		.info = &vcnl4040_info,
1913		.irq_thread = vcnl4040_irq_thread,
1914		.int_reg = VCNL4040_INT_FLAGS,
1915		.ps_it_times = &vcnl4040_ps_it_times,
1916		.num_ps_it_times = ARRAY_SIZE(vcnl4040_ps_it_times),
1917		.als_it_times = &vcnl4040_als_it_times,
1918		.num_als_it_times = ARRAY_SIZE(vcnl4040_als_it_times),
1919		.ulux_step = 100000,
1920	},
1921	[VCNL4200] = {
1922		.prod = "VCNL4200",
1923		.init = vcnl4200_init,
1924		.measure_light = vcnl4200_measure_light,
1925		.measure_proximity = vcnl4200_measure_proximity,
1926		.set_power_state = vcnl4200_set_power_state,
1927		.channels = vcnl4040_channels,
1928		.num_channels = ARRAY_SIZE(vcnl4000_channels),
1929		.info = &vcnl4040_info,
1930		.irq_thread = vcnl4040_irq_thread,
1931		.int_reg = VCNL4200_INT_FLAGS,
1932		.ps_it_times = &vcnl4200_ps_it_times,
1933		.num_ps_it_times = ARRAY_SIZE(vcnl4200_ps_it_times),
1934		.als_it_times = &vcnl4200_als_it_times,
1935		.num_als_it_times = ARRAY_SIZE(vcnl4200_als_it_times),
1936		.ulux_step = 24000,
1937	},
1938};
1939
1940static const struct iio_trigger_ops vcnl4010_trigger_ops = {
1941	.validate_device = iio_trigger_validate_own_device,
1942};
1943
1944static int vcnl4010_probe_trigger(struct iio_dev *indio_dev)
1945{
1946	struct vcnl4000_data *data = iio_priv(indio_dev);
1947	struct i2c_client *client = data->client;
1948	struct iio_trigger *trigger;
1949
1950	trigger = devm_iio_trigger_alloc(&client->dev, "%s-dev%d",
1951					 indio_dev->name,
1952					 iio_device_id(indio_dev));
1953	if (!trigger)
1954		return -ENOMEM;
1955
1956	trigger->ops = &vcnl4010_trigger_ops;
1957	iio_trigger_set_drvdata(trigger, indio_dev);
1958
1959	return devm_iio_trigger_register(&client->dev, trigger);
1960}
1961
1962static int vcnl4000_probe(struct i2c_client *client)
1963{
1964	const struct i2c_device_id *id = i2c_client_get_device_id(client);
1965	struct vcnl4000_data *data;
1966	struct iio_dev *indio_dev;
1967	int ret;
1968
1969	indio_dev = devm_iio_device_alloc(&client->dev, sizeof(*data));
1970	if (!indio_dev)
1971		return -ENOMEM;
1972
1973	data = iio_priv(indio_dev);
1974	i2c_set_clientdata(client, indio_dev);
1975	data->client = client;
1976	data->id = id->driver_data;
1977	data->chip_spec = &vcnl4000_chip_spec_cfg[data->id];
1978
1979	mutex_init(&data->vcnl4000_lock);
1980
1981	ret = data->chip_spec->init(data);
1982	if (ret < 0)
1983		return ret;
1984
1985	dev_dbg(&client->dev, "%s Ambient light/proximity sensor, Rev: %02x\n",
1986		data->chip_spec->prod, data->rev);
1987
1988	if (device_property_read_u32(&client->dev, "proximity-near-level",
1989				     &data->near_level))
1990		data->near_level = 0;
1991
1992	indio_dev->info = data->chip_spec->info;
1993	indio_dev->channels = data->chip_spec->channels;
1994	indio_dev->num_channels = data->chip_spec->num_channels;
1995	indio_dev->name = VCNL4000_DRV_NAME;
1996	indio_dev->modes = INDIO_DIRECT_MODE;
1997
1998	if (data->chip_spec->trig_buffer_func &&
1999	    data->chip_spec->buffer_setup_ops) {
2000		ret = devm_iio_triggered_buffer_setup(&client->dev, indio_dev,
2001						      NULL,
2002						      data->chip_spec->trig_buffer_func,
2003						      data->chip_spec->buffer_setup_ops);
2004		if (ret < 0) {
2005			dev_err(&client->dev,
2006				"unable to setup iio triggered buffer\n");
2007			return ret;
2008		}
2009	}
2010
2011	if (client->irq && data->chip_spec->irq_thread) {
2012		ret = devm_request_threaded_irq(&client->dev, client->irq,
2013						NULL, data->chip_spec->irq_thread,
2014						IRQF_TRIGGER_FALLING |
2015						IRQF_ONESHOT,
2016						"vcnl4000_irq",
2017						indio_dev);
2018		if (ret < 0) {
2019			dev_err(&client->dev, "irq request failed\n");
2020			return ret;
2021		}
2022
2023		ret = vcnl4010_probe_trigger(indio_dev);
2024		if (ret < 0)
2025			return ret;
2026	}
2027
2028	ret = pm_runtime_set_active(&client->dev);
2029	if (ret < 0)
2030		goto fail_poweroff;
2031
2032	ret = iio_device_register(indio_dev);
2033	if (ret < 0)
2034		goto fail_poweroff;
2035
2036	pm_runtime_enable(&client->dev);
2037	pm_runtime_set_autosuspend_delay(&client->dev, VCNL4000_SLEEP_DELAY_MS);
2038	pm_runtime_use_autosuspend(&client->dev);
2039
2040	return 0;
2041fail_poweroff:
2042	data->chip_spec->set_power_state(data, false);
2043	return ret;
2044}
2045
2046static const struct of_device_id vcnl_4000_of_match[] = {
2047	{
2048		.compatible = "vishay,vcnl4000",
2049		.data = (void *)VCNL4000,
2050	},
2051	{
2052		.compatible = "vishay,vcnl4010",
2053		.data = (void *)VCNL4010,
2054	},
2055	{
2056		.compatible = "vishay,vcnl4020",
2057		.data = (void *)VCNL4010,
2058	},
2059	{
2060		.compatible = "vishay,vcnl4040",
2061		.data = (void *)VCNL4040,
2062	},
2063	{
2064		.compatible = "vishay,vcnl4200",
2065		.data = (void *)VCNL4200,
2066	},
2067	{},
2068};
2069MODULE_DEVICE_TABLE(of, vcnl_4000_of_match);
2070
2071static void vcnl4000_remove(struct i2c_client *client)
2072{
2073	struct iio_dev *indio_dev = i2c_get_clientdata(client);
2074	struct vcnl4000_data *data = iio_priv(indio_dev);
2075	int ret;
2076
2077	pm_runtime_dont_use_autosuspend(&client->dev);
2078	pm_runtime_disable(&client->dev);
2079	iio_device_unregister(indio_dev);
2080	pm_runtime_set_suspended(&client->dev);
2081
2082	ret = data->chip_spec->set_power_state(data, false);
2083	if (ret)
2084		dev_warn(&client->dev, "Failed to power down (%pe)\n",
2085			 ERR_PTR(ret));
2086}
2087
2088static int vcnl4000_runtime_suspend(struct device *dev)
2089{
2090	struct iio_dev *indio_dev = i2c_get_clientdata(to_i2c_client(dev));
2091	struct vcnl4000_data *data = iio_priv(indio_dev);
2092
2093	return data->chip_spec->set_power_state(data, false);
2094}
2095
2096static int vcnl4000_runtime_resume(struct device *dev)
2097{
2098	struct iio_dev *indio_dev = i2c_get_clientdata(to_i2c_client(dev));
2099	struct vcnl4000_data *data = iio_priv(indio_dev);
2100
2101	return data->chip_spec->set_power_state(data, true);
2102}
2103
2104static DEFINE_RUNTIME_DEV_PM_OPS(vcnl4000_pm_ops, vcnl4000_runtime_suspend,
2105				 vcnl4000_runtime_resume, NULL);
2106
2107static struct i2c_driver vcnl4000_driver = {
2108	.driver = {
2109		.name   = VCNL4000_DRV_NAME,
2110		.pm	= pm_ptr(&vcnl4000_pm_ops),
2111		.of_match_table = vcnl_4000_of_match,
2112	},
2113	.probe = vcnl4000_probe,
2114	.id_table = vcnl4000_id,
2115	.remove	= vcnl4000_remove,
2116};
2117
2118module_i2c_driver(vcnl4000_driver);
2119
2120MODULE_AUTHOR("Peter Meerwald <pmeerw@pmeerw.net>");
2121MODULE_AUTHOR("Mathieu Othacehe <m.othacehe@gmail.com>");
2122MODULE_DESCRIPTION("Vishay VCNL4000 proximity/ambient light sensor driver");
2123MODULE_LICENSE("GPL");