2. 开发环境搭建:Ubuntu系统配置、ROS2 Humble安装、交叉编译工具链配置
说实话,嵌入式ROS开发最让人头疼的往往不是算法本身,而是环境搭建。我见过太多新手卡在这一步,一卡就是好几天。今天我就把这几年的经验捋一捋,带你把这套环境搭得明明白白。
2.1 Ubuntu系统配置——打好地基
我个人习惯用Ubuntu 22.04 LTS,原因很简单:ROS2 Humble官方推荐的就是这个版本。你想想看,官方测试最多的系统,坑自然最少。
系统要求速查表
| 项目 | 推荐配置 | 最低要求 |
|---|---|---|
| 操作系统 | Ubuntu 22.04 LTS | Ubuntu 20.04 |
| 内存 | 16GB | 8GB |
| 磁盘空间 | 80GB | 40GB |
| CPU | 4核以上 | 双核 |
装完系统后,第一件事就是换源。别问我为什么,你试试不换源装个ROS2,等半小时还在转圈,你就懂了。
# 备份原源
sudo cp /etc/apt/sources.list /etc/apt/sources.list.bak
# 替换为清华源(我个人最常用)
sudo sed -i 's/archive.ubuntu.com/mirrors.tuna.tsinghua.edu.cn/g' /etc/apt/sources.list
sudo sed -i 's/security.ubuntu.com/mirrors.tuna.tsinghua.edu.cn/g' /etc/apt/sources.list
# 更新
sudo apt update && sudo apt upgrade -y
小技巧:我习惯装完系统先装这几个包——vim、git、curl、net-tools。别小看它们,后面调试的时候能省不少事。
2.2 ROS2 Humble安装——别踩这些坑
ROS2 Humble是2022年5月发布的,到现在已经很稳定了。我在项目里用了大半年,基本没出过什么幺蛾子。
安装过程其实就三步,但每一步都有坑。我一个个说。
2.2.1 设置语言环境
这一步很多人会跳过,结果后面编译时一堆乱码错误。嗯,这里要注意:
sudo apt install locales
sudo locale-gen en_US en_US.UTF-8
sudo update-locale LC_ALL=en_US.UTF-8 LANG=en_US.UTF-8
export LANG=en_US.UTF-8
2.2.2 添加ROS2源
记得先装curl和gnupg,不然会报错。我曾经在这卡了半小时,后来发现是没装gnupg。
sudo apt install curl gnupg lsb-release
sudo curl -sSL https://raw.githubusercontent.com/ros/rosdistro/master/ros.key -o /usr/share/keyrings/ros-archive-keyring.gpg
echo "deb [arch=$(dpkg --print-architecture) signed-by=/usr/share/keyrings/ros-archive-keyring.gpg] http://packages.ros.org/ros2/ubuntu $(lsb_release -cs) main" | sudo tee /etc/apt/sources.list.d/ros2.list > /dev/null
sudo apt update
2.2.3 安装ROS2 Humble
这里有两个选择:桌面版和基础版。我建议你装桌面版,因为包含了可视化工具,调试时很有用。
# 桌面版(推荐)
sudo apt install ros-humble-desktop
# 或者基础版(仅命令行)
# sudo apt install ros-humble-ros-base
注意:安装过程可能会提示你安装一些依赖包,比如python3-colcon-common-extensions。别犹豫,直接装。我见过有人跳过依赖,结果编译工作空间时报错,又回头补装。
2.2.4 配置环境变量
装完别忘了配置环境变量。我习惯把它写到.bashrc里,这样每次打开终端自动生效。
echo "source /opt/ros/humble/setup.bash" >> ~/.bashrc
source ~/.bashrc
验证一下是否安装成功:
ros2 run demo_nodes_cpp talker
如果看到"Hello World"在刷屏,恭喜你,装好了。
2.3 交叉编译工具链配置——嵌入式开发的核心
交叉编译,说白了就是在PC上编译出能在ARM板子上跑的程序。我刚开始做嵌入式ROS时,总觉得直接在板子上编译不就行了?后来发现,板子那点算力,编译一个功能包能等半小时。嗯,从那以后我再也不敢偷懒了。
2.3.1 安装交叉编译工具链
以ARM Cortex-A系列为例,我常用的是gcc-arm-9.2-2019.12-x86_64-arm-none-linux-gnueabihf。为什么选这个?因为我在项目里实测过,兼容性最好。
# 下载工具链
wget https://developer.arm.com/-/media/Files/downloads/gnu-a/9.2-2019.12/binrel/gcc-arm-9.2-2019.12-x86_64-arm-none-linux-gnueabihf.tar.xz
# 解压到指定目录
sudo tar -xf gcc-arm-9.2-2019.12-x86_64-arm-none-linux-gnueabihf.tar.xz -C /opt/
# 配置环境变量
echo 'export PATH=$PATH:/opt/gcc-arm-9.2-2019.12-x86_64-arm-none-linux-gnueabihf/bin' >> ~/.bashrc
source ~/.bashrc
# 验证
arm-none-linux-gnueabihf-gcc --version
2.3.2 配置ROS2交叉编译环境
这里有个关键点:ROS2的交叉编译需要用到toolchain文件。说白了就是告诉编译器:目标平台是什么、头文件在哪、库文件在哪。
我写了一个通用的toolchain文件,你可以直接拿来用:
# 创建toolchain文件
cat > ~/ros2_ws/toolchain.cmake << 'EOF'
set(CMAKE_SYSTEM_NAME Linux)
set(CMAKE_SYSTEM_PROCESSOR arm)
# 指定交叉编译器
set(CMAKE_C_COMPILER /opt/gcc-arm-9.2-2019.12-x86_64-arm-none-linux-gnueabihf/bin/arm-none-linux-gnueabihf-gcc)
set(CMAKE_CXX_COMPILER /opt/gcc-arm-9.2-2019.12-x86_64-arm-none-linux-gnueabihf/bin/arm-none-linux-gnueabihf-g++)
# 指定sysroot(目标系统的根文件系统)
set(CMAKE_SYSROOT /opt/ros2_humble_sysroot)
# 查找工具链中的程序
set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER)
set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY)
set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY)
set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY)
EOF
关键点:CMAKE_SYSROOT指向的是目标板子的根文件系统。你需要把板子上的/usr、/opt等目录拷贝到PC上,或者用QEMU模拟。我一般用rsync同步:
rsync -avz root@板子IP:/ /opt/ros2_humble_sysroot/
2.3.3 编译测试
配置好之后,就可以交叉编译ROS2功能包了。我习惯用colcon,加上--cmake-args参数指定toolchain文件:
cd ~/ros2_ws
colcon build \
--cmake-args \
-DCMAKE_TOOLCHAIN_FILE=toolchain.cmake \
-DCMAKE_BUILD_TYPE=Release
避坑指南:我曾经在编译时遇到"找不到rosidl_typesupport"的错误。后来发现是sysroot里缺少ROS2的安装文件。解决办法:在板子上完整安装一遍ROS2 Humble,然后再同步sysroot。
2.4 验证环境——跑个例子试试
环境搭好了,总得验证一下。我一般写个简单的发布订阅程序,在PC上编译,然后拷到板子上跑。
# PC端交叉编译
cd ~/ros2_ws
colcon build --packages-select my_test_pkg --cmake-args -DCMAKE_TOOLCHAIN_FILE=toolchain.cmake
# 把编译好的文件拷到板子上
scp install/my_test_pkg/lib/libmy_test_pkg.so root@板子IP:/opt/ros2_humble/lib/
# 板子上运行
ssh root@板子IP
source /opt/ros/humble/setup.bash
ros2 run my_test_pkg my_test_node
如果能看到节点正常运行,说明你的环境搭建成功了。
最后提醒一句:交叉编译时,一定要注意目标板子的架构。ARMv7和ARMv8的指令集不同,编译选项也不一样。我见过有人用ARMv7的工具链去编译ARMv8的程序,结果跑起来直接段错误。
好了,环境搭建这部分就到这里。下一章我们聊聊ROS2的节点通信机制,那才是真正有意思的东西。