Merge "input: touchscreen: Change late_init call to module_init"
This commit is contained in:
commit
33b8c0517b
5 changed files with 449 additions and 414 deletions
|
@ -35,6 +35,7 @@ Optional properties:
|
|||
min y, max x and max y values.
|
||||
- goodix,i2c-pull-up : To specify pull up is required.
|
||||
- goodix,no-force-update : To specify force update is allowed.
|
||||
- goodix,enable-power-off : Power off touchscreen during suspend.
|
||||
- goodix,button-map : Button map of key codes. The number of key codes
|
||||
depend on panel.
|
||||
- goodix,cfg-data0 : Touch screen controller config data group 0. Ask vendor
|
||||
|
@ -55,6 +56,7 @@ Optional properties:
|
|||
to provide that.
|
||||
- goodix,cfg-data5 : Touch screen controller config data group 5. Ask vendor
|
||||
to provide that.
|
||||
- goodix,fw-name : Touch screen controller firmware file name.
|
||||
Example:
|
||||
i2c@f9927000 {
|
||||
goodix@5d {
|
||||
|
@ -89,5 +91,6 @@ i2c@f9927000 {
|
|||
20 21 22 24 26 28 29 2A FF FF
|
||||
FF FF FF FF FF FF FF 22 22 22
|
||||
22 22 22 FF 07 01];
|
||||
goodix,fw_name = "gtp_fw.bin";
|
||||
};
|
||||
};
|
||||
|
|
|
@ -85,7 +85,6 @@ static void tool_set_proc_name(char *procname)
|
|||
}
|
||||
|
||||
snprintf(procname, 20, "gmnode%04d%02d%02d", n_year, n_month, n_day);
|
||||
/* GTP_DEBUG("procname = %s", procname); */
|
||||
}
|
||||
|
||||
static s32 tool_i2c_read_no_extra(u8 *buf, u16 len)
|
||||
|
@ -180,11 +179,11 @@ static void register_i2c_func(void)
|
|||
&& strcmp(IC_TYPE, "GTxxx")) {
|
||||
tool_i2c_read = tool_i2c_read_with_extra;
|
||||
tool_i2c_write = tool_i2c_write_with_extra;
|
||||
GTP_DEBUG("I2C function: with pre and end cmd!");
|
||||
pr_debug("I2C function: with pre and end cmd!\n");
|
||||
} else {
|
||||
tool_i2c_read = tool_i2c_read_no_extra;
|
||||
tool_i2c_write = tool_i2c_write_no_extra;
|
||||
GTP_INFO("I2C function: without pre and end cmd!");
|
||||
pr_info("I2C function: without pre and end cmd!\n");
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -192,7 +191,7 @@ static void unregister_i2c_func(void)
|
|||
{
|
||||
tool_i2c_read = NULL;
|
||||
tool_i2c_write = NULL;
|
||||
GTP_INFO("I2C function: unregister i2c transfer function!");
|
||||
pr_info("I2C function: unregister i2c transfer function!\n");
|
||||
}
|
||||
|
||||
s32 init_wr_node(struct i2c_client *client)
|
||||
|
@ -215,7 +214,7 @@ s32 init_wr_node(struct i2c_client *client)
|
|||
DATA_LENGTH = i * DATA_LENGTH_UINT;
|
||||
dev_dbg(&client->dev, "Applied memory size:%d.", DATA_LENGTH);
|
||||
} else {
|
||||
GTP_ERROR("Apply for memory failed.");
|
||||
pr_err("Apply for memory failed.\n");
|
||||
return FAIL;
|
||||
}
|
||||
|
||||
|
@ -228,7 +227,7 @@ s32 init_wr_node(struct i2c_client *client)
|
|||
tool_set_proc_name(procname);
|
||||
goodix_proc_entry = create_proc_entry(procname, 0660, NULL);
|
||||
if (goodix_proc_entry == NULL) {
|
||||
GTP_ERROR("Couldn't create proc entry!");
|
||||
pr_err("Couldn't create proc entry!\n");
|
||||
return FAIL;
|
||||
}
|
||||
GTP_INFO("Create proc entry success!");
|
||||
|
@ -257,7 +256,7 @@ static u8 relation(u8 src, u8 dst, u8 rlt)
|
|||
|
||||
case 1:
|
||||
ret = (src == dst) ? true : false;
|
||||
GTP_DEBUG("equal:src:0x%02x dst:0x%02x ret:%d.",
|
||||
pr_debug("equal:src:0x%02x dst:0x%02x ret:%d.\n",
|
||||
src, dst, (s32)ret);
|
||||
break;
|
||||
|
||||
|
@ -308,14 +307,14 @@ static u8 comfirm(void)
|
|||
|
||||
for (i = 0; i < cmd_head.times; i++) {
|
||||
if (tool_i2c_read(buf, 1) <= 0) {
|
||||
GTP_ERROR("Read flag data failed!");
|
||||
pr_err("Read flag data failed!\n");
|
||||
return FAIL;
|
||||
}
|
||||
if (true == relation(buf[GTP_ADDR_LENGTH], cmd_head.flag_val,
|
||||
cmd_head.flag_relation)) {
|
||||
GTP_DEBUG("value at flag addr:0x%02x.",
|
||||
pr_debug("value at flag addr:0x%02x.\n",
|
||||
buf[GTP_ADDR_LENGTH]);
|
||||
GTP_DEBUG("flag value:0x%02x.", cmd_head.flag_val);
|
||||
pr_debug("flag value:0x%02x.\n", cmd_head.flag_val);
|
||||
break;
|
||||
}
|
||||
|
||||
|
@ -323,7 +322,7 @@ static u8 comfirm(void)
|
|||
}
|
||||
|
||||
if (i >= cmd_head.times) {
|
||||
GTP_ERROR("Didn't get the flag to continue!");
|
||||
pr_debug("Didn't get the flag to continue!\n");
|
||||
return FAIL;
|
||||
}
|
||||
|
||||
|
@ -344,41 +343,38 @@ static s32 goodix_tool_write(struct file *filp, const char __user *buff,
|
|||
{
|
||||
s32 ret = 0;
|
||||
|
||||
GTP_DEBUG_FUNC();
|
||||
GTP_DEBUG_ARRAY((u8 *)buff, len);
|
||||
|
||||
mutex_lock(&lock);
|
||||
ret = copy_from_user(&cmd_head, buff, CMD_HEAD_LENGTH);
|
||||
if (ret) {
|
||||
GTP_ERROR("copy_from_user failed.");
|
||||
pr_err("copy_from_user failed.\n");
|
||||
ret = -EACCES;
|
||||
goto exit;
|
||||
}
|
||||
|
||||
GTP_DEBUG("wr :0x%02x.", cmd_head.wr);
|
||||
GTP_DEBUG("flag:0x%02x.", cmd_head.flag);
|
||||
GTP_DEBUG("flag addr:0x%02x%02x.", cmd_head.flag_addr[0],
|
||||
pr_debug("wr :0x%02x.\n", cmd_head.wr);
|
||||
pr_debug("flag:0x%02x.\n", cmd_head.flag);
|
||||
pr_debug("flag addr:0x%02x%02x.\n", cmd_head.flag_addr[0],
|
||||
cmd_head.flag_addr[1]);
|
||||
GTP_DEBUG("flag val:0x%02x.", cmd_head.flag_val);
|
||||
GTP_DEBUG("flag rel:0x%02x.", cmd_head.flag_relation);
|
||||
GTP_DEBUG("circle :%d.", (s32)cmd_head.circle);
|
||||
GTP_DEBUG("times :%d.", (s32)cmd_head.times);
|
||||
GTP_DEBUG("retry :%d.", (s32)cmd_head.retry);
|
||||
GTP_DEBUG("delay :%d.", (s32)cmd_head.delay);
|
||||
GTP_DEBUG("data len:%d.", (s32)cmd_head.data_len);
|
||||
GTP_DEBUG("addr len:%d.", (s32)cmd_head.addr_len);
|
||||
GTP_DEBUG("addr:0x%02x%02x.", cmd_head.addr[0], cmd_head.addr[1]);
|
||||
GTP_DEBUG("len:%d.", (s32)len);
|
||||
GTP_DEBUG("buf[20]:0x%02x.", buff[CMD_HEAD_LENGTH]);
|
||||
pr_debug("flag val:0x%02x.\n", cmd_head.flag_val);
|
||||
pr_debug("flag rel:0x%02x.\n", cmd_head.flag_relation);
|
||||
pr_debug("circle :%d.\n", (s32)cmd_head.circle);
|
||||
pr_debug("times :%d.\n", (s32)cmd_head.times);
|
||||
pr_debug("retry :%d.\n", (s32)cmd_head.retry);
|
||||
pr_debug("delay :%d.\n", (s32)cmd_head.delay);
|
||||
pr_debug("data len:%d.\n", (s32)cmd_head.data_len);
|
||||
pr_debug("addr len:%d.\n", (s32)cmd_head.addr_len);
|
||||
pr_debug("addr:0x%02x%02x.\n", cmd_head.addr[0], cmd_head.addr[1]);
|
||||
pr_debug("len:%d.\n", (s32)len);
|
||||
pr_debug("buf[20]:0x%02x.\n", buff[CMD_HEAD_LENGTH]);
|
||||
|
||||
if (cmd_head.data_len > (DATA_LENGTH - GTP_ADDR_LENGTH)) {
|
||||
pr_err("data len %d > data buff %d, rejected!\n",
|
||||
pr_debug("data len %d > data buff %d, rejected!\n",
|
||||
cmd_head.data_len, (DATA_LENGTH - GTP_ADDR_LENGTH));
|
||||
ret = -EINVAL;
|
||||
goto exit;
|
||||
}
|
||||
if (cmd_head.addr_len > GTP_ADDR_LENGTH) {
|
||||
pr_err(" addr len %d > data buff %d, rejected!\n",
|
||||
pr_debug(" addr len %d > data buff %d, rejected!\n",
|
||||
cmd_head.addr_len, GTP_ADDR_LENGTH);
|
||||
ret = -EINVAL;
|
||||
goto exit;
|
||||
|
@ -391,19 +387,14 @@ static s32 goodix_tool_write(struct file *filp, const char __user *buff,
|
|||
ret = copy_from_user(&cmd_head.data[GTP_ADDR_LENGTH],
|
||||
&buff[CMD_HEAD_LENGTH], cmd_head.data_len);
|
||||
if (ret)
|
||||
GTP_ERROR("copy_from_user failed.");
|
||||
pr_err("copy_from_user failed.\n");
|
||||
|
||||
memcpy(&cmd_head.data[GTP_ADDR_LENGTH - cmd_head.addr_len],
|
||||
cmd_head.addr, cmd_head.addr_len);
|
||||
|
||||
GTP_DEBUG_ARRAY(cmd_head.data,
|
||||
cmd_head.data_len + cmd_head.addr_len);
|
||||
GTP_DEBUG_ARRAY((u8 *)&buff[CMD_HEAD_LENGTH],
|
||||
cmd_head.data_len);
|
||||
|
||||
if (cmd_head.flag == 1) {
|
||||
if (comfirm() == FAIL) {
|
||||
GTP_ERROR("[WRITE]Comfirm fail!");
|
||||
pr_err("[WRITE]Comfirm fail!\n");
|
||||
ret = -EINVAL;
|
||||
goto exit;
|
||||
}
|
||||
|
@ -413,14 +404,11 @@ static s32 goodix_tool_write(struct file *filp, const char __user *buff,
|
|||
if (tool_i2c_write(
|
||||
&cmd_head.data[GTP_ADDR_LENGTH - cmd_head.addr_len],
|
||||
cmd_head.data_len + cmd_head.addr_len) <= 0) {
|
||||
GTP_ERROR("[WRITE]Write data failed!");
|
||||
pr_err("[WRITE]Write data failed!\n");
|
||||
ret = -EIO;
|
||||
goto exit;
|
||||
}
|
||||
|
||||
GTP_DEBUG_ARRAY(
|
||||
&cmd_head.data[GTP_ADDR_LENGTH - cmd_head.addr_len],
|
||||
cmd_head.data_len + cmd_head.addr_len);
|
||||
if (cmd_head.delay)
|
||||
msleep(cmd_head.delay);
|
||||
|
||||
|
@ -431,10 +419,10 @@ static s32 goodix_tool_write(struct file *filp, const char __user *buff,
|
|||
ret = copy_from_user(&cmd_head.data[0], &buff[CMD_HEAD_LENGTH],
|
||||
cmd_head.data_len);
|
||||
if (ret)
|
||||
GTP_ERROR("copy_from_user failed.");
|
||||
pr_err("copy_from_user failed.\n");
|
||||
|
||||
if (cmd_head.data_len > sizeof(IC_TYPE)) {
|
||||
pr_err("<<-GTP->> data len %d > data buff %d, rejected!\n",
|
||||
pr_debug("<<-GTP->> data len %d > data buff %d, rejected!\n",
|
||||
cmd_head.data_len, sizeof(IC_TYPE));
|
||||
ret = -EINVAL;
|
||||
goto exit;
|
||||
|
@ -473,13 +461,13 @@ static s32 goodix_tool_write(struct file *filp, const char __user *buff,
|
|||
ret = copy_from_user(&cmd_head.data[GTP_ADDR_LENGTH],
|
||||
&buff[CMD_HEAD_LENGTH], cmd_head.data_len);
|
||||
if (ret)
|
||||
GTP_DEBUG("copy_from_user failed.");
|
||||
pr_debug("copy_from_user failed.\n");
|
||||
if (cmd_head.data[GTP_ADDR_LENGTH]) {
|
||||
GTP_DEBUG("gtp enter rawdiff.");
|
||||
pr_debug("gtp enter rawdiff.\n");
|
||||
ts->gtp_rawdiff_mode = true;
|
||||
} else {
|
||||
ts->gtp_rawdiff_mode = false;
|
||||
GTP_DEBUG("gtp leave rawdiff.");
|
||||
pr_debug("gtp leave rawdiff.\n");
|
||||
}
|
||||
ret = CMD_HEAD_LENGTH;
|
||||
goto exit;
|
||||
|
@ -495,7 +483,7 @@ static s32 goodix_tool_write(struct file *filp, const char __user *buff,
|
|||
show_len = 0;
|
||||
total_len = 0;
|
||||
if (cmd_head.data_len + 1 > DATA_LENGTH) {
|
||||
pr_err("<<-GTP->> data len %d > data buff %d, rejected!\n",
|
||||
pr_debug("<<-GTP->> data len %d > data buff %d, rejected!\n",
|
||||
cmd_head.data_len + 1, DATA_LENGTH);
|
||||
ret = -EINVAL;
|
||||
goto exit;
|
||||
|
@ -530,7 +518,6 @@ static s32 goodix_tool_read(char *page, char **start, off_t off, int count,
|
|||
int *eof, void *data)
|
||||
{
|
||||
s32 ret;
|
||||
GTP_DEBUG_FUNC();
|
||||
|
||||
mutex_lock(&lock);
|
||||
if (cmd_head.wr % 2) {
|
||||
|
@ -544,7 +531,7 @@ static s32 goodix_tool_read(char *page, char **start, off_t off, int count,
|
|||
|
||||
if (cmd_head.flag == 1) {
|
||||
if (comfirm() == FAIL) {
|
||||
GTP_ERROR("[READ]Comfirm fail!");
|
||||
pr_err("[READ]Comfirm fail!\n");
|
||||
ret = -EINVAL;
|
||||
goto exit;
|
||||
}
|
||||
|
@ -554,9 +541,9 @@ static s32 goodix_tool_read(char *page, char **start, off_t off, int count,
|
|||
|
||||
memcpy(cmd_head.data, cmd_head.addr, cmd_head.addr_len);
|
||||
|
||||
GTP_DEBUG("[CMD HEAD DATA] ADDR:0x%02x%02x.", cmd_head.data[0],
|
||||
pr_debug("[CMD HEAD DATA] ADDR:0x%02x%02x.\n", cmd_head.data[0],
|
||||
cmd_head.data[1]);
|
||||
GTP_DEBUG("[CMD HEAD ADDR] ADDR:0x%02x%02x.", cmd_head.addr[0],
|
||||
pr_debug("[CMD HEAD ADDR] ADDR:0x%02x%02x.\n", cmd_head.addr[0],
|
||||
cmd_head.addr[1]);
|
||||
|
||||
if (cmd_head.delay)
|
||||
|
@ -572,16 +559,13 @@ static s32 goodix_tool_read(char *page, char **start, off_t off, int count,
|
|||
data_len -= len;
|
||||
|
||||
if (tool_i2c_read(cmd_head.data, len) <= 0) {
|
||||
GTP_ERROR("[READ]Read data failed!");
|
||||
pr_err("[READ]Read data failed!\n");
|
||||
ret = -EINVAL;
|
||||
goto exit;
|
||||
}
|
||||
memcpy(&page[loc], &cmd_head.data[GTP_ADDR_LENGTH],
|
||||
len);
|
||||
loc += len;
|
||||
|
||||
GTP_DEBUG_ARRAY(&cmd_head.data[GTP_ADDR_LENGTH], len);
|
||||
GTP_DEBUG_ARRAY(page, len);
|
||||
}
|
||||
} else if (cmd_head.wr == 2) {
|
||||
/* memcpy(page, "gt8", cmd_head.data_len);
|
||||
|
@ -589,7 +573,7 @@ static s32 goodix_tool_read(char *page, char **start, off_t off, int count,
|
|||
* page[5] = 0;
|
||||
*/
|
||||
|
||||
GTP_DEBUG("Return ic type:%s len:%d.", page,
|
||||
pr_debug("Return ic type:%s len:%d.\n", page,
|
||||
(s32)cmd_head.data_len);
|
||||
ret = cmd_head.data_len;
|
||||
goto exit;
|
||||
|
|
|
@ -77,19 +77,13 @@
|
|||
#if GTP_HAVE_TOUCH_KEY
|
||||
static const u16 touch_key_array[] = {KEY_MENU, KEY_HOMEPAGE, KEY_BACK};
|
||||
|
||||
#if GTP_DEBUG_ON
|
||||
static const int key_codes[] = {
|
||||
KEY_HOME, KEY_BACK, KEY_MENU, KEY_SEARCH
|
||||
};
|
||||
static const char *const key_names[] = {
|
||||
"Key_Home", "Key_Back", "Key_Menu", "Key_Search"
|
||||
};
|
||||
#endif
|
||||
#endif
|
||||
|
||||
static void gtp_reset_guitar(struct goodix_ts_data *ts, int ms);
|
||||
static void gtp_int_sync(struct goodix_ts_data *ts, int ms);
|
||||
static int gtp_i2c_test(struct i2c_client *client);
|
||||
static int goodix_power_off(struct goodix_ts_data *ts);
|
||||
static int goodix_power_on(struct goodix_ts_data *ts);
|
||||
|
||||
#if defined(CONFIG_FB)
|
||||
static int fb_notifier_callback(struct notifier_block *self,
|
||||
|
@ -493,30 +487,19 @@ static void goodix_ts_work_func(struct work_struct *work)
|
|||
memcpy(&point_data[12], &buf[2], 8 * (touch_num - 1));
|
||||
}
|
||||
|
||||
#if GTP_HAVE_TOUCH_KEY
|
||||
|
||||
key_value = point_data[3 + 8 * touch_num];
|
||||
|
||||
if (key_value || pre_key) {
|
||||
for (i = 0; i < ARRAY_SIZE(touch_key_array); i++) {
|
||||
#if GTP_DEBUG_ON
|
||||
for (ret = 0; ret < 4; ++ret) {
|
||||
if (key_codes[ret] == touch_key_array[i]) {
|
||||
GTP_DEBUG("Key: %s %s",
|
||||
key_names[ret],
|
||||
(key_value & (0x01 << i))
|
||||
? "Down" : "Up");
|
||||
break;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
for (i = 0; i < ts->pdata->num_button; i++) {
|
||||
input_report_key(ts->input_dev,
|
||||
touch_key_array[i], key_value & (0x01<<i));
|
||||
ts->pdata->button_map[i],
|
||||
key_value & (0x01<<i));
|
||||
}
|
||||
touch_num = 0;
|
||||
pre_touch = 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
pre_key = key_value;
|
||||
|
||||
#if GTP_WITH_PEN
|
||||
|
@ -754,7 +737,7 @@ Input:
|
|||
ts: private data.
|
||||
Output:
|
||||
Executive outcomes.
|
||||
1: succeed, otherwise failed.
|
||||
>0: succeed, otherwise failed.
|
||||
*******************************************************/
|
||||
static s8 gtp_enter_sleep(struct goodix_ts_data *ts)
|
||||
{
|
||||
|
@ -765,12 +748,28 @@ static s8 gtp_enter_sleep(struct goodix_ts_data *ts)
|
|||
(u8)GTP_REG_SLEEP, 5};
|
||||
|
||||
ret = gpio_direction_output(ts->pdata->irq_gpio, 0);
|
||||
if (ret)
|
||||
dev_err(&ts->client->dev,
|
||||
"GTP sleep: Cannot reconfig gpio %d.\n",
|
||||
ts->pdata->irq_gpio);
|
||||
if (ts->pdata->enable_power_off) {
|
||||
ret = gpio_direction_output(ts->pdata->reset_gpio, 0);
|
||||
if (ret)
|
||||
dev_err(&ts->client->dev,
|
||||
"GTP sleep: Cannot reconfig gpio %d.\n",
|
||||
ts->pdata->reset_gpio);
|
||||
ret = goodix_power_off(ts);
|
||||
if (ret) {
|
||||
dev_err(&ts->client->dev, "GTP power off failed.\n");
|
||||
return 0;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
usleep(5000);
|
||||
while (retry++ < GTP_I2C_RETRY_5) {
|
||||
ret = gtp_i2c_write(ts->client, i2c_control_buf, 3);
|
||||
if (ret > 0) {
|
||||
dev_dbg(&ts->client->dev,
|
||||
"GTP enter sleep!");
|
||||
if (ret == 1) {
|
||||
dev_dbg(&ts->client->dev, "GTP enter sleep!");
|
||||
return ret;
|
||||
}
|
||||
msleep(20);
|
||||
|
@ -778,7 +777,7 @@ static s8 gtp_enter_sleep(struct goodix_ts_data *ts)
|
|||
dev_err(&ts->client->dev, "GTP send sleep cmd failed.\n");
|
||||
return ret;
|
||||
}
|
||||
#endif
|
||||
#endif /* !GTP_SLIDE_WAKEUP */
|
||||
|
||||
/*******************************************************
|
||||
Function:
|
||||
|
@ -794,17 +793,36 @@ static s8 gtp_wakeup_sleep(struct goodix_ts_data *ts)
|
|||
u8 retry = 0;
|
||||
s8 ret = -1;
|
||||
|
||||
#if GTP_POWER_CTRL_SLEEP
|
||||
gtp_reset_guitar(ts, 20);
|
||||
if (ts->pdata->enable_power_off) {
|
||||
ret = gpio_direction_output(ts->pdata->irq_gpio, 0);
|
||||
if (ret)
|
||||
dev_err(&ts->client->dev,
|
||||
"GTP wakeup: Cannot reconfig gpio %d.\n",
|
||||
ts->pdata->irq_gpio);
|
||||
ret = gpio_direction_output(ts->pdata->reset_gpio, 0);
|
||||
if (ret)
|
||||
dev_err(&ts->client->dev,
|
||||
"GTP wakeup: Cannot reconfig gpio %d.\n",
|
||||
ts->pdata->reset_gpio);
|
||||
ret = goodix_power_on(ts);
|
||||
if (ret) {
|
||||
dev_err(&ts->client->dev, "GTP power on failed.\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
gtp_reset_guitar(ts, 20);
|
||||
|
||||
ret = gtp_send_cfg(ts);
|
||||
if (ret <= 0) {
|
||||
dev_err(&ts->client->dev,
|
||||
"GTP wakeup sleep failed.\n");
|
||||
return ret;
|
||||
}
|
||||
|
||||
ret = gtp_send_cfg(ts);
|
||||
if (ret > 0) {
|
||||
dev_dbg(&ts->client->dev,
|
||||
"Wakeup sleep send config success.");
|
||||
return 1;
|
||||
}
|
||||
#else
|
||||
while (retry++ < GTP_I2C_RETRY_10) {
|
||||
"Wakeup sleep send config success.");
|
||||
} else {
|
||||
err_retry:
|
||||
#if GTP_SLIDE_WAKEUP
|
||||
/* wakeup not by slide */
|
||||
if (doze_status != DOZE_WAKEUP)
|
||||
|
@ -821,7 +839,7 @@ static s8 gtp_wakeup_sleep(struct goodix_ts_data *ts)
|
|||
}
|
||||
#endif
|
||||
ret = gtp_i2c_test(ts->client);
|
||||
if (ret > 0) {
|
||||
if (ret == 2) {
|
||||
dev_dbg(&ts->client->dev, "GTP wakeup sleep.");
|
||||
#if (!GTP_SLIDE_WAKEUP)
|
||||
if (chip_gt9xxs == 0) {
|
||||
|
@ -835,10 +853,10 @@ static s8 gtp_wakeup_sleep(struct goodix_ts_data *ts)
|
|||
return ret;
|
||||
}
|
||||
gtp_reset_guitar(ts, 20);
|
||||
if (retry++ < GTP_I2C_RETRY_10)
|
||||
goto err_retry;
|
||||
dev_err(&ts->client->dev, "GTP wakeup sleep failed.\n");
|
||||
}
|
||||
#endif
|
||||
|
||||
dev_err(&ts->client->dev, "GTP wakeup sleep failed.\n");
|
||||
return ret;
|
||||
}
|
||||
#endif /* !CONFIG_HAS_EARLYSUSPEND && !CONFIG_FB*/
|
||||
|
@ -1051,9 +1069,7 @@ static int gtp_check_product_id(struct i2c_client *client)
|
|||
|
||||
dev_info(&client->dev, "Goodix Product ID = %s\n", product_id);
|
||||
|
||||
if (!IS_ERR(ts->pdata->product_id))
|
||||
ret = strcmp(product_id, ts->pdata->product_id);
|
||||
|
||||
ret = strcmp(product_id, ts->pdata->product_id);
|
||||
if (ret != 0)
|
||||
return -EINVAL;
|
||||
|
||||
|
@ -1232,12 +1248,11 @@ static int gtp_request_input_dev(struct goodix_ts_data *ts)
|
|||
/* in case of "out of memory" */
|
||||
input_mt_init_slots(ts->input_dev, 10, 0);
|
||||
|
||||
#if GTP_HAVE_TOUCH_KEY
|
||||
for (index = 0; index < ARRAY_SIZE(touch_key_array); index++) {
|
||||
for (index = 0; index < ts->pdata->num_button; index++) {
|
||||
input_set_capability(ts->input_dev,
|
||||
EV_KEY, touch_key_array[index]);
|
||||
EV_KEY, ts->pdata->button_map[index]);
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
#if GTP_SLIDE_WAKEUP
|
||||
input_set_capability(ts->input_dev, EV_KEY, KEY_POWER);
|
||||
|
@ -1305,6 +1320,12 @@ static int goodix_power_on(struct goodix_ts_data *ts)
|
|||
{
|
||||
int ret;
|
||||
|
||||
if (ts->power_on) {
|
||||
dev_info(&ts->client->dev,
|
||||
"Device already power on\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!IS_ERR(ts->avdd)) {
|
||||
ret = reg_set_optimum_mode_check(ts->avdd,
|
||||
GOODIX_VDD_LOAD_MAX_UA);
|
||||
|
@ -1371,6 +1392,7 @@ static int goodix_power_on(struct goodix_ts_data *ts)
|
|||
}
|
||||
}
|
||||
|
||||
ts->power_on = true;
|
||||
return 0;
|
||||
|
||||
err_enable_vcc_i2c:
|
||||
|
@ -1389,6 +1411,7 @@ err_set_vtg_vdd:
|
|||
regulator_disable(ts->avdd);
|
||||
err_enable_avdd:
|
||||
err_set_opt_avdd:
|
||||
ts->power_on = false;
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
@ -1402,6 +1425,12 @@ static int goodix_power_off(struct goodix_ts_data *ts)
|
|||
{
|
||||
int ret;
|
||||
|
||||
if (!ts->power_on) {
|
||||
dev_info(&ts->client->dev,
|
||||
"Device already power off\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!IS_ERR(ts->vcc_i2c)) {
|
||||
ret = regulator_set_voltage(ts->vcc_i2c, 0,
|
||||
GOODIX_I2C_VTG_MAX_UV);
|
||||
|
@ -1434,6 +1463,7 @@ static int goodix_power_off(struct goodix_ts_data *ts)
|
|||
"Regulator avdd disable failed ret=%d\n", ret);
|
||||
}
|
||||
|
||||
ts->power_on = false;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -1486,6 +1516,50 @@ static int goodix_power_deinit(struct goodix_ts_data *ts)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static ssize_t gtp_fw_name_show(struct device *dev,
|
||||
struct device_attribute *attr, char *buf)
|
||||
{
|
||||
struct goodix_ts_data *ts = dev_get_drvdata(dev);
|
||||
|
||||
if (!strlen(ts->fw_name))
|
||||
return snprintf(buf, GTP_FW_NAME_MAXSIZE - 1,
|
||||
"No fw name has been given.");
|
||||
else
|
||||
return snprintf(buf, GTP_FW_NAME_MAXSIZE - 1,
|
||||
"%s\n", ts->fw_name);
|
||||
}
|
||||
|
||||
static ssize_t gtp_fw_name_store(struct device *dev,
|
||||
struct device_attribute *attr,
|
||||
const char *buf, size_t size)
|
||||
{
|
||||
struct goodix_ts_data *ts = dev_get_drvdata(dev);
|
||||
|
||||
if (size > GTP_FW_NAME_MAXSIZE - 1) {
|
||||
dev_err(dev, "FW name size exceeds the limit.");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
strlcpy(ts->fw_name, buf, size);
|
||||
if (ts->fw_name[size-1] == '\n')
|
||||
ts->fw_name[size-1] = '\0';
|
||||
|
||||
return size;
|
||||
}
|
||||
|
||||
static DEVICE_ATTR(fw_name, (S_IRUGO | S_IWUSR | S_IWGRP),
|
||||
gtp_fw_name_show,
|
||||
gtp_fw_name_store);
|
||||
|
||||
static struct attribute *gtp_attrs[] = {
|
||||
&dev_attr_fw_name.attr,
|
||||
NULL
|
||||
};
|
||||
|
||||
static const struct attribute_group gtp_attr_grp = {
|
||||
.attrs = gtp_attrs,
|
||||
};
|
||||
|
||||
static int goodix_ts_get_dt_coords(struct device *dev, char *name,
|
||||
struct goodix_ts_platform_data *pdata)
|
||||
{
|
||||
|
@ -1549,6 +1623,9 @@ static int goodix_parse_dt(struct device *dev,
|
|||
|
||||
pdata->no_force_update = of_property_read_bool(np,
|
||||
"goodix,no-force-update");
|
||||
|
||||
pdata->enable_power_off = of_property_read_bool(np,
|
||||
"goodix,enable-power-off");
|
||||
/* reset, irq gpio info */
|
||||
pdata->reset_gpio = of_get_named_gpio_flags(np, "reset-gpios",
|
||||
0, &pdata->reset_gpio_flags);
|
||||
|
@ -1562,8 +1639,17 @@ static int goodix_parse_dt(struct device *dev,
|
|||
|
||||
rc = of_property_read_string(np, "goodix,product-id",
|
||||
&pdata->product_id);
|
||||
if (rc < 0 || strlen(pdata->product_id) > GTP_PRODUCT_ID_MAXSIZE)
|
||||
return rc;
|
||||
if (rc && (rc != -EINVAL)) {
|
||||
dev_err(dev, "Failed to parse product_id.");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
rc = of_property_read_string(np, "goodix,fw_name",
|
||||
&pdata->fw_name);
|
||||
if (rc && (rc != -EINVAL)) {
|
||||
dev_err(dev, "Failed to parse firmware name.\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
prop = of_find_property(np, "goodix,button-map", NULL);
|
||||
if (prop) {
|
||||
|
@ -1578,6 +1664,9 @@ static int goodix_parse_dt(struct device *dev,
|
|||
dev_err(dev, "Unable to read key codes\n");
|
||||
return rc;
|
||||
}
|
||||
pdata->num_button = num_buttons;
|
||||
memcpy(pdata->button_map, button_map,
|
||||
pdata->num_button * sizeof(u32));
|
||||
}
|
||||
|
||||
read_cfg_num = 0;
|
||||
|
@ -1670,6 +1759,7 @@ static int goodix_ts_probe(struct i2c_client *client,
|
|||
spin_lock_init(&ts->irq_lock);
|
||||
i2c_set_clientdata(client, ts);
|
||||
ts->gtp_rawdiff_mode = 0;
|
||||
ts->power_on = false;
|
||||
|
||||
ret = gtp_request_io_port(ts);
|
||||
if (ret) {
|
||||
|
@ -1697,12 +1787,16 @@ static int goodix_ts_probe(struct i2c_client *client,
|
|||
goto exit_power_off;
|
||||
}
|
||||
|
||||
if (pdata->fw_name)
|
||||
strlcpy(ts->fw_name, pdata->fw_name,
|
||||
strlen(pdata->fw_name) + 1);
|
||||
|
||||
#if GTP_AUTO_UPDATE
|
||||
ret = gup_init_update_proc(ts);
|
||||
if (ret < 0) {
|
||||
dev_err(&client->dev,
|
||||
"GTP Create firmware update thread error.\n");
|
||||
goto exit_free_io_port;
|
||||
goto exit_power_off;
|
||||
}
|
||||
#endif
|
||||
|
||||
|
@ -1719,7 +1813,9 @@ static int goodix_ts_probe(struct i2c_client *client,
|
|||
dev_err(&client->dev, "GTP request input dev failed.\n");
|
||||
goto exit_free_inputdev;
|
||||
}
|
||||
input_set_drvdata(ts->input_dev, ts);
|
||||
|
||||
mutex_init(&ts->lock);
|
||||
#if defined(CONFIG_FB)
|
||||
ts->fb_notif.notifier_call = fb_notifier_callback;
|
||||
ret = fb_register_client(&ts->fb_notif);
|
||||
|
@ -1762,9 +1858,16 @@ static int goodix_ts_probe(struct i2c_client *client,
|
|||
#if GTP_ESD_PROTECT
|
||||
gtp_esd_switch(client, SWITCH_ON);
|
||||
#endif
|
||||
ret = sysfs_create_group(&client->dev.kobj, >p_attr_grp);
|
||||
if (ret < 0) {
|
||||
dev_err(&client->dev, "sys file creation failed.\n");
|
||||
goto exit_free_irq;
|
||||
}
|
||||
|
||||
init_done = true;
|
||||
return 0;
|
||||
exit_free_irq:
|
||||
mutex_destroy(&ts->lock);
|
||||
#if defined(CONFIG_FB)
|
||||
if (fb_unregister_client(&ts->fb_notif))
|
||||
dev_err(&client->dev,
|
||||
|
@ -1813,6 +1916,8 @@ static int goodix_ts_remove(struct i2c_client *client)
|
|||
{
|
||||
struct goodix_ts_data *ts = i2c_get_clientdata(client);
|
||||
|
||||
sysfs_remove_group(&ts->input_dev->dev.kobj, >p_attr_grp);
|
||||
|
||||
#if defined(CONFIG_FB)
|
||||
if (fb_unregister_client(&ts->fb_notif))
|
||||
dev_err(&client->dev,
|
||||
|
@ -1820,6 +1925,7 @@ static int goodix_ts_remove(struct i2c_client *client)
|
|||
#elif defined(CONFIG_HAS_EARLYSUSPEND)
|
||||
unregister_early_suspend(&ts->early_suspend);
|
||||
#endif
|
||||
mutex_destroy(&ts->lock);
|
||||
|
||||
#if GTP_CREATE_WR_NODE
|
||||
uninit_wr_node();
|
||||
|
@ -1873,6 +1979,7 @@ static void goodix_ts_suspend(struct goodix_ts_data *ts)
|
|||
{
|
||||
int ret = -1, i;
|
||||
|
||||
mutex_lock(&ts->lock);
|
||||
#if GTP_ESD_PROTECT
|
||||
ts->gtp_is_suspend = 1;
|
||||
gtp_esd_switch(ts->client, SWITCH_OFF);
|
||||
|
@ -1893,12 +2000,13 @@ static void goodix_ts_suspend(struct goodix_ts_data *ts)
|
|||
|
||||
ret = gtp_enter_sleep(ts);
|
||||
#endif
|
||||
if (ret < 0)
|
||||
if (ret <= 0)
|
||||
dev_err(&ts->client->dev, "GTP early suspend failed.\n");
|
||||
/* to avoid waking up while not sleeping,
|
||||
* delay 48 + 10ms to ensure reliability
|
||||
*/
|
||||
msleep(58);
|
||||
mutex_unlock(&ts->lock);
|
||||
}
|
||||
|
||||
/*******************************************************
|
||||
|
@ -1913,13 +2021,14 @@ static void goodix_ts_resume(struct goodix_ts_data *ts)
|
|||
{
|
||||
int ret = -1;
|
||||
|
||||
mutex_lock(&ts->lock);
|
||||
ret = gtp_wakeup_sleep(ts);
|
||||
|
||||
#if GTP_SLIDE_WAKEUP
|
||||
doze_status = DOZE_DISABLED;
|
||||
#endif
|
||||
|
||||
if (ret < 0)
|
||||
if (ret <= 0)
|
||||
dev_err(&ts->client->dev, "GTP resume failed.\n");
|
||||
|
||||
if (ts->use_irq)
|
||||
|
@ -1932,6 +2041,7 @@ static void goodix_ts_resume(struct goodix_ts_data *ts)
|
|||
ts->gtp_is_suspend = 0;
|
||||
gtp_esd_switch(ts->client, SWITCH_ON);
|
||||
#endif
|
||||
mutex_unlock(&ts->lock);
|
||||
}
|
||||
|
||||
#if defined(CONFIG_FB)
|
||||
|
@ -2177,7 +2287,7 @@ static void __exit goodix_ts_exit(void)
|
|||
i2c_del_driver(&goodix_ts_driver);
|
||||
}
|
||||
|
||||
late_initcall(goodix_ts_init);
|
||||
module_init(goodix_ts_init);
|
||||
module_exit(goodix_ts_exit);
|
||||
|
||||
MODULE_DESCRIPTION("GTP Series Driver");
|
||||
|
|
|
@ -33,6 +33,7 @@
|
|||
#include <linux/regulator/consumer.h>
|
||||
#include <linux/firmware.h>
|
||||
#include <linux/debugfs.h>
|
||||
#include <linux/mutex.h>
|
||||
|
||||
#if defined(CONFIG_FB)
|
||||
#include <linux/notifier.h>
|
||||
|
@ -42,13 +43,17 @@
|
|||
#define GOODIX_SUSPEND_LEVEL 1
|
||||
#endif
|
||||
|
||||
#define MAX_BUTTONS 4
|
||||
#define GOODIX_MAX_CFG_GROUP 6
|
||||
#define GTP_FW_NAME_MAXSIZE 50
|
||||
|
||||
struct goodix_ts_platform_data {
|
||||
int irq_gpio;
|
||||
u32 irq_gpio_flags;
|
||||
int reset_gpio;
|
||||
u32 reset_gpio_flags;
|
||||
const char *product_id;
|
||||
const char *fw_name;
|
||||
u32 x_max;
|
||||
u32 y_max;
|
||||
u32 x_min;
|
||||
|
@ -59,8 +64,11 @@ struct goodix_ts_platform_data {
|
|||
u32 panel_maxy;
|
||||
bool no_force_update;
|
||||
bool i2c_pull_up;
|
||||
bool enable_power_off;
|
||||
size_t config_data_len[GOODIX_MAX_CFG_GROUP];
|
||||
u8 *config_data[GOODIX_MAX_CFG_GROUP];
|
||||
u32 button_map[MAX_BUTTONS];
|
||||
u8 num_button;
|
||||
};
|
||||
struct goodix_ts_data {
|
||||
spinlock_t irq_lock;
|
||||
|
@ -70,6 +78,7 @@ struct goodix_ts_data {
|
|||
struct hrtimer timer;
|
||||
struct workqueue_struct *goodix_wq;
|
||||
struct work_struct work;
|
||||
struct delayed_work goodix_update_work;
|
||||
s32 irq_is_disabled;
|
||||
s32 use_irq;
|
||||
u16 abs_x_max;
|
||||
|
@ -86,6 +95,8 @@ struct goodix_ts_data {
|
|||
u8 fixed_cfg;
|
||||
u8 esd_running;
|
||||
u8 fw_error;
|
||||
bool power_on;
|
||||
struct mutex lock;
|
||||
struct regulator *avdd;
|
||||
struct regulator *vdd;
|
||||
struct regulator *vcc_i2c;
|
||||
|
@ -104,7 +115,6 @@ extern u16 total_len;
|
|||
#define GTP_CHANGE_X2Y 0
|
||||
#define GTP_DRIVER_SEND_CFG 1
|
||||
#define GTP_HAVE_TOUCH_KEY 1
|
||||
#define GTP_POWER_CTRL_SLEEP 0
|
||||
|
||||
/* auto updated by .bin file as default */
|
||||
#define GTP_AUTO_UPDATE 0
|
||||
|
@ -117,14 +127,11 @@ extern u16 total_len;
|
|||
#define GTP_ESD_PROTECT 0
|
||||
#define GTP_WITH_PEN 0
|
||||
|
||||
/* This cannot work when enable-power-off is on */
|
||||
#define GTP_SLIDE_WAKEUP 0
|
||||
/* double-click wakeup, function together with GTP_SLIDE_WAKEUP */
|
||||
#define GTP_DBL_CLK_WAKEUP 0
|
||||
|
||||
#define GTP_DEBUG_ON 0
|
||||
#define GTP_DEBUG_ARRAY_ON 0
|
||||
#define GTP_DEBUG_FUNC_ON 0
|
||||
|
||||
/*************************** PART2:TODO define *******************************/
|
||||
/* STEP_1(REQUIRED): Define Configuration Information Group(s) */
|
||||
/* Sensor_ID Map: */
|
||||
|
@ -190,39 +197,6 @@ extern u16 total_len;
|
|||
#define RESOLUTION_LOC 3
|
||||
#define TRIGGER_LOC 8
|
||||
|
||||
/* Log define */
|
||||
#define GTP_DEBUG(fmt, arg...) do {\
|
||||
if (GTP_DEBUG_ON) {\
|
||||
pr_debug("<<-GTP-DEBUG->> [%d]"fmt"\n",\
|
||||
__LINE__, ##arg); } \
|
||||
} while (0)
|
||||
|
||||
#define GTP_DEBUG_ARRAY(array, num) do {\
|
||||
s32 i; \
|
||||
u8 *a = array; \
|
||||
if (GTP_DEBUG_ARRAY_ON) {\
|
||||
pr_debug("<<-GTP-DEBUG-ARRAY->>\n");\
|
||||
for (i = 0; i < (num); i++) { \
|
||||
pr_debug("%02x ", (a)[i]);\
|
||||
if ((i + 1) % 10 == 0) { \
|
||||
pr_debug("\n");\
|
||||
} \
|
||||
} \
|
||||
pr_debug("\n");\
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
#define GTP_DEBUG_FUNC() do {\
|
||||
if (GTP_DEBUG_FUNC_ON)\
|
||||
pr_debug("<<-GTP-FUNC->> Func:%s@Line:%d\n",\
|
||||
__func__, __LINE__);\
|
||||
} while (0)
|
||||
|
||||
#define GTP_SWAP(x, y) do {\
|
||||
typeof(x) z = x;\
|
||||
x = y;\
|
||||
y = z;\
|
||||
} while (0)
|
||||
/*****************************End of Part III********************************/
|
||||
|
||||
void gtp_esd_switch(struct i2c_client *client, int on);
|
||||
|
|
File diff suppressed because it is too large
Load diff
Loading…
Add table
Reference in a new issue