Linux USB热插拔

2019-04-14 18:25发布

Linux USB的挂载分为两种,一种是开机自动挂载,指的是设备上电之前就把U盘插上然后再上电。这种情况网上有很多讲解,也没有太大的技术难题。本文描述的是设备已经上电,然后再插拔U盘的情况。
    本文以openWrt为样例来描述USB热插拔的问题,也是我曾经遇到过的问题。
    1. Linux 内核要支持USB自动挂载(make menuconfig)
    1)添加USB相关
  1. Kernel modules —> USB Support —> <*> kmod-usb-core.  ##默认已经选了  
  2. Kernel modules —> USB Support —> <*> kmod-usb-ohci.  ##默认已选 old usb1.0  
  3. Kernel modules —> USB Support —> <*> kmod-usb-uhci.  ## usb1.1  
  4. Kernel modules —> USB Support —> <*> kmod-usb-storage.  
  5. Kernel modules —> USB Support —> <*> kmod-usb-storage-extras.  
  6. Kernel modules —> USB Support —> <*> kmod-usb2.  ##默认已经选了 usb2.0  
    2)添加SCSI 支持

  1. Kernel modules —> Block Devices —> <*>kmod-scsi-core  ##默认已经选了 usb3.0
    3)添加USB挂载

  1. Base system —> <*>block-mount 
    4)添加文件系统支持
  1. Kernel modules —> Filesystems —> <*> kmod-fs-ext4 (移动硬盘EXT4格式选择)  
  2. Kernel modules —> Filesystems —> <*> kmod-fs-vfat(FAT16 / FAT32 格式 选择)  
  3. Kernel modules —> Filesystems —> <*> kmod-fs-ntfs (NTFS 格式 选择) 
         2、添加自动挂载脚本/etc/hotplug.d/block/10-mount
                注意,文件名“10-mount” 前面的数字代表了该脚本被调用的顺序。比如/etc/hotplug.d/block/ 路径下还有其他脚本,如20-xxx,30-xxxx,则脚本被调用的顺序为10-mount  ->   20-xxx  -> 30-xxxx,该执行顺序有Linux内核决定。

                在10-mount 中增加如下代码:
        #!/bin/sh        case "$ACTION" in                add)                    for device in $(ls /dev/ | grep 'sd[a-z][1-9]')                        do                                if  [ `which blkid` ]; then                                             isntfs=`blkid /dev/$device | grep ntfs`                                             uuid =`blkid /dev/$device | awk '{print $2}' | cut -d " -f 2`   #获取U盘的UUID                                             isvfat=`blkid /dev/$device | grep fat`                                             isfuse=`lsmod | grep fuse`                                             isntfs3g=`which ntfs-3g`                                else                                             isntfs=""                                             isvfat=""                                fi                                # mount with ntfs-3g if possible, else with default mount                                if [ "$isntfs" -a "$isntfs3g" ]; then                                             #mkdir -p /mnt/$device                                             ntfs-3g -o nls=utf8 /dev/$device /mnt/                                             if [ "$?" -ne 0 ];then                                                ntfs-3g -o nls=utf8 /dev/$device /mnt/                                             fi                                             mkdir /mnt/ebook && touch /mnt/ebook/demo.pdf                                             mkdir /mnt/movie && touch /mnt/movie/demo.mp4                                             mkdir /mnt/music && touch /mnt/music/demo.mp3                                             mkdir /mnt/picture && touch /mnt/picture/demo.jpg                                             mkdir /mnt/slider && touch /mnt/slider/demo.jpg                                             if [ ! -f "/mnt/tvlist.json" ];then                                                    cp /etc/tvlist.json.in /mnt/tvlist.json                                             fi                                elif [ "$isvfat" ]; then                                             #mkdir -p /mnt/$device                                             #mount -t vfat -o iocharset=utf8,rw,sync,umask=0000,dmask /dev/$device /mnt/                                             mount -t vfat -o iocharset=utf8,rw,sync,umask=0000 -U $uuid /mnt/                                             #mount -o iocharset=utf8,rw /dev/$i /mnt                                             if [ "$?" -ne 0 ];then                                                #mount -o rw /dev/$i /mnt                                                mount -t vfat -o iocharset=utf8,rw,sync,umask=0000 -U $uuid /mnt/                                             fi                                             mkdir /mnt/ebook && touch /mnt/ebook/demo.mdf                                             mkdir /mnt/movie && touch /mnt/movie/demo.mp4                                             mkdir /mnt/music && touch /mnt/music/demo.mp3                                             mkdir /mnt/picture && touch /mnt/picture/demo.jpg                                             mkdir /mnt/slider && touch /mnt/slider/demo.jpg                                             if [ ! -f "/mnt/tvlist.json" ];then                                                    cp /etc/tvlist.json.in /mnt/tvlist.json                                             fi                                else                                             #mkdir -p /mnt/$device                                             mount /dev/$device /mnt/                                             mkdir /mnt/ebook && touch /mnt/ebook/demo.mdf                                             mkdir /mnt/movie && touch /mnt/movie/demo.mp4                                             mkdir /mnt/music && touch /mnt/music/demo.mp3                                             mkdir /mnt/picture && touch /mnt/picture/demo.jpg                                             mkdir /mnt/slider && touch /mnt/slider/demo.jpg                                             if [ ! -f "/mnt/tvlist.json" ];then                                                    cp /etc/tvlist.json.in /mnt/tvlist.json                                             fi                                fi                        done                    ;;                remove)                    MOUNT=`mount | grep -o '/mnt`                    for device in $MOUNT                        do                                umount $device                        done                    ;;        esac