一、什么是交叉编译
交叉编译是指在一种平台上编译另一种平台运行的程序。比如在 x86_64 Ubuntu 电脑上编译 ARM 开发板运行的程序。
常见组合:
1 | 开发机:x86_64 Linux |
为什么需要交叉编译:
- 开发板性能弱,编译慢。
- 开发板存储小,不适合安装完整工具链。
- CI/CD 通常运行在服务器上。
- 需要统一构建环境。
二、确认目标架构
在开发板上查看:
1 | uname -m |
常见输出:
1 | armv7l |
查看系统 ABI:
1 | file /bin/sh |
输出里会包含架构、位数、动态链接器等信息。
三、交叉编译器命名
常见工具链前缀:
1 | arm-linux-gnueabihf- |
区别:
arm-linux-gnueabihf:ARM Linux,硬浮点 ABI。aarch64-linux-gnu:64 位 ARM Linux。arm-none-eabi:裸机或 RTOS,通常没有 Linux。
查看编译器:
1 | arm-linux-gnueabihf-gcc --version |
Ubuntu 安装示例:
1 | sudo apt install -y gcc-arm-linux-gnueabihf g++-arm-linux-gnueabihf |
四、最小交叉编译
hello.c:
1 |
|
编译 ARM 32 位:
1 | arm-linux-gnueabihf-gcc hello.c -o hello_arm |
检查文件:
1 | file hello_arm |
复制到开发板:
1 | scp hello_arm root@192.168.1.100:/tmp/ |
开发板运行:
1 | chmod +x /tmp/hello_arm |
五、CMake 工具链文件
创建 toolchain-armhf.cmake:
1 | set(CMAKE_SYSTEM_NAME Linux) |
构建:
1 | cmake -S . -B build-arm -DCMAKE_TOOLCHAIN_FILE=toolchain-armhf.cmake |
六、项目结构建议
1 | embedded-app/ |
scripts/build-arm.sh:
1 |
|
scripts/deploy.sh:
1 |
|
七、动态库问题
交叉编译后复制到开发板运行,可能出现:
1 | No such file or directory |
明明文件存在,为什么提示不存在?常见原因是动态链接器或依赖库不匹配。
检查:
1 | file app |
查看依赖:
1 | arm-linux-gnueabihf-readelf -d app |
在开发板上:
1 | ldd ./app |
如果依赖库不存在,需要把库一起部署,或者使用目标板对应的 sysroot 编译。
八、sysroot
sysroot 是目标系统根目录的一个镜像,里面包含目标板的头文件和库。
常见来源:
- SDK 提供。
- 从开发板复制。
- Buildroot / Yocto 生成。
使用 sysroot:
1 | set(CMAKE_SYSROOT /opt/arm-sysroot) |
编译器会从 sysroot 里找目标平台的头文件和库,避免错误链接到开发机库。
九、部署方式
常见方式:
scp复制单个程序。- 打包 tar.gz。
- 制作 deb/rpm 包。
- 放进 rootfs 镜像。
- OTA 升级。
入门阶段建议先用 scp,流程简单,便于快速验证。
1 | scp build-arm/app root@board:/tmp/ |
稳定后再考虑系统化部署。
十、常见问题
10.1 Exec format error
架构不匹配。例如把 x86 程序放到 ARM 板运行。
检查:
1 | file app |
10.2 GLIBC 版本不匹配
开发机工具链生成的程序依赖较新 glibc,目标板系统太旧。
解决:
- 使用板厂 SDK。
- 使用和目标板一致的 sysroot。
- 使用 Buildroot/Yocto 统一生成工具链和系统。
10.3 找不到动态库
检查:
1 | ldd ./app |
临时:
1 | LD_LIBRARY_PATH=./lib ./app |
长期:
- 安装库到系统路径。
- 配置动态链接器。
- 部署启动脚本。
十一、总结
嵌入式交叉编译的核心不是会敲一条编译命令,而是保证工具链、目标架构、sysroot、动态库和部署环境一致。
一旦出现运行失败,优先检查:
1 | file -> readelf -> ldd -> sysroot -> 目标板系统版本 |
这条链路能解决大部分交叉编译入门问题。
- 本文链接: https://blog.hansong.icu/2026/06/21/Embedded_Dev_Cross_Compile_CMake/
- 版权声明: 本博客所有文章除特别声明外,均默认采用 CC BY-NC-SA 4.0 许可协议。