Apollo 10.0
自动驾驶开放平台
apollo::cyber::plugin_manager::PluginManager类 参考

#include <plugin_manager.h>

apollo::cyber::plugin_manager::PluginManager 的协作图:

Public 成员函数

 ~PluginManager ()
 
bool ProcessPluginDescriptionFile (const std::string &file_path, std::string *library_path)
 parse plugin description file and load the library TODO(liangjinping): parse description to struct
 
bool LoadPlugin (const std::string &plugin_description_file_path)
 load plugin clases from file
 
template<typename Base >
std::shared_ptr< BaseCreateInstance (const std::string &derived_class)
 create plugin instance of derived class based on Base
 
bool FindPluginIndexAndLoad (const std::string &plugin_index_path)
 find plugin index file and load plugins
 
bool LoadInstalledPlugins ()
 load plugins from installed path
 
template<typename Base >
std::string GetPluginClassHomePath (const std::string &class_name)
 @bried get plugin description file location that class belongs to
 
template<typename Base >
std::string GetPluginConfPath (const std::string &class_name, const std::string &conf_name)
 get plugin configuration file location
 
bool LoadLibrary (const std::string &library_path)
 load library of plugin
 
template<typename Base >
bool IsLibraryLoaded (const std::string &class_name)
 check if library of plugin is loaded
 
template<typename Base >
bool CheckAndLoadPluginLibrary (const std::string &class_name)
 check if library of plugin is loaded, and load it if not
 
template<typename Base >
std::vector< std::string > GetDerivedClassNameByBaseClass ()
 Get all derived class name by base class name
 

静态 Public 成员函数

static PluginManagerInstance ()
 get singleton instance of PluginManager
 

详细描述

在文件 plugin_manager.h37 行定义.

构造及析构函数说明

◆ ~PluginManager()

PluginManager::~PluginManager ( )

在文件 plugin_manager.cc39 行定义.

39{}

成员函数说明

◆ CheckAndLoadPluginLibrary()

template<typename Base >
bool PluginManager::CheckAndLoadPluginLibrary ( const std::string &  class_name)

check if library of plugin is loaded, and load it if not

参数
class_namederived class name of plugin
返回
result of checking, true for loaded

在文件 plugin_manager.h231 行定义.

231 {
232 if (IsLibraryLoaded<Base>(class_name)) {
233 return true;
234 }
235 int status = 0;
236 std::string base_class_name =
237 abi::__cxa_demangle(typeid(Base).name(), 0, 0, &status);
238 if (plugin_class_plugin_name_map_.find({class_name, base_class_name}) ==
239 plugin_class_plugin_name_map_.end()) {
240 // not found
241 AWARN << "plugin of class " << class_name << " not found, "
242 << "please check if it's registered";
243 return false;
244 }
245 std::string plugin_name =
246 plugin_class_plugin_name_map_[{class_name, base_class_name}];
247 if (plugin_description_map_.find(plugin_name) ==
248 plugin_description_map_.end()) {
249 // not found
250 AWARN << "plugin description of class " << class_name << " not found, "
251 << "please check if it's loaded";
252 return false;
253 }
254 auto plugin_description = plugin_description_map_[plugin_name];
255 return LoadLibrary(plugin_description->actual_library_path_);
256}
Definition base.h:20
bool LoadLibrary(const std::string &library_path)
load library of plugin
#define AWARN
Definition log.h:43

◆ CreateInstance()

template<typename Base >
std::shared_ptr< Base > PluginManager::CreateInstance ( const std::string &  derived_class)

create plugin instance of derived class based on Base

参数
derived_classclass name of the derived class
返回
instance pointer

在文件 plugin_manager.h150 行定义.

151 {
152 AINFO << "creating plugin instance of " << derived_class;
153 if (!CheckAndLoadPluginLibrary<Base>(derived_class)) {
154 AERROR << "plugin of class " << derived_class << " have not been loaded";
155 return nullptr;
156 }
157 return class_loader_manager_.CreateClassObj<Base>(derived_class);
158}
std::shared_ptr< Base > CreateClassObj(const std::string &class_name)
#define AERROR
Definition log.h:44
#define AINFO
Definition log.h:42

