Closed Karsten1987 closed 5 years ago
exposes a new symbol in the each message library in order to load the cpp typesupport.
rosidl_typesupport_cpp__get_message_type_support_handle__<pkg_name>__msg__<message_type>
This then allows to open the library (e.g. via Poco) and get the typesupport in order to create a ROS 2 publisher or subscriber:
#include <unistd.h> #include "ament_index_cpp/get_resources.hpp" #include "ament_index_cpp/get_package_prefix.hpp" #include "Poco/SharedLibrary.h" #include "rcl/rcl.h" #include "rcutils/snprintf.h" #include "rosidl_generator_c/message_type_support_struct.h" std::string get_typesupport_library(const std::string & package_name) { const char * env_var; char separator; const char * filename_prefix; const char * filename_extension; #ifdef _WIN32 env_var = "PATH"; separator = ';'; filename_prefix = ""; filename_extension = ".dll"; #elif __APPLE__ env_var = "DYLD_LIBRARY_PATH"; separator = ':'; filename_prefix = "lib"; filename_extension = ".dylib"; #else env_var = "LD_LIBRARY_PATH"; separator = ':'; filename_prefix = "lib"; filename_extension = ".so"; #endif auto package_prefix = ament_index_cpp::get_package_prefix(package_name); auto library_path = package_prefix + "/lib/" + filename_prefix + package_name + "__rosidl_typesupport_cpp" + filename_extension; fprintf(stderr, "package prefix for %s: %s\n", package_name.c_str(), package_prefix.c_str()); fprintf(stderr, "full path to library: %s\n", library_path.c_str()); return library_path; } int main(int argc, char ** argv) { (void) argc; (void) argv; std::string type_name = "MyMessageType"; std::string package_name = "my_message_type"; auto library_path = get_typesupport_library(package_name); std::shared_ptr<Poco::SharedLibrary> typesupport_library = nullptr; const rosidl_message_type_support_t * ts = nullptr; try { typesupport_library = std::make_shared<Poco::SharedLibrary>(library_path); auto symbol_name = std::string("rosidl_typesupport_cpp__get_message_type_support_handle__") + package_name + "__msg__" + type_name; fprintf(stderr, "sumbol name %s\n", symbol_name.c_str()); if (!typesupport_library->hasSymbol(symbol_name)) { fprintf(stderr, "symbol not found %s\n", symbol_name.c_str()); return -1; } fprintf(stderr, "symbol found\n"); const rosidl_message_type_support_t * (*get_ts)(void) = nullptr; get_ts = (decltype(get_ts)) typesupport_library->getSymbol(symbol_name); ts = get_ts(); if (!ts) { fprintf(stderr, "ts is null\n"); return -1; } fprintf(stderr, "ts identifier %s\n", ts->typesupport_identifier); } catch (Poco::LibraryLoadException & e) { fprintf(stderr, "poco exception: %s\n", e.what()); } return 0; }
CI (testing only std_msgs):
std_msgs
linux: aarch: osx: win:
exposes a new symbol in the each message library in order to load the cpp typesupport.
This then allows to open the library (e.g. via Poco) and get the typesupport in order to create a ROS 2 publisher or subscriber: