Chinaunix首页 | 论坛 | 博客
  • 博客访问: 151567
  • 博文数量: 25
  • 博客积分: 1632
  • 博客等级: 上尉
  • 技术积分: 324
  • 用 户 组: 普通用户
  • 注册时间: 2010-04-02 21:19
文章分类

全部博文(25)

文章存档

2011年(13)

2010年(12)

我的朋友

分类: LINUX

2010-04-11 20:40:23

现在我们来进行最简单的设备程序的编写LED的驱动.
首先进入根文件目录
# mkdir driver
# cd driver/
# mkdir led
# cd led
# vim leds.c
#include
#include
#include
#include
#include
#include
#include
#include
#define NAME "four led test"
static int major =231;//定义主设备号
static unsigned long led_table [] = //定义不同的led控制引脚
{
    AT91_PIN_PA15,
    AT91_PIN_PA16,
    AT91_PIN_PA30,
    AT91_PIN_PA31,
};
static int myled_driver_open(struct inode *inode,struct file *file)
{
    unsigned m =iminor(inode);
    if(m>63) return -EINVAL;
    printk("led test driver opened! ");
    return nonseekable_open(inode,file);
}
static int myled_driver_release(struct inode *inode,struct file *file)
{
    printk("my test driver released! ");
    return 0;
}
static int myled_driver_ioctl(struct inode *inode,struct file *file,unsigned int cmd,unsigned long arg)
{
      unsigned int regled1;
      regled1=gpio_get_value(led_table[arg]);
      printk("led1 reg is : %d",regled1);
      at91_set_gpio_output(led_table[arg],1);
      switch(cmd)//控制led_table[arg]的亮灭
      {
        case    0x00:at91_set_gpio_value(led_table[arg],0);
                    break;     
        case    0x01:gpio_set_value(led_table[arg],1);
                    break;
        default:   
                    break;   
     }
     return 1;
}
static struct file_operations myled_driver_fops = 
{
    .owner =THIS_MODULE,
    .ioctl =myled_driver_ioctl,
    .open =myled_driver_open,
    .release =myled_driver_release,
};
 
static int __init myled_driver_init(void) //执行insmod的时候调用次函数
{
       int ret;   
       gpio_set_value(led_table[0],0);
       gpio_set_value(led_table[1],0);
       gpio_set_value(led_table[2],0);
       gpio_set_value(led_table[3],0);
       printk(KERN_ALERT "led modules is install ");
       ret=register_chrdev(major,NAME,&myled_driver_fops);
       if(ret<0)
        {
             printk("unable to register myled driver! ");
             return ret;
        }           
       return 0;
}
 
static void __exit myled_driver_exit(void) //执行rmmod的时候调用次函数
{
        unregister_chrdev(major,NAME);
        printk("Goodbye,cruel world! ");
}
 module_init(myled_driver_init);
module_exit(myled_driver_exit);
 MODULE_AUTHOR("microcreat");
MODULE_DESCRIPTION("this is test modules used to test at91sam9261 led");
MODULE_LICENSE("Dual BSD/GPL"); 
然后写一个Makefile文件
# Makefile2.6
 ifneq ($(KERNELRELEASE),)
#kbuild syntax. dependency relationship of files and target modules are listed here.
 obj-m +=leds.o
#obj-m :=gpio_driver.o
 else
 PWD :=$(shell pwd)
 KEVER ?=$(shell uname -r)
 KDIR :=/workdir/at91sam9261/kernel/linux-2.6.24
default:
       #$(MAKE) -C $(KDIR) M=$(PWD)
 make -C $(KDIR) M=$(PWD) modules
clean:
 rm -rf .*.cmd *.o *.mod.c *.ko .tmp_versions *.order *symvers
endif
然后进行make
# ls
leds.c  Makefile
# make
make -C /workdir/at91sam9261/kernel/linux-2.6.24 M=/workdir/at91sam9261/filesyetem/rootfs/driver/led modules
make[1]: Entering directory `/workdir/at91sam9261/kernel/linux-2.6.24'
  CC [M]  /workdir/at91sam9261/filesyetem/rootfs/driver/led/leds.o
  Building modules, stage 2.
  MODPOST 1 modules
  CC      /workdir/at91sam9261/filesyetem/rootfs/driver/led/leds.mod.o
  LD [M]  /workdir/at91sam9261/filesyetem/rootfs/driver/led/leds.ko
make[1]: Leaving directory `/workdir/at91sam9261/kernel/linux-2.6.24'
# ls
leds.c  leds.ko  leds.mod.c  leds.mod.o  leds.o  Makefile  Module.symvers
然后建立一个led的测试文件:
# mkdir ledtest
# cd ledtest
# vim ledtest.c
#include
#include
#include
#include
int main(void)
{
   int fd;
   fd=open("/dev/leds",0);
   if(fd<0)
   {
      printf("Can't open /dev/leds\n");
      goto end1;
   }
   while(1)
   {
     ioctl(fd,0,0);
     sleep(1);
     ioctl(fd,1,0);
     sleep(1);
   }
   close(fd);
end1:
   return 0;
}
保存退出
# arm-none-linux-gnueabi-gcc -static ledtest.c -o ledtest
# ls
ledtest  ledtest.c
这样生成的led的测试文件.
然后将新的文件系统制作成为cramfs下载到板子上去,当板子进入界面后进行下面的操作.
[root@microcreat /]$ls
app      dev      home     mnt      sbin     usr
bin      driver   lib      proc     sys      var
boot     etc      linuxrc  root     tmp
[root@microcreat /]$cd /driver/led/
[root@microcreat led]$ls
Makefile        leds.c          leds.mod.c      leds.o
Module.symvers  leds.ko         leds.mod.o
[root@microcreat led]$insmod leds.ko
led modules is install
可以看到动态加载成功!
[root@microcreat led]$mknod /dev/leds c 231 0
建立设备节点
这样就到ledtest目录下运行led测试程序.
[root@microcreat led]$cd /app/ledtest/
[root@microcreat ledtest]$ls
ledtest    ledtest.c
[root@microcreat ledtest]$./ledtest
led test driver opened! led1 reg is : 1led1 reg is : 0led1 reg is : 1led1 reg is : 0led1 reg is : 1led1 reg is : 0led1 reg is : 1led1 reg is : 0led1 reg is : 1
可以看到对应的LED闪烁,这样就点亮了led灯了!
 

 
阅读(2554) | 评论(3) | 转发(0) |
给主人留下些什么吧!~~

chinaunix网友2010-05-12 09:13:05

什么时候能出裸奔笔记。毕竟咱们做硬件的,偏向底层。小弟最近在做NORFLASH启动,呵呵刚起步。IAR环境,难度不小。这个CPU资料没有2410多。

dream_microcreat2010-05-06 23:25:27

这个是我自己的经历,也有很多笨办法,自己摸着石头过河!现在也是皮毛! 以后多交流呵呵! 很多东西都是google而来,自己修改,然后在自己板子上跑起来!

chinaunix网友2010-05-04 13:32:10

博主再接再励,多出9261笔记。俺也在学这个CPU,不过俺打算裸机,不上系统。