ARTICLE DETAIL

资讯详情

深耕郑州网站建设与运营推广的一线实战洞察。

RK3588调试串口波特率改造:从1500000到115200完整实操指南

RK3588调试串口波特率改造:从1500000到115200完整实操指南 最近在折腾RK3588的开发板碰到一个看起来很基础、但确实让不少人栽过跟头的问题把调试串口默认的1500000波特率改成115200。RK3588这颗SoC的调试串口debug uart出厂固件默认是1500000也就是常见的1.5Mbps。这个速率在RK官方文档、规格书里都写得很清楚官方SDK用的也是这个值。但实际做项目时很多工程师和玩家并不需要这么高的速度反而会因为1.5M这个非标速率遇到一堆麻烦USB转串口模块认不出来、CH340/PL2303驱动不给力、工控现场那台老旧的串口服务器只支持115200、SecureCRT/minicom配置起来麻烦再往小了说逻辑分析仪抓串口数据时也经常卡在采样率上。所以把debug串口波特率改成115200是一个相当高频、真实、覆盖面很广的刚需。这篇文章就记录一下我从源码层面把RK3588调试串口完整改成115200的全过程。注意我说的是“完整”二字因为这里的水很深U-Boot、Kernel、Android板级配置三处都要动否则就会遇到启动到一半突然乱码、或者内核起来后串口直接没有输出的怪问题。我会把这几个位置的修改逻辑、具体命令、验证方法、常见坑全部拆开讲清楚。不管你是正在用RK3588做核心板、工控底板还是刚买了开发板想统一终端工具参数这篇内容都能直接抄作业。1. 为什么RK3588调试串口默认是1500000又为什么要改1.1 RK平台使用1.5M波特率的历史原因很多人第一次接触RK3588时看到官方烧录工具里“波特率1500000”这个选项都会愣一下。实际上这不只是RK3588的习惯Rockchip整个系列的芯片从RK3288、RK3399到RK3568、RK3588调试串口和Maskrom模式下的烧录通信默认波特率基本都是1500000。官方之所以选这个非标数值主要是从调试效率考虑的。RK3588启动阶段日志非常密集从BootROM、SPL到U-Boot再到Kernel一次完整开机打印出来的字符数量非常可观在1500000波特率下传输明显比115200快得多能减少开发阶段等待日志滚动的时间。另外还有一个工程上的原因RK的Loader烧录模式下的下载固件通道也要走这个串口波特率太低会明显拉长整机烧录时间。对产线来说每台设备烧录快几秒累积起来就是可观的效率提升。所以从方案设计角度看1.5M波特率是有它存在道理的并不是随手填的一个数。1.2 标准波特率115200在真实项目里的优势那为什么还有这么多人想改回115200我总结了一下基本逃不开下面几类场景USB转串口模块兼容性市面上一大把CH340模块官方驱动宣称支持到2Mbps但实际在Windows老版本驱动、Linux某些内核版本下跑1500000这个非标速率时不稳定经常出现乱码、丢字符、甚至设备掉线。反而是115200这种标准速率几乎所有芯片、所有驱动版本都支持得非常好。工控设备对接很多PLC、HMI、串口服务器、旧款工业主机串口只支持标准波特率它们只会列出9600、19200、38400、115200这类档位根本不会有1500000这个选项。如果你要用RK3588去跟这类设备通过debug口联调不改波特率连不上。逻辑分析仪抓包用逻辑分析仪直接抓RK3588串口波形来排查问题的时候1500000对采样率要求很高比较便宜的24MHz/48MHz采样率的分析仪抓1.5M波特率的信号会非常吃力改动115200后抓包就轻松多了。统一下发工具链公司内部已有的产测工具、日志采集脚本如果都是按115200开发的新增RK3588产品线时改波特率能减少一套工具链的维护成本。我之前还遇到过一个更极端的例子——甲方要求debug口必须接到他们机房已有的串口终端服务器上那台设备菜单里根本没有1500000这个选项最高只到115200最后只能从固件层面把波特率整个改掉。所以这次把RK3588改成115200的过程本质上是把RK默认的“开发调试高速方案”切换成“全场景通用标准方案”。1.3 修改前的总体认知串口参数到底经过哪几层在动手改之前你脑子里得先有一张串口参数传递的链路图。RK3588的调试串口不是简单在某个配置文件里改一个数字就完事的它至少经历四层层次作用阶段参数位置影响U-Boot自身波特率BootROM到U-Boot启动早期u-boot源码config头文件里的CONFIG_BAUDRATE决定U-Boot阶段串口实际速率U-Boot设备树bootargsU-Boot启动内核前u-boot/arch/arm/dts下dtsi的chosen节点作为cmdline传给内核Kernel设备树bootargs内核启动阶段kernel/arch/arm64/boot/dts/rockchip下dtsi的chosen节点决定内核console使用的串口与速率Android板级BOOTARGS系统启动阶段device/rockchip下的BoardConfig.mk可能覆盖或追加内核命令行参数这四层只要有一层没改就会出现“某个阶段正常、某个阶段乱码”的诡异现象。比如你只改了Kernel设备树那U-Boot阶段大概率还是1500000你会看到板子上电后先正常显示一段U-Boot日志然后到了内核接管串口时刷的一下变成乱码——因为内核已经把波特率切成115200了而你的终端还停在1500000。这种半改状态是最容易让人怀疑人生的。2. 修改前的准备工作硬件、软件与源码环境2.1 硬件串口模块的选择与接线注意RK3588调试串口一般是板子上的一个4针或3针排针对应UART2的TX、RX、GND有些板子还会引出VCC。接线原则很简单开发板的TX接USB转串口模块的RX开发板的RX接模块的TXGND一定要共地。别小看共地这个问题我接过不少只插了TX/RX、没接地线的板子结果数据完全是花的加了一根地线立刻恢复正常。USB转串口模块方面我的建议是首选CP2102或FT232这两类的驱动和稳定性最好跑1500000也完全没问题。CH340不是不能用但如果你需要在1.5M下调串口最好先去官网把最新驱动装上Linux下用内核自带的ch341驱动一般也能识别。对了修改波特率之前先确认一下PC上能正确识别到串口设备。Linux下用lsusb看设备然后用dmesg | tail -20确认有没有生成/dev/ttyUSB0Windows下打开设备管理器看“端口(COM和LPT)”里有没有新增的COM口。这一步虽然基础但在现场最容易出问题。2.2 终端软件的波特率配置方法串口终端软件这块Linux下我个人最喜欢用picocom轻量、参数清晰minicom也是一个经典选择。接线和驱动确认正常后先用当前固件的1500000波特率连一下确保能进系统确认硬件链路没问题再做源码修改。命令参考# 使用picocom连接波特率根据当前固件情况修改 picocom -b 1500000 /dev/ttyUSB0 # 使用minicom先运行minicom -s进入配置界面 # 选择“Serial port setup”将波特率改为1500000 # 保存配置后连接 minicom /dev/ttyUSB0Windows下建议用MobaXterm的Serial会话、SecureCRT或者Xshell新建连接时选择SERIAL速率填1500000数据位8、停止位1、无校验、无流控。这里有一个非常重要的细节串口参数是8N18数据位、无校验、1停止位流控必须关掉。有些终端工具默认会打开硬件流控RTS/CTS如果不关就可能出现“能收不能发”或者干脆完全没反应的情况。2.3 RK SDK源码目录结构与编译环境确认这篇文章假设你手里已经有一套完整的RK3588 SDK源码不管是官方Release包还是Rockchip GitHub拉下来的常用的目录结构基本一致u-boot/U-Boot源码里面arch/arm/dts/下存放U-Boot侧设备树kernel-5.10/或者kernel-6.1等版本内核源码设备树在arch/arm64/boot/dts/rockchip/device/rockchip/Android板级配置目录build.sh顶层编译脚本开工之前先确认编译环境能正常出包至少你要能编译U-Boot或Kernel其中之一。如果你只是拿别人编译好的镜像反编译来改那我建议还是先搭建好源码编译环境因为后续修改牵扯到的dts和mk文件必须重新编译打包烧录才能生效只改镜像里的文本是不现实的。3. 完整修改流程U-Boot、Kernel与Android三层同步改3.1 第一步确认调试串口对应的设备树节点RK3588的debug串口默认接到UART2对应设备树节点uart2。不过不同核心板厂商可能有改动所以最稳妥的办法是先在源码里搜一下确认当前调试串口到底用的哪个节点。重点搜索两个东西stdout-path和ttyFIQ0。注意U-Boot和Kernel的设备树是两份独立的文件要分别搜索。# 在U-Boot源码中搜索 grep -rn stdout-path\|ttyFIQ0\|chosen u-boot/arch/arm/dts/ | grep -i rk3588 # 在内核源码中搜索 grep -rn stdout-path\|ttyFIQ0\|chosen kernel-5.10/arch/arm64/boot/dts/rockchip/ | grep -i rk3588找到对应文件后打开chosen节点通常会看到类似下面的内容chosen { stdout-path uart2; bootargs consolettyFIQ0,1500000; };consolettyFIQ0是Rockchip平台特有的FIQ调试串口配置ttyFIQ0背后绑定的是serial节点由fiq_debugger驱动接管。看到1500000这个数字就说明你找对地方了。另外顺手确认一下uart2节点下有没有status okay如果uart2都没打开那串口肯定是不工作的。3.2 第二步修改U-Boot设备树和默认波特率U-Boot阶段的修改是这次操作里最关键的一步因为它决定了从板子上电到内核接手之前这一大段日志能否正常输出。我的建议是分两个地方同步改第一处U-Boot设备树的chosen节点把bootargs里的1500000改成115200// u-boot/arch/arm/dts/rk3588-evb.dtsi或你手上的板级dts chosen { stdout-path uart2; bootargs consolettyFIQ0,115200; };第二处U-Boot配置头文件里的CONFIG_BAUDRATE。这是很多人容易漏掉的地方。U-Boot在启动早期、设备树还没完全解析的时候串口波特率是用这个宏来确定的。如果只改bootargs而不改这个宏SRAM里SPL阶段会继续用1500000输出日志直到U-Boot某个阶段切换console参数后才变成115200结果就是你看到一段“前面正常、某一行突然开始乱码”的输出。具体路径因SDK版本而异一般在u-boot/include/configs/rk3588_common.h或rockchip-common.h里搜一下就能找到grep -rn CONFIG_BAUDRATE u-boot/include/configs/找到后把1500000改成115200#define CONFIG_BAUDRATE 115200这里解释一下为什么必须在两个位置同时改。CONFIG_BAUDRATE是U-Boot编译期的默认波特率偏底层而chosen节点里的bootargs是U-Boot在启动内核时拼进cmdline用的偏上层。两者职责不同但都直接影响串口。双双改成115200之后U-Boot从头到尾都是115200不会出现阶段性的跳变。3.3 第三步修改Kernel设备树和console参数U-Boot改完之后接着改内核侧。打开Kernel源码下对应的RK3588设备树文件同样找到chosen节点。这里要注意有些SDK里内核的dtsi不会直接写bootargs而是留着让U-Boot通过tag方式传给内核这种情况下你只需要保证U-Boot的bootargs正确就行。但如果内核dtsi里也有硬编码的bootargs那必须同步修改否则U-Boot传过去的参数有可能被覆盖。// kernel-5.10/arch/arm64/boot/dts/rockchip/rk3588-evb.dtsi chosen { bootargs consolettyFIQ0,115200; };内核对调试串口的命名可能有几种比如ttyFIQ0、ttyS2具体要看内核的fiq_debugger配置。在RK3588的安卓SDK里ttyFIQ0是常见写法如果搜不到这个字符串就搜bootargs.*115200或者chosen节点看看现有配置里console参数给的是哪个设备。另外部分内核设备树里还有一个额外的fiq_debugger节点里面可能会带rockchip,baudrate属性这个属性同样需要检查存在的话一并改成115200。例如fiq_debugger: fiq-debugger { compatible rockchip,fiq-debugger; rockchip,serial-id 2; rockchip,wake-irq 0; rockchip,baudrate 115200; // 这里原来是1500000 interrupts GIC_SPI 252 IRQ_TYPE_LEVEL_LOW; status okay; };这个节点的baudrate属性直接决定了FIQ调试串口驱动初始化的速率。有些平台的fiq_debugger逻辑是优先读节点里的baudrate而不是bootargs里的console参数所以这一处漏改的话内核启动后波特率可能还是1.5M导致系统起来后串口乱码。3.4 第四步修改Android板级BOOTARGS配置如果你用的是RK官方Android SDK那么仅仅改完U-Boot和Kernel设备树还不算完。RK的Android构建系统会在打包阶段从device/rockchip/目录下的BoardConfig.mk里读取BOOTARGS变量再把它拼到最终的内核启动参数里。这个变量的优先级很高经常会把设备树里的bootargs整个覆盖掉。我见过太多人改了dts后重新编译Android整包烧进去发现还是1.5M最后一查问题就出在这个mk文件上。具体操作先全局搜索一下grep -rn BOOTARGS device/rockchip/正常情况下会在device/rockchip/rk3588/BoardConfig.mk或device/rockchip/common/BoardConfig.mk里找到类似这样的配置BOOTARGS : ... consolettyFIQ0,1500000 ...把其中的波特率改成115200然后重新编译内核和boot镜像。举个例子如果原本是BOOTARGS : androidboot.hardwarerk3588 consolettyFIQ0,1500000 androidboot.consolettyFIQ0改成BOOTARGS : androidboot.hardwarerk3588 consolettyFIQ0,115200 androidboot.consolettyFIQ0这里androidboot.consolettyFIQ0的作用是把Android userspace的console也绑到FIQ调试串口上波特率同样要跟着改。这一步不做的话你会看到内核日志是115200正常但Android系统起来后logcat或者shell输出又变乱码了。3.5 第五步重新编译与烧录验证所有源码层面的修改完成后就到了编译和烧录环节。以RK3588 SDK为例如果你是Android整包开发可以直接./build.sh -A Kernel -u这个命令会重新编译内核和U-Boot并打包生成新的镜像。如果你的SDK结构不一样也可以分开操作# 单独编译U-Boot cd u-boot make rk3588_defconfig make -j$(nproc) # 编译内核设备树和内核 cd ../kernel-5.10 make ARCHarm64 rockchip_defconfig make ARCHarm64 dtbs make ARCHarm64 boot.img -j$(nproc)编译完成之后把新生成的U-Boot镜像、boot.img或resource.img以及Android系统镜像通过RKDevTool烧录到板子上。烧录时建议进入Maskrom模式或者Loader模式用升级固件的方式整体写入避免只烧单个分区导致版本不一致。烧录完成后把串口终端软件波特率切到115200重新上电观察日志。正常情况应该是从第一行U-Boot打印到最后系统完全启动全程一字不差、无乱码、无断流。到这里整个修改流程就闭环了。4. 验证、排查与避坑实战中遇到的典型问题4.1 启动日志里的波特率切换现象分析我在调试过程中特意记录了几种典型现象方便你对照自己的情况判断是哪里没改到位现象AU-Boot正常内核开始后立刻乱码。这说明U-Boot侧已经是115200但内核侧还是1500000两边不一致。优先查Kernel设备树的chosen节点再看fiq_debugger节点里的rockchip,baudrate。现象BU-Boot乱码内核阶段正常。这种比较少见通常是U-Boot的CONFIG_BAUDRATE没改或者U-Boot设备树里的bootargs是115200但编译头文件还是1500000。回查CONFIG_BAUDRATE。现象CU-Boot和内核都正常Android起来后没有shell或输出变乱码。说明问题出在Android userspace层重点检查BoardConfig.mk里的BOOTARGS特别是androidboot.consolettyFIQ0后面的波特率。现象D全程完全没有输出。先别怀疑源码优先检查接线、终端软件波特率、串口模块驱动大概率是硬件链路问题。尤其是USB转串口模块没插好或者GND没接。为了方便排查我整理了一份速查表现象可能原因排查方向上电无输出接线错误、串口模块坏、终端波特率错检查TX/RX/GND换模块换波特率U-Boot正常内核乱码Kernel dts未改或fiq_debugger节点未改改kernel dts的chosen和fiq_debugger内核正常Android后乱码BoardConfig.mk的BOOTARGS未改改device/rockchip下的mk文件某一阶段突然无打印流控被打开关闭RTS/CTS烧录后进不了系统boot.img/resource.img未重新打包重新编译并确认烧录了新镜像全程偶发乱码USB转串口模块驱动问题更新驱动或换FTDI/CP21024.2 容易被忽略的三个细节第一个细节U-Boot和Kernel的设备树是两套独立文件千万别以为改了一个就万事大吉。RK SDK里U-Boot的dts在u-boot/arch/arm/dts/内核的dts在kernel-5.10/arch/arm64/boot/dts/rockchip/两者虽然大部分内容长得像但编译时各用各的必须同步修改。第二个细节部分核心板厂商会在SPL阶段读取eMMC或SD卡里预留的config分区里面可能覆盖了bootargs中的波特率参数。如果你改了源码并重新编译烧录后发现还是老样子建议把config分区一并擦除或者重新写入。这个情况在RK3568、RK3588的核心板上都出现过属于厂商自定义逻辑不是标准SDK行为但遇到了会让人非常困惑。第三个细节修改波特率后如果后续还要用RKDevTool进行Maskrom烧录注意烧录工具里的通信波特率可能也会变化。RK的Loader下载协议默认跟uboot的配置走你已经改成115200了那烧录工具里如果还写着1500000就会下载失败。遇到烧录失败时先看看工具的波特率设置是不是也要跟着改成115200。4.3 修改完之后的验证脚本与日常使用建议改完之后强烈建议把串口使用的波特率信息固化到项目文档里尤其是团队协作时。我自己习惯在仓库里建一个docs/debug_uart.md内容很简单开发板型号、debug串口对应排针位置、USB转串口模块型号、系统改动前波特率、改动后波特率、终端软件推荐配置、常见问题链接。这样新同事或者客户拿到板子后不需要猜直接照着文档就能连上。另外如果你经常在Linux主机上切换不同开发板的串口建议给RK3588单独写一个/etc/udev/rules.d/规则把USB转串口固定成一个稳定的设备名比如/dev/rk3588_uart这样每次插拔后不会因为ttyUSB编号变化而找不到设备。规则示例# /etc/udev/rules.d/99-rk3588-uart.rules SUBSYSTEMtty, ATTRS{idVendor}1a86, ATTRS{idProduct}7523, SYMLINKrk3588_uart这里的idVendor和idProduct需要根据你手头CH340的实际值修改用lsusb就能查到。连接时直接picocom -b 115200 /dev/rk3588_uart方便很多。4.4 关于回退改完之后想恢复1500000怎么办如果你改完之后发现某些场景还是需要1.5M比如想用RK官方更高速的日志抓取工具回退也很简单把U-Boot的CONFIG_BAUDRATE、U-Boot dts的bootargs、Kernel dts的bootargs、fiq_debugger节点的baudrate、以及BoardConfig.mk里的BOOTARGS全部改回1500000重新编译烧录即可。改来改去的过程其实很机械化最关键的还是别忘了“四层同步改”这个原则。我个人在实际操作中的体会是调试串口波特率这种修改看起来只是“一个数字的事”但牵一发动全身U-Boot、内核、Android userspace只要有一层掉链子表现出来都是非常折磨人的乱码或者静默。按照“先U-Boot、再Kernel、再Android板级配置”这个顺序一层层捋下来半小时内就能搞定。如果你在改的过程中遇到其他奇怪的现象欢迎在评论区留言把你看到的启动日志贴出来我们一起来定位。
返回列表