1 /*
2 * (C) Copyright 2017 Rockchip Electronics Co., Ltd
3 *
4 * SPDX-License-Identifier: GPL-2.0+
5 */
6
7 #include <common.h>
8 #include <adc.h>
9 #include <div64.h>
10 #include <dm.h>
11 #include <irq-generic.h>
12 #include <key.h>
13 #include <dm/lists.h>
14 #include <dm/uclass-internal.h>
15
16 #define KEY_WARN(fmt, args...) printf("Key Warn: "fmt, ##args)
17 #define KEY_ERR(fmt, args...) printf("Key Error: "fmt, ##args)
18 #define KEY_DBG(fmt, args...) debug("Key Debug: "fmt, ##args)
19
arch_counter_get_cntpct(void)20 static inline uint64_t arch_counter_get_cntpct(void)
21 {
22 uint64_t cval = 0;
23
24 isb();
25 #ifdef CONFIG_ARM64
26 asm volatile("mrs %0, cntpct_el0" : "=r" (cval));
27 #else
28 asm volatile("mrrc p15, 0, %Q0, %R0, c14" : "=r" (cval));
29 #endif
30 return cval;
31 }
32
key_timer(uint64_t base)33 uint64_t key_timer(uint64_t base)
34 {
35 uint64_t cntpct;
36
37 cntpct = arch_counter_get_cntpct() / 24000UL;
38 return (cntpct > base) ? (cntpct - base) : 0;
39 }
40
41 #ifdef CONFIG_ADC
adc_raw_to_mV(struct udevice * dev,unsigned int raw,int * mV)42 static int adc_raw_to_mV(struct udevice *dev, unsigned int raw, int *mV)
43 {
44 unsigned int data_mask;
45 int ret, vref = 1800000;
46 u64 raw64 = raw;
47
48 ret = adc_data_mask(dev, &data_mask);
49 if (ret)
50 return ret;
51
52 raw64 *= vref;
53 do_div(raw64, data_mask);
54 *mV = raw64;
55
56 return 0;
57 }
58
key_adc_event(struct udevice * dev,struct dm_key_uclass_platdata * uc_key,int adcval)59 static int key_adc_event(struct udevice *dev,
60 struct dm_key_uclass_platdata *uc_key, int adcval)
61 {
62 int val = adcval;
63
64 if (uc_key->in_volt) {
65 if (adc_raw_to_mV(dev, adcval, &val))
66 return KEY_PRESS_NONE;
67 }
68
69 debug("[%s] <%d, %d, %d>: adcval=%d -> mV=%d\n",
70 uc_key->name, uc_key->min, uc_key->center, uc_key->max,
71 adcval, val);
72
73 return (val <= uc_key->max && val >= uc_key->min) ?
74 KEY_PRESS_DOWN : KEY_PRESS_NONE;
75 }
76 #endif
77
key_gpio_event(struct dm_key_uclass_platdata * uc_key)78 static int key_gpio_event(struct dm_key_uclass_platdata *uc_key)
79 {
80 if (!dm_gpio_is_valid(&uc_key->gpio)) {
81 KEY_ERR("'%s' Invalid gpio\n", uc_key->name);
82 return KEY_PRESS_NONE;
83 }
84
85 return dm_gpio_get_value(&uc_key->gpio) ?
86 KEY_PRESS_DOWN : KEY_PRESS_NONE;
87 }
88
key_gpio_interrupt_event(struct dm_key_uclass_platdata * uc_key)89 static int key_gpio_interrupt_event(struct dm_key_uclass_platdata *uc_key)
90 {
91 int event;
92
93 debug("%s: %s: up=%llu, down=%llu, delta=%llu\n",
94 __func__, uc_key->name, uc_key->rise_ms, uc_key->fall_ms,
95 uc_key->rise_ms - uc_key->fall_ms);
96
97 /* Possible this is machine power-on long pressed, so ignore this */
98 if (uc_key->fall_ms == 0 && uc_key->rise_ms != 0) {
99 event = KEY_PRESS_NONE;
100 goto out;
101 }
102
103 if ((uc_key->rise_ms > uc_key->fall_ms) &&
104 (uc_key->rise_ms - uc_key->fall_ms) >= KEY_LONG_DOWN_MS) {
105 uc_key->rise_ms = 0;
106 uc_key->fall_ms = 0;
107 event = KEY_PRESS_LONG_DOWN;
108 KEY_DBG("%s key long pressed..\n", uc_key->name);
109 } else if (uc_key->fall_ms &&
110 key_timer(uc_key->fall_ms) >= KEY_LONG_DOWN_MS) {
111 uc_key->rise_ms = 0;
112 uc_key->fall_ms = 0;
113 event = KEY_PRESS_LONG_DOWN;
114 KEY_DBG("%s key long pressed(hold)..\n", uc_key->name);
115 } else if ((uc_key->rise_ms > uc_key->fall_ms) &&
116 (uc_key->rise_ms - uc_key->fall_ms) < KEY_LONG_DOWN_MS) {
117 uc_key->rise_ms = 0;
118 uc_key->fall_ms = 0;
119 event = KEY_PRESS_DOWN;
120 KEY_DBG("%s key short pressed..\n", uc_key->name);
121 /* Possible in charge animation, we enable irq after fuel gauge updated */
122 } else if (uc_key->rise_ms && uc_key->fall_ms &&
123 (uc_key->rise_ms == uc_key->fall_ms)) {
124 uc_key->rise_ms = 0;
125 uc_key->fall_ms = 0;
126 event = KEY_PRESS_DOWN;
127 KEY_DBG("%s key short pressed..\n", uc_key->name);
128 } else {
129 event = KEY_PRESS_NONE;
130 }
131
132 out:
133 return event;
134 }
135
key_is_pressed(int event)136 int key_is_pressed(int event)
137 {
138 return (event == KEY_PRESS_DOWN || event == KEY_PRESS_LONG_DOWN);
139 }
140
key_core_read(struct dm_key_uclass_platdata * uc_key)141 static int key_core_read(struct dm_key_uclass_platdata *uc_key)
142 {
143 if (uc_key->type == ADC_KEY) {
144 #ifdef CONFIG_ADC
145 struct udevice *dev;
146 unsigned int adcval;
147 int ret;
148
149 ret = uclass_get_device_by_name(UCLASS_ADC, "saradc", &dev);
150 if (ret) {
151 KEY_ERR("%s: No saradc\n", uc_key->name);
152 return KEY_NOT_EXIST;
153 }
154
155 ret = adc_start_channel(dev, uc_key->channel);
156 if (ret) {
157 KEY_ERR("%s: Failed to start saradc\n", uc_key->name);
158 return KEY_NOT_EXIST;
159 }
160
161 ret = adc_channel_data(dev, uc_key->channel, &adcval);
162 if (ret) {
163 KEY_ERR("%s: Failed to read saradc, %d\n", uc_key->name, ret);
164 return KEY_NOT_EXIST;
165 }
166
167 return key_adc_event(dev, uc_key, adcval);
168 #else
169 return KEY_NOT_EXIST;
170 #endif
171 }
172
173 return (uc_key->code == KEY_POWER) ?
174 key_gpio_interrupt_event(uc_key) :
175 key_gpio_event(uc_key);
176 }
177
key_read(int code)178 int key_read(int code)
179 {
180 struct dm_key_uclass_platdata *uc_key;
181 struct udevice *dev;
182 struct uclass *uc;
183 bool allow_pre_reloc = false;
184 int ret, event = KEY_NOT_EXIST;
185
186 ret = uclass_get(UCLASS_KEY, &uc);
187 if (ret)
188 return ret;
189
190 try_again:
191 for (uclass_first_device(UCLASS_KEY, &dev);
192 dev;
193 uclass_next_device(&dev)) {
194 uc_key = dev_get_uclass_platdata(dev);
195
196 if (!allow_pre_reloc && uc_key->pre_reloc)
197 continue;
198
199 if (uc_key->code != code)
200 continue;
201
202 event = key_core_read(uc_key);
203 if (key_is_pressed(event))
204 return event;
205 }
206
207 /* If not find valid key node from kernel, try from u-boot */
208 if (event == KEY_NOT_EXIST && !allow_pre_reloc) {
209 allow_pre_reloc = true;
210 goto try_again;
211 }
212
213 return event;
214 }
215
key_exist(int code)216 int key_exist(int code)
217 {
218 struct dm_key_uclass_platdata *uc_key;
219 struct udevice *dev;
220
221 for (uclass_find_first_device(UCLASS_KEY, &dev);
222 dev;
223 uclass_find_next_device(&dev)) {
224 uc_key = dev_get_uclass_platdata(dev);
225
226 if (uc_key->code == code)
227 return 1;
228 }
229
230 return 0;
231 }
232
233 #if CONFIG_IS_ENABLED(IRQ)
234 #if defined(CONFIG_PWRKEY_DNL_TRIGGER_NUM) && \
235 (CONFIG_PWRKEY_DNL_TRIGGER_NUM > 0)
power_key_download(struct dm_key_uclass_platdata * uc_key)236 static void power_key_download(struct dm_key_uclass_platdata *uc_key)
237 {
238 int trig_cnt = CONFIG_PWRKEY_DNL_TRIGGER_NUM;
239 static u64 old_rise_ms;
240
241 if (uc_key->code == KEY_POWER && old_rise_ms != uc_key->rise_ms) {
242 old_rise_ms = uc_key->rise_ms;
243 uc_key->trig_cnt++;
244 if (uc_key->trig_cnt >= trig_cnt) {
245 printf("\nEnter download mode by pwrkey\n");
246 irq_handler_disable(uc_key->irq);
247 run_command("download", 0);
248 }
249 }
250 }
251
pwrkey_download_init(void)252 int pwrkey_download_init(void)
253 {
254 return (KEY_NOT_EXIST == key_read(KEY_POWER));
255 }
256 #endif
257
gpio_irq_handler(int irq,void * data)258 static void gpio_irq_handler(int irq, void *data)
259 {
260 struct udevice *dev = data;
261 struct dm_key_uclass_platdata *uc_key = dev_get_uclass_platdata(dev);
262
263 if (uc_key->irq != irq)
264 return;
265
266 if (uc_key->irq_thread) {
267 uc_key->irq_thread(irq, data);
268 } else {
269 if (irq_get_gpio_level(irq)) {
270 uc_key->rise_ms = key_timer(0);
271 KEY_DBG("%s: key dn: %llu ms\n",
272 uc_key->name, uc_key->fall_ms);
273 } else {
274 uc_key->fall_ms = key_timer(0);
275 KEY_DBG("%s: key up: %llu ms\n",
276 uc_key->name, uc_key->rise_ms);
277 }
278
279 /* Must delay */
280 mdelay(10);
281 irq_revert_irq_type(irq);
282 }
283
284 /* Hook event: enter download mode by pwrkey */
285 #if defined(CONFIG_PWRKEY_DNL_TRIGGER_NUM) && \
286 (CONFIG_PWRKEY_DNL_TRIGGER_NUM > 0)
287 power_key_download(uc_key);
288 #endif
289 }
290 #endif
291
key_bind_children(struct udevice * dev,const char * drv_name)292 int key_bind_children(struct udevice *dev, const char *drv_name)
293 {
294 const char *name;
295 ofnode node;
296 int ret;
297
298 dev_for_each_subnode(node, dev) {
299 /*
300 * If this node has "compatible" property, this is not
301 * a amp subnode, but a normal device. skip.
302 */
303 ofnode_get_property(node, "compatible", &ret);
304 if (ret >= 0)
305 continue;
306
307 if (ret != -FDT_ERR_NOTFOUND)
308 return ret;
309
310 name = ofnode_get_name(node);
311 if (!name)
312 return -EINVAL;
313 ret = device_bind_driver_to_node(dev, drv_name, name,
314 node, NULL);
315 if (ret)
316 return ret;
317 }
318
319 return 0;
320 }
321
key_post_probe(struct udevice * dev)322 static int key_post_probe(struct udevice *dev)
323 {
324 struct dm_key_uclass_platdata *uc_key;
325 int ret;
326
327 uc_key = dev_get_uclass_platdata(dev);
328 if (!uc_key)
329 return -ENXIO;
330
331 /* True from U-Boot key node */
332 uc_key->pre_reloc = dev_read_bool(dev, "u-boot,dm-pre-reloc") ||
333 dev_read_bool(dev, "u-boot,dm-spl");
334
335 if (uc_key->type != ADC_KEY) {
336 if (uc_key->code == KEY_POWER) {
337 #if CONFIG_IS_ENABLED(IRQ)
338 int irq;
339
340 if (uc_key->skip_irq_init)
341 return 0;
342
343 irq = phandle_gpio_to_irq(uc_key->gpios[0],
344 uc_key->gpios[1]);
345 if (irq < 0) {
346 KEY_ERR("%s: failed to request irq, ret=%d\n",
347 uc_key->name, irq);
348 return irq;
349 }
350
351 if (uc_key->code != KEY_POWER && uc_key->irq_thread) {
352 KEY_WARN("%s: only power key can request irq thread\n",
353 uc_key->name);
354 return -EINVAL;
355 }
356
357 uc_key->irq = irq;
358 irq_install_handler(irq, gpio_irq_handler, dev);
359 irq_set_irq_type(irq, IRQ_TYPE_EDGE_FALLING);
360 irq_handler_enable(irq);
361 #else
362 KEY_WARN("%s: no IRQ framework available\n", uc_key->name);
363 #endif
364 } else {
365 ret = gpio_request_by_name(dev, "gpios", 0,
366 &uc_key->gpio, GPIOD_IS_IN);
367 if (ret) {
368 KEY_ERR("%s: failed to request gpio, ret=%d\n",
369 uc_key->name, ret);
370 return ret;
371 }
372 }
373 }
374
375 #ifdef DEBUG
376 printf("[%s] (%s, %s, %s):\n", uc_key->name,
377 uc_key->type == ADC_KEY ? "ADC" : "GPIO",
378 uc_key->pre_reloc ? "U-Boot" : "Kernel",
379 dev->parent->name);
380
381 if (uc_key->type == ADC_KEY) {
382 printf(" %s: %d (%d, %d)\n",
383 uc_key->in_volt ? "volt" : " adc",
384 uc_key->center, uc_key->min, uc_key->max);
385 printf(" channel: %d\n\n", uc_key->channel);
386 } else {
387 const char *gpio_name =
388 ofnode_get_name(ofnode_get_by_phandle(uc_key->gpios[0]));
389
390 printf(" irq: %d\n", uc_key->irq);
391 printf(" gpio[0]: %s\n", gpio_name);
392 printf(" gpio[1]: %d\n\n", uc_key->gpios[1]);
393 }
394 #endif
395
396 return 0;
397 }
398
399 UCLASS_DRIVER(key) = {
400 .id = UCLASS_KEY,
401 .name = "key",
402 .post_probe = key_post_probe,
403 .per_device_platdata_auto_alloc_size =
404 sizeof(struct dm_key_uclass_platdata),
405 };
406