file:recurrent_runner.h
class RecurrentRunner {
public:
RecurrentRunner(const std::string &name, const double interval);
virtual ~RecurrentRunner() = default;
// Tick once, which may or may not execute the RunOnce() function, based on
// the interval setting.
void Tick(const double current_time);
// Do the actual work.
virtual void RunOnce(const double current_time) = 0;
protected:
std::string name_;
unsigned int round_count_ = 0;
private:
double interval_;
double next_round_ = 0;
};
RecurrentRunner是一个抽象类,它定义了一个周期性执行的任务的基本框架。
该类有一个构造函数,可以用来指定任务的名称和执行间隔。它还有一个虚析构函数,用来清理类的资源。
RecurrentRunner类有两个公共成员函数:
-
Tick函数:控制任务的执行。它接受一个当前时间的参数,并根据执行间隔来决定是否执行任务。
-
RunOnce函数:定义任务的具体内容。该函数是一个虚函数,子类需要实现它来定义任务的具体内容。
RecurrentRunner类还有两个保护成员变量:
-
name_:任务的名称。
-
round_count_:任务执行的次数。
还有两个私有成员变量:
-
interval_:任务执行的间隔。
-
next_round_:下一次执行任务的时间。
基于这些成员变量和成员函数,可以通过实现不同的任务内容来创建多种周期性任务。
void RecurrentRunner::Tick(const double current_time) {
if (next_round_ <= current_time) {
++round_count_;
AINFO_EVERY(100) << name_ << " is running round #" << round_count_;
next_round_ = current_time + interval_;
RunOnce(current_time);
}
}
Tick是RecurrentRunner类的一个成员函数,它控制任务的执行。它接受一个当前时间的参数,并根据执行间隔来决定是否执行任务。
首先,Tick函数检查当前时间是否大于等于下一次执行任务的时间(next_round_)。如果是,则执行任务。
具体地,Tick函数会将round_count_自增1,表示任务执行的次数增加了1。然后,Tick函数使用AINFO_EVERY宏输出任务的信息。AINFO_EVERY宏会在任务执行的次数(round_count_)是100的倍数时输出信息。
最后,Tick函数会调用RunOnce函数来执行任务的具体内容,并更新next_round_变量为当前时间加上执行间隔,以便下一次执行任务。
如果当前时间小于下一次执行任务的时间,Tick函数就不会执行任务。
file:monitor_manager.h
class MonitorManager {
public:
void Init(const std::shared_ptr<apollo::cyber::Node>& node);
// Start and end a monitoring frame.
bool StartFrame(const double current_time);
void EndFrame();
// Getters.
const apollo::dreamview::HMIMode& GetHMIMode() const { return mode_config_; }
bool IsInAutonomousMode() const { return in_autonomous_driving_; }
SystemStatus* GetStatus() { return &status_; }
apollo::common::monitor::MonitorLogBuffer& LogBuffer() { return log_buffer_; }
// Cyber reader / writer creator.
template <class T>
std::shared_ptr<cyber::Reader<T>> CreateReader(const std::string& channel) {
if (readers_.find(channel) == readers_.end()) {
readers_.emplace(channel, node_->CreateReader<T>(channel));
}
return std::dynamic_pointer_cast<cyber::Reader<T>>(readers_[channel]);
}
template <class T>
std::shared_ptr<cyber::Writer<T>> CreateWriter(const std::string& channel) {
return node_->CreateWriter<T>(channel);
}
private:
SystemStatus status_;
// Input statuses.
std::string current_mode_;
const apollo::dreamview::HMIConfig hmi_config_;
apollo::dreamview::HMIMode mode_config_;
bool in_autonomous_driving_ = false;
bool CheckAutonomousDriving(const double current_time);
apollo::common::monitor::MonitorLogBuffer log_buffer_;
std::shared_ptr<apollo::cyber::Node> node_;
std::unordered_map<std::string, std::shared_ptr<cyber::ReaderBase>> readers_;
DECLARE_SINGLETON(MonitorManager)
};
这是一个用于监控的类。它包含了初始化方法,用于初始化类的一些内部变量;以及开始和结束监控帧的方法。这个类还有几个 getter 方法,用于获取类的内部变量的值。这个类还有一些模板方法,用于创建 cyber 中的 reader 和 writer,以便与其他模块通信。这个类还有一些私有方法,用于检查自动驾驶状态。这个类还有一个单例声明,表示这个类只能有一个实例。
bool MonitorManager::StartFrame(const double current_time) {
// Get latest HMIStatus.
static auto hmi_status_reader =
CreateReader<apollo::dreamview::HMIStatus>(FLAGS_hmi_status_topic);
hmi_status_reader->Observe();
const auto hmi_status = hmi_status_reader->GetLatestObserved();
if (hmi_status == nullptr) {
AERROR << "No HMIStatus was received.";
return false;
}
if (current_mode_ != hmi_status->current_mode()) {
// Mode changed, update configs and monitored.
current_mode_ = hmi_status->current_mode();
mode_config_ = HMIWorker::LoadMode(hmi_config_.modes().at(current_mode_));
status_.clear_hmi_modules();
for (const auto& iter : mode_config_.modules()) {
status_.mutable_hmi_modules()->insert({iter.first, {}});
}
status_.clear_components();
for (const auto& iter : mode_config_.monitored_components()) {
status_.mutable_components()->insert({iter.first, {}});
}
status_.clear_other_components();
for (const auto& iter : mode_config_.other_components()) {
status_.mutable_other_components()->insert({iter.first, {}});
}
} else {
// Mode not changed, clear component summary from the last frame.
for (auto& iter : *status_.mutable_components()) {
iter.second.clear_summary();
}
}
in_autonomous_driving_ = CheckAutonomousDriving(current_time);
return true;
}
这是一个类的成员方法,用于开始一个监控帧。它会获取最新的 HMIStatus 信息。如果当前模式和最新的 HMIStatus 中的模式不同,则更新内部变量 mode_config_ 和 status_ 中的 hmi_modules、components 和 other_components 变量。如果模式没有发生变化,则清空 status_ 中 components 变量的 summary 字段。最后,调用 CheckAutonomousDriving 方法更新 in_autonomous_driving_ 变量。