【玩泰山派】4、制作ubuntu镜像-(4)Ubuntu rootfs补充WiFi驱动

发布于:2025-09-06 ⋅ 阅读:(13) ⋅ 点赞:(0)

前言

上篇文章制作的ubuntu的镜像虽然能正常启动,但是ip a发现没有wifi网卡(准确的说是名为wlan0的网络设备)。导致不能使用网络。可能是参考文档参考的不对了。这里也不纠结了,就排查原因,然后把这个东西补上。

原因排查

原来是缺少网卡驱动

因为直接使用sdk制作的buildroot的镜像是有wlan0网卡的,但是我制作的ubuntu镜像就没有,于是就对比一下哪里有差别。通过dmesg查看发现ubuntu镜像少一段相关的初始化日志。然后lsmod了一下,发现ubuntu镜像少一个内核模块bcmdhd。豆包搜索了一下bcmdhd内核模块,是无线网卡的驱动程序。那怪不得没有wlan0网卡,感情连网卡驱动都没装0.0。那后面就想着手动安装这个驱动。

给ubuntu rootfs补充网卡驱动

linux可以把内核模块编译进内核,也可以以内核模块(ko)的形式加载。既然buildroot都是以内核模块的形式价值的,那我也以这个形式。

添加bcmdhd.ko模块

我看了下执行完编译buildroot镜像后产生的内核模块。发现除了bcmdhd.ko外还有mwifiex_sdio.ko和mwifiex.ko,不知道有没有用,一股脑都给它加进去。

root@lckfb:/home/lckfb/kernel# find . -name *.ko
./drivers/net/wireless/rockchip_wlan/rkwifi/bcmdhd/bcmdhd.ko
./drivers/net/wireless/marvell/mwifiex/mwifiex_sdio.ko
./drivers/net/wireless/marvell/mwifiex/mwifiex.ko

安装 kmod 软件包

我打算以标准的在/lib/module/4.19.232/(当前使用的linux内核是4.19.232版本)目录下去安装内核模块,要使用depmod去生成相关文件,所以先给rootfs去安装kmod 软件包,支持内核模块的相关命令。(在arm机器中chroot之后去安装就行)

  • apt install kmod

创建/lib/modules/4.19.232目录

  • mkdier -p /lib/modules/4.19.232

拷贝modules.builtin和modules.order

使用depmod生成相关文件需要modules.builtin和modules.order,这两个文件在编译内核模块时会产生。可以在${sdk根目录}/kernel/下找到,这个目录其实也是sdk的放置linux内核源码的目录。

拷贝modules.builtin和modules.order文件到ubuntu rootfs的/lib/modules/4.19.232下

拷贝相关ko文件

主要是将下面的三个ko文件拷贝到ubuntu rootfs的对应的目录下

./drivers/net/wireless/rockchip_wlan/rkwifi/bcmdhd/bcmdhd.ko
./drivers/net/wireless/marvell/mwifiex/mwifiex_sdio.ko
./drivers/net/wireless/marvell/mwifiex/mwifiex.ko

/lib/modules/4.19.232下的如下路径

kernel/drivers/net/wireless/marvell/mwifiex/mwifiex.ko
kernel/drivers/net/wireless/marvell/mwifiex/mwifiex_sdio.ko
kernel/drivers/net/wireless/rockchip_wlan/rkwifi/bcmdhd/bcmdhd.ko

然后将新的ubuntu rootfs去生成新的镜像,烧录到sd卡,并启动

在板子启动后,执行depmod 4.19.232,会自动生成内核模块的相关文件。这些文件在使用modprobe这种命令时可能就需要了。

lckfb@192:/lib/modules/4.19.232$ ll
total 92
drwxr-xr-x 3 root root  4096 Mar  2  2023 ./
drwxr-xr-x 3 root root  4096 Apr  4 02:20 ../
drwxr-xr-x 3 root root  4096 Apr  4 02:35 kernel/
-rw-r--r-- 1 root root   625 Mar  2  2023 modules.alias
-rw-r--r-- 1 root root   781 Mar  2  2023 modules.alias.bin
-rw-r--r-- 1 root root 20672 Apr  4 02:33 modules.builtin
-rw-r--r-- 1 root root 22208 Mar  2  2023 modules.builtin.bin
-rw-r--r-- 1 root root   239 Mar  2  2023 modules.dep
-rw-r--r-- 1 root root   349 Mar  2  2023 modules.dep.bin
-rw-r--r-- 1 root root     0 Mar  2  2023 modules.devname
-rw-r--r-- 1 root root   181 Apr  4 02:32 modules.order
-rw-r--r-- 1 root root    55 Mar  2  2023 modules.softdep
-rw-r--r-- 1 root root  1226 Mar  2  2023 modules.symbols
-rw-r--r-- 1 root root  1432 Mar  2  2023 modules.symbols.bin

然后执行modprobe bcmdhd,发现加载内核模块成功。此时再ip a去查看,就发现已经有wlan0网卡了。0.0

但是发现网卡还是不能正常工作,使用nmcli device发现wlan0的状态不对。而且会有内核打印如下报错:

root@localhost:/lib/modules/4.19.232# [  972.881275] [dhd] dhd_conf_read_config : Ignore config file /vendor/etc/firmware/config.txt
[  972.881392] [dhd] dhd_conf_set_path_params : Final fw_path=/vendor/etc/firmware/fw_bcm43438a1.bin
[  972.881421] [dhd] dhd_conf_set_path_params : Final nv_path=/vendor/etc/firmware/nvram_ap6212a.txt
[  972.881444] [dhd] dhd_conf_set_path_params : Final clm_path=/vendor/etc/firmware/clm_bcm43438a1.blob
[  972.881466] [dhd] dhd_conf_set_path_params : Final conf_path=/vendor/etc/firmware/config.txt
[  972.885080] [dhd-wlan0] wl_android_wifi_on : Failed
[  972.885166] [dhd-wlan0] wl_android_wifi_off : in g_wifi_on=0, on_failure=1
[  972.885423] [dhd-wlan0] wl_android_wifi_off : out
[  972.936645] [dhd-wlan0] wl_android_wifi_on : in g_wifi_on=0
[  973.647729] [dhd] dhd_conf_read_config : Ignore config file /vendor/etc/firmware/config.txt
[  973.647850] [dhd] dhd_conf_set_path_params : Final fw_path=/vendor/etc/firmware/fw_bcm43438a1.bin
[  973.647882] [dhd] dhd_conf_set_path_params : Final nv_path=/vendor/etc/firmware/nvram_ap6212a.txt
[  973.647905] [dhd] dhd_conf_set_path_params : Final clm_path=/vendor/etc/firmware/clm_bcm43438a1.blob
[  973.647929] [dhd] dhd_conf_set_path_params : Final conf_path=/vendor/etc/firmware/config.txt
[  973.649972] [dhd-wlan0] wl_android_wifi_on : Failed
[  973.650081] [dhd-wlan0] wl_android_wifi_off : in g_wifi_on=0, on_failure=1
[  973.650292] [dhd-wlan0] wl_android_wifi_off : out
[  973.654492] [dhd-wlan0] wl_android_wifi_on : in g_wifi_on=0
[  974.352025] [dhd] dhd_conf_read_config : Ignore config file /vendor/etc/firmware/config.txt
[  974.352153] [dhd] dhd_conf_set_path_params : Final fw_path=/vendor/etc/firmware/fw_bcm43438a1.bin
[  974.352372] [dhd] dhd_conf_set_path_params : Final nv_path=/vendor/etc/firmware/nvram_ap6212a.txt
[  974.352452] [dhd] dhd_conf_set_path_params : Final clm_path=/vendor/etc/firmware/clm_bcm43438a1.blob
[  974.352501] [dhd] dhd_conf_set_path_params : Final conf_path=/vendor/etc/firmware/config.txt
[  974.354419] [dhd-wlan0] wl_android_wifi_on : Failed
[  974.354501] [dhd-wlan0] wl_android_wifi_off : in g_wifi_on=0, on_failure=1
[  974.354726] [dhd-wlan0] wl_android_wifi_off : out

从上面可以看到是缺少一些固件文件,ds搜索也是这么说的,那基本可以确认是缺少一下网卡驱动的固件文件。老办法,去buildroot镜像中去找(其实sdk目录下能搜索到,但是相对零散)。

添加相关网卡驱动固件文件

去buildroot的rootfs上查看,发现了相关固件,并且也看到了bcmdhd.ko的位置

# tree system
system
├── etc
│   └── firmware
│       ├── BCM43430A1.hcd
│       ├── fw_bcm43438a0.bin
│       ├── fw_bcm43438a1.bin
│       ├── fw_bcm43438a1_mfg.bin
│       ├── nvram_ap6212a.txt
│       └── nvram_ap6212.txt
└── lib
    └── modules
        └── bcmdhd.ko

一股脑将对应的firmware下面的所有文件都拷贝到对应的我的ubuntu rootfs的目录下。然后做一个软链,vendor -> system,因为看报错找固件是在/vendor/目录下。而且buildroot镜像也是这么做的。

然后重新制作新的镜像后,烧录到sd卡,然后启动开发板,然后执行modprobe bcmdhd后,一切都ok了.
可以使用

  • nmcli radio wifi on 开启wifi
  • nmcli device wifi list 列出wifi
  • nmcli device wifi connect “SSID_NAME” password “YOUR_PASSWORD” 连接wifi了。
    然后就可以愉快的连接网络玩耍了0.0

总结制作update.img的流程

我这个制作update.img的流程确实有点绕,简单总结下怕以后忘了0.0

1、登录x86开发机

2、登录ubuntu的容器(在容器中去启动qemu)

  • docker exec -it e6789e3c22bb /bin/bash

3、启动qemu的arm debian虚拟机

  • bash start_arm64_debian.sh,这里我直接写成脚本了。其实这个虚拟机可以开个sshd,这样就不用每次重新启动了。
root@e6789e3c22bb:~/data# cat start_arm64_debian.sh
qemu-system-aarch64 \
  -M virt -cpu cortex-a57 -smp 4 -m 4096 \
  -drive if=pflash,format=raw,file=efi.img,readonly=on \
  -drive if=virtio,file=debian-12-nocloud-arm64.qcow2 \
  -device virtio-net-pci,netdev=net0 \
  -netdev user,id=net0,hostfwd=tcp::2222-:22 \
  -nographic

执行完就已经进入到arm的debian虚拟机中了,登录root就可以,这个镜像默认无密码登录。

4、修改之前制作linuxroot.img(ubuntu18.04的rootfs)

修改的话,通常就是apt安装一些东西,拷贝一些文件之类的。

cd /root
# 挂载linuxroot.img到rootfs目录
mount linuxroot.img rootfs
# 执行脚本,这会chroot到rootfs
bash rootfs-mount.sh -m rootfs
# 执行apt命令安装想要的东西
...
# exit退出chroot的rootfs
exit
# 解挂linuxroot.img
umount rootfs

这样就修改好linuxroot.img了

5、拷贝linuxroot.img到x86开发机

bash scp_linuxroot.sh

  • 我直接写了个脚本,能拷贝到x86机器上的sdk的rockdev目录了。而且我之前是x86 机器上的ubuntu sdk编译容器是映射了x86机器的sdk目录的,所以就相当于直接拷贝到x86的ubuntu的编译容器中了。

6、在x86 机器上的ubuntu sdk编译容器中执行脚本生成sd卡镜像

cd rockdev
# 先做个rootfs.img到linuxroot.img的软链,因为脚本是使用rootfs.img 
ln -snf linuxroot.img rootfs.img
# 执行脚本生成updateimg
cd ..
./build.sh updateimg
# 会在./rockdev/目录下生成userdata.img,这个就是sd卡镜像了

sd卡镜像制作完成。可以使用瑞芯微的sd烧录工具去烧写了。

小结

1、我这个制作ubuntu镜像的流程确实感觉非常笨,而且很绕。如果网友有更好的方法,可以评论区交流下。
2、瑞芯微的sd烧录工具当前只有windows的版本,这使得我不得不在mac上安装一个windows的虚拟机去做烧录动作。我看了下,这个工具的烧录原理应该就是将sd卡重新分成若干的分区。然后依次装入下面的各个内容,比如:MiniLoaderAll.bin、uboot、内核、rootfs、recovery之类的。

lrwxrwxrwx  1 root root         18 Apr  6 06:22 boot.img -> ../kernel/boot.img
-rw-r--r--  1 root root  941568000 Apr  6 11:40 linuxroot.img
lrwxrwxrwx  1 root root         41 Apr  6 06:22 MiniLoaderAll.bin -> ../u-boot/rk356x_spl_loader_v1.13.112.bin
lrwxrwxrwx  1 root root         44 Apr  6 06:22 misc.img -> ../device/rockchip/rockimg/wipe_all-misc.img*
-rw-r--r--  1 root root   17457152 Apr  6 06:22 oem.img
lrwxrwxrwx  1 root root         53 Apr  6 06:22 parameter.txt -> ../device/rockchip/rk356x/parameter-buildroot-fit.txt
lrwxrwxrwx  1 root root         64 Apr  6 06:22 recovery.img -> ../buildroot/output/rockchip_rk356x_recovery/images/recovery.img
lrwxrwxrwx  1 root root         54 Apr  6 06:22 rootfs.ext4 -> ../buildroot/output/rockchip_rk3566/images/rootfs.ext2
lrwxrwxrwx  1 root root         13 Apr  6 11:40 rootfs.img -> linuxroot.img
lrwxrwxrwx  1 root root         19 Apr  6 06:22 uboot.img -> ../u-boot/uboot.img
-rw-r--r--  1 root root    4472832 Apr  6 06:22 userdata.img

update.img其实就是上面文件的打包。那其实咱们理论上可以在linux上自己用脚本完成这个过程,但是不知道有没有额外的什么格式校验之类的。这样就不用windows工具了。不知道有没有网友了解这个。。。

其他

1、其实我的内核模块的构建目录比较繁琐,直接像buildroot这样的结构应该就可以,但是这样应该处理不了依赖啥的,而且我以后想要单独再编译自己的内核模块啥的做练习,我那个标准目录应该比较好0.0

2、根文件系统可能没有占满对应的分区,使用resize2fs /dev/mmcblk1p6去扩展一下文件系统,占满整个分区。


网站公告

今日签到

点亮在社区的每一天
去签到