2 * Copyright (c) 2010 SAMSUNG
4 * This program is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU General Public License
6 * as published by the Free Software Foundation; either version 2
7 * of the License, or (at your option) any later version.
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
14 * You should have received a copy of the GNU General Public License
15 * along with this program; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
20 #include <linux/delay.h>
21 #include <linux/errno.h>
22 #include <linux/init.h>
23 #include <linux/input.h>
24 #include <linux/kernel.h>
25 #include <linux/module.h>
26 #include <linux/mutex.h>
27 #include <linux/types.h>
28 #include <linux/platform_device.h>
29 #include <linux/input/gp2a.h>
30 #include <linux/slab.h>
31 #include <linux/regulator/consumer.h>
36 /*********** for debug ***************************/
38 #define gprintk(fmt, x...) printk(KERN_INFO "%s(%d): " fmt\
39 , __func__ , __LINE__, ## x)
41 #define gprintk(x...) do { } while (0)
43 /***********************************************/
45 #define SENSOR_NAME "light_gp2a"
46 #define SENSOR_MAX_DELAY (2000) /* 2000 ms */
47 #define LIGHT_BUFFER_NUM 5
51 struct delayed_work work;
52 struct input_dev *input_dev;
53 struct workqueue_struct *wq;
60 /*TODO Need to change depends on the lightsensor table*/
61 static const int adc_table[4] = {
62 15, /*15 lux match adc value */
63 140, /*150 lux match adc value */
64 1490, /*1500 lux match adc value */
65 15000, /*15000 lux match adc value */
68 static bool first_value = true;
69 u8 lightsensor_mode; /* 0 = low, 1 = high */
71 static int lightsensor_get_adc(void);
72 static int lightsensor_onoff(u8 onoff);
75 light_curr_adc_show(struct device *dev, struct device_attribute *attr, char *buf)
79 adc = lightsensor_get_adcvalue();
81 return sprintf(buf, "%d\n", adc);
85 light_delay_show(struct device *dev, struct device_attribute *attr, char *buf)
87 struct input_dev *input_data = to_input_dev(dev);
88 struct sensor_data *data = input_get_drvdata(input_data);
90 return sprintf(buf, "%d\n", data->delay);
94 light_delay_store(struct device *dev, struct device_attribute *attr,
95 const char *buf, size_t count)
97 struct input_dev *input_data = to_input_dev(dev);
98 struct sensor_data *data = input_get_drvdata(input_data);
103 ret = strict_strtol(buf, 10, &tempv);
105 if ((ret != 0) || (tempv <= 0))
108 delay = tempv/1000000; /* ns to msec */
110 pr_info("%s, new_delay = %d(ms), old_delay = %d(ms)",
111 __func__, delay, data->delay);
113 if (SENSOR_MAX_DELAY < delay)
114 delay = SENSOR_MAX_DELAY;
118 mutex_lock(&data->mutex);
121 cancel_delayed_work_sync(&data->work);
122 queue_delayed_work(data->wq, &data->work,
123 msecs_to_jiffies(delay));
126 mutex_unlock(&data->mutex);
132 light_enable_show(struct device *dev, struct device_attribute *attr, char *buf)
134 struct input_dev *input_data = to_input_dev(dev);
135 struct sensor_data *data = input_get_drvdata(input_data);
138 enabled = data->enabled;
140 return sprintf(buf, "%d\n", enabled);
144 light_enable_store(struct device *dev, struct device_attribute *attr,
145 const char *buf, size_t count)
147 struct input_dev *input_data = to_input_dev(dev);
148 struct sensor_data *data = input_get_drvdata(input_data);
152 ret = strict_strtol(buf, 10, &value);
154 if ((ret != 0) || (value != 0 && value != 1))
157 mutex_lock(&data->mutex);
159 if (data->enabled && !value) {
160 cancel_delayed_work_sync(&data->work);
161 gprintk("timer canceled.\n");
162 lightsensor_onoff(0);
163 data->enabled = value;
165 if (!data->enabled && value) {
166 lightsensor_onoff(1);
167 data->enabled = value;
169 queue_delayed_work(data->wq, &data->work, 0);
170 gprintk("timer started.\n");
173 mutex_unlock(&data->mutex);
178 static DEVICE_ATTR(poll_delay, S_IRUGO | S_IWUSR, light_delay_show, light_delay_store);
179 static DEVICE_ATTR(enable, S_IRUGO | S_IWUSR, light_enable_show, light_enable_store);
180 static DEVICE_ATTR(curr_adc, S_IRUGO, light_curr_adc_show, NULL);
182 static struct attribute *lightsensor_attributes[] = {
183 &dev_attr_poll_delay.attr,
184 &dev_attr_enable.attr,
185 &dev_attr_curr_adc.attr,
189 static struct attribute_group lightsensor_attribute_group = {
190 .attrs = lightsensor_attributes
193 int lightsensor_get_adc(void)
195 unsigned char get_data[4] = { 0, };
206 int d0_boundary = 93;
208 ret = opt_i2c_read(DATA0_LSB, get_data, sizeof(get_data));
211 D0_raw_data = (get_data[1] << 8) | get_data[0]; /* clear */
212 D1_raw_data = (get_data[3] << 8) | get_data[2]; /* IR */
214 if (lightsensor_mode) { /* HIGH_MODE */
215 if (100 * D1_raw_data <= 32 * D0_raw_data) {
218 } else if (100 * D1_raw_data <= 67 * D0_raw_data) {
221 } else if (100 * D1_raw_data <= d0_boundary * D0_raw_data) {
228 } else { /* LOW_MODE */
229 if (100 * D1_raw_data <= 32 * D0_raw_data) {
232 } else if (100 * D1_raw_data <= 67 * D0_raw_data) {
235 } else if (100 * D1_raw_data <= d0_boundary * D0_raw_data) {
244 if (lightsensor_mode) { /* HIGH_MODE */
245 D0_data = D0_raw_data * 16;
246 D1_data = D1_raw_data * 16;
247 } else { /* LOW_MODE */
248 D0_data = D0_raw_data;
249 D1_data = D1_raw_data;
252 if ((D0_data == 0 || D1_data == 0)\
253 && (D0_data < 300 && D1_data < 300)) {
256 gprintk("lx is 0 : D0=%d, D1=%d\n", D0_raw_data, D1_raw_data);
258 } else if (lightsensor_mode == 0
259 && (D0_raw_data >= 16000 || D1_raw_data >= 16000)
260 && (D0_raw_data <= 16383 && D1_raw_data <= 16383)) {
262 gprintk("need to changed HIGH_MODE D0=%d, D1=%d\n",
263 D0_raw_data, D1_raw_data);
266 } else if ((100 * D1_data > d0_boundary * D0_data)
267 || (100 * D1_data < 15 * D0_data)) {
270 gprintk("Data range over so ues prev_lx value=%d D0=%d, D1=%d mode=%d\n",\
271 lx, D0_data, D1_data, lightsensor_mode);
275 lx = (int)((light_alpha / 10 * D0_data * 33)
276 - (light_beta / 10 * D1_data * 33)) / 1000;
278 gprintk("D0=%d, D1=%d, lx=%d mode=%d a=%d, b=%d prev_lx=%d\n",
279 D0_raw_data, D1_raw_data, lx, lightsensor_mode,
280 light_alpha, light_beta, lx_prev);
286 if (lightsensor_mode) { /* HIGH MODE */
287 if (D0_raw_data < 1000) {
289 "%s: change to LOW_MODE detection=%d\n",
290 __func__, proximity_sensor_detection);
291 lightsensor_mode = 0; /* change to LOW MODE */
294 opt_i2c_write(COMMAND1, &value);
296 if (proximity_sensor_detection)
300 opt_i2c_write(COMMAND2, &value);
302 if (proximity_enable)
306 opt_i2c_write(COMMAND1, &value);
308 } else { /* LOW MODE*/
309 if (D0_raw_data > 16000 || D1_raw_data > 16000) {
310 printk(KERN_INFO "%s: change to HIGH_MODE detection=%d\n",
311 __func__, proximity_sensor_detection);
312 lightsensor_mode = 1; /* change to HIGH MODE */
315 opt_i2c_write(COMMAND1, &value);
317 if (proximity_sensor_detection)
321 opt_i2c_write(COMMAND2, &value);
323 if (proximity_enable)
327 opt_i2c_write(COMMAND1, &value);
334 int lightsensor_get_adcvalue(void)
336 int i, j, value, adc_avr_value;
337 unsigned int adc_total = 0, adc_max, adc_min, adc_index;
338 static unsigned int adc_index_count;
339 static int adc_value_buf[ADC_BUFFER_NUM] = { 0, };
341 value = lightsensor_get_adc();
343 adc_index = (adc_index_count++) % ADC_BUFFER_NUM;
345 /*ADC buffer initialize (light sensor off ---> light sensor on) */
346 if (first_value == true) {
347 for (j = 0; j < ADC_BUFFER_NUM; j++)
348 adc_value_buf[j] = value;
351 adc_value_buf[adc_index] = value;
354 adc_max = adc_value_buf[0];
355 adc_min = adc_value_buf[0];
357 for (i = 0; i < ADC_BUFFER_NUM; i++) {
358 adc_total += adc_value_buf[i];
360 if (adc_max < adc_value_buf[i])
361 adc_max = adc_value_buf[i];
363 if (adc_min > adc_value_buf[i])
364 adc_min = adc_value_buf[i];
367 (adc_total - (adc_max + adc_min)) / (ADC_BUFFER_NUM - 2);
369 if (adc_index_count == ADC_BUFFER_NUM - 1)
372 return adc_avr_value;
375 static int lightsensor_onoff(u8 onoff)
380 printk(KERN_INFO "%s : light_sensor onoff = %d\n", __func__, onoff);
381 printk(KERN_INFO "%s : proximity_enable onoff = %d\n", __func__,
386 /*in calling, must turn on proximity sensor */
387 if (proximity_enable == 0) {
389 opt_i2c_write(COMMAND4, &value);
392 opt_i2c_write(COMMAND2, &value);
393 /*OP3 : 1(operating mode) OP2 :1
394 (coutinuous operating mode)
395 OP1 : 01(ALS mode) TYPE=0(auto) */
397 opt_i2c_write(COMMAND1, &value);
398 /* other setting have defualt value. */
401 /*in calling, must turn on proximity sensor */
402 if (proximity_enable == 0) {
403 value = 0x00; /*shutdown mode */
404 opt_i2c_write((u8) (COMMAND1), &value);
411 static void gp2a_work_func_light(struct work_struct *work)
413 struct sensor_data *data = container_of((struct delayed_work *)work,
414 struct sensor_data, work);
418 adc = lightsensor_get_adcvalue();
420 for (i = 0; ARRAY_SIZE(adc_table); i++)
421 if (adc <= adc_table[i])
424 if (data->light_buffer == i) {
425 if (data->light_count++ == LIGHT_BUFFER_NUM) {
426 input_report_rel(data->input_dev, REL_MISC, adc);
427 input_sync(data->input_dev);
428 data->light_count = 0;
431 data->light_buffer = i;
432 data->light_count = 0;
436 queue_delayed_work(data->wq, &data->work,
437 msecs_to_jiffies(data->delay));
440 static int lightsensor_probe(struct platform_device *pdev)
442 struct sensor_data *data = NULL;
444 unsigned char get_data = 0;
446 /* Check I2C communication */
447 rt = opt_i2c_read(DATA0_LSB, &get_data, sizeof(get_data));
450 pr_err("%s failed : threre is no such device.\n", __func__);
454 pr_info("%s : probe start!\n", __func__);
456 data = kzalloc(sizeof(struct sensor_data), GFP_KERNEL);
458 pr_err("%s failed to alloc memory.\n", __func__);
461 data->delay = SENSOR_MAX_DELAY;
463 data->input_dev = input_allocate_device();
464 if (!data->input_dev) {
465 pr_err("%s: could not allocate input device\n", __func__);
467 goto err_input_allocate_device_light;
470 input_set_capability(data->input_dev, EV_REL, REL_MISC);
471 data->input_dev->name = SENSOR_NAME;
473 rt = input_register_device(data->input_dev);
475 pr_err("%s: could not register input device\n", __func__);
476 input_free_device(data->input_dev);
477 goto err_input_allocate_device_light;
479 input_set_drvdata(data->input_dev, data);
481 rt = sysfs_create_group(&data->input_dev->dev.kobj,
482 &lightsensor_attribute_group);
484 pr_err("%s: could not create sysfs group\n", __func__);
485 goto err_sysfs_create_group_light;
487 mutex_init(&data->mutex);
489 data->wq = create_singlethread_workqueue("gp2a_wq");
492 pr_err("%s: could not create workqueue\n", __func__);
493 goto err_create_workqueue;
496 /* this is the thread function we run on the work queue */
497 INIT_DELAYED_WORK(&data->work, gp2a_work_func_light);
500 platform_set_drvdata(pdev, data);
502 pr_info("%s : probe success!\n", __func__);
506 /* error, unwind it all */
507 err_create_workqueue:
508 mutex_destroy(&data->mutex);
509 sysfs_remove_group(&data->input_dev->dev.kobj,
510 &lightsensor_attribute_group);
511 err_sysfs_create_group_light:
512 input_unregister_device(data->input_dev);
513 err_input_allocate_device_light:
519 static int lightsensor_remove(struct platform_device *pdev)
521 struct sensor_data *data = platform_get_drvdata(pdev);
524 sysfs_remove_group(&data->input_dev->dev.kobj,
525 &lightsensor_attribute_group);
526 cancel_delayed_work_sync(&data->work);
527 flush_workqueue(data->wq);
528 destroy_workqueue(data->wq);
529 input_unregister_device(data->input_dev);
530 mutex_destroy(&data->mutex);
537 static void lightsensor_shutdown(struct platform_device *pdev)
539 struct sensor_data *data = platform_get_drvdata(pdev);
542 sysfs_remove_group(&data->input_dev->dev.kobj,
543 &lightsensor_attribute_group);
544 cancel_delayed_work_sync(&data->work);
545 flush_workqueue(data->wq);
546 destroy_workqueue(data->wq);
547 input_unregister_device(data->input_dev);
554 static int lightsensor_suspend(struct device *dev)
556 struct platform_device *pdev = to_platform_device(dev);
557 struct sensor_data *data = platform_get_drvdata(pdev);
561 mutex_lock(&data->mutex);
564 rt = cancel_delayed_work_sync(&data->work);
565 gprintk(": The timer is cancled.\n");
568 mutex_unlock(&data->mutex);
573 static int lightsensor_resume(struct device *dev)
575 struct platform_device *pdev = to_platform_device(dev);
576 struct sensor_data *data = platform_get_drvdata(pdev);
579 data->light_count = 0;
580 data->light_buffer = 0;
583 mutex_lock(&data->mutex);
586 rt = queue_delayed_work(data->wq, &data->work, 0);
587 gprintk(": The timer is started.\n");
590 mutex_unlock(&data->mutex);
595 static int lightsensor_freeze(struct device *dev)
597 struct platform_device *pdev = to_platform_device(dev);
598 struct sensor_data *data = platform_get_drvdata(pdev);
602 cancel_delayed_work_sync(&data->work);
603 gprintk("timer canceled.\n");
604 rt = lightsensor_onoff(0);
610 static int lightsensor_restore(struct device *dev)
612 struct platform_device *pdev = to_platform_device(dev);
613 struct sensor_data *data = platform_get_drvdata(pdev);
617 lightsensor_onoff(1);
618 rt = queue_delayed_work(data->wq, &data->work, 0);
619 gprintk("timer started.\n");
625 static struct dev_pm_ops lightsensor_dev_pm_ops = {
626 .suspend = lightsensor_suspend,
627 .resume = lightsensor_resume,
628 .freeze = lightsensor_freeze,
629 .restore = lightsensor_restore,
632 #define LIGHTSENSOR_DEV_PM_OPS (&lightsensor_dev_pm_ops)
634 #define LIGHTSENSOR_DEV_PM_OPS NULL
635 #endif /* CONFIG_PM */
638 * Module init and exit
640 static struct platform_driver lightsensor_driver = {
641 .probe = lightsensor_probe,
642 .remove = lightsensor_remove,
643 .shutdown = lightsensor_shutdown,
646 .owner = THIS_MODULE,
647 .pm = LIGHTSENSOR_DEV_PM_OPS,
651 /* TODO Need to check if we need this or not.*/
653 #ifdef CONFIG_BATTERY_SEC
654 extern unsigned int is_lpcharging_state(void);
658 static int __init lightsensor_init(void)
661 #ifdef CONFIG_BATTERY_SEC
662 if (is_lpcharging_state()) {
663 pr_info("%s : LPM Charging Mode! return 0\n", __func__);
669 return platform_driver_register(&lightsensor_driver);
672 module_init(lightsensor_init);
674 static void __exit lightsensor_exit(void)
676 platform_driver_unregister(&lightsensor_driver);
679 module_exit(lightsensor_exit);
681 MODULE_AUTHOR("SAMSUNG");
682 MODULE_DESCRIPTION("Optical Sensor driver for GP2AP020A00F");
683 MODULE_LICENSE("GPL");