第三章 开发环境搭建:交叉编译工具链安装、系统烧录、SSH远程连接与文件传输、基础SDK验证
说实话,嵌入式开发的第一步往往是最劝退的。我记得刚入行那会儿,光配环境就折腾了整整两天。后来带新人时发现,十个人里有八个卡在这一步。所以这一章,咱们就把这些「脏活累活」一次讲透。
3.1 交叉编译工具链:为什么非得「交叉」?
你想想看,你的电脑是 x86 架构,而嵌入式板子通常是 ARM 架构。x86 编译出来的程序,ARM 根本跑不了。所以我们需要在 PC 上装一个「能生成 ARM 机器码的编译器」——这就是交叉编译工具链。
我个人习惯用 Linaro 提供的 GCC 工具链,稳定且社区活跃。以 ARM Cortex-A 系列为例,下载地址一般是:
https://releases.linaro.org/components/toolchain/binaries/
选择对应版本,比如 gcc-linaro-7.5.0-2019.12-x86_64_arm-linux-gnueabihf.tar.xz。解压后配置环境变量:
tar -xvf gcc-linaro-7.5.0-2019.12-x86_64_arm-linux-gnueabihf.tar.xz
sudo mv gcc-linaro-7.5.0-2019.12-x86_64_arm-linux-gnueabihf /opt/
export PATH=$PATH:/opt/gcc-linaro-7.5.0-2019.12-x86_64_arm-linux-gnueabihf/bin
验证是否安装成功:
arm-linux-gnueabihf-gcc --version
如果看到版本号输出,恭喜你,第一步走通了。
3.2 系统烧录:把系统「灌」进板子
拿到一块空板子,第一件事就是烧录系统。市面上常见的烧录方式有几种:SD 卡烧录、USB OTG 烧录、以及通过网络烧录。我个人最常用的是 SD 卡烧录,因为简单粗暴。
以 Raspberry Pi 或类似的 ARM 板为例,步骤大致如下:
- 准备一张 16GB 以上的 SD 卡(建议 Class 10 以上)
- 下载板子对应的系统镜像,比如 Ubuntu 或 Buildroot 生成的
.img文件 - 使用
dd命令或 balenaEtcher 工具写入 SD 卡
用 dd 命令时一定要小心:
sudo dd if=ubuntu-20.04.3-preinstalled-server-armhf.img of=/dev/sdb bs=4M status=progress
of= 后面是设备名,不是分区名。比如 /dev/sdb 而不是 /dev/sdb1。写错了可能会把你的硬盘数据清空,别问我怎么知道的。
烧录完成后,把 SD 卡插入板子,上电。如果板子有 HDMI 接口,接上显示器看看启动日志。没有显示器也没关系,我们接下来用串口或 SSH 连接。
3.3 SSH 远程连接:告别显示器和键盘
嵌入式开发中,板子通常没有显示器。你总不能每次都搬个显示器过去吧?所以 SSH 是必备技能。
首先,确保板子和 PC 在同一个局域网内。可以通过路由器,或者直接用网线直连。我个人习惯用路由器,因为 DHCP 会自动分配 IP。
查看板子的 IP 地址:
ifconfig
# 或者
ip addr show
然后在 PC 上执行:
ssh username@192.168.1.100
默认密码一般是 root 或 admin,具体看你的系统镜像。
ssh-keygen 生成密钥对,然后把公钥传到板子上:ssh-copy-id username@192.168.1.100。这样以后连接就一键直达了。
3.4 文件传输:把代码「扔」到板子上
代码在 PC 上写好,怎么传到板子上?常用的方法有三种:
| 方法 | 命令 | 适用场景 |
|---|---|---|
| SCP | scp file username@ip:/path/ |
单个文件或少量文件 |
| SFTP | sftp username@ip |
交互式传输,支持目录 |
| NFS | 挂载远程目录 | 开发阶段频繁修改代码 |
我个人的工作流是这样的:开发阶段用 NFS 挂载,代码在 PC 上修改后,板子上直接运行。调试稳定后,再用 SCP 把最终版本传到板子上。
配置 NFS 稍微麻烦一点,但值得。在 PC 上安装 NFS 服务器:
sudo apt install nfs-kernel-server
sudo mkdir /home/user/nfs_share
sudo chmod 777 /home/user/nfs_share
echo "/home/user/nfs_share *(rw,sync,no_subtree_check)" | sudo tee -a /etc/exports
sudo exportfs -a
sudo systemctl restart nfs-kernel-server
在板子上挂载:
sudo mount -t nfs 192.168.1.2:/home/user/nfs_share /mnt
sync 一下,或者重新挂载。
3.5 基础 SDK 验证:跑通第一个程序
环境搭好了,总得验证一下能不能用。写一个最简单的 Hello World:
// hello.c
#include <stdio.h>
int main() {
printf("Hello from ARM board!\n");
return 0;
}
用交叉编译器编译:
arm-linux-gnueabihf-gcc hello.c -o hello
把编译好的文件传到板子上:
scp hello username@192.168.1.100:/home/username/
在板子上运行:
./hello
如果看到 Hello from ARM board!,说明整个开发环境已经打通了。
3.6 避坑指南:我踩过的那些坑
- 工具链版本不匹配: 我曾经用 GCC 8.3 编译的程序,在只支持 GCC 7.5 的板子上跑,结果段错误。后来我养成了习惯:板子用什么版本的 GCC,我就用什么版本的工具链。
- 烧录时写错设备: 有一次我急着下班,把
of=/dev/sda写成了of=/dev/sda1,结果系统直接挂了。从那以后,我每次烧录前都会用lsblk确认三遍。 - SSH 连接超时: 板子启动后,SSH 连不上。排查了半天,发现是板子的防火墙没关。用
sudo ufw disable解决。 - NFS 权限问题: 挂载后无法写入,检查发现是
/etc/exports里忘了加rw选项。
嗯,这些坑我都踩过。你遇到了也别慌,一步步排查,总能解决。
下一章,我们会开始搭建嵌入式 Linux 系统,从 Bootloader 到内核,再到根文件系统。到时候你会发现,今天配的环境,就是后面所有工作的基石。