Apollo星火培训——Cyber RT基础入门与实践

2023-11-23 22:30

本文主要是介绍Apollo星火培训——Cyber RT基础入门与实践,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

第一天 Cyber RT基础入门与实践

  • 背景
  • 1.1 Cyber简介
    • 1.1.1 框架优势
    • 1.1.2 框架结构
    • 1.1.3 通信构成
    • 1.1.4 程序构成
    • 1.1.5 系统安装
  • 1.2 Bazel简介
    • 1.2.1 Bazel项目结构
    • 1.2.2 了解BUILD文件
    • 1.2.1 了解 buildtool工具

本文来源于:https://apollo.baidu.com/community/article/1093
仅学习用,若有侵权,可联系删除

背景

Apollo8.0的架构图中,软件核心层中,感知、规划、控制等模块的存在使得汽车具备了类人的驾驶能力,但是这些模块在软件系统中是相互解耦的,Cyber RT就担负起了把自动驾驶中的各个算法模块组织串联的重任,满足了各算法模块之间的数据通信需求,同时也保证在数据通信过程中的实时性与可靠性。这就好比是人的血管、肌肉与大脑的关系。

1.1 Cyber简介

Apollo Cyber是首个专为自动驾驶定制的高性能且开源的实时通信框架,于2019年与Apollo 3.5开放平台同期发布,它主要解决了自动驾驶系统的高并发、低延迟、高吞吐、任务调度等问题,同时还提供了多种通信机制和用户级的协程,在资源有限的情况下会根据任务的优先级来进行调度处理。如下图所示,Cyber RT通过Component来封装每个算法模块,通过有向无环图(DAG)来描述Components之间的逻辑关系。对于每个算法模块,都有其优先级、运行时间、使用资源等方面的配置。系统启动时,系统会结合DAG文件、调度配置等信息,创建相应的任务,从框架内部来讲,就是协程,然后图中间的调度器把任务放到各个处理器的队列中,最后由左上角Sensor输入的数据,驱动整个系统运转

在这里插入图片描述

1.1.1 框架优势

Apollo Cyber框架的优点主要有以下几点:

  • 高性能:Apollo Cyber是专为自动驾驶定制的高性能运行时框架,能够处理高并发、低延迟、高吞吐等自动驾驶系统中的复杂任务。
  • 灵活性:Apollo Cyber提供了多种通信机制和用户级的协程,可以根据任务的优先级来进行调度处理,能够灵活地应对各种自动驾驶场景。
  • 可靠性:Apollo Cyber通过Component来封装每个算法模块,通过有向无环图(DAG)来描述Components之间的逻辑关系,能够确保系统各个模块之间的稳定性和可靠性。
  • 扩展性:Apollo Cyber的架构可以支持各种不同类型和不同层次的自动驾驶任务,并且可以方便地扩展和升级。

1.1.2 框架结构

如下头所示为Cyber RT的框架结构图。
在这里插入图片描述

  • 第一层:主要是Apollo实现的基础库,比如有Lock-Free的对象池,Lock-Free的队列等。实现基础库可以减少相关的依赖并提高运行效率。
  • 第二层、三层:主要是负责管理Cyber的通信机制,包括服务发现(负责管理通信中的Node节点)和Publish-Subscribe通信机制。并且Cyber也支持跨机、进程间、进程内通信,而且会根据不同的数据传输和业务逻辑自动选择效率最高最匹配的通信方式来进行通信。
  • 第四层:主要是对传输过后的数据进行缓存,并会根据不同传感器得到的数据进行融合得到一个可处理可读的数据发送给另一个模块。
  • 第五、六层:主要是管理每一个任务的调度和数据处理。
  • 第七层:提供给开发者的一些API接口,让开发者有更多可操作性,提高开发效率。

1.1.3 通信构成

Node是Cyber的基础构建,每一个模块都会包含一个Node节点,模块之间通过Node节点来进行通信。Node之间的通信可以设定不同的模式,有Reader/Writer和Service/Client。
Cyber采用的是分布式系统,Node是通过Topology来管理的,每个Node都是这个拓扑图的顶点,其中每个Node顶点是通过Channel或者Service来连接的。Node节点是去中心化的,可以动态监控节点的增加和删除。Channel可以理解为一块共享内存,采用共享内存的通信方式,可以大大提高通信效率。下图1-2就能更加形象得表现Node之间的关系与数据流向。
图1-2 Topology管理图

