资料下载
coding无法使用浏览器打开,必须用git工具下载:
git clone https://e.coding.net/weidongshan/linux/doc_and_source_for_drivers.git
视频观看
百问网驱动大全
I2C接口触摸屏驱动分析参考资料:
-
Linux 5.x内核
- Documentation\devicetree\bindings\input\touchscreen\goodix.txt
- drivers/input/touchscreen/goodix.c
-
Linux 4.x内核
- Documentation\devicetree\bindings\input\touchscreen\goodix.txt
- drivers/input/touchscreen/gt9xx/gt9xx.c
-
设备树
- IMX6ULL:
Linux-4.9.88/arch/arm/boot/dts/100ask_imx6ull-14x14.dts
- STM32MP157:
Linux-5.4/arch/arm/boot/dts/stm32mp15xx-100ask.dtsi
- IMX6ULL:
示例:
i2c@00000000 {
/* ... */
gt928@5d {
compatible = "goodix,gt928";
reg = ;
interrupt-parent = ;
interrupts = ;
irq-gpios = ;
reset-gpios = ;
};
/* ... */
};
作为一个I2C设备,在某个I2C控制器节点下创建一个子节点。 属性:
-
必备,根据这个属性找到驱动程序:
compatible = "xxxx";
-
必备,I2C设备地址:
reg = ;
-
可选:
- 中断
-
复位引脚
&i2c2 {
gt9xx@5d {
compatible = "goodix,gt9xx";
reg = ;
status = "okay";
interrupt-parent = ;
interrupts = ;
pinctrl-names = "default";
pinctrl-0 = ;
/*pinctrl-1 = ;*/
/*
pinctrl-names = "default", "int-output-low", "int-output-high", "int-input";
pinctrl-0 = ;
pinctrl-1 = ;
pinctrl-2 = ;
pinctrl-3 = ;
*/
reset-gpios = ;
irq-gpios = ;
irq-flags = ; /*1:rising 2: falling*/
touchscreen-max-id = ;
touchscreen-size-x = ;
touchscreen-size-y = ;
touchscreen-max-w = ;
touchscreen-max-p = ;
/*touchscreen-key-map = , ;*/ /*KEY_HOMEPAGE, KEY_BACK*/
goodix,type-a-report = ;
goodix,driver-send-cfg = ;
goodix,create-wr-node = ;
goodix,wakeup-with-reset = ;
goodix,resume-in-workqueue = ;
goodix,int-sync = ;
goodix,swap-x2y = ;
goodix,esd-protect = ;
goodix,pen-suppress-finger = ;
goodix,auto-update = ;
goodix,auto-update-cfg = ;
goodix,power-off-sleep = ;
/* ...... */
};
};
2.3 100ASK_STM32MP157
&i2c4 {
gt911@5d {
compatible = "goodix,gt928";
reg = ;
interrupt-parent = ;
interrupts = ;
reset-gpios = ;
irq-gpios = ;
irq-flags = ; /*1:rising 2: falling*/
touchscreen-max-id = ;
touchscreen-size-x = ;
touchscreen-size-y = ;
};
};
3. 驱动程序分析
3.1 分配/设置/注册input_dev
- IMX6ULL Linux 4.x
gtp_probe
ret = gtp_request_input_dev(ts);
ts->input_dev = input_allocate_device();
......
ret = input_register_device(ts->input_dev);
ret = gtp_request_irq(ts);
- STM32MP157 Linux 5.x
goodix_ts_probe
error = request_firmware_nowait(THIS_MODULE, true, ts->cfg_name,
&client->dev, GFP_KERNEL, ts,
goodix_config_cb);
goodix_config_cb
goodix_configure_dev(ts);
ts->input_dev = devm_input_allocate_device(&ts->client->dev);
......
error = input_register_device(ts->input_dev);
error = goodix_request_irq(ts);
3.2 注册中断处理函数
- IMX6ULL Linux 4.x
ret = request_threaded_irq(ts->client->irq, NULL,
gtp_irq_handler,
ts->pdata->irq_flags | IRQF_ONESHOT,
ts->client->name,
ts);
- STM32MP157 Linux 5.x
static int goodix_request_irq(struct goodix_ts_data *ts)
{
return devm_request_threaded_irq(&ts->client->dev, ts->client->irq,
NULL, goodix_ts_irq_handler,
ts->irq_flags, ts->client->name, ts);
}
3.3 中断处理函数分析
通过I2C函数读取数据、上报数据。
- IMX6ULL Linux 4.x
gtp_irq_handler
gtp_work_func(ts);
point_state = gtp_get_points(ts, points, &key_value);
gtp_i2c_read
i2c_transfer
gtp_mt_slot_report(ts, point_state & 0x0f, points);
input_mt_slot
input_mt_report_slot_state
input_report_abs
- STM32MP157 Linux 5.x
goodix_ts_irq_handler
goodix_process_events(ts);
touch_num = goodix_ts_read_input_report(ts, point_data);
goodix_i2c_read
i2c_transfer
goodix_ts_report_touch_9b
input_mt_slot
input_mt_report_slot_state
touchscreen_report_pos
input_report_abs
touch_num = goodix_ts_read_input_report(ts, point_data);
goodix_i2c_read
i2c_transfer
goodix_ts_report_touch_9b
input_mt_slot
input_mt_report_slot_state
touchscreen_report_pos
input_report_abs