- #include<linux/module.h>
- #include<linux/kernel.h>
- #include<linux/cdev.h>
- #include<linux/irq.h>
- #include<linux/slab.h>
- #include <linux/init.h>
- #include <mach/gpio.h>
- #include<linux/gpio.h>
- #include <linux/input.h>
- #include <linux/timer.h>
- #define KEY_MAJOR 233
- #define DEVICE_NAME "gpio_key"
- struct input_dev *buttons_dev;
- struct timer_list buttons_timer;
- struct work_struct* work;
- int irq;
- static volatile int status;
- static volatile int key_status;
- static void gpio_keys_report_event(void)
- {
- status=gpio_get_value(GPIOG(0));
- if(status==1){
- input_event(buttons_dev,EV_KEY,KEY_WAKEUP,!!status);
- input_sync(buttons_dev);
- printk("<0>""the value of pin is %d\n",status);
- }
- else if(status==0){
- input_event(buttons_dev,EV_KEY,KEY_WAKEUP,!!status);
- input_sync(buttons_dev);
- printk("<0>""the value of pin2 is %d\n",status);
- }
- }
- static void work_func(struct work_struct *work)
- {
- int ret=0;
- ret=mod_timer(&buttons_timer, jiffies+(HZ/50));
- if (ret){
- printk("<0>""the mod time is on job with %d\n",ret);
- }
- }
- static void gpio_keys_timer(unsigned long _data)
- {
- gpio_keys_report_event();
- }
- static irqreturn_t gpio_key_isr(int irq, void *dev_id)
- {
- // disable_irq_nosync(irq);
- schedule_work(work);
- // enable_irq(irq);
- return IRQ_HANDLED;
- }
- static const struct file_operations key_ops={
- .owner =THIS_MODULE,
- };
- static int __init gpio_keys_init(void)
- {
- int ret = 0;
- int error;
- ret = register_chrdev(KEY_MAJOR, DEVICE_NAME, &key_ops);
- if (ret < 0) {
- printk("can't register gpio_keys_number\n");
- return -1;
- }
- buttons_dev = input_allocate_device();
- buttons_dev->name="keyboard";
- set_bit(EV_KEY,buttons_dev->evbit);
- set_bit(EV_REP,buttons_dev->evbit);
- set_bit(KEY_WAKEUP,buttons_dev->keybit);
- ret=gpio_is_valid(GPIOG(0)); //判断gpio是否合法
- printk("<0>""the valid value is %d\n",ret);
- if(gpio_request(GPIOG(0),NULL)){
- printk("<0>""request gpio error\n");
- }
- gpio_direction_input(GPIOG(0)); //把pg0设置为输入
- irq=gpio_to_irq(GPIOG(0)); //gpio实现虚拟irq
- printk("<0>""the irq value is %d\n",irq);
- error=request_irq(irq,gpio_key_isr,IRQF_TRIGGER_FALLING|IRQF_TRIGGER_RISING,"KEY_111",NULL); //上升沿下降沿触发
- if(error){
- printk("<0>""request irq error\n");
- }
- printk("<0>""the value of error is %d\n",error);
- work=kmalloc(sizeof(struct work_struct),GFP_KERNEL);
- INIT_WORK(work, work_func);
- init_timer(&buttons_timer);
- buttons_timer.function=gpio_keys_timer;
- add_timer(&buttons_timer);
- // key_status=KEYS_UP;
- ret = input_register_device(buttons_dev);
- if(ret) {
- printk("unable to register input device\n");
- return -1;
- }
- printk("gpio_keys init\n");
- return 0;
- }
- static void __exit gpio_keys_exit(void)
- {
- free_irq(irq,NULL);
- gpio_free(GPIOG(0));
- del_timer(&buttons_timer);
- unregister_chrdev(KEY_MAJOR, DEVICE_NAME);
- }
- module_init(gpio_keys_init);
- module_exit(gpio_keys_exit);
- MODULE_LICENSE("GPL");
复制代码 我做了一个按键唤醒功能的驱动,用的是定时器,上升沿下降沿触发,但是发现还是消不了抖动,请大家帮我看看问题,还有我这个功能是按一下屏幕打开,再按一下屏幕关闭,怎么改成上升沿点亮,下降沿灭掉。 |