diff --git a/src/Client.cpp b/src/Client.cpp index 1d68d28..99624bf 100644 --- a/src/Client.cpp +++ b/src/Client.cpp @@ -27,9 +27,9 @@ #include #include #include -#if FASTRTPS_VERSION_MINOR >= 2 +#if FASTRTPS_VERSION_MAJOR >= 2 && FASTRTPS_VERSION_MINOR >= 2 #include -#endif // if FASTRTPS_VERSION_MINOR >= 2 +#endif // if FASTRTPS_VERSION_MAJOR >= 2 && FASTRTPS_VERSION_MINOR >= 2 #include diff --git a/src/Participant.cpp b/src/Participant.cpp index a6fbc63..50729f3 100644 --- a/src/Participant.cpp +++ b/src/Participant.cpp @@ -18,7 +18,9 @@ #include "Participant.hpp" #include "DDSMiddlewareException.hpp" #include "Conversion.hpp" +#include "utils/databroker/utils.hpp" +#include #include #include @@ -35,7 +37,7 @@ Participant::Participant() : dds_participant_(nullptr) , logger_("is::sh::FastDDS::Participant") { - build_participant(); + build_participant(YAML::Node()); } Participant::Participant( @@ -43,98 +45,105 @@ Participant::Participant( : dds_participant_(nullptr) , logger_("is::sh::FastDDS::Participant") { - using fastrtps::xmlparser::XMLP_ret; - using fastrtps::xmlparser::XMLProfileManager; + build_participant(config); +} - if (!config.IsMap() || !config["file_path"] || !config["profile_name"]) +Participant::~Participant() +{ + if (!dds_participant_->has_active_entities()) { - if (config["domain_id"]) + dds_participant_->set_listener(nullptr); + + if (fastrtps::types::ReturnCode_t::RETCODE_OK != + ::fastdds::dds::DomainParticipantFactory::get_instance()->delete_participant(dds_participant_)) { - const ::fastdds::dds::DomainId_t domain_id = config["domain_id"].as(); - build_participant(domain_id); + logger_ << eprosima::is::utils::Logger::Level::ERROR + << "Cannot delete Fast DDS participant yet: it has active entities" << std::endl; } - else - { - std::ostringstream err; - err << "The node 'participant' in the YAML configuration of the 'fastdds' system " - << "must be a map containing two keys: 'file_path' and 'profile_name'"; + } +} - throw DDSMiddlewareException(logger_, err.str()); - } +void Participant::build_participant( + const YAML::Node& config) +{ + // Set 0 as default domain + eprosima::fastdds::dds::DomainId_t domain_id(0); + // Check if domain_id tag is present in configuration, if not 0 as default + if (config["domain_id"]) + { + domain_id = config["domain_id"].as(); } - else + + logger_ << eprosima::is::utils::Logger::Level::DEBUG + << "Creating Fast DDS Participant in domain " << domain_id << std::endl; + + // Load default XML files + fastrtps::xmlparser::XMLProfileManager::loadDefaultXMLFile(); + + // Loading XML if file_path is given + if (config["file_path"]) { - const std::string file_path = config["file_path"].as(); - if (XMLP_ret::XML_OK != XMLProfileManager::loadXMLFile(file_path)) + if (fastrtps::xmlparser::XMLP_ret::XML_OK != + fastrtps::xmlparser::XMLProfileManager::loadXMLFile(config["file_path"].as())) { + std::ostringstream err; + err << "Failed to load XML file provided in 'file_path': " << config["file_path"].as() + << ". It cannot be found or is incorrect."; throw DDSMiddlewareException( - logger_, "Loading provided XML file in 'file_path' field was not successful"); + logger_, err.str()); } + } - const std::string profile_name = config["profile_name"].as(); + // Debug variable + std::string participant_name; - dds_participant_ = this->create_participant_with_profile(profile_name); + // If profile_name is given in configuration, the other tags do not apply + if (!config["profile_name"]) + { + // Participant QoS + ::fastdds::dds::DomainParticipantQos participant_qos; - if (dds_participant_) + // Depending the SH type, use participant qos or databroker qos + // TODO : change for databroker alias refactor + if (config["discovery-server"]) { - logger_ << utils::Logger::Level::INFO - << "Created Fast DDS participant '" << dds_participant_->get_qos().name() - << "' from profile configuration '" << profile_name << "'" << std::endl; + participant_qos = get_databroker_qos(config["discovery-server"]); } else { - std::ostringstream err; - err << "Fast DDS participant '" << dds_participant_->get_qos().name() - << "' from profile configuration '" << profile_name << "' creation failed"; - - throw DDSMiddlewareException(logger_, err.str()); + participant_qos = get_default_participant_qos(); } - } -} -Participant::~Participant() -{ - if (!dds_participant_->has_active_entities()) - { - dds_participant_->set_listener(nullptr); + participant_name = participant_qos.name(); - if (fastrtps::types::ReturnCode_t::RETCODE_OK != - ::fastdds::dds::DomainParticipantFactory::get_instance()->delete_participant(dds_participant_)) - { - logger_ << utils::Logger::Level::ERROR - << "Cannot delete Fast DDS participant yet: it has active entities" << std::endl; - } + dds_participant_ = + ::fastdds::dds::DomainParticipantFactory::get_instance()->create_participant( + domain_id, + participant_qos); } -} - -void Participant::build_participant( - const ::fastdds::dds::DomainId_t& domain_id) -{ - ::fastdds::dds::DomainParticipantQos participant_qos = ::fastdds::dds::PARTICIPANT_QOS_DEFAULT; - participant_qos.name("default_IS-FastDDS-SH_participant"); - - // By default use UDPv4 due to communication failures between dockers sharing the network with the host - // When it is solved in Fast-DDS delete the following lines and use the default builtin transport. - participant_qos.transport().use_builtin_transports = false; - auto udp_transport = std::make_shared<::fastdds::rtps::UDPv4TransportDescriptor>(); - participant_qos.transport().user_transports.push_back(udp_transport); + else + { + participant_name = config["profile_name"].as(); - dds_participant_ = ::fastdds::dds::DomainParticipantFactory::get_instance()->create_participant( - domain_id, participant_qos); + // Create Participant from profile name + dds_participant_ = + ::fastdds::dds::DomainParticipantFactory::get_instance()->create_participant_with_profile( + domain_id, + config["profile_name"].as()); + } if (dds_participant_) { - logger_ << utils::Logger::Level::INFO - << "Created Fast DDS participant '" << participant_qos.name() - << "' with default QoS attributes and Domain ID: " - << domain_id << std::endl; + logger_ << eprosima::is::utils::Logger::Level::INFO + << "Created Fast DDS participant '" << participant_name + << "' with Domain ID: " << domain_id << std::endl; } else { std::ostringstream err; - err << "Error while creating Fast DDS participant '" << participant_qos.name() - << "' with default QoS attributes and Domain ID: " << domain_id; + err << "Error while creating Fast DDS participant '" << participant_name + << "' with Domain ID: " << domain_id; throw DDSMiddlewareException(logger_, err.str()); } @@ -162,7 +171,7 @@ void Participant::register_dynamic_type( // Type known, add the entry in the map topic->type topic_to_type_.emplace(topic_name, type_name); - logger_ << utils::Logger::Level::DEBUG + logger_ << eprosima::is::utils::Logger::Level::DEBUG << "Adding type '" << type_name << "' to topic '" << topic_name << "'" << std::endl; @@ -211,7 +220,7 @@ void Participant::register_dynamic_type( if (pair.second) { - logger_ << utils::Logger::Level::DEBUG + logger_ << eprosima::is::utils::Logger::Level::DEBUG << "Registered type '" << type_name << "' in topic '" << topic_name << "'" << std::endl; @@ -219,7 +228,7 @@ void Participant::register_dynamic_type( } else { - logger_ << utils::Logger::Level::WARN + logger_ << eprosima::is::utils::Logger::Level::WARN << "Failed registering type '" << type_name << "' in topic '" << topic_name << "'" << std::endl; } @@ -322,62 +331,187 @@ bool Participant::dissociate_topic_from_dds_entity( } } -static void set_qos_from_attributes( - ::fastdds::dds::DomainParticipantQos& qos, - const eprosima::fastrtps::rtps::RTPSParticipantAttributes& attr) +eprosima::fastdds::dds::DomainParticipantQos Participant::get_default_participant_qos() +{ + eprosima::fastdds::dds::DomainParticipantQos df_pqos; + df_pqos.name("default_IS-FastDDS-SH_participant"); + + // By default use UDPv4 due to communication failures between dockers sharing the network with the host + // When it is solved in Fast-DDS delete the following lines and use the default builtin transport. + df_pqos.transport().use_builtin_transports = false; + auto udp_transport = std::make_shared<::fastdds::rtps::UDPv4TransportDescriptor>(); + df_pqos.transport().user_transports.push_back(udp_transport); + + return df_pqos; +} + +eprosima::fastdds::dds::DomainParticipantQos Participant::get_databroker_qos( + const YAML::Node& config) { - qos.user_data().setValue(attr.userData); - qos.allocation() = attr.allocation; - qos.properties() = attr.properties; - qos.wire_protocol().prefix = attr.prefix; - qos.wire_protocol().participant_id = attr.participantID; - qos.wire_protocol().builtin = attr.builtin; - qos.wire_protocol().port = attr.port; - qos.wire_protocol().throughput_controller = attr.throughputController; - qos.wire_protocol().default_unicast_locator_list = attr.defaultUnicastLocatorList; - qos.wire_protocol().default_multicast_locator_list = attr.defaultMulticastLocatorList; - - if (attr.useBuiltinTransports) + // Use the Participant QoS as base for the Databroker QoS + eprosima::fastdds::dds::DomainParticipantQos pqos = get_default_participant_qos(); + + // Server id + // Show warning if both set + if (config["server_id"] && config["server_guid"]) { - // By default use UDPv4 due to communication failures between dockers sharing the network with the host - // When it is solved in Fast-DDS delete the following lines and use the default builtin transport. - qos.transport().use_builtin_transports = false; - auto udp_transport = std::make_shared<::fastdds::rtps::UDPv4TransportDescriptor>(); - qos.transport().user_transports.push_back(udp_transport); + logger_ << eprosima::is::utils::Logger::Level::WARN + << "Server ID and Server GUID are both set. Only GUID will be used." << std::endl; + } + + // Set GUID depending on the id + pqos.wire_protocol().prefix = eprosima::is::sh::fastdds::utils::guid_server(config["server_id"], config["server_guid"]); + pqos.name("DataBroker_IS-FastDDS-SH_participant_" + + eprosima::is::sh::fastdds::utils::guid_to_string(pqos.wire_protocol().prefix)); + + // Listening addresses + if (config["listening_addresses"]) + { + // Configure listening address + for (auto address : config["listening_addresses"]) + { + std::string ip; + uint16_t port; + + // Get address values. If not present, send error + if (address["ip"]) + { + ip = address["ip"].as(); + } + else + { + logger_ << eprosima::is::utils::Logger::Level::WARN + << "The addresses in 'listening_addresses' must contain a tag 'ip'." << std::endl; + continue; + } + + if (address["port"]) + { + port = address["port"].as(); + } + else + { + logger_ << eprosima::is::utils::Logger::Level::WARN + << "The addresses in 'listening_addresses' must contain a tag 'port'. " << std::endl; + continue; + } + + // Create TCPv4 transport + std::shared_ptr descriptor = + std::make_shared(); + + descriptor->add_listener_port(port); + descriptor->set_WAN_address(ip); + + descriptor->sendBufferSize = 0; + descriptor->receiveBufferSize = 0; + + pqos.transport().user_transports.push_back(descriptor); + + // Create Locator + eprosima::fastrtps::rtps::Locator_t tcp_locator; + tcp_locator.kind = LOCATOR_KIND_TCPv4; + + eprosima::fastrtps::rtps::IPLocator::setIPv4(tcp_locator, ip); + eprosima::fastrtps::rtps::IPLocator::setWan(tcp_locator, ip); + eprosima::fastrtps::rtps::IPLocator::setLogicalPort(tcp_locator, port); + eprosima::fastrtps::rtps::IPLocator::setPhysicalPort(tcp_locator, port); + + pqos.wire_protocol().builtin.metatrafficUnicastLocatorList.push_back(tcp_locator); + + logger_ << eprosima::is::utils::Logger::Level::DEBUG + << "Server listening in: " << ip << ":" << port << std::endl; + } } else { - qos.transport().user_transports = attr.userTransports; - qos.transport().use_builtin_transports = attr.useBuiltinTransports; + logger_ << eprosima::is::utils::Logger::Level::WARN + << "Server has no listening address." + << "It will not discover or connect to other servers." + << std::endl; } - - qos.transport().send_socket_buffer_size = attr.sendSocketBufferSize; - qos.transport().listen_socket_buffer_size = attr.listenSocketBufferSize; - qos.name() = attr.getName(); -} -::fastdds::dds::DomainParticipant* Participant::create_participant_with_profile( - const std::string& profile_name) -{ - using namespace fastrtps::xmlparser; - - fastrtps::ParticipantAttributes attr; - if (XMLP_ret::XML_OK == XMLProfileManager::fillParticipantAttributes(profile_name, attr)) + // Connection addresses + if (config["connection_addresses"]) { - ::fastdds::dds::DomainParticipantQos qos = ::fastdds::dds::PARTICIPANT_QOS_DEFAULT; - set_qos_from_attributes(qos, attr.rtps); + // Configure listening address + for (auto address : config["connection_addresses"]) + { + std::string ip; + uint16_t port; + + // Get address values. If not present, send error + if (address["ip"]) + { + ip = address["ip"].as(); + } + else + { + logger_ << eprosima::is::utils::Logger::Level::WARN + << "The addresses in 'connection_addresses' must contain a tag 'ip'." << std::endl; + continue; + } - return ::fastdds::dds::DomainParticipantFactory::get_instance()-> - create_participant(attr.domainId, qos); + if (address["port"]) + { + port = address["port"].as(); + } + else + { + logger_ << eprosima::is::utils::Logger::Level::WARN + << "The addresses in 'connection_addresses' must contain a tag 'port'." << std::endl; + continue; + } + + if (! (address["server_id"] || address["server_guid"])) + { + logger_ << eprosima::is::utils::Logger::Level::WARN + << "The addresses in 'connection_addresses' must contain a tag 'server_id' or 'server_guid'." + << std::endl; + continue; + } + + // Set Server GUID + eprosima::fastrtps::rtps::RemoteServerAttributes server_attr; + server_attr.guidPrefix = eprosima::is::sh::fastdds::utils::guid_server( + address["server_id"], + address["server_guid"]); + + // Discovery server locator configuration TCP + eprosima::fastrtps::rtps::Locator_t tcp_locator; + tcp_locator.kind = LOCATOR_KIND_TCPv4; + eprosima::fastrtps::rtps::IPLocator::setIPv4(tcp_locator, ip); + eprosima::fastrtps::rtps::IPLocator::setLogicalPort(tcp_locator, port); + eprosima::fastrtps::rtps::IPLocator::setPhysicalPort(tcp_locator, port); + server_attr.metatrafficUnicastLocatorList.push_back(tcp_locator); + + pqos.wire_protocol().builtin.discovery_config.m_DiscoveryServers.push_back(server_attr); + + logger_ << eprosima::is::utils::Logger::Level::DEBUG + << "Connecting to remote server with GUID: " << server_attr.guidPrefix + << " in: " << ip << ":" << port << std::endl; + } } else { - std::ostringstream err; - err << "Failed to fetch Fast DDS participant attributes from XML " - << "for profile named '" << profile_name << "'"; - - throw DDSMiddlewareException(logger_, err.str()); + logger_ << eprosima::is::utils::Logger::Level::INFO + << "Server has no connection addresses. It will not try to connect to remote servers" + << std::endl; } + + // TODO decide the discovery server configuration + pqos.wire_protocol().builtin.discovery_config.leaseDuration = fastrtps::c_TimeInfinite; + pqos.wire_protocol().builtin.discovery_config.leaseDuration_announcementperiod = + fastrtps::Duration_t(2, 0); + + // Set this participant as a SERVER + pqos.wire_protocol().builtin.discovery_config.discoveryProtocol = + fastrtps::rtps::DiscoveryProtocol::SERVER; + + logger_ << eprosima::is::utils::Logger::Level::DEBUG + << "Databroker initialized with GUID: " << pqos.wire_protocol().prefix << std::endl; + + return pqos; } } // namespace fastdds diff --git a/src/Participant.hpp b/src/Participant.hpp index 412422f..f8d834c 100644 --- a/src/Participant.hpp +++ b/src/Participant.hpp @@ -21,6 +21,7 @@ #include #include +#include #include #include #include @@ -68,7 +69,7 @@ class Participant * in the *YAML* configuration file. * * @param[in] config The configuration provided by the user. - * It must contain two keys in the *YAML* map: + * In case of fastdds type it can contain two keys in the *YAML* map: * * - `file_path`: Specifies the path to the XML profile that will be used to configure the * *DomainParticipant*. More information on how to write these XML profiles can be found @@ -79,6 +80,24 @@ class Participant * that corresponds to the configuration profile that we want this Participant * to be configured with. * + * In case of databroker type it can contain three keys in the *YAML* map: + * + * - `server_id`: Specifies the Discovery Server ID in order to generate its GUID. + * It is incompatible with setting the GUID. + * + * - `server_guid`: Specifies the Discovery Server GUID. + * It is incompatible with setting the ID. + * + * - `listening_addresses`: Specifies a list of TCP listening addresses. + * - `ip`: Provides the public IP where the Server will be listening. + * - `port`: Provides the port where the Server will be listening. + * + * - `connection_addresses`: Specifies a list of TCP connection addresses. + * - `ip`: Provides the public IP of the Server to connect to. + * - `port`: Provides the port of the Server to connect to. + * - `server_id`: Provides the ID of the remote Server to connect to [incompatible with GUID]. + * - `server_guid`: Provides the GUID of the remote Server to connect to [incompatible with ID]. + * * @throws DDSMiddlewareException If the XML profile was incorrect and, thus, the * *DomainParticipant* could not be created. */ @@ -93,12 +112,12 @@ class Participant /** * @brief Construct a *Fast DDS DomainParticipant*, given its DDS domain ID. * - * @param[in] domain_id The DDS domain ID for this participant. + * @param[in] config The configuration provided by the user. * * @throws DDSMiddlewareException If the *DomainParticipant* could not be created. */ void build_participant( - const ::fastdds::dds::DomainId_t& domain_id = 0); + const YAML::Node& config); /** * @brief Get the associate *FastDDS DomainParticipant* attribute. @@ -193,23 +212,37 @@ class Participant ::fastdds::dds::Topic* topic, ::fastdds::dds::DomainEntity* entity); -private: +protected: /** - * @brief Create a *Fast DDS DomainParticipant* using a certain profile. + * @brief Get Fast DDS System Handle Participant default QoS * - * @note This method is a workaround due to `v2.0.X` versions of *Fast DDS* not including - * this method inside the *DomainParticipantFactory* class. - * - * @param[in] profile_name The XML profile name for the participant. + * @return Default Participant QoS + */ + eprosima::fastdds::dds::DomainParticipantQos get_default_participant_qos(); + + /** + * @brief Get Databroker DomainParticipantQos. + * @details The transport used over WAN is TCP. + * It calls \c get_participant_qos to reuse Participant YAML tags and then applies the specific Databroker tags: + * Databroker tags: + * * server_id: ID of the Discovery Server. It must be within the valid range [0:256). + * * listening_addresses: Listening addresses (public) for Discovery Server to listen in TCP. + * * ip + * * port + * * connection_addresses: Connection addresses for Discovery Server to connect to other servers. + * * ip + * * port + * * server_id * - * @returns A correctly initialized DomainParticipant. + * @param[in] config The configuration provided by the user. * - * @throws DDSMiddlewareException if some error occurs during the creation process. + * @return Specific QoS by user configuration. */ - ::fastdds::dds::DomainParticipant* create_participant_with_profile( - const std::string& profile_name); + eprosima::fastdds::dds::DomainParticipantQos get_databroker_qos( + const YAML::Node& config); +private: /** * Class members. diff --git a/src/Server.cpp b/src/Server.cpp index 823941b..9e9fb99 100644 --- a/src/Server.cpp +++ b/src/Server.cpp @@ -27,9 +27,9 @@ #include #include #include -#if FASTRTPS_VERSION_MINOR >= 2 +#if FASTRTPS_VERSION_MAJOR >= 2 && FASTRTPS_VERSION_MINOR >= 2 #include -#endif // if FASTRTPS_VERSION_MINOR >= 2 +#endif // if FASTRTPS_VERSION_MAJOR >= 2 && FASTRTPS_VERSION_MINOR >= 2 #include #include @@ -546,11 +546,11 @@ void Server::on_data_available( if (!stop_cleaner_ && fastrtps::types::ReturnCode_t::RETCODE_OK == reply_entities_.dds_datareader->take_next_sample(reply_entities_.dynamic_data, &info)) { -#if FASTRTPS_VERSION_MINOR < 2 +#if FASTRTPS_VERSION_MAJOR < 2 || FASTRTPS_VERSION_MINOR < 2 if (::fastdds::dds::InstanceStateKind::ALIVE == info.instance_state) #else if (::fastdds::dds::InstanceStateKind::ALIVE_INSTANCE_STATE == info.instance_state) -#endif // if FASTRTPS_VERSION_MINOR < 2 +#endif // if FASTRTPS_VERSION_MAJOR < 2 || FASTRTPS_VERSION_MINOR < 2 { logger_ << utils::Logger::Level::DEBUG << "Process incoming data available for service reply topic '" diff --git a/src/Subscriber.cpp b/src/Subscriber.cpp index 82aebae..f628734 100644 --- a/src/Subscriber.cpp +++ b/src/Subscriber.cpp @@ -23,9 +23,9 @@ #include #include #include -#if FASTRTPS_VERSION_MINOR >= 2 +#if FASTRTPS_VERSION_MAJOR >= 2 && FASTRTPS_VERSION_MINOR >= 2 #include -#endif // if FASTRTPS_VERSION_MINOR >= 2 +#endif // if FASTRTPS_VERSION_MAJOR >= 2 && FASTRTPS_VERSION_MINOR >= 2 #include #include @@ -214,11 +214,11 @@ void Subscriber::on_data_available( if (!stop_cleaner_ && fastrtps::types::ReturnCode_t::RETCODE_OK == dds_datareader_->take_next_sample(dynamic_data_, &info)) { -#if FASTRTPS_VERSION_MINOR < 2 +#if FASTRTPS_VERSION_MAJOR < 2 || FASTRTPS_VERSION_MINOR < 2 if (::fastdds::dds::InstanceStateKind::ALIVE == info.instance_state) #else if (::fastdds::dds::InstanceStateKind::ALIVE_INSTANCE_STATE == info.instance_state) -#endif // if FASTRTPS_VERSION_MINOR < 2 +#endif // if FASTRTPS_VERSION_MAJOR < 2 || FASTRTPS_VERSION_MINOR < 2 { logger_ << utils::Logger::Level::DEBUG << "Processing incoming data available for topic '" diff --git a/src/SystemHandle.cpp b/src/SystemHandle.cpp index 81f77b1..620e363 100644 --- a/src/SystemHandle.cpp +++ b/src/SystemHandle.cpp @@ -1,5 +1,5 @@ /* - * Copyright 2019 Proyectos y Sistemas de Mantenimiento SL (eProsima). + * Copyright 2021 Proyectos y Sistemas de Mantenimiento SL (eProsima). * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -85,6 +85,7 @@ class SystemHandle : public virtual FullSystem } catch (DDSMiddlewareException& e) { + logger_ << utils::Logger::Level::ERROR << "Participant creation failed." << std::endl; e.from_logger << utils::Logger::Level::ERROR << e.what() << std::endl; return false; } @@ -301,4 +302,5 @@ class SystemHandle : public virtual FullSystem } // namespace is } // namespace eprosima +// TODO aliases must come from CMAKE IS_REGISTER_SYSTEM("fastdds", eprosima::is::sh::fastdds::SystemHandle) diff --git a/src/utils/databroker/utils.cpp b/src/utils/databroker/utils.cpp new file mode 100644 index 0000000..b6372e4 --- /dev/null +++ b/src/utils/databroker/utils.cpp @@ -0,0 +1,81 @@ +/* + * Copyright 2019 Proyectos y Sistemas de Mantenimiento SL (eProsima). + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#include "Participant.hpp" +#include "DDSMiddlewareException.hpp" +#include "Conversion.hpp" +#include "utils/databroker/utils.hpp" + +#include +#include + +#include +#include + +#include + +namespace eprosima { +namespace is { +namespace sh { +namespace fastdds { +namespace utils { + +eprosima::fastrtps::rtps::GuidPrefix_t guid_server( + uint8_t id) +{ + eprosima::fastrtps::rtps::GuidPrefix_t guid; + std::istringstream(SERVER_DEFAULT_GUID) >> guid; + guid.value[SERVER_DEFAULT_GUID_ID_INDEX] = static_cast(id); + return guid; +} + +eprosima::fastrtps::rtps::GuidPrefix_t guid_server( + const YAML::Node& server_id, + const YAML::Node& server_guid) +{ + if (server_guid) + { + // Server GUID set and used + eprosima::fastrtps::rtps::GuidPrefix_t guid; + std::istringstream(server_guid.as()) >> guid; + return guid; // There is no easy wat to directly return the guid + } + else if (server_id && !server_guid) + { + // Server ID set without GUID set + return guid_server(server_id.as() % std::numeric_limits::max()); + } + else + { + // Server GUID by default with ID 0 + return guid_server(0); + } +} + +std::string guid_to_string( + const eprosima::fastrtps::rtps::GuidPrefix_t& guid) +{ + std::ostringstream guid_ostream; + guid_ostream << guid; + return guid_ostream.str(); +} + +} // namespace utils +} // namespace fastdds +} // namespace sh +} // namespace is +} // namespace eprosima diff --git a/src/utils/databroker/utils.hpp b/src/utils/databroker/utils.hpp new file mode 100644 index 0000000..55a9746 --- /dev/null +++ b/src/utils/databroker/utils.hpp @@ -0,0 +1,84 @@ +// Copyright 2021 Proyectos y Sistemas de Mantenimiento SL (eProsima). +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +/** + * @file utils.hpp + * + */ + +#ifndef _IS_SH_FASTDDS__INTERNAL__UTILS_HPP_ +#define _IS_SH_FASTDDS__INTERNAL__UTILS_HPP_ + +#include +#include + +#include + +namespace eprosima { +namespace is { +namespace sh { +namespace fastdds { + +namespace utils { + +#define SERVER_DEFAULT_GUID "01.0f.00.44.41.54.95.42.52.4f.4b.45.52" +#define SERVER_DEFAULT_GUID_ID_INDEX 2 + +inline eprosima::fastrtps::rtps::GuidPrefix_t guid_server( + uint8_t id) +{ + eprosima::fastrtps::rtps::GuidPrefix_t guid; + std::istringstream(SERVER_DEFAULT_GUID) >> guid; + guid.value[SERVER_DEFAULT_GUID_ID_INDEX] = static_cast(id); + return guid; +} + +inline eprosima::fastrtps::rtps::GuidPrefix_t guid_server( + const YAML::Node& server_id, + const YAML::Node& server_guid) +{ + if (server_guid) + { + // Server GUID set and used + eprosima::fastrtps::rtps::GuidPrefix_t guid; + std::istringstream(server_guid.as()) >> guid; + return guid; // There is no easy wat to directly return the guid + } + else if (server_id) + { + // Server ID set without GUID set + return guid_server(server_id.as() % std::numeric_limits::max()); + } + else + { + // Server GUID by default with ID 0 + return guid_server(0); + } +} + +inline std::string guid_to_string( + const eprosima::fastrtps::rtps::GuidPrefix_t& guid) +{ + std::ostringstream guid_ostream; + guid_ostream << guid; + return guid_ostream.str(); +} + +} // namespace utils +} // namespace fastdds +} // namespace sh +} // namespace is +} // namespace eprosima + +#endif // _IS_SH_FASTDDS__INTERNAL__UTILS_HPP_ diff --git a/test/unitary/qos.cpp b/test/unitary/qos.cpp new file mode 100644 index 0000000..5947e52 --- /dev/null +++ b/test/unitary/qos.cpp @@ -0,0 +1,57 @@ +/* + * Copyright 2021 - present Proyectos y Sistemas de Mantenimiento SL (eProsima). + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#include + +#include + +namespace fastdds = eprosima::fastdds; + +namespace eprosima { +namespace is { +namespace sh { +namespace fastdds { +namespace test { + +TEST(FastDDS_set_qos, get_databroker_qos) +{ + +} + +TEST(FastDDS_set_qos, get_databroker_qos) +{ + +} + +TEST(FastDDS_set_qos, get_databroker_qos) +{ + +} + +} // namespace test +} // namespace fastdds +} // namespace sh +} // namespace is +} // namespace eprosima + +int main( + int argc, + char** argv) +{ + testing::InitGoogleTest(&argc, argv); + return RUN_ALL_TESTS(); +}