blob: e7a2a2229ed21f7113e0420c42ac9d03ae771f97 [file] [log] [blame]
Jongrak Kwonae680ab2012-06-15 22:06:54 -07001/* Touch_synaptics.c
2 *
3 * Copyright (C) 2011 LGE.
4 *
5 * Author: yehan.ahn@lge.com, hyesung.shin@lge.com
6 *
7 * This software is licensed under the terms of the GNU General Public
8 * License version 2, as published by the Free Software Foundation, and
9 * may be copied, distributed, and modified under those terms.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 */
17
18#include <linux/err.h>
19#include <linux/module.h>
20#include <linux/delay.h>
21#include <linux/i2c.h>
22#include <linux/slab.h>
23
24#include <linux/gpio.h>
25
26#include <linux/earlysuspend.h>
Jongrak Kwonb5e69d82012-06-29 18:03:36 -070027#include <linux/input/mt.h>
Jongrak Kwonae680ab2012-06-15 22:06:54 -070028#include <linux/input/lge_touch_core.h>
29#include <linux/input/touch_synaptics.h>
30
Jongrak Kwonae680ab2012-06-15 22:06:54 -070031#include "SynaImage.h"
Jongrak Kwonae680ab2012-06-15 22:06:54 -070032#include <linux/regulator/machine.h>
33
34/* RMI4 spec from (RMI4 spec)511-000136-01_revD
35 * Function Purpose See page
36 * $01 RMI Device Control 29
37 * $08 BIST(Built-in Self Test) 38
38 * $09 BIST(Built-in Self Test) 42
39 * $11 2-D TouchPad sensors 46
40 * $19 0-D capacitive button sensors 69
41 * $30 GPIO/LEDs (includes mechanical buttons) 76
42 * $32 Timer 89
43 * $34 Flash Memory Management 93
44 */
45#define RMI_DEVICE_CONTROL 0x01
46#define TOUCHPAD_SENSORS 0x11
47#if defined(CONFIG_TOUCH_REG_MAP_TM2000) || defined(CONFIG_TOUCH_REG_MAP_TM2372)
48#define CAPACITIVE_BUTTON_SENSORS 0x1A
49#define GPIO_LEDS 0x31
50#define ANALOG_CONTROL 0x54
51#else
52#define CAPACITIVE_BUTTON_SENSORS 0x19
53#define GPIO_LEDS 0x30
54#endif
55#define TIMER 0x32
56#define FLASH_MEMORY_MANAGEMENT 0x34
57
58/* Register Map & Register bit mask
59 * - Please check "One time" this map before using this device driver
60 */
61
62#define MANUFACTURER_ID_REG (ts->common_dsc.query_base) /* Manufacturer ID */
63#define FW_REVISION_REG (ts->common_dsc.query_base+3) /* FW revision */
64#define PRODUCT_ID_REG (ts->common_dsc.query_base+11) /* Product ID */
65#if defined(CONFIG_TOUCH_REG_MAP_TM2000) || defined(CONFIG_TOUCH_REG_MAP_TM2372)
66#define FW_VERSION (ts->flash_dsc.control_base)
67#endif
68
69#define DEVICE_CONTROL_REG (ts->common_dsc.control_base) /* Device Control */
70#define DEVICE_CONTROL_NORMAL_OP 0x00 /* sleep mode : go to doze mode after 500 ms */
ks.kwon22c5f0b2012-08-07 13:50:18 +090071#define DEVICE_CONTROL_SLEEP 0x01 /* sleep mode : go to sleep */
Jongrak Kwonae680ab2012-06-15 22:06:54 -070072#define DEVICE_CONTROL_SPECIFIC 0x02 /* sleep mode : go to doze mode after 5 sec */
73#define DEVICE_CONTROL_NOSLEEP 0x04
74#define DEVICE_CONTROL_CONFIGURED 0x80
75
76#define INTERRUPT_ENABLE_REG (ts->common_dsc.control_base+1) /* Interrupt Enable 0 */
77
78#define DEVICE_STATUS_REG (ts->common_dsc.data_base) /* Device Status */
79#define DEVICE_FAILURE_MASK 0x03
80#define DEVICE_CRC_ERROR_MASK 0x04
81#define DEVICE_STATUS_FLASH_PROG 0x40
82#define DEVICE_STATUS_UNCONFIGURED 0x80
83
84#define INTERRUPT_STATUS_REG (ts->common_dsc.data_base+1) /* Interrupt Status */
85#define BUTTON_DATA_REG (ts->button_dsc.data_base) /* Button Data */
86#define MAX_NUM_OF_BUTTON 4
87
88#define FINGER_STATE_REG (ts->finger_dsc.data_base) /* Finger State */
89#define FINGER_DATA_REG_START (ts->finger_dsc.data_base+3) /* Finger Data Register */
90#define FINGER_STATE_MASK 0x03
91#define REG_X_POSITION 0
92#define REG_Y_POSITION 1
93#define REG_YX_POSITION 2
94#define REG_WY_WX 3
95#define REG_Z 4
96
97#define TWO_D_REPORTING_MODE (ts->finger_dsc.control_base+0) /* 2D Reporting Mode */
98#define REPORT_MODE_CONTINUOUS 0x00
99#define REPORT_MODE_REDUCED 0x01
100#define ABS_FILTER 0x08
101#define PALM_DETECT_REG (ts->finger_dsc.control_base+1) /* Palm Detect */
Jongrak Kwon9ed2a932012-06-19 23:38:02 -0700102#define DELTA_X_THRESH_REG (ts->finger_dsc.control_base+2) /* Delta-X Thresh */
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700103#define DELTA_Y_THRESH_REG (ts->finger_dsc.control_base+3) /* Delta-Y Thresh */
104#define SENSOR_MAX_X_POS (ts->finger_dsc.control_base+6) /* SensorMaxXPos */
105#define SENSOR_MAX_Y_POS (ts->finger_dsc.control_base+8) /* SensorMaxYPos */
106#if defined(CONFIG_TOUCH_REG_MAP_TM2000) || defined(CONFIG_TOUCH_REG_MAP_TM2372)
107/*do nothing*/
108#else
109#define GESTURE_ENABLE_1_REG (ts->finger_dsc.control_base+10) /* Gesture Enables 1 */
110#define GESTURE_ENABLE_2_REG (ts->finger_dsc.control_base+11) /* Gesture Enables 2 */
111#endif
112
113#if defined(CONFIG_TOUCH_REG_MAP_TM2000) || defined(CONFIG_TOUCH_REG_MAP_TM2372)
114#define PAGE_SELECT_REG 0xFF /* Button exists Page 02 */
115#define ANALOG_CONTROL_REG (ts->analog_dsc.control_base)
116#define ANALOG_COMMAND_REG (ts->analog_dsc.command_base)
117#define FAST_RELAXATION_RATE (ts->analog_dsc.control_base+16)
118#define FORCE_FAST_RELAXATION 0x04
119#define FORCE_UPDATE 0x04
120#else
121#define MELT_CONTROL_REG 0xF0
122#define MELT_CONTROL_NO_MELT 0x00
123#define MELT_CONTROL_MELT 0x01
124#define MELT_CONTROL_NUKE_MELT 0x80
125#endif
126
127#define DEVICE_COMMAND_REG (ts->common_dsc.command_base)
128#define FINGER_COMMAND_REG (ts->finger_dsc.command_base)
129#define BUTTON_COMMAND_REG (ts->button_dsc.command_base)
130
131#define FLASH_CONTROL_REG (ts->flash_dsc.data_base+18) /* Flash Control */
132#define FLASH_STATUS_MASK 0xF0
Jongrak Kwon8c0f1692012-07-16 19:01:35 -0700133#define FW_OFFSET_PRODUCT_ID 0x40
134#define FW_OFFSET_IMAGE_VERSION 0xB100
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700135
136/* Get user-finger-data from register.
137 */
138#define TS_SNTS_GET_X_POSITION(_high_reg, _low_reg) \
139 (((u16)(((_high_reg) << 4) & 0x0FF0) | (u16)((_low_reg) & 0x0F)))
140#define TS_SNTS_GET_Y_POSITION(_high_reg, _low_reg) \
141 (((u16)(((_high_reg) << 4) & 0x0FF0) | (u16)(((_low_reg) >> 4) & 0x0F)))
142#define TS_SNTS_GET_WIDTH_MAJOR(_width) \
143 ((((((_width) & 0xF0) >> 4) - ((_width) & 0x0F)) > 0) ? \
144 ((_width) & 0xF0) >> 4 : (_width) & 0x0F)
145#define TS_SNTS_GET_WIDTH_MINOR(_width) \
146 ((((((_width) & 0xF0) >> 4) - ((_width) & 0x0F)) > 0) ? \
147 (_width) & 0x0F : ((_width) & 0xF0) >> 4)
148#define TS_SNTS_GET_ORIENTATION(_width) \
Jongrak Kwonef6ce3c2012-08-28 00:01:59 -0700149 ((((((_width) & 0xF0) >> 4) - ((_width) & 0x0F)) >= 0) ? 0 : 1)
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700150#define TS_SNTS_GET_PRESSURE(_pressure) (_pressure)
151
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700152#define FINGER_STATE_NO_PRESENT 0
153#define FINGER_STATE_PRESENT_VALID 1
154#define FINGER_STATE_PRESENT_NOVALID 2
155#define FINGER_STATE_REVSERVED 3
156
Jongrak Kwon5b6082d2012-09-01 03:50:16 -0700157#define CHARGER_CONNECTED 0x20
158
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700159int synaptics_ts_get_data(struct i2c_client *client, struct t_data* data,
160 struct b_data* button, u8* total_num)
161{
162 struct synaptics_ts_data* ts =
163 (struct synaptics_ts_data*)get_touch_handle(client);
164
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700165 u32 finger_status=0;
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700166 u8 id=0;
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700167 u8 cnt;
168
169 if (unlikely(touch_debug_mask & DEBUG_TRACE))
170 TOUCH_DEBUG_MSG("\n");
171
172 if (unlikely(touch_i2c_read(client, DEVICE_STATUS_REG,
Jongrak Kwon5297b722012-06-22 11:18:36 -0700173 sizeof(ts->ts_data.device_status_reg),
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700174 &ts->ts_data.device_status_reg) < 0)) {
175 TOUCH_ERR_MSG("DEVICE_STATUS_REG read fail\n");
176 goto err_synaptics_getdata;
177 }
178
179 /* ESD damage check */
180 if ((ts->ts_data.device_status_reg & DEVICE_FAILURE_MASK) ==
181 DEVICE_FAILURE_MASK) {
182 TOUCH_ERR_MSG("ESD damage occured. Reset Touch IC\n");
183 goto err_synaptics_device_damage;
184 }
185
186 /* Internal reset check */
187 if (((ts->ts_data.device_status_reg & DEVICE_STATUS_UNCONFIGURED) >> 7) == 1) {
188 TOUCH_ERR_MSG("Touch IC resetted internally. "
189 "Reconfigure register setting\n");
190 goto err_synaptics_device_damage;
191 }
192
193 if (unlikely(touch_i2c_read(client, INTERRUPT_STATUS_REG,
194 sizeof(ts->ts_data.interrupt_status_reg),
195 &ts->ts_data.interrupt_status_reg) < 0)) {
196 TOUCH_ERR_MSG("INTERRUPT_STATUS_REG read fail\n");
197 goto err_synaptics_getdata;
198 }
199
200 if (unlikely(touch_debug_mask & DEBUG_GET_DATA))
201 TOUCH_INFO_MSG("Interrupt_status : 0x%x\n",
202 ts->ts_data.interrupt_status_reg);
203
204 /* IC bug Exception handling - Interrupt status reg is 0 when interrupt occur */
205 if (ts->ts_data.interrupt_status_reg == 0) {
Jongrak Kwonecef32b2012-08-29 13:58:51 -0700206 TOUCH_ERR_MSG("Interrupt_status reg is 0. -> ignore\n");
207 goto err_synaptics_ignore;
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700208 }
209
210 /* Because of ESD damage... */
211 if (unlikely(ts->ts_data.interrupt_status_reg & ts->interrupt_mask.flash)) {
212 TOUCH_ERR_MSG("Impossible Interrupt\n");
213 goto err_synaptics_device_damage;
214 }
215
216 /* Finger */
217 if (likely(ts->ts_data.interrupt_status_reg & ts->interrupt_mask.abs)) {
218 if (unlikely(touch_i2c_read(client, FINGER_STATE_REG,
219 sizeof(ts->ts_data.finger.finger_status_reg),
220 ts->ts_data.finger.finger_status_reg) < 0)) {
221 TOUCH_ERR_MSG("FINGER_STATE_REG read fail\n");
222 goto err_synaptics_getdata;
223 }
224
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700225 finger_status = ts->ts_data.finger.finger_status_reg[0] |
226 ts->ts_data.finger.finger_status_reg[1] << 8 |
227 (ts->ts_data.finger.finger_status_reg[2] & 0xF) << 16;
228
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700229 if (unlikely(touch_debug_mask & DEBUG_GET_DATA)) {
230 TOUCH_INFO_MSG("Finger_status : 0x%x, 0x%x, 0x%x\n",
231 ts->ts_data.finger.finger_status_reg[0],
232 ts->ts_data.finger.finger_status_reg[1],
233 ts->ts_data.finger.finger_status_reg[2]);
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700234 TOUCH_INFO_MSG("Touch_bit_mask: 0x%x\n", finger_status);
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700235 }
236
Jongrak Kwon8c0f1692012-07-16 19:01:35 -0700237 for (id = 0; id < ts->pdata->caps->max_id; id++) {
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700238 switch (((finger_status >> (id*2)) & 0x3)) {
239 case FINGER_STATE_PRESENT_VALID:
240 touch_i2c_read(ts->client,
241 FINGER_DATA_REG_START + NUM_OF_EACH_FINGER_DATA_REG * id,
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700242 NUM_OF_EACH_FINGER_DATA_REG,
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700243 ts->ts_data.finger.finger_reg[id]);
244 data[id].state = ABS_PRESS;
245 data[id].x_position = TS_SNTS_GET_X_POSITION(
246 ts->ts_data.finger.finger_reg[id][REG_X_POSITION],
247 ts->ts_data.finger.finger_reg[id][REG_YX_POSITION]);
248 data[id].y_position = TS_SNTS_GET_Y_POSITION(ts->ts_data.finger.finger_reg[id][REG_Y_POSITION], ts->ts_data.finger.finger_reg[id][REG_YX_POSITION]);
249 data[id].width_major = TS_SNTS_GET_WIDTH_MAJOR(ts->ts_data.finger.finger_reg[id][REG_WY_WX]);
250 data[id].width_minor = TS_SNTS_GET_WIDTH_MINOR(ts->ts_data.finger.finger_reg[id][REG_WY_WX]);
Jongrak Kwon4ea40bb2012-08-23 17:59:06 -0700251 data[id].tool_type = MT_TOOL_FINGER;
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700252 data[id].width_orientation = TS_SNTS_GET_ORIENTATION(ts->ts_data.finger.finger_reg[id][REG_WY_WX]);
253 data[id].pressure = TS_SNTS_GET_PRESSURE(ts->ts_data.finger.finger_reg[id][REG_Z]);
254
255 if (unlikely(touch_debug_mask & DEBUG_GET_DATA))
256 TOUCH_INFO_MSG("[%d] pos(%4d,%4d) w_m[%2d] w_n[%2d] w_o[%2d] p[%2d]\n",
Jongrak Kwon4ea40bb2012-08-23 17:59:06 -0700257 id,
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700258 data[id].x_position,
259 data[id].y_position,
260 data[id].width_major,
261 data[id].width_minor,
262 data[id].width_orientation,
263 data[id].pressure);
264 (*total_num)++;
265 break;
266
267 case FINGER_STATE_NO_PRESENT:
268 if (data[id].state == ABS_PRESS)
269 data[id].state = ABS_RELEASE;
270 break;
271
272 default:
273 /* Do nothing including inacurate data */
274 break;
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700275 }
276
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700277 }
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700278 if (unlikely(touch_debug_mask & DEBUG_GET_DATA))
279 TOUCH_INFO_MSG("Total_num: %d\n", *total_num);
280 }
281
282 /* Button */
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700283 if ((ts->button_dsc.id != 0) && (ts->ts_data.interrupt_status_reg &
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700284 ts->interrupt_mask.button)) {
285
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700286 if (unlikely(touch_i2c_write_byte(client,
287 PAGE_SELECT_REG, 0x02) < 0)) {
288 TOUCH_ERR_MSG("PAGE_SELECT_REG write fail\n");
289 return -EIO;
290 }
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700291
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700292 if (unlikely(touch_i2c_read(client, BUTTON_DATA_REG,
293 sizeof(ts->ts_data.button_data_reg),
294 &ts->ts_data.button_data_reg) < 0)) {
295 TOUCH_ERR_MSG("BUTTON_DATA_REG read fail\n");
296 goto err_synaptics_getdata;
297 }
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700298
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700299 if (unlikely(touch_i2c_write_byte(client,
300 PAGE_SELECT_REG, 0x00) < 0)) {
301 TOUCH_ERR_MSG("PAGE_SELECT_REG write fail\n");
302 return -EIO;
303 }
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700304
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700305 if (unlikely(touch_debug_mask & DEBUG_BUTTON))
306 TOUCH_DEBUG_MSG("Button register: 0x%x\n",
307 ts->ts_data.button_data_reg);
308
309 if (ts->ts_data.button_data_reg) {
310 /* pressed - find first one */
311 for (cnt = 0; cnt < ts->pdata->caps->number_of_button; cnt++) {
312 if ((ts->ts_data.button_data_reg >> cnt) & 1)
313 {
314 ts->ts_data.button.key_code =
315 ts->pdata->caps->button_name[cnt];
316 button->key_code =
317 ts->ts_data.button.key_code;
318 button->state = 1;
319 break;
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700320 }
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700321 }
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700322 } else {
323 /* release */
324 button->key_code = ts->ts_data.button.key_code;
325 button->state = 0;
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700326 }
327 }
328
329 return 0;
330
331err_synaptics_device_damage:
332err_synaptics_getdata:
333 return -EIO;
Jongrak Kwonecef32b2012-08-29 13:58:51 -0700334err_synaptics_ignore:
335 return -EINVAL;
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700336}
337
338static int read_page_description_table(struct i2c_client* client)
339{
340 struct synaptics_ts_data* ts =
341 (struct synaptics_ts_data*)get_touch_handle(client);
342 struct ts_function_descriptor buffer;
343 unsigned short u_address;
344
345 if (touch_debug_mask & DEBUG_TRACE)
346 TOUCH_DEBUG_MSG("\n");
347
348 memset(&buffer, 0x0, sizeof(struct ts_function_descriptor));
349
350 ts->common_dsc.id = 0;
351 ts->finger_dsc.id = 0;
352 ts->button_dsc.id = 0;
353 ts->flash_dsc.id = 0;
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700354 ts->analog_dsc.id = 0;
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700355
356 for (u_address = DESCRIPTION_TABLE_START; u_address > 10;
357 u_address -= sizeof(struct ts_function_descriptor)) {
358 if (unlikely(touch_i2c_read(client, u_address, sizeof(buffer),
359 (unsigned char *)&buffer) < 0)) {
360 TOUCH_ERR_MSG("RMI4 Function Descriptor read fail\n");
361 return -EIO;
362 }
363
364 if (buffer.id == 0)
365 break;
366
367 switch (buffer.id) {
368 case RMI_DEVICE_CONTROL:
369 ts->common_dsc = buffer;
370 break;
371 case TOUCHPAD_SENSORS:
372 ts->finger_dsc = buffer;
373 break;
374 case FLASH_MEMORY_MANAGEMENT:
375 ts->flash_dsc = buffer;
Jongrak Kwon420825a2012-06-26 16:33:25 -0700376 break;
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700377 }
378 }
379
380#if defined(CONFIG_TOUCH_REG_MAP_TM2000) || defined(CONFIG_TOUCH_REG_MAP_TM2372)
381 if (unlikely(touch_i2c_write_byte(client, PAGE_SELECT_REG, 0x01) < 0)) {
382 TOUCH_ERR_MSG("PAGE_SELECT_REG write fail\n");
383 return -EIO;
384 }
385
Jongrak Kwon420825a2012-06-26 16:33:25 -0700386 if (unlikely(touch_i2c_read(client, ANALOG_TABLE_START, sizeof(buffer), (unsigned char *)&buffer) < 0)) {
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700387 TOUCH_ERR_MSG("RMI4 Function Descriptor read fail\n");
388 return -EIO;
389 }
390
Jongrak Kwon420825a2012-06-26 16:33:25 -0700391 if (buffer.id == ANALOG_CONTROL) {
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700392 ts->analog_dsc = buffer;
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700393 }
394
395 if (unlikely(touch_i2c_write_byte(client, PAGE_SELECT_REG, 0x02) < 0)) {
396 TOUCH_ERR_MSG("PAGE_SELECT_REG write fail\n");
397 return -EIO;
398 }
399
Jongrak Kwon420825a2012-06-26 16:33:25 -0700400 if (unlikely(touch_i2c_read(ts->client, BUTTON_TABLE_START, sizeof(buffer), (unsigned char *)&buffer))) {
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700401 TOUCH_ERR_MSG("Button ts_function_descriptor read fail\n");
402 return -EIO;
403 }
404
Jongrak Kwon420825a2012-06-26 16:33:25 -0700405 if (buffer.id == CAPACITIVE_BUTTON_SENSORS)
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700406 ts->button_dsc = buffer;
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700407
408 if (unlikely(touch_i2c_write_byte(client, PAGE_SELECT_REG, 0x00) < 0)) {
409 TOUCH_ERR_MSG("PAGE_SELECT_REG write fail\n");
410 return -EIO;
411 }
412#endif
413
414 /* set interrupt mask */
415 ts->interrupt_mask.flash = 0x1;
416 ts->interrupt_mask.status = 0x2;
417
418 if (ts->button_dsc.id == 0) {
419 ts->interrupt_mask.abs = 0x4;
420 } else {
421 if (ts->finger_dsc.data_base > ts->button_dsc.data_base) {
422#if defined(CONFIG_TOUCH_REG_MAP_TM2000) || defined(CONFIG_TOUCH_REG_MAP_TM2372)
423 ts->interrupt_mask.abs = 0x4;
424 ts->interrupt_mask.button = 0x20;
425#else
426 ts->interrupt_mask.abs = 0x8;
427 ts->interrupt_mask.button = 0x4;
428#endif
429 } else {
430 ts->interrupt_mask.abs = 0x4;
431 ts->interrupt_mask.button = 0x8;
432 }
433 }
434
435 if (ts->common_dsc.id == 0 || ts->finger_dsc.id == 0 ||
436 ts->flash_dsc.id == 0) {
437 TOUCH_ERR_MSG("common_dsc/finger_dsc/flash_dsc are not initiailized\n");
438 return -EPERM;
439 }
440
441 if (touch_debug_mask & DEBUG_BASE_INFO)
442 TOUCH_INFO_MSG("common[%d] finger[%d] flash[%d] button[%d]\n",
443 ts->common_dsc.id, ts->finger_dsc.id,
444 ts->flash_dsc.id, ts->button_dsc.id);
445
446 return 0;
447}
448
449int get_ic_info(struct synaptics_ts_data* ts, struct touch_fw_info* fw_info)
450{
451#if defined(ARRAYED_TOUCH_FW_BIN)
452 int cnt;
453#endif
454 u8 device_status = 0;
455 u8 flash_control = 0;
456
457 read_page_description_table(ts->client);
458
459 memset(fw_info, 0, sizeof(fw_info));
460
461 if (unlikely(touch_i2c_read(ts->client, FW_REVISION_REG,
462 sizeof(fw_info->fw_rev), &fw_info->fw_rev) < 0)) {
463 TOUCH_ERR_MSG("FW_REVISION_REG read fail\n");
464 return -EIO;
465 }
466
467 if (unlikely(touch_i2c_read(ts->client, MANUFACTURER_ID_REG,
468 sizeof(fw_info->manufacturer_id),
469 &fw_info->manufacturer_id) < 0)) {
470 TOUCH_ERR_MSG("MANUFACTURER_ID_REG read fail\n");
471 return -EIO;
472 }
473
474 if (unlikely(touch_i2c_read(ts->client, PRODUCT_ID_REG,
475 sizeof(fw_info->product_id) - 1,
476 fw_info->product_id) < 0)) {
477 TOUCH_ERR_MSG("PRODUCT_ID_REG read fail\n");
478 return -EIO;
479 }
480
481 if (unlikely(touch_i2c_read(ts->client, FW_VERSION,
482 sizeof(fw_info->fw_version) - 1,
483 fw_info->fw_version) < 0)) {
484 TOUCH_ERR_MSG("FW_VERSION read fail\n");
485 return -EIO;
486 }
487
Jongrak Kwon8c0f1692012-07-16 19:01:35 -0700488 ts->ic_panel_type = IC7020_G2_H_PTN;
Jongrak Kwonecef32b2012-08-29 13:58:51 -0700489 TOUCH_INFO_MSG("IC is 7020, H pattern, panel is G2, Firmware: %s.", fw_info->fw_version);
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700490
491#if defined(ARRAYED_TOUCH_FW_BIN)
492 for (cnt = 0; cnt < sizeof(SynaFirmware)/sizeof(SynaFirmware[0]); cnt++) {
493 strncpy(fw_info->fw_image_product_id,
Jongrak Kwon8c0f1692012-07-16 19:01:35 -0700494 &SynaFirmware[cnt][FW_OFFSET_PRODUCT_ID], 10);
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700495 if (!(strncmp(fw_info->product_id,
496 fw_info->fw_image_product_id, 10)))
497 break;
498 }
499 fw_info->fw_start = (unsigned char *)&SynaFirmware[cnt][0];
500 fw_info->fw_size = sizeof(SynaFirmware[0]);
501#else
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700502 fw_info->fw_start = (unsigned char *)&SynaFirmware[0];
503 fw_info->fw_size = sizeof(SynaFirmware);
504#endif
505
Jongrak Kwon8c0f1692012-07-16 19:01:35 -0700506 strncpy(fw_info->fw_image_product_id,
507 &fw_info->fw_start[FW_OFFSET_PRODUCT_ID], 10);
508 strncpy(fw_info->fw_image_version,
509 &fw_info->fw_start[FW_OFFSET_IMAGE_VERSION],4);
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700510
511 if (unlikely(touch_i2c_read(ts->client, FLASH_CONTROL_REG,
512 sizeof(flash_control), &flash_control) < 0)) {
513 TOUCH_ERR_MSG("FLASH_CONTROL_REG read fail\n");
514 return -EIO;
515 }
516
517 if (unlikely(touch_i2c_read(ts->client, DEVICE_STATUS_REG,
518 sizeof(device_status), &device_status) < 0)) {
519 TOUCH_ERR_MSG("DEVICE_STATUS_REG read fail\n");
520 return -EIO;
521 }
522
523 /* Firmware has a problem, so we should firmware-upgrade */
524 if (device_status & DEVICE_STATUS_FLASH_PROG
525 || (device_status & DEVICE_CRC_ERROR_MASK) != 0
526 || (flash_control & FLASH_STATUS_MASK) != 0) {
527 TOUCH_ERR_MSG("Firmware has a unknown-problem, "
528 "so it needs firmware-upgrade.\n");
529 TOUCH_ERR_MSG("FLASH_CONTROL[%x] DEVICE_STATUS_REG[%x]\n",
530 (u32)flash_control, (u32)device_status);
531
532 fw_info->fw_rev = 0;
533#if defined(CONFIG_TOUCH_REG_MAP_TM2000) || defined(CONFIG_TOUCH_REG_MAP_TM2372)
534 fw_info->fw_force_rework = true;
535#endif
536 }
537
538 ts->fw_info = fw_info;
539
540 return 0;
541}
542
543int synaptics_ts_init(struct i2c_client* client, struct touch_fw_info* fw_info)
544{
545 struct synaptics_ts_data* ts =
546 (struct synaptics_ts_data*)get_touch_handle(client);
Jongrak Kwon9ed2a932012-06-19 23:38:02 -0700547 struct lge_touch_data *lg_ts =
548 (struct lge_touch_data *) i2c_get_clientdata(client);
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700549 u8 buf;
550
551 if (touch_debug_mask & DEBUG_TRACE)
552 TOUCH_DEBUG_MSG("\n");
553
554 if (!ts->is_probed)
555 if (unlikely(get_ic_info(ts, fw_info) < 0))
556 return -EIO;
557
558 if (unlikely(touch_i2c_write_byte(client, DEVICE_CONTROL_REG,
Jongrak Kwon5b6082d2012-09-01 03:50:16 -0700559 DEVICE_CONTROL_NOSLEEP | DEVICE_CONTROL_CONFIGURED |
560 (lg_ts->charger_type ? CHARGER_CONNECTED : 0)) < 0)) {
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700561 TOUCH_ERR_MSG("DEVICE_CONTROL_REG write fail\n");
562 return -EIO;
563 }
564
565 if (unlikely(touch_i2c_read(client, INTERRUPT_ENABLE_REG,
566 1, &buf) < 0)) {
567 TOUCH_ERR_MSG("INTERRUPT_ENABLE_REG read fail\n");
568 return -EIO;
569 }
Jongrak Kwon9ed2a932012-06-19 23:38:02 -0700570
571 if (!lg_ts->pdata->caps->button_support) {
572 buf &= ~ts->interrupt_mask.button;
573 ts->interrupt_mask.button = 0;
574 }
575
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700576 if (unlikely(touch_i2c_write_byte(client, INTERRUPT_ENABLE_REG,
577 buf | ts->interrupt_mask.abs | ts->interrupt_mask.button) < 0)) {
578 TOUCH_ERR_MSG("INTERRUPT_ENABLE_REG write fail\n");
579 return -EIO;
580 }
581
582#if defined(CONFIG_TOUCH_REG_MAP_TM2000) || defined(CONFIG_TOUCH_REG_MAP_TM2372)
Jongrak Kwonef6ce3c2012-08-28 00:01:59 -0700583 if (unlikely(touch_i2c_read(client, TWO_D_REPORTING_MODE, 1, &buf) < 0)) {
584 TOUCH_ERR_MSG("TWO_D_REPORTING_MODE read fail\n");
585 return -EIO;
586 }
587
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700588 if (ts->pdata->role->report_mode == CONTINUOUS_REPORT_MODE) {
589 if (unlikely(touch_i2c_write_byte(client, TWO_D_REPORTING_MODE,
Jongrak Kwonef6ce3c2012-08-28 00:01:59 -0700590 (buf & ~7) | REPORT_MODE_CONTINUOUS) < 0)) {
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700591 TOUCH_ERR_MSG("TWO_D_REPORTING_MODE write fail\n");
592 return -EIO;
593 }
594 } else { /* REDUCED_REPORT_MODE */
595 if (unlikely(touch_i2c_write_byte(client, TWO_D_REPORTING_MODE,
Jongrak Kwonef6ce3c2012-08-28 00:01:59 -0700596 (buf & ~7) | REPORT_MODE_REDUCED) < 0)) {
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700597 TOUCH_ERR_MSG("TWO_D_REPORTING_MODE write fail\n");
598 return -EIO;
599 }
Jongrak Kwon9ed2a932012-06-19 23:38:02 -0700600
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700601 if (unlikely(touch_i2c_write_byte(client, DELTA_X_THRESH_REG,
602 ts->pdata->role->delta_pos_threshold) < 0)) {
603 TOUCH_ERR_MSG("DELTA_X_THRESH_REG write fail\n");
604 return -EIO;
605 }
606 if (unlikely(touch_i2c_write_byte(client, DELTA_Y_THRESH_REG,
607 ts->pdata->role->delta_pos_threshold) < 0)) {
608 TOUCH_ERR_MSG("DELTA_Y_THRESH_REG write fail\n");
609 return -EIO;
610 }
611 }
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700612#else
613 if (unlikely(touch_i2c_write_byte(client,
614 GESTURE_ENABLE_1_REG, 0x00) < 0)) {
615 TOUCH_ERR_MSG("GESTURE_ENABLE_1_REG write fail\n");
616 return -EIO;
617 }
618 if (unlikely(touch_i2c_write_byte(client, GESTURE_ENABLE_2_REG, 0x00) < 0)) {
619 TOUCH_ERR_MSG("GESTURE_ENABLE_2_REG write fail\n");
620 return -EIO;
621 }
622
Jongrak Kwonef6ce3c2012-08-28 00:01:59 -0700623 if (unlikely(touch_i2c_read(client, TWO_D_REPORTING_MODE, 1, &buf) < 0)) {
624 TOUCH_ERR_MSG("TWO_D_REPORTING_MODE read fail\n");
625 return -EIO;
626 }
627
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700628 if (ts->pdata->role->report_mode == CONTINUOUS_REPORT_MODE) {
629 if (unlikely(touch_i2c_write_byte(client, TWO_D_REPORTING_MODE,
Jongrak Kwonef6ce3c2012-08-28 00:01:59 -0700630 (buf & ~7) | REPORT_MODE_CONTINUOUS) < 0)) {
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700631 TOUCH_ERR_MSG("TWO_D_REPORTING_MODE write fail\n");
632 return -EIO;
633 }
634 } else { /* REDUCED_REPORT_MODE */
635 if (unlikely(touch_i2c_write_byte(client, TWO_D_REPORTING_MODE,
Jongrak Kwonef6ce3c2012-08-28 00:01:59 -0700636 (buf & ~7) | REPORT_MODE_REDUCED) < 0)) {
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700637 TOUCH_ERR_MSG("TWO_D_REPORTING_MODE write fail\n");
638 return -EIO;
639 }
640
641 if (unlikely(touch_i2c_write_byte(client, DELTA_X_THRESH_REG,
642 ts->pdata->role->delta_pos_threshold) < 0)) {
643 TOUCH_ERR_MSG("DELTA_X_THRESH_REG write fail\n");
644 return -EIO;
645 }
646 if (unlikely(touch_i2c_write_byte(client, DELTA_Y_THRESH_REG,
647 ts->pdata->role->delta_pos_threshold) < 0)) {
648 TOUCH_ERR_MSG("DELTA_Y_THRESH_REG write fail\n");
649 return -EIO;
650 }
651 }
652#endif
653
654 if (unlikely(touch_i2c_read(client, INTERRUPT_STATUS_REG, 1, &buf) < 0)) {
655 TOUCH_ERR_MSG("INTERRUPT_STATUS_REG read fail\n");
656 return -EIO; /* it is critical problem because interrupt will not occur. */
657 }
658
659 if (unlikely(touch_i2c_read(client, FINGER_STATE_REG,
660 sizeof(ts->ts_data.finger.finger_status_reg),
661 ts->ts_data.finger.finger_status_reg) < 0)) {
662 TOUCH_ERR_MSG("FINGER_STATE_REG read fail\n");
663 /* it is critical problem because interrupt will not occur on some FW. */
664 return -EIO;
665 }
666
667 ts->is_probed = 1;
668
669 return 0;
670}
671
672int synaptics_ts_power(struct i2c_client* client, int power_ctrl)
673{
674 struct synaptics_ts_data* ts =
675 (struct synaptics_ts_data*)get_touch_handle(client);
Jongrak Kwon5b6082d2012-09-01 03:50:16 -0700676 struct lge_touch_data *lg_ts =
677 (struct lge_touch_data *) i2c_get_clientdata(client);
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700678
679 if (touch_debug_mask & DEBUG_TRACE)
680 TOUCH_DEBUG_MSG("\n");
681
682 switch (power_ctrl) {
683 case POWER_OFF:
ks.kwon22c5f0b2012-08-07 13:50:18 +0900684 if (ts->pdata->reset_pin > 0)
685 gpio_set_value(ts->pdata->reset_pin, 0);
686
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700687 if (ts->pdata->pwr->use_regulator) {
688 regulator_disable(ts->regulator_vio);
689 regulator_disable(ts->regulator_vdd);
690 }
691 else
692 ts->pdata->pwr->power(0);
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700693 break;
694 case POWER_ON:
695 if (ts->pdata->pwr->use_regulator) {
696 regulator_enable(ts->regulator_vdd);
697 regulator_enable(ts->regulator_vio);
698 }
699 else
700 ts->pdata->pwr->power(1);
701
ks.kwon22c5f0b2012-08-07 13:50:18 +0900702 if (ts->pdata->reset_pin > 0)
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700703 gpio_set_value(ts->pdata->reset_pin, 1);
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700704 break;
705 case POWER_SLEEP:
706 if (unlikely(touch_i2c_write_byte(client, DEVICE_CONTROL_REG,
Jongrak Kwon5b6082d2012-09-01 03:50:16 -0700707 DEVICE_CONTROL_SLEEP |
708 (lg_ts->charger_type ? CHARGER_CONNECTED : 0) |
709 DEVICE_CONTROL_CONFIGURED) < 0)) {
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700710 TOUCH_ERR_MSG("DEVICE_CONTROL_REG write fail\n");
711 return -EIO;
712 }
713 break;
714 case POWER_WAKE:
715 if (unlikely(touch_i2c_write_byte(client, DEVICE_CONTROL_REG,
Jongrak Kwon5b6082d2012-09-01 03:50:16 -0700716 DEVICE_CONTROL_SPECIFIC |
717 (lg_ts->charger_type ? CHARGER_CONNECTED : 0) |
718 DEVICE_CONTROL_CONFIGURED) < 0)) {
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700719 TOUCH_ERR_MSG("DEVICE_CONTROL_REG write fail\n");
720 return -EIO;
721 }
722 break;
723 default:
724 return -EIO;
725 break;
726 }
727
728 return 0;
729}
730
731int synaptics_ts_probe(struct i2c_client* client)
732{
733 struct synaptics_ts_data* ts;
734 int ret = 0;
735
736 if (touch_debug_mask & DEBUG_TRACE)
737 TOUCH_DEBUG_MSG("\n");
738
739 ts = kzalloc(sizeof(struct synaptics_ts_data), GFP_KERNEL);
740 if (!ts) {
741 TOUCH_ERR_MSG("Can not allocate memory\n");
742 ret = -ENOMEM;
743 goto err_alloc_data_failed;
744 }
745
746 set_touch_handle(client, ts);
747
748 ts->client = client;
749 ts->pdata = client->dev.platform_data;
750#if defined(CONFIG_TOUCH_REG_MAP_TM2000)
751 ts->ic_panel_type = IC7020_G2_H_PTN;
752#elif defined(CONFIG_TOUCH_REG_MAP_TM2372)
753 ts->ic_panel_type = IC7020_GFF_H_PTN;
754#endif
755
756 if (ts->pdata->pwr->use_regulator) {
757 ts->regulator_vdd =
758 regulator_get_exclusive(NULL, ts->pdata->pwr->vdd);
759 if (IS_ERR(ts->regulator_vdd)) {
760 TOUCH_ERR_MSG("FAIL: regulator_get_vdd - %s\n",
761 ts->pdata->pwr->vdd);
762 ret = -EPERM;
763 goto err_get_vdd_failed;
764 }
765
766 ts->regulator_vio = regulator_get_exclusive(NULL,
767 ts->pdata->pwr->vio);
768 if (IS_ERR(ts->regulator_vio)) {
769 TOUCH_ERR_MSG("FAIL: regulator_get_vio - %s\n",
770 ts->pdata->pwr->vio);
771 ret = -EPERM;
772 goto err_get_vio_failed;
773 }
774
775 if (ts->pdata->pwr->vdd_voltage > 0) {
776 ret = regulator_set_voltage(ts->regulator_vdd,
777 ts->pdata->pwr->vdd_voltage,
778 ts->pdata->pwr->vdd_voltage);
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700779 if (ret < 0) {
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700780 TOUCH_ERR_MSG("FAIL: VDD voltage setting"
781 " - (%duV)\n",
782 ts->pdata->pwr->vdd_voltage);
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700783 ret = -EPERM;
784 goto err_set_voltage;
785 }
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700786 }
787
788 if (ts->pdata->pwr->vio_voltage > 0) {
789 ret = regulator_set_voltage(ts->regulator_vio,
790 ts->pdata->pwr->vio_voltage,
791 ts->pdata->pwr->vio_voltage);
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700792 if (ret < 0) {
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700793 TOUCH_ERR_MSG("FAIL: VIO voltage setting"
794 " - (%duV)\n",
795 ts->pdata->pwr->vio_voltage);
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700796 ret = -EPERM;
797 goto err_set_voltage;
798 }
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700799 }
800 }
801
802 return ret;
803
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700804err_set_voltage:
805 if (ts->pdata->pwr->use_regulator) {
806 regulator_put(ts->regulator_vio);
807 }
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700808err_get_vio_failed:
809 if (ts->pdata->pwr->use_regulator) {
810 regulator_put(ts->regulator_vdd);
811 }
812err_get_vdd_failed:
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700813 kfree(ts);
Jongrak Kwon098aa9d2012-06-26 11:53:27 -0700814err_alloc_data_failed:
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700815 return ret;
816}
817
818void synaptics_ts_remove(struct i2c_client* client)
819{
820 struct synaptics_ts_data* ts =
821 (struct synaptics_ts_data*)get_touch_handle(client);
822
823 if (touch_debug_mask & DEBUG_TRACE)
824 TOUCH_DEBUG_MSG("\n");
825
826 if (ts->pdata->pwr->use_regulator) {
827 regulator_put(ts->regulator_vio);
828 regulator_put(ts->regulator_vdd);
829 }
830
831 kfree(ts);
832}
833
834int synaptics_ts_fw_upgrade(struct i2c_client* client, const char* fw_path)
835{
836 struct synaptics_ts_data* ts =
837 (struct synaptics_ts_data*)get_touch_handle(client);
838 int ret = 0;
839
840 ts->is_probed = 0;
841
842 ret = FirmwareUpgrade(ts, fw_path);
843
844 /* update IC info */
845 get_ic_info(ts, ts->fw_info);
846
847 return ret;
848}
849
850int synaptics_ts_ic_ctrl(struct i2c_client *client, u8 code, u16 value)
851{
852 struct synaptics_ts_data* ts =
853 (struct synaptics_ts_data*)get_touch_handle(client);
854 u8 buf = 0;
Jongrak Kwon5b6082d2012-09-01 03:50:16 -0700855 u8 new;
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700856
857 switch (code) {
858 case IC_CTRL_BASELINE:
859 switch (value) {
860 case BASELINE_OPEN:
Jongrak Kwon420825a2012-06-26 16:33:25 -0700861 if (!ts->analog_dsc.id) /* If not supported, ignore */
862 break;
863
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700864#if defined(CONFIG_TOUCH_REG_MAP_TM2000) || defined(CONFIG_TOUCH_REG_MAP_TM2372)
865 if (unlikely(touch_i2c_write_byte(client,
866 PAGE_SELECT_REG, 0x01) < 0)) {
867 TOUCH_ERR_MSG("PAGE_SELECT_REG write fail\n");
868 return -EIO;
869 }
870
871 if (unlikely(touch_i2c_write_byte(client,
872 ANALOG_CONTROL_REG,
873 FORCE_FAST_RELAXATION) < 0)) {
874 TOUCH_ERR_MSG("ANALOG_CONTROL_REG write fail\n");
875 return -EIO;
876 }
877
878 msleep(10);
879
880 if (unlikely(touch_i2c_write_byte(client,
881 ANALOG_COMMAND_REG,
882 FORCE_UPDATE) < 0)) {
883 TOUCH_ERR_MSG("force fast relaxation command write fail\n");
884 return -EIO;
885 }
886
887 if (unlikely(touch_i2c_write_byte(client,
888 PAGE_SELECT_REG, 0x00) < 0)) {
889 TOUCH_ERR_MSG("PAGE_SELECT_REG write fail\n");
890 return -EIO;
891 }
892
893 if (unlikely(touch_debug_mask & DEBUG_GHOST))
894 TOUCH_INFO_MSG("BASELINE_OPEN ~~~~~~~~\n");
895#else
896 if (unlikely(touch_i2c_write_byte(client,
897 MELT_CONTROL_REG,
898 MELT_CONTROL_MELT) < 0)) {
899 TOUCH_ERR_MSG("MELT_CONTROL_REG write fail\n");
900 return -EIO;
901 }
902#endif
903 break;
904 case BASELINE_FIX:
Jongrak Kwon420825a2012-06-26 16:33:25 -0700905 if (!ts->analog_dsc.id) /* If not supported, ignore */
906 break;
907
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700908#if defined(CONFIG_TOUCH_REG_MAP_TM2000) || defined(CONFIG_TOUCH_REG_MAP_TM2372)
909 if (unlikely(touch_i2c_write_byte(client,
910 PAGE_SELECT_REG, 0x01) < 0)) {
911 TOUCH_ERR_MSG("PAGE_SELECT_REG write fail\n");
912 return -EIO;
913 }
914
915 if (unlikely(touch_i2c_write_byte(client,
916 ANALOG_CONTROL_REG, 0x0) < 0)) {
917 TOUCH_ERR_MSG("ANALOG_CONTROL_REG write fail\n");
918 return -EIO;
919 }
920
921 msleep(10);
922
923 if (unlikely(touch_i2c_write_byte(client,
924 ANALOG_COMMAND_REG,
925 FORCE_UPDATE) < 0)) {
926 TOUCH_ERR_MSG("force fast relaxation command write fail\n");
927 return -EIO;
928 }
929
930 if (unlikely(touch_i2c_write_byte(client,
931 PAGE_SELECT_REG, 0x00) < 0)) {
932 TOUCH_ERR_MSG("PAGE_SELECT_REG write fail\n");
933 return -EIO;
934 }
935
936 if (unlikely(touch_debug_mask & DEBUG_GHOST))
937 TOUCH_INFO_MSG("BASELINE_FIX ~~~~~~~~\n");
938#else
939 if (unlikely(touch_i2c_write_byte(client,
940 MELT_CONTROL_REG,
941 MELT_CONTROL_NO_MELT) < 0)) {
942 TOUCH_ERR_MSG("MELT_CONTROL_REG write fail\n");
943 return -EIO;
944 }
945#endif
946 break;
947 case BASELINE_REBASE:
948 /* rebase base line */
949 if (likely(ts->finger_dsc.id != 0)) {
950 if (unlikely(touch_i2c_write_byte(client,
951 FINGER_COMMAND_REG, 0x1) < 0)) {
952 TOUCH_ERR_MSG("finger baseline reset "
953 "command write fail\n");
954 return -EIO;
955 }
956 }
957
958#if defined(CONFIG_TOUCH_REG_MAP_TM2000) || defined(CONFIG_TOUCH_REG_MAP_TM2372)
959/* do nothing */
960#else
961 if (unlikely(ts->button_dsc.id != 0)) {
962 if (unlikely(touch_i2c_write_byte(client,
963 BUTTON_COMMAND_REG, 0x1) < 0)) {
964 TOUCH_ERR_MSG("finger baseline reset "
965 "command write fail\n");
966 return -EIO;
967 }
968 }
969#endif
970 break;
971 default:
972 break;
973 }
974 break;
975 case IC_CTRL_READ:
Jongrak Kwon9ed2a932012-06-19 23:38:02 -0700976#if defined(CONFIG_TOUCH_REG_MAP_TM2000) || defined(CONFIG_TOUCH_REG_MAP_TM2372)
977 if (unlikely(touch_i2c_write_byte(client,
978 PAGE_SELECT_REG, ((value & 0xFF00) >> 8)) < 0)) {
979 TOUCH_ERR_MSG("PAGE_SELECT_REG write fail\n");
980 return -EIO;
981 }
982
983 if (touch_i2c_read(client, (value & 0xFF), 1, &buf) < 0) {
984 TOUCH_ERR_MSG("IC register read fail\n");
985 return -EIO;
986 }
987
988 if (unlikely(touch_i2c_write_byte(client,
989 PAGE_SELECT_REG, 0x00) < 0)) {
990 TOUCH_ERR_MSG("PAGE_SELECT_REG write fail\n");
991 return -EIO;
992 }
993#else
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700994 if (touch_i2c_read(client, value, 1, &buf) < 0) {
995 TOUCH_ERR_MSG("IC register read fail\n");
996 return -EIO;
997 }
Jongrak Kwon9ed2a932012-06-19 23:38:02 -0700998#endif
Jongrak Kwonae680ab2012-06-15 22:06:54 -0700999 break;
1000 case IC_CTRL_WRITE:
Jongrak Kwon9ed2a932012-06-19 23:38:02 -07001001#if defined(CONFIG_TOUCH_REG_MAP_TM2000) || defined(CONFIG_TOUCH_REG_MAP_TM2372)
1002 if (unlikely(touch_i2c_write_byte(client,
1003 PAGE_SELECT_REG, ((value & 0xFF0000) >> 16)) < 0)) {
1004 TOUCH_ERR_MSG("PAGE_SELECT_REG write fail\n");
1005 return -EIO;
1006 }
1007
Jongrak Kwonae680ab2012-06-15 22:06:54 -07001008 if (touch_i2c_write_byte(client,
1009 ((value & 0xFF00) >> 8), (value & 0xFF)) < 0) {
1010 TOUCH_ERR_MSG("IC register write fail\n");
1011 return -EIO;
1012 }
Jongrak Kwon9ed2a932012-06-19 23:38:02 -07001013
1014 if (unlikely(touch_i2c_write_byte(client,
1015 PAGE_SELECT_REG, 0x00) < 0)) {
1016 TOUCH_ERR_MSG("PAGE_SELECT_REG write fail\n");
1017 return -EIO;
1018 }
1019#else
1020 if (touch_i2c_write_byte(client,
1021 ((value & 0xFF00) >> 8), (value & 0xFF)) < 0) {
1022 TOUCH_ERR_MSG("IC register write fail\n");
1023 return -EIO;
1024 }
1025#endif
Jongrak Kwonae680ab2012-06-15 22:06:54 -07001026 break;
1027 case IC_CTRL_RESET_CMD:
1028 if (unlikely(touch_i2c_write_byte(client,
1029 DEVICE_COMMAND_REG, 0x1) < 0)) {
1030 TOUCH_ERR_MSG("IC Reset command write fail\n");
1031 return -EIO;
1032 }
1033 break;
Jongrak Kwon5b6082d2012-09-01 03:50:16 -07001034 case IC_CTRL_CHARGER:
1035 if (touch_i2c_read(client, DEVICE_CONTROL_REG, 1, &buf) < 0) {
1036 TOUCH_ERR_MSG("IC register read fail\n");
1037 return -EIO;
1038 }
1039
1040 new = buf & ~CHARGER_CONNECTED;
1041 new |= value ? CHARGER_CONNECTED : 0;
1042
1043 if (new != buf) {
1044 if (unlikely(touch_i2c_write_byte(client,
1045 DEVICE_CONTROL_REG, new) < 0)) {
1046 TOUCH_ERR_MSG("IC Reset command write fail\n");
1047 return -EIO;
1048 }
1049 TOUCH_INFO_MSG("CHARGER = %d\n", !!value);
1050 }
1051
1052 break;
Jongrak Kwonae680ab2012-06-15 22:06:54 -07001053 default:
1054 break;
1055 }
1056
1057 return buf;
1058}
1059
1060int synaptics_ts_fw_upgrade_check(struct lge_touch_data *ts)
1061{
Jongrak Kwon8c0f1692012-07-16 19:01:35 -07001062 if (ts->fw_info.fw_force_rework || ts->fw_upgrade.fw_force_upgrade) {
Jongrak Kwonae680ab2012-06-15 22:06:54 -07001063 TOUCH_INFO_MSG("FW-upgrade Force Rework.\n");
1064 } else {
Jongrak Kwon8c0f1692012-07-16 19:01:35 -07001065 if (((int)simple_strtoul(&ts->fw_info.fw_version[1], NULL, 10) >= (int)simple_strtoul(&ts->fw_info.fw_image_version[1], NULL, 10))) {
1066 TOUCH_INFO_MSG("DO NOT UPDATE 7020 G2 H " "pattern FW-upgrade is not executed\n");
Jongrak Kwonae680ab2012-06-15 22:06:54 -07001067 return -1;
Jongrak Kwonae680ab2012-06-15 22:06:54 -07001068 } else {
Jongrak Kwon8c0f1692012-07-16 19:01:35 -07001069 TOUCH_INFO_MSG("7020 G2 H pattern FW-upgrade " "is executed\n");
Jongrak Kwonae680ab2012-06-15 22:06:54 -07001070 }
1071 }
Jongrak Kwonae680ab2012-06-15 22:06:54 -07001072
1073 return 0;
1074}
1075
1076struct touch_device_driver synaptics_ts_driver = {
1077 .probe = synaptics_ts_probe,
1078 .remove = synaptics_ts_remove,
1079 .init = synaptics_ts_init,
1080 .data = synaptics_ts_get_data,
1081 .power = synaptics_ts_power,
1082 .fw_upgrade = synaptics_ts_fw_upgrade,
1083 .ic_ctrl = synaptics_ts_ic_ctrl,
1084 .fw_upgrade_check = synaptics_ts_fw_upgrade_check,
1085};
1086
1087static int __devinit touch_init(void)
1088{
1089 if (touch_debug_mask & DEBUG_TRACE)
1090 TOUCH_DEBUG_MSG("\n");
1091
1092 return touch_driver_register(&synaptics_ts_driver);
1093}
1094
1095static void __exit touch_exit(void)
1096{
1097 if (touch_debug_mask & DEBUG_TRACE)
1098 TOUCH_DEBUG_MSG("\n");
1099
1100 touch_driver_unregister();
1101}
1102
1103module_init(touch_init);
1104module_exit(touch_exit);
1105
1106MODULE_AUTHOR("yehan.ahn@lge.com, hyesung.shin@lge.com");
1107MODULE_DESCRIPTION("LGE Touch Driver");
1108MODULE_LICENSE("GPL");
1109