xref: /openbmc/linux/drivers/iio/light/ltrf216a.c (revision 7cf15f42)
1 // SPDX-License-Identifier: GPL-2.0-only
2 /*
3  * LTRF216A Ambient Light Sensor
4  *
5  * Copyright (C) 2022 Collabora, Ltd.
6  * Author: Shreeya Patel <shreeya.patel@collabora.com>
7  *
8  * Copyright (C) 2021 Lite-On Technology Corp (Singapore)
9  * Author: Shi Zhigang <Zhigang.Shi@liteon.com>
10  *
11  * IIO driver for LTRF216A (7-bit I2C slave address 0x53).
12  */
13 
14 #include <linux/bitfield.h>
15 #include <linux/bits.h>
16 #include <linux/delay.h>
17 #include <linux/i2c.h>
18 #include <linux/init.h>
19 #include <linux/iopoll.h>
20 #include <linux/mod_devicetable.h>
21 #include <linux/module.h>
22 #include <linux/mutex.h>
23 #include <linux/pm.h>
24 #include <linux/pm_runtime.h>
25 #include <linux/regmap.h>
26 
27 #include <linux/iio/iio.h>
28 
29 #include <asm/unaligned.h>
30 
31 #define LTRF216A_ALS_RESET_MASK		BIT(4)
32 #define LTRF216A_ALS_DATA_STATUS	BIT(3)
33 #define LTRF216A_ALS_ENABLE_MASK	BIT(1)
34 #define LTRF216A_MAIN_CTRL		0x00
35 #define LTRF216A_ALS_MEAS_RES		0x04
36 #define LTRF216A_ALS_GAIN		0x05
37 #define LTRF216A_PART_ID		0x06
38 #define LTRF216A_MAIN_STATUS		0x07
39 #define LTRF216A_ALS_CLEAR_DATA_0	0x0a
40 #define LTRF216A_ALS_CLEAR_DATA_1	0x0b
41 #define LTRF216A_ALS_CLEAR_DATA_2	0x0c
42 #define LTRF216A_ALS_DATA_0		0x0d
43 #define LTRF216A_ALS_DATA_1		0x0e
44 #define LTRF216A_ALS_DATA_2		0x0f
45 #define LTRF216A_INT_CFG		0x19
46 #define LTRF216A_INT_PST		0x1a
47 #define LTRF216A_ALS_THRES_UP_0		0x21
48 #define LTRF216A_ALS_THRES_UP_1		0x22
49 #define LTRF216A_ALS_THRES_UP_2		0x23
50 #define LTRF216A_ALS_THRES_LOW_0	0x24
51 #define LTRF216A_ALS_THRES_LOW_1	0x25
52 #define LTRF216A_ALS_THRES_LOW_2	0x26
53 #define LTRF216A_ALS_READ_DATA_DELAY_US	20000
54 
55 static const int ltrf216a_int_time_available[][2] = {
56 	{ 0, 400000 },
57 	{ 0, 200000 },
58 	{ 0, 100000 },
59 	{ 0,  50000 },
60 	{ 0,  25000 },
61 };
62 
63 static const int ltrf216a_int_time_reg[][2] = {
64 	{ 400, 0x03 },
65 	{ 200, 0x13 },
66 	{ 100, 0x22 },
67 	{  50, 0x31 },
68 	{  25, 0x40 },
69 };
70 
71 /*
72  * Window Factor is needed when the device is under Window glass
73  * with coated tinted ink. This is to compensate for the light loss
74  * due to the lower transmission rate of the window glass and helps
75  * in calculating lux.
76  */
77 #define LTRF216A_WIN_FAC	1
78 
79 struct ltrf216a_data {
80 	struct regmap *regmap;
81 	struct i2c_client *client;
82 	u32 int_time;
83 	u16 int_time_fac;
84 	u8 als_gain_fac;
85 	/*
86 	 * Protects regmap accesses and makes sure integration time
87 	 * remains constant during the measurement of lux.
88 	 */
89 	struct mutex lock;
90 };
91 
92 static const struct iio_chan_spec ltrf216a_channels[] = {
93 	{
94 		.type = IIO_LIGHT,
95 		.info_mask_separate =
96 			BIT(IIO_CHAN_INFO_RAW) |
97 			BIT(IIO_CHAN_INFO_PROCESSED) |
98 			BIT(IIO_CHAN_INFO_INT_TIME),
99 		.info_mask_separate_available =
100 			BIT(IIO_CHAN_INFO_INT_TIME),
101 	},
102 };
103 
ltrf216a_reset(struct iio_dev * indio_dev)104 static void ltrf216a_reset(struct iio_dev *indio_dev)
105 {
106 	struct ltrf216a_data *data = iio_priv(indio_dev);
107 
108 	/* reset sensor, chip fails to respond to this, so ignore any errors */
109 	regmap_write(data->regmap, LTRF216A_MAIN_CTRL, LTRF216A_ALS_RESET_MASK);
110 
111 	/* reset time */
112 	usleep_range(1000, 2000);
113 }
114 
ltrf216a_enable(struct iio_dev * indio_dev)115 static int ltrf216a_enable(struct iio_dev *indio_dev)
116 {
117 	struct ltrf216a_data *data = iio_priv(indio_dev);
118 	struct device *dev = &data->client->dev;
119 	int ret;
120 
121 	/* enable sensor */
122 	ret = regmap_set_bits(data->regmap,
123 			      LTRF216A_MAIN_CTRL, LTRF216A_ALS_ENABLE_MASK);
124 	if (ret) {
125 		dev_err(dev, "failed to enable sensor: %d\n", ret);
126 		return ret;
127 	}
128 
129 	/* sleep for one integration cycle after enabling the device */
130 	msleep(ltrf216a_int_time_reg[0][0]);
131 
132 	return 0;
133 }
134 
ltrf216a_disable(struct iio_dev * indio_dev)135 static int ltrf216a_disable(struct iio_dev *indio_dev)
136 {
137 	struct ltrf216a_data *data = iio_priv(indio_dev);
138 	struct device *dev = &data->client->dev;
139 	int ret;
140 
141 	ret = regmap_write(data->regmap, LTRF216A_MAIN_CTRL, 0);
142 	if (ret)
143 		dev_err(dev, "failed to disable sensor: %d\n", ret);
144 
145 	return ret;
146 }
147 
ltrf216a_cleanup(void * data)148 static void ltrf216a_cleanup(void *data)
149 {
150 	struct iio_dev *indio_dev = data;
151 
152 	ltrf216a_disable(indio_dev);
153 }
154 
ltrf216a_set_int_time(struct ltrf216a_data * data,int itime)155 static int ltrf216a_set_int_time(struct ltrf216a_data *data, int itime)
156 {
157 	struct device *dev = &data->client->dev;
158 	unsigned int i;
159 	u8 reg_val;
160 	int ret;
161 
162 	for (i = 0; i < ARRAY_SIZE(ltrf216a_int_time_available); i++) {
163 		if (ltrf216a_int_time_available[i][1] == itime)
164 			break;
165 	}
166 	if (i == ARRAY_SIZE(ltrf216a_int_time_available))
167 		return -EINVAL;
168 
169 	reg_val = ltrf216a_int_time_reg[i][1];
170 
171 	ret = regmap_write(data->regmap, LTRF216A_ALS_MEAS_RES, reg_val);
172 	if (ret) {
173 		dev_err(dev, "failed to set integration time: %d\n", ret);
174 		return ret;
175 	}
176 
177 	data->int_time_fac = ltrf216a_int_time_reg[i][0];
178 	data->int_time = itime;
179 
180 	return 0;
181 }
182 
ltrf216a_get_int_time(struct ltrf216a_data * data,int * val,int * val2)183 static int ltrf216a_get_int_time(struct ltrf216a_data *data,
184 				 int *val, int *val2)
185 {
186 	*val = 0;
187 	*val2 = data->int_time;
188 	return IIO_VAL_INT_PLUS_MICRO;
189 }
190 
ltrf216a_set_power_state(struct ltrf216a_data * data,bool on)191 static int ltrf216a_set_power_state(struct ltrf216a_data *data, bool on)
192 {
193 	struct device *dev = &data->client->dev;
194 	int ret = 0;
195 
196 	if (on) {
197 		ret = pm_runtime_resume_and_get(dev);
198 		if (ret) {
199 			dev_err(dev, "failed to resume runtime PM: %d\n", ret);
200 			return ret;
201 		}
202 	} else {
203 		pm_runtime_mark_last_busy(dev);
204 		pm_runtime_put_autosuspend(dev);
205 	}
206 
207 	return ret;
208 }
209 
ltrf216a_read_data(struct ltrf216a_data * data,u8 addr)210 static int ltrf216a_read_data(struct ltrf216a_data *data, u8 addr)
211 {
212 	struct device *dev = &data->client->dev;
213 	int ret, val;
214 	u8 buf[3];
215 
216 	ret = regmap_read_poll_timeout(data->regmap, LTRF216A_MAIN_STATUS,
217 				       val, val & LTRF216A_ALS_DATA_STATUS,
218 				       LTRF216A_ALS_READ_DATA_DELAY_US,
219 				       LTRF216A_ALS_READ_DATA_DELAY_US * 50);
220 	if (ret) {
221 		dev_err(dev, "failed to wait for measurement data: %d\n", ret);
222 		return ret;
223 	}
224 
225 	ret = regmap_bulk_read(data->regmap, addr, buf, sizeof(buf));
226 	if (ret) {
227 		dev_err(dev, "failed to read measurement data: %d\n", ret);
228 		return ret;
229 	}
230 
231 	return get_unaligned_le24(&buf[0]);
232 }
233 
ltrf216a_get_lux(struct ltrf216a_data * data)234 static int ltrf216a_get_lux(struct ltrf216a_data *data)
235 {
236 	int ret, greendata;
237 	u64 lux, div;
238 
239 	ret = ltrf216a_set_power_state(data, true);
240 	if (ret)
241 		return ret;
242 
243 	greendata = ltrf216a_read_data(data, LTRF216A_ALS_DATA_0);
244 	if (greendata < 0)
245 		return greendata;
246 
247 	ltrf216a_set_power_state(data, false);
248 
249 	lux = greendata * 45 * LTRF216A_WIN_FAC * 100;
250 	div = data->als_gain_fac * data->int_time_fac * 100;
251 
252 	return div_u64(lux, div);
253 }
254 
ltrf216a_read_raw(struct iio_dev * indio_dev,struct iio_chan_spec const * chan,int * val,int * val2,long mask)255 static int ltrf216a_read_raw(struct iio_dev *indio_dev,
256 			     struct iio_chan_spec const *chan, int *val,
257 			     int *val2, long mask)
258 {
259 	struct ltrf216a_data *data = iio_priv(indio_dev);
260 	int ret;
261 
262 	switch (mask) {
263 	case IIO_CHAN_INFO_RAW:
264 		ret = ltrf216a_set_power_state(data, true);
265 		if (ret)
266 			return ret;
267 		mutex_lock(&data->lock);
268 		ret = ltrf216a_read_data(data, LTRF216A_ALS_DATA_0);
269 		mutex_unlock(&data->lock);
270 		ltrf216a_set_power_state(data, false);
271 		if (ret < 0)
272 			return ret;
273 		*val = ret;
274 		return IIO_VAL_INT;
275 	case IIO_CHAN_INFO_PROCESSED:
276 		mutex_lock(&data->lock);
277 		ret = ltrf216a_get_lux(data);
278 		mutex_unlock(&data->lock);
279 		if (ret < 0)
280 			return ret;
281 		*val = ret;
282 		return IIO_VAL_INT;
283 	case IIO_CHAN_INFO_INT_TIME:
284 		mutex_lock(&data->lock);
285 		ret = ltrf216a_get_int_time(data, val, val2);
286 		mutex_unlock(&data->lock);
287 		return ret;
288 	default:
289 		return -EINVAL;
290 	}
291 }
292 
ltrf216a_write_raw(struct iio_dev * indio_dev,struct iio_chan_spec const * chan,int val,int val2,long mask)293 static int ltrf216a_write_raw(struct iio_dev *indio_dev,
294 			      struct iio_chan_spec const *chan, int val,
295 			      int val2, long mask)
296 {
297 	struct ltrf216a_data *data = iio_priv(indio_dev);
298 	int ret;
299 
300 	switch (mask) {
301 	case IIO_CHAN_INFO_INT_TIME:
302 		if (val != 0)
303 			return -EINVAL;
304 		mutex_lock(&data->lock);
305 		ret = ltrf216a_set_int_time(data, val2);
306 		mutex_unlock(&data->lock);
307 		return ret;
308 	default:
309 		return -EINVAL;
310 	}
311 }
312 
ltrf216a_read_available(struct iio_dev * indio_dev,struct iio_chan_spec const * chan,const int ** vals,int * type,int * length,long mask)313 static int ltrf216a_read_available(struct iio_dev *indio_dev,
314 				   struct iio_chan_spec const *chan,
315 				   const int **vals, int *type, int *length,
316 				   long mask)
317 {
318 	switch (mask) {
319 	case IIO_CHAN_INFO_INT_TIME:
320 		*length = ARRAY_SIZE(ltrf216a_int_time_available) * 2;
321 		*vals = (const int *)ltrf216a_int_time_available;
322 		*type = IIO_VAL_INT_PLUS_MICRO;
323 		return IIO_AVAIL_LIST;
324 	default:
325 		return -EINVAL;
326 	}
327 }
328 
329 static const struct iio_info ltrf216a_info = {
330 	.read_raw = ltrf216a_read_raw,
331 	.write_raw = ltrf216a_write_raw,
332 	.read_avail = ltrf216a_read_available,
333 };
334 
ltrf216a_readable_reg(struct device * dev,unsigned int reg)335 static bool ltrf216a_readable_reg(struct device *dev, unsigned int reg)
336 {
337 	switch (reg) {
338 	case LTRF216A_MAIN_CTRL:
339 	case LTRF216A_ALS_MEAS_RES:
340 	case LTRF216A_ALS_GAIN:
341 	case LTRF216A_PART_ID:
342 	case LTRF216A_MAIN_STATUS:
343 	case LTRF216A_ALS_CLEAR_DATA_0:
344 	case LTRF216A_ALS_CLEAR_DATA_1:
345 	case LTRF216A_ALS_CLEAR_DATA_2:
346 	case LTRF216A_ALS_DATA_0:
347 	case LTRF216A_ALS_DATA_1:
348 	case LTRF216A_ALS_DATA_2:
349 	case LTRF216A_INT_CFG:
350 	case LTRF216A_INT_PST:
351 	case LTRF216A_ALS_THRES_UP_0:
352 	case LTRF216A_ALS_THRES_UP_1:
353 	case LTRF216A_ALS_THRES_UP_2:
354 	case LTRF216A_ALS_THRES_LOW_0:
355 	case LTRF216A_ALS_THRES_LOW_1:
356 	case LTRF216A_ALS_THRES_LOW_2:
357 		return true;
358 	default:
359 		return false;
360 	}
361 }
362 
ltrf216a_writable_reg(struct device * dev,unsigned int reg)363 static bool ltrf216a_writable_reg(struct device *dev, unsigned int reg)
364 {
365 	switch (reg) {
366 	case LTRF216A_MAIN_CTRL:
367 	case LTRF216A_ALS_MEAS_RES:
368 	case LTRF216A_ALS_GAIN:
369 	case LTRF216A_INT_CFG:
370 	case LTRF216A_INT_PST:
371 	case LTRF216A_ALS_THRES_UP_0:
372 	case LTRF216A_ALS_THRES_UP_1:
373 	case LTRF216A_ALS_THRES_UP_2:
374 	case LTRF216A_ALS_THRES_LOW_0:
375 	case LTRF216A_ALS_THRES_LOW_1:
376 	case LTRF216A_ALS_THRES_LOW_2:
377 		return true;
378 	default:
379 		return false;
380 	}
381 }
382 
ltrf216a_volatile_reg(struct device * dev,unsigned int reg)383 static bool ltrf216a_volatile_reg(struct device *dev, unsigned int reg)
384 {
385 	switch (reg) {
386 	case LTRF216A_MAIN_STATUS:
387 	case LTRF216A_ALS_CLEAR_DATA_0:
388 	case LTRF216A_ALS_CLEAR_DATA_1:
389 	case LTRF216A_ALS_CLEAR_DATA_2:
390 	case LTRF216A_ALS_DATA_0:
391 	case LTRF216A_ALS_DATA_1:
392 	case LTRF216A_ALS_DATA_2:
393 		return true;
394 	default:
395 		return false;
396 	}
397 }
398 
ltrf216a_precious_reg(struct device * dev,unsigned int reg)399 static bool ltrf216a_precious_reg(struct device *dev, unsigned int reg)
400 {
401 	return reg == LTRF216A_MAIN_STATUS;
402 }
403 
404 static const struct regmap_config ltrf216a_regmap_config = {
405 	.name = "ltrf216a",
406 	.reg_bits = 8,
407 	.val_bits = 8,
408 	.cache_type = REGCACHE_RBTREE,
409 	.max_register = LTRF216A_ALS_THRES_LOW_2,
410 	.readable_reg = ltrf216a_readable_reg,
411 	.writeable_reg = ltrf216a_writable_reg,
412 	.volatile_reg = ltrf216a_volatile_reg,
413 	.precious_reg = ltrf216a_precious_reg,
414 	.disable_locking = true,
415 };
416 
ltrf216a_probe(struct i2c_client * client)417 static int ltrf216a_probe(struct i2c_client *client)
418 {
419 	struct ltrf216a_data *data;
420 	struct iio_dev *indio_dev;
421 	int ret;
422 
423 	indio_dev = devm_iio_device_alloc(&client->dev, sizeof(*data));
424 	if (!indio_dev)
425 		return -ENOMEM;
426 
427 	data = iio_priv(indio_dev);
428 
429 	data->regmap = devm_regmap_init_i2c(client, &ltrf216a_regmap_config);
430 	if (IS_ERR(data->regmap))
431 		return dev_err_probe(&client->dev, PTR_ERR(data->regmap),
432 				     "regmap initialization failed\n");
433 
434 	i2c_set_clientdata(client, indio_dev);
435 	data->client = client;
436 
437 	mutex_init(&data->lock);
438 
439 	indio_dev->info = &ltrf216a_info;
440 	indio_dev->name = "ltrf216a";
441 	indio_dev->channels = ltrf216a_channels;
442 	indio_dev->num_channels = ARRAY_SIZE(ltrf216a_channels);
443 	indio_dev->modes = INDIO_DIRECT_MODE;
444 
445 	ret = pm_runtime_set_active(&client->dev);
446 	if (ret)
447 		return ret;
448 
449 	/* reset sensor, chip fails to respond to this, so ignore any errors */
450 	ltrf216a_reset(indio_dev);
451 
452 	ret = regmap_reinit_cache(data->regmap, &ltrf216a_regmap_config);
453 	if (ret)
454 		return dev_err_probe(&client->dev, ret,
455 				     "failed to reinit regmap cache\n");
456 
457 	ret = ltrf216a_enable(indio_dev);
458 	if (ret)
459 		return ret;
460 
461 	ret = devm_add_action_or_reset(&client->dev, ltrf216a_cleanup,
462 				       indio_dev);
463 	if (ret)
464 		return ret;
465 
466 	ret = devm_pm_runtime_enable(&client->dev);
467 	if (ret)
468 		return dev_err_probe(&client->dev, ret,
469 				     "failed to enable runtime PM\n");
470 
471 	pm_runtime_set_autosuspend_delay(&client->dev, 1000);
472 	pm_runtime_use_autosuspend(&client->dev);
473 
474 	data->int_time = 100000;
475 	data->int_time_fac = 100;
476 	data->als_gain_fac = 3;
477 
478 	return devm_iio_device_register(&client->dev, indio_dev);
479 }
480 
ltrf216a_runtime_suspend(struct device * dev)481 static int ltrf216a_runtime_suspend(struct device *dev)
482 {
483 	struct iio_dev *indio_dev = i2c_get_clientdata(to_i2c_client(dev));
484 	struct ltrf216a_data *data = iio_priv(indio_dev);
485 	int ret;
486 
487 	ret = ltrf216a_disable(indio_dev);
488 	if (ret)
489 		return ret;
490 
491 	regcache_cache_only(data->regmap, true);
492 
493 	return 0;
494 }
495 
ltrf216a_runtime_resume(struct device * dev)496 static int ltrf216a_runtime_resume(struct device *dev)
497 {
498 	struct iio_dev *indio_dev = i2c_get_clientdata(to_i2c_client(dev));
499 	struct ltrf216a_data *data = iio_priv(indio_dev);
500 	int ret;
501 
502 	regcache_cache_only(data->regmap, false);
503 	regcache_mark_dirty(data->regmap);
504 	ret = regcache_sync(data->regmap);
505 	if (ret)
506 		goto cache_only;
507 
508 	ret = ltrf216a_enable(indio_dev);
509 	if (ret)
510 		goto cache_only;
511 
512 	return 0;
513 
514 cache_only:
515 	regcache_cache_only(data->regmap, true);
516 
517 	return ret;
518 }
519 
520 static DEFINE_RUNTIME_DEV_PM_OPS(ltrf216a_pm_ops, ltrf216a_runtime_suspend,
521 				 ltrf216a_runtime_resume, NULL);
522 
523 static const struct i2c_device_id ltrf216a_id[] = {
524 	{ "ltrf216a" },
525 	{}
526 };
527 MODULE_DEVICE_TABLE(i2c, ltrf216a_id);
528 
529 static const struct of_device_id ltrf216a_of_match[] = {
530 	{ .compatible = "liteon,ltrf216a" },
531 	{ .compatible = "ltr,ltrf216a" },
532 	{}
533 };
534 MODULE_DEVICE_TABLE(of, ltrf216a_of_match);
535 
536 static struct i2c_driver ltrf216a_driver = {
537 	.driver = {
538 		.name = "ltrf216a",
539 		.pm = pm_ptr(&ltrf216a_pm_ops),
540 		.of_match_table = ltrf216a_of_match,
541 	},
542 	.probe = ltrf216a_probe,
543 	.id_table = ltrf216a_id,
544 };
545 module_i2c_driver(ltrf216a_driver);
546 
547 MODULE_AUTHOR("Shreeya Patel <shreeya.patel@collabora.com>");
548 MODULE_AUTHOR("Shi Zhigang <Zhigang.Shi@liteon.com>");
549 MODULE_DESCRIPTION("LTRF216A ambient light sensor driver");
550 MODULE_LICENSE("GPL");
551