拿到了鲁班猫2开发板裸板之后,发现并没有板载WIFI和BT模块。虽然有两个以太网接口,但是无线网络连接还是感觉更好一些。
恰好手头上有一个大约10年前的买的360 USB随身Wifi。
插到开发板一试,直接可用。
1.节外生枝
但故事并没有这样结束。考虑到这个360随身WIFI年事已高,且USB连接器上甚至出现了锈迹,我决定买个新的USB WIFI。
USB WIFI这种在我印象里的小众电子产品还是有不少选择的,价格也不贵,不到20元买了Tenda的AX300系列。
连到鲁班猫2,一试,没有出现无线网络设备,只有一个大容量存储设备。
查了查资料,才知道这个大容量存储设备设备是为了存放Windows系统使用的驱动安装包的,这样就不用在包装盒里放一个装驱动的光盘了,真正实现了免(光)驱!
*根据网友的提示,在Linux系统应该将这个大容量存储设备弹出(Eject),才能进入一个新的世界。
2.安装驱动
又查了一些资料之后,我终于意识到可能是需要在Linux系统装驱动了。这不能跟我的360随身WIFI比,它出现得早,系统大概率是已经包含了他的驱动。
去Tenda的官网看了一下,还好,确实是有ARM版本的驱动。
下载解压之后,dpkg -i 安装deb文件,Fail!
Eject没找到,使用apt-get install即可。fixdep exec format错误,当时确实判断失误了。
cat@lubancat:~/Downloads/Tenda$ sudo dpkg -i AX300-WiFi-Adapter-Linux-Driver-arm.deb
正在选中未选择的软件包 ax300-wifi-adapter-linux-driver。
(正在读取数据库 ... 系统当前共安装有 139452 个文件和目录。)
准备解压 AX300-WiFi-Adapter-Linux-Driver-arm.deb ...
Install aic8800 wifi driver!!!!!
正在解压 ax300-wifi-adapter-linux-driver (1.0.2) ...
正在设置 ax300-wifi-adapter-linux-driver (1.0.2) ...
udev done
device exist
/var/lib/dpkg/info/ax300-wifi-adapter-linux-driver.postinst:行10: eject:未找到命令
cp fw done
make -C /lib/modules/4.19.232/build M=/AIC8800/drivers/aic8800 ARCH=arm64 CROSS_COMPILE= modules
make[1]: 进入目录“/usr/src/linux-headers-4.19.232”
CC [M] /AIC8800/drivers/aic8800/aic8800_fdrv/rwnx_msg_tx.o
/bin/sh: 1: scripts/basic/fixdep: Exec format error
make[3]: *** [scripts/Makefile.build:334:/AIC8800/drivers/aic8800/aic8800_fdrv/rwnx_msg_tx.o] 错误 2
make[3]: *** 正在删除文件“/AIC8800/drivers/aic8800/aic8800_fdrv/rwnx_msg_tx.o”
make[2]: *** [scripts/Makefile.build:637:/AIC8800/drivers/aic8800/aic8800_fdrv] 错误 2
make[1]: *** [Makefile:1676:_module_/AIC8800/drivers/aic8800] 错误 2
make[1]: 离开目录“/usr/src/linux-headers-4.19.232”
make: *** [Makefile:55:modules] 错误 2
make failed, install aic8800 wifi drvier failed
dpkg: 处理软件包 ax300-wifi-adapter-linux-driver (--install)时出错:
已安装 ax300-wifi-adapter-linux-driver 软件包 post-installation 脚本 子进程返回错误状态 1
在处理时有错误发生:
ax300-wifi-adapter-linux-driver
3.编译驱动
当时,我选择了认为这个是错误是由于deb包与我的处理器、系统等不匹配导致的,应该自行编译一下驱动源码。在驱动安装包里也有驱动的源码,可以自由编译。
3.1开始编译驱动
如果直接make的话会出现一些错误:
cat@lubancat:~/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800$ sudo make
make -C /lib/modules/4.19.232/build M=/home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800 ARCH=arm CROSS_COMPILE= modules
make[1]: 进入目录“/usr/src/linux-headers-4.19.232”
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_msg_tx.o
gcc: error: unrecognized argument in option '-mabi=apcs-gnu'
gcc: note: valid arguments to '-mabi=' are: ilp32 lp64
gcc: error: unrecognized command line option '-mapcs'; did you mean '--specs'?
gcc: error: unrecognized command line option '-mno-sched-prolog'; did you mean '-Wno-sign-promo'?
gcc: error: unrecognized command line option '-msoft-float'
make[3]: *** [scripts/Makefile.build:334:/home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_msg_tx.o] 错误 1
make[2]: *** [scripts/Makefile.build:637:/home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv] 错误 2
make[1]: *** [Makefile:1676:_module_/home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800] 错误 2
make[1]: 离开目录“/usr/src/linux-headers-4.19.232”
make: *** [Makefile:55:modules] 错误 2
指定目标ARCH=arm64,终于可以编译了。但是同样出现了那个fixdep相关的问题。
cat@lubancat:~/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800$ sudo make ARCH=arm64
make -C /lib/modules/4.19.232/build M=/home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800 ARCH=arm64 CROSS_COMPILE= modules
make[1]: 进入目录“/usr/src/linux-headers-4.19.232”
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_msg_tx.o
/bin/sh: 1: scripts/basic/fixdep: Exec format error
make[3]: *** [scripts/Makefile.build:334:/home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_msg_tx.o] 错误 2
make[3]: *** 正在删除文件“/home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_msg_tx.o”
make[2]: *** [scripts/Makefile.build:637:/home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv] 错误 2
make[1]: *** [Makefile:1676:_module_/home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800] 错误 2
make[1]: 离开目录“/usr/src/linux-headers-4.19.232”
make: *** [Makefile:55:modules] 错误 2
3.2Fix Fixdep
查找了一些资料,认定就是文件格式不正确,使用file指令一试,确实是X86格式的。
cat@lubancat:/usr/src/linux-headers-4.19.232/scripts/basic$ file fixdep
fixdep: ELF 64-bit LSB shared object, x86-64, version 1 (SYSV), dynamically linked, interpreter /lib64/ld-linux-x86-64.so.2, BuildID[sha1]=9ee189e914fcc03fdc06192ca239fad425348351, for GNU/Linux 3.2.0, not stripped
使用make scripts重新编译这个,
cat@lubancat:/usr/src/linux-headers-4.19.232$ sudo make scripts
HOSTCC scripts/basic/fixdep
HOSTCC scripts/kconfig/conf.o
HOSTCC scripts/kconfig/zconf.tab.o
HOSTLD scripts/kconfig/conf
scripts/kconfig/conf --syncconfig Kconfig
再用file查看一下,格式就对了。
cat@lubancat:/usr/src/linux-headers-4.19.232/scripts/basic$ file fixdep
fixdep: ELF 64-bit LSB pie executable, ARM aarch64, version 1 (SYSV), dynamically linked, interpreter /lib/ld-linux-aarch64.so.1, for GNU/Linux 3.7.0, BuildID[sha1]=5b3755bf35f2141b1e9262563eb92120c3945799, not stripped
3.3二次编译驱动
没有了Fixdep这个问题,驱动编译就顺利多了。make、make install都OK。
cat@lubancat:~/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800$ sudo make ARCH=arm64
make -C /lib/modules/4.19.232/build M=/home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800 ARCH=arm64 CROSS_COMPILE= modules
make[1]: 进入目录“/usr/src/linux-headers-4.19.232”
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_msg_tx.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_msg_rx.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_utils.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_cmds.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_irqs.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_cfgfile.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_strs.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_rx.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_tx.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_txq.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_main.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_mod_params.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_mesh.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_platform.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_pci.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_dini.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_v7.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/ipc_host.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_tdls.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/regdb.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/md5.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/aicwf_compat_8800dc.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_radar.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_debugfs.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_fw_trace.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/rwnx_testmode.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/usb_host.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/aicwf_txrxif.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/aicwf_usb.o
LD [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/aic8800_fdrv.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic_load_fw/aic_bluetooth_main.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic_load_fw/aicbluetooth.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic_load_fw/aicwf_usb.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic_load_fw/aic_txrxif.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic_load_fw/aicbluetooth_cmds.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic_load_fw/md5.o
CC [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic_load_fw/aicwf_txq_prealloc.o
LD [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic_load_fw/aic_load_fw.o
Building modules, stage 2.
MODPOST 2 modules
CC /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/aic8800_fdrv.mod.o
LD [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic8800_fdrv/aic8800_fdrv.ko
CC /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic_load_fw/aic_load_fw.mod.o
LD [M] /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic_load_fw/aic_load_fw.ko
cat@lubancat:~/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800$ sudo make install
mkdir -p /lib/modules/4.19.232/kernel/drivers/net/wireless/aic8800
install -p -m 644 aic_load_fw/aic_load_fw.ko /lib/modules/4.19.232/kernel/drivers/net/wireless/aic8800/
install -p -m 644 aic8800_fdrv/aic8800_fdrv.ko /lib/modules/4.19.232/kernel/drivers/net/wireless/aic8800/
/sbin/depmod -a 4.19.232
然而,插入Tenda USB WIFI,依旧没有什么反应。
4.Dmesg
我已经记不清如何想到使用dmesg查看到系统log了。从log上可以看到,USB Wifi在执行过程中出现了错误。
[ 1241.117067] AICWFDBG(LOGINFO) rwnx_cfg80211_init sizeof(struct rwnx_hw):14560
[ 1241.117418] ------------[ cut here ]------------
[ 1241.117439] kernel BUG at /home/cat/Downloads/linux_driver_sourcecode/aic8800_linux_drvier/drivers/aic8800/aic_load_fw/aicwf_txq_prealloc.c:16!
[ 1241.117453] Internal error: Oops - BUG: 0 [#1] SMP
[ 1241.129925] Modules linked in: aic8800_fdrv(O+) aic_load_fw(O) mt7601u
[ 1241.129943] Process systemd-udevd (pid: 5066, stack limit = 0x0000000008ee8f41)
[ 1241.129951] CPU: 1 PID: 5066 Comm: systemd-udevd Tainted: G O 4.19.232 #18
[ 1241.129953] Hardware name: EmbedFire LubanCat-2 (DT)
[ 1241.129956] pstate: 20400009 (nzCv daif +PAN -UAO)
[ 1241.129977] pc : aicwf_prealloc_txq_alloc+0x28/0x130 [aic_load_fw]
[ 1241.130041] lr : rwnx_cfg80211_init+0x24c/0x8dc [aic8800_fdrv]
查看USB Wifi驱动源码猜测,传入的参数超出了代码中设定的最大值。
struct prealloc_txq prealloc_txq;
#define MAX_TXQ_SIZE 30 * 1024
void *aicwf_prealloc_txq_alloc(size_t size)
{
BUG_ON(size > MAX_TXQ_SIZE);
//check prealloc_txq.size
if((int)prealloc_txq.size != (int)size)
{
AICWFDBG(LOGINFO, "%s size is diff will to be kzalloc \r\n", __func__);
这个设定应该是个缓冲器的大小,那就先随便改大一些,也加了log打印看一下到此出进来的参数是多少。
struct prealloc_txq prealloc_txq;
#define MAX_TXQ_SIZE 60 * 1024
void *aicwf_prealloc_txq_alloc(size_t size)
{
AICWFDBG(LOGINFO, "aicwf_prealloc_txq_alloc size:%d \r\n", (int)size);
BUG_ON(size > MAX_TXQ_SIZE);
//check prealloc_txq.size
if((int)prealloc_txq.size != (int)size)
{
AICWFDBG(LOGINFO, "%s size is diff will to be kzalloc \r\n", __func__);
5.终于好了
重新编译驱动并安装,(可能需要重启一下)再插入Tenda USB Wifi,出现了。出现了新的无线连接设备。使用ifconfig可以看到wlan0这个无线网络设备。
使用dmesg查看log,可以看出之前Bug的地方已经输出了正常的log,之前导致Bug的那个参数实际上是35640,确实超过了设定值。
[ 8.540982] AICWFDBG(LOGINFO) aicwf_prealloc_txq_alloc size:35640
[ 8.556262] AICWFDBG(LOGINFO) aicwf_prealloc_txq_alloc size is diff will to be kzalloc
[ 8.556369] AICWFDBG(LOGINFO) aicwf_prealloc_txq_alloc txq kzalloc successful
6.再出发
其实在想到用dmesg查看log之前,我已经准备放弃Tenda了,我转身买了MERCURY、COMFAST、EDUP、UGREEN的各一款USB WIFI。在Tenda WIFI变得可以使用的那个周六的早上,他们几个已经快要被放进我家附近的菜鸟驿站了。
下一篇Blog,我将讲一下他们几个的故事。
备注:
1、360随身WIFI图片来自网络,侵删。
2、相关参考信息的连接:W311MIv6.0 Linux系统驱动- ARM架构 (Ubuntu/UOS/kylin OS)_腾达(Tenda)官方网站