ROS 1 中的一些设计决策使得很难将硬件设备(例如传感器或执行器)本地集成到 ROS 图中。 master 是 ROS 图中的中心实体,需要在任何节点之前启动。此外,节点和主节点之间的通信是使用 XML-RPC 完成的,由于其递归无界性质,当在小型资源约束系统/微控制器上实现时,这会造成很大的依赖性。相反,通常使用一个驱动程序,它使用自定义协议在设备和计算机之间进行通信,并在计算机上公开一个 ROS 接口。
将来应该可以直接在设备嵌入式系统上实现 ROS 协议。然后,启用 ROS 的设备将能够自动发现其他节点并公开 ROS 接口(由发布者、服务和参数组成)。采用像 DDS 这样的行业标准以及中间件的去中心化特性是实现这一目标的重要部分。
这种方法的优点是双重的:
在 ROS 1 中,节点通常使用 Node API 并实现自己的主要功能。只有少数包利用 Nodelet API 并将其组件编译到共享库中。开发人员必须在这两种不同的 API 之间进行选择,并且从使用一种转换为另一种需要一些不小的努力。
在 ROS 2 中,推荐的节点编写方式类似于 nodelet。这将使用户能够在部署时决定如何启动一组节点。一方面,每个节点都可以在单独的进程中启动,以方便单独调试它们。在其他多个节点上,可以在单个进程中聚合,以受益于进程内消息传递可能带来的性能优势。
这种在一个进程中集束多枚节点,使得系统扩张性好、而且体积小、效率高。
在 ROS 1 中,启动系统只能启动一组进程。如果流程已完成,它不会提供超出信息的任何反馈。对于复杂的系统,这通常是不够的。开发人员以等待固定时间或等待自定义标志的方式编写他们的流程是很常见的,该标志表示“一切”在开始处理数据之前已准备好。此外,当启动过程中出现“某事”出错时,细心的开发人员会注意到并手动重新启动启动过程。显然,在产品上使用软件的用例中,这也是不可行的。
目标是使发射系统能够确保确定性结果。为了实现这一点,启动系统需要能够自省已启动的进程(通常是 ROS 节点),并确保它们已成功启动、完成初始化,并已与其他实体建立了所有需要的通信通道。这将需要一个简约的生命周期以及从启动系统内省状态的能力。甚至可以将启动的 ROS 图与“已知良好”状态进行比较,以确保系统已按照预期启动。
在复杂系统中,系统及其动态配置的观察变得更加重要。在 ROS 1 中,节点没有任何特定的状态,只有少数组件(如 nodelet 管理器)提供了一个接口来获取信息甚至操作正在运行的系统。
一旦 ROS 系统使用了上述特性(Nodelet 样式的节点和可访问的生命周期),就可以利用内省和编排的能力来构建更复杂的系统。以下仅是由全面的自省和调试功能启用的几个示例场景:
本文列举四类工程需求:
以上都是做为机器人操作系统的刚性需求,而要完成上述四点,还必须是从系统的底层框架完成,重新构建是不能回避的障碍,因而ROS2就是全新的系统框架,与ROS1全然不同。