使用香橙派学习Linux udev的rules 并实现U盘的自动挂载

在之前编程首先语音刷抖音的博文里提到过udev,现在回顾一下:

什么是udev?

  • udev是一个设备管理工具,udev以守护进程的形式运行,通过侦听内核发出来的uevent来管理/dev目录下的设备文件。udev在用户空间运行,而不在内核空间 运行。它能够根据系统中的硬 件设备的状态动态更新设备文件,包括设备文件的创建,删除等。设备文件通常放在/dev目录下。使用udev后,在/dev目录下就只包含系统中真正存在的设备。

本节就深入学习以下udev相关的知识,以下是一些参考链接:

[Linux 基础] -- udev 和 rules 使用规则_udev rules_BestW2Y的博客-CSDN博客

udev概述

在之前多次提到过:Linux中一切皆文件 。在早期的 Linux 版本中,/dev 目录包含了所有可能出现的设备的设备文件。很难想象 Linux 用户如何在这些大量的设备文件中找到匹配条件的设备文件。现在 udev 只为那些连接到 Linux 操作系统的设备产生设备文件并且 udev 能通过定义一个 udev 规则(rule)来产生匹配设备属性的设备文件,这些设备属性可以是内核设备名称、总线路径、厂商名称、型号、序列号或者磁盘大小等等。

udev 添加/删除 设备文件的过程

udev的规则(rule)

规则文件是 udev 里最重要的部分,默认是存放在 /etc/udev/rule.d/ 下。所有的规则文件必须以 ".rules" 为后缀名。

下面是一个简单的规则:(规则就是规则文件里的内容)

cpp 复制代码
KERNEL=="sda", NAME="my_root_disk", MODE="0660"

其中:KERNEL 是匹配键,NAME 和 MODE 是赋值键。这条规则的意思是:如果有一个设备的内核名称为 sda,则该条件生效,执行后面的赋值:在 /dev 下产生一个名为my_root_disk 的设备文件,并把设备 文件的权限设为 0660。

同时,在语音刷抖音项目中,手机接入香橙派不能识别的解决办法,也是在udev的rules文件夹下创建规则文件" 51-android.rules ",并写入以下规则:

cpp 复制代码
SUBSYSTEM=="usb", ENV{DEVTYPE}=="usb_device", MODE="0666" 

为什么此处的规则要这么写?

首先,插入的手机usb设备对应的设备文件在"/dev/bus/usb/001"下:

可见,这个文件的名字是063(001是系统的)

通过" udevadm info --attribute-walk --name=/dev/bus/usb/001/设备名字 " 可以看到设备的详细信息,此处设备名字就写063

其中,就可以找到刚刚规则中第一句" SUBSYSTEM=="usb""的由来:

  • 这也是为什么规则第一句写上" SUBSYSTEM=="usb"",udev就能知道:这条规则是针对手机这个设备。
  • 第二句的" ENV{DEVTYPE}=="usb_device" ",和第一句一样,都是匹配键:用来设置环境变量;
  • 最后一句的" MODE="0666" "才是赋值键,用来赋予权限

所以其实,想要通过规则来匹配一个设备文件,方法不止一种,我同样可以用其他的属性来进行匹配:

比如,在上图打印的信息中注意到了VID和PID的值,用他们来写规则:

cpp 复制代码
SUBSYSTEM=="usb", ATTR{idProduct}=="ff08", ATTR{idVendor}=="2717", MODE="0666"

那么现在这条规则实现的效果 和 "之前那条使用环境变量来匹配的规则实现的效果" 是一样的。

为了验证,我修改 " /etc/udev/rules.d/ " 下的 "51-android.rules":

然后再次插入手机。并查看"/dev/bus/usb/001"路径:

可见,多了一个078

然后调用"adb devices":

可见可以成功脸上,说明用新的规则确实可以成功匹配到手机的设备文件