1.1.4 程序构成

如图1-3所示,这是由3个Component(Cyber把每个模块,例如Camera驱动、控制模块都会有对应的Component组件)组成的一个简单的网络, 最左边Camera Driver作为系统的输入节点,从传感器读取数据并发送到/sensor/camera/image这个Channel(Component之间通信的通道)中,然后中间的这个Perception Component,它会订阅相机驱动传感器的数据,从/sensor/camera/image这个Channel中取出数据并进行相应的算法处理,将得到的结果从/perception/obstacles这个channel中进行输出,最右边的是Planning component,它会从/perception/obstacles这个Channel中取出感知结果并得到一个决策规划的结果。下面就是具体的Component的实例,实例中的Perception它不需要关心上下模块是Camera还是Planning,只需要定义自己的输入,也就是SensorMessage这个类型的数据,以及在配置文件中定义输入的Channel名字即可,在开发阶段就能大大减少两个模块之间的耦合。

图1-3 通信流程图

1.1.5 系统安装

在使用Cyber框架时会进入到Apollo的docker容器中,所以要先安装好Apollo并进入到容器内操作,Cyber框架代码在apollo/cyber。

Apollo Cyber安装可参考链接: 安装链接

1.2 Bazel简介

在学习和使用CyberRT时需要用到Bazel,所以这里我们了解一下Bazel。Bazel是Google研发的一款开源构建和测试工具,也是一种简单、易读的构建工具。其优点如下:

  • Bazel 仅重建必要的内容。借助高级的本地和分布式缓存,优化的依赖关系分析和并行执行,可以获得快速而增量的构建。
  • 构建和测试 Java、C++、Android、iOS、和其他各种语言平台。Bazel 可以在 Windows、macOS 和 Linux 上运行。
  • Bazel 帮助你扩展你的组织、代码库和持续集成系统。它可以处理任何规模的代码库。

1.2.1 Bazel项目结构

在构建项目之前,您需要设置其工作区。工作区是一个保存项目源文件和 Bazel 构建输出的目录。它还包含 Bazel 识别为特殊的文件:

  • 该WORKSPACE文件将目录及其内容标识为 Bazel 工作区并位于项目目录结构的根部,
  • 一个或多个BUILD文件,告诉 Bazel 如何构建项目的不同部分。
    其目录结构大致如下:
project
|-- pkg
|   |-- BUILD
|   |-- src.cc
|-- WORKSPACE

1.2.2 了解BUILD文件

一个BUILD文件包含多种不同类型的 Bazel 指令。最重要的类型是构建规则,它告诉 Bazel 如何构建所需的输出,例如可执行二进制文件或库。文件中构建规则的每个实例BUILD称为目标,并指向一组特定的源文件和依赖项。一个目标也可以指向其他目标。例如:

cc_binary(name = "hello_world",srcs = ["hello_world.cc"],
)

在示例中,hello-world目标实例化 Bazel 的内置 cc_binary规则。该规则告诉 Bazel 从源文件构建一个独立的可执行二进制文件。

