百度 Apollo Cyber RT简介基本概念以及与 ROS 对照
Posted 飘飘白云
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了百度 Apollo Cyber RT简介基本概念以及与 ROS 对照相关的知识,希望对你有一定的参考价值。
一,背景
ROS 应用于自动驾驶领域的不足:
- 调度的不确定性:各节点以独立进程运行,节点运行顺序无法确定,因而业务逻辑的调度顺序无法保证;
- 运行效率:ROS 为分布式系统,存在通信开销
二,Cyber RT 框架
从下到上依次为:
- 基础库:高性能,无锁队列;
- 通信层:Publish/Subscribe机制,Service/Client机制,服务自发现,自适应的通信机制(共享内存、Socket、进程内);
- 数据层:数据缓存与融合。多路传感器之间数据需要融合,而且算法可能需要缓存一定的数据。比如典型的仿真应用,不同算法模块之间需要有一个数据桥梁,数据层起到了这个模块间通信的桥梁的作用;
- 计算层:计算模型,任务以及任务调度;
三,运行流程
- 算法模块通过有向无环图(DAG),配置任务间的逻辑关系。对于每个算法可以进行优先级、运行时间、使用资源等方面的配置。
- 系统启动时,结合DAG、调度配置等,创建相应的任务,从框架内部来讲,就是协程(coroutine)
- 调度器把任务放到各个 Processor 的队列中。
- 然后,由 Sensor 输入的数据,驱动整个系统运转。
四,基本概念以及与 ROS 对照
Cyber | ROS | 注释 |
---|---|---|
Component | 无 | 组件之间通过 Cyber channel 通信。 |
Channel | Topic | channel 用于管理数据通信,用户可以通过 publish/subscribe 相同的 channel 来通信。 |
Node | Node | 每一个模块包含 Node 并通过 Node 来通信。一个模块通过定义 read/write 和/或 service/client 使用不同的通信模式。 |
Reader/Writer | Publish/Subscribe | 订阅者模式。往 channel 读写消息的类。 通常作为 Node 主要的消息传输接口。 |
Service/Client | Service/Client | 请求/响应模式,支持节点间双向通信。 |
Message | Message | Cyber RT 中用于模块间通信的数据单元。其实现基于 protobuf |
Parameter | Parameter | Parameter 服务提供全局参数访问接口。该服务基于 service/client 模式。 |
Record file | Bag file | 用于记录从 channel 发送或接收的消息。 回放 record file 可以重现之前的操作行为。 |
Launch file | Launch file | 提供一种启动模块的便利途径。通过在 launch file 中定义一个或多个 dag 文件,可以同时启动多个 modules。 |
Task | 无 | 异步计算任务 |
CRoutine | 无 | 协程,优化线程使用与系统资源分配 |
Scheduler | 无 | 任务调度器,用户空间。 |
Dag file | 无 | 定义模块拓扑结构的配置文件。 |
五,特色
- 高性能:无锁对象,协程(coroutine),自适应通信机制;
- 确定性:可配置的任务以及任务调度,通过协程将调度从内核空间转移到用户空间;
- 模块化:在框架内实现组件以及节点,即可完成系统任务;
- 便利性:创建和使用任务
六,示例
Writer/Reader
Message:
syntax = "proto2";
package apollo.cyber.examples.proto;
message Chatter
optional uint64 timestamp = 1;
optional uint64 lidar_timestamp = 2;
optional uint64 seq = 3;
optional bytes content = 4;
;
Writer:
#include "cyber/cyber.h"
#include "cyber/examples/proto/examples.pb.h"
#include "cyber/time/rate.h"
#include "cyber/time/time.h"
using apollo::cyber::Rate;
using apollo::cyber::Time;
using apollo::cyber::examples::proto::Chatter;
int main(int argc, char *argv[])
// init cyber framework
apollo::cyber::Init(argv[0]);
// create talker node
auto talker_node = apollo::cyber::CreateNode("talker");
// create talker
auto talker = talker_node->CreateWriter<Chatter>("channel/chatter");
Rate rate(1.0);
while (apollo::cyber::OK())
static uint64_t seq = 0;
auto msg = std::make_shared<Chatter>();
msg->set_timestamp(Time::Now().ToNanosecond());
msg->set_lidar_timestamp(Time::Now().ToNanosecond());
msg->set_seq(seq++);
msg->set_content("Hello, apollo!");
talker->Write(msg);
AINFO << "talker sent a message!";
rate.Sleep();
return 0;
Reader:
#include "cyber/cyber.h"
#include "cyber/examples/proto/examples.pb.h"
void MessageCallback(
const std::shared_ptr<apollo::cyber::examples::proto::Chatter>& msg)
AINFO << "Received message seq-> " << msg->seq();
AINFO << "msgcontent->" << msg->content();
int main(int argc, char* argv[])
// init cyber framework
apollo::cyber::Init(argv[0]);
// create listener node
auto listener_node = apollo::cyber::CreateNode("listener");
// create listener
auto listener =
listener_node->CreateReader<apollo::cyber::examples::proto::Chatter>(
"channel/chatter", MessageCallback);
apollo::cyber::WaitForShutdown();
return 0;
Service/Client
Message:
syntax = "proto2";
package apollo.cyber.examples.proto;
message Driver
optional string content = 1;
optional uint64 msg_id = 2;
optional uint64 timestamp = 3;
;
Service/client:
#include "cyber/cyber.h"
#include "cyber/examples/proto/examples.pb.h"
using apollo::cyber::examples::proto::Driver;
int main(int argc, char* argv[])
apollo::cyber::Init(argv[0]);
std::shared_ptr<apollo::cyber::Node> node(
apollo::cyber::CreateNode("start_node"));
auto server = node->CreateService<Driver, Driver>(
"test_server", [](const std::shared_ptr<Driver>& request,
std::shared_ptr<Driver>& response)
AINFO << "server: i am driver server";
static uint64_t id = 0;
++id;
response->set_msg_id(id);
response->set_timestamp(0);
);
auto client = node->CreateClient<Driver, Driver>("test_server");
auto driver_msg = std::make_shared<Driver>();
driver_msg->set_msg_id(0);
driver_msg->set_timestamp(0);
while (apollo::cyber::OK())
auto res = client->SendRequest(driver_msg);
if (res != nullptr)
AINFO << "client: responese: " << res->ShortDebugString();
else
AINFO << "client: service may not ready.";
sleep(1);
apollo::cyber::WaitForShutdown();
return 0;
七,Apollo 整体框架
以上是关于百度 Apollo Cyber RT简介基本概念以及与 ROS 对照的主要内容,如果未能解决你的问题,请参考以下文章
百度 Apollo Cyber RT简介基本概念以及与 ROS 对照
Apollo Advanced Lesson | Cyber RT