【ROS2有线多机通讯】基于CycloneDDS的有线组网与发现机制优化
·
前言
- 前几期我们同时在RDKX5上部署了双激光雷达融合和双摄像头推理
- 很明显出现的一个情况就是当车上同时启动多激光雷达和多摄像机的时候,由于RDKX5的4个USB接口同时共用一条总线,导致总线带宽与供电压力瞬间达到上限,从而触发USB 设备(包括网卡驱动)整体重连甚至系统级掉线。
- 典型内核日志如下:
5usb 1-1.2: clear tt 1 (90d2) error -71
usb 1-1: USB disconnect, device number 2
usb 1-1.1: USB disconnect, device number 3
uvcvideo ... Failed to resubmit video URB (-19)
cdc_ncm ... unregister 'cdc_ncm'
rndis_host ... unregister 'rndis_host'
- 那么为了解决上述问题,我们计划使用两块 RDKX5 分别承担不同计算负载,并通过 ROS2 DDS 进行多机通信。
1 ROS2多机通讯
1-1 无线通讯
- 在 ROS2 中,多机通信本质上依赖 DDS(Data Distribution Service)的自动发现机制。
- 只要满足以下条件,即可实现节点自动发现与话题互通。
- 所有设备处于同一局域网
- 使用相同的
ROS_DOMAIN_ID
- 在所有设备上统一配置:
export ROS_DOMAIN_ID=10
- 可以看到各个设备上都能直接进行话题通讯

1-2 局限
- 但是考虑到局域网网络波动以及数据传输延迟等因素,我们这里使用网线直接将两块RDKX5直接相连,然后通过网线配置静态ip的方式,配合ROS2配置CycloneDDS实现有线通讯。
2 网线配置静态ip
2-1 绑定有线网口
- 我们分别在两块板子上设置
sudo ip addr flush dev eth0
sudo ip addr add 192.168.10.1/24 dev eth0
sudo ip link set eth0 up
- 另一块板子
sudo ip addr flush dev eth0
sudo ip addr add 192.168.10.2/24 dev eth0
sudo ip link set eth0 up
2-2 测试
- 可以使用下述命令测试绑定的ip
ip addr show eth0

- 然后我们可以通过ping的方式测试是否能访问到另一快板子
ping 192.168.10.2

3 ROS2配置CycloneDDS
3-1 DDS
- DDS(Data Distribution Service)是 ROS2 的底层通信中间件标准,用于实现节点之间的发布/订阅通信机制。与 ROS1 依赖中心化 Master 不同,ROS2 采用 DDS 实现去中心化通信架构。
- DDS 的核心特点包括:
- 去中心化通信:节点自动发现,无需中心服务器
- 发布/订阅模型:数据生产者与消费者解耦
- 基于 QoS 策略:支持可靠性、延迟、历史缓存等配置
- 跨网络通信能力:支持局域网甚至跨域通信(需配置)
- 常见 DDS 实现包括:
| DDS 实现 | 特点 |
|---|---|
| Fast DDS | 默认实现,生态成熟 |
| CycloneDDS | 轻量、低延迟、配置灵活 |
| RTI Connext | 工业级,高性能但商业授权 |
3-2 CycloneDDS
- CycloneDDS 是 ROS2 官方支持的 DDS 实现之一,特点是轻量、高性能、可配置性强,非常适合嵌入式平台(如 RDKX5)和多机系统部署。
- 安装:
sudo apt install ros-humble-rmw-cyclonedds-cpp
- 安装后只需设置环境变量即可切换 DDS 实现:
export RMW_IMPLEMENTATION=rmw_cyclonedds_cpp
- 可以检查自己是否成功设置了:
echo $RMW_IMPLEMENTATION

