Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0-only
0002 
0003 #include <linux/bits.h>
0004 #include <linux/delay.h>
0005 #include <linux/i2c.h>
0006 #include <linux/input.h>
0007 #include <linux/input/mt.h>
0008 #include <linux/input/touchscreen.h>
0009 #include <linux/kernel.h>
0010 #include <linux/module.h>
0011 #include <linux/property.h>
0012 #include <linux/regulator/consumer.h>
0013 
0014 #define IST3038C_HIB_ACCESS     (0x800B << 16)
0015 #define IST3038C_DIRECT_ACCESS      BIT(31)
0016 #define IST3038C_REG_CHIPID     0x40001000
0017 #define IST3038C_REG_HIB_BASE       0x30000100
0018 #define IST3038C_REG_TOUCH_STATUS   (IST3038C_REG_HIB_BASE | IST3038C_HIB_ACCESS)
0019 #define IST3038C_REG_TOUCH_COORD    (IST3038C_REG_HIB_BASE | IST3038C_HIB_ACCESS | 0x8)
0020 #define IST3038C_REG_INTR_MESSAGE   (IST3038C_REG_HIB_BASE | IST3038C_HIB_ACCESS | 0x4)
0021 #define IST3038C_WHOAMI         0x38c
0022 #define IST3038C_CHIP_ON_DELAY_MS   60
0023 #define IST3038C_I2C_RETRY_COUNT    3
0024 #define IST3038C_MAX_FINGER_NUM     10
0025 #define IST3038C_X_MASK         GENMASK(23, 12)
0026 #define IST3038C_X_SHIFT        12
0027 #define IST3038C_Y_MASK         GENMASK(11, 0)
0028 #define IST3038C_AREA_MASK      GENMASK(27, 24)
0029 #define IST3038C_AREA_SHIFT     24
0030 #define IST3038C_FINGER_COUNT_MASK  GENMASK(15, 12)
0031 #define IST3038C_FINGER_COUNT_SHIFT 12
0032 #define IST3038C_FINGER_STATUS_MASK GENMASK(9, 0)
0033 
0034 struct imagis_ts {
0035     struct i2c_client *client;
0036     struct input_dev *input_dev;
0037     struct touchscreen_properties prop;
0038     struct regulator_bulk_data supplies[2];
0039 };
0040 
0041 static int imagis_i2c_read_reg(struct imagis_ts *ts,
0042                    unsigned int reg, u32 *data)
0043 {
0044     __be32 ret_be;
0045     __be32 reg_be = cpu_to_be32(reg);
0046     struct i2c_msg msg[] = {
0047         {
0048             .addr = ts->client->addr,
0049             .flags = 0,
0050             .buf = (unsigned char *)&reg_be,
0051             .len = sizeof(reg_be),
0052         }, {
0053             .addr = ts->client->addr,
0054             .flags = I2C_M_RD,
0055             .buf = (unsigned char *)&ret_be,
0056             .len = sizeof(ret_be),
0057         },
0058     };
0059     int ret, error;
0060     int retry = IST3038C_I2C_RETRY_COUNT;
0061 
0062     /* Retry in case the controller fails to respond */
0063     do {
0064         ret = i2c_transfer(ts->client->adapter, msg, ARRAY_SIZE(msg));
0065         if (ret == ARRAY_SIZE(msg)) {
0066             *data = be32_to_cpu(ret_be);
0067             return 0;
0068         }
0069 
0070         error = ret < 0 ? ret : -EIO;
0071         dev_err(&ts->client->dev,
0072             "%s - i2c_transfer failed: %d (%d)\n",
0073             __func__, error, ret);
0074     } while (--retry);
0075 
0076     return error;
0077 }
0078 
0079 static irqreturn_t imagis_interrupt(int irq, void *dev_id)
0080 {
0081     struct imagis_ts *ts = dev_id;
0082     u32 intr_message, finger_status;
0083     unsigned int finger_count, finger_pressed;
0084     int i;
0085     int error;
0086 
0087     error = imagis_i2c_read_reg(ts, IST3038C_REG_INTR_MESSAGE,
0088                     &intr_message);
0089     if (error) {
0090         dev_err(&ts->client->dev,
0091             "failed to read the interrupt message: %d\n", error);
0092         goto out;
0093     }
0094 
0095     finger_count = (intr_message & IST3038C_FINGER_COUNT_MASK) >>
0096                 IST3038C_FINGER_COUNT_SHIFT;
0097     if (finger_count > IST3038C_MAX_FINGER_NUM) {
0098         dev_err(&ts->client->dev,
0099             "finger count %d is more than maximum supported\n",
0100             finger_count);
0101         goto out;
0102     }
0103 
0104     finger_pressed = intr_message & IST3038C_FINGER_STATUS_MASK;
0105 
0106     for (i = 0; i < finger_count; i++) {
0107         error = imagis_i2c_read_reg(ts,
0108                         IST3038C_REG_TOUCH_COORD + (i * 4),
0109                         &finger_status);
0110         if (error) {
0111             dev_err(&ts->client->dev,
0112                 "failed to read coordinates for finger %d: %d\n",
0113                 i, error);
0114             goto out;
0115         }
0116 
0117         input_mt_slot(ts->input_dev, i);
0118         input_mt_report_slot_state(ts->input_dev, MT_TOOL_FINGER,
0119                        finger_pressed & BIT(i));
0120         touchscreen_report_pos(ts->input_dev, &ts->prop,
0121                        (finger_status & IST3038C_X_MASK) >>
0122                         IST3038C_X_SHIFT,
0123                        finger_status & IST3038C_Y_MASK, 1);
0124         input_report_abs(ts->input_dev, ABS_MT_TOUCH_MAJOR,
0125                  (finger_status & IST3038C_AREA_MASK) >>
0126                     IST3038C_AREA_SHIFT);
0127     }
0128 
0129     input_mt_sync_frame(ts->input_dev);
0130     input_sync(ts->input_dev);
0131 
0132 out:
0133     return IRQ_HANDLED;
0134 }
0135 
0136 static void imagis_power_off(void *_ts)
0137 {
0138     struct imagis_ts *ts = _ts;
0139 
0140     regulator_bulk_disable(ARRAY_SIZE(ts->supplies), ts->supplies);
0141 }
0142 
0143 static int imagis_power_on(struct imagis_ts *ts)
0144 {
0145     int error;
0146 
0147     error = regulator_bulk_enable(ARRAY_SIZE(ts->supplies), ts->supplies);
0148     if (error)
0149         return error;
0150 
0151     msleep(IST3038C_CHIP_ON_DELAY_MS);
0152 
0153     return 0;
0154 }
0155 
0156 static int imagis_start(struct imagis_ts *ts)
0157 {
0158     int error;
0159 
0160     error = imagis_power_on(ts);
0161     if (error)
0162         return error;
0163 
0164     enable_irq(ts->client->irq);
0165 
0166     return 0;
0167 }
0168 
0169 static int imagis_stop(struct imagis_ts *ts)
0170 {
0171     disable_irq(ts->client->irq);
0172 
0173     imagis_power_off(ts);
0174 
0175     return 0;
0176 }
0177 
0178 static int imagis_input_open(struct input_dev *dev)
0179 {
0180     struct imagis_ts *ts = input_get_drvdata(dev);
0181 
0182     return imagis_start(ts);
0183 }
0184 
0185 static void imagis_input_close(struct input_dev *dev)
0186 {
0187     struct imagis_ts *ts = input_get_drvdata(dev);
0188 
0189     imagis_stop(ts);
0190 }
0191 
0192 static int imagis_init_input_dev(struct imagis_ts *ts)
0193 {
0194     struct input_dev *input_dev;
0195     int error;
0196 
0197     input_dev = devm_input_allocate_device(&ts->client->dev);
0198     if (!input_dev)
0199         return -ENOMEM;
0200 
0201     ts->input_dev = input_dev;
0202 
0203     input_dev->name = "Imagis capacitive touchscreen";
0204     input_dev->phys = "input/ts";
0205     input_dev->id.bustype = BUS_I2C;
0206     input_dev->open = imagis_input_open;
0207     input_dev->close = imagis_input_close;
0208 
0209     input_set_drvdata(input_dev, ts);
0210 
0211     input_set_capability(input_dev, EV_ABS, ABS_MT_POSITION_X);
0212     input_set_capability(input_dev, EV_ABS, ABS_MT_POSITION_Y);
0213     input_set_abs_params(input_dev, ABS_MT_TOUCH_MAJOR, 0, 255, 0, 0);
0214 
0215     touchscreen_parse_properties(input_dev, true, &ts->prop);
0216     if (!ts->prop.max_x || !ts->prop.max_y) {
0217         dev_err(&ts->client->dev,
0218             "Touchscreen-size-x and/or touchscreen-size-y not set in dts\n");
0219         return -EINVAL;
0220     }
0221 
0222     error = input_mt_init_slots(input_dev,
0223                     IST3038C_MAX_FINGER_NUM,
0224                     INPUT_MT_DIRECT | INPUT_MT_DROP_UNUSED);
0225     if (error) {
0226         dev_err(&ts->client->dev,
0227             "Failed to initialize MT slots: %d", error);
0228         return error;
0229     }
0230 
0231     error = input_register_device(input_dev);
0232     if (error) {
0233         dev_err(&ts->client->dev,
0234             "Failed to register input device: %d", error);
0235         return error;
0236     }
0237 
0238     return 0;
0239 }
0240 
0241 static int imagis_init_regulators(struct imagis_ts *ts)
0242 {
0243     struct i2c_client *client = ts->client;
0244 
0245     ts->supplies[0].supply = "vdd";
0246     ts->supplies[1].supply = "vddio";
0247     return devm_regulator_bulk_get(&client->dev,
0248                        ARRAY_SIZE(ts->supplies),
0249                        ts->supplies);
0250 }
0251 
0252 static int imagis_probe(struct i2c_client *i2c)
0253 {
0254     struct device *dev = &i2c->dev;
0255     struct imagis_ts *ts;
0256     int chip_id, error;
0257 
0258     ts = devm_kzalloc(dev, sizeof(*ts), GFP_KERNEL);
0259     if (!ts)
0260         return -ENOMEM;
0261 
0262     ts->client = i2c;
0263 
0264     error = imagis_init_regulators(ts);
0265     if (error) {
0266         dev_err(dev, "regulator init error: %d\n", error);
0267         return error;
0268     }
0269 
0270     error = imagis_power_on(ts);
0271     if (error) {
0272         dev_err(dev, "failed to enable regulators: %d\n", error);
0273         return error;
0274     }
0275 
0276     error = devm_add_action_or_reset(dev, imagis_power_off, ts);
0277     if (error) {
0278         dev_err(dev, "failed to install poweroff action: %d\n", error);
0279         return error;
0280     }
0281 
0282     error = imagis_i2c_read_reg(ts,
0283             IST3038C_REG_CHIPID | IST3038C_DIRECT_ACCESS,
0284             &chip_id);
0285     if (error) {
0286         dev_err(dev, "chip ID read failure: %d\n", error);
0287         return error;
0288     }
0289 
0290     if (chip_id != IST3038C_WHOAMI) {
0291         dev_err(dev, "unknown chip ID: 0x%x\n", chip_id);
0292         return -EINVAL;
0293     }
0294 
0295     error = devm_request_threaded_irq(dev, i2c->irq,
0296                       NULL, imagis_interrupt,
0297                       IRQF_ONESHOT | IRQF_NO_AUTOEN,
0298                       "imagis-touchscreen", ts);
0299     if (error) {
0300         dev_err(dev, "IRQ %d allocation failure: %d\n",
0301             i2c->irq, error);
0302         return error;
0303     }
0304 
0305     error = imagis_init_input_dev(ts);
0306     if (error)
0307         return error;
0308 
0309     return 0;
0310 }
0311 
0312 static int __maybe_unused imagis_suspend(struct device *dev)
0313 {
0314     struct i2c_client *client = to_i2c_client(dev);
0315     struct imagis_ts *ts = i2c_get_clientdata(client);
0316     int retval = 0;
0317 
0318     mutex_lock(&ts->input_dev->mutex);
0319 
0320     if (input_device_enabled(ts->input_dev))
0321         retval = imagis_stop(ts);
0322 
0323     mutex_unlock(&ts->input_dev->mutex);
0324 
0325     return retval;
0326 }
0327 
0328 static int __maybe_unused imagis_resume(struct device *dev)
0329 {
0330     struct i2c_client *client = to_i2c_client(dev);
0331     struct imagis_ts *ts = i2c_get_clientdata(client);
0332     int retval = 0;
0333 
0334     mutex_lock(&ts->input_dev->mutex);
0335 
0336     if (input_device_enabled(ts->input_dev))
0337         retval = imagis_start(ts);
0338 
0339     mutex_unlock(&ts->input_dev->mutex);
0340 
0341     return retval;
0342 }
0343 
0344 static SIMPLE_DEV_PM_OPS(imagis_pm_ops, imagis_suspend, imagis_resume);
0345 
0346 #ifdef CONFIG_OF
0347 static const struct of_device_id imagis_of_match[] = {
0348     { .compatible = "imagis,ist3038c", },
0349     { },
0350 };
0351 MODULE_DEVICE_TABLE(of, imagis_of_match);
0352 #endif
0353 
0354 static struct i2c_driver imagis_ts_driver = {
0355     .driver = {
0356         .name = "imagis-touchscreen",
0357         .pm = &imagis_pm_ops,
0358         .of_match_table = of_match_ptr(imagis_of_match),
0359     },
0360     .probe_new = imagis_probe,
0361 };
0362 
0363 module_i2c_driver(imagis_ts_driver);
0364 
0365 MODULE_DESCRIPTION("Imagis IST3038C Touchscreen Driver");
0366 MODULE_AUTHOR("Markuss Broks <markuss.broks@gmail.com>");
0367 MODULE_LICENSE("GPL");