BUILD文件中常见的两种规则:

  • cc_binary:表示要构建对应文件变成二进制文件。

    • name:表示构建完成后的文件名字。
    • srcs:表示要构建的源文件。
    • deps:表示构建该文件所依赖相关的库。
  • cc_library:表示要构建对应文件变成相关依赖库。

    • hdrs:表示的是源文件对应的头文件路径。
    • package(default_visibility = [“//visibility:public”])这段代码则表示该文件是公开的,能被所有对象找到并依赖。

1.2.1 了解 buildtool工具

Apollo源码版采用原生的bazel编译,但包管理环境下我们使用buildtool来对代码进行编译。Apollo buildtool是一个命令行工具,提供编译、测试、安装或运行Apollo模块等功能。基于buildtool,不仅可以方便地安装Apollo中各个模块的二进制包,还可以对这些源代码进行二次开发、编译和测试,而不需要下载整个Apollo。buildtool可以让开发者只关注需要开发的模块,提高整体开发效率。

buildtool详细使用方法请参考: buildtools工具

这篇关于Apollo星火培训——Cyber RT基础入门与实践的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/420791

相关文章

Java调用DeepSeek API的最佳实践及详细代码示例

《Java调用DeepSeekAPI的最佳实践及详细代码示例》:本文主要介绍如何使用Java调用DeepSeekAPI,包括获取API密钥、添加HTTP客户端依赖、创建HTTP请求、处理响应、... 目录1. 获取API密钥2. 添加HTTP客户端依赖3. 创建HTTP请求4. 处理响应5. 错误处理6.

golang内存对齐的项目实践

《golang内存对齐的项目实践》本文主要介绍了golang内存对齐的项目实践,内存对齐不仅有助于提高内存访问效率,还确保了与硬件接口的兼容性,是Go语言编程中不可忽视的重要优化手段,下面就来介绍一下... 目录一、结构体中的字段顺序与内存对齐二、内存对齐的原理与规则三、调整结构体字段顺序优化内存对齐四、内

0基础租个硬件玩deepseek,蓝耘元生代智算云|本地部署DeepSeek R1模型的操作流程

《0基础租个硬件玩deepseek,蓝耘元生代智算云|本地部署DeepSeekR1模型的操作流程》DeepSeekR1模型凭借其强大的自然语言处理能力,在未来具有广阔的应用前景,有望在多个领域发... 目录0基础租个硬件玩deepseek,蓝耘元生代智算云|本地部署DeepSeek R1模型,3步搞定一个应

C++实现封装的顺序表的操作与实践

《C++实现封装的顺序表的操作与实践》在程序设计中,顺序表是一种常见的线性数据结构,通常用于存储具有固定顺序的元素,与链表不同,顺序表中的元素是连续存储的,因此访问速度较快,但插入和删除操作的效率可能... 目录一、顺序表的基本概念二、顺序表类的设计1. 顺序表类的成员变量2. 构造函数和析构函数三、顺序表

python实现简易SSL的项目实践

《python实现简易SSL的项目实践》本文主要介绍了python实现简易SSL的项目实践,包括CA.py、server.py和client.py三个模块,文中通过示例代码介绍的非常详细,对大家的学习... 目录运行环境运行前准备程序实现与流程说明运行截图代码CA.pyclient.pyserver.py参

使用C++实现单链表的操作与实践

《使用C++实现单链表的操作与实践》在程序设计中,链表是一种常见的数据结构,特别是在动态数据管理、频繁插入和删除元素的场景中,链表相比于数组,具有更高的灵活性和高效性,尤其是在需要频繁修改数据结构的应... 目录一、单链表的基本概念二、单链表类的设计1. 节点的定义2. 链表的类定义三、单链表的操作实现四、

Spring Boot统一异常拦截实践指南(最新推荐)

《SpringBoot统一异常拦截实践指南(最新推荐)》本文介绍了SpringBoot中统一异常处理的重要性及实现方案,包括使用`@ControllerAdvice`和`@ExceptionHand... 目录Spring Boot统一异常拦截实践指南一、为什么需要统一异常处理二、核心实现方案1. 基础组件

SpringBoot项目中Maven剔除无用Jar引用的最佳实践

《SpringBoot项目中Maven剔除无用Jar引用的最佳实践》在SpringBoot项目开发中,Maven是最常用的构建工具之一,通过Maven,我们可以轻松地管理项目所需的依赖,而,... 目录1、引言2、Maven 依赖管理的基础概念2.1 什么是 Maven 依赖2.2 Maven 的依赖传递机

Oracle查询优化之高效实现仅查询前10条记录的方法与实践

《Oracle查询优化之高效实现仅查询前10条记录的方法与实践》:本文主要介绍Oracle查询优化之高效实现仅查询前10条记录的相关资料,包括使用ROWNUM、ROW_NUMBER()函数、FET... 目录1. 使用 ROWNUM 查询2. 使用 ROW_NUMBER() 函数3. 使用 FETCH FI

在C#中获取端口号与系统信息的高效实践

《在C#中获取端口号与系统信息的高效实践》在现代软件开发中,尤其是系统管理、运维、监控和性能优化等场景中,了解计算机硬件和网络的状态至关重要,C#作为一种广泛应用的编程语言,提供了丰富的API来帮助开... 目录引言1. 获取端口号信息1.1 获取活动的 TCP 和 UDP 连接说明:应用场景:2. 获取硬