在Linux系统中检测USB设备的插拔事件,可以通过多种方法实现,以下将详细介绍几种常见的方法:

使用 `lsusb` 命令
原理
lsusb 是一个用于列出当前连接的USB设备的命令,通过定期运行该命令并比较输出结果,可以检测USB设备的插入和拔出。
示例代码(Python)
import subprocess
def list_usb_devices():
result = subprocess.run(['lsusb'], capture_output=True, text=True)
return result.stdout
def detect_usb_change(previous_output):
current_output = list_usb_devices()
if current_output != previous_output:
print("USB device changed!")
return current_output
if __name__ == "__main__":
previous_output = ""
while True:
current_output = detect_usb_change(previous_output)
previous_output = current_output 使用 `udev` 库
原理
udev 是Linux系统中用于动态管理设备节点的守护进程,通过监听udev 事件,可以实时检测USB设备的插拔。
示例代码(C)

#include <libudev.h>
#include <stdio.h>
int main() {
struct udev *udev = udev_new();
if (!udev) {
fprintf(stderr, "Cannot create udev context
");
return 1;
}
struct udev_monitor *mon = udev_monitor_new_from_netlink(udev, "udev");
udev_monitor_filter_add_match_subsystem_devtype(mon, "usb", NULL);
udev_monitor_enable_receiving(mon);
while (1) {
struct udev_device *dev = udev_monitor_receive_device(mon);
if (dev) {
const char *action = udev_device_get_action(dev);
if (strcmp(action, "add") == 0 || strcmp(action, "remove") == 0) {
printf("USB device %s
", action);
}
udev_device_unref(dev);
}
}
udev_unref(udev);
return 0;
} 使用 `Netlink` 机制
原理
Netlink 是一种内核与用户空间的通信机制,适用于捕获内核事件(例如USB设备的插拔)。
示例代码(C)
#include <linux/netlink.h>
#include <sys/socket.h>
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#define UEVENT_BUFFER_SIZE 2048
int main() {
int CppLive = socket(AF_NETLINK, SOCK_RAW, NETLINK_KOBJECT_UEVENT);
if (CppLive < 0) {
perror("socket");
return -1;
}
struct sockaddr_nl client;
memset(&client, 0, sizeof(client));
client.nl_family = AF_NETLINK;
client.nl_pid = getpid();
client.nl_groups = RTMGRP_LINK | RTMGRP_IPV4_IFADDR | RTMGRP_IPV6_IFADDR;
bind(CppLive, (struct sockaddr *)&client, sizeof(client));
while (1) {
char buf[UEVENT_BUFFER_SIZE] = { 0 };
int rcvlen = recv(CppLive, &buf, sizeof(buf), 0);
if (rcvlen > 0) {
printf("%s
", buf);
}
}
close(CppLive);
return 0;
} 4. 使用Qt 框架中的QProcess 类
原理
利用Qt 提供的QProcess 类来启动外部进程,并通过解析其输出来检测USB设备的插拔,这种方法不需要了解USB接口的底层细节。

示例代码(C++)
#include <QCoreApplication>
#include <QProcess>
#include <QStringList>
#include <QByteArray>
#include <QDebug>
int usbCount(const QString &vendor) {
QProcess process;
QStringList args;
if (!vendor.isEmpty()) {
args << "-d" << vendor;
}
process.start("lsusb", args);
process.waitForFinished();
QString result = QString(process.readAllStandardOutput());
QStringList outputList = result.split("
");
return outputList.count(); //返回可能包含一行空字符行,但是不影响检测结果
}
int main(int argc, char *argv[]) {
QCoreApplication a(argc, argv);
int usbCnt = -1;
bool usbChanged = true;
QString argd = "096e:0303"; // USB设备的venderID和productID,这个是可以预知的,当然不输入也可以
do {
int usbCnt_new = usbCount(argd);
if (usbCnt == usbCnt_new) {
usbChanged = false;
} else {
usbChanged = true;
}
usbCnt = usbCnt_new;
if (usbChanged) {
// yes!
QThread::sleep(2000); // 休眠2秒以避免频繁检测
}
} while (true);
return a.exec();
} 以下是对这几种方法的详细对比:
| 方法 | 优点 | 缺点 | 适用场景 |
lsusb | 简单易用,无需额外依赖 | 需要定期轮询,资源消耗较大 | 简单的USB设备监控 |
udev | 实时性强,适合系统级应用 | 需要了解udev库的使用 | 嵌入式系统、复杂应用 |
Netlink | 高效,适合高性能需求 | 实现复杂,需要处理内核消息 | 高性能需求的应用 |
Qt + QProcess | 跨平台,集成方便 | 依赖于Qt框架 | Qt应用程序中集成USB监控 |
Linux下检测USB设备的插拔有多种方法,可以根据具体需求选择合适的方案,无论是简单的脚本还是复杂的系统级应用,都有相应的解决方案。
以上就是关于“linux 检测usb插拔”的问题,朋友们可以点击主页了解更多内容,希望可以够帮助大家!
本文来源于互联网,如若侵权,请联系管理员删除,本文链接:https://www.9969.net/85857.html