diff --git a/drivers/input/touchscreen/nova_0flash_mmi/nt36xxx.c b/drivers/input/touchscreen/nova_0flash_mmi/nt36xxx.c index 8b18af7bce9e..27702b628e5d 100644 --- a/drivers/input/touchscreen/nova_0flash_mmi/nt36xxx.c +++ b/drivers/input/touchscreen/nova_0flash_mmi/nt36xxx.c @@ -1670,6 +1670,7 @@ static irqreturn_t nvt_ts_work_func(int irq, void *data) uint8_t input_id = 0; #if MT_PROTOCOL_B uint8_t press_id[TOUCH_MAX_FINGER_NUM] = {0}; + static uint8_t touchdown[TOUCH_MAX_FINGER_NUM]; #endif /* MT_PROTOCOL_B */ int32_t i = 0; int32_t finger_cnt = 0; @@ -1826,14 +1827,21 @@ static irqreturn_t nvt_ts_work_func(int irq, void *data) if (input_p == 0) input_p = 1; -#if MT_PROTOCOL_B press_id[input_id - 1] = 1; - input_mt_slot(ts->input_dev, input_id - 1); - input_mt_report_slot_state(ts->input_dev, MT_TOOL_FINGER, true); + /* log touch down event once */ + if (touchdown[input_id - 1] == 0) { +#if MT_PROTOCOL_B + ts->last_event_time = ktime_get(); + pr_debug("TOUCH: [%d] logged timestamp\n", input_id - 1); + touchdown[input_id - 1] = 1; + pr_debug("TOUCH: [%d] pressed (event %d)\n", input_id - 1, point_data[position] & 0x07); + input_mt_slot(ts->input_dev, input_id - 1); + input_mt_report_slot_state(ts->input_dev, MT_TOOL_FINGER, true); #else /* MT_PROTOCOL_B */ - input_report_abs(ts->input_dev, ABS_MT_TRACKING_ID, input_id - 1); - input_report_key(ts->input_dev, BTN_TOUCH, 1); + input_report_abs(ts->input_dev, ABS_MT_TRACKING_ID, input_id - 1); + input_report_key(ts->input_dev, BTN_TOUCH, 1); #endif /* MT_PROTOCOL_B */ + } #ifdef PALM_GESTURE if((point_data[position] & 0x07) == PALM_TOUCH) { //palm @@ -1868,7 +1876,7 @@ static irqreturn_t nvt_ts_work_func(int irq, void *data) #if MT_PROTOCOL_B for (i = 0; i < ts->max_touch_num; i++) { - if (press_id[i] != 1) { + if (!press_id[i] && touchdown[i]) { input_mt_slot(ts->input_dev, i); #ifdef PALM_GESTURE_RANGE input_report_abs(ts->input_dev, ABS_MT_TOUCH_MINOR, 0); @@ -1877,6 +1885,8 @@ static irqreturn_t nvt_ts_work_func(int irq, void *data) input_report_abs(ts->input_dev, ABS_MT_TOUCH_MAJOR, 0); input_report_abs(ts->input_dev, ABS_MT_PRESSURE, 0); input_mt_report_slot_state(ts->input_dev, MT_TOOL_FINGER, false); + touchdown[i] = 0; + pr_debug("TOUCH: [%d] release\n", i); } } diff --git a/drivers/input/touchscreen/nova_0flash_mmi/nt36xxx.h b/drivers/input/touchscreen/nova_0flash_mmi/nt36xxx.h index 6bd48f527752..f3d16f7a802b 100644 --- a/drivers/input/touchscreen/nova_0flash_mmi/nt36xxx.h +++ b/drivers/input/touchscreen/nova_0flash_mmi/nt36xxx.h @@ -24,6 +24,7 @@ #include #include #include +#include #include #ifdef NVT_SENSOR_EN @@ -279,6 +280,7 @@ struct nvt_ts_data { uint8_t edge_cmd[3]; /* /< edge switching command */ uint8_t rotate_cmd; /* /< rotate switching command */ bool edge_ctrl; /* /< edge rate switching */ + ktime_t last_event_time; }; #if NVT_TOUCH_PROC diff --git a/drivers/input/touchscreen/nova_0flash_mmi/nt36xxx_mmi_class.c b/drivers/input/touchscreen/nova_0flash_mmi/nt36xxx_mmi_class.c index 77fb2b3864db..a9e36c8f7de6 100644 --- a/drivers/input/touchscreen/nova_0flash_mmi/nt36xxx_mmi_class.c +++ b/drivers/input/touchscreen/nova_0flash_mmi/nt36xxx_mmi_class.c @@ -41,6 +41,8 @@ static ssize_t nvt_mmi_edge_store(struct device *dev, struct device_attribute *attr, const char *buf, size_t size); static ssize_t nvt_mmi_edge_show(struct device *dev, struct device_attribute *attr, char *buf); +static ssize_t nvt_mmi_timestamp_show(struct device *dev, + struct device_attribute *attr, char *buf); static DEVICE_ATTR(interpolation, (S_IRUGO | S_IWUSR | S_IWGRP), nvt_mmi_interpolation_show, nvt_mmi_interpolation_store); @@ -50,6 +52,7 @@ static DEVICE_ATTR(jitter, (S_IRUGO | S_IWUSR | S_IWGRP), nvt_mmi_jitter_show, nvt_mmi_jitter_store); static DEVICE_ATTR(edge, (S_IRUGO | S_IWUSR | S_IWGRP), nvt_mmi_edge_show, nvt_mmi_edge_store); +static DEVICE_ATTR(timestamp, S_IRUGO, nvt_mmi_timestamp_show, NULL); #define MAX_ATTRS_ENTRIES 10 #define UI_FEATURE_ENABLE 1 @@ -100,6 +103,8 @@ static int nvt_mmi_extend_attribute_group(struct device *dev, struct attribute_g if (ts->edge_ctrl) ADD_ATTR(edge); + ADD_ATTR(timestamp); + if (idx) { ext_attributes[idx] = NULL; *group = &ext_attr_group; @@ -189,6 +194,22 @@ static ssize_t nvt_mmi_interpolation_show(struct device *dev, return scnprintf(buf, PAGE_SIZE, "0x%02x\n", ts->interpolation_cmd[0]); } +static ssize_t nvt_mmi_timestamp_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + ktime_t last_ktime; + struct timespec64 last_ts; + + mutex_lock(&ts->lock); + last_ktime = ts->last_event_time; + ts->last_event_time = 0; + mutex_unlock(&ts->lock); + + last_ts = ktime_to_timespec64(last_ktime); + + return scnprintf(buf, PAGE_SIZE, "%lld.%ld\n", last_ts.tv_sec, last_ts.tv_nsec); +} + static ssize_t nvt_mmi_jitter_store(struct device *dev, struct device_attribute *attr, const char *buf, size_t size) {