^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) // SPDX-License-Identifier: GPL-2.0-only
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) * Driver for Semtech SX8654 I2C touchscreen controller.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) * Copyright (c) 2015 Armadeus Systems
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) * Sébastien Szymanski <sebastien.szymanski@armadeus.com>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) * Using code from:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) * - sx865x.c
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) * Copyright (c) 2013 U-MoBo Srl
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) * Pierluigi Passaro <p.passaro@u-mobo.com>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) * - sx8650.c
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) * Copyright (c) 2009 Wayne Roberts
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) * - tsc2007.c
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) * Copyright (c) 2008 Kwangwoo Lee
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) * - ads7846.c
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) * Copyright (c) 2005 David Brownell
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18) * Copyright (c) 2006 Nokia Corporation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) * - corgi_ts.c
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20) * Copyright (C) 2004-2005 Richard Purdie
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) * - omap_ts.[hc], ads7846.h, ts_osk.c
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) * Copyright (C) 2002 MontaVista Software
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) * Copyright (C) 2004 Texas Instruments
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) * Copyright (C) 2005 Dirk Behme
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) #include <linux/bitops.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) #include <linux/delay.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) #include <linux/gpio/consumer.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) #include <linux/i2c.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) #include <linux/input.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) #include <linux/input/touchscreen.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) #include <linux/interrupt.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) #include <linux/irq.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) #include <linux/module.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) #include <linux/of.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) /* register addresses */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) #define I2C_REG_TOUCH0 0x00
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40) #define I2C_REG_TOUCH1 0x01
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) #define I2C_REG_CHANMASK 0x04
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) #define I2C_REG_IRQMASK 0x22
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) #define I2C_REG_IRQSRC 0x23
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) #define I2C_REG_SOFTRESET 0x3f
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) #define I2C_REG_SX8650_STAT 0x05
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) #define SX8650_STAT_CONVIRQ BIT(7)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) /* commands */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) #define CMD_READ_REGISTER 0x40
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) #define CMD_PENTRG 0xe0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) /* value for I2C_REG_SOFTRESET */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) #define SOFTRESET_VALUE 0xde
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) /* bits for I2C_REG_IRQSRC */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) #define IRQ_PENTOUCH_TOUCHCONVDONE BIT(3)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) #define IRQ_PENRELEASE BIT(2)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) /* bits for RegTouch1 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) #define CONDIRQ 0x20
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) #define RPDNT_100K 0x00
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) #define FILT_7SA 0x03
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65) /* bits for I2C_REG_CHANMASK */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) #define CONV_X BIT(7)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) #define CONV_Y BIT(6)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) /* coordinates rate: higher nibble of CTRL0 register */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) #define RATE_MANUAL 0x00
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) #define RATE_5000CPS 0xf0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73) /* power delay: lower nibble of CTRL0 register */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) #define POWDLY_1_1MS 0x0b
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) /* for sx8650, as we have no pen release IRQ there: timeout in ns following the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) * last PENIRQ after which we assume the pen is lifted.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) #define SX8650_PENIRQ_TIMEOUT msecs_to_jiffies(10)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) #define MAX_12BIT ((1 << 12) - 1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) #define MAX_I2C_READ_LEN 10 /* see datasheet section 5.1.5 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) /* channel definition */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) #define CH_X 0x00
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) #define CH_Y 0x01
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) struct sx865x_data {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) u8 cmd_manual;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) u8 chan_mask;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91) bool has_irq_penrelease;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) bool has_reg_irqmask;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) irq_handler_t irqh;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) struct sx8654 {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) struct input_dev *input;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) struct i2c_client *client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) struct gpio_desc *gpio_reset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) spinlock_t lock; /* for input reporting from irq/timer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) struct timer_list timer;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) struct touchscreen_properties props;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) const struct sx865x_data *data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) static inline void sx865x_penrelease(struct sx8654 *ts)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) struct input_dev *input_dev = ts->input;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) input_report_key(input_dev, BTN_TOUCH, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) input_sync(input_dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) static void sx865x_penrelease_timer_handler(struct timer_list *t)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) struct sx8654 *ts = from_timer(ts, t, timer);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) unsigned long flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) spin_lock_irqsave(&ts->lock, flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) sx865x_penrelease(ts);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) spin_unlock_irqrestore(&ts->lock, flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) dev_dbg(&ts->client->dev, "penrelease by timer\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) static irqreturn_t sx8650_irq(int irq, void *handle)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) struct sx8654 *ts = handle;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) struct device *dev = &ts->client->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) int len, i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) unsigned long flags;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) u8 stat;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) u16 x, y;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) u16 ch;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) u16 chdata;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) __be16 data[MAX_I2C_READ_LEN / sizeof(__be16)];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) u8 nchan = hweight32(ts->data->chan_mask);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) u8 readlen = nchan * sizeof(*data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) stat = i2c_smbus_read_byte_data(ts->client, CMD_READ_REGISTER
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) | I2C_REG_SX8650_STAT);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) if (!(stat & SX8650_STAT_CONVIRQ)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) dev_dbg(dev, "%s ignore stat [0x%02x]", __func__, stat);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) return IRQ_HANDLED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) len = i2c_master_recv(ts->client, (u8 *)data, readlen);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) if (len != readlen) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) dev_dbg(dev, "ignore short recv (%d)\n", len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) return IRQ_HANDLED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) spin_lock_irqsave(&ts->lock, flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) x = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) y = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) for (i = 0; i < nchan; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) chdata = be16_to_cpu(data[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) if (unlikely(chdata == 0xFFFF)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) dev_dbg(dev, "invalid qualified data @ %d\n", i);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) } else if (unlikely(chdata & 0x8000)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) dev_warn(dev, "hibit @ %d [0x%04x]\n", i, chdata);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) ch = chdata >> 12;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) if (ch == CH_X)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) x = chdata & MAX_12BIT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) else if (ch == CH_Y)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) y = chdata & MAX_12BIT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) dev_warn(dev, "unknown channel %d [0x%04x]\n", ch,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) chdata);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) touchscreen_report_pos(ts->input, &ts->props, x, y, false);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) input_report_key(ts->input, BTN_TOUCH, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) input_sync(ts->input);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) dev_dbg(dev, "point(%4d,%4d)\n", x, y);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) mod_timer(&ts->timer, jiffies + SX8650_PENIRQ_TIMEOUT);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) spin_unlock_irqrestore(&ts->lock, flags);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) return IRQ_HANDLED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) static irqreturn_t sx8654_irq(int irq, void *handle)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) struct sx8654 *sx8654 = handle;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) int irqsrc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) u8 data[4];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) unsigned int x, y;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) int retval;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) irqsrc = i2c_smbus_read_byte_data(sx8654->client,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) CMD_READ_REGISTER | I2C_REG_IRQSRC);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) dev_dbg(&sx8654->client->dev, "irqsrc = 0x%x", irqsrc);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) if (irqsrc < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) if (irqsrc & IRQ_PENRELEASE) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) dev_dbg(&sx8654->client->dev, "pen release interrupt");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) input_report_key(sx8654->input, BTN_TOUCH, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) input_sync(sx8654->input);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) if (irqsrc & IRQ_PENTOUCH_TOUCHCONVDONE) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) dev_dbg(&sx8654->client->dev, "pen touch interrupt");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) retval = i2c_master_recv(sx8654->client, data, sizeof(data));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) if (retval != sizeof(data))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219) goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) /* invalid data */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) if (unlikely(data[0] & 0x80 || data[2] & 0x80))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) x = ((data[0] & 0xf) << 8) | (data[1]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) y = ((data[2] & 0xf) << 8) | (data[3]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) touchscreen_report_pos(sx8654->input, &sx8654->props, x, y,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) false);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) input_report_key(sx8654->input, BTN_TOUCH, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) input_sync(sx8654->input);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) dev_dbg(&sx8654->client->dev, "point(%4d,%4d)\n", x, y);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) return IRQ_HANDLED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) static int sx8654_reset(struct sx8654 *ts)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) int err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) if (ts->gpio_reset) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) gpiod_set_value_cansleep(ts->gpio_reset, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) udelay(2); /* Tpulse > 1µs */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) gpiod_set_value_cansleep(ts->gpio_reset, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) dev_dbg(&ts->client->dev, "NRST unavailable, try softreset\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) err = i2c_smbus_write_byte_data(ts->client, I2C_REG_SOFTRESET,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) SOFTRESET_VALUE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) static int sx8654_open(struct input_dev *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) struct sx8654 *sx8654 = input_get_drvdata(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) struct i2c_client *client = sx8654->client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) int error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) /* enable pen trigger mode */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) error = i2c_smbus_write_byte_data(client, I2C_REG_TOUCH0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) RATE_5000CPS | POWDLY_1_1MS);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) if (error) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) dev_err(&client->dev, "writing to I2C_REG_TOUCH0 failed");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) error = i2c_smbus_write_byte(client, CMD_PENTRG);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) if (error) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) dev_err(&client->dev, "writing command CMD_PENTRG failed");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) enable_irq(client->irq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) static void sx8654_close(struct input_dev *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) struct sx8654 *sx8654 = input_get_drvdata(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287) struct i2c_client *client = sx8654->client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) int error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290) disable_irq(client->irq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) if (!sx8654->data->has_irq_penrelease)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293) del_timer_sync(&sx8654->timer);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) /* enable manual mode mode */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) error = i2c_smbus_write_byte(client, sx8654->data->cmd_manual);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) if (error) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) dev_err(&client->dev, "writing command CMD_MANUAL failed");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) error = i2c_smbus_write_byte_data(client, I2C_REG_TOUCH0, RATE_MANUAL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) if (error) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) dev_err(&client->dev, "writing to I2C_REG_TOUCH0 failed");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) static int sx8654_probe(struct i2c_client *client,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) const struct i2c_device_id *id)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) struct sx8654 *sx8654;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) struct input_dev *input;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) int error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) if (!i2c_check_functionality(client->adapter,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) I2C_FUNC_SMBUS_READ_WORD_DATA))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) return -ENXIO;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) sx8654 = devm_kzalloc(&client->dev, sizeof(*sx8654), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) if (!sx8654)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) sx8654->gpio_reset = devm_gpiod_get_optional(&client->dev, "reset",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325) GPIOD_OUT_HIGH);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) if (IS_ERR(sx8654->gpio_reset)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) error = PTR_ERR(sx8654->gpio_reset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) if (error != -EPROBE_DEFER)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) dev_err(&client->dev, "unable to get reset-gpio: %d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) error);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) dev_dbg(&client->dev, "got GPIO reset pin\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) sx8654->data = device_get_match_data(&client->dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) if (!sx8654->data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) sx8654->data = (const struct sx865x_data *)id->driver_data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) if (!sx8654->data) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) dev_err(&client->dev, "invalid or missing device data\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) if (!sx8654->data->has_irq_penrelease) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) dev_dbg(&client->dev, "use timer for penrelease\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) timer_setup(&sx8654->timer, sx865x_penrelease_timer_handler, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) spin_lock_init(&sx8654->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) input = devm_input_allocate_device(&client->dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) if (!input)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353) input->name = "SX8654 I2C Touchscreen";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) input->id.bustype = BUS_I2C;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) input->dev.parent = &client->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356) input->open = sx8654_open;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) input->close = sx8654_close;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359) __set_bit(INPUT_PROP_DIRECT, input->propbit);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) input_set_capability(input, EV_KEY, BTN_TOUCH);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) input_set_abs_params(input, ABS_X, 0, MAX_12BIT, 0, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) input_set_abs_params(input, ABS_Y, 0, MAX_12BIT, 0, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) touchscreen_parse_properties(input, false, &sx8654->props);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366) sx8654->client = client;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) sx8654->input = input;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) input_set_drvdata(sx8654->input, sx8654);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) error = sx8654_reset(sx8654);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) if (error) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) dev_err(&client->dev, "reset failed");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) error = i2c_smbus_write_byte_data(client, I2C_REG_CHANMASK,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) sx8654->data->chan_mask);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) if (error) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380) dev_err(&client->dev, "writing to I2C_REG_CHANMASK failed");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381) return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) if (sx8654->data->has_reg_irqmask) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) error = i2c_smbus_write_byte_data(client, I2C_REG_IRQMASK,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) IRQ_PENTOUCH_TOUCHCONVDONE |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) IRQ_PENRELEASE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388) if (error) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) dev_err(&client->dev, "writing I2C_REG_IRQMASK failed");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390) return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394) error = i2c_smbus_write_byte_data(client, I2C_REG_TOUCH1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) CONDIRQ | RPDNT_100K | FILT_7SA);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396) if (error) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) dev_err(&client->dev, "writing to I2C_REG_TOUCH1 failed");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) error = devm_request_threaded_irq(&client->dev, client->irq,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402) NULL, sx8654->data->irqh,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403) IRQF_ONESHOT,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) client->name, sx8654);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405) if (error) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) dev_err(&client->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) "Failed to enable IRQ %d, error: %d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) client->irq, error);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) /* Disable the IRQ, we'll enable it in sx8654_open() */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413) disable_irq(client->irq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) error = input_register_device(sx8654->input);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416) if (error)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417) return error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) static const struct sx865x_data sx8650_data = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423) .cmd_manual = 0xb0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) .has_irq_penrelease = false,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425) .has_reg_irqmask = false,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426) .chan_mask = (CONV_X | CONV_Y),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427) .irqh = sx8650_irq,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) static const struct sx865x_data sx8654_data = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) .cmd_manual = 0xc0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432) .has_irq_penrelease = true,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) .has_reg_irqmask = true,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434) .chan_mask = (CONV_X | CONV_Y),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435) .irqh = sx8654_irq,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438) #ifdef CONFIG_OF
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 439) static const struct of_device_id sx8654_of_match[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 440) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 441) .compatible = "semtech,sx8650",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 442) .data = &sx8650_data,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 443) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 444) .compatible = "semtech,sx8654",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 445) .data = &sx8654_data,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 446) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 447) .compatible = "semtech,sx8655",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 448) .data = &sx8654_data,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 449) }, {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 450) .compatible = "semtech,sx8656",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 451) .data = &sx8654_data,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 452) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 453) { }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 454) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 455) MODULE_DEVICE_TABLE(of, sx8654_of_match);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 456) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 457)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 458) static const struct i2c_device_id sx8654_id_table[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 459) { .name = "semtech_sx8650", .driver_data = (long)&sx8650_data },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 460) { .name = "semtech_sx8654", .driver_data = (long)&sx8654_data },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 461) { .name = "semtech_sx8655", .driver_data = (long)&sx8654_data },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 462) { .name = "semtech_sx8656", .driver_data = (long)&sx8654_data },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 463) { }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 464) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 465) MODULE_DEVICE_TABLE(i2c, sx8654_id_table);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 466)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 467) static struct i2c_driver sx8654_driver = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 468) .driver = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 469) .name = "sx8654",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 470) .of_match_table = of_match_ptr(sx8654_of_match),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 471) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 472) .id_table = sx8654_id_table,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 473) .probe = sx8654_probe,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 474) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 475) module_i2c_driver(sx8654_driver);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 476)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 477) MODULE_AUTHOR("Sébastien Szymanski <sebastien.szymanski@armadeus.com>");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 478) MODULE_DESCRIPTION("Semtech SX8654 I2C Touchscreen Driver");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 479) MODULE_LICENSE("GPL");