基于中断的按键驱动以及其测试程序

原创 2017年02月28日 10:46:45

驱动程序如下

#include <linux/device.h>

#include <linux/interrupt.h>

#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/fs.h>
#include <linux/init.h>
#include <linux/delay.h>
#include <linux/irq.h>
#include <asm/uaccess.h>
#include <asm/irq.h>
#include <asm/io.h>
#include <mach/gpio.h>
#include<linux/cdev.h>
 
int key_id;
struct cdev cdev;
dev_t devno;
/*等待队列头*/
wait_queue_head_t key_q;
/*中断事件标志,中断服务程序将它置为1,read函数将它置为0*/
unsigned int key_num=0;
#define DRIVER_NAME "my_key_driver"
struct class *my_class;

static irqreturn_t key_func(int irq,void *dev_id)
{
key_id=(int)dev_id;


/*唤醒*/
key_num=1;
wake_up(&key_q);




return 0;
}


static int key_open(struct inode *inode,struct file *file)
{


request_irq(IRQ_EINT(16),key_func,IRQF_TRIGGER_FALLING,"k1",1);
request_irq(IRQ_EINT(17),key_func,IRQF_TRIGGER_FALLING,"k2",2);
request_irq(IRQ_EINT(18),key_func,IRQF_TRIGGER_FALLING,"k3",3);
request_irq(IRQ_EINT(19),key_func,IRQF_TRIGGER_FALLING,"k4",4);
request_irq(IRQ_EINT(24),key_func,IRQF_TRIGGER_FALLING,"k5",5);
request_irq(IRQ_EINT(25),key_func,IRQF_TRIGGER_FALLING,"k6",6);
request_irq(IRQ_EINT(26),key_func,IRQF_TRIGGER_FALLING,"k7",7);
request_irq(IRQ_EINT(27),key_func,IRQF_TRIGGER_FALLING,"k8",8);
return 0;
}


static int key_close(struct inode *inode,struct file *file)
{


free_irq(IRQ_EINT(16),1);
free_irq(IRQ_EINT(17),2);
free_irq(IRQ_EINT(18),3);
free_irq(IRQ_EINT(19),4);
free_irq(IRQ_EINT(24),5);
free_irq(IRQ_EINT(25),6);
free_irq(IRQ_EINT(26),7);
free_irq(IRQ_EINT(27),8);


return 0;
}


ssize_t key_read(struct file *filp, char __user *buf, size_t size,loff_t *pos)
{
/*如果没有按键按下,休眠,让出CPU*/
wait_event(key_q,key_num);
/*如果有按键按下*/
copy_to_user(buf,&key_id,sizeof(key_id)); 
key_num=0;


return 0;
}




static struct file_operations key_fops =
{
.owner = THIS_MODULE,
.open = key_open,
.release = key_close,
.read=key_read,
};




static int __init key_interrupt_init(void)
{
cdev_init(&cdev,&key_fops);
alloc_chrdev_region(&devno, 0 , 1 , "mykey_interrupt");
cdev_add(&cdev, devno, 1);
my_class = class_create(THIS_MODULE, "key_interrupt_class");
if(IS_ERR(my_class))
{
printk("Err: failed in creating class.\n");
return -1;
}
device_create(my_class, NULL, devno,NULL,"key_interrput_driver");
init_waitqueue_head(&key_q);
return 0;
}


static void key_interrupt_exit(void)
{
device_destroy(my_class,devno);
class_destroy(my_class);
cdev_del(&cdev);
unregister_chrdev_region(devno,1);
}


module_init(key_interrupt_init);
module_exit(key_interrupt_exit);
MODULE_LICENSE("GPL");

MODULE_AUTHOR("EIGHT_FIVE");


测试程序如下

#include<stdio.h>
#include<sys/ioctl.h>
#include<sys/types.h>
#include<sys/stat.h>
#include<fcntl.h>


int main(int argv,char **argc)
{
int fd,buf;
fd=open("/dev/key_interrput_driver",0x666);


while(1)
{


read(fd,&buf,4);
printf("key_val =%d\n",buf);
}
return 0;


}



版权声明:本文为博主原创文章,未经博主允许不得转载。

相关文章推荐

Android Studio - 基本配置

正所谓“磨刀不误砍柴工”,Android开发中最重要的利器就是Android Studio。上一章介绍了如何安装Android Studio和如何配置Android模拟器。本章主要讲解Android ...

Apache 使用ssl模块配置HTTPS

Web服务器在默认情况下使用HTTP,这是一个纯文本的协议。正如其名称所暗示的,纯文本协议不会对传输中的数据进行任何形式的加密。而基于HTTP的Web服务器是非常容易配置,它在安全方面有重大缺陷。任何...

XAMPP各个版本配置

XAMPP这集成环境也很不错 如果你的PHP代码有加密部分,而Zend Guard 5.2加密的代码不能用5.3解密, 只有下载最后一个PHP5.2版本的xampp 1.7.1,并改动...

unity地形编辑扩展插件Landspace Auto Material介绍

LAM是一套针对复杂地形和植物的编辑工具, 增加了一些unity自带地形编辑器没有的功能, 对其用法做一下简单介绍。

Android设计模式学习之观察者模式

观察者模式在实际项目中使用的也是非常频繁的,它最常用的地方是GUI系统、订阅——发布系统等。因为这个模式的一个重要作用就是解耦,使得它们之间的依赖性更小,甚至做到毫无依赖。以GUI系统来说,应用的UI...

夕拾朝花——我的2016

夕拾朝花——我的2016走在北航的林间小道上,两边稀稀落落侥幸残留几片枯叶在冷风中瑟瑟抖动,北京 的冬日就是这样,异显凄凉。我常想在纷扰中寻出一点闲静来,然而委实不容易。趁着圣诞的间隙,从快节奏的生活...
  • yzzst
  • yzzst
  • 2016-12-24 23:53
  • 12811

xamarin android异步更新UI线程

UI线程简单了解 一些从事web开发的同学,可能对UI线程没有这个概念,没办法,毕竟“UI线程”这个概念只存在一些客户端(window客户端软件、app等)。其实android在子线程中更新UI线程,...

Java开发中的23种设计模式详解

一、设计模式的分类 总体来说设计模式分为三大类: 创建型模式,共五种:工厂方法模式、抽象工厂模式、单例模式、建造者模式、原型模式。 结构型模式,共七种:适配器模式、装饰器模式、代理模...

Windows 下安装 swoole 具体步骤

(*^__^*) 嘻嘻…… 挺累的。
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:深度学习:神经网络中的前向传播和反向传播算法推导
举报原因:
原因补充:

(最多只允许输入30个字)