diff options
Diffstat (limited to 'drivers/input/touchscreen/atmel_mxt_ts.c')
-rw-r--r-- | drivers/input/touchscreen/atmel_mxt_ts.c | 391 |
1 files changed, 345 insertions, 46 deletions
diff --git a/drivers/input/touchscreen/atmel_mxt_ts.c b/drivers/input/touchscreen/atmel_mxt_ts.c index 95ee92a91bd2..2875ddf37289 100644 --- a/drivers/input/touchscreen/atmel_mxt_ts.c +++ b/drivers/input/touchscreen/atmel_mxt_ts.c | |||
@@ -25,6 +25,7 @@ | |||
25 | #include <linux/interrupt.h> | 25 | #include <linux/interrupt.h> |
26 | #include <linux/of.h> | 26 | #include <linux/of.h> |
27 | #include <linux/slab.h> | 27 | #include <linux/slab.h> |
28 | #include <asm/unaligned.h> | ||
28 | 29 | ||
29 | /* Version */ | 30 | /* Version */ |
30 | #define MXT_VER_20 20 | 31 | #define MXT_VER_20 20 |
@@ -79,6 +80,7 @@ | |||
79 | #define MXT_SPT_DIGITIZER_T43 43 | 80 | #define MXT_SPT_DIGITIZER_T43 43 |
80 | #define MXT_SPT_MESSAGECOUNT_T44 44 | 81 | #define MXT_SPT_MESSAGECOUNT_T44 44 |
81 | #define MXT_SPT_CTECONFIG_T46 46 | 82 | #define MXT_SPT_CTECONFIG_T46 46 |
83 | #define MXT_TOUCH_MULTITOUCHSCREEN_T100 100 | ||
82 | 84 | ||
83 | /* MXT_GEN_MESSAGE_T5 object */ | 85 | /* MXT_GEN_MESSAGE_T5 object */ |
84 | #define MXT_RPTID_NOMSG 0xff | 86 | #define MXT_RPTID_NOMSG 0xff |
@@ -185,6 +187,36 @@ struct t9_range { | |||
185 | #define MXT_RESET_VALUE 0x01 | 187 | #define MXT_RESET_VALUE 0x01 |
186 | #define MXT_BACKUP_VALUE 0x55 | 188 | #define MXT_BACKUP_VALUE 0x55 |
187 | 189 | ||
190 | /* T100 Multiple Touch Touchscreen */ | ||
191 | #define MXT_T100_CTRL 0 | ||
192 | #define MXT_T100_CFG1 1 | ||
193 | #define MXT_T100_TCHAUX 3 | ||
194 | #define MXT_T100_XRANGE 13 | ||
195 | #define MXT_T100_YRANGE 24 | ||
196 | |||
197 | #define MXT_T100_CFG_SWITCHXY BIT(5) | ||
198 | |||
199 | #define MXT_T100_TCHAUX_VECT BIT(0) | ||
200 | #define MXT_T100_TCHAUX_AMPL BIT(1) | ||
201 | #define MXT_T100_TCHAUX_AREA BIT(2) | ||
202 | |||
203 | #define MXT_T100_DETECT BIT(7) | ||
204 | #define MXT_T100_TYPE_MASK 0x70 | ||
205 | |||
206 | enum t100_type { | ||
207 | MXT_T100_TYPE_FINGER = 1, | ||
208 | MXT_T100_TYPE_PASSIVE_STYLUS = 2, | ||
209 | MXT_T100_TYPE_HOVERING_FINGER = 4, | ||
210 | MXT_T100_TYPE_GLOVE = 5, | ||
211 | MXT_T100_TYPE_LARGE_TOUCH = 6, | ||
212 | }; | ||
213 | |||
214 | #define MXT_DISTANCE_ACTIVE_TOUCH 0 | ||
215 | #define MXT_DISTANCE_HOVERING 1 | ||
216 | |||
217 | #define MXT_TOUCH_MAJOR_DEFAULT 1 | ||
218 | #define MXT_PRESSURE_DEFAULT 1 | ||
219 | |||
188 | /* Delay times */ | 220 | /* Delay times */ |
189 | #define MXT_BACKUP_TIME 50 /* msec */ | 221 | #define MXT_BACKUP_TIME 50 /* msec */ |
190 | #define MXT_RESET_TIME 200 /* msec */ | 222 | #define MXT_RESET_TIME 200 /* msec */ |
@@ -244,6 +276,9 @@ struct mxt_data { | |||
244 | unsigned int max_y; | 276 | unsigned int max_y; |
245 | bool in_bootloader; | 277 | bool in_bootloader; |
246 | u16 mem_size; | 278 | u16 mem_size; |
279 | u8 t100_aux_ampl; | ||
280 | u8 t100_aux_area; | ||
281 | u8 t100_aux_vect; | ||
247 | u8 max_reportid; | 282 | u8 max_reportid; |
248 | u32 config_crc; | 283 | u32 config_crc; |
249 | u32 info_crc; | 284 | u32 info_crc; |
@@ -253,6 +288,7 @@ struct mxt_data { | |||
253 | bool update_input; | 288 | bool update_input; |
254 | u8 last_message_count; | 289 | u8 last_message_count; |
255 | u8 num_touchids; | 290 | u8 num_touchids; |
291 | u8 multitouch; | ||
256 | 292 | ||
257 | /* Cached parameters from object table */ | 293 | /* Cached parameters from object table */ |
258 | u16 T5_address; | 294 | u16 T5_address; |
@@ -264,6 +300,8 @@ struct mxt_data { | |||
264 | u8 T9_reportid_max; | 300 | u8 T9_reportid_max; |
265 | u8 T19_reportid; | 301 | u8 T19_reportid; |
266 | u16 T44_address; | 302 | u16 T44_address; |
303 | u8 T100_reportid_min; | ||
304 | u8 T100_reportid_max; | ||
267 | 305 | ||
268 | /* for fw update in bootloader */ | 306 | /* for fw update in bootloader */ |
269 | struct completion bl_completion; | 307 | struct completion bl_completion; |
@@ -771,6 +809,114 @@ static void mxt_proc_t9_message(struct mxt_data *data, u8 *message) | |||
771 | data->update_input = true; | 809 | data->update_input = true; |
772 | } | 810 | } |
773 | 811 | ||
812 | static void mxt_proc_t100_message(struct mxt_data *data, u8 *message) | ||
813 | { | ||
814 | struct device *dev = &data->client->dev; | ||
815 | struct input_dev *input_dev = data->input_dev; | ||
816 | int id; | ||
817 | u8 status; | ||
818 | u8 type = 0; | ||
819 | u16 x; | ||
820 | u16 y; | ||
821 | int distance = 0; | ||
822 | int tool = 0; | ||
823 | u8 major = 0; | ||
824 | u8 pressure = 0; | ||
825 | u8 orientation = 0; | ||
826 | |||
827 | id = message[0] - data->T100_reportid_min - 2; | ||
828 | |||
829 | /* ignore SCRSTATUS events */ | ||
830 | if (id < 0) | ||
831 | return; | ||
832 | |||
833 | status = message[1]; | ||
834 | x = get_unaligned_le16(&message[2]); | ||
835 | y = get_unaligned_le16(&message[4]); | ||
836 | |||
837 | if (status & MXT_T100_DETECT) { | ||
838 | type = (status & MXT_T100_TYPE_MASK) >> 4; | ||
839 | |||
840 | switch (type) { | ||
841 | case MXT_T100_TYPE_HOVERING_FINGER: | ||
842 | tool = MT_TOOL_FINGER; | ||
843 | distance = MXT_DISTANCE_HOVERING; | ||
844 | |||
845 | if (data->t100_aux_vect) | ||
846 | orientation = message[data->t100_aux_vect]; | ||
847 | |||
848 | break; | ||
849 | |||
850 | case MXT_T100_TYPE_FINGER: | ||
851 | case MXT_T100_TYPE_GLOVE: | ||
852 | tool = MT_TOOL_FINGER; | ||
853 | distance = MXT_DISTANCE_ACTIVE_TOUCH; | ||
854 | |||
855 | if (data->t100_aux_area) | ||
856 | major = message[data->t100_aux_area]; | ||
857 | |||
858 | if (data->t100_aux_ampl) | ||
859 | pressure = message[data->t100_aux_ampl]; | ||
860 | |||
861 | if (data->t100_aux_vect) | ||
862 | orientation = message[data->t100_aux_vect]; | ||
863 | |||
864 | break; | ||
865 | |||
866 | case MXT_T100_TYPE_PASSIVE_STYLUS: | ||
867 | tool = MT_TOOL_PEN; | ||
868 | |||
869 | /* | ||
870 | * Passive stylus is reported with size zero so | ||
871 | * hardcode. | ||
872 | */ | ||
873 | major = MXT_TOUCH_MAJOR_DEFAULT; | ||
874 | |||
875 | if (data->t100_aux_ampl) | ||
876 | pressure = message[data->t100_aux_ampl]; | ||
877 | |||
878 | break; | ||
879 | |||
880 | case MXT_T100_TYPE_LARGE_TOUCH: | ||
881 | /* Ignore suppressed touch */ | ||
882 | break; | ||
883 | |||
884 | default: | ||
885 | dev_dbg(dev, "Unexpected T100 type\n"); | ||
886 | return; | ||
887 | } | ||
888 | } | ||
889 | |||
890 | /* | ||
891 | * Values reported should be non-zero if tool is touching the | ||
892 | * device | ||
893 | */ | ||
894 | if (!pressure && type != MXT_T100_TYPE_HOVERING_FINGER) | ||
895 | pressure = MXT_PRESSURE_DEFAULT; | ||
896 | |||
897 | input_mt_slot(input_dev, id); | ||
898 | |||
899 | if (status & MXT_T100_DETECT) { | ||
900 | dev_dbg(dev, "[%u] type:%u x:%u y:%u a:%02X p:%02X v:%02X\n", | ||
901 | id, type, x, y, major, pressure, orientation); | ||
902 | |||
903 | input_mt_report_slot_state(input_dev, tool, 1); | ||
904 | input_report_abs(input_dev, ABS_MT_POSITION_X, x); | ||
905 | input_report_abs(input_dev, ABS_MT_POSITION_Y, y); | ||
906 | input_report_abs(input_dev, ABS_MT_TOUCH_MAJOR, major); | ||
907 | input_report_abs(input_dev, ABS_MT_PRESSURE, pressure); | ||
908 | input_report_abs(input_dev, ABS_MT_DISTANCE, distance); | ||
909 | input_report_abs(input_dev, ABS_MT_ORIENTATION, orientation); | ||
910 | } else { | ||
911 | dev_dbg(dev, "[%u] release\n", id); | ||
912 | |||
913 | /* close out slot */ | ||
914 | input_mt_report_slot_state(input_dev, 0, 0); | ||
915 | } | ||
916 | |||
917 | data->update_input = true; | ||
918 | } | ||
919 | |||
774 | static int mxt_proc_message(struct mxt_data *data, u8 *message) | 920 | static int mxt_proc_message(struct mxt_data *data, u8 *message) |
775 | { | 921 | { |
776 | u8 report_id = message[0]; | 922 | u8 report_id = message[0]; |
@@ -786,9 +932,12 @@ static int mxt_proc_message(struct mxt_data *data, u8 *message) | |||
786 | * is not yet registered. | 932 | * is not yet registered. |
787 | */ | 933 | */ |
788 | mxt_dump_message(data, message); | 934 | mxt_dump_message(data, message); |
789 | } else if (report_id >= data->T9_reportid_min | 935 | } else if (report_id >= data->T9_reportid_min && |
790 | && report_id <= data->T9_reportid_max) { | 936 | report_id <= data->T9_reportid_max) { |
791 | mxt_proc_t9_message(data, message); | 937 | mxt_proc_t9_message(data, message); |
938 | } else if (report_id >= data->T100_reportid_min && | ||
939 | report_id <= data->T100_reportid_max) { | ||
940 | mxt_proc_t100_message(data, message); | ||
792 | } else if (report_id == data->T19_reportid) { | 941 | } else if (report_id == data->T19_reportid) { |
793 | mxt_input_button(data, message); | 942 | mxt_input_button(data, message); |
794 | data->update_input = true; | 943 | data->update_input = true; |
@@ -1411,6 +1560,8 @@ static void mxt_free_object_table(struct mxt_data *data) | |||
1411 | data->T9_reportid_max = 0; | 1560 | data->T9_reportid_max = 0; |
1412 | data->T19_reportid = 0; | 1561 | data->T19_reportid = 0; |
1413 | data->T44_address = 0; | 1562 | data->T44_address = 0; |
1563 | data->T100_reportid_min = 0; | ||
1564 | data->T100_reportid_max = 0; | ||
1414 | data->max_reportid = 0; | 1565 | data->max_reportid = 0; |
1415 | } | 1566 | } |
1416 | 1567 | ||
@@ -1487,6 +1638,7 @@ static int mxt_get_object_table(struct mxt_data *data) | |||
1487 | data->T7_address = object->start_address; | 1638 | data->T7_address = object->start_address; |
1488 | break; | 1639 | break; |
1489 | case MXT_TOUCH_MULTI_T9: | 1640 | case MXT_TOUCH_MULTI_T9: |
1641 | data->multitouch = MXT_TOUCH_MULTI_T9; | ||
1490 | data->T9_reportid_min = min_id; | 1642 | data->T9_reportid_min = min_id; |
1491 | data->T9_reportid_max = max_id; | 1643 | data->T9_reportid_max = max_id; |
1492 | data->num_touchids = object->num_report_ids | 1644 | data->num_touchids = object->num_report_ids |
@@ -1498,6 +1650,13 @@ static int mxt_get_object_table(struct mxt_data *data) | |||
1498 | case MXT_SPT_GPIOPWM_T19: | 1650 | case MXT_SPT_GPIOPWM_T19: |
1499 | data->T19_reportid = min_id; | 1651 | data->T19_reportid = min_id; |
1500 | break; | 1652 | break; |
1653 | case MXT_TOUCH_MULTITOUCHSCREEN_T100: | ||
1654 | data->multitouch = MXT_TOUCH_MULTITOUCHSCREEN_T100; | ||
1655 | data->T100_reportid_min = min_id; | ||
1656 | data->T100_reportid_max = max_id; | ||
1657 | /* first two report IDs reserved */ | ||
1658 | data->num_touchids = object->num_report_ids - 2; | ||
1659 | break; | ||
1501 | } | 1660 | } |
1502 | 1661 | ||
1503 | end_address = object->start_address | 1662 | end_address = object->start_address |
@@ -1582,22 +1741,138 @@ static int mxt_read_t9_resolution(struct mxt_data *data) | |||
1582 | return 0; | 1741 | return 0; |
1583 | } | 1742 | } |
1584 | 1743 | ||
1744 | static int mxt_read_t100_config(struct mxt_data *data) | ||
1745 | { | ||
1746 | struct i2c_client *client = data->client; | ||
1747 | int error; | ||
1748 | struct mxt_object *object; | ||
1749 | u16 range_x, range_y; | ||
1750 | u8 cfg, tchaux; | ||
1751 | u8 aux; | ||
1752 | |||
1753 | object = mxt_get_object(data, MXT_TOUCH_MULTITOUCHSCREEN_T100); | ||
1754 | if (!object) | ||
1755 | return -EINVAL; | ||
1756 | |||
1757 | error = __mxt_read_reg(client, | ||
1758 | object->start_address + MXT_T100_XRANGE, | ||
1759 | sizeof(range_x), &range_x); | ||
1760 | if (error) | ||
1761 | return error; | ||
1762 | |||
1763 | le16_to_cpus(&range_x); | ||
1764 | |||
1765 | error = __mxt_read_reg(client, | ||
1766 | object->start_address + MXT_T100_YRANGE, | ||
1767 | sizeof(range_y), &range_y); | ||
1768 | if (error) | ||
1769 | return error; | ||
1770 | |||
1771 | le16_to_cpus(&range_y); | ||
1772 | |||
1773 | error = __mxt_read_reg(client, | ||
1774 | object->start_address + MXT_T100_CFG1, | ||
1775 | 1, &cfg); | ||
1776 | if (error) | ||
1777 | return error; | ||
1778 | |||
1779 | error = __mxt_read_reg(client, | ||
1780 | object->start_address + MXT_T100_TCHAUX, | ||
1781 | 1, &tchaux); | ||
1782 | if (error) | ||
1783 | return error; | ||
1784 | |||
1785 | /* Handle default values */ | ||
1786 | if (range_x == 0) | ||
1787 | range_x = 1023; | ||
1788 | |||
1789 | if (range_y == 0) | ||
1790 | range_y = 1023; | ||
1791 | |||
1792 | if (cfg & MXT_T100_CFG_SWITCHXY) { | ||
1793 | data->max_x = range_y; | ||
1794 | data->max_y = range_x; | ||
1795 | } else { | ||
1796 | data->max_x = range_x; | ||
1797 | data->max_y = range_y; | ||
1798 | } | ||
1799 | |||
1800 | /* allocate aux bytes */ | ||
1801 | aux = 6; | ||
1802 | |||
1803 | if (tchaux & MXT_T100_TCHAUX_VECT) | ||
1804 | data->t100_aux_vect = aux++; | ||
1805 | |||
1806 | if (tchaux & MXT_T100_TCHAUX_AMPL) | ||
1807 | data->t100_aux_ampl = aux++; | ||
1808 | |||
1809 | if (tchaux & MXT_T100_TCHAUX_AREA) | ||
1810 | data->t100_aux_area = aux++; | ||
1811 | |||
1812 | dev_dbg(&client->dev, | ||
1813 | "T100 aux mappings vect:%u ampl:%u area:%u\n", | ||
1814 | data->t100_aux_vect, data->t100_aux_ampl, data->t100_aux_area); | ||
1815 | |||
1816 | dev_info(&client->dev, | ||
1817 | "T100 Touchscreen size X%uY%u\n", data->max_x, data->max_y); | ||
1818 | |||
1819 | return 0; | ||
1820 | } | ||
1821 | |||
1585 | static int mxt_input_open(struct input_dev *dev); | 1822 | static int mxt_input_open(struct input_dev *dev); |
1586 | static void mxt_input_close(struct input_dev *dev); | 1823 | static void mxt_input_close(struct input_dev *dev); |
1587 | 1824 | ||
1588 | static int mxt_initialize_t9_input_device(struct mxt_data *data) | 1825 | static void mxt_set_up_as_touchpad(struct input_dev *input_dev, |
1826 | struct mxt_data *data) | ||
1589 | { | 1827 | { |
1590 | struct device *dev = &data->client->dev; | ||
1591 | const struct mxt_platform_data *pdata = data->pdata; | 1828 | const struct mxt_platform_data *pdata = data->pdata; |
1829 | int i; | ||
1830 | |||
1831 | input_dev->name = "Atmel maXTouch Touchpad"; | ||
1832 | |||
1833 | __set_bit(INPUT_PROP_BUTTONPAD, input_dev->propbit); | ||
1834 | |||
1835 | input_abs_set_res(input_dev, ABS_X, MXT_PIXELS_PER_MM); | ||
1836 | input_abs_set_res(input_dev, ABS_Y, MXT_PIXELS_PER_MM); | ||
1837 | input_abs_set_res(input_dev, ABS_MT_POSITION_X, | ||
1838 | MXT_PIXELS_PER_MM); | ||
1839 | input_abs_set_res(input_dev, ABS_MT_POSITION_Y, | ||
1840 | MXT_PIXELS_PER_MM); | ||
1841 | |||
1842 | for (i = 0; i < pdata->t19_num_keys; i++) | ||
1843 | if (pdata->t19_keymap[i] != KEY_RESERVED) | ||
1844 | input_set_capability(input_dev, EV_KEY, | ||
1845 | pdata->t19_keymap[i]); | ||
1846 | } | ||
1847 | |||
1848 | static int mxt_initialize_input_device(struct mxt_data *data) | ||
1849 | { | ||
1850 | const struct mxt_platform_data *pdata = data->pdata; | ||
1851 | struct device *dev = &data->client->dev; | ||
1592 | struct input_dev *input_dev; | 1852 | struct input_dev *input_dev; |
1593 | int error; | 1853 | int error; |
1594 | unsigned int num_mt_slots; | 1854 | unsigned int num_mt_slots; |
1595 | unsigned int mt_flags = 0; | 1855 | unsigned int mt_flags = 0; |
1596 | int i; | ||
1597 | 1856 | ||
1598 | error = mxt_read_t9_resolution(data); | 1857 | switch (data->multitouch) { |
1599 | if (error) | 1858 | case MXT_TOUCH_MULTI_T9: |
1600 | dev_warn(dev, "Failed to initialize T9 resolution\n"); | 1859 | num_mt_slots = data->T9_reportid_max - data->T9_reportid_min + 1; |
1860 | error = mxt_read_t9_resolution(data); | ||
1861 | if (error) | ||
1862 | dev_warn(dev, "Failed to initialize T9 resolution\n"); | ||
1863 | break; | ||
1864 | |||
1865 | case MXT_TOUCH_MULTITOUCHSCREEN_T100: | ||
1866 | num_mt_slots = data->num_touchids; | ||
1867 | error = mxt_read_t100_config(data); | ||
1868 | if (error) | ||
1869 | dev_warn(dev, "Failed to read T100 config\n"); | ||
1870 | break; | ||
1871 | |||
1872 | default: | ||
1873 | dev_err(dev, "Invalid multitouch object\n"); | ||
1874 | return -EINVAL; | ||
1875 | } | ||
1601 | 1876 | ||
1602 | input_dev = input_allocate_device(); | 1877 | input_dev = input_allocate_device(); |
1603 | if (!input_dev) { | 1878 | if (!input_dev) { |
@@ -1612,54 +1887,76 @@ static int mxt_initialize_t9_input_device(struct mxt_data *data) | |||
1612 | input_dev->open = mxt_input_open; | 1887 | input_dev->open = mxt_input_open; |
1613 | input_dev->close = mxt_input_close; | 1888 | input_dev->close = mxt_input_close; |
1614 | 1889 | ||
1615 | __set_bit(EV_ABS, input_dev->evbit); | 1890 | input_set_capability(input_dev, EV_KEY, BTN_TOUCH); |
1616 | __set_bit(EV_KEY, input_dev->evbit); | ||
1617 | __set_bit(BTN_TOUCH, input_dev->keybit); | ||
1618 | 1891 | ||
1619 | if (pdata->t19_num_keys) { | 1892 | /* For single touch */ |
1620 | __set_bit(INPUT_PROP_BUTTONPAD, input_dev->propbit); | 1893 | input_set_abs_params(input_dev, ABS_X, 0, data->max_x, 0, 0); |
1894 | input_set_abs_params(input_dev, ABS_Y, 0, data->max_y, 0, 0); | ||
1621 | 1895 | ||
1622 | for (i = 0; i < pdata->t19_num_keys; i++) | 1896 | if (data->multitouch == MXT_TOUCH_MULTI_T9 || |
1623 | if (pdata->t19_keymap[i] != KEY_RESERVED) | 1897 | (data->multitouch == MXT_TOUCH_MULTITOUCHSCREEN_T100 && |
1624 | input_set_capability(input_dev, EV_KEY, | 1898 | data->t100_aux_ampl)) { |
1625 | pdata->t19_keymap[i]); | 1899 | input_set_abs_params(input_dev, ABS_PRESSURE, 0, 255, 0, 0); |
1900 | } | ||
1626 | 1901 | ||
1902 | /* If device has buttons we assume it is a touchpad */ | ||
1903 | if (pdata->t19_num_keys) { | ||
1904 | mxt_set_up_as_touchpad(input_dev, data); | ||
1627 | mt_flags |= INPUT_MT_POINTER; | 1905 | mt_flags |= INPUT_MT_POINTER; |
1628 | |||
1629 | input_abs_set_res(input_dev, ABS_X, MXT_PIXELS_PER_MM); | ||
1630 | input_abs_set_res(input_dev, ABS_Y, MXT_PIXELS_PER_MM); | ||
1631 | input_abs_set_res(input_dev, ABS_MT_POSITION_X, | ||
1632 | MXT_PIXELS_PER_MM); | ||
1633 | input_abs_set_res(input_dev, ABS_MT_POSITION_Y, | ||
1634 | MXT_PIXELS_PER_MM); | ||
1635 | |||
1636 | input_dev->name = "Atmel maXTouch Touchpad"; | ||
1637 | } | 1906 | } |
1638 | 1907 | ||
1639 | /* For single touch */ | ||
1640 | input_set_abs_params(input_dev, ABS_X, | ||
1641 | 0, data->max_x, 0, 0); | ||
1642 | input_set_abs_params(input_dev, ABS_Y, | ||
1643 | 0, data->max_y, 0, 0); | ||
1644 | input_set_abs_params(input_dev, ABS_PRESSURE, | ||
1645 | 0, 255, 0, 0); | ||
1646 | |||
1647 | /* For multi touch */ | 1908 | /* For multi touch */ |
1648 | num_mt_slots = data->T9_reportid_max - data->T9_reportid_min + 1; | ||
1649 | error = input_mt_init_slots(input_dev, num_mt_slots, mt_flags); | 1909 | error = input_mt_init_slots(input_dev, num_mt_slots, mt_flags); |
1650 | if (error) { | 1910 | if (error) { |
1651 | dev_err(dev, "Error %d initialising slots\n", error); | 1911 | dev_err(dev, "Error %d initialising slots\n", error); |
1652 | goto err_free_mem; | 1912 | goto err_free_mem; |
1653 | } | 1913 | } |
1654 | 1914 | ||
1655 | input_set_abs_params(input_dev, ABS_MT_TOUCH_MAJOR, | 1915 | if (data->multitouch == MXT_TOUCH_MULTITOUCHSCREEN_T100) { |
1656 | 0, MXT_MAX_AREA, 0, 0); | 1916 | input_set_abs_params(input_dev, ABS_MT_TOOL_TYPE, |
1917 | 0, MT_TOOL_MAX, 0, 0); | ||
1918 | input_set_abs_params(input_dev, ABS_MT_DISTANCE, | ||
1919 | MXT_DISTANCE_ACTIVE_TOUCH, | ||
1920 | MXT_DISTANCE_HOVERING, | ||
1921 | 0, 0); | ||
1922 | } | ||
1923 | |||
1657 | input_set_abs_params(input_dev, ABS_MT_POSITION_X, | 1924 | input_set_abs_params(input_dev, ABS_MT_POSITION_X, |
1658 | 0, data->max_x, 0, 0); | 1925 | 0, data->max_x, 0, 0); |
1659 | input_set_abs_params(input_dev, ABS_MT_POSITION_Y, | 1926 | input_set_abs_params(input_dev, ABS_MT_POSITION_Y, |
1660 | 0, data->max_y, 0, 0); | 1927 | 0, data->max_y, 0, 0); |
1661 | input_set_abs_params(input_dev, ABS_MT_PRESSURE, | 1928 | |
1662 | 0, 255, 0, 0); | 1929 | if (data->multitouch == MXT_TOUCH_MULTI_T9 || |
1930 | (data->multitouch == MXT_TOUCH_MULTITOUCHSCREEN_T100 && | ||
1931 | data->t100_aux_area)) { | ||
1932 | input_set_abs_params(input_dev, ABS_MT_TOUCH_MAJOR, | ||
1933 | 0, MXT_MAX_AREA, 0, 0); | ||
1934 | } | ||
1935 | |||
1936 | if (data->multitouch == MXT_TOUCH_MULTI_T9 || | ||
1937 | (data->multitouch == MXT_TOUCH_MULTITOUCHSCREEN_T100 && | ||
1938 | data->t100_aux_ampl)) { | ||
1939 | input_set_abs_params(input_dev, ABS_MT_PRESSURE, | ||
1940 | 0, 255, 0, 0); | ||
1941 | } | ||
1942 | |||
1943 | if (data->multitouch == MXT_TOUCH_MULTITOUCHSCREEN_T100 && | ||
1944 | data->t100_aux_vect) { | ||
1945 | input_set_abs_params(input_dev, ABS_MT_ORIENTATION, | ||
1946 | 0, 255, 0, 0); | ||
1947 | } | ||
1948 | |||
1949 | if (data->multitouch == MXT_TOUCH_MULTITOUCHSCREEN_T100 && | ||
1950 | data->t100_aux_ampl) { | ||
1951 | input_set_abs_params(input_dev, ABS_MT_PRESSURE, | ||
1952 | 0, 255, 0, 0); | ||
1953 | } | ||
1954 | |||
1955 | if (data->multitouch == MXT_TOUCH_MULTITOUCHSCREEN_T100 && | ||
1956 | data->t100_aux_vect) { | ||
1957 | input_set_abs_params(input_dev, ABS_MT_ORIENTATION, | ||
1958 | 0, 255, 0, 0); | ||
1959 | } | ||
1663 | 1960 | ||
1664 | input_set_drvdata(input_dev, data); | 1961 | input_set_drvdata(input_dev, data); |
1665 | 1962 | ||
@@ -1765,9 +2062,13 @@ static int mxt_configure_objects(struct mxt_data *data, | |||
1765 | dev_warn(dev, "Error %d updating config\n", error); | 2062 | dev_warn(dev, "Error %d updating config\n", error); |
1766 | } | 2063 | } |
1767 | 2064 | ||
1768 | error = mxt_initialize_t9_input_device(data); | 2065 | if (data->multitouch) { |
1769 | if (error) | 2066 | error = mxt_initialize_input_device(data); |
1770 | return error; | 2067 | if (error) |
2068 | return error; | ||
2069 | } else { | ||
2070 | dev_warn(dev, "No touch object detected\n"); | ||
2071 | } | ||
1771 | 2072 | ||
1772 | dev_info(dev, | 2073 | dev_info(dev, |
1773 | "Family: %u Variant: %u Firmware V%u.%u.%02X Objects: %u\n", | 2074 | "Family: %u Variant: %u Firmware V%u.%u.%02X Objects: %u\n", |
@@ -2044,15 +2345,13 @@ static const struct attribute_group mxt_attr_group = { | |||
2044 | static void mxt_start(struct mxt_data *data) | 2345 | static void mxt_start(struct mxt_data *data) |
2045 | { | 2346 | { |
2046 | /* Touch enable */ | 2347 | /* Touch enable */ |
2047 | mxt_write_object(data, | 2348 | mxt_write_object(data, data->multitouch, MXT_TOUCH_CTRL, 0x83); |
2048 | MXT_TOUCH_MULTI_T9, MXT_TOUCH_CTRL, 0x83); | ||
2049 | } | 2349 | } |
2050 | 2350 | ||
2051 | static void mxt_stop(struct mxt_data *data) | 2351 | static void mxt_stop(struct mxt_data *data) |
2052 | { | 2352 | { |
2053 | /* Touch disable */ | 2353 | /* Touch disable */ |
2054 | mxt_write_object(data, | 2354 | mxt_write_object(data, data->multitouch, MXT_TOUCH_CTRL, 0); |
2055 | MXT_TOUCH_MULTI_T9, MXT_TOUCH_CTRL, 0); | ||
2056 | } | 2355 | } |
2057 | 2356 | ||
2058 | static int mxt_input_open(struct input_dev *dev) | 2357 | static int mxt_input_open(struct input_dev *dev) |