当前位置:文档之家› 实验六LED 控制实验

实验六LED 控制实验

实验六LED 控制实验一、实验目的通过实验学习如何将一个驱动添加到Kconfig,编译到内核;通过实验掌握在Linux 下驱动程序的编写方法。

二、实验设备硬件:EduKit-IV 嵌入式教学实验平台、Mini2410 核心子板、PC 机;软件:Windows 2000/NT/XP、Ubuntu 8.04、其他嵌入式软件包。

三、实验内容编写EduKit-IV 实验箱Linux 操作系统下LED 灯的应用程序。

编写 EduKit-IV 实验箱Linux 操作系统下LED 灯的驱动;实验步骤:下面介绍如何将一个驱动添加到内核中,并且在配置选项中能够通过menuconfig 配置内核时选择该驱动:1)单击菜单应用程序->附件->终端打开终端,在终端中输入以下命令设置开发所需的环境变量。

$ source /usr/local/src/EduKit-IV/Mini2410/set_env_linux.sh$ source /usr/crosstool/gcc-3.4.5-glibc-2.3.6/arm-linux/path.sh2)将实验目录$SIMPLEDIR/8.1-led_test/driver 下的eduk4-led.c 复制到目录内核目录$KERNELDIR/drivers/char 下。

3)修改$KERNELDIR/drivers/char 目录下的Kconfig 文件,在文件的末尾按照如下内容修改并保存:….config MMTIMERtristate "MMTIMER Memory mapped RTC for SGI Altix"depends on IA64_GENERIC || IA64_SGI_SN2default yhelpThe mmtimer device allows direct userspace access to theAltix system timer.config EDUKIT4_LEDtristate "Edukit4 Led"source "drivers/char/tpm/Kconfig"endmenu这样当make menuconfig 时,将会出现Edukit4 Led 选项。

4)修改$KERNELDIR/drivers/char 目录下的Makefile 文档,在文件的适当位置按照如下内容修改并保存:….obj-$(CONFIG_HANGCHECK_TIMER) += hangcheck-timer.oobj-$(CONFIG_TCG_TPM) += tpm/obj-$(CONFIG_EDUKIT4_LED) += eduk4-led.o11# Files generated that shall be removed upon make clean….5)单击菜单应用程序->附件->终端打开终端,在终端命令行输入以下命令配置裁剪内核。

$ cd $KERNELDIR$ make menuconfig稍后将弹出以下菜单:图8-1-6 make menuconfig 后弹出的菜单我们选择出厂提供的配置文件,选择Load an Alternate Configuration File,将弹出配置文件选择对话框,在文本框中输入配置文件config-eduk4,如下图,选择“OK”按回车键完成配置文件的选择:图8-1-7 出厂默认配置文件6)完成配置文件的选择后,菜单将进入到初始界面,接下来将根据下面的步骤来完成对LED 驱动的支持,通过计算机键盘上下键选择Device Drivers 并按回车,将出现以下菜单:图8-1-8 选择Device Drivers 后的菜单按上下键选择Character devices 并按回车,将出现以下菜单:图8-1-9 选择Character devices 后菜单按上下键选择Edukit4 Led 并按y 键,前面的<>内将有*号,表明选中Led 驱动,如下图:图8-1-10 选择Led 驱动按左右键选择Exit 回到上一级菜单,依次,当最后一次选择Exit 时,会弹出以下对话框提示是否保存配置:图8-1-11 保存配置直接选择“Yes”回车,配置完成。

7)执行以下命令编译内核:$ make编译完成之后将在路径$KERNELDIR/arch/arm/boot 下生成zImage 镜象,同时也会自动拷贝到$EXPDIR 目录下。

按照前面章节的介绍将该镜象下载到flash 中。

8)将路径切换到$SIMPLEDIR/8.1-led_test/app 下,执行以下命令编译应用程序:$ cd $SIMPLEDIR/8.1-led_test/app$ make$ make install$ make clean在该目录下将生成可执行文件led_test,并自动将该文件拷贝到/home/example/tftp/目录下。

9)准备好EduKit-IV + Mini2410-IV 平台,注意Mini2410-IV 板上的跳线为闭合状态,且确保Mini2410-IV 板载Linux 映像为实验映像(请参照下册开篇:实验环境构建),连接好交叉串口线于板载COM2 和PC 端串口,连接好交叉网线与板载主板网卡接口和PC 端网口。

