1 /*
2 * Copyright (c) 2023 Espressif Systems (Shanghai) Co., Ltd.
3 *
4 * SPDX-License-Identifier: Apache-2.0
5 */
6
7 #define DT_DRV_COMPAT espressif_esp32_touch
8
9 #include <zephyr/device.h>
10 #include <zephyr/input/input.h>
11 #include <zephyr/kernel.h>
12 #include <zephyr/logging/log.h>
13 #include <zephyr/drivers/interrupt_controller/intc_esp32.h>
14
15 #include <esp_err.h>
16 #include <soc/soc_pins.h>
17 #include <soc/periph_defs.h>
18 #include <hal/touch_sensor_types.h>
19 #include <hal/touch_sensor_hal.h>
20 #include <driver/rtc_io.h>
21 #include <esp_intr_alloc.h>
22
23 LOG_MODULE_REGISTER(espressif_esp32_touch, CONFIG_INPUT_LOG_LEVEL);
24
25 #define ESP32_SCAN_DONE_MAX_COUNT 5
26
27 #if defined(CONFIG_SOC_SERIES_ESP32)
28 #define ESP32_RTC_INTR_MSK RTC_CNTL_TOUCH_INT_ST_M
29 #elif defined(CONFIG_SOC_SERIES_ESP32S2) || defined(CONFIG_SOC_SERIES_ESP32S3)
30
31 #define ESP32_RTC_INTR_MSK (RTC_CNTL_TOUCH_DONE_INT_ST_M | \
32 RTC_CNTL_TOUCH_ACTIVE_INT_ST_M | \
33 RTC_CNTL_TOUCH_INACTIVE_INT_ST_M | \
34 RTC_CNTL_TOUCH_SCAN_DONE_INT_ST_M | \
35 RTC_CNTL_TOUCH_TIMEOUT_INT_ST_M)
36
37 #define ESP32_TOUCH_PAD_INTR_MASK (TOUCH_PAD_INTR_MASK_ACTIVE | \
38 TOUCH_PAD_INTR_MASK_INACTIVE | \
39 TOUCH_PAD_INTR_MASK_TIMEOUT | \
40 TOUCH_PAD_INTR_MASK_SCAN_DONE)
41
42 #endif /* defined(CONFIG_SOC_SERIES_ESP32) */
43
44 struct esp32_touch_sensor_channel_config {
45 int32_t channel_num;
46 int32_t channel_sens;
47 uint32_t zephyr_code;
48 };
49
50 struct esp32_touch_sensor_config {
51 uint32_t debounce_interval_ms;
52 int num_channels;
53 int href_microvolt_enum_idx;
54 int lref_microvolt_enum_idx;
55 int href_atten_microvolt_enum_idx;
56 int filter_mode;
57 int filter_debounce_cnt;
58 int filter_noise_thr;
59 int filter_jitter_step;
60 int filter_smooth_level;
61 const struct esp32_touch_sensor_channel_config *channel_cfg;
62 struct esp32_touch_sensor_channel_data *channel_data;
63 };
64
65 struct esp32_touch_sensor_channel_data {
66 const struct device *dev;
67 struct k_work_delayable work;
68 uint32_t status;
69 #if defined(CONFIG_SOC_SERIES_ESP32S2) || defined(CONFIG_SOC_SERIES_ESP32S3)
70 uint32_t last_status;
71 #endif /* defined(CONFIG_SOC_SERIES_ESP32S2) || defined(CONFIG_SOC_SERIES_ESP32S3) */
72 };
73
74 struct esp32_touch_sensor_data {
75 };
76
esp32_touch_sensor_interrupt_cb(void * arg)77 static void esp32_touch_sensor_interrupt_cb(void *arg)
78 {
79 const struct device *dev = arg;
80 const struct esp32_touch_sensor_config *dev_cfg = dev->config;
81 const struct esp32_touch_sensor_channel_config *channel_cfg;
82 const int num_channels = dev_cfg->num_channels;
83 uint32_t pad_status;
84
85 #if defined(CONFIG_SOC_SERIES_ESP32)
86 touch_hal_intr_clear();
87
88 #elif defined(CONFIG_SOC_SERIES_ESP32S2) || defined(CONFIG_SOC_SERIES_ESP32S3)
89 static uint8_t scan_done_counter;
90
91 touch_pad_intr_mask_t intr_mask = touch_hal_read_intr_status_mask();
92
93 if (intr_mask & TOUCH_PAD_INTR_MASK_SCAN_DONE) {
94 if (++scan_done_counter == ESP32_SCAN_DONE_MAX_COUNT) {
95 touch_hal_intr_disable(TOUCH_PAD_INTR_MASK_SCAN_DONE);
96 for (int i = 0; i < num_channels; i++) {
97 channel_cfg = &dev_cfg->channel_cfg[i];
98
99 /* Set interrupt threshold */
100 uint32_t benchmark_value;
101
102 touch_hal_read_benchmark(channel_cfg->channel_num,
103 &benchmark_value);
104 touch_hal_set_threshold(channel_cfg->channel_num,
105 channel_cfg->channel_sens * benchmark_value / 100);
106 }
107 }
108 return;
109 }
110 #endif /* defined(CONFIG_SOC_SERIES_ESP32) */
111
112 touch_hal_read_trigger_status_mask(&pad_status);
113 #if defined(CONFIG_SOC_SERIES_ESP32)
114 touch_hal_clear_trigger_status_mask();
115 #endif /* defined(CONFIG_SOC_SERIES_ESP32) */
116 for (int i = 0; i < num_channels; i++) {
117 uint32_t channel_status;
118
119 channel_cfg = &dev_cfg->channel_cfg[i];
120 channel_status = (pad_status >> channel_cfg->channel_num) & 0x01;
121
122 #if defined(CONFIG_SOC_SERIES_ESP32)
123 if (channel_status != 0) {
124 #elif defined(CONFIG_SOC_SERIES_ESP32S2) || defined(CONFIG_SOC_SERIES_ESP32S3)
125 uint32_t channel_num = (uint32_t)touch_hal_get_current_meas_channel();
126
127 if (channel_cfg->channel_num == channel_num) {
128 #endif /* CONFIG_SOC_SERIES_ESP32 */
129 struct esp32_touch_sensor_channel_data
130 *channel_data = &dev_cfg->channel_data[i];
131
132 channel_data->status = channel_status;
133 (void)k_work_reschedule(&channel_data->work,
134 K_MSEC(dev_cfg->debounce_interval_ms));
135 }
136 }
137 }
138
139 static void esp32_touch_rtc_isr(void *arg)
140 {
141 uint32_t status = REG_READ(RTC_CNTL_INT_ST_REG);
142
143 if (!(status & ESP32_RTC_INTR_MSK)) {
144 return;
145 }
146
147 esp32_touch_sensor_interrupt_cb(arg);
148 REG_WRITE(RTC_CNTL_INT_CLR_REG, status);
149 }
150
151
152 /**
153 * Handle debounced touch sensor touch state.
154 */
155 static void esp32_touch_sensor_change_deferred(struct k_work *work)
156 {
157 struct k_work_delayable *dwork = k_work_delayable_from_work(work);
158 struct esp32_touch_sensor_channel_data *channel_data =
159 CONTAINER_OF(dwork, struct esp32_touch_sensor_channel_data, work);
160 const struct device *dev = channel_data->dev;
161 const struct esp32_touch_sensor_config *dev_cfg = dev->config;
162 int key_index = channel_data - &dev_cfg->channel_data[0];
163 const struct esp32_touch_sensor_channel_config
164 *channel_cfg = &dev_cfg->channel_cfg[key_index];
165
166 #if defined(CONFIG_SOC_SERIES_ESP32S2) || defined(CONFIG_SOC_SERIES_ESP32S3)
167 if (channel_data->last_status != channel_data->status) {
168 #endif /* defined(CONFIG_SOC_SERIES_ESP32S2) || defined(CONFIG_SOC_SERIES_ESP32S3) */
169 input_report_key(dev, channel_cfg->zephyr_code,
170 channel_data->status, true, K_FOREVER);
171 #if defined(CONFIG_SOC_SERIES_ESP32S2) || defined(CONFIG_SOC_SERIES_ESP32S3)
172 channel_data->last_status = channel_data->status;
173 }
174 #endif /* defined(CONFIG_SOC_SERIES_ESP32S2) || defined(CONFIG_SOC_SERIES_ESP32S3) */
175 }
176
177 static int esp32_touch_sensor_init(const struct device *dev)
178 {
179 esp_err_t err, flags;
180
181 const struct esp32_touch_sensor_config *dev_cfg = dev->config;
182 const int num_channels = dev_cfg->num_channels;
183
184 touch_hal_init();
185
186 #if defined(CONFIG_SOC_SERIES_ESP32)
187 touch_hal_volt_t volt = {
188 .refh = dev_cfg->href_microvolt_enum_idx,
189 .refh = dev_cfg->href_microvolt_enum_idx,
190 .atten = dev_cfg->href_atten_microvolt_enum_idx
191 };
192
193 touch_hal_set_voltage(&volt);
194 touch_hal_set_fsm_mode(TOUCH_FSM_MODE_TIMER);
195 #endif /* defined(CONFIG_SOC_SERIES_ESP32) */
196
197 for (int i = 0; i < num_channels; i++) {
198 struct esp32_touch_sensor_channel_data *channel_data = &dev_cfg->channel_data[i];
199 const struct esp32_touch_sensor_channel_config *channel_cfg =
200 &dev_cfg->channel_cfg[i];
201
202 if (!(channel_cfg->channel_num > 0 &&
203 channel_cfg->channel_num < SOC_TOUCH_SENSOR_NUM)) {
204 LOG_ERR("Touch %d configuration failed: "
205 "Touch channel error", i);
206 return -EINVAL;
207 }
208
209 #if defined(CONFIG_SOC_SERIES_ESP32S2) || defined(CONFIG_SOC_SERIES_ESP32S3)
210 if (channel_cfg->channel_num == SOC_TOUCH_DENOISE_CHANNEL) {
211 LOG_ERR("Touch %d configuration failed: "
212 "TOUCH0 is internal denoise channel", i);
213 return -EINVAL;
214 }
215 #endif /* defined(CONFIG_SOC_SERIES_ESP32S2) || defined(CONFIG_SOC_SERIES_ESP32S3) */
216
217 gpio_num_t gpio_num = touch_sensor_channel_io_map[channel_cfg->channel_num];
218
219 rtc_gpio_init(gpio_num);
220 rtc_gpio_set_direction(gpio_num, RTC_GPIO_MODE_DISABLED);
221 rtc_gpio_pulldown_dis(gpio_num);
222 rtc_gpio_pullup_dis(gpio_num);
223
224 touch_hal_config(channel_cfg->channel_num);
225 #if defined(CONFIG_SOC_SERIES_ESP32)
226 touch_hal_set_threshold(channel_cfg->channel_num, 0);
227 touch_hal_set_group_mask(BIT(channel_cfg->channel_num),
228 BIT(channel_cfg->channel_num));
229 #endif /* defined(CONFIG_SOC_SERIES_ESP32) */
230 touch_hal_set_channel_mask(BIT(channel_cfg->channel_num));
231
232 channel_data->status = 0;
233 #if defined(CONFIG_SOC_SERIES_ESP32S2) || defined(CONFIG_SOC_SERIES_ESP32S3)
234 channel_data->last_status = 0;
235 #endif /* defined(CONFIG_SOC_SERIES_ESP32S2) || defined(CONFIG_SOC_SERIES_ESP32S3) */
236 channel_data->dev = dev;
237
238 k_work_init_delayable(&channel_data->work, esp32_touch_sensor_change_deferred);
239 }
240
241 #if defined(CONFIG_SOC_SERIES_ESP32)
242 for (int i = 0; i < num_channels; i++) {
243 const struct esp32_touch_sensor_channel_config *channel_cfg =
244 &dev_cfg->channel_cfg[i];
245 uint32_t ref_time;
246
247 ref_time = k_uptime_get_32();
248 while (!touch_hal_meas_is_done()) {
249 if (k_uptime_get_32() - ref_time > 500) {
250 return -ETIMEDOUT;
251 }
252 k_busy_wait(1000);
253 }
254 uint16_t touch_value = touch_hal_read_raw_data(channel_cfg->channel_num);
255
256 touch_hal_set_threshold(channel_cfg->channel_num,
257 touch_value * (100 - channel_cfg->channel_num) / 100);
258 }
259
260 #elif defined(CONFIG_SOC_SERIES_ESP32S2) || defined(CONFIG_SOC_SERIES_ESP32S3)
261 touch_filter_config_t filter_info = {
262 .mode = dev_cfg->filter_mode,
263 .debounce_cnt = dev_cfg->filter_debounce_cnt,
264 .noise_thr = dev_cfg->filter_noise_thr,
265 .jitter_step = dev_cfg->filter_jitter_step,
266 .smh_lvl = dev_cfg->filter_smooth_level,
267 };
268 touch_hal_filter_set_config(&filter_info);
269 touch_hal_filter_enable();
270
271 touch_hal_timeout_enable();
272 touch_hal_timeout_set_threshold(SOC_TOUCH_PAD_THRESHOLD_MAX);
273 #endif /* defined(CONFIG_SOC_SERIES_ESP32) */
274
275 flags = ESP_PRIO_TO_FLAGS(DT_IRQ_BY_IDX(DT_NODELABEL(touch), 0, priority)) |
276 ESP_INT_FLAGS_CHECK(DT_IRQ_BY_IDX(DT_NODELABEL(touch), 0, flags)) |
277 ESP_INTR_FLAG_SHARED;
278 err = esp_intr_alloc(DT_IRQ_BY_IDX(DT_NODELABEL(touch), 0, irq), flags, esp32_touch_rtc_isr,
279 (void *)dev, NULL);
280 if (err) {
281 LOG_ERR("Failed to register ISR\n");
282 return -EFAULT;
283 }
284
285 #if defined(CONFIG_SOC_SERIES_ESP32)
286 touch_hal_intr_enable();
287 #elif defined(CONFIG_SOC_SERIES_ESP32S2) || defined(CONFIG_SOC_SERIES_ESP32S3)
288 touch_hal_intr_enable(ESP32_TOUCH_PAD_INTR_MASK);
289 touch_hal_set_fsm_mode(TOUCH_FSM_MODE_TIMER);
290 #endif /* defined(CONFIG_SOC_SERIES_ESP32) */
291
292 touch_hal_start_fsm();
293
294 return 0;
295 }
296
297 #define ESP32_TOUCH_SENSOR_CHANNEL_CFG_INIT(node_id) \
298 { \
299 .channel_num = DT_PROP(node_id, channel_num), \
300 .channel_sens = DT_PROP(node_id, channel_sens), \
301 .zephyr_code = DT_PROP(node_id, zephyr_code), \
302 }
303
304 #define ESP32_TOUCH_SENSOR_INIT(inst) \
305 static const struct esp32_touch_sensor_channel_config \
306 esp32_touch_sensor_channel_config_##inst[] = { \
307 DT_INST_FOREACH_CHILD_STATUS_OKAY_SEP(inst, \
308 ESP32_TOUCH_SENSOR_CHANNEL_CFG_INIT, (,)) \
309 }; \
310 \
311 static struct esp32_touch_sensor_channel_data esp32_touch_sensor_channel_data_##inst \
312 [ARRAY_SIZE(esp32_touch_sensor_channel_config_##inst)]; \
313 \
314 static const struct esp32_touch_sensor_config esp32_touch_sensor_config_##inst = { \
315 .debounce_interval_ms = DT_INST_PROP(inst, debounce_interval_ms), \
316 .num_channels = ARRAY_SIZE(esp32_touch_sensor_channel_config_##inst), \
317 .href_microvolt_enum_idx = DT_INST_ENUM_IDX(inst, href_microvolt), \
318 .lref_microvolt_enum_idx = DT_INST_ENUM_IDX(inst, lref_microvolt), \
319 .href_atten_microvolt_enum_idx = DT_INST_ENUM_IDX(inst, href_atten_microvolt), \
320 .filter_mode = DT_INST_PROP(inst, filter_mode), \
321 .filter_debounce_cnt = DT_INST_PROP(inst, filter_debounce_cnt), \
322 .filter_noise_thr = DT_INST_PROP(inst, filter_noise_thr), \
323 .filter_jitter_step = DT_INST_PROP(inst, filter_jitter_step), \
324 .filter_smooth_level = DT_INST_PROP(inst, filter_smooth_level), \
325 .channel_cfg = esp32_touch_sensor_channel_config_##inst, \
326 .channel_data = esp32_touch_sensor_channel_data_##inst, \
327 }; \
328 \
329 static struct esp32_touch_sensor_data esp32_touch_sensor_data_##inst; \
330 \
331 DEVICE_DT_INST_DEFINE(inst, \
332 &esp32_touch_sensor_init, \
333 NULL, \
334 &esp32_touch_sensor_data_##inst, \
335 &esp32_touch_sensor_config_##inst, \
336 POST_KERNEL, CONFIG_INPUT_INIT_PRIORITY, \
337 NULL);
338
339 DT_INST_FOREACH_STATUS_OKAY(ESP32_TOUCH_SENSOR_INIT)
340