3-3 CycloneDDS配置文件
- CycloneDDS 支持通过 XML 文件进行网络优化配置
- 我们分别在两个RDKX5的任意位置新建
cyclonedds.xml(需要记住路径,后面要使用,以本教程为例子,放置在/root/cyclonedds.xml) - 然后我们添加如下内容:
<?xml version="1.0" encoding="UTF-8" ?>
<CycloneDDS xmlns="https://cdds.io/config" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="https://cdds.io/config https://raw.githubusercontent.com/eclipse-cyclonedds/cyclonedds/master/etc/cyclonedds.xsd">
<Domain Id="10">
<General>
<Interfaces>
<NetworkInterface name="eth0"/>
</Interfaces>
<AllowMulticast>false</AllowMulticast>
</General>
<Discovery>
<Peers>
<Peer Address="192.168.10.1"/>
<Peer Address="192.168.10.2"/>
</Peers>
<ParticipantIndex>auto</ParticipantIndex>
</Discovery>
<Tracing>
<Verbosity>config</Verbosity>
<OutputFile>cdds.log.${CYCLONEDDS_PID}</OutputFile>
</Tracing>
</Domain>
</CycloneDDS>
<Domain Id="10">该配置适用于所有 DDS Domain,配合前面说的ROS_DOMAIN_ID使用<NetworkInterface name="eth0"/>强制指定 DDS 使用 eth0 网卡通信<AllowMulticast>false</AllowMulticast>关闭 DDS multicast(组播发现机制)Discovery为节点发现机制<Peer Address="192.168.10.1"/>手动指定 DDS 通信对端节点,替代 multicast 自动发现机制<ParticipantIndex>auto</ParticipantIndex>自动分配 DDS participant index
<Verbosity>config</Verbosity>为日志级别设为 config
3-4 加载配置
- 我们同一加载下述配置,可以把下述内容写在
.bashrc里头
export ROS_DOMAIN_ID=10
export RMW_IMPLEMENTATION=rmw_cyclonedds_cpp
export CYCLONEDDS_URI=file://$HOME/cyclonedds.xml
- 然后我们再次运行发布与订阅节点
ros2 run demo_nodes_cpp talker
- 远端和本地同时打开监听节点,可以看到由于走了有线DDS,本地自然就无法进行访问了。
ros2 run demo_nodes_cpp listener

3-5 bashrc同一配置
- 板子A:
sudo ip addr flush dev eth0
sudo ip addr add 192.168.10.1/24 dev eth0
sudo ip link set eth0 up
export ROS_DOMAIN_ID=10
export RMW_IMPLEMENTATION=rmw_cyclonedds_cpp
export CYCLONEDDS_URI=file://$HOME/cyclonedds.xml
- 板子B:
sudo ip addr flush dev eth0
sudo ip addr add 192.168.10.2/24 dev eth0
sudo ip link set eth0 up
export ROS_DOMAIN_ID=10
export RMW_IMPLEMENTATION=rmw_cyclonedds_cpp
export CYCLONEDDS_URI=file://$HOME/cyclonedds.xml
3-6 本地无法访问Rviz2的解决措施
- 通过上述配置,两块RDKX5进行静态IP进行DDS通讯的时候本地是无法像以前一样通过DDS访问到车上的
topic的,因此解决方式是两块RDKX5至少有一个使用桌面端,然后通过x11转发的方式回传RVIZ2- 这个可以参考之前写的文章【Linux-SSH远程窗口回传】使用X11或Wayland进行SSH窗口转发
ssh -cx root@192.168.3.3
总结
- 本文围绕 RDKX5 双机ROS2通信系统的搭建过程,完成了从网络层到DDS层的整体配置设计。在网络层通过对两块设备分别配置静态 IP(192.168.10.1 / 192.168.10.2)并启用 eth0 有线直连,实现稳定局域网通信。在 ROS2 层统一设置
ROS_DOMAIN_ID=10并切换至 CycloneDDS 实现通信中间件统一。进一步通过 XML 配置文件对 CycloneDDS进行定制,包括指定通信网卡为 eth0、关闭 multicast 组播发现机制、使用 Peer 方式手动定义通信节点,并启用自动 ParticipantIndex 分配。同时结合日志系统输出配置,实现多节点通信过程的可观测性。最终构建出基于有线网络的 ROS2 多机 DDS 通信架构,实现节点间稳定的发布/订阅数据交互。 - 如有错误,欢迎支持!
- 感谢大家的支持!

AtomGit 是由开放原子开源基金会联合 CSDN 等生态伙伴共同推出的新一代开源与人工智能协作平台。平台坚持“开放、中立、公益”的理念,把代码托管、模型共享、数据集托管、智能体开发体验和算力服务整合在一起,为开发者提供从开发、训练到部署的一站式体验。
更多推荐
所有评论(0)