实验21-LinuxLED驱动实验_第1页
实验21-LinuxLED驱动实验_第2页
实验21-LinuxLED驱动实验_第3页
实验21-LinuxLED驱动实验_第4页
实验21-LinuxLED驱动实验_第5页
已阅读5页,还剩3页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

1、Linux LED 设备驱动实验1.1 实验目的 (1)了解 LED 原理及其与 S3C2410 的接口电路设计 (2)了解S3C2410芯片的 I/O 端口配置方法 (3)通过S3C2410芯片的 GPF4 端口控制 Super-ARM主板上 D1 的亮灭 (4)掌握 LED 驱动的编写及测试过程,进而熟悉开发简单字符设备驱动的方法 1.2 实验原理 (1)LED 接口电路 由于单只 LED 管的工作电压低(大约在 1.52V) ,个别需达到 4V,同时工作电流仅为 15mA,因此可以用 CPU 的通用输入输出管脚(GPIO)直接控制 LED 的亮灭。 LED 的接口电路如下图1所示:图1

2、LED接口电路1.3 实验任务 本实验的最终目的是实现Super-ARM平台上的 LED 驱动。包含以下几个任务: (1)编写 LED 设备驱动程序,驱动程序中手动定义设备名称及主设备号,这个设备号必须是系统尚未使用的设备号,笔者这里暂用 212,你也可以尝试用别的数字。当然最好的方法是动态分配设备号,如果使用这种方法,在/dev 目录下为 LED 设备建立设备节点的时候,需要先从/proc/devices 文件中获取该设备的主设备号。在驱动程序中还要实现与 LED 相应的 I/O 配置,以及读写设备的接口函数等。 (2)将驱动编译成模块,并实现模块的加载及卸载。 (3)编写驱动的测试程序,在

3、程序中实现打开 LED 设备,控制 LED 设备一亮一灭,关闭 LED 设备等。1.4 实验步骤 编写 led.c文件 建立 led目录: #mkdir /gdut2410/led 进入led目录,在该目录下建立两个子目录driver 和 test ,前者用来存放驱动程序,后者用来存放驱动测试程序: #cd /gdut2410/led #mkdir driver test 进入驱动程序目录,建立设备驱动文件 led.c: cd driver gedit led.c LED 驱动程序如代码清单5-1 所示:代码清单 5-1 LED驱动程序 led.c /* 头文件 * #include #inc

4、lude #include #include #include #include #include #include #include #include #include #include /* 定义设备结构体及相关宏 * #define DEVICE_NAME led /定义设备名 #define DEVICE_MAJOR 212 /手动定义 LED 设备的主设备号为 212 static int led_major = DEVICE_MAJOR ; #define LED1 S3C2410_GPF4 /定义LED1 对应 S3C2410 的 GPF4 端口 #define LED1_OUT

5、P S3C2410_GPF4_OUTP #define LED_ON 0 /给端口低电平(0)时,LED 亮 #define LED_OFF 1 /给端口高电平(1)时,LED 灭 /定义 LED 设备结构体 struct s3c2410_led_dev struct cdev cdev; /LED 设备对应一个字符设备结构体 int status; /LED 状态标识,0 代表灭,1 代表亮 ; static struct s3c2410_led_dev dev; /* 函数声明 * void s3c2410_led_InitIO(void); /初始化 IO 端口的函数/* 函数定义 *

6、/* = s3c2410_led _InitIO() 描述 : 初始化 IO 端口 参数 : 无 返回值 : 无 = */ void s3c2410_led_InitIO(void) int i; /配置 LED 对应的端口为输出 s3c2410_gpio_cfgpin(LED1, LED1_OUTP); /配置 LED 初始为熄灭状态 s3c2410_gpio_setpin(LED1, LED_OFF); /* = s3c2410_led_open() 描述 : 打开设备 参数 : 返回值 : 0 = */ static int s3c2410_led_open(struct inode *

7、inode,struct file *filp) return 0; /* = s3c2410_led_release() 描述 : 注销设备 参数 : 返回值 : 0 = */ static int s3c2410_led_release(struct inode *inode,struct file *filp) return 0; /* = s3c2410_led_ioctl() 描述 : IO 控制函数,通过 LED_ON 和 LED_OFF命令控制 LED 的亮灭 参数 : cmd:用户控制命令,包括 LED_ON 和LED_OFF 返回值 : 0 = */static int s3

