diff options
author | PixelBot AutoMerger <android-nexus-securitybot@system.gserviceaccount.com> | 2022-07-03 18:28:04 -0700 |
---|---|---|
committer | Robin Peng <robinpeng@google.com> | 2022-07-06 03:07:21 +0000 |
commit | 591daad6521b8ae1ece4930bc63fb2eac40f85aa (patch) | |
tree | eec486c54435410386131a74437bf517ea05136d | |
parent | f03f25010d4e4d393561d74a4df1fb1b40c40261 (diff) | |
parent | b3e734863d475b878856d513179c96b152b0590d (diff) | |
download | focaltech_touch-591daad6521b8ae1ece4930bc63fb2eac40f85aa.tar.gz |
Merge android13-gs-pixel-5.10-tm-d1 into android13-gs-pixel-5.10-tm-qpr1
Bug: 233569354
SBMerger: 442815275
Change-Id: I9b852aa5a73f4f886f21b049019bce75e95e4113
Signed-off-by: SecurityBot <android-nexus-securitybot@system.gserviceaccount.com>
-rw-r--r-- | ft3658/focaltech_common.h | 4 | ||||
-rw-r--r-- | ft3658/focaltech_core.c | 95 | ||||
-rw-r--r-- | ft3658/focaltech_core.h | 25 | ||||
-rw-r--r-- | ft3658/focaltech_gesture.c | 106 |
4 files changed, 158 insertions, 72 deletions
diff --git a/ft3658/focaltech_common.h b/ft3658/focaltech_common.h index 4688d96..be4583f 100644 --- a/ft3658/focaltech_common.h +++ b/ft3658/focaltech_common.h @@ -151,6 +151,10 @@ #define FTS_PRESSURE_SCALE 85 // 255 / 3 #define FTS_CUSTOMER_STATUS_LEN 4 #define FTS_CUSTOMER_STATUS1_MASK 0x0F +#define FTS_ORIENTATION_SCALE 45 +#define FTS_GESTURE_ID_STTW 0x25 +#define FTS_GESTURE_ID_LPTW_DOWN 0x26 +#define FTS_GESTURE_ID_LPTW_UP 0x27 #define FTS_SYSFS_ECHO_ON(buf) (buf[0] == '1') #define FTS_SYSFS_ECHO_OFF(buf) (buf[0] == '0') diff --git a/ft3658/focaltech_core.c b/ft3658/focaltech_core.c index f982bd7..5d3ebad 100644 --- a/ft3658/focaltech_core.c +++ b/ft3658/focaltech_core.c @@ -50,6 +50,7 @@ #include <linux/earlysuspend.h> #define FTS_SUSPEND_LEVEL 1 /* Early-suspend level */ #endif +#include <linux/types.h> #include "focaltech_core.h" /***************************************************************************** @@ -828,15 +829,15 @@ static int fts_read_touchdata(struct fts_ts_data *data) FTS_ERROR("touch data(%x) abnormal,ret:%d", buf[1], ret); return -EIO; } +#endif if (data->gesture_mode) { - ret = fts_gesture_readdata(data, buf + FTS_TOUCH_DATA_LEN); + ret = fts_gesture_readdata(data, true); if (ret == 0) { FTS_INFO("succuss to get gesture data in irq handler"); return 1; } } -#endif #if IS_ENABLED(GOOGLE_REPORT_MODE) if (data->work_mode == FTS_REG_WORKMODE_WORK_VALUE) { @@ -3549,7 +3550,7 @@ static int fts_ts_suspend(struct device *dev) fts_irq_disable(); #if IS_ENABLED(CONFIG_TOUCHSCREEN_HEATMAP) - fts_set_heatmap_mode(ts_data, FW_HEATMAP_MODE_DISABLE); + fts_set_heatmap_mode(ts_data, FW_HEATMAP_MODE_DISABLE); #endif FTS_DEBUG("make TP enter into sleep mode"); mutex_lock(&ts_data->reg_lock); @@ -3575,6 +3576,85 @@ static int fts_ts_suspend(struct device *dev) return 0; } + +/** + * Report a finger down event on the long press gesture area then immediately + * report a cancel event(MT_TOOL_PALM). + */ +static void fts_report_cancel_event(struct fts_ts_data *ts_data) +{ + FTS_INFO("Report cancel event for UDFPS"); + + mutex_lock(&ts_data->report_mutex); + /* Finger down on UDFPS area. */ + input_mt_slot(ts_data->input_dev, 0); + input_report_key(ts_data->input_dev, BTN_TOUCH, 1); + input_mt_report_slot_state(ts_data->input_dev, MT_TOOL_FINGER, 1); + input_report_abs(ts_data->input_dev, ABS_MT_POSITION_X, + ts_data->fts_gesture_data.coordinate_x[0]); + input_report_abs(ts_data->input_dev, ABS_MT_POSITION_Y, + ts_data->fts_gesture_data.coordinate_y[0]); + input_report_abs(ts_data->input_dev, ABS_MT_TOUCH_MAJOR, + ts_data->fts_gesture_data.major[0]); + input_report_abs(ts_data->input_dev, ABS_MT_TOUCH_MINOR, + ts_data->fts_gesture_data.minor[0]); +#ifndef SKIP_PRESSURE + input_report_abs(ts_data->input_dev, ABS_MT_PRESSURE, 1); +#endif + input_report_abs(ts_data->input_dev, ABS_MT_ORIENTATION, + ts_data->fts_gesture_data.orientation[0]); + input_sync(ts_data->input_dev); + + /* Report MT_TOOL_PALM for canceling the touch event. */ + input_mt_slot(ts_data->input_dev, 0); + input_report_key(ts_data->input_dev, BTN_TOUCH, 1); + input_mt_report_slot_state(ts_data->input_dev, MT_TOOL_PALM, 1); + input_sync(ts_data->input_dev); + + /* Release touches. */ + input_mt_slot(ts_data->input_dev, 0); +#ifndef SKIP_PRESSURE + input_report_abs(ts_data->input_dev, ABS_MT_PRESSURE, 0); +#endif + input_mt_report_slot_state(ts_data->input_dev, MT_TOOL_FINGER, 0); + input_report_abs(ts_data->input_dev, ABS_MT_TRACKING_ID, -1); + input_report_key(ts_data->input_dev, BTN_TOUCH, 0); + input_sync(ts_data->input_dev); + mutex_unlock(&ts_data->report_mutex); +} + +static void fts_check_finger_status(struct fts_ts_data *ts_data) +{ + int ret = 0; + u8 power_mode = FTS_REG_POWER_MODE_SLEEP; + ktime_t timeout = ktime_add_ms(ktime_get(), 500); /* 500ms. */ + + /* If power mode is deep sleep mode, then reurn. */ + ret = fts_read_reg(FTS_REG_POWER_MODE, &power_mode); + if (ret) + return; + + if (power_mode == FTS_REG_POWER_MODE_SLEEP) + return; + + while (ktime_get() < timeout) { + ret = fts_gesture_readdata(ts_data, false); + if (ret) + break; + + if (ts_data->fts_gesture_data.gesture_id == FTS_GESTURE_ID_LPTW_DOWN) { + msleep(30); + continue; + } + + if (ts_data->fts_gesture_data.gesture_id == FTS_GESTURE_ID_LPTW_UP || + ts_data->fts_gesture_data.gesture_id == FTS_GESTURE_ID_STTW) { + fts_report_cancel_event(ts_data); + } + break; + } +} + static int fts_ts_resume(struct device *dev) { struct fts_ts_data *ts_data = fts_data; @@ -3589,9 +3669,13 @@ static int fts_ts_resume(struct device *dev) fts_release_all_finger(); if (!ts_data->ic_info.is_incell) { + if (!ts_data->gesture_mode) { #if FTS_POWER_SOURCE_CUST_EN - fts_power_source_resume(ts_data); + fts_power_source_resume(ts_data); #endif + fts_check_finger_status(ts_data); + } + fts_reset_proc(FTS_RESET_INTERVAL); } @@ -3599,7 +3683,8 @@ static int fts_ts_resume(struct device *dev) if (ret != 0) { FTS_ERROR("Resume has been cancelled by wake up timeout"); #if FTS_POWER_SOURCE_CUST_EN - fts_power_source_suspend(ts_data); + if (!ts_data->gesture_mode) + fts_power_source_suspend(ts_data); #endif return ret; } diff --git a/ft3658/focaltech_core.h b/ft3658/focaltech_core.h index d63d493..515d28a 100644 --- a/ft3658/focaltech_core.h +++ b/ft3658/focaltech_core.h @@ -80,7 +80,8 @@ #define FTS_TOUCH_DATA_LEN (FTS_MAX_POINTS_SUPPORT * FTS_ONE_TCH_LEN + 3) #define FTS_GESTURE_POINTS_MAX 1 -#define FTS_GESTURE_DATA_LEN (FTS_GESTURE_POINTS_MAX * 4 + 4) +#define FTS_GESTURE_DATA_LEN 14 +#define FTS_GESTURE_TOTAL_DATA_SIZE (FTS_GESTURE_POINTS_MAX * FTS_GESTURE_DATA_LEN) #define FTS_MAX_ID 0x0A #define FTS_TOUCH_X_H_POS 3 @@ -204,6 +205,25 @@ enum MF_MODE { MF_ON, }; +/* +* gesture_id - mean which gesture is recognised +* point_num - points number of this gesture +* coordinate_x - All gesture point x coordinate +* coordinate_y - All gesture point y coordinate +* major - All gesture major value +* minor - All gesture minor value +* orientation - All gesture orientation value +*/ +struct fts_gesture_st { + u8 gesture_id; + u8 point_num; + int coordinate_x[FTS_GESTURE_POINTS_MAX]; + int coordinate_y[FTS_GESTURE_POINTS_MAX]; + int major[FTS_GESTURE_POINTS_MAX]; + int minor[FTS_GESTURE_POINTS_MAX]; + int orientation[FTS_GESTURE_POINTS_MAX]; +}; + struct fts_ts_data { struct i2c_client *client; struct spi_device *spi; @@ -226,6 +246,7 @@ struct fts_ts_data { struct mutex reg_lock; struct mutex device_mutex; struct completion bus_resumed; + struct fts_gesture_st fts_gesture_data; unsigned long intr_jiffies; int irq; int log_level; @@ -393,7 +414,7 @@ int fts_spi_transfer_direct(u8 *writebuf, u32 writelen, u8 *readbuf, u32 readlen int fts_gesture_init(struct fts_ts_data *ts_data); int fts_gesture_exit(struct fts_ts_data *ts_data); void fts_gesture_recovery(struct fts_ts_data *ts_data); -int fts_gesture_readdata(struct fts_ts_data *ts_data, u8 *data); +int fts_gesture_readdata(struct fts_ts_data *ts_data, bool is_report); int fts_gesture_suspend(struct fts_ts_data *ts_data); int fts_gesture_resume(struct fts_ts_data *ts_data); diff --git a/ft3658/focaltech_gesture.c b/ft3658/focaltech_gesture.c index 36e1565..811f574 100644 --- a/ft3658/focaltech_gesture.c +++ b/ft3658/focaltech_gesture.c @@ -73,29 +73,10 @@ /***************************************************************************** * Private enumerations, structures and unions using typedef *****************************************************************************/ -/* -* gesture_id - mean which gesture is recognised -* point_num - points number of this gesture -* coordinate_x - All gesture point x coordinate -* coordinate_y - All gesture point y coordinate -* mode - gesture enable/disable, need enable by host -* - 1:enable gesture function(default) 0:disable -* active - gesture work flag, -* always set 1 when suspend, set 0 when resume -*/ -struct fts_gesture_st { - u8 gesture_id; - u8 point_num; - u16 coordinate_x[FTS_GESTURE_POINTS_MAX]; - u16 coordinate_y[FTS_GESTURE_POINTS_MAX]; - u8 Gesture_major[FTS_GESTURE_POINTS_MAX]; - u8 Gesture_minor[FTS_GESTURE_POINTS_MAX]; -}; /***************************************************************************** * Static variables *****************************************************************************/ -static struct fts_gesture_st fts_gesture_data; /***************************************************************************** * Global variable or extern global variabls/functions @@ -146,7 +127,7 @@ static ssize_t fts_gesture_buf_show( int count = 0; int i = 0; struct input_dev *input_dev = fts_data->input_dev; - struct fts_gesture_st *gesture = &fts_gesture_data; + struct fts_gesture_st *gesture = &fts_data->fts_gesture_data; mutex_lock(&input_dev->mutex); count = snprintf(buf, PAGE_SIZE, "Gesture ID:%d\n", gesture->gesture_id); @@ -290,76 +271,71 @@ static void fts_gesture_report(struct input_dev *input_dev, int gesture_id) * It will be called this function every intrrupt when FTS_GESTURE_EN = 1 * * gesture data length: 1(enable) + 1(reserve) + 2(header) + 6 * 4 -* Input: ts_data - global struct data -* data - gesture data buffer if non-flash, else NULL +* Input: ts_data - global struct data +* is_report - whether report gesture event or not. * Output: * Return: 0 - read gesture data successfully, the report data is gesture data * 1 - tp not in suspend/gesture not enable in TP FW * -Exx - error *****************************************************************************/ -int fts_gesture_readdata(struct fts_ts_data *ts_data, u8 *data) +int fts_gesture_readdata(struct fts_ts_data *ts_data, bool is_report) { - int ret = 0; int i = 0; int index = 0; - u8 buf[FTS_GESTURE_DATA_LEN] = { 0 }; struct input_dev *input_dev = ts_data->input_dev; - struct fts_gesture_st *gesture = &fts_gesture_data; - u8 majorminor_buf[8 * FTS_GESTURE_POINTS_MAX] = { 0 }; + struct fts_gesture_st *gesture = &fts_data->fts_gesture_data; + u8 gesture_buf[FTS_GESTURE_TOTAL_DATA_SIZE] = { 0 }; u8 cmd[2] = { 0 }; cmd[0] = FTS_GESTURE_MAJOR_MINOR; - if (!ts_data->suspended || !ts_data->gesture_mode) { - return 1; + if (!ts_data->suspended) { + return -EINVAL; } - if (!data) { - FTS_ERROR("gesture data buffer is null"); - ret = -EINVAL; - return ret; - } + fts_read(cmd, 1, gesture_buf, FTS_GESTURE_TOTAL_DATA_SIZE); - memcpy(buf, data, FTS_GESTURE_DATA_LEN); - if (buf[0] != ENABLE) { + if (gesture_buf[0] != ENABLE) { FTS_DEBUG("gesture not enable in fw, don't process gesture"); - return 1; + return -EINVAL; } /* init variable before read gesture point */ memset(gesture->coordinate_x, 0, FTS_GESTURE_POINTS_MAX * sizeof(u16)); memset(gesture->coordinate_y, 0, FTS_GESTURE_POINTS_MAX * sizeof(u16)); - gesture->gesture_id = buf[2]; - gesture->point_num = buf[3]; - FTS_DEBUG("gesture_id=0x%x, point_num=%d", - gesture->gesture_id, gesture->point_num); - fts_read(cmd, 1, majorminor_buf, 8 * FTS_GESTURE_POINTS_MAX); - + gesture->point_num = gesture_buf[2]; + gesture->gesture_id = gesture_buf[3]; + if (ts_data->log_level >= 1) { + FTS_DEBUG("gesture_id=0x%x, point_num=%d", + gesture->gesture_id, gesture->point_num); + } /* save point data,max:6 */ for (i = 0; i < FTS_GESTURE_POINTS_MAX; i++) { - index = 4 * i + 4; - gesture->coordinate_x[i] = (u16)(((buf[0 + index] & 0x0F) << 8) - + buf[1 + index]); - gesture->coordinate_y[i] = (u16)(((buf[2 + index] & 0x0F) << 8) - + buf[3 + index]); - - gesture->Gesture_major[i] = majorminor_buf[8 * i + 4]; - gesture->Gesture_minor[i] = majorminor_buf[8 * i + 5]; - - FTS_DEBUG("x=%d, y=%d, major=%d, minor=%d\n", - gesture->coordinate_x[i], gesture->coordinate_y[i], - gesture->Gesture_major[i], gesture->Gesture_minor[i]); + index = FTS_GESTURE_DATA_LEN * i; + gesture->major[i] = + (u16)(gesture_buf[6 + index] * ts_data->pdata->mm2px); + gesture->minor[i] = + (u16)(gesture_buf[7 + index] * ts_data->pdata->mm2px); + gesture->coordinate_x[i] = (u16)(((gesture_buf[8 + index] & 0x0F) << 8) + + gesture_buf[9 + index]); + gesture->coordinate_y[i] = (u16)(((gesture_buf[10 + index] & 0x0F) << 8) + + (gesture_buf[11 + index]& 0xFF)); + gesture->orientation[i] = + (s16)(gesture_buf[13 + index] * FTS_ORIENTATION_SCALE); + + if (ts_data->log_level >= 1) { + FTS_DEBUG("x=%d, y=%d, major=%d, minor=%d, orientation=%d\n", + gesture->coordinate_x[i], gesture->coordinate_y[i], + gesture->major[i], gesture->minor[i], + gesture->orientation[i]); + } } - /* report gesture to OS */ - fts_gesture_report(input_dev, gesture->gesture_id); - - for(i = 0; i < gesture->point_num; i++) { - input_report_abs(input_dev, ABS_MT_POSITION_X, gesture->coordinate_x[i]); - input_report_abs(input_dev, ABS_MT_POSITION_Y, gesture->coordinate_y[i]); - input_report_abs(input_dev, ABS_MT_TOUCH_MAJOR, gesture->Gesture_major[i]); - input_report_abs(input_dev, ABS_MT_TOUCH_MINOR, gesture->Gesture_minor[i]); - input_sync(input_dev); + if (is_report) { + mutex_lock(&ts_data->report_mutex); + /* report gesture to OS. */ + fts_gesture_report(input_dev, gesture->gesture_id); + mutex_unlock(&ts_data->report_mutex); } return 0; @@ -477,7 +453,7 @@ int fts_gesture_init(struct fts_ts_data *ts_data) fts_create_gesture_sysfs(ts_data->dev); - memset(&fts_gesture_data, 0, sizeof(struct fts_gesture_st)); + memset(&ts_data->fts_gesture_data, 0, sizeof(struct fts_gesture_st)); ts_data->gesture_mode = FTS_GESTURE_EN; FTS_FUNC_EXIT(); |