udev 规则的匹配键

  • ACTION:事件(uevent)的行为,例如:add(添加设备)、remove(删除设备)
  • KERNEL:内核设备名称,例如:sda,cdrom
  • DEVPATH:设备的 devpath 路径
  • SUBSYSTEM:设备的子系统名称,例如:sda 的系统为 block
  • BUS:设备在 devpath 里的总线名称,例如:usb
  • DRIVER:设备在 devpath 的设备驱动名称,例如:ide-cdrom
  • ID:设备在 devpath 里的识别号
  • SYSFS{filename}:设备的 devpath 路径下,设备的属性文件 "filename" 里的内容
  • ENV{key}:环境变量。在一条规则中,可以设定最多五条环境变量的 匹配键
  • PROGRAM:调用外部命令
  • RESULT:外部命令 PROGRAM 的返回结果

U盘的自动挂载

拿出我的U盘,它同样有一个USB口,将它接入香橙派:

然后执行" dmesg "指令:

可见,内核识别到了这个设备!且显示是sda4

然后执行"sudo mount /dev/sda4 /mnt/ " 再 "cd /mnt" 就可以查看U盘中的内容:

(乱码是因为文件名是中文)

但是这样很麻烦,每次U盘插入后还要执行两个指令,可以用udev来实现U盘的自动挂载:

首先,执行**"** **udevadm info --attribute-walk --name=/dev/sda4 "**来查看U盘的信息:

在里面可以选取用于匹配U盘的udev规则,通常使用KERNAL 或 SUBSYSTEM来匹配U盘

那么话不多说,直接再次 " cd /etc/udev/rules.d/ " 然后 " sudo vim my_storage.rules "

规则具体为:

cpp 复制代码
ACTION=="add", SUBSYSTEMS=="block", SUBSYSTEM=="block", RUN{program}+="/bin/mkdir
/media/%k" ,RUN{program}+="/usr/bin/systemd-mount --no-block --collect $devnode
/media/%k"
  • ACTION:匹配键,匹配添加设备的动作
  • SUBSYSTEMS:匹配键,匹配为block(此处也可以是usb)
  • SUBSYSTEM:匹配键,匹配为block

通过这三个匹配键,匹配到U盘

  • RUN:运行命令,此处执行" /bin/mkdir "指令创建一个名为"media"的文件夹,里面有名为"%k" 的文件,%k是sda/sdb的通配符
  • RUN:运行命令,此处执行" /usr/bin/systemd-mount "指令挂载U盘到"%k"文件夹下

实现效果

重新拔插U盘,并"sudo service udev restart"重启udev后,查看media文件夹:

可见此时没有输入任何命令,就可以访问U盘的文件了,成功实现了U盘的自动挂载!

另外,可以安装一个tree指令来查看U盘文件,使用"sudo apt-get install tree"来安装;

安装完成后,进入media文件夹后,直接输入"tree ",就可以清晰的看到文件结构了:

此时拔掉U盘,再次输入"tree":

可见,此时就没有任何文件了!

相关推荐
CoolTiger、9 分钟前
【Vmware16安装教程】
linux·虚拟机·vmware16
jiao0000138 分钟前
数据结构——队列
c语言·数据结构·算法
m0_7417688540 分钟前
使用docker的小例子
运维·docker·容器
铁匠匠匠42 分钟前
从零开始学数据结构系列之第六章《排序简介》
c语言·数据结构·经验分享·笔记·学习·开源·课程设计
C-SDN花园GGbond44 分钟前
【探索数据结构与算法】插入排序:原理、实现与分析(图文详解)
c语言·开发语言·数据结构·排序算法
学习3人组1 小时前
CentOS 中配置 OpenJDK以及多版本管理
linux·运维·centos
厨 神2 小时前
vmware中的ubuntu系统扩容分区
linux·运维·ubuntu
Karoku0662 小时前
【网站架构部署与优化】web服务与http协议
linux·运维·服务器·数据库·http·架构
迷迭所归处2 小时前
C++ —— 关于vector
开发语言·c++·算法
geek_Chen012 小时前
虚拟机共享文件夹开启后mnt/hgfs/下无sharefiles? --已解决
linux·运维·服务器