通过Netlink检测USB设备的插拔

    在Android的Vold里面可以了解到,其检测USB的插拔是通过Netlink机制来实现的,那我们也来尝试下如何在Linux下写个程序检测USB设备的插拔,下面我们将使用Netlink的NETLINK_KOBJECT_UEVENT类型套接字与Kernel进行通信,然后使用setsocketopt()来利用该套接字,再使用select()并发检测相应的套接写是否可操作,具体的代码实现 如下:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <fcntl.h>
#include <sys/socket.h>
#include <linux/netlink.h>
#define UEVENT_BUFFER_SIZE 2048
int main(void)
{
    struct sockaddr_nl client;
    struct timeval tv;
    int fd, rcvlen, ret;
    fd_set fds;
    int buffersize = 1024;
    fd = socket(AF_NETLINK, SOCK_RAW, NETLINK_KOBJECT_UEVENT);
    memset(&client, 0, sizeof(client));
    client.nl_family = AF_NETLINK;
    client.nl_pid = getpid();
    client.nl_groups = 1; /* receive broadcast message*/
    setsockopt(fd, SOL_SOCKET, SO_RCVBUF, &buffersize, sizeof(buffersize));
    bind(fd, (struct sockaddr*)&client, sizeof(client));
    while (1) {
        char buf[UEVENT_BUFFER_SIZE] = { 0 };
        FD_ZERO(&fds);
        FD_SET(fd, &fds);
        tv.tv_sec = 0;
        tv.tv_usec = 100 * 1000;
        ret = select(fd + 1, &fds, NULL, NULL, &tv);
        if(ret < 0)
            continue;
        if(!(ret > 0 && FD_ISSET(fd, &fds)))
            continue;
        /* receive data */
        rcvlen = recv(fd, &buf, sizeof(buf), 0);
        if (rcvlen > 0) {
            printf("%s\n", buf);
            /*You can do something here to make the program more perfect!!!*/
        }
    }
    close(fd);
    return 0;
}
    然后将其交叉编译下并放到我们的Mstar板卡上,插拔U盘和USB鼠标时有如下提示:
add@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.2
add@/devices/platform/Mstar[  120.529879] scsi0 : usb-storage 4-1.2:1.0
-ehci-2.1/usb4/4-1/4-1.2/4-1.2:1.0
add@/devices[  120.537275] isa bounce pool size: 16 pages
/platform/Mstar-[  120.543612] scsi 0:0:0:0: Direct-Access     SanDisk  Cruzer Blade     2.01 PQ: 0 ANSI: 5
ehci-2.1/usb4/4-1/4-1.2/4-1.2:1.0/host0
add@/de[  120.556037] sd 0:0:0:0: [sda] 7821312 512-byte logical blocks: (4.00 GB/3.72 GiB)
vices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.2/4-1[  120.567115] sd 0:0:0:0: [sda] Write Protect is off
.2:1.0/host0/scs[  120.573404] sd 0:0:0:0: [sda] Write cache: disabled, read cache: enabled, doesn't support DPO or FUA
i_host/host0
add@/devices/platform/Mstar-ehci-2[  120.587278] emmc_partition()
.1/usb4/4-1/4-1.2/usb_device/usbdev4.4
add@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.2/4-1.[  120.598422] 0x0
2:1.0/host0/targ[  120.600753]  sda: sda1
et0:0:0
add@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.2/4-1.2:1.0/host0/target0:0:0/0:0:0:0
add@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.2/4-1.2:1.0/host0/target0:0:0/0:0:0:0/scsi_disk/0:0:0:0
add@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.2/4-1.2:1.0/host0/target0:0:0/0:0:0:0/scsi_device[  120.629463] sd 0:0:0:0: [sda] Attached SCSI removable disk
/0:0:0:0
add@/devices/virtual/bdi/8:0
add@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.2/4-1.2:1.0/host0/target0:0:0/0:0:0:0/block/sda
add@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.2/4-1.2:1.0/host0/target0:0:0/0:0:0:0/block/sda/sda1
add@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.4
add@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-[  163.282004] input: PIXART USB OPTICAL MOUSE as /devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.4/4-1.4:1.0/input/input10
1.4/4-1.4:1.0
add@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1[  163.297335] generic-usb 0003:093A:2510.0003: input,hidraw1: USB HID v1.11 Mouse [PIXART USB OPTICAL MOUSE] on usb-mstar-1.4/input0
.4/4-1.4:1.0/0003:093A:2510.0003
add@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.4/4-1.4:1.0/input/input10
add@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.4/4-1.4:1.0/input/input10/mouse2
add@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.4/4-1.4:1.0/input/input10/event4
add@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.4/4-1.4:1.0/0003:093A:2510.0003/hidraw/hidraw1
add@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.4/usb_device/usbdev4.5
remove@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.2/4-1.2:1.0/host0/target0:0:0/0:0:0:0/block/sda/sda1
remove@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.2/4-1.2:1.0/host0/target0:0:0/0:0:0:0/scsi_disk/0:0:0:0
remove@/devices/virtual/bdi/8:0
remove@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.2/4-1.2:1.0/host0/target0:0:0/0:0:0:0/block/sda
remove@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.2/4-1.2:1.0/host0/target0:0:0/0:0:0:0
remove@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.2/4-1.2:1.0/host0/target0:0:0
remove@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.2/4-1.2:1.0/host0/scsi_host/host0
remove@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.2/4-1.2:1.0/host0
remove@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.2/4-1.2:1.0
remove@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.2/usb_device/usbdev4.4
remove@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.2
remove@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.4/4-1.4:1.0/input/input4/mouse2
remove@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.4/4-1.4:1.0/input/input4/event4
remove@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.4/4-1.4:1.0/input/input4
remove@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.4/4-1.4:1.0/0003:093A:2510.0002/hidraw/hidraw1
remove@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.4/4-1.4:1.0/0003:093A:2510.0002
remove@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.4/4-1.4:1.0
remove@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.4/usb_device/usbdev4.3
remove@/devices/platform/Mstar-ehci-2.1/usb4/4-1/4-1.4
    从上面的打印信息,我们看到插入时会以add@开头,而拔掉时会以remove@开头,通过判断这样的头部信息可以判断是不是有设备进行插拔,进而再处理后面的内容来判断具体是哪个设备。

评论

此博客中的热门博文

I/O映射之I/O端口

通过Netlink检测网线插拔

使用seq_file