10 编译与测试
对应源码:../slam_toolbox(ros2 分支,包版本 2.10.0)。
本机环境:Ubuntu 22.04 · ROS 2 Humble · CMake 3.22 · Ceres 2.0.0。
官方 ros2 分支默认对着 Jazzy / Ubuntu 24.04 / Ceres ≥ 2.1。在 Humble 上能编过,是本仓库加过兼容层,不是上游原样。系统 apt 仍是 2.6.10(launch 还不是 Lifecycle),编完必须 overlay,不要和 apt 包混用。
10.1 工作空间
colcon 在仓库根目录,不在 third_party/slam_toolbox 里直接 cmake:
1 2 3 4 5 6
| slamDev/ ├── src/slam_toolbox → ../third_party/slam_toolbox ├── build/ gitignore ├── install/ gitignore ├── log/ gitignore └── third_party/slam_toolbox/ 源码(含本机 Humble 补丁)
|
建软链(已做过可跳过):
1 2 3
| cd /home/cp/work2/slamDev mkdir -p src ln -sfn ../third_party/slam_toolbox src/slam_toolbox
|
build/ install/ log/ 已在仓库 .gitignore。
10.2 依赖
ros-humble-desktop + 本机已装的求解库即可。缺包时:
1 2 3 4 5 6 7 8 9
| source /opt/ros/humble/setup.bash sudo apt update sudo apt install -y \ libceres-dev libsuitesparse-dev liblapack-dev libomp-dev libtbb-dev \ libboost-serialization-dev libboost-filesystem-dev libboost-thread-dev \ qtbase5-dev libqt5-core5a \ ros-humble-nav2-map-server ros-humble-interactive-markers \ ros-humble-rviz-common ros-humble-rviz-default-plugins \ python3-colcon-common-extensions
|
或:
1 2 3
| cd /home/cp/work2/slamDev source /opt/ros/humble/setup.bash rosdep install --from-paths src --ignore-src -r -y
|
核对:
| 项 |
本机当时 |
| ROS |
Humble(/opt/ros/humble) |
| CMake |
3.22.1(不认识 CMP0167) |
| Ceres |
2.0.0(没有 autodiff_manifold.h) |
| apt slam_toolbox |
2.6.10 |
10.3 Humble 兼容(本树已改)
2.10 原样在 Humble 上会失败。本仓库改动如下,再编不用手改:
| 失败点 |
文件 |
处理 |
Policy CMP0167 is not known |
lib/karto_sdk/CMakeLists.txt |
if(POLICY CMP0167) 再 SET |
tf2_sensor_msgs::tf2_sensor_msgs 不存在 |
CMakeLists.txt |
Humble 头文件包,补 INTERFACE target |
ceres/autodiff_manifold.h 找不到 |
solvers/ceres_utils.h 等 |
Ceres < 2.1 走 LocalParameterization |
message_filters::Subscriber 不接 LifecycleNode + SensorDataQoS |
slam_toolbox_common.* |
SLAM_TOOLBOX_HUMBLE_COMPAT:rmw_qos_profile_sensor_data |
CMake 在 ROS_DISTRO=humble 时定义 SLAM_TOOLBOX_HUMBLE_COMPAT。换 Jazzy 编同一棵树时不要带这个宏,走上游 API。
10.4 编译
1 2 3 4 5 6
| cd /home/cp/work2/slamDev source /opt/ros/humble/setup.bash colcon build --packages-select slam_toolbox \ --allow-overriding slam_toolbox \ --symlink-install \ --cmake-args -DCMAKE_EXPORT_COMPILE_COMMANDS=ON
|
--allow-overriding 必须加:underlay 里已有 apt 的同名包。
C++17,CMakeLists.txt 默认 Release。首次大约 5 分钟。
只改过某个 .cpp 时同样命令即可,--symlink-install 下 launch / yaml 改完不用重编。
成功时:
1 2
| Finished <<< slam_toolbox Summary: 1 package finished
|
产物:
1 2 3 4 5 6 7 8
| install/slam_toolbox/lib/slam_toolbox/ async_slam_toolbox_node sync_slam_toolbox_node localization_slam_toolbox_node lifelong_slam_toolbox_node map_and_localization_slam_toolbox_node decentralized_multirobot_slam_toolbox_node merge_maps_kinematic
|
库:install/slam_toolbox/lib/libtoolbox_common.so、libkartoSlamToolbox.so、libceres_solver_plugin.so、libSlamToolboxPlugin.so。
跳转定义:把 build/slam_toolbox/compile_commands.json 链到源码根(已链过可跳过):
1 2
| ln -sfn /home/cp/work2/slamDev/build/slam_toolbox/compile_commands.json \ /home/cp/work2/slamDev/third_party/slam_toolbox/compile_commands.json
|
IDE / clangd Reload Window。
10.5 环境(overlay)
每个新终端:
1 2
| source /opt/ros/humble/setup.bash source /home/cp/work2/slamDev/install/setup.bash
|
确认吃到的是 2.10,不是 apt 2.6:
1 2 3 4 5
| ros2 pkg prefix slam_toolbox
ros2 pkg executables slam_toolbox
|
10.6 仓库自带测试
CMakeLists.txt 里 gtest 整段注释掉了,colcon test --packages-select slam_toolbox 现在几乎无用例。
test/lifelong_metrics_test.cpp 测 lifelong 的包围盒 / IoU,不是建图正确性。要跑:先取消这段注释,再:
1 2 3 4 5 6
| cd /home/cp/work2/slamDev source /opt/ros/humble/setup.bash colcon build --packages-select slam_toolbox --allow-overriding slam_toolbox \ --cmake-args -DBUILD_TESTING=ON colcon test --packages-select slam_toolbox colcon test-result --verbose
|
test/process_constraints.py 是画「节点约束数」的离线脚本,要先在 publishGraph 里加它注释里的打印,不是 CI。
10.7 冒烟:包与节点
不接雷达,只确认 overlay 和可执行文件:
1 2 3 4 5 6 7
| source /opt/ros/humble/setup.bash source /home/cp/work2/slamDev/install/setup.bash
test "$(ros2 pkg prefix slam_toolbox)" = "/home/cp/work2/slamDev/install/slam_toolbox" && echo "overlay OK"
ros2 run slam_toolbox async_slam_toolbox_node --ros-args --params-file \ $(ros2 pkg prefix slam_toolbox)/share/slam_toolbox/config/mapper_params_online_async.yaml
|
Lifecycle 节点起来后停在 unconfigured(没有 launch 的 configure/activate)。另开终端:
1 2 3 4 5
| source /opt/ros/humble/setup.bash source /home/cp/work2/slamDev/install/setup.bash ros2 lifecycle list /slam_toolbox ros2 lifecycle set /slam_toolbox configure
|
看到 CeresSolver: Using ... 或 SlamToolbox: ... 日志,说明插件和公共层加载成功。
10.8 冒烟:launch(需要 scan + TF)
2.10 的 launch 是 Lifecycle:autostart:=true 时自动 configure → activate。
最低输入:
/scan(sensor_msgs/LaserScan)
- TF
odom → base_frame(默认 base_footprint,按 YAML 改)
- 雷达相对 base 的
tf_static
仿真 / bag 记得 use_sim_time:=true,并先播 /clock。
1 2 3 4 5 6 7 8 9
| source /opt/ros/humble/setup.bash source /home/cp/work2/slamDev/install/setup.bash
ros2 launch slam_toolbox online_async_launch.py \ use_sim_time:=true \ autostart:=true
|
其它入口:
| launch |
节点 |
场景 |
online_async_launch.py |
async_slam_toolbox_node |
在线建图(先跑这个) |
online_sync_launch.py |
sync_slam_toolbox_node |
bag 回放不丢帧 |
localization_launch.py |
localization_slam_toolbox_node |
已有 .posegraph |
offline_launch.py |
sync + 离线 YAML |
离线建图 |
merge_maps_kinematic_launch.py |
merge_maps_kinematic |
刚体拼图,不是匹配 |
通过标准(async 建图):
ros2 topic hz /map 有输出(有订阅者时才更新,RViz 订 /map)
ros2 topic echo /tf --once 里有 map → odom
ros2 topic echo /pose --once 有位姿
- 转一圈墙角大致对齐,没有整图拧成麻花(回环阈值另见 08)
存图:
1 2 3 4 5 6 7
| ros2 service call /slam_toolbox/serialize_map slam_toolbox/srv/SerializePoseGraph \ "{filename: '/tmp/test_map'}"
ros2 service call /slam_toolbox/save_map slam_toolbox/srv/SaveMap \ "{name: {data: '/tmp/test_map'}}"
|
定位模式:YAML 里填 map_file_name,或启动后再 deserialize_map。RViz 2D Pose Estimate 发 /initialpose。
10.9 对照实验(建议新手做)
改一个量,看图怎么变;比空跑 gtest 有用:
| 动作 |
预期 |
use_scan_matching: false |
图跟着里程计漂 |
do_loop_closing: false |
绕回起点对不齐 |
| async 换 sync + bag |
不丢帧,CPU 可能更高 |
不播 odom→base |
MessageFilter 一直等,不加节点 |
| 不 overlay,直接用 apt launch |
2.6 行为,和这份源码对不上 |
10.10 编译失败对照
| 现象 |
原因 |
处理 |
提示加 --allow-overriding slam_toolbox |
apt 已占包名 |
加上该参数 |
CMP0167 is not known |
CMake < 3.30 |
确认 karto 的 if(POLICY CMP0167) 还在 |
tf2_sensor_msgs::... was not found |
Humble 无该 target |
确认 CMakeLists.txt 里 INTERFACE 补丁 |
autodiff_manifold.h |
Ceres 2.0 |
确认 ceres_utils.h 的版本分支 |
Subscriber / SensorDataQoS 编译错 |
没带 Humble 宏 |
echo $ROS_DISTRO 为 humble 后再 colcon |
ros2 pkg prefix 仍是 /opt/ros/humble |
没 source install |
先 humble 再 overlay |
和系统节点抢 /map、map→odom |
同时开了 apt 节点 |
只留 overlay 这一份 |
| SSH 不能跳转到定义 |
无 compile_commands.json |
见 10.4,Reload Window |
清掉重编:
1 2
| cd /home/cp/work2/slamDev rm -rf build/slam_toolbox install/slam_toolbox log
|
不要 rm -rf build 整个目录,除非没有其它包。
10.11 和二次开发的关系
- 改 YAML / launch:
--symlink-install 后直接 relaunch。
- 改
src/、solvers/、karto_sdk:按 10.4 重编,再 overlay。
- 上实车若只用 apt 2.6.10:不要用 2.10 的 Lifecycle launch 去喂系统包。
- 读码顺序仍见 09。编译只保证「能跑」,不代替沿
Process() 走一帧。