1 #include <linux/module.h>
2 #include <linux/device.h>
3 #include <linux/platform_device.h>
4 #include <linux/gpio_event.h>
7 #define PREFIX "debounce: "
9 static unsigned old_flags
= 0;
10 static ktime_t old_debounce_delay
;
11 static ktime_t old_settle_time
;
12 static ktime_t old_poll_time
;
13 static struct gpio_event_matrix_info
*gpio_evmi
= NULL
;
14 static int hw_debounce
= 0;
15 static int hw_debounce_time
= 0;
17 static int find_ms2_dev(struct device
*dev
, void *data
)
19 if (!strncmp((char*)data
, dev_name(dev
), strlen((char*)data
))) {
20 printk(KERN_INFO PREFIX
"Found it\n");
26 /* hardware debounce: (time + 1) * 31us */
27 static void hw_debounce_set(int enable
, int time
) {
30 if (gpio_evmi
== NULL
)
33 for (i
= 0; i
< gpio_evmi
->ninputs
; i
++) {
34 int gpio
= gpio_evmi
->input_gpios
[i
];
37 printk(KERN_INFO PREFIX
"%sabling hardware debounce for GPIO %d\n", (enable
?"En":"Dis"), gpio
);
38 omap_set_gpio_debounce(gpio
, enable
);
41 if ((time
!= -1) && hw_debounce
) {
42 printk(KERN_INFO PREFIX
"Setting hardware debounce time for GPIO %d to %d (%dus)\n", gpio
, time
, (time
+1)*31);
43 omap_set_gpio_debounce_time(gpio
, time
);
49 static ssize_t
show_debounce_delay(struct device
*dev
, struct device_attribute
*attr
, char *buf
)
54 return snprintf(buf
, PAGE_SIZE
, "%ld\n", (gpio_evmi
->debounce_delay
.tv
.nsec
/ NSEC_PER_MSEC
));
57 static void set_debounce_delay(long delay
)
59 if (gpio_evmi
->debounce_delay
.tv
.nsec
!= delay
* NSEC_PER_MSEC
) {
60 printk(KERN_INFO PREFIX
"Changing debounce_delay\n");
61 gpio_evmi
->debounce_delay
.tv
.nsec
= delay
* NSEC_PER_MSEC
;
62 printk(KERN_INFO PREFIX
"debounce_delay: %u\n", gpio_evmi
->debounce_delay
.tv
.nsec
);
66 if (gpio_evmi
->debounce_delay
.tv
.nsec
!= 0) {
67 if (!(gpio_evmi
->flags
& GPIOKPF_DEBOUNCE
)) {
68 printk(KERN_INFO PREFIX
"Activating debounce\n");
69 gpio_evmi
->flags
|= GPIOKPF_DEBOUNCE
;
72 if (gpio_evmi
->flags
& GPIOKPF_DEBOUNCE
) {
73 printk(KERN_INFO PREFIX
"Deactivating debounce\n");
74 gpio_evmi
->flags
&= ~GPIOKPF_DEBOUNCE
;
80 static ssize_t
store_debounce_delay(struct device
*dev
, struct device_attribute
*attr
, const char *buf
, size_t count
)
87 sscanf(buf
, "%ld", &delay
);
88 set_debounce_delay(delay
);
93 static ssize_t
show_settle_time(struct device
*dev
, struct device_attribute
*attr
, char *buf
)
98 return snprintf(buf
, PAGE_SIZE
, "%ld\n", (gpio_evmi
->settle_time
.tv
.nsec
/ NSEC_PER_USEC
));
101 static ssize_t
store_settle_time(struct device
*dev
, struct device_attribute
*attr
, const char *buf
, size_t count
)
108 sscanf(buf
, "%ld", &delay
);
109 gpio_evmi
->settle_time
.tv
.nsec
= delay
* NSEC_PER_USEC
;
114 static ssize_t
show_poll_time(struct device
*dev
, struct device_attribute
*attr
, char *buf
)
119 return snprintf(buf
, PAGE_SIZE
, "%ld\n", (gpio_evmi
->poll_time
.tv
.nsec
/ NSEC_PER_MSEC
));
122 static ssize_t
store_poll_time(struct device
*dev
, struct device_attribute
*attr
, const char *buf
, size_t count
)
129 sscanf(buf
, "%ld", &delay
);
130 gpio_evmi
->poll_time
.tv
.nsec
= delay
* NSEC_PER_MSEC
;
135 static ssize_t
show_flags(struct device
*dev
, struct device_attribute
*attr
, char *buf
)
140 return snprintf(buf
, PAGE_SIZE
, "0x%x\n", gpio_evmi
->flags
);
143 static ssize_t
store_flags(struct device
*dev
, struct device_attribute
*attr
, const char *buf
, size_t count
)
150 sscanf(buf
, "0x%x", &flags
);
152 printk(KERN_INFO PREFIX
"flags: 0x%x\n", flags
);
154 gpio_evmi
->flags
= flags
;
159 static ssize_t
show_debounce_flag(struct device
*dev
, struct device_attribute
*attr
, char *buf
)
164 return snprintf(buf
, PAGE_SIZE
, "%u\n", (gpio_evmi
->flags
& GPIOKPF_DEBOUNCE
) ? 1 : 0);
167 static ssize_t
store_debounce_flag(struct device
*dev
, struct device_attribute
*attr
, const char *buf
, size_t count
)
174 sscanf(buf
, "%u", &flag
);
177 gpio_evmi
->flags
|= GPIOKPF_DEBOUNCE
;
179 gpio_evmi
->flags
&= ~GPIOKPF_DEBOUNCE
;
185 static ssize_t
show_remove_some_phantom_keys_flag(struct device
*dev
, struct device_attribute
*attr
, char *buf
)
190 return snprintf(buf
, PAGE_SIZE
, "%u\n", (gpio_evmi
->flags
& GPIOKPF_REMOVE_SOME_PHANTOM_KEYS
) ? 1 : 0);
193 static ssize_t
store_remove_some_phantom_keys_flag(struct device
*dev
, struct device_attribute
*attr
, const char *buf
, size_t count
)
200 sscanf(buf
, "%u", &flag
);
203 gpio_evmi
->flags
|= GPIOKPF_REMOVE_SOME_PHANTOM_KEYS
;
205 gpio_evmi
->flags
&= ~GPIOKPF_REMOVE_SOME_PHANTOM_KEYS
;
211 static ssize_t
show_print_unmapped_keys_flag(struct device
*dev
, struct device_attribute
*attr
, char *buf
)
216 return snprintf(buf
, PAGE_SIZE
, "%u\n", (gpio_evmi
->flags
& GPIOKPF_PRINT_UNMAPPED_KEYS
) ? 1 : 0);
219 static ssize_t
store_print_unmapped_keys_flag(struct device
*dev
, struct device_attribute
*attr
, const char *buf
, size_t count
)
226 sscanf(buf
, "%u", &flag
);
229 gpio_evmi
->flags
|= GPIOKPF_PRINT_UNMAPPED_KEYS
;
231 gpio_evmi
->flags
&= ~GPIOKPF_PRINT_UNMAPPED_KEYS
;
237 static ssize_t
show_print_mapped_keys_flag(struct device
*dev
, struct device_attribute
*attr
, char *buf
)
242 return snprintf(buf
, PAGE_SIZE
, "%u\n", (gpio_evmi
->flags
& GPIOKPF_PRINT_MAPPED_KEYS
) ? 1 : 0);
245 static ssize_t
store_print_mapped_keys_flag(struct device
*dev
, struct device_attribute
*attr
, const char *buf
, size_t count
)
252 sscanf(buf
, "%u", &flag
);
255 gpio_evmi
->flags
|= GPIOKPF_PRINT_MAPPED_KEYS
;
257 gpio_evmi
->flags
&= ~GPIOKPF_PRINT_MAPPED_KEYS
;
263 static ssize_t
show_print_phantom_keys_flag(struct device
*dev
, struct device_attribute
*attr
, char *buf
)
268 return snprintf(buf
, PAGE_SIZE
, "%u\n", (gpio_evmi
->flags
& GPIOKPF_PRINT_PHANTOM_KEYS
) ? 1 : 0);
271 static ssize_t
store_print_phantom_keys_flag(struct device
*dev
, struct device_attribute
*attr
, const char *buf
, size_t count
)
278 sscanf(buf
, "%u", &flag
);
281 gpio_evmi
->flags
|= GPIOKPF_PRINT_PHANTOM_KEYS
;
283 gpio_evmi
->flags
&= ~GPIOKPF_PRINT_PHANTOM_KEYS
;
289 static ssize_t
show_active_high_flag(struct device
*dev
, struct device_attribute
*attr
, char *buf
)
294 return snprintf(buf
, PAGE_SIZE
, "%u\n", (gpio_evmi
->flags
& GPIOKPF_ACTIVE_HIGH
) ? 1 : 0);
297 static ssize_t
store_active_high_flag(struct device
*dev
, struct device_attribute
*attr
, const char *buf
, size_t count
)
304 sscanf(buf
, "%u", &flag
);
307 gpio_evmi
->flags
|= GPIOKPF_ACTIVE_HIGH
;
309 gpio_evmi
->flags
&= ~GPIOKPF_ACTIVE_HIGH
;
315 static ssize_t
show_drive_inactive_flag(struct device
*dev
, struct device_attribute
*attr
, char *buf
)
320 return snprintf(buf
, PAGE_SIZE
, "%u\n", (gpio_evmi
->flags
& GPIOKPF_DRIVE_INACTIVE
) ? 1 : 0);
323 static ssize_t
store_drive_inactive_flag(struct device
*dev
, struct device_attribute
*attr
, const char *buf
, size_t count
)
330 sscanf(buf
, "%u", &flag
);
333 gpio_evmi
->flags
|= GPIOKPF_DRIVE_INACTIVE
;
335 gpio_evmi
->flags
&= ~GPIOKPF_DRIVE_INACTIVE
;
341 static ssize_t
show_hw_debounce(struct device
*dev
, struct device_attribute
*attr
, char *buf
)
343 return snprintf(buf
, PAGE_SIZE
, "%d\n", hw_debounce
);
346 static ssize_t
store_hw_debounce(struct device
*dev
, struct device_attribute
*attr
, const char *buf
, size_t count
)
350 sscanf(buf
, "%d", &enable
);
353 hw_debounce_set(1, -1);
357 hw_debounce_set(0, -1);
364 static ssize_t
show_hw_debounce_time(struct device
*dev
, struct device_attribute
*attr
, char *buf
)
366 return snprintf(buf
, PAGE_SIZE
, "%d\n", hw_debounce_time
);
369 static ssize_t
store_hw_debounce_time(struct device
*dev
, struct device_attribute
*attr
, const char *buf
, size_t count
)
373 sscanf(buf
, "%d", &time
);
375 if ((time
< 0) || (time
> 0xff))
378 hw_debounce_set(-1, time
);
379 hw_debounce_time
= time
;
384 static DEVICE_ATTR(debounce_delay
, (S_IRUGO
| S_IWUGO
), show_debounce_delay
, store_debounce_delay
);
385 static DEVICE_ATTR(settle_time
, (S_IRUGO
| S_IWUGO
), show_settle_time
, store_settle_time
);
386 static DEVICE_ATTR(poll_time
, (S_IRUGO
| S_IWUGO
), show_poll_time
, store_poll_time
);
387 static DEVICE_ATTR(flags
, (S_IRUGO
), show_flags
, store_flags
);
388 static DEVICE_ATTR(debounce_flag
, (S_IRUGO
| S_IWUGO
), show_debounce_flag
, store_debounce_flag
);
389 static DEVICE_ATTR(remove_some_phantom_keys_flag
, (S_IRUGO
| S_IWUGO
), show_remove_some_phantom_keys_flag
, store_remove_some_phantom_keys_flag
);
390 static DEVICE_ATTR(print_unmapped_keys_flag
, (S_IRUGO
| S_IWUGO
), show_print_unmapped_keys_flag
, store_print_unmapped_keys_flag
);
391 static DEVICE_ATTR(print_mapped_keys_flag
, (S_IRUGO
| S_IWUGO
), show_print_mapped_keys_flag
, store_print_mapped_keys_flag
);
392 static DEVICE_ATTR(print_phantom_keys_flag
, (S_IRUGO
| S_IWUGO
), show_print_phantom_keys_flag
, store_print_phantom_keys_flag
);
393 static DEVICE_ATTR(active_high_flag
, (S_IRUGO
), show_active_high_flag
, store_active_high_flag
);
394 static DEVICE_ATTR(drive_inactive_flag
, (S_IRUGO
| S_IWUGO
), show_drive_inactive_flag
, store_drive_inactive_flag
);
395 static DEVICE_ATTR(hw_debounce
, (S_IRUGO
| S_IWUGO
), show_hw_debounce
, store_hw_debounce
);
396 static DEVICE_ATTR(hw_debounce_time
, (S_IRUGO
| S_IWUGO
), show_hw_debounce_time
, store_hw_debounce_time
);
398 static void debounce_release(struct device
*dev
)
402 static struct device debounce_device
= {
403 .init_name
= "debounce",
404 .release
= debounce_release
,
407 static int __init
debounce_init(void)
409 struct device
*event_dev
= NULL
;
410 struct gpio_event_platform_data
*gpio_epd
;
411 struct gpio_event_info
*gpio_ei
;
414 printk(KERN_INFO PREFIX
"Searching for " GPIO_EVENT_DEV_NAME
"...\n");
416 event_dev
= device_find_child(&platform_bus
, GPIO_EVENT_DEV_NAME
, find_ms2_dev
);
417 if (event_dev
== NULL
)
420 gpio_epd
= (struct gpio_event_platform_data
*)event_dev
->platform_data
;
421 printk(KERN_INFO PREFIX
"And there is a %s connected...\n", gpio_epd
->name
);
422 if (strcmp(gpio_epd
->name
, "sholes-keypad"))
425 gpio_ei
= (struct gpio_event_info
*)gpio_epd
->info
[0];
426 gpio_evmi
= container_of(gpio_ei
, struct gpio_event_matrix_info
, info
);
428 err
= device_register(&debounce_device
);
433 err
= device_create_file(&debounce_device
, &dev_attr_debounce_delay
);
434 err
= device_create_file(&debounce_device
, &dev_attr_settle_time
);
435 err
= device_create_file(&debounce_device
, &dev_attr_poll_time
);
436 err
= device_create_file(&debounce_device
, &dev_attr_flags
);
437 err
= device_create_file(&debounce_device
, &dev_attr_debounce_flag
);
438 err
= device_create_file(&debounce_device
, &dev_attr_remove_some_phantom_keys_flag
);
439 err
= device_create_file(&debounce_device
, &dev_attr_print_unmapped_keys_flag
);
440 err
= device_create_file(&debounce_device
, &dev_attr_print_mapped_keys_flag
);
441 err
= device_create_file(&debounce_device
, &dev_attr_print_phantom_keys_flag
);
442 err
= device_create_file(&debounce_device
, &dev_attr_active_high_flag
);
443 err
= device_create_file(&debounce_device
, &dev_attr_drive_inactive_flag
);
444 err
= device_create_file(&debounce_device
, &dev_attr_hw_debounce
);
445 err
= device_create_file(&debounce_device
, &dev_attr_hw_debounce_time
);
447 printk(KERN_INFO PREFIX
"settle_time: %u\n", gpio_evmi
->settle_time
.tv
.nsec
);
448 printk(KERN_INFO PREFIX
"poll_time: %u\n", gpio_evmi
->poll_time
.tv
.nsec
);
449 printk(KERN_INFO PREFIX
"debounce_delay: %u\n", gpio_evmi
->debounce_delay
.tv
.nsec
);
450 printk(KERN_INFO PREFIX
"flags: 0x%x\n", gpio_evmi
->flags
);
452 old_debounce_delay
= gpio_evmi
->debounce_delay
;
453 old_settle_time
= gpio_evmi
->settle_time
;
454 old_poll_time
= gpio_evmi
->poll_time
;
455 old_flags
= gpio_evmi
->flags
;
457 printk(KERN_INFO PREFIX
"flags: 0x%x\n", gpio_evmi
->flags
);
462 static void __exit
debounce_exit(void)
465 if (gpio_evmi
->debounce_delay
.tv
.nsec
!= old_debounce_delay
.tv
.nsec
) {
466 printk(KERN_INFO PREFIX
"Restoring debounce_delay\n");
467 gpio_evmi
->debounce_delay
= old_debounce_delay
;
468 printk(KERN_INFO PREFIX
"debounce_delay: %u\n", gpio_evmi
->debounce_delay
.tv
.nsec
);
470 if (gpio_evmi
->flags
!= old_flags
) {
471 printk(KERN_INFO PREFIX
"Restoring flags\n");
472 gpio_evmi
->flags
= old_flags
;
473 printk(KERN_INFO PREFIX
"flags: 0x%x\n", gpio_evmi
->flags
);
475 gpio_evmi
->settle_time
= old_settle_time
;
476 gpio_evmi
->poll_time
= old_poll_time
;
478 hw_debounce_set(0, 0);
479 device_remove_file(&debounce_device
, &dev_attr_debounce_delay
);
480 device_remove_file(&debounce_device
, &dev_attr_settle_time
);
481 device_remove_file(&debounce_device
, &dev_attr_poll_time
);
482 device_remove_file(&debounce_device
, &dev_attr_flags
);
483 device_remove_file(&debounce_device
, &dev_attr_debounce_flag
);
484 device_remove_file(&debounce_device
, &dev_attr_remove_some_phantom_keys_flag
);
485 device_remove_file(&debounce_device
, &dev_attr_print_unmapped_keys_flag
);
486 device_remove_file(&debounce_device
, &dev_attr_print_mapped_keys_flag
);
487 device_remove_file(&debounce_device
, &dev_attr_print_phantom_keys_flag
);
488 device_remove_file(&debounce_device
, &dev_attr_active_high_flag
);
489 device_remove_file(&debounce_device
, &dev_attr_drive_inactive_flag
);
490 device_remove_file(&debounce_device
, &dev_attr_hw_debounce
);
491 device_remove_file(&debounce_device
, &dev_attr_hw_debounce_time
);
492 device_unregister(&debounce_device
);
495 module_init(debounce_init
);
496 module_exit(debounce_exit
);
498 MODULE_LICENSE("GPL");
499 MODULE_AUTHOR("Michael Gernoth <michael@gernoth.net>");