10)在终端执行以下命令打开minicom 串口终端:$ sudo minicom11)给实验平台加电,进入Linux 系统,可以看到minicom 终端的启动打印信息。

12)启动完成后,在minicom 下执行以下命令将led_test 下载到tmp 目录下:# cd /tmp# tftp -g 192.192.192.190 -r./led_test -l./led_test附:请用交叉网线连接主机和实验平台,注意实验平台上的网卡是打开的,并核对主机网卡的ip 地址是否为192.192.192.190,设置方法可参照上册第六章节6.5。

13)给led_test 添加可执行权限。

# chmod 777 led_test14)运行led_test。

# ./led_testPlease look at the leds这时观看主板上的四个LED 灯在循环闪.,表明应用程序运行成功,进一步表明驱动添加成功!参考程序:1.驱动程序#include <linux/config.h>#include <linux/module.h>#include <linux/kernel.h>#include <linux/fs.h>#include <linux/init.h>#include <linux/devfs_fs_kernel.h>#include <linux/miscdevice.h>#include <linux/delay.h>#include <asm/irq.h>#include <asm/io.h>#include <asm/arch/regs-gpio.h>#include <asm/hardware.h>#define DEVICE_NAME "led"#define LED_MAJOR 231#define LED_BASE (0xE1180000)static int eduk4_led_ioctl(struct inode *inode, struct file *file, unsigned int cmd, unsigned long arg) {unsigned char status;switch(cmd) {case 0:case 1:if (arg > 4) {return -EINVAL;}status = inb(LED_BASE);if(0 == cmd){status &= ~(0x1 << arg);}else if(1 == cmd){status |= (0x1 << arg);}outb(status, LED_BASE);return 0;default:return -EINVAL;}}static struct file_operations eduk4_led_fops = {.owner.ioctl};==THIS_MODULE,eduk4_led_ioctl,static int __init eduk4_led_init(void){int ret;unsigned char status;ret = register_chrdev(LED_MAJOR, DEVICE_NAME, &eduk4_led_fops);if (ret < 0) {printk(DEVICE_NAME " can't register major number\n");return ret;}devfs_mk_cdev(MKDEV(LED_MAJOR, 0), S_IFCHR | S_IRUSR | S_IWUSR | S_IRGRP, DEVICE_NAME);status = inb(LED_BASE);outb(status & 0xf0,LED_BASE);printk(DEVICE_NAME " initialized\n");return 0;}static void __exit eduk4_led_exit(void){unsigned char status;status = inb(LED_BASE);outb(status | 0x0f,LED_BASE);printk(DEVICE_NAME " remove\n");devfs_remove(DEVICE_NAME);unregister_chrdev(LED_MAJOR, DEVICE_NAME);}module_init(eduk4_led_init);module_exit(eduk4_led_exit);MODULE_LICENSE("BSD/GPL");2.应用程序#include <stdio.h>#include <stdlib.h>#include <unistd.h>#include <sys/ioctl.h>#include <sys/types.h>#include <sys/stat.h>#include <fcntl.h>#include <sys/select.h>#include <sys/time.h>static int led_fd;int main(void){// open deviceled_fd = open("/dev/led", 0);if (led_fd < 0) {perror("open device led");exit(1);}printf("Please look at the leds\n"); // led all offioctl(led_fd, 1, 0);ioctl(led_fd, 1, 1);ioctl(led_fd, 1, 2);ioctl(led_fd, 1, 3);for(;;){// led on one by oneioctl(led_fd, 0, 0);usleep(500000);ioctl(led_fd, 0, 1);usleep(500000);ioctl(led_fd, 0, 2);usleep(500000);ioctl(led_fd, 0, 3);usleep(500000);// led off one by oneioctl(led_fd, 1, 0);usleep(500000);ioctl(led_fd, 1, 1);usleep(500000);ioctl(led_fd, 1, 2);usleep(500000);ioctl(led_fd, 1, 3);usleep(500000);// all led onioctl(led_fd, 0, 0);ioctl(led_fd, 0, 1);ioctl(led_fd, 0, 2);ioctl(led_fd, 0, 3);usleep(500000);// all led offioctl(led_fd, 1, 0);ioctl(led_fd, 1, 1);ioctl(led_fd, 1, 2);ioctl(led_fd, 1, 3);usleep(500000);}close(led_fd);return 0;}练习题:更改驱动程序,将控制由ioctl 形式改为write 形式,并添加read 接口,通过read 可获取LED状态。

相关主题