免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
查看: 783 | 回复: 0
打印 上一主题 下一主题

linux设备驱动笔记2——字符设备驱动 [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2008-11-24 22:22 |只看该作者 |倒序浏览
  “全局性”是指,如果打开设备多次,所有打开它的文件描述符共享其中的数据。“持久性”是指,如果设备关闭后再次打开,数据不丢失。
※       真实的驱动程序利用中断与它们的设备同步

主设备号和次设备号
※       主
设备号标识设备对应的驱动程序;次设备号由内核使用,用于正确确定设备文件所指的设备。我们可以通过次设备号获得一个指向内核设备的直接指针,也可将次设
备号当作设备本地数组的索引,不管用哪种方式,除了知道次设备号用来指向驱动程序所实现的设备之外,内核本身基本上不关心关于次设备号的任何其他消息。
※       设备编号的内部表达
n         在内核中,dev_t类型(在中定义)用来保存设备编号——包括主设备号和次设备号。
n         MAJOR(dev_t dev);      MINOR(dev_t dev)              MKDEV(int major, int minor)

※       分配和释放设备编号
n         :
int register_chrdev_region(dev_t first, unsigned int count, char *name);
int alloc_chrdev_region(dev_t *dev, unsigned int firstminor,                         unsigned int count, char *name);void unregister_chrdev_region(dev_t first, unsigned int count); 驱动程序需要将设备编号和内部函数连接起来,这些内部函数用来实现设备的操作。

※       动态分配主设备号
n         某些主设备号已经静态地分配给了大部分公用设备。在内核源码树的Documentation/device.txt文件中可以找到这些设备的列表。
n         一旦驱动程序被广泛使用,随机选定的主设备号可能造成冲突和麻烦
n         强烈推荐你不要随便选择一个一个当前不用的设备号做为主设备号,而使用动态分配机制获取你的主设备号。
n         动态分配的缺点是,由于分配给你的主设备号不能保证总是一样的,无法事先创建设备节点。然而这不是什么问题,这是因为一旦分配了设备号,你就可以从/proc/devices读到。为了加载一个设备驱动程序,对insmod的调用被替换为一个简单的脚本,它通过/proc/devices获得新分配的主设备号,并创建节点
#!/bin/shmodule="scull"device="scull"mode="664" # invoke insmod with all arguments we got# and use a pathname, as newer modutils don't look in . by default /sbin/insmod ./$module.ko $* || exit 1 # remove stale nodes rm -f /dev/${device}[0-3]major=$(awk "\\$2=  =\"$module\" {print \\$1}" /proc/devices)mknod /dev/${device}0 c $major 0mknod /dev/${device}1 c $major 1mknod /dev/${device}2 c $major 2mknod /dev/${device}3 c $major 3 # give appropriate group/permissions, and change the group.# Not all distributions have staff, some have "wheel" instead. group="staff"grep -q '^staff:' /etc/group || group="wheel" chgrp $group /dev/${device}[0-3]chmod $mode  /dev/${device}[0-3]
n         分配主设备号的最佳方式:默认采用动态分配,同时保留在加载甚至是编译时指定主设备号的余地。
n         Here's the code we use in scull 's source to get a major number:

if (scull_major) {    dev = MKDEV(scull_major, scull_minor);    result = register_chrdev_region(dev, scull_nr_devs, "scull");} else {    result = alloc_chrdev_region(&dev, scull_minor, scull_nr_devs, "scull");    scull_major = MAJOR(dev);}if (result     printk(KERN_WARNING "scull: can't get major %d\n", scull_major);    return result;}
字符设备的注册n 内核内部使用struct cdev结构来表示字符设备。为此我们的代码应包含,
其中定义了这个结构以及与其相关的一些辅助函数。
※  The classic way to register a char device driver is with:
int register_chrdev(unsigned int major, const char *name,
struct file_operations *fops);int unregister_chrdev(unsigned int major, const char *name);
               
               
               

本文来自ChinaUnix博客,如果查看原文请点:http://blog.chinaunix.net/u2/86325/showart_1663903.html
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP