一、介绍usb_modeswitch功能
usb_modeswitch是对USB设备的工作模式进行转换,usb工作模式:usb存储模式,usb serial模式。现在3G,无线网卡模块使用USB接口,他们的工作模式是usb serial模式。
二、下载
1、下载usb-modeswitch-2.2.0.tar.bz2和usb-modeswitch-data-20140529.tar.bz2
http://www.draisberghof.de/usb_modeswitch/#download
2、下载 libusb-1.0.19.tar.bz2
http://sourceforge.net/projects/libusb/files/libusb-1.0/ 如果网速太慢可以使用下面下载链接
csdn下载链接:http://download.csdn.net/detail/lin_jianbin/8339561
3、下载 libusb-compat-0.1.5.tar.bz2(可不需要安装)
libusb分为0.1和1.0两版本,而1.0版本与0.1有较大的不同,并不向下兼容,必须依赖libusb-compat
因本人安装这个没有兼容性问题所以没安装。
http://sourceforge.net/projects/libusb/files/libusb-compat-0.1/
注:usb-modeswitch-2.2.0.tar.bz2这个版本一定要使用libusb-1.x版本。否则版本不兼容。
三、安装
1、交叉编译libusb-1.0.19.tar.bz2
解压:tar -jxvf libusb-1.0.19.tar.bz2
进入目录:cd libusb-1.0.19
配置:./configure -build=i686-linux --host=arm-linux --prefix=/opt/ProgramFiles/libusb --disable-shared --enable-static
--host=arm-linux:配置交叉编译器
--prefix=/opt/ProgramFiles/libusb :安装生成的路径
-enable-static:生成静态库,注:这样libusb-1.0.a就不需要复制到开发板上因为是静态库
出现错误:configure: error: "udev support requested but libudev not installed"这个错误
原因:开发环境没有libudev。
解决:
方法1、如果是Ubuntu可用: apt-get install libudev-dev安装,若不想安装或安装失败可用方法2
方法2、在./configure 最后加入 --disable-udev
编译:make
编译生成:make install
成功,可以在/opt/ProgramFiles/libusb目录下生成 include和lib文件夹
2、交叉编译usb-modeswitch-2.2.0.tar.bz2
解压:tar -jxvf usb-modeswitch-2.2.0.tar.bz2
修改Makefile文件
CC =arm-linux-gcc ##指定编译器 交叉编译
STRIP =arm-linux-strip
CFLAGS += -Wall -I/opt/ProgramFiles/libusb/include/libusb-1.0
LIBS = -lpthread /opt/ProgramFiles/libusb/lib/libusb-1.0.a
-I/opt/ProgramFiles/libusb/include/libusb-1.0 这个为上面安装libusb的头文件路径
/opt/ProgramFiles/libusb/lib/libusb-1.0.a 这个为上面安装libusb的库路径
-lpthread 线程库
编译:make
成功,在目录下会生成 usb_modeswitch 可执行文件
3、解压usb-modeswitch-data-20140529.tar.bz2得到配置文件
解压: tar -jxvf usb-modeswitch-data-20140529.tar.bz2
文件如下:
40-usb_modeswitch.rules : udev规则文件
usb_modeswitch.d: 文件夹中包含大部分厂家的配置信息
修改usb_modeswitch.d文件夹下文件19d2:2000(因为本人使用的模块厂家信息是这个文件,这个要根据自己的实际模块而定)
########################################################
# ZTE devices
DefaultVendor= 0x19d2
DefaultProduct= 0x2000(usb设备ID)
TargetVendor= 0x19d2
TargetProductList="0001,0002,0015,0016,0017,0031,0037,0052,0055,0063,0064,0108,0128"(usb设备转为serial后的ID)
MessageContent="5553424312345678000000000000061e000000000000000000000000000000"
MessageContent2="5553424312345679000000000000061b000000020000000000000000000000"
MessageContent3="55534243123456702000000080000c85010101180101010101000000000000"
NeedResponse=1
CheckSuccess=5(检查次数)
四、移植到开发板
1、模块为内置模块,不考虑兼容性和热插拔问题
将生成的可执行文件拷贝到开发板/usr/sbin/目录下,将usb_modeswitch.d文件夹下的19d2:2000配置文件拷贝到开发板/etc/usb_modeswitch.d目录下(可自己选择路径)
到开发板上执行
# usb_modeswitch -W -c 19d2:2000
-W 显示执行过程及各参数设备情况
-c 配置文件
如何判断usb转串口成功?
在没有执行usb_modeswitch前使用命令lsusb
# lsusb
Bus 001 Device 002: ID 19d2:2000
执行usb_modeswitch后使用命令lsusb
# lsusb
Bus 001 Device 003: ID 19d2:0117
可看到ID号已经变化,如果没有变化说明没有成功
usb转串口没有成功的原因
19d2:2000 配置文件不正确。
方法:可以参考桌面Linux系统的配置文件,在/etc/usb_modeswitch.d目录下。
usb转串口成功但是在/dev/目录下看不到设备ttyUSB0 ttyUSB1 ttyUSB2
解决:卸载掉之前加载的usb转串口驱动(如果已经加载)
# lsmod
Module Size Used by
option 14456 0
usb_wwan 7838 1 option
usbserial 25343 2 option,usb_wwan
#rmmod usbserial.ko
#rmmod usb_wwan.ko
#rmmod option.ko
重新加载驱动模块
#insmod usbserial.ko
#insmod usb_wwan.ko
#insmod option.ko
重新加载驱动模块后还是看不到设备ttyUSB0 ttyUSB1 ttyUSB2
原因:option.c中没有增加厂家ID
解决:修改option.c文件
可参考本博客文章:http://blog.csdn.net/lin_jianbin/article/details/42520845
验证是否option.c中没有增加厂家ID方法
#insmod usbserial.ko vendor=0x19d2 product=0x2000
加载usbserial.ko驱动时指定 厂家号和设备号
#insmod usb_wwan.ko
#insmod option.ko
这两句可不执行。
正确加载输出如下:
usbcore: registered new interface driver usbserial
USB Serial support registered for generic
usbcore: registered new interface driver usbserial_generic
usbserial: USB Serial Driver core
USB Serial support registered for GSM modem (1-port)
option 1-2:1.0: GSM modem (1-port) converter detected
usb 1-2: GSM modem (1-port) converter now attached to ttyUSB0
option 1-2:1.1: GSM modem (1-port) converter detected
usb 1-2: GSM modem (1-port) converter now attached to ttyUSB1
option 1-2:1.2: GSM modem (1-port) converter detected
usb 1-2: GSM modem (1-port) converter now attached to ttyUSB2
usbcore: registered new interface driver option
option: v0.7.2:USB Driver for GSM modems
恭喜成功
2、模块为外置模块,需要考虑兼容性和热插拔问题
将生成的可执行文件拷贝到开发板/usr/sbin/目录下,将usb_modeswitch.d文件夹拷贝到开发板/etc目录下,将40-usb_modeswitch.rules文件拷贝到开发板/etc/udev/rules.d目录下.
40-usb_modeswitch.rules 是udev规则文件,相关知识可查找 udev规则
如下是文件中的一小部分
# Vodafone (ZTE) K3806-Z
ATTRS{idVendor}=="19d2", ATTRS{idProduct}=="1013", RUN+="usb_modeswitch '%b/%k'"
# ZTE devices
ATTRS{idVendor}=="19d2", ATTRS{idProduct}=="2000", RUN+="usb_modeswitch '%b/%k'"
支持热插拔的步骤:
当有设备插入时,udev就会被内核触发,寻找与设备配对的配置。
udev会到/etc/udev/rules.d/目录下 遍历所有的udev规则文件。不会因为找到配对的就停止而是全部遍历完。
我们拷贝到/etc/udev/rules.d目录下的40-usb_modeswitch.rules 文件也会被遍历到
当插入的厂家ID号为19d2 设备号为 2000 时就是调用RUN+="usb_modeswitch '%b/%k'"
RUN+= 可以加入自己的可执行程序或者脚本等等。因而在热插拔时我们可以实现我们自己想做的事情。
调用 usb_modeswitch 这里需要注意的是usb_modeswitch不是可执行文件而是一个脚本。
本人起初以为是可执行程序,而不明白其后更得参数。之后得知是脚本焕然大悟。
这样就实现了usb_modeswitch自动启动功能。当有3G设备插入时,如果usb_modeswitch.d目录下有找到匹配的设备ID配置,就会启动usb_modeswitch。实现自动将usb转为usb serial模式。