驱动程序源代码:led_timer.c
#include <linux/init.h>
#include <linux/module.h>
#include <linux/fs.h>
#include <asm/uaccess.h>
#include <asm/io.h>
#include <linux/delay.h>
#include <linux/jiffies.h>
#include <linux/timer.h>
static volatile unsigned int *GPJ2CON,*GPJ2DAT;
static int major = 0;
struct timer_list time;
static int counter;
static void led(unsigned long arg)//定时器处理函数
{
*GPJ2DAT &= 0xf0;
mdelay(500);
*GPJ2DAT |= 0x0f;
printk(KERN_NOTICE "current jiffies is %ld\n",jiffies);
counter++;
mod_timer(&time,jiffies + HZ); //修改定时时间
}
static int led_open(struct inode *pi, struct file *pf)
{
printk("<open>test open.\n");
*GPJ2CON &= 0xffff0000;
*GPJ2CON |= 0x00001111; //设置为输出
*GPJ2DAT |= 0x0f; //熄灭所有LED
counter = 0;
init_timer(&time);//初始化定时器
time.function = &led;
time.expires = jiffies + HZ;
/*
HZ = 1S
jiffies_to_msecs(1000) = 3906
jiffies_to_msecs(10000) = 39062
msecs_to_jiffies(1000) = 256
*/
add_timer(&time);//添加,启动定时器
return 0;
}
static int led_release(struct inode *pi, struct file *pf)
{
del_timer(&time);
printk("<release> test release.\n");
return 0;
}
static ssize_t led_read(struct file *pf, char __user *pbuf, size_t len, loff_t *ppos)
{
put_user(counter,(int *)pbuf);
return 0;
}
static struct file_operations led_fops =
{
.owner = THIS_MODULE,
.open = led_open,
.release = led_release,
.read = led_read,
};
static __init int led_init(void)
{
major = register_chrdev(0, "LED", &led_fops);
printk("major = %d\n",major);
GPJ2CON = ioremap(0xe0200280, 8);
GPJ2DAT = GPJ2CON + 1;
return 0;
}
static __exit void led_exit(void)
{
iounmap(GPJ2CON);
unregister_chrdev(major, "LED");
*GPJ2DAT |= 0x0f;
printk("\n Goodbye!\n\n");
}
module_init(led_init);
module_exit(led_exit);
MODULE_LICENSE("GPL");
MODULE_AUTHOR("Huang Dezhi");
MODULE_DESCRIPTION("This is LED TIMER");
在kernel/drivers/char下的Kconfig里面添加
config LED_TIMER
tristate "LED TIMER"
default y
在kernel/drivers/char下的Makefile里面添加
obj-m += led-timer.o
在kernel下编译:$ make menuconfig
$ make modules
应用程序:led_timer_app.c
#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <string.h>
#include <unistd.h>
#include <stdlib.h>
int main()
{
int fd;
int counter = 0;
int count ;
char buf[4];
fgets(buf,sizeof(buf),stdin);
count = atoi(buf);
fd = open("led",O_RDWR);
/*打开second设备文件*/
if(fd != -1)
{
while( (count -1) >= counter )
{
read(fd,&counter,sizeof(unsigned int));//读目前经历的秒数
}
}
else
{
printf("Device open failure\n");
}
return 0;
}
下载到开发板上:tftp -g -r led_timer.ko 192.168.x.x
tftp -g -r led_timer_app 192.168.x.x
修改led_timer_app 的权限: chmod 777 led_timer_app
装载模块:insmod led_timer.ko
创建设备:mknod led c 251 0
执行程序:./led_timer_app
然后输入数字会看到LED闪亮指定次数