BQ27501驱动和用户空间交互数据
2012-04-10 19:22
435 查看
内核中的数据与用户空间数据交互常用的函数有copy_to_user,copy_from_user,和宏定义put_user,get_user,__put_user,__get_user。copy_from_user和copy_to_user函数复制块数据,如数组,结构体;put_user,get_user,__put_user,__get_user复制的内存是简单类型,如char,int,long,而且只能复制1,2,4,8个字节。put_user,get_user,__put_user,__get_user执行效率比copy_to_user,copy_from_user的效率要高很多。put_user和__put_user区别在于,前者会调用access_ok进行内核地址的检查,而后者不进行地址检查。bq27501驱动的功能是向用户空间提供电池相关的信息;而且不需要用户空间向电池输入数据;另外电池的信息都是很小的数据,都可以使用unsigned short表示,所以没有必要使用copy_to_user块数据传递的函数;另外再根据《Linux驱动程序》书中“大多数驱动程序代码中都不需要access_ok,内存管理程序会处理它”,所以选择__put_user来向用户空间传递电池信息数据。
__put_user(var, ptr),var将内核中的数据var复制到用户空间;ptr是用户地址空间的指针,指向内核空间中ioctl最后一个参数。bq27501与用户空间交互的代码片段如下: static long bq27501_ioctl(struct file *file, unsigned int cmd, unsigned long arg) { BATT_INFO *pBattInfo = &BattInfo; unsigned short temp; switch(cmd) { case GET_RM: if((i2c_read_reg(&bq27501_i2c_client,RM_REG_ADDR_L, &pBattInfo->RemainingCapacity))>=0){ printk(KERN_ALERT"RaminingCapacity is %u mAh ...\n",pBattInfo->RemainingCapacity); __put_user(pBattInfo->RemainingCapacity, (int __user *)arg); } break; …… } 在用户空间, ioctl 系统调用的原型为:int ioctl(int fd, unsigned long cmd, ...); 这个原型中的点表示函数有一个单个可选的参数, 传统上标识为 char *argp. 这些点在那里只是为了阻止在编译时的类型检查。第二个参数,是用户向驱动传递的命令(如读取剩余电量值)。第三个参数的实际特点依赖所发出的特定的控制命令,即第二个参数。一些命令不用参数, 一些用一个整数值, 以及一些使用指向其他数据的指针。是否使用参数和指针是根据打开字符设备的方式决定,打开设备的方式有三种,在fcntl.h有其宏定义,只读,只写,读写,如下所示: #define O_RDONLY 00 #define O_WRONLY 01 #define O_RDWR 02 用户空间读取驱动中参数代码片段如下: if((fd = open("/dev/bq27501",2)) == -1) { perror("device open err!\n"); return -1; } printf("open ok!\n"); ioctl(fd,atoi(argv[1]),&v); //v是一个整型,用于保存内核空间传递过来的数据 printf("(2)........cmd = [%d],val = [%d]...........\n",atoi(argv[1]),v);
相关文章推荐
- WDF驱动开发(3)- 用户模式程序和驱动的数据交互
- Binder框架 -- 用户空间和驱动的交互
- 用户空间与内核空间数据交互
- linux驱动开发之字符设备--内核和用户空间数据的交换(ioctl)
- linux驱动开发--copy_to_user 、copy_from_user函数实现内核空间数据与用户空间数据的相互访问
- linux驱动开发之字符设备--内核和用户空间数据的交换(read write)
- 用户空间与内核驱动的交互过程 — ioctl
- linux驱动开发之字符设备--内核和用户空间数据的交换(sysfs)
- Linux驱动:用户空间,内核空间内存交互测试
- poll在用户空间与驱动中的交互及使用事项
- Driver:LED灯操作、内核空间和用户空间的数据交互、ioctl函数、设备文件安装与销毁
- 用户空间与内核空间数据交换的方式(6)------模块参数与sysfs
- 【转载】在 Linux 下用户空间与内核空间数据交换的方式,第 1 部分: 内核启动参数、模块参数与sysfs、sysctl、系统调用和netlink
- 统计用户占用多大的空间,一行数据超过4k
- 简单统计SQLSERVER用户数据表大小(包括记录总数和空间占用情况)
- Oracle(11g)建库、建表空间、建用户并授权、导入导出数据表
- Linux 下用户空间与内核空间数据交换的方式
- 用户空间与内核空间数据交换的方式(5)------内核启动参数
- linux用户空间和内核空间交换数据