xref: /rk3399_rockchip-uboot/drivers/input/key-uclass.c (revision a2df960601036d3fd0d00ea8f43cdde52b5eddbe)
1 /*
2  * (C) Copyright 2017 Rockchip Electronics Co., Ltd
3  *
4  * SPDX-License-Identifier:     GPL-2.0+
5  */
6 
7 #include <dm.h>
8 #include <key.h>
9 #include <common.h>
10 #include <dm.h>
11 
12 static inline uint64_t arch_counter_get_cntpct(void)
13 {
14 	uint64_t cval = 0;
15 
16 	isb();
17 #ifdef CONFIG_ARM64
18 	asm volatile("mrs %0, cntpct_el0" : "=r" (cval));
19 #else
20 	asm volatile ("mrrc p15, 0, %Q0, %R0, c14" : "=r" (cval));
21 #endif
22 	return cval;
23 }
24 
25 uint64_t key_get_timer(uint64_t base)
26 {
27 	uint64_t cntpct;
28 
29 	cntpct = arch_counter_get_cntpct() / 24000UL;
30 	return (cntpct > base) ? (cntpct - base) : 0;
31 }
32 
33 static int key_state_valid(int state)
34 {
35 	return (state >= KEY_PRESS_NONE && state < KEY_NOT_EXIST);
36 }
37 
38 static int key_read(struct udevice *dev, int code)
39 {
40 	const struct dm_key_ops *ops = dev_get_driver_ops(dev);
41 
42 	if (!ops || !ops->read)
43 		return -ENOSYS;
44 
45 	return ops->read(dev, code);
46 }
47 
48 int platform_key_read(int code)
49 {
50 	struct udevice *dev;
51 	int report = KEY_NOT_EXIST;
52 
53 	for (uclass_first_device(UCLASS_KEY, &dev);
54 	     dev;
55 	     uclass_next_device(&dev)) {
56 		debug("key dev.name = %s, code = %d\n", dev->name, code);
57 		report = key_read(dev, code);
58 		if (key_state_valid(report)) {
59 			debug("key dev.name = %s, state=%d\n", dev->name, report);
60 			break;
61 		}
62 	}
63 
64 	return report;
65 }
66 
67 UCLASS_DRIVER(key) = {
68 	.id		= UCLASS_KEY,
69 	.name		= "key",
70 };
71