第三章:字符设备驱动-1:Major and Minor Numbers

In continuation of the previous text:第三章:字符设备驱动-0:The Design of scull, let's GO ahead.

Major and Minor Numbers

Char devices are accessed through names in the filesystem. Those names are called special files or device files or simply nodes of the filesystem tree; they are conventionally located in the /dev directory. Special files for char drivers are identified by a “c” in the first column of the output of ls –l. Block devices appear in /dev as well, but they are identified by a “b.” The focus of this chapter is on char devices, but much ofthe following information applies to block devices as well.

字符设备通过文件系统中的名称进行访问,这些名称被称为特殊文件设备文件或简称为文件系统树的节点;它们通常位于 /dev 目录下。

字符驱动对应的特殊文件可通过 ls -l 命令的输出识别:其权限列的第一个字符为 “c”(表示 char)。块设备同样位于 /dev 目录下,但权限列第一个字符为 “b”(表示 block)。本章重点讨论字符设备,但以下内容的大部分也适用于块设备。

If you issue the ls –l command, you’ll see two numbers (separated by a comma) in the device file entries before the date of the last modification, where the file length normally appears. These numbers are the major and minor device number for the particular device. The following listing shows a few devices as they appear on a typical system. Their major numbers are 1, 4, 7, and 10, while the minors are 1, 3, 5, 64, 65, and 129.

执行 ls -l 命令后,在设备文件条目的 “最后修改日期” 之前、通常显示文件长度的位置,会看到两个用逗号分隔的数字。这两个数字分别是该设备的主设备号(major device number)和次设备号(minor device number)。

以下列表展示了典型系统中的几个设备示例:它们的主设备号分别为 1、4、7、10,次设备号则为 1、3、5、64、65、129。

crw-rw-rw- 1 root root    1,   3 Apr 11 2002 null
crw------- 1 root root   10,   1 Apr 11 2002 psaux
crw------- 1 root root    4,   1 Oct 28 03:04 tty1
crw-rw-rw- 1 root tty     4,  64 Apr 11 2002 ttyS0
crw-rw---- 1 root uucp    4,  65 Apr 11 2002 ttyS1
crw--w---- 1 root vcsa    7,   1 Apr 11 2002 vcs1
crw--w---- 1 root vcsa    7, 129 Apr 11 2002 vcsa1
crw-rw-rw- 1 root root    1,   5 Apr 11 2002 zero

Traditionally, the major number identifies the driver associated with the device. For example, /dev/null and /dev/zero are both managed by driver 1, whereas virtual consoles and serial terminals are managed by driver 4; similarly, both vcs1 and vcsa1 devices are managed by driver 7. Modern Linux kernels allow multiple drivers to share major numbers, but most devices that you will see are still organized on the one-major-one-driver principle.

传统上,主设备号用于标识与设备关联的驱动程序。例如,/dev/null 和 /dev/zero 均由主设备号为 1 的驱动管理,而虚拟控制台和串行终端由主设备号为 4 的驱动管理;同样,vcs1 和 vcsa1 设备均由主设备号为 7 的驱动管理。现代 Linux 内核允许多个驱动程序共享主设备号,但你常见的大多数设备仍遵循 “一个主设备号对应一个驱动” 的原则。

The minor number is used by the kernel to determine exactly which device is being referred to. Depending on how your driver is written (as we will see below), you can either get a direct pointer to your device from the kernel, or you can use the minor number yourself as an index into a local array of devices. Either way, the kernel itself knows almost nothing about minor numbers beyond the fact that they refer to devices implemented by your driver.

次设备号被内核用来精确区分具体指向哪个设备。根据驱动程序的编写方式(我们将在下文介绍),你既可以从内核获取设备的直接指针,也可以将次设备号用作本地设备数组的索引。无论哪种方式,内核本身对次设备号的了解仅限于:它们指向由你的驱动程序实现的设备。

补充说明:

  1. 设备文件的核心作用

    设备文件并非存储实际数据的普通文件,而是 “用户态与内核驱动的交互接口”:

    1. 设备文件本身不包含数据,仅通过 “设备号”关联到内核中的驱动程序,实现 “文件操作→驱动函数” 的映射。

    2. 用户态程序通过 open/read/write 等常规文件操作函数访问设备文件时,内核会将这些操作转发给对应的设备驱动;

  2. /dev 目录的特殊性

    /dev 目录通常挂载的是 devtmpfs 或 tmpfs 这类临时文件系统,特点是:

    1. 目录中的内容不存储在磁盘上,而是存在内存中,系统重启后会重新生成,避免磁盘占用。

    2. 设备文件在系统启动时由 udev(或 mdev)工具自动创建,无需手动新建;

  3. 主设备号的核心作用:关联驱动程序

    主设备号是内核识别 “设备所属驱动” 的关键标识 —— 同一类设备(由同一个驱动管理)共享相同的主设备号。例如:

    1. tty1ttyS0ttyS1 的主设备号均为 4,说明它们由同一个终端驱动管理。内核通过主设备号在 “驱动注册表” 中查找对应的驱动程序,将设备文件操作转发给该驱动。

    2. 示例中 null 和 zero 的主设备号均为 1,说明它们由同一个内核驱动(char/mem.c 中的内存类驱动)管理;

  4. 次设备号的核心作用:区分设备实例

    次设备号用于区分 “同一个驱动管理的多个设备实例”,由驱动自行定义其含义,常见用途包括:

    1. 标识逻辑功能:如 vcs1(次设备号 1)和 vcsa1(次设备号 129),虽主设备号相同(7),但次设备号区分了 “文本模式” 和 “属性模式” 两种逻辑功能。

    2. 标识设备分区 / 功能:如块设备中,次设备号可区分磁盘的不同分区(如 /dev/sda1 次设备号为 1,对应第一个分区);

    3. 标识物理设备:如串口驱动中,次设备号 64 对应 ttyS0(第一个串口),65 对应 ttyS1(第二个串口);

  5. 设备号的分配规则

    ​​​​​​​主设备号分为 “静态分配” 和 “动态分配” 两种方式:

    1. 动态分配:无需指定具体主设备号,通过 alloc_chrdev_region() 让内核自动分配未占用的主设备号(推荐现代驱动使用,避免设备号冲突)。次设备号通常由驱动自行管理,可一次性申请一个 “次设备号范围”(如申请 0-3 共 4 个次设备号,对应 scull0~scull3)。

    2. 静态分配:需提前在 /proc/devices 中查询未占用的主设备号,通过 register_chrdev_region() 申请(适用于需固定设备号的场景,如经典设备 null 主设备号固定为 1);


技术交流,欢迎加入社区:GPUers

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

DeeplyMind

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值