◆ FindPluginIndexAndLoad()

bool PluginManager::FindPluginIndexAndLoad ( const std::string &  plugin_index_path)

find plugin index file and load plugins

参数
plugin_index_pathplugin index file directory
返回
result of loadding plugins, true for success

在文件 plugin_manager.cc106 行定义.

107 {
108 std::vector<std::string> plugin_index_list;
109 apollo::cyber::common::FindPathByPattern(plugin_index_path, "", DT_REG, false,
110 &plugin_index_list);
111 bool success = true;
112 for (auto plugin_index : plugin_index_list) {
113 std::string plugin_name = apollo::cyber::common::GetFileName(plugin_index);
114 AINFO << "plugin index[" << plugin_index << "] name[" << plugin_name
115 << "] found";
116 if (plugin_description_map_.find(plugin_name) !=
117 plugin_description_map_.end()) {
118 AWARN << "plugin [" << plugin_name << "] already loaded";
119 continue;
120 }
121
122 auto description = std::make_shared<PluginDescription>(plugin_name);
123 if (!description->ParseFromIndexFile(plugin_index)) {
124 success = false;
125 // invalid index file
126 continue;
127 }
128
129 // if (!class_loader_manager_.LoadLibrary(actual_library_path)) {
130 // success = false;
131 // AWARN << "plugin index[" << plugin_index << "] name[" << plugin_name
132 // << "] load failed, library[" << actual_library_path << "]
133 // invalid";
134 // continue;
135 // }
136 // lazy load
137 plugin_loaded_map_[description->name_] = false;
138 plugin_description_map_[description->name_] = description;
139 for (auto& class_name_pair : description->class_name_base_class_name_map_) {
140 plugin_class_plugin_name_map_[class_name_pair] = description->name_;
141 }
142 AINFO << "plugin index[" << plugin_index << "] name[" << description->name_
143 << "] lazy load success";
144 }
145 return success;
146}
size_t FindPathByPattern(const std::string &base_path, const std::string &patt, const unsigned char d_type, const bool recursive, std::vector< std::string > *result_list)
Find path with pattern
Definition file.cc:374
std::string GetFileName(const std::string &path, const bool remove_extension)
Definition file.cc:415

◆ GetDerivedClassNameByBaseClass()

template<typename Base >
std::vector< std::string > PluginManager::GetDerivedClassNameByBaseClass ( )

Get all derived class name by base class name

返回
all derived class name of base class name

在文件 plugin_manager.h259 行定义.

259 {
260 int status = 0;
261 std::string base_class_name =
262 abi::__cxa_demangle(typeid(Base).name(), 0, 0, &status);
263 std::vector<std::string> derived_class_name;
264 for (const auto& iter : plugin_class_plugin_name_map_) {
265 if (iter.first.second == base_class_name) {
266 derived_class_name.push_back(iter.first.first);
267 }
268 }
269 return derived_class_name;
270}

◆ GetPluginClassHomePath()

template<typename Base >
std::string PluginManager::GetPluginClassHomePath ( const std::string &  class_name)

@bried get plugin description file location that class belongs to

参数
class_namederived class name
返回
location of plugin description file

在文件 plugin_manager.h161 行定义.

162 {
163 if (!CheckAndLoadPluginLibrary<Base>(class_name)) {
164 AERROR << "plugin of class " << class_name << " have not been loaded";
165 return "";
166 }
167 std::string library_path =
168 class_loader_manager_.GetClassValidLibrary<Base>(class_name);
169 if (library_path == "") {
170 AWARN << "plugin of class " << class_name << " not found";
171 return "";
172 }
173 for (auto it = plugin_description_map_.begin();
174 it != plugin_description_map_.end(); ++it) {
175 if (it->second->actual_library_path_ == library_path) {
176 // TODO(liangjinping): remove hard code of relative prefix
177 std::string relative_prefix = "share/";
178 std::string relative_plugin_home_path =
179 apollo::cyber::common::GetDirName(it->second->description_path_);
180 if (relative_plugin_home_path.rfind(relative_prefix, 0) == 0) {
181 relative_plugin_home_path =
182 relative_plugin_home_path.substr(relative_prefix.size());
183 }
184 return relative_plugin_home_path;
185 }
186 }
187 // not found
188 return "";
189}
std::string GetClassValidLibrary(const std::string &class_name)
get pathof library that class belongs to
std::string GetDirName(const std::string &path)
get directory name of path
Definition file.cc:406

