Chinaunix首页 | 论坛 | 博客
  • 博客访问: 98139
  • 博文数量: 38
  • 博客积分: 0
  • 博客等级: 民兵
  • 技术积分: 384
  • 用 户 组: 普通用户
  • 注册时间: 2014-04-06 16:52
文章分类

全部博文(38)

文章存档

2014年(38)

我的朋友

分类: 嵌入式

2014-05-05 17:08:08

1.按键驱动button.c代码如下

点击(此处)折叠或打开

  1. //moudle.h 包含了大量加载模块需要的函数和符号的定义
  2. #include <linux/module.h>
  3. //kernel.h以便使用printk()等函数
  4. #include <linux/kernel.h>
  5. //fs.h包含常用的数据结构,如struct file等
  6. #include <linux/fs.h>
  7. //uaccess.h 包含copy_to_user(),copy_from_user()等函数
  8. #include <linux/uaccess.h>
  9. //io.h 包含inl(),outl(),readl(),writel()等IO口操作函数
  10. #include <linux/io.h>
  11. #include <linux/miscdevice.h>
  12. #include <linux/pci.h>
  13. //init.h来指定你的初始化和清理函数,例如:module_init(init_function)、module_exit(cleanup_function)
  14. #include <linux/init.h>
  15. #include <linux/delay.h>
  16. #include <linux/device.h>
  17. #include <linux/cdev.h>
  18. #include <linux/gpio.h>
  19. #include <linux/irq.h>
  20. #include <linux/sched.h>
  21. #include <linux/interrupt.h>
  22. #include <linux/poll.h>
  23. //irq.h中断与并发请求事件
  24. #include <asm/irq.h>
  25. //下面这些头文件是IO口在内核的虚拟映射地址,涉及IO口的操作所必须包含
  26. //#include <mach/gpio.h>
  27. #include <mach/regs-gpio.h>
  28. #include <plat/gpio-cfg.h>
  29. #include <mach/hardware.h>
  30. #include <mach/map.h>


  31. static struct class *button_class;
  32. static int major;


  33. static int button_open(struct inode *inode, struct file *file)
  34. {    
  35.     /*设置6410的GPIO管脚的功能可以用s3c_gpio_cfgpin函数*/
  36.     s3c_gpio_cfgpin(S3C64XX_GPN(0), S3C_GPIO_INPUT);//设置GPN0为输入引脚
  37.     s3c_gpio_cfgpin(S3C64XX_GPN(1), S3C_GPIO_INPUT);//设置GPN1为输入引脚
  38.     s3c_gpio_cfgpin(S3C64XX_GPN(2), S3C_GPIO_INPUT);//设置GPN2为输入引脚
  39.     s3c_gpio_cfgpin(S3C64XX_GPN(3), S3C_GPIO_INPUT);//设置GPN3为输入引脚
  40.     s3c_gpio_cfgpin(S3C64XX_GPN(4), S3C_GPIO_INPUT);//设置GPN4为输入引脚
  41.     s3c_gpio_cfgpin(S3C64XX_GPN(5), S3C_GPIO_INPUT);//设置GPN5为输入引脚
  42.     return 0;
  43. }

  44. static ssize_t button_read(struct file *file, char __user *buf, size_t size, loff_t * ppos)
  45. {
  46.     unsigned char button_vals[6];

  47.     if (size != sizeof(button_vals))
  48.         return -EINVAL;//若返回的数据大小不等于数组大小,返回错误值

  49.     button_vals[0] = gpio_get_value(S3C64XX_GPN(0)) ;//读取GPNDAT0的值
  50.     button_vals[1] = gpio_get_value(S3C64XX_GPN(1)) ;//读取GPNDAT2的值
  51.     button_vals[2] = gpio_get_value(S3C64XX_GPN(2)) ;//读取GPNDAT3的值
  52.     button_vals[3] = gpio_get_value(S3C64XX_GPN(3)) ;//读取GPNDAT4的值
  53.     button_vals[4] = gpio_get_value(S3C64XX_GPN(4)) ;//读取GPNDAT5的值
  54.     button_vals[5] = gpio_get_value(S3C64XX_GPN(5)) ;//读取GPNDAT6的值

  55.     if( copy_to_user(buf, button_vals, sizeof(button_vals)) )//把button_val的值传递给用户(测试程序)
  56.     {
  57.         printk("error in function ‘copy_to_user’ !\n");
  58.         return -EFAULT;
  59.     }
  60.     return 0;
  61. }

  62. static ssize_t button_write(struct file *file, const char __user *buf, size_t count, loff_t * ppos)
  63. {
  64.     return 0;
  65. }

  66. static struct file_operations button_fops = {
  67.     .owner = THIS_MODULE, /* 这是一个宏,推向编译模块时自动创建的__this_module变量 */
  68.     .open = button_open,
  69.     .read = button_read,
  70.     .write = button_write,
  71. };

  72. static int button_init(void)
  73. {
  74.     major = register_chrdev(0, "button_dev", &button_fops);//注册,告诉内核
  75.     button_class = class_create(THIS_MODULE, "button_cls");
  76.     device_create(button_class, NULL, MKDEV(major, 0), NULL, "button");/* /dev/button */
  77.     
  78.     return 0;
  79. }

  80. static void button_exit(void)
  81. {
  82.     unregister_chrdev(major, "button_cls");
  83.     device_destroy(button_class, MKDEV(major, 0));
  84.     class_destroy(button_class);
  85. }

  86. module_init(button_init);
  87. module_exit(button_exit);

  88. MODULE_LICENSE("GPL");

2.按键测试程序button_test.c代码如下

点击(此处)折叠或打开

  1. #include <sys/types.h>
  2. #include <sys/stat.h>
  3. #include <fcntl.h>
  4. #include <stdio.h>

  5. int main(int argc, char **argv)
  6. {
  7.     int fd;
  8.     unsigned char button_vals[6];
  9.     int cnt = 0;
  10.     
  11.     /*打开/dev/button设备*/
  12.     fd = open("/dev/button", O_RDWR);
  13.     if (fd < 0)
  14.         printf("can't open!\n");
  15.     
  16.     /*死循环*/
  17.     while(1)
  18.     {    
  19.         /*从驱动程序中读取button_vals的值,与驱动程序中的copy_to_user对应*/
  20.         read(fd, button_vals, sizeof(button_vals));
  21.         
  22.         /*如果有按键按下,打印*/
  23.         if(!button_vals[0] || !button_vals[1] || !button_vals[2] || !button_vals[3] || !button_vals[4] || !button_vals[5])
  24.         {
  25.             printf("%4d button pressed : %d %d %d %d %d %d\n", cnt++, button_vals[0] ,button_vals[1] ,button_vals[2] ,button_vals[3] ,button_vals[4] ,button_vals[5]);
  26.         }
  27.     }    
  28.     return 0;

3.执行测试程序后,按下按键后就能打印出按键信息,但是程序一直处于死循环状态,大量消耗cpu资源
    可通过./button_test &命令使测试程序后台运行,然后用top命令查看cpu使用状态,可见cpu使用率接近100%。

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