1 // SPDX-License-Identifier: GPL-2.0-only
3 * JSA1212 Ambient Light & Proximity Sensor Driver
5 * Copyright (c) 2014, Intel Corporation.
7 * JSA1212 I2C slave address: 0x44(ADDR tied to GND), 0x45(ADDR tied to VDD)
9 * TODO: Interrupt support, thresholds, range support.
12 #include <linux/kernel.h>
13 #include <linux/slab.h>
14 #include <linux/module.h>
15 #include <linux/delay.h>
16 #include <linux/i2c.h>
17 #include <linux/mutex.h>
18 #include <linux/acpi.h>
19 #include <linux/regmap.h>
20 #include <linux/iio/iio.h>
21 #include <linux/iio/sysfs.h>
23 /* JSA1212 reg address */
24 #define JSA1212_CONF_REG 0x01
25 #define JSA1212_INT_REG 0x02
26 #define JSA1212_PXS_LT_REG 0x03
27 #define JSA1212_PXS_HT_REG 0x04
28 #define JSA1212_ALS_TH1_REG 0x05
29 #define JSA1212_ALS_TH2_REG 0x06
30 #define JSA1212_ALS_TH3_REG 0x07
31 #define JSA1212_PXS_DATA_REG 0x08
32 #define JSA1212_ALS_DT1_REG 0x09
33 #define JSA1212_ALS_DT2_REG 0x0A
34 #define JSA1212_ALS_RNG_REG 0x0B
35 #define JSA1212_MAX_REG 0x0C
37 /* JSA1212 reg masks */
38 #define JSA1212_CONF_MASK 0xFF
39 #define JSA1212_INT_MASK 0xFF
40 #define JSA1212_PXS_LT_MASK 0xFF
41 #define JSA1212_PXS_HT_MASK 0xFF
42 #define JSA1212_ALS_TH1_MASK 0xFF
43 #define JSA1212_ALS_TH2_LT_MASK 0x0F
44 #define JSA1212_ALS_TH2_HT_MASK 0xF0
45 #define JSA1212_ALS_TH3_MASK 0xFF
46 #define JSA1212_PXS_DATA_MASK 0xFF
47 #define JSA1212_ALS_DATA_MASK 0x0FFF
48 #define JSA1212_ALS_DT1_MASK 0xFF
49 #define JSA1212_ALS_DT2_MASK 0x0F
50 #define JSA1212_ALS_RNG_MASK 0x07
52 /* JSA1212 CONF REG bits */
53 #define JSA1212_CONF_PXS_MASK 0x80
54 #define JSA1212_CONF_PXS_ENABLE 0x80
55 #define JSA1212_CONF_PXS_DISABLE 0x00
56 #define JSA1212_CONF_ALS_MASK 0x04
57 #define JSA1212_CONF_ALS_ENABLE 0x04
58 #define JSA1212_CONF_ALS_DISABLE 0x00
59 #define JSA1212_CONF_IRDR_MASK 0x08
60 /* Proxmity sensing IRDR current sink settings */
61 #define JSA1212_CONF_IRDR_200MA 0x08
62 #define JSA1212_CONF_IRDR_100MA 0x00
63 #define JSA1212_CONF_PXS_SLP_MASK 0x70
64 #define JSA1212_CONF_PXS_SLP_0MS 0x70
65 #define JSA1212_CONF_PXS_SLP_12MS 0x60
66 #define JSA1212_CONF_PXS_SLP_50MS 0x50
67 #define JSA1212_CONF_PXS_SLP_75MS 0x40
68 #define JSA1212_CONF_PXS_SLP_100MS 0x30
69 #define JSA1212_CONF_PXS_SLP_200MS 0x20
70 #define JSA1212_CONF_PXS_SLP_400MS 0x10
71 #define JSA1212_CONF_PXS_SLP_800MS 0x00
73 /* JSA1212 INT REG bits */
74 #define JSA1212_INT_CTRL_MASK 0x01
75 #define JSA1212_INT_CTRL_EITHER 0x00
76 #define JSA1212_INT_CTRL_BOTH 0x01
77 #define JSA1212_INT_ALS_PRST_MASK 0x06
78 #define JSA1212_INT_ALS_PRST_1CONV 0x00
79 #define JSA1212_INT_ALS_PRST_4CONV 0x02
80 #define JSA1212_INT_ALS_PRST_8CONV 0x04
81 #define JSA1212_INT_ALS_PRST_16CONV 0x06
82 #define JSA1212_INT_ALS_FLAG_MASK 0x08
83 #define JSA1212_INT_ALS_FLAG_CLR 0x00
84 #define JSA1212_INT_PXS_PRST_MASK 0x60
85 #define JSA1212_INT_PXS_PRST_1CONV 0x00
86 #define JSA1212_INT_PXS_PRST_4CONV 0x20
87 #define JSA1212_INT_PXS_PRST_8CONV 0x40
88 #define JSA1212_INT_PXS_PRST_16CONV 0x60
89 #define JSA1212_INT_PXS_FLAG_MASK 0x80
90 #define JSA1212_INT_PXS_FLAG_CLR 0x00
92 /* JSA1212 ALS RNG REG bits */
93 #define JSA1212_ALS_RNG_0_2048 0x00
94 #define JSA1212_ALS_RNG_0_1024 0x01
95 #define JSA1212_ALS_RNG_0_512 0x02
96 #define JSA1212_ALS_RNG_0_256 0x03
97 #define JSA1212_ALS_RNG_0_128 0x04
99 /* JSA1212 INT threshold range */
100 #define JSA1212_ALS_TH_MIN 0x0000
101 #define JSA1212_ALS_TH_MAX 0x0FFF
102 #define JSA1212_PXS_TH_MIN 0x00
103 #define JSA1212_PXS_TH_MAX 0xFF
105 #define JSA1212_ALS_DELAY_MS 200
106 #define JSA1212_PXS_DELAY_MS 100
108 #define JSA1212_DRIVER_NAME "jsa1212"
109 #define JSA1212_REGMAP_NAME "jsa1212_regmap"
111 enum jsa1212_op_mode
{
112 JSA1212_OPMODE_ALS_EN
,
113 JSA1212_OPMODE_PXS_EN
,
116 struct jsa1212_data
{
117 struct i2c_client
*client
;
120 bool als_en
; /* ALS enable status */
121 bool pxs_en
; /* proximity enable status */
122 struct regmap
*regmap
;
125 /* ALS range idx to val mapping */
126 static const int jsa1212_als_range_val
[] = {2048, 1024, 512, 256, 128,
129 /* Enables or disables ALS function based on status */
130 static int jsa1212_als_enable(struct jsa1212_data
*data
, u8 status
)
134 ret
= regmap_update_bits(data
->regmap
, JSA1212_CONF_REG
,
135 JSA1212_CONF_ALS_MASK
,
140 data
->als_en
= !!status
;
145 /* Enables or disables PXS function based on status */
146 static int jsa1212_pxs_enable(struct jsa1212_data
*data
, u8 status
)
150 ret
= regmap_update_bits(data
->regmap
, JSA1212_CONF_REG
,
151 JSA1212_CONF_PXS_MASK
,
156 data
->pxs_en
= !!status
;
161 static int jsa1212_read_als_data(struct jsa1212_data
*data
,
167 ret
= jsa1212_als_enable(data
, JSA1212_CONF_ALS_ENABLE
);
171 /* Delay for data output */
172 msleep(JSA1212_ALS_DELAY_MS
);
174 /* Read 12 bit data */
175 ret
= regmap_bulk_read(data
->regmap
, JSA1212_ALS_DT1_REG
, &als_data
, 2);
177 dev_err(&data
->client
->dev
, "als data read err\n");
178 goto als_data_read_err
;
181 *val
= le16_to_cpu(als_data
);
184 return jsa1212_als_enable(data
, JSA1212_CONF_ALS_DISABLE
);
187 static int jsa1212_read_pxs_data(struct jsa1212_data
*data
,
191 unsigned int pxs_data
;
193 ret
= jsa1212_pxs_enable(data
, JSA1212_CONF_PXS_ENABLE
);
197 /* Delay for data output */
198 msleep(JSA1212_PXS_DELAY_MS
);
200 /* Read out all data */
201 ret
= regmap_read(data
->regmap
, JSA1212_PXS_DATA_REG
, &pxs_data
);
203 dev_err(&data
->client
->dev
, "pxs data read err\n");
204 goto pxs_data_read_err
;
207 *val
= pxs_data
& JSA1212_PXS_DATA_MASK
;
210 return jsa1212_pxs_enable(data
, JSA1212_CONF_PXS_DISABLE
);
213 static int jsa1212_read_raw(struct iio_dev
*indio_dev
,
214 struct iio_chan_spec
const *chan
,
215 int *val
, int *val2
, long mask
)
218 struct jsa1212_data
*data
= iio_priv(indio_dev
);
221 case IIO_CHAN_INFO_RAW
:
222 mutex_lock(&data
->lock
);
223 switch (chan
->type
) {
225 ret
= jsa1212_read_als_data(data
, val
);
228 ret
= jsa1212_read_pxs_data(data
, val
);
234 mutex_unlock(&data
->lock
);
235 return ret
< 0 ? ret
: IIO_VAL_INT
;
236 case IIO_CHAN_INFO_SCALE
:
237 switch (chan
->type
) {
239 *val
= jsa1212_als_range_val
[data
->als_rng_idx
];
240 *val2
= BIT(12); /* Max 12 bit value */
241 return IIO_VAL_FRACTIONAL
;
253 static const struct iio_chan_spec jsa1212_channels
[] = {
256 .info_mask_separate
= BIT(IIO_CHAN_INFO_RAW
) |
257 BIT(IIO_CHAN_INFO_SCALE
),
260 .type
= IIO_PROXIMITY
,
261 .info_mask_separate
= BIT(IIO_CHAN_INFO_RAW
),
265 static const struct iio_info jsa1212_info
= {
266 .read_raw
= &jsa1212_read_raw
,
269 static int jsa1212_chip_init(struct jsa1212_data
*data
)
273 ret
= regmap_write(data
->regmap
, JSA1212_CONF_REG
,
274 (JSA1212_CONF_PXS_SLP_50MS
|
275 JSA1212_CONF_IRDR_200MA
));
279 ret
= regmap_write(data
->regmap
, JSA1212_INT_REG
,
280 JSA1212_INT_ALS_PRST_4CONV
);
284 data
->als_rng_idx
= JSA1212_ALS_RNG_0_2048
;
289 static bool jsa1212_is_volatile_reg(struct device
*dev
, unsigned int reg
)
292 case JSA1212_PXS_DATA_REG
:
293 case JSA1212_ALS_DT1_REG
:
294 case JSA1212_ALS_DT2_REG
:
295 case JSA1212_INT_REG
:
302 static const struct regmap_config jsa1212_regmap_config
= {
303 .name
= JSA1212_REGMAP_NAME
,
306 .max_register
= JSA1212_MAX_REG
,
307 .cache_type
= REGCACHE_RBTREE
,
308 .volatile_reg
= jsa1212_is_volatile_reg
,
311 static int jsa1212_probe(struct i2c_client
*client
,
312 const struct i2c_device_id
*id
)
314 struct jsa1212_data
*data
;
315 struct iio_dev
*indio_dev
;
316 struct regmap
*regmap
;
319 indio_dev
= devm_iio_device_alloc(&client
->dev
, sizeof(*data
));
323 regmap
= devm_regmap_init_i2c(client
, &jsa1212_regmap_config
);
324 if (IS_ERR(regmap
)) {
325 dev_err(&client
->dev
, "Regmap initialization failed.\n");
326 return PTR_ERR(regmap
);
329 data
= iio_priv(indio_dev
);
331 i2c_set_clientdata(client
, indio_dev
);
332 data
->client
= client
;
333 data
->regmap
= regmap
;
335 mutex_init(&data
->lock
);
337 ret
= jsa1212_chip_init(data
);
341 indio_dev
->channels
= jsa1212_channels
;
342 indio_dev
->num_channels
= ARRAY_SIZE(jsa1212_channels
);
343 indio_dev
->name
= JSA1212_DRIVER_NAME
;
344 indio_dev
->modes
= INDIO_DIRECT_MODE
;
346 indio_dev
->info
= &jsa1212_info
;
348 ret
= iio_device_register(indio_dev
);
350 dev_err(&client
->dev
, "%s: register device failed\n", __func__
);
355 /* power off the device */
356 static int jsa1212_power_off(struct jsa1212_data
*data
)
360 mutex_lock(&data
->lock
);
362 ret
= regmap_update_bits(data
->regmap
, JSA1212_CONF_REG
,
363 JSA1212_CONF_ALS_MASK
|
364 JSA1212_CONF_PXS_MASK
,
365 JSA1212_CONF_ALS_DISABLE
|
366 JSA1212_CONF_PXS_DISABLE
);
369 dev_err(&data
->client
->dev
, "power off cmd failed\n");
371 mutex_unlock(&data
->lock
);
376 static int jsa1212_remove(struct i2c_client
*client
)
378 struct iio_dev
*indio_dev
= i2c_get_clientdata(client
);
379 struct jsa1212_data
*data
= iio_priv(indio_dev
);
381 iio_device_unregister(indio_dev
);
383 return jsa1212_power_off(data
);
386 #ifdef CONFIG_PM_SLEEP
387 static int jsa1212_suspend(struct device
*dev
)
389 struct jsa1212_data
*data
;
391 data
= iio_priv(i2c_get_clientdata(to_i2c_client(dev
)));
393 return jsa1212_power_off(data
);
396 static int jsa1212_resume(struct device
*dev
)
399 struct jsa1212_data
*data
;
401 data
= iio_priv(i2c_get_clientdata(to_i2c_client(dev
)));
403 mutex_lock(&data
->lock
);
406 ret
= jsa1212_als_enable(data
, JSA1212_CONF_ALS_ENABLE
);
408 dev_err(dev
, "als resume failed\n");
414 ret
= jsa1212_pxs_enable(data
, JSA1212_CONF_PXS_ENABLE
);
416 dev_err(dev
, "pxs resume failed\n");
420 mutex_unlock(&data
->lock
);
424 static SIMPLE_DEV_PM_OPS(jsa1212_pm_ops
, jsa1212_suspend
, jsa1212_resume
);
426 #define JSA1212_PM_OPS (&jsa1212_pm_ops)
428 #define JSA1212_PM_OPS NULL
431 static const struct acpi_device_id jsa1212_acpi_match
[] = {
435 MODULE_DEVICE_TABLE(acpi
, jsa1212_acpi_match
);
437 static const struct i2c_device_id jsa1212_id
[] = {
438 { JSA1212_DRIVER_NAME
, 0 },
441 MODULE_DEVICE_TABLE(i2c
, jsa1212_id
);
443 static struct i2c_driver jsa1212_driver
= {
445 .name
= JSA1212_DRIVER_NAME
,
446 .pm
= JSA1212_PM_OPS
,
447 .acpi_match_table
= ACPI_PTR(jsa1212_acpi_match
),
449 .probe
= jsa1212_probe
,
450 .remove
= jsa1212_remove
,
451 .id_table
= jsa1212_id
,
453 module_i2c_driver(jsa1212_driver
);
455 MODULE_AUTHOR("Sathya Kuppuswamy <sathyanarayanan.kuppuswamy@linux.intel.com>");
456 MODULE_DESCRIPTION("JSA1212 proximity/ambient light sensor driver");
457 MODULE_LICENSE("GPL v2");