◆ GetPluginConfPath()

template<typename Base >
std::string PluginManager::GetPluginConfPath ( const std::string &  class_name,
const std::string &  conf_name 
)

get plugin configuration file location

参数
class_namederived class name
conf_nameconfiguration file name
返回
location of plugin configuration file

在文件 plugin_manager.h192 行定义.

193 {
194 std::string plugin_home_path = GetPluginClassHomePath<Base>(class_name);
195 if (apollo::cyber::common::PathIsAbsolute(plugin_home_path)) {
196 // can not detect the plugin relative path
197 AWARN << "plugin of class " << class_name << " load from absolute path, "
198 << "conf path will be relative to it's description file";
199 }
200
201 std::string relative_conf_path = plugin_home_path + "/" + conf_name;
202 std::string actual_conf_path;
204 relative_conf_path, "APOLLO_CONF_PATH", &actual_conf_path)) {
205 return actual_conf_path;
206 }
207 return plugin_home_path + "/" + conf_name;
208}
bool GetFilePathWithEnv(const std::string &path, const std::string &env_var, std::string *file_path)
get file path, judgement priority:
Definition file.cc:436
bool PathIsAbsolute(const std::string &path)
Definition file.cc:200

◆ Instance()

PluginManager * PluginManager::Instance ( )
static

get singleton instance of PluginManager

返回
instance pointer

在文件 plugin_manager.cc203 行定义.

203{ return instance_; }

◆ IsLibraryLoaded()

template<typename Base >
bool PluginManager::IsLibraryLoaded ( const std::string &  class_name)

check if library of plugin is loaded

参数
class_namederived class name of plugin
返回
result of checking, true for loaded

在文件 plugin_manager.h211 行定义.

211 {
212 int status = 0;
213 std::string base_class_name =
214 abi::__cxa_demangle(typeid(Base).name(), 0, 0, &status);
215 if (plugin_class_plugin_name_map_.find({class_name, base_class_name}) ==
216 plugin_class_plugin_name_map_.end()) {
217 // not found
218 return false;
219 }
220 std::string plugin_name =
221 plugin_class_plugin_name_map_[{class_name, base_class_name}];
222 if (plugin_loaded_map_.find(plugin_name) == plugin_loaded_map_.end()) {
223 // not found
224 return false;
225 }
226
227 return plugin_loaded_map_[plugin_name];
228}

◆ LoadInstalledPlugins()

bool PluginManager::LoadInstalledPlugins ( )

load plugins from installed path

返回
result of loadding plugins, true for success

在文件 plugin_manager.cc148 行定义.

148 {
149 if (apollo::cyber::common::GetEnv("APOLLO_PLUGIN_SEARCH_IN_BAZEL_OUTPUT") ==
150 "1") {
151 AWARN << "search plugin index path under bazel-bin enabled, it may take "
152 "longer time to load plugins";
153 // enable scanning cyber_plugin_index path under bazel-bin
154 const std::string apollo_root =
155 apollo::cyber::common::GetEnv("APOLLO_ROOT_DIR");
156 // TODO(infra): make it configurable or detect automatically
157 const std::string bazel_bin_path = apollo_root + "/bazel-bin";
158 std::vector<std::string> user_plugin_index_path_list;
159 AINFO << "scanning plugin index path under " << bazel_bin_path;
160 FindPlunginIndexPath(bazel_bin_path, &user_plugin_index_path_list);
161 // load user plugin with higher priority
162 for (auto dir : user_plugin_index_path_list) {
163 AINFO << "loading user plugins from path[" << dir << "]";
165 }
166 }
167
168 std::string plugin_index_path =
169 apollo::cyber::common::GetEnv("APOLLO_PLUGIN_INDEX_PATH");
170 if (plugin_index_path.empty()) {
171 // env not set, use default
172 const std::string apollo_distribution_home =
173 apollo::cyber::common::GetEnv("APOLLO_DISTRIBUTION_HOME");
174 const std::string plugin_index_path =
175 apollo_distribution_home + "/share/cyber_plugin_index";
176 }
177 AINFO << "loading plugins from APOLLO_PLUGIN_INDEX_PATH[" << plugin_index_path
178 << "]";
179 size_t begin = 0;
180 size_t index;
181 do {
182 index = plugin_index_path.find(':', begin);
183 auto p = plugin_index_path.substr(begin, index - begin);
185 AINFO << "loading plugins from plugin index path[" << p << "]";
187 } else {
188 AWARN << "plugin index path[" << p << "] not exists";
189 }
190 begin = index + 1;
191 } while (index != std::string::npos);
192 return true;
193}
bool FindPluginIndexAndLoad(const std::string &plugin_index_path)
find plugin index file and load plugins
std::string GetEnv(const std::string &var_name, const std::string &default_value="")
Definition environment.h:29
bool DirectoryExists(const std::string &directory_path)
Check if the directory specified by directory_path exists and is indeed a directory.
Definition file.cc:207
bool FindPlunginIndexPath(const std::string &base_path, std::vector< std::string > *path_list)
find cyber_plugin_index directory

◆ LoadLibrary()

bool PluginManager::LoadLibrary ( const std::string &  library_path)

load library of plugin

参数
library_pathlibrary path
返回
result of loading library, true for success

在文件 plugin_manager.cc195 行定义.

195 {
196 if (!class_loader_manager_.LoadLibrary(library_path)) {
197 AWARN << "plugin library[" << library_path << "] load failed";
198 return false;
199 }
200 return true;
201}
bool LoadLibrary(const std::string &library_path)

◆ LoadPlugin()

bool PluginManager::LoadPlugin ( const std::string &  plugin_description_file_path)

load plugin clases from file

参数
pluin_description_file_pathfile path
返回
result of loadding plugin, true for success

在文件 plugin_manager.cc58 行定义.

59 {
60 AINFO << "loading plugin from description[" << plugin_description_file_path
61 << "]";
62
63 auto description =
64 std::make_shared<apollo::cyber::plugin_manager::PluginDescription>();
65 if (!description->ParseFromDescriptionFile(plugin_description_file_path)) {
66 return false;
67 }
68
69 if (plugin_description_map_.find(description->name_) !=
70 plugin_description_map_.end()) {
71 AWARN << "plugin [" << description->name_ << "] already loaded";
72 return true;
73 }
74
75 if (!LoadLibrary(description->actual_library_path_)) {
76 AWARN << "plugin description[" << plugin_description_file_path << "] name["
77 << description->name_ << "] load failed, library["
78 << description->actual_library_path_ << "] invalid";
79 return false;
80 }
81
82 plugin_loaded_map_[description->name_] = true;
83 plugin_description_map_[description->name_] = description;
84 for (auto& class_name_pair : description->class_name_base_class_name_map_) {
85 plugin_class_plugin_name_map_[class_name_pair] = description->name_;
86 }
87 AINFO << "plugin description[" << plugin_description_file_path << "] name["
88 << description->name_ << "] load success";
89 return true;
90}

◆ ProcessPluginDescriptionFile()

bool PluginManager::ProcessPluginDescriptionFile ( const std::string &  file_path,
std::string *  library_path 
)

parse plugin description file and load the library TODO(liangjinping): parse description to struct

参数
file_paththe path of plugin description file
返回
process result, true for success

在文件 plugin_manager.cc41 行定义.

42 {
43 tinyxml2::XMLDocument doc;
44 if (doc.LoadFile(file_path.c_str()) != tinyxml2::XML_SUCCESS) {
45 AWARN << "fail to process file " << file_path;
46 return false;
47 }
48 const tinyxml2::XMLElement* root = doc.RootElement();
49
50 // TODO(liangjinping): parse as struct
51 *library_path = root->Attribute("path");
52
53 // TODO(liangjinping): parse description file and do something more
54
55 return true;
56}

该类的文档由以下文件生成: