RK3229 SDK编译环境搭建与固件烧写实战指南
简介:《Rockchip RK3229 软件开发指南 V1.03》是瑞芯微官方于2017年11月发布的芯片开发调试文档,面向软件开发工程师与技术支持工程师,帮助其快速上手RK3229平台的Linux 3.10内核与Android 6.0.1/7.1.2系统开发。资源包共1个文件,为PDF格式,大小约1.61MB,单文档即涵盖完整技术说明,便于随查随用。内容从DDR、NAND、EMMC、WiFi/BT及多媒体编解码支持列表切入,延伸至SDK编译烧写、system分区与odex预编译配置、禁用SELinux、Box产测工具、jack-server配置、USB默认开启ADB、开机视频与低内存优化、WIDEVINE level 1 DRM配置等开发者特性,并附工具版本更新与开机logo限制、序列号/Mac烧写说明。目前已有627人学习下载,适合需要系统掌握RK3229软硬件适配与调试要点的嵌入式开发者对照查阅。
1. 从一块 RK3229 盒子板说起:为什么 2017 年的 SDK 今天还有人装
上周帮朋友救一块 RK3229 的电视盒子板,板子能通电、串口有输出,但 Android 起不来,卡在开机 logo 反复重启。他第一反应是“固件坏了,重刷一个就行”,结果刷完还是老样子。真正的问题在编译环境:他用的 Ubuntu 20.04 默认 GCC 9,而这份 2017 年 11 月发布的 RK3229 软件开发指南 V1.03 对应的 SDK 是 Linux 3.10 内核 + Android 6.0.1 / 7.1.2 的 32 位系统,整套工具链、jack-server、repo 脚本都停留在那个年代。环境不对,编出来的镜像看着能烧,跑起来就是玄学重启。
RK3229 这类芯片在盒子、广告机、商显板卡上存量很大,SDK 又只在特定渠道流转,所以“拿到 SDK 却装不起来”是常态。这篇笔记按我实际搭环境的顺序写:先列清版本和依赖,再走 SDK 获取、编译、烧写,中间穿插 U-Boot、内核 DTS、Android 常用配置,最后落到怎么验证镜像真的跑通。适合手上已经有 RK3229 Box SDK 包、准备第一次编译出固件的开发者,也适合被旧环境坑过、想找一份可复现步骤的熟手。
2. 环境准备:Ubuntu 14.04/16.04、JDK 7/8 与 32 位依赖库
这套 SDK 的编译环境不能随便挑。指南里没有明写“必须 Ubuntu 14.04”,但从 Linux 3.10 内核、Android 6.0.1 的 repo 同步脚本、以及 jack-server 对 JDK 的要求倒推,合格运维最稳的做法是 Ubuntu 14.04 LTS 或 16.04 LTS 的 64 位桌面版,装在一台独立机器或虚拟机上,不要和日常开发机混用。原因很直接:Android 7.1 编译要 jack-server,jack 对 JDK 版本敏感,JDK 9 以上直接罢工;而 Ubuntu 18.04 之后默认的 Python 3、GCC 7+ 又会让 U-Boot 和内核的老 Makefile 报一堆 warning 甚至 error。
2.1 版本对照:内核、Android 与工具链的对应关系
先把这张表贴墙上,后面每一步都对着它查:
| 项目 | 版本 | 说明 |
|---|---|---|
| 芯片 | RK3229 | 32 位 ARM 平台 |
| 内核 | Linux 3.10 | SDK 固定,不要自行升级 |
| Android | 6.0.1 / 7.1.2 | 两套分支,7.1 多 jack-server、开机视频、低内存优化、Widevine L1 |
| 编译主机 | Ubuntu 14.04 / 16.04 64 位 | 16.04 需额外补 32 位库 |
| JDK | OpenJDK 7(6.0.1)/ OpenJDK 8(7.1) | 7.1 的 jack-server 必须 JDK 8 |
| Python | 2.7 | repo、打包脚本都是 py2 |
| 交叉工具链 | arm-eabi-4.6 / arm-linux-androideabi-4.8 | 随 SDK prebuilts 提供,不要换 |
这张表里最容易翻车的是 JDK。Android 6.0.1 分支用 JDK 7 编得动,切到 7.1.2 分支如果还留着 JDK 7,jack-server 起不来,报“Failed to contact Jack server”。我一般两个分支各备一台机器,或者用 update-alternatives 切 JDK,别在同一台机器上反复改 JAVA_HOME 又忘了改回来。
2.2 装依赖:一条命令补齐 32 位库和编译工具
Ubuntu 16.04 上我用的依赖安装命令如下,14.04 把libncurses5-dev换成libncurses5-dev即可,其余基本一致:
sudo apt-get update sudo apt-get install -y \ git-core gnupg flex bison gperf build-essential \ zip curl zlib1g-dev gcc-multilib g++-multilib \ libc6-dev-i386 lib32ncurses5-dev x11proto-core-dev \ libx11-dev lib32z-dev ccache libgl1-mesa-dev \ libxml2-utils xsltproc unzip python2.7 openjdk-8-jdk这段命令的逻辑是:gcc-multilib和g++-multilib提供 32 位编译能力,因为 SDK 里不少 prebuilt 工具是 32 位 ELF;lib32ncurses5-dev、lib32z-dev是 32 位链接库,缺了会在编 U-Boot 的mkimage或打包工具时报“cannot execute binary file”;python2.7显式装上,因为 16.04 默认 python 可能指向 py3,而 repo 脚本 shebang 写的是python。装完用python --version确认是 2.7.x,不是就sudo update-alternatives --config python切过去。
JDK 部分单独说。Android 7.1 分支需要 JDK 8,装完确认:
java -version # 期望输出 openjdk version "1.8.0_xxx"如果机器上同时有 JDK 7 和 8,用update-alternatives --config java和--config javac切到 8。注意JAVA_HOME也要跟着改,jack-server 读的是环境变量,不是 alternatives 的软链。
2.3 目录规划与磁盘:源码放哪、留多少空间
SDK 解压后源码加编译产物轻松超过 60GB,我一般给/home单独留 120GB 以上,源码放在~/rk3229/sdk这种纯英文无空格路径下。路径里有中文或空格,repo 同步和 make 的某些脚本会莫名其妙失败,这是血泪经验。另外把 ccache 打开,export USE_CCACHE=1写进~/.bashrc,第二次全编能省一半时间。
提示:不要在 NTFS 挂载盘或共享文件夹里编译,文件权限和大小写敏感问题会让
mke2fs、make_ext4fs直接失败。
3. SDK 获取与整包编译:repo 同步、lunch 选择与 jack-server
环境齐了才动 SDK。RK3229 的 SDK 是 Rockchip 打包好的 repo 工程,通常以压缩包或内部 git 服务形式给到,指南 3.1 节只写了“SDK 获取”的入口,具体地址随项目走。拿到包之后先别急着 make,按下面的顺序走一遍,能避开大部分“编到一半挂掉”的情况。
3.1 解压与 repo 同步:先看分支再动手
假设 SDK 包解压到~/rk3229/sdk,里面应该有repo、.repo目录和RKDocs。如果是纯源码包没有.repo,直接跳到 3.2;如果是带.repo的工程,先确认 manifest 分支:
cd ~/rk3229/sdk repo init -u <manifest 地址> -b <分支名> # 地址和分支以实际 SDK 包内 README 为准 repo sync -j8 --no-tags-j8是并发数,按机器核数给,8 核给 8,16 核给 16,给太高反而因为磁盘 IO 卡住。--no-tags少拉标签,省时间。同步完成后repo status应该是干净的,如果有本地修改,先repo forall -c 'git reset --hard'清掉,别带着脏改动编译。
3.2 lunch 选择与整包编译:6.0.1 和 7.1.2 的差别
进入源码根目录,先 source 环境再 lunch:
source build/envsetup.sh lunch # 列表里选 rk3229_box-userdebug 或对应 7.1 的 rk3229_box-userdebuglunch 列表里会同时出现 6.0.1 和 7.1.2 的 target,名字相近,选错分支编出来的镜像烧进去可能起不来。选完lunch会打印TARGET_PRODUCT、TARGET_BUILD_VARIANT,确认 product 是 rk3229 系列再继续。
整包编译:
make -j8 # 或者分模块:make bootimage、make systemimage、make otapackage-j8同上按核数给。第一次全编 1 到 2 小时很正常,开了 ccache 第二次 20 到 40 分钟。编完产物在out/target/product/rk3229_box/下,关键文件是boot.img、system.img、recovery.img、parameter.txt,量产还要update.img。
3.3 jack-server 配置:Android 7.1 必过的一关
Android 7.1.2 分支编译时 jack-server 是绕不开的。默认配置下它监听本地端口,如果机器上已经有别的 jack 实例或者端口被占,会报:
Failed to contact Jack server: Problem reading .../jack-server-xxxx.log处理办法是改~/.jack-settings和~/.jack-server/config.properties,把SERVER_PORT_SERVICE和SERVER_PORT_ADMIN换成没被占用的端口,比如 8076 和 8077,然后:
./prebuilts/sdk/tools/jack-admin kill-server ./prebuilts/sdk/tools/jack-admin start-server再make一次。如果还报 JDK 版本不对,回到 2.2 节确认java -version是 1.8。jack-server 的日志在~/.jack-server/logs/,起不来先看那里,比瞎猜快。
3.4 固件烧写:Android 开发工具与量产工具的分工
编译产物出来后,单板调试用 Android 开发工具(RK 的 Windows 端烧写工具),量产用 8.9 节的量产工具。单板烧写步骤:板子进 loader 模式(按住 recovery 键上电或短接),工具识别到设备后加载parameter.txt、boot.img、system.img等分区文件,点“执行”烧写。烧完串口看 log,能过 U-Boot、进 kernel、起 Android 才算数。
注意:烧写前确认
parameter.txt里的分区大小和实际镜像匹配,system 分区给小了,烧写会报“download image failed”,或者烧进去后 Android 起不来。
4. U-Boot 与内核配置:DTS、WiFi/BT、GPIO 与 adb 默认打开
整包能编过只是第一步,板子能不能跑、外设能不能用,全在 U-Boot 和内核 DTS 的配置里。指南第 4、5 章把这些拆得很细,我按实际调试顺序挑几个必改项。
4.1 U-Boot 编译与 logo 配置
U-Boot 单独编译:
cd u-boot make rk3229_box_defconfig make -j8产物是u-boot.bin,打包进boot.img或单独烧到 loader 区。logo 相关配置在 4.5 节,改u-boot/include/configs/rk3229_box.h里的CONFIG_ROCKCHIP_BMP_LOGO和 logo 分区偏移。开机 logo 有大小限制,指南 4.5.2 提到限制描述,实际做法是把 bmp 控制在分区预留范围内,超了 U-Boot 会跳过 logo 直接黑屏,看着像“没显示”,其实是图太大。
4.2 DTS 改 WiFi/BT 与 GPIO:先对原理图再改节点
内核配置的核心是arch/arm/boot/dts/rk3229-box.dts。WiFi/BT 的配置在 5.2 节,典型改法是找到sdio节点和wireless-wlan节点,把status改成okay,并按模组 datasheet 填wifi_chip_type、clocks、interrupt-parent。GPIO 对应关系在 5.3 节特别提醒过:DTS 里的 GPIO 编号和原理图上的 bank 编号不是一回事,要按GPIOx_YN的换算规则算,算错了表现为“驱动加载了但中断不来”,log 里一堆 timeout。
&sdio { status = "okay"; max-frequency = <50000000>; /* 以下按实际 WiFi 模组 datasheet 填 */ };改完 DTS 重新make bootimage,烧kernel.img或boot.img,串口看dmesg | grep -i wifi有没有识别到模组。
4.3 USB 默认打开 adb 调试
指南 5.7 节专门写了 USB 默认打开 adb。做法是在 DTS 的usb节点或rk3229-box.dts里确认rockchip,usb-adb相关属性,或者在device/rockchip/rk3229/下的init.rc里确保persist.sys.usb.config默认包含adb。改完烧机,插 USB 到主机,adb devices能列出设备就说明生效。这一步对后面 logcat、dumpsys 调试是前提,别等出问题才回头补。
5. Android 常用配置与系统调试:分区、OTA、低内存与 Widevine
Android 层的配置项多且杂,指南第 6 章按功能列了十几项。我挑几个实际项目里改得最多、也最容易改错的:system 分区大小、odex 预编译、禁用 selinux、7.1 的低内存优化和 Widevine L1。
5.1 system 分区大小与 odex 预编译
system 分区大小在parameter.txt和device/rockchip/rk3229/BoardConfig.mk里两处要对上。parameter.txt里0x...@0x...的 system 分区长度改大,BOARD_SYSTEMIMAGE_PARTITION_SIZE同步改,否则编出来的system.img超过分区,烧写失败。odex 预编译在 3.2.6 节,改device/rockchip/rk3229/system.prop或BoardConfig.mk里的WITH_DEXPREOPT := true,能减少首次开机时间,但会占更多 system 空间,分区小的时候别开。
5.2 禁用 selinux 与 7.1 低内存优化
调试阶段经常要禁用 selinux,指南 6.10 节的做法是改BoardConfig.mk里BOARD_SELINUX_ENFORCING := false,或者内核 cmdline 加androidboot.selinux=permissive。量产前记得改回 enforcing,不然过不了某些认证。
Android 7.1 的低内存优化在 6.12 节,针对 512MB/1GB 内存的盒子,主要是调lowmemorykiller的 minfree 和ro.config.low_ram。改device/rockchip/rk3229/init.rc里的write /sys/module/lowmemorykiller/parameters/minfree值,按实际内存给,给太激进会频繁杀后台,给太松会 OOM。
5.3 Widevine L1 与 OTA 升级
Widevine L1 配置在 6.13 节,涉及vendor/widevine下的 keybox 和media.codec配置,属于需要授权文件的部分,没有 keybox 只能到 L3。OTA 升级在 6.7 节,make otapackage出ota_update.zip,放到/sdcard或 OTA 服务器,recovery 里手动或自动升级。OTA 包签名要和系统签名一致,否则升级校验失败。
5.4 系统调试三件套:adb、logcat、procrank
调试阶段最常用的是 7.1 到 7.4 节的工具。adb logcat -v time看运行日志,adb shell procrank看进程内存排名,adb shell dumpsys meminfo看整体内存。盒子卡顿先 procrank 找内存大户,再 dumpsys 看是不是 system_server 异常。这些工具在 userdebug 版本上默认可用,user 版本要确认ro.debuggable=1。
6. 避坑与排查:五条装环境时真踩过的坑
6.1 现象:编 U-Boot 报 “cannot execute binary file”
原因:主机缺 32 位运行库,SDK 里prebuilts/gcc下的工具链是 32 位 ELF。解决:回 2.2 节补lib32ncurses5-dev、lib32z-dev、gcc-multilib,file命令确认工具链是 ELF 32-bit 后再编。
6.2 现象:jack-server 起不来,日志报 JDK 版本不匹配
原因:Android 7.1 分支要求 JDK 8,机器上JAVA_HOME还指向 JDK 7。解决:update-alternatives切 java/javac 到 8,改~/.bashrc里JAVA_HOME,jack-admin kill-server后重启,再make。
6.3 现象:烧写报 “download image failed”,或烧完卡 logo
原因:parameter.txt分区大小和镜像不匹配,system 分区给小了最常见。解决:对照out/target/product/rk3229_box/system.img实际大小改parameter.txt和BOARD_SYSTEMIMAGE_PARTITION_SIZE,重新打包烧写。
6.4 现象:WiFi 驱动加载了但连不上,dmesg 里中断 timeout
原因:DTS 里 GPIO 编号按原理图 bank 直接填了,没做GPIOx_YN换算。解决:按 5.3 节规则重算 GPIO,改 DTS 对应节点,重编boot.img,dmesg | grep -i wifi确认中断注册成功。
6.5 现象:repo sync 到一半报错,或 make 报路径含非法字符
原因:源码放在中文路径、空格路径或 NTFS 挂载盘。解决:挪到~/rk3229/sdk这类纯英文 ext4 路径,repo forall -c 'git reset --hard'清脏改动后重新 sync。
7. 装完怎么验证:从串口 log 到 adb 的三层确认
环境装没装成,不看 make 有没有报错,看板子跑不跑得起来。我一般分三层验证,每层都有明确的通过标准,任何一层不过就停在那里查,不往下走。
第一层是串口 log。板子上电,串口工具(115200 8N1)抓 log,能依次看到 U-Boot 版本打印、Loading kernel、kernel 启动 log、init: starting service系列,最后停在 Android 的SurfaceFlinger或 launcher 起来。如果卡在 U-Boot 就查parameter.txt和 loader 烧写;卡在 kernel 早期就查 DTS 和 cmdline;卡在 init 就查init.rc和分区挂载。
第二层是 adb。系统起来后adb devices能列出设备,adb shell getprop ro.build.version.release返回 6.0.1 或 7.1.2,adb shell getprop ro.product.device返回 rk3229 系列。再跑adb shell dumpsys meminfo | head -20看内存是否正常,adb shell procrank看有没有异常进程吃内存。
第三层是功能抽检。WiFi 能扫到热点并连上,蓝牙能开,USB adb 稳定不掉线,播放一段 4K H.265 视频不花屏(对应 1.6 节的多媒体能力)。这三项过了,说明这套 SDK 编出来的镜像基本可用,可以进应用层开发。
| 验证层 | 命令/手段 | 通过标准 |
|---|---|---|
| 启动 | 串口 115200 | 过 U-Boot、kernel、init,进 launcher |
| 系统 | adb devices、getprop | 设备在线,版本/产品名正确 |
| 功能 | WiFi 连接、4K 播放 | 外设可用,视频不花屏 |
有个细节值得单独说:验证 Widevine 和 OTA 这类功能,别在第一次 bring-up 时就测,先把基础启动和 adb 跑通,再逐项加。我见过有人在系统还没稳定时就急着配 L1,结果 keybox 加载失败,误以为是配置写错,其实是 system 分区没挂对,白折腾两天。
从那以后我每次搭这类老 SDK 环境,都强制先跑一遍“串口 + adb + 4K 播放”三件套,任何一项不过就不碰应用层配置。这套习惯帮我省下的时间,比任何调试技巧都多。希望帮到你。
本文还有配套的精品资源,点击获取