8、c2410_led_ioctl(struct inode *inode,struct file *filp, unsigned int cmd,unsigned long arg) switch(cmd) case LED_ON: s3c2410_gpio_setpin(LED1, LED_ON); dev.status = 1; break; case LED_OFF: s3c2410_gpio_setpin(LED1, LED_OFF); dev.status = 0; break; default: return -EINVAL; return 0; /* = s3c2410_led_r

9、ead() 描述 : 读函数,读取 LED 的状态 参数 : buffer: 用来存储读取的 LED 状态; count: 用来记录用户读取了多少个字符 返回值 : count = */ static ssize_t s3c2410_led_read(struct file *filp,char *buffer, ize_t count,loff_t *ppos) put_user(dev.status,(int *)buffer); /读取 LED 状态 return 1; /* = s3c2410_led_write() 描述 : 写操作函数,本实例中不做任何事 参数 : 返回值 : co

10、unt = */ static ssize_t s3c2410_led_write(struct file *filp,char *buffer, size_t count,loff_t *ppos) get_user(dev.status,(int *)buffer); if(dev.status = 0) /灭 s3c2410_gpio_setpin(LED1, LED_OFF); else if(dev.status = 1)/亮 s3c2410_gpio_setpin(LED1, LED_ON); return 1; /* = s3c2410_led_fops 描述 : 文件操作结构体

11、,实现 s3c2410_button_open()等函数与 open()等系统调 用的连接 参数 : 无 返回值 : 无 = */ static struct file_operations s3c2410_led_fops = .owner = THIS_MODULE, .open = s3c2410_led_open, .release = s3c2410_led_release, .ioctl = s3c2410_led_ioctl,.read = s3c2410_led_read, .write = s3c2410_led_write, ; /* = led_setup_cdev()

12、描述 : 安装 LED 设备的功能函数,在设备加载模块里面调用 参数 : 无 返回值 : 无 = */ static void led_setup_cdev(void) int err ,devno = MKDEV (led_major , 0); cdev_init(&dev.cdev,&s3c2410_led_fops); dev.cdev.owner = THIS_MODULE; dev.cdev.ops = &s3c2410_led_fops; /建立设备文件操作与系统调用之间的连接 err = cdev_add(&dev.cdev,devno,1); /向系统添加该设备 if(err

13、) printk(Error %d adding LED %d,err); /* = s3c2410_led_init() 描述 : 模块加载,IO 及相关变量初始化 参数 : 无 返回值 : 无 = */ static int s3c2410_led_init(void) int result; dev_t devno = MKDEV(led_major,0);/根据主设备号得到dev_t类型的设备号 devno if(led_major) /如果手动分配了主设备号 result = register_chrdev_region(devno,1,DEVICE_NAME); /向系统申请该设备

14、号 else /否则动态获取设备号 result = alloc_chrdev_region(&devno ,0 ,1,DEVICE_NAME); led_major = MAJOR(devno); if(result 0) return result; led_setup_cdev(); / 注册 LED 设备 s3c2410_led_InitIO(); / 初始化 IO 端口 / initialize the vals; dev.status = 0; /LED 的初始状态是灭printk(DEVICE_NAME initializedn); return 0; /* = s3c2410_

15、led_exit() 描述 : 模块卸载函数 参数 : 无 返回值 : 无 = */ static void s3c2410_led_exit(void) cdev_del(&dev.cdev); /注销设备 unregister_chrdev_region(MKDEV(led_major,0),1); /释放设备号 module_init(s3c2410_led_init); module_exit(s3c2410_led_exit); MODULE_LICENSE(GPL); /设备许可 编写Makefile文件在主机的/gdut2410/led/driver 目录下#cd /gdut24

16、10/led/driver# vi Makefile 在该文件中加入以下内容: (其中 KDIR 是内核目录,读者要根据自己的内核所在目录来设置)obj-m := led.o KDIR := /gdut2410/kernel/linux- PWD := $(shell pwd) default: $(MAKE) -C $(KDIR) SUBDIRS=$(PWD) modules # 编译 #make 编译完成后,该目录下会生成 led.ko文件,该文件就是编译成功的模块文件,然后把led.ko拷贝到nfs共享目录。 创建设备 进入/gdut2410/rootfs/rootfs/dev 目录,创

17、建设备,设备名为 led,属于字符型设备,主设备号是 212,次设备号是 0。 (要与 led.c文件中的定义相符) : # cd /gdut2410/rootfs/rootfs/dev # mknod led c 212 0 加载模块 在宿主机上运行 minicom,打开实验箱电源,加载完 U-Boot,内核和文件系统之后按回车键进入目标机 shell 控制台,在控制台中输入nfs挂载命令:#mount -t nfs -o nolock 192.168.1.10:/mnt/nfs /mnt/nfs /这里根据自己实际情况设置目录然后执行内核模块加载命令: #insmod mnt/nfs/le

18、d.ko 如果输出“led initialized” ,表示led设备驱动加载成功 编写测试文件 led_test.c 进入宿主机的/gdut2410/led/test目录,编辑测试文件led_test.c: cd /gdut2410/led/test gedit led_test.c 在测试文件中加入代码清单 5-2所示的内容: 代码清单5-2 LED 驱动测试文件 led_test.c #include #include #include #include sys/types.h #include sys/ioctl.h #include stdlib.h #include termios

19、.h #include sys/stat.h #include fcntl.h #include sys/time.h #define LED_ON 0 #define LED_OFF 1int main() int fd,i,j; int led_status = 0; /初始状态为熄灭 fd = open(/dev/led, O_RDWR); /打开设备 if (fd 0) /如果打开设备失败,退出 perror(open device led failed !); exit(1); printf(led test show. press ctrl+c to exit n); ioctl(fd,LED_OFF); while(1)/主循环 read (fd,&led_status,1); /读取 LED1 的当前状态到 led_status if(led_status =0) /如果是灭的 ioctl(fd,LED_ON); /点亮 else if(led_status =1) /如果是亮的 ioctl(fd,LED_OFF); /熄灭 printf(led: on and offn); for(i=0;i300;i+) for(j=0;j10000;j

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论