半年前我第一次在RK3588开发板上接O9201SB这个WiFi模组时,以为这活和当年在树莓派上插USB网卡一样简单,插上就能用。结果从模组焊到板子上到wlan0真正出现,我整整折腾了三个晚上,中途一度怀疑是模组坏了还是自己改错了设备树。后来冷静下来,把SDIO配置的所有环节拆开梳理了一遍,才意识到RK3588上接SDIO WiFi本质上要同时摆平三件事:硬件电气、设备树、内核驱动/固件,哪一环掉链子,现象都长得差不多,排查起来特别考验耐心。
这篇文章就把我这次O9201SB接入的完整过程写出来,包括选型原因、硬件接入细节、DTS里那些一旦写错就抓瞎的属性、内核驱动和固件的部署方式,以及最后从识别失败到吞吐量优化的排查链路。不管你是刚拿到RK3588开发板想扩展WiFi能力,还是在自己的底板设计里要加一个SDIO接口的无线模组,这篇文章应该都能帮你少走好几天的弯路。
1. 为什么RK3588的SDIO WiFi接入会让人头疼
1.1 一块RK3588上塞着好几个"长得一样"的MMC控制器
很多第一次在RK3588上接SDIO设备的人,第一反应是"找个SDIO接口接上不就行了"。但翻开原理图或者SDK里的设备树就会发现,RK3588的MMC相关控制器多到让你怀疑人生:SDMMC管TF卡、SDIO管WiFi/BT这种组合模组、SDHCI管eMMC,还有一个SDMMC/SDIO复用节点。节点名字也经常是&sdmmc、&sdio、&sdhci混着来,不同厂商的SDK里甚至管&sdio叫&mmc1或者&sdhci0,新手很容易一上来就把WiFi接到了TF卡的控制器上,或者反过来。
这个"控制器选错"的坑非常隐蔽。因为我最初犯的错误就是抄了一份网上RK3399的SDIO配置,直接改到RK3588上,引脚全对不上,上电后总线扫描一片空白。后来我把SDK里原厂的rk3588-evb.dts翻出来,才确认RK3588的SDIO控制器在设备树里对应的节点名,以及它默认挂在哪个电源域、哪组引脚下面。这件事给我最大的教训是:任何DTS配置,第一步永远是翻自己板卡的原理图和原厂dts,而不是凭经验套用其他芯片的方案。
1.2 SDIO WiFi和USB WiFi的取舍逻辑
做产品的人经常问我:为什么不用USB WiFi?USB网卡确实是即插即用,在Linux下几乎不用配置,但代价也很明显。USB WiFi的吞吐量上限受限于USB总线调度,高负载下延迟不稳定,而且很多USB WiFi方案用的芯片在Linux驱动上并不比SDIO方案省心。SDIO WiFi的优势在于走的是MMC总线那种"准专用通道",带宽、延迟、低功耗表现都更好,尤其是WiFi/BT combo模组,几乎清一色是SDIO接口。
但SDIO接口的代价就是配置复杂度全堆在软件侧。你需要处理供电时序、复位引脚、1.8V/3.3V电平匹配、SDIO时钟频率与采样相位、内核驱动开关、固件文件路径,每一环都缺一不可。USB WiFi插上就有网,SDIO WiFi要过了九九八十一难才有wlan0。这是用SDIO方案必须接受的事实。
1.3 配置难点其实就三大类:内核开关、设备树、固件
我用一次"故障现象—原因归类"的思路把SDIO WiFi的坑分成了三层。第一层是内核,WiFi驱动对应的config没开,或者编成了模块但没打包进文件系统,驱动就永远加载不出来。第二层是设备树,电源没拉起来、复位引脚被其他外设占用了、SDIO时钟没配对,总线直接枚举不到设备。第三层是固件,驱动加载成功了,但/lib/firmware下面没有对应固件,内核就会报一个很隐晦的firmware load失败,然后wlan0依然不出现。
这三层有个很坑爹的特点:它们出错时的表现形式高度相似,都是"没有wlan0"或者"SDIO card not found"。如果没有一套系统的排查顺序,光是反复编译、烧写、看dmesg就能耗掉一整天。所以后文我会在调试章节里,专门给出一条从总线枚举到驱动加载再到固件检查的排查链路,这也是这次项目里我觉得最值得沉淀的部分。
2. O9201SB模组选型分析:为什么要用这颗料
2.1 模组核心规格
O9201SB是一颗基于瑞昱RTL8852BS方案的WiFi 6 SDIO模组,支持2.4GHz和5GHz双频,802.11a/b/g/n/ac/ax,蓝牙部分一般支持BT5.x。接口是SDIO 3.0,4位总线模式下理论带宽足够跑满WiFi 6的多数场景。这里要特别提醒一句:我拿到的是RTL8852BS方案的版本,如果你手里的O9201SB后缀或者丝印不同,引脚定义和驱动匹配方式可能会有差异,动手前一定先确认模组规格书。
从指标上看,这颗模组属于"够用就好"的类型。WiFi 6带来的OFDMA和MU-MIMO特性在密集AP环境下很实用,SDIO 3.0的带宽不像老款模组那样成为瓶颈,而成本又比老牌BCM43752方案明显低一截。选型的时候我对比过AP6275P和RTL8852BS,最终选O9201SB的一大原因就是Rockchip SDK里对RTL8852BS的驱动支持非常成熟,社区里踩坑资料也多,这在中后期调试阶段是巨大的隐形优势。
2.2 引脚定义与最小系统
模组引脚图每家封装的叫法可能不太一样,但涉及SDIO WiFi接入的核心引脚基本是固定的。
| 引脚 | 功能说明 | 接入注意事项 |
|---|---|---|
| VBAT | 主供电,通常3.3V | 纹波要小,瞬时电流大,靠近模组放电容 |
| VDDIO | IO域供电,1.8V或3.3V | 必须和主控SDIO IO域电平一致 |
| SDIO_CLK | 时钟线 | 走线短且远离干扰源 |
| SDIO_CMD | 命令线 | 需要上拉电阻 |
| SDIO_D0-D3 | 4位数据线 | 对齐等长,上拉电阻 |
| WL_REG_ON | WiFi电源/复位使能 | 控制时序,上电后延时拉高 |
| BT_REG_ON | 蓝牙使能 | 用不到BT可接地或悬空 |
| HOST_WAKE | 模组唤醒主机 | 可接GPIO,也可悬空 |
| 32.768KHz | 慢时钟输入 | 如果没有外部时钟,部分版本也支持内部时钟 |
最小系统其实非常精简:VBAT和VDDIO供电,WL_REG_ON拉高,SDIO_CLK/CMD/D0-D3接主控,就具备了让wlan0冒出来的条件。蓝牙部分后续再说,先把WiFi跑通是第一目标。
2.3 为什么选它:成本、性能与驱动兼容性的平衡
选O9201SB还有一个很现实的原因:Rockchip SDK里几乎自带RTL8852BS的驱动。这意味着你不用去GitHub上翻那些几百年不更新的vendor驱动,也不用冒着风险打一堆补丁。对比过其他SDIO WiFi模组之后你会发现,很多模组的瓶颈根本不在硬件,而在驱动没人维护。O9201SB凭借RTL8852BS这颗芯片的普及度,在主线内核的rtw89驱动和Rockchip SDK的rockchip_wlan驱动里都有对应支持,等于给你上了双保险。
性能方面我实测下来,5GHz频段近距离通过iperf3可以跑到接近600Mbps,2.4GHz也有200Mbps以上,对一个SDIO接口的WiFi模组来说已经完全够用了。如果你选型时对蓝牙并发、低功耗唤醒或者漫游有更高要求,可以再评估其他方案,但如果只是想快速让RK3588具备可靠的无线网络能力,O9201SB是个性价比很稳的选择。
3. 硬件接入的关键细节:电平匹配、电源时序与天线布局
3.1 供电设计:3.3V的纹波远比你想的更敏感
SDIO WiFi模组对供电的敏感度,很多人是低估的。模组在工作状态下的电流会随着收发数据剧烈波动,尤其在5GHz发射时瞬时电流能冲到几百毫安,如果VBAT的纹波过大,轻则吞吐量不稳定,重则SDIO总线直接掉卡。规格书里一般要求纹波控制在50mV以内,最好能留出20%以上的余量。
我的做法是在模组的VBAT引脚旁边放了一颗10uF陶瓷电容和一颗0.1uF电容并联,PCB走线上尽量从DC-DC转换器单独拉一条粗线过来,避免和主控核心供电共用一个比较长的过孔通道。VDDIO那边也别省电容,1uF起步比较稳。如果条件允许,用示波器实测一下上电和ping包大流量时的电源纹波,比什么玄学调参都管用。
3.2 电平匹配:1.8V还是3.3V一定要先确认
RK3588的SDIO控制器IO域电压是可以配置的,常见的是1.8V或3.3V,具体由底板上的VCCIO_SDIO供电决定。O9201SB的VDDIO同样支持1.8V或3.3V版本,选型时不能只看模组型号,还要看你的VDDIO供电电压跟主控SDIO域是否一致。
如果主控SDIO域是1.8V,模组VDDIO却接了3.3V,那SDIO引脚之间就是3.3V对1.8V的电平不匹配,轻则ios上拉失效导致总线偶发错误,重则直接把主控引脚打坏。反过来主控3.3V、模组1.8V也同理。最稳妥的方案是让两者完全共用一个电源轨,这样电平天然一致,省去电平转换芯片的成本和麻烦。我在这块底板上就是直接让VDDIO和主控SDIO IO域共用1.8V,省事又可靠。
3.3 电源时序与复位引脚:别把WL_REG_ON当普通GPIO来拍
SDIO WiFi模组的使能时序是有讲究的。一般来说,要求VBAT和VDDIO先稳定,然后WL_REG_ON拉高,拉高之后还需要等待一段时间让模组内部的晶振和固件初始化完成,然后SDIO主机才能开始枚举。这个延时通常在10ms到200ms之间,不同模组规格书会有明确要求。
在设备树里,这个时序逻辑通常用mmc-pwrseq-simple节点来实现,代码里会有一个post-power-on-delay-ms参数,我习惯给200ms,留有充足余量。OWL这个问题上,我做过的板子里至少有一块是因为WL_REG_ON和另一颗芯片的复位脚共用了一个GPIO,结果两边互相干扰,WiFi死活起不来。所以硬件设计阶段一定要检查WL_REG_ON有没有被其他外设占用,软件阶段则要确认GPIO的active电平与模组实际使能极性匹配。
3.4 天线布局与PCB走线:决定吞吐量上限的隐藏变量
SDIO_CLK、SDIO_CMD和SDIO_D0-D3这六根线,在高速模式下对PCB走线的要求很高。SDIO_CLK信号完整性差的话,总线枚举都会时好时坏;数据线如果长度差太多,会导致采样窗口变小。设计时尽量把这组线走短、走直、包地处理,不同信号线之间拉开距离,避免和DC-DC或者PWM风扇这类干扰源平行走线。
天线那边更是血的教训。我第一版PCB把天线座放在了金属外壳的螺柱旁边,结果5GHz吞吐量只有不到100Mbps,后来把天线净空区重新调整、加了π型匹配电路才恢复正常。如果你用的是模组上的板载天线或者通过IPEX座外接天线,记得天线区域下方不能铺铜,周围不要放金属件和高频器件。很多"WiFi信号弱"的问题,根子不在驱动,而在射频环境被自己毁了。
4. 设备树配置的坑:iomux、电源域与SDIO时延参数
4.1 先查原理图再改设备树,顺序错了就是白折腾
设备树配置是这次项目里最磨人的部分。RK3588的SDIO引脚在SoC内部有多组复用选项,同样一组物理引脚可能被配置成SDIO、UART、PWM或者普通GPIO,一旦被别的外设功能占用,SDIO总线就起不来。所以改DTS之前,第一步永远是打开原理图,确认WiF模组的SDIO引脚接到了RK3588的哪一组ball上,再看这个ball对应的复用选项有哪些。
以我板卡为例,SDIO总线接的是GPIO4的C组引脚,WL_REG_ON接在GPIO4的某个普通GPIO上。这些信息在SDK自带的dts里其实已经有默认pinctrl配置,正常情况下不需要自己重新写iomux。真正会出问题的是两种场景:一是你用了非默认引脚,需要新增pinctrl子节点;二是某个引脚被其他功能模块先声明了,产生pin conflict。这种冲突在编译时不一定报错,得上电后用GPIO调试工具或者示波器才能发现。
4.2 sdio_pwrseq电源序列节点:让WL_REG_ON按规矩办事
设备树里控制模组上电时序最标准的做法是定义sdio_pwrseq节点,绑定到&sdio上。下面这个写法是Rockchip SDK里最常见的模板,我基于实际需求加了延时和引脚定义。
/ { sdio_pwrseq: sdio-pwrseq { compatible = "mmc-pwrseq-simple"; pinctrl-names = "default"; pinctrl-0 = <&wifi_enable_h>; reset-gpios = <&gpio4 RK_PC2 GPIO_ACTIVE_LOW>; post-power-on-delay-ms = <200>; }; };这里有一个非常容易踩的细节:reset-gpios用的是GPIO_ACTIVE_LOW,而硬件上WL_REG_ON是高电平使能。看起来好像反了,其实mmc-pwrseq-simple框架的语义是"复位时拉低、释放时拉高",配合GPIO_ACTIVE_LOW的极性反转,最终在post-power-on阶段输出到物理引脚上的正好是高电平,也就是模组的使能电平。如果你照抄模板却发现WiFi没使能,第一件事就是确认你这颗模组WL_REG_ON的有效电平,以及GPIO_ACTIVE_LOW/HIGH写反了没有。
对应的pinctrl子节点建议这么写:
&pinctrl { sdio-pwrseq { wifi_enable_h: wifi-enable-h { rockchip,pins = <4 RK_PC2 RK_FUNC_GPIO &pcfg_pull_none>; }; }; };4.3 &sdio节点里那些"看着没用但缺了就炸"的属性
接下来是&sdio节点本身。这是整篇设备树里信息密度最高的地方,我直接给出经过验证的一套配置,再逐个解释为什么必须有。
&sdio { bus-width = <4>; cap-sdio-irq; keep-power-in-suspend; non-removable; mmc-pwrseq = <&sdio_pwrseq>; rockchip,default-sample-phase = <90>; max-frequency = <150000000>; status = "okay"; };bus-width = <4>指定SDIO走4位数据总线,如果这里不写或者默认是1位,WiFi驱动也能工作,但吞吐量会跌到惨不忍睹。cap-sdio-irq表示支持SDIO设备通过CMD线向主机发中断,WiFi模组的SDIO异步中断机制依赖这个属性,不加的话可能出现收发数据大量丢包甚至死等。keep-power-in-suspend是深睡眠时保持SDIO供电,少了它之后系统休眠再唤醒,WiFi往往就掉线了。non-removable告诉内核这根总线上的设备是不可插拔的,避免内核周期性探测卡状态而干扰WiFi工作。
4.4 SDIO频率和采样相位:吞吐量的隐形调节开关
max-frequency我初始设了150MHz,对应SDIO 3.0的SDR104模式。这里有个很现实的矛盾:频率越高,吞吐量上限越高,但对PCB布线质量和采样时序要求也越苛刻。如果你的板子走线不理想,150MHz下可能连SDIO卡都枚举不稳定,这时候强行追求高频只会浪费一整天调试时间。我的建议是先降到50MHz把整个链路跑通,再逐步往上拉。
rockchip,default-sample-phase = <90>是Rockchip比较特殊的一个属性,用来调整SDIO主机采样数据的相位窗口。不同板卡因为走线长度和负载差异,最佳采样相位可能完全不同。我在同一型号的两块板子上分别测过,一块用90度很稳定,另一块必须改到120度才能跑满吞吐量。这个参数没有银弹,只能靠实测调。后文调试章节会专门讲怎么判断相位不对的症状。
4.5 设备树编译与反编译验证
DTS改完之后,编译和烧写也要细致。RK3588的SDK里一般用make dtbs编译设备树,产物是.dtb文件,烧写时要确认烧到对应的dtb分区。我的经验是,改完DTS后先本地反编译验证一下:
dtc -I dtb -O dts -o verify.dts arch/arm64/boot/dts/rockchip/rk3588-evb.dtb然后人肉对比verify.dts里&sdio节点和sdio_pwrseq节点是不是自己预期的样子。这个习惯帮我抓出过一次"改了源码但烧进板子的dtb还是旧的"这种低级错误。如果你同时改了kernel和dtb,务必把boot.img一起重新打包烧录,别只烧dtb而忽略了内核。
5. 内核驱动与固件加载:从编译到文件系统部署
5.1 驱动方案选择:SDK自带驱动还是主线rtw89
O9201SB对应RTL8852BS芯片,驱动有两条路可走。第一条是Rockchip SDK里自带的rockchip_wlan目录下的rtl8852bs驱动,这条路最大的优势是和SDK内核匹配度高,配置少,适合快速集成产品。第二条是主线内核的rtw89驱动,需要内核版本较新,对SDIO接口的8852BS支持在主线里相对年轻,好处是跟内核社区同步、修bug快。
我这次用的是Rockchip SDK自带驱动,原因很直接:SDK里默认已经把编译依赖都调好了,almost不用自己解决函数符号依赖问题。如果你用的是主线内核或者自己维护的kernel,那可以考虑rtw89路线,但要做好内核升级后驱动接口变化导致加载失败的心理准备。初学者我强烈建议先走SDK自带驱动,等wlan0稳定出现了,再去纠结要不要切主线驱动。
5.2 内核配置与编译步骤
首先要确认内核配置里把RTL8852BS驱动打开。Rockchip SDK通常可以在menuconfig里找到:
make ARCH=arm64 rockchip_defconfig make ARCH=arm64 menuconfigmenuconfig里的路径一般是Device Drivers -> Network device support -> Wireless LAN -> Realtek rtl8852bs SDIO,选中为模块<M>还是编进内核<*>各有优劣。编成模块的好处是调试时不用每次改配置就烧整个boot.img,直接insmod/rmmod就能换,我调试阶段用的就是模块方式;量产时更推荐直接编进内核,省去文件系统里放ko和加载顺序的麻烦。
编译命令大致如下:
make ARCH=arm64 CROSS_COMPILE=aarch64-linux-gnu- -j$(nproc) dtbs make ARCH=arm64 CROSS_COMPILE=aarch64-linux-gnu- -j$(nproc) modules make ARCH=arm64 CROSS_COMPILE=aarch64-linux-gnu- -j$(nproc) boot.img如果你的SDK里dtb是独立分区,烧写时单独烧dtb即可,不用连boot.img一起烧,能省不少时间。我习惯把rockchip_defconfig打开后,用grep RTL8852BS .config确认一下选项确实生效了,防止被其他config覆盖掉。
5.3 固件文件放置:驱动加载的最后一道闸门
驱动编译装好了,还有一道关卡是固件。RTL8852BS的固件文件一般叫rtl8852bs_fw.bin或者类似的名字,外加一份nvram参数文件。具体文件名和存放路径,Rockchip SDK和主线rtw89的要求不一样。SDK方案一般会把固件放到根文件系统的/vendor/etc/firmware/目录,主线内核则是放在/lib/firmware/rtw89/。
最直接的确认方式就是看dmesg报错。驱动加载时如果找不到固件,会有类似Direct firmware load for xxx failed的提示,跟着提示里的路径去放文件就行。我踩过一次比较隐蔽的坑:文件路径、文件名全对,但文件权限是600,只有root能读,驱动以非root方式加载时固件读取失败。后来统一改成644,问题立刻消失。如果你固件看起来全对但驱动还是起不来,检查一下权限。
5.4 蓝牙的"顺手"配置:等WiFi稳了再管它
O9201SB是WiFi/BT combo模组,蓝牙部分一般走UART,由BT_REG_ON控制使能,驱动侧是hci_uart或者bluetooth子系统。这次项目我刚开始就试图同时把WiFi和蓝牙都调好,结果两边都没调好。后面学乖了,先把蓝牙相关配置全部关掉,专注WiFi链路,等wlan0稳定后再开蓝牙。蓝牙的接线、设备树、firmware和WiFi是完全独立的一条链路,混在一起排查只会让问题复杂度翻倍。如果你也只是想让板子有网,完全可以暂时不管蓝牙。
6. 上电调试全流程:从识别失败到吞吐量优化的实战排错
6.1 第一步:确认SDIO设备是否被总线枚举到
上电后我习惯先执行dmesg | grep -i mmc,看系统启动过程中有没有出现新的SDIO卡枚举记录。正常情况下会看到类似下面这样的输出:
mmc2: new high speed SDIO card at address 0001注意这个mmcX的编号不固定,取决于你的系统里有哪些MMC控制器被使能。如果dmesg里完全没有新的SDIO卡记录,说明MMC总线层面就没枚举到模组,此时优先检查供电、复位GPIO、电平匹配和设备树里&sdio节点是否真的生效了,而不是去查驱动。
还想看得更细,可以看下面的debug信息:
cat /sys/kernel/debug/mmc2/ios这里能看到当前SDIO总线的时钟频率、总线宽度、电压等信息。如果显示频率只有400kHz,说明还处于初始化模式,没有切换到高速模式;如果频率已经到150MHz但卡还是不稳定,那就回到采样相位和硬件走线的问题上。
6.2 第二步:驱动加载和固件链路排查
总线枚举到了SDIO卡,但ifconfig -a里没有wlan0,问题就落在驱动和固件这一层。执行:
lsmod | grep 8852 dmesg | grep -i 8852 dmesg | grep -i firmware排查逻辑是这样的:如果lsmod里没有驱动模块,说明ko文件没加载成功,可能的原因包括文件系统里没有ko、驱动和内核版本不匹配、或者依赖的符号缺失。如果驱动模块在,但dmesg里报firmware相关错误,那就按上一节的方法检查固件路径和权限。正常情况下驱动加载成功后,dmesg里能看到RTL8852BS识别到设备并注册了wlan0接口。
这里还要提一个容易被忽略的点:驱动加载顺序。如果你的根文件系统用了systemd,可能需要在启动服务里加modprobe rtl8852bs或者在合适的位置加载模块。我在buildroot系统里就遇到过wpa_supplicant启动时wlan0还不存在,导致服务启动失败的连锁问题,后来在启动脚本里加了一个等待wlan0出现的循环才解决。
6.3 第三步:用wpa_supplicant把WiFi连起来
wlan0出现后,可以先用iwlist wlan0 scan看能不能扫描到AP。如果扫描结果为空,大概率不是驱动问题,而是天线或射频侧的问题。能扫到AP之后就配置wpa_supplicant联网。最小配置文件如下:
ctrl_interface=/var/run/wpa_supplicant network={ ssid="your_ap_ssid" psk="your_password" key_mgmt=WPA-PSK }启动命令:
wpa_supplicant -Dnl80211 -iwlan0 -c /etc/wpa_supplicant.conf -B dhclient wlan0然后ping一下网关。如果ping不通,先确认IP地址是否拿到的、网关是否可达,再回头查驱动和射频。
6.4 第四步:吞吐量测试与采样相位微调
联网成功只是第一步,吞吐量才是验收标准。我用iperf3分别在2.4GHz和5GHz频段测过:
# 服务端(PC) iperf3 -s # 开发板 iperf3 -c 192.168.1.100 -t 30 -i 1如果测下来的吞吐量明显低于预期,比如5GHz才跑几十Mbps,先把天线和环境因素排除掉,然后重点怀疑SDIO采样相位。rockchip,default-sample-phase这个参数不同角度对吞吐量的影响非常大。我实测同一个硬件,90度时能跑接近600Mbps,改成0度后直接掉到200Mbps,稳定性和丢包率也明显变差。但这个最优角度没有规律可循,只能编译几版不同相位的dtb逐一测试,记录每组角度的iperf3数值和dmesg里的错误计数。
如果调相位也解决不了,还可以把max-frequency从150MHz降到100MHz试试。很多走线不理想的板子在150MHz下总是偶发错误,降到100MHz后反而更稳定,吞吐量损失也很小。性能优化在没有仪器的情况下,本质上就是个二分法试验。
6.5 实战排错对照表:把这次踩过的坑一次性说清楚
我把这次项目里遇到过的典型现象和解决方法整理成一张表,后续再碰到类似问题可以直接对号入座。
| 现象 | 大概率原因 | 排查动作 |
|---|---|---|
| 启动日志里没有任何SDIO新设备 | 供电/复位/电平不匹配 | 示波器量WL_REG_ON波形,检查VDDIO电压 |
| 枚举到SDIO卡但没有wlan0 | 驱动未加载或固件缺失 | lsmod、dmesg查firmware load |
| wlan0存在但扫描不到AP | 天线/净空/射频电路问题 | 换天线、检查IPEX座、测量射频供电 |
| 连接后频繁掉线 | 电源纹波大或SDIO频率过高 | 示波器看VBAT纹波,降max-frequency |
| 吞吐量远低于理论值 | 采样相位不对或天线环境差 | 遍历rockchip,default-sample-phase |
| 休眠唤醒后WiFi消失 | 缺少keep-power-in-suspend | 检查DTS该属性 |
这张表Practically覆盖了SDIO WiFi接入90%的问题。剩下的10%,大多出在模组批次差异或者SDK版本缺陷上,那就不属于配置问题,而是得换模组或者升SDK版本了。
这次项目做下来,我个人最大的体会是:SDIO WiFi接入没有玄学,每一步都有明确的逻辑链,但每一步都可能因为一个极小的细节功亏一篑。你在网上抄来的每一段dts配置,都有它特定的硬件前提,直接套用前一定要对照自己的原理图逐项核实。如果调试陷入僵局,先把max-frequency降下来,把default-sample-phase设置为中间值,把内核驱动编成模块,这样每改动一个变量都能快速验证,效率反而最高。
最后分享一个实用小技巧:如果SDIO枚举一直过不了,与其反复烧写dtb,不如拿一个GPIO手动控制WL_REG_ON,在系统运行时拉低再拉高,观察dmesg里是否会触发重新枚举。这个办法能帮你把"时序问题"和"静态配置问题"快速区分开,省下大量编译烧写的重复时间。希望这篇文章能让你在RK3588上接O9201SB时,把本该花在调配置上的时间用来做更有价值的事。