mirror of
https://github.com/BobTheBlinker/android_kernel_motorola_sm6375.git
synced 2026-10-25 22:23:14 -04:00
sec_mmi: wakeup gestures support
Support wakeup gestures required for single and zero tap features Change-Id: Ifc15207dcd57b2b775ec63f4c1ba51f4ad90a9e9 Signed-off-by: Konstantin Makariev <hcv867@motorola.com> Reviewed-on: https://gerrit.mot.com/1469723 SLTApproved: Slta Waiver SME-Granted: SME Approvals Granted Tested-by: Jira Key Reviewed-by: Konstantin Makariev <kmakariev@motorola.com> Submit-Approved: Jira Key
This commit is contained in:
parent
3294fe5535
commit
59da923193
4 changed files with 106 additions and 56 deletions
|
|
@ -10,5 +10,9 @@ ifneq (,$(filter racer% burton%,$(TARGET_PRODUCT)))
|
|||
EXTRA_CFLAGS += -DUSE_STUBS -DCONFIG_DRM_DYNAMIC_REFRESH_RATE
|
||||
endif
|
||||
|
||||
ifneq (,$(filter burton%,$(TARGET_PRODUCT)))
|
||||
EXTRA_CFLAGS += -DCONFIG_PANEL_NOTIFICATIONS
|
||||
endif
|
||||
|
||||
obj-m := sec_mmi.o
|
||||
sec_mmi-objs = sec_ts.o sec_ts_fn.o sec_ts_fw.o sec_ts_mmi.o sec_cmd.o sec_ts_only_vendor.o
|
||||
|
|
|
|||
|
|
@ -7,8 +7,10 @@
|
|||
#include <linux/usb.h>
|
||||
#include <linux/power_supply.h>
|
||||
|
||||
#if defined(CONFIG_PANEL_NOTIFICATIONS)
|
||||
#include <linux/panel_notifier.h>
|
||||
#endif
|
||||
#if defined(CONFIG_DRM)
|
||||
#include <linux/msm_drm_notify.h>
|
||||
extern bool dsi_display_is_panel_enable(int id, int *probe_status, char **pname);
|
||||
#endif
|
||||
|
||||
|
|
@ -38,6 +40,8 @@ struct sec_mmi_data {
|
|||
|
||||
atomic_t touch_stopped;
|
||||
|
||||
bool gpio_config;
|
||||
bool gestures_enabled;
|
||||
bool power_off_suspend;
|
||||
unsigned int reset;
|
||||
bool usb_detection;
|
||||
|
|
@ -60,6 +64,7 @@ struct sec_mmi_data {
|
|||
};
|
||||
|
||||
int sec_mmi_data_init(struct sec_ts_data *ts, bool enable);
|
||||
void sec_mmi_gesture_handler(void *data);
|
||||
|
||||
#define DEV_MMI (&data->i2c_client->dev)
|
||||
#define DEV_TS (&ts->client->dev)
|
||||
|
|
|
|||
|
|
@ -883,6 +883,7 @@ static void sec_ts_read_event(struct sec_ts_data *ts)
|
|||
/* */
|
||||
/* Gesture event handling */
|
||||
/* */
|
||||
sec_mmi_gesture_handler((void *)event_buff);
|
||||
break;
|
||||
case SEC_TS_GESTURE_CODE_DOUBLE_TAP:
|
||||
/* */
|
||||
|
|
@ -2108,7 +2109,10 @@ int sec_ts_set_lowpowermode(struct sec_ts_data *ts, u8 mode)
|
|||
}
|
||||
#endif
|
||||
|
||||
data = (ts->lowpower_mode & SEC_TS_MODE_LOWPOWER_FLAG) >> 1;
|
||||
//data = (ts->lowpower_mode & SEC_TS_MODE_LOWPOWER_FLAG) >> 1;
|
||||
data = 0x1;
|
||||
input_err(true, &ts->client->dev, "%s: setting gesture mode (%X)\n",
|
||||
__func__, data);
|
||||
ret = sec_ts_i2c_write(ts, SEC_TS_CMD_WAKEUP_GESTURE_MODE, &data, 1);
|
||||
if (ret < 0) {
|
||||
input_err(true, &ts->client->dev, "%s: Failed to set\n", __func__);
|
||||
|
|
|
|||
|
|
@ -364,6 +364,16 @@ static int sec_mmi_dt(struct sec_mmi_data *data)
|
|||
ts->force_calibration = true;
|
||||
}
|
||||
|
||||
if (of_property_read_bool(np, "sec,enable-gestures")) {
|
||||
dev_info(DEV_MMI, "%s: using enable gestures\n", __func__);
|
||||
data->gestures_enabled = true;
|
||||
}
|
||||
|
||||
if (of_property_read_bool(np, "sec,gpio-config")) {
|
||||
dev_info(DEV_MMI, "%s: using gpio config\n", __func__);
|
||||
data->gpio_config = true;
|
||||
}
|
||||
|
||||
if (!of_property_read_u32(np, "sec,reset-on-resume", &data->reset))
|
||||
dev_info(DEV_MMI, "%s: using %u reset on resume\n",
|
||||
__func__, data->reset);
|
||||
|
|
@ -712,8 +722,9 @@ static int inline sec_mmi_display_off(struct sec_mmi_data *data)
|
|||
if (data->power_off_suspend)
|
||||
sec_ts_irq_enable(ts, false);
|
||||
else
|
||||
sec_ts_set_lowpowermode(ts, TO_SLEEP_MODE);
|
||||
|
||||
sec_ts_set_lowpowermode(ts,
|
||||
data->gestures_enabled ?
|
||||
TO_LOWPOWER_MODE : TO_SLEEP_MODE);
|
||||
cancel_delayed_work_sync(&data->resume_work);
|
||||
|
||||
if (ts->lowpower_mode)
|
||||
|
|
@ -727,60 +738,46 @@ static int inline sec_mmi_display_off(struct sec_mmi_data *data)
|
|||
static int sec_mmi_panel_cb(struct notifier_block *nb,
|
||||
unsigned long event, void *evd)
|
||||
{
|
||||
struct msm_drm_notifier *evdata = evd;
|
||||
struct sec_mmi_data *data =
|
||||
container_of(nb, struct sec_mmi_data, panel_nb);
|
||||
struct sec_ts_data *ts = data->ts_ptr;
|
||||
|
||||
if (!evdata || (evdata->id != data->ctrl_dsi)) {
|
||||
dev_dbg(DEV_MMI, "%s: drm notification: id(%d) != ctrl_dsi(%d)\n",
|
||||
__func__, evdata->id, data->ctrl_dsi);
|
||||
return 0;
|
||||
}
|
||||
/* entering suspend upon early blank event */
|
||||
/* to ensure shared power supply is still on */
|
||||
/* for in-cell design touch solutions */
|
||||
switch (event) {
|
||||
case PANEL_EVENT_PRE_DISPLAY_OFF:
|
||||
/* put in reset first */
|
||||
if (data->power_off_suspend)
|
||||
sec_ts_pinctrl_configure(ts, false);
|
||||
sec_mmi_display_off(data);
|
||||
break;
|
||||
|
||||
if ((event == MSM_DRM_EARLY_EVENT_BLANK || event == MSM_DRM_EVENT_BLANK) &&
|
||||
evdata && evdata->data && data) {
|
||||
struct sec_ts_data *ts = data->ts_ptr;
|
||||
int *blank = evdata->data;
|
||||
case PANEL_EVENT_DISPLAY_OFF:
|
||||
if (data->power_off_suspend) {
|
||||
/* then proceed with de-powering */
|
||||
sec_ts_power((void *)ts, false);
|
||||
dev_dbg(DEV_MMI, "%s: touch powered off\n", __func__);
|
||||
}
|
||||
break;
|
||||
|
||||
dev_dbg(DEV_MMI, "%s: drm notification: event = %lu blank = %d\n",
|
||||
__func__, event, *blank);
|
||||
/* entering suspend upon early blank event */
|
||||
/* to ensure shared power supply is still on */
|
||||
/* for in-cell design touch solutions */
|
||||
switch (event) {
|
||||
case MSM_DRM_EARLY_EVENT_BLANK:
|
||||
if (*blank == MSM_DRM_BLANK_POWERDOWN) {
|
||||
/* put in reset first */
|
||||
if (data->power_off_suspend)
|
||||
sec_ts_pinctrl_configure(ts, false);
|
||||
case PANEL_EVENT_PRE_DISPLAY_ON:
|
||||
if (data->power_off_suspend) {
|
||||
/* powering on early */
|
||||
sec_ts_power((void *)ts, true);
|
||||
dev_dbg(DEV_MMI, "%s: touch powered on\n", __func__);
|
||||
} else if (data->reset) {
|
||||
dev_dbg(DEV_MMI, "%s: resetting...\n", __func__);
|
||||
data->reset_func(ts->mmi_ptr, data->reset);
|
||||
}
|
||||
break;
|
||||
|
||||
sec_mmi_display_off(data);
|
||||
|
||||
} else if (data->power_off_suspend) {
|
||||
/* powering on early */
|
||||
sec_ts_power((void *)ts, true);
|
||||
dev_dbg(DEV_MMI, "%s: touch powered on\n", __func__);
|
||||
} else if (data->reset) {
|
||||
dev_dbg(DEV_MMI, "%s: resetting...\n", __func__);
|
||||
data->reset_func(ts->mmi_ptr, data->reset);
|
||||
}
|
||||
break;
|
||||
|
||||
case MSM_DRM_EVENT_BLANK:
|
||||
if (*blank == MSM_DRM_BLANK_UNBLANK) {
|
||||
/* out of reset to allow wait for boot complete */
|
||||
if (data->power_off_suspend)
|
||||
sec_ts_pinctrl_configure(ts, true);
|
||||
|
||||
sec_mmi_display_on(data);
|
||||
|
||||
} else if (data->power_off_suspend) {
|
||||
/* then proceed with de-powering */
|
||||
sec_ts_power((void *)ts, false);
|
||||
dev_dbg(DEV_MMI, "%s: touch powered off\n", __func__);
|
||||
}
|
||||
break;
|
||||
}
|
||||
case PANEL_EVENT_DISPLAY_ON:
|
||||
/* out of reset to allow wait for boot complete */
|
||||
if (data->power_off_suspend)
|
||||
sec_ts_pinctrl_configure(ts, true);
|
||||
sec_mmi_display_on(data);
|
||||
break;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
|
@ -817,7 +814,7 @@ static int sec_mmi_register_notifiers(
|
|||
|
||||
if (enable) {
|
||||
data->panel_nb.notifier_call = sec_mmi_panel_cb;
|
||||
rc = msm_drm_register_client(&data->panel_nb);
|
||||
rc = panel_register_notifier(&data->panel_nb);
|
||||
|
||||
if (data->usb_detection) {
|
||||
data->ps_notif.notifier_call = sec_mmi_ps_notify_callback;
|
||||
|
|
@ -830,7 +827,8 @@ static int sec_mmi_register_notifiers(
|
|||
&dsi_freq_head, &data->freq_nb);
|
||||
}
|
||||
} else {
|
||||
rc = msm_drm_unregister_client(&data->panel_nb);
|
||||
rc = panel_unregister_notifier(&data->panel_nb);
|
||||
|
||||
if (data->usb_detection)
|
||||
power_supply_unreg_notifier(&data->ps_notif);
|
||||
|
||||
|
|
@ -850,6 +848,42 @@ static int sec_mmi_register_notifiers(
|
|||
return rc;
|
||||
}
|
||||
|
||||
void sec_mmi_gesture_handler(void *data)
|
||||
{
|
||||
struct sec_ts_gesture_status *gs =
|
||||
(struct sec_ts_gesture_status *)data;
|
||||
|
||||
if (gs->eid != SEC_TS_GESTURE_EVENT) {
|
||||
pr_info("%s: invalid gesture ID\n", __func__);
|
||||
return;
|
||||
}
|
||||
|
||||
pr_info("%s: GESTURE %x %x %x %x %x %x %x %x\n", __func__,
|
||||
gs->eid | (gs->stype << 4) | (gs->sf << 6),
|
||||
gs->gesture_id,
|
||||
gs->gesture_data_1,
|
||||
gs->gesture_data_2,
|
||||
gs->gesture_data_3,
|
||||
gs->gesture_data_4,
|
||||
gs->reserved_1,
|
||||
gs->left_event_5_0 | (gs->reserved_2 << 6));
|
||||
|
||||
switch (gs->gesture_id) {
|
||||
case 1:
|
||||
pr_info("%s: single tap\n", __func__);
|
||||
break;
|
||||
case 2:
|
||||
pr_info("%s: zero tap; x=%x, y=%x, w=%x, p=%x\n", __func__,
|
||||
gs->gesture_data_1+((gs->gesture_data_3 & 0x0f) << 8),
|
||||
gs->gesture_data_2+((gs->gesture_data_3 & 0xf0) << 8),
|
||||
gs->gesture_data_4,
|
||||
gs->reserved_1);
|
||||
break;
|
||||
default:
|
||||
pr_info("%s: unknown id=%\n", __func__, gs->gesture_id);
|
||||
}
|
||||
}
|
||||
|
||||
static ssize_t sec_mmi_panel_supplier_show(struct device *dev,
|
||||
struct device_attribute *attr, char *buf)
|
||||
{
|
||||
|
|
@ -1240,6 +1274,9 @@ int sec_mmi_data_init(struct sec_ts_data *ts, bool enable)
|
|||
if (data->usb_detection)
|
||||
INIT_WORK(&data->ps_notify_work, sec_mmi_ps_work);
|
||||
|
||||
if (data->gpio_config)
|
||||
sec_mmi_ic_reset(data, 1);
|
||||
|
||||
data->task = MMI_TASK_INIT;
|
||||
schedule_delayed_work(&data->work, msecs_to_jiffies(50));
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in a new issue