OpenDDS  Snapshot(2023/04/07-19:43)
Classes | Public Types | Public Member Functions | Public Attributes | Private Types | Private Member Functions | Private Attributes | List of all members
OpenDDS::ICE::EndpointManager Struct Reference

#include <EndpointManager.h>

Inheritance diagram for OpenDDS::ICE::EndpointManager:
Inheritance graph
[legend]
Collaboration diagram for OpenDDS::ICE::EndpointManager:
Collaboration graph
[legend]

Classes

struct  ChangePasswordTask
 
struct  ServerReflexiveTask
 

Public Types

typedef std::set< std::string > FoundationSet
 

Public Member Functions

 EndpointManager (AgentImpl *a_agent_impl, DCPS::WeakRcHandle< Endpoint > a_endpoint)
 
const AgentInfoagent_info () const
 
const FoundationSetfoundations () const
 
void add_agent_info_listener (const DCPS::GUID_t &a_local_guid, DCPS::WeakRcHandle< AgentInfoListener > a_agent_info_listener)
 
void remove_agent_info_listener (const DCPS::GUID_t &a_local_guid)
 
void start_ice (const DCPS::GUID_t &a_local_guid, const DCPS::GUID_t &a_remote_guid, const AgentInfo &a_remote_agent_info)
 
void stop_ice (const DCPS::GUID_t &local_guid, const DCPS::GUID_t &remote_guid)
 
ACE_INET_Addr get_address (const DCPS::GUID_t &a_local_guid, const DCPS::GUID_t &a_remote_guid) const
 
void receive (const ACE_INET_Addr &a_local_address, const ACE_INET_Addr &a_remote_address, const STUN::Message &a_message)
 
void set_responsible_checklist (const STUN::TransactionId &a_transaction_id, ChecklistPtr a_checklist)
 
void unset_responsible_checklist (const STUN::TransactionId &a_transaction_id, ChecklistPtr a_checklist)
 
void set_responsible_checklist (const GuidPair &a_guid_pair, ChecklistPtr a_checklist)
 
void unset_responsible_checklist (const GuidPair &a_guid_pair, ChecklistPtr a_checklist)
 
void set_responsible_checklist (const std::string &a_username, ChecklistPtr a_checklist)
 
void unset_responsible_checklist (const std::string &a_username, ChecklistPtr a_checklist)
 
void unfreeze ()
 
void unfreeze (const FoundationType &a_foundation)
 
void compute_active_foundations (ActiveFoundationSet &a_active_foundations) const
 
void check_invariants () const
 
void ice_connect (const GuidSetType &guids, const ACE_INET_Addr &addr)
 
void ice_disconnect (const GuidSetType &guids, const ACE_INET_Addr &addr)
 
void network_change ()
 
void send (const ACE_INET_Addr &address, const STUN::Message &message)
 
void purge ()
 
- Public Member Functions inherited from OpenDDS::DCPS::RcObject
virtual ~RcObject ()
 
virtual void _add_ref ()
 
virtual void _remove_ref ()
 
long ref_count () const
 
WeakObject_get_weak_object () const
 

Public Attributes

AgentImpl *const agent_impl
 
DCPS::WeakRcHandle< Endpoint > const endpoint
 

Private Types

typedef std::deque< DeferredTriggeredCheckDeferredTriggeredCheckListType
 
typedef std::map< std::string, DeferredTriggeredCheckListTypeDeferredTriggeredChecksType
 
typedef std::map< std::string, ChecklistPtrUsernameToChecklistType
 
typedef std::map< STUN::TransactionId, ChecklistPtrTransactionIdToChecklistType
 
typedef std::map< GuidPair, ChecklistPtrGuidPairToChecklistType
 
typedef std::map< DCPS::GUID_t, DCPS::WeakRcHandle< AgentInfoListener >, DCPS::GUID_tKeyLessThanAgentInfoListenersType
 

Private Member Functions

void change_username ()
 
void change_password (bool password_only)
 
void set_host_addresses (const AddressListType &a_host_addresses)
 
void set_server_reflexive_address (const ACE_INET_Addr &a_server_reflexive_address, const ACE_INET_Addr &a_stun_server_address)
 
void regenerate_agent_info (bool password_only)
 
void server_reflexive_task (const DCPS::MonotonicTimePoint &a_now)
 
bool success_response (const STUN::Message &a_message)
 
bool error_response (const STUN::Message &a_message)
 
ChecklistPtr create_checklist (const AgentInfo &a_remote_agent_info)
 
STUN::Message make_unknown_attributes_error_response (const STUN::Message &a_message, const std::vector< STUN::AttributeType > &a_unknown_attributes)
 
STUN::Message make_bad_request_error_response (const STUN::Message &a_message, const std::string &a_reason)
 
STUN::Message make_unauthorized_error_response (const STUN::Message &a_message)
 
void request (const ACE_INET_Addr &a_local_address, const ACE_INET_Addr &a_remote_address, const STUN::Message &a_message)
 
void indication (const ACE_INET_Addr &a_local_address, const ACE_INET_Addr &a_remote_address, const STUN::Message &a_message)
 
void success_response (const ACE_INET_Addr &a_local_address, const ACE_INET_Addr &a_remote_address, const STUN::Message &a_message)
 
void error_response (const ACE_INET_Addr &a_local_address, const ACE_INET_Addr &a_remote_address, const STUN::Message &a_message)
 

Private Attributes

AddressListType host_addresses_
 
ACE_INET_Addr server_reflexive_address_
 
ACE_INET_Addr stun_server_address_
 
ACE_UINT64 ice_tie_breaker_
 
AgentInfo agent_info_
 
FoundationSet foundations_
 
bool requesting_
 
size_t send_count_
 
ACE_INET_Addr next_stun_server_address_
 
STUN::Message binding_request_
 
DeferredTriggeredChecksType deferred_triggered_checks_
 
UsernameToChecklistType username_to_checklist_
 
TransactionIdToChecklistType transaction_id_to_checklist_
 
GuidPairToChecklistType guid_pair_to_checklist_
 
AgentInfoListenersType agent_info_listeners_
 
DCPS::RcHandle< ServerReflexiveTaskserver_reflexive_task_
 
DCPS::RcHandle< ChangePasswordTaskchange_password_task_
 

Additional Inherited Members

- Protected Member Functions inherited from OpenDDS::DCPS::RcObject
 RcObject ()
 

Detailed Description

Definition at line 51 of file EndpointManager.h.

Member Typedef Documentation

◆ AgentInfoListenersType

Definition at line 198 of file EndpointManager.h.

◆ DeferredTriggeredCheckListType

Definition at line 182 of file EndpointManager.h.

◆ DeferredTriggeredChecksType

Definition at line 183 of file EndpointManager.h.

◆ FoundationSet

typedef std::set<std::string> OpenDDS::ICE::EndpointManager::FoundationSet

Definition at line 62 of file EndpointManager.h.

◆ GuidPairToChecklistType

Definition at line 195 of file EndpointManager.h.

◆ TransactionIdToChecklistType

Definition at line 191 of file EndpointManager.h.

◆ UsernameToChecklistType

Definition at line 187 of file EndpointManager.h.

Constructor & Destructor Documentation

◆ EndpointManager()

OpenDDS::ICE::EndpointManager::EndpointManager ( AgentImpl a_agent_impl,
DCPS::WeakRcHandle< Endpoint a_endpoint 
)

Definition at line 28 of file EndpointManager.cpp.

References agent_info_, binding_request_, change_username(), OpenDDS::STUN::Message::clear_transaction_id(), endpoint, OpenDDS::ICE::FULL, ice_tie_breaker_, OpenDDS::DCPS::WeakRcHandle< T >::lock(), set_host_addresses(), TheSecurityRegistry, and OpenDDS::ICE::AgentInfo::type.

28  :
29  agent_impl(a_agent_impl),
30  endpoint(a_endpoint),
31  requesting_(true),
32  send_count_(0),
33  server_reflexive_task_(DCPS::make_rch<ServerReflexiveTask>(rchandle_from(this))),
34  change_password_task_(DCPS::make_rch<ChangePasswordTask>(rchandle_from(this)))
35 {
36 
38 
39  // Set the type.
41 
42  TheSecurityRegistry->builtin_config()->get_utility()->generate_random_bytes(&ice_tie_breaker_, sizeof(ice_tie_breaker_));
43 
45  DCPS::RcHandle<Endpoint> e = endpoint.lock();
46  if (e) {
47  set_host_addresses(e->host_addresses());
48  }
49 }
void set_host_addresses(const AddressListType &a_host_addresses)
RcHandle< T > lock() const
Definition: RcObject.h:188
void clear_transaction_id()
Definition: Stun.cpp:611
#define TheSecurityRegistry
DCPS::RcHandle< ChangePasswordTask > change_password_task_
DCPS::RcHandle< ServerReflexiveTask > server_reflexive_task_
RcHandle< T > rchandle_from(T *pointer)
Definition: RcHandle_T.h:310
DCPS::WeakRcHandle< Endpoint > const endpoint
AgentType type
Definition: Ice.h:75

Member Function Documentation

◆ add_agent_info_listener()

void OpenDDS::ICE::EndpointManager::add_agent_info_listener ( const DCPS::GUID_t a_local_guid,
DCPS::WeakRcHandle< AgentInfoListener a_agent_info_listener 
)
inline

Definition at line 68 of file EndpointManager.h.

70  {
71  agent_info_listeners_[a_local_guid] = a_agent_info_listener;
72  }
AgentInfoListenersType agent_info_listeners_

◆ agent_info()

const AgentInfo& OpenDDS::ICE::EndpointManager::agent_info ( ) const
inline

Definition at line 57 of file EndpointManager.h.

Referenced by regenerate_agent_info().

58  {
59  return agent_info_;
60  }

◆ change_password()

void OpenDDS::ICE::EndpointManager::change_password ( bool  password_only)
private

Definition at line 176 of file EndpointManager.cpp.

References agent_info_, guid_pair_to_checklist_, OpenDDS::ICE::AgentInfo::password, regenerate_agent_info(), TheSecurityRegistry, and OpenDDS::DCPS::to_hex_dds_string().

Referenced by change_username().

177 {
178  if (password_only && guid_pair_to_checklist_.empty()) {
179  return;
180  }
181 
182  unsigned char password[16] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
183  TheSecurityRegistry->builtin_config()->get_utility()->generate_random_bytes(password, sizeof(password));
185  regenerate_agent_info(password_only);
186 }
void regenerate_agent_info(bool password_only)
std::string password
Definition: Ice.h:78
String to_hex_dds_string(const unsigned char *data, const size_t size, const char delim, const size_t delim_every)
#define TheSecurityRegistry
GuidPairToChecklistType guid_pair_to_checklist_

◆ change_username()

void OpenDDS::ICE::EndpointManager::change_username ( )
private

Definition at line 167 of file EndpointManager.cpp.

References agent_info_, change_password(), TheSecurityRegistry, OpenDDS::DCPS::to_hex_dds_string(), and OpenDDS::ICE::AgentInfo::username.

Referenced by EndpointManager(), and start_ice().

168 {
169  // Generate the username.
170  unsigned char username[16] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
171  TheSecurityRegistry->builtin_config()->get_utility()->generate_random_bytes(username, sizeof(username));
173  change_password(false);
174 }
void change_password(bool password_only)
String to_hex_dds_string(const unsigned char *data, const size_t size, const char delim, const size_t delim_every)
#define TheSecurityRegistry
std::string username
Definition: Ice.h:77

◆ check_invariants()

void OpenDDS::ICE::EndpointManager::check_invariants ( ) const

Definition at line 735 of file EndpointManager.cpp.

References deferred_triggered_checks_, guid_pair_to_checklist_, OpenDDS::ICE::Configuration::instance(), OPENDDS_ASSERT, OpenDDS::ICE::Configuration::server_reflexive_address_period(), transaction_id_to_checklist_, and username_to_checklist_.

736 {
737  // Check for expired deferred checks.
738  for (DeferredTriggeredChecksType::const_iterator pos = deferred_triggered_checks_.begin(),
739  limit = deferred_triggered_checks_.end(); pos != limit; ++pos) {
740  const DeferredTriggeredCheckListType& list = pos->second;
741  ACE_UNUSED_ARG(list);
742  OPENDDS_ASSERT(!list.empty());
744  }
745 
746  for (UsernameToChecklistType::const_iterator pos = username_to_checklist_.begin(),
747  limit = username_to_checklist_.end(); pos != limit; ++pos) {
748  ChecklistPtr checklist = pos->second;
749  OPENDDS_ASSERT(checklist->original_remote_agent_info().username == pos->first);
750  checklist->check_invariants();
751  }
752 
753  for (TransactionIdToChecklistType::const_iterator pos = transaction_id_to_checklist_.begin(),
754  limit = transaction_id_to_checklist_.end(); pos != limit; ++pos) {
755  ChecklistPtr checklist = pos->second;
756  ACE_UNUSED_ARG(checklist);
757  OPENDDS_ASSERT(checklist->has_transaction_id(pos->first));
758  }
759 
760  for (GuidPairToChecklistType::const_iterator pos = guid_pair_to_checklist_.begin(),
761  limit = guid_pair_to_checklist_.end(); pos != limit; ++pos) {
762  ChecklistPtr checklist = pos->second;
763  ACE_UNUSED_ARG(checklist);
764  OPENDDS_ASSERT(checklist->has_guid_pair(pos->first));
765  }
766 }
DCPS::RcHandle< Checklist > ChecklistPtr
Definition: Checklist.h:288
#define OPENDDS_ASSERT(C)
Definition: Definitions.h:66
static Configuration * instance()
Definition: Ice.cpp:109
TransactionIdToChecklistType transaction_id_to_checklist_
std::deque< DeferredTriggeredCheck > DeferredTriggeredCheckListType
UsernameToChecklistType username_to_checklist_
GuidPairToChecklistType guid_pair_to_checklist_
void server_reflexive_address_period(const DCPS::TimeDuration &x)
Definition: RTPS/ICE/Ice.h:118
DeferredTriggeredChecksType deferred_triggered_checks_

◆ compute_active_foundations()

void OpenDDS::ICE::EndpointManager::compute_active_foundations ( ActiveFoundationSet a_active_foundations) const

Definition at line 726 of file EndpointManager.cpp.

References username_to_checklist_.

727 {
728  for (UsernameToChecklistType::const_iterator pos = username_to_checklist_.begin(),
729  limit = username_to_checklist_.end(); pos != limit; ++pos) {
730  ChecklistPtr checklist = pos->second;
731  checklist->compute_active_foundations(a_active_foundations);
732  }
733 }
DCPS::RcHandle< Checklist > ChecklistPtr
Definition: Checklist.h:288
UsernameToChecklistType username_to_checklist_

◆ create_checklist()

ChecklistPtr OpenDDS::ICE::EndpointManager::create_checklist ( const AgentInfo a_remote_agent_info)
private

Definition at line 406 of file EndpointManager.cpp.

References agent_info_, deferred_triggered_checks_, ice_tie_breaker_, OpenDDS::DCPS::ref(), and OpenDDS::ICE::AgentInfo::username.

Referenced by regenerate_agent_info(), and start_ice().

407 {
408  ChecklistPtr checklist = DCPS::make_rch<Checklist>(this, DCPS::ref(agent_info_), DCPS::ref(remote_agent_info), ice_tie_breaker_);
409  // Add the deferred triggered first in case there was a nominating check.
410  DeferredTriggeredChecksType::iterator pos = deferred_triggered_checks_.find(remote_agent_info.username);
411 
412  if (pos != deferred_triggered_checks_.end()) {
413  const DeferredTriggeredCheckListType& list = pos->second;
414 
415  for (DeferredTriggeredCheckListType::const_iterator pos2 = list.begin(), limit2 = list.end(); pos2 != limit2; ++pos2) {
416  checklist->generate_triggered_check(pos2->local_address, pos2->remote_address, pos2->priority, pos2->use_candidate);
417  }
418 
419  deferred_triggered_checks_.erase(pos);
420  }
421 
422  checklist->unfreeze();
423 
424  return checklist;
425 }
reference_wrapper< T > ref(T &r)
Definition: RcHandle_T.h:237
DCPS::RcHandle< Checklist > ChecklistPtr
Definition: Checklist.h:288
std::deque< DeferredTriggeredCheck > DeferredTriggeredCheckListType
DeferredTriggeredChecksType deferred_triggered_checks_

◆ error_response() [1/2]

bool OpenDDS::ICE::EndpointManager::error_response ( const STUN::Message a_message)
private

Definition at line 380 of file EndpointManager.cpp.

References ACE_ERROR, ACE_TEXT(), binding_request_, OpenDDS::STUN::Message::get_error_code(), OpenDDS::STUN::Message::get_error_reason(), OpenDDS::STUN::Message::get_unknown_attributes(), OpenDDS::STUN::Message::has_error_code(), OpenDDS::STUN::Message::has_unknown_attributes(), LM_WARNING, OpenDDS::STUN::Message::transaction_id, and OpenDDS::STUN::UNKNOWN_ATTRIBUTE.

Referenced by error_response(), and receive().

381 {
382  if (a_message.transaction_id != binding_request_.transaction_id) {
383  return false;
384  }
385 
386  if (a_message.has_error_code()) {
387  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::error_response: WARNING STUN error response code=%d reason=%s\n"), a_message.get_error_code(), a_message.get_error_reason().c_str()));
388 
389  if (a_message.get_error_code() == STUN::UNKNOWN_ATTRIBUTE && a_message.has_unknown_attributes()) {
390  std::vector<STUN::AttributeType> unknown_attributes = a_message.get_unknown_attributes();
391 
392  for (std::vector<STUN::AttributeType>::const_iterator pos = unknown_attributes.begin(),
393  limit = unknown_attributes.end(); pos != limit; ++pos) {
394  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::error_response: WARNING Unknown STUN attribute %d\n"), *pos));
395  }
396  }
397  }
398 
399  else {
400  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::error_response: WARNING STUN error response (no code)\n")));
401  }
402 
403  return true;
404 }
#define ACE_ERROR(X)
TransactionId transaction_id
Definition: Stun.h:186
const ACE_UINT16 UNKNOWN_ATTRIBUTE
Definition: Stun.h:53
ACE_TEXT("TCP_Factory")

◆ error_response() [2/2]

void OpenDDS::ICE::EndpointManager::error_response ( const ACE_INET_Addr a_local_address,
const ACE_INET_Addr a_remote_address,
const STUN::Message a_message 
)
private

Definition at line 696 of file EndpointManager.cpp.

References ACE_ERROR, ACE_TEXT(), OpenDDS::STUN::BINDING, error_response(), LM_WARNING, OpenDDS::STUN::Message::method, OpenDDS::STUN::Message::transaction_id, and transaction_id_to_checklist_.

699 {
700  switch (a_message.method) {
701  case STUN::BINDING: {
702  if (error_response(a_message)) {
703  return;
704  }
705 
706  TransactionIdToChecklistType::const_iterator pos = transaction_id_to_checklist_.find(a_message.transaction_id);
707 
708  if (pos == transaction_id_to_checklist_.end()) {
709  // Probably a check that got cancelled.
710  return;
711  }
712 
713  // Checklist is responsible for updating the map.
714  // Checklist also checks for required parameters.
715  pos->second->error_response(a_local_address, a_remote_address, a_message);
716  }
717  break;
718 
719  default:
720  // Unknown method. Stop processing.
721  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::error_response: WARNING Unknown STUN method\n")));
722  break;
723  }
724 }
#define ACE_ERROR(X)
TransactionIdToChecklistType transaction_id_to_checklist_
bool error_response(const STUN::Message &a_message)
ACE_TEXT("TCP_Factory")

◆ foundations()

const FoundationSet& OpenDDS::ICE::EndpointManager::foundations ( ) const
inline

Definition at line 63 of file EndpointManager.h.

Referenced by OpenDDS::ICE::Checklist::unfreeze().

64  {
65  return foundations_;
66  }

◆ get_address()

ACE_INET_Addr OpenDDS::ICE::EndpointManager::get_address ( const DCPS::GUID_t a_local_guid,
const DCPS::GUID_t a_remote_guid 
) const

Definition at line 129 of file EndpointManager.cpp.

References guid_pair_to_checklist_.

131 {
132  GuidPair guidp(a_local_guid, a_remote_guid);
133  GuidPairToChecklistType::const_iterator pos = guid_pair_to_checklist_.find(guidp);
134 
135  if (pos != guid_pair_to_checklist_.end()) {
136  return pos->second->selected_address();
137  }
138 
139  return ACE_INET_Addr();
140 }
GuidPairToChecklistType guid_pair_to_checklist_

◆ ice_connect()

void OpenDDS::ICE::EndpointManager::ice_connect ( const GuidSetType guids,
const ACE_INET_Addr addr 
)
inline

Definition at line 146 of file EndpointManager.h.

References OpenDDS::DCPS::WeakRcHandle< T >::lock().

Referenced by OpenDDS::ICE::Checklist::execute(), and OpenDDS::ICE::Checklist::succeeded().

147  {
148  DCPS::RcHandle<Endpoint> e = endpoint.lock();
149  if (e) {
150  e->ice_connect(guids, addr);
151  }
152  }
RcHandle< T > lock() const
Definition: RcObject.h:188
DCPS::WeakRcHandle< Endpoint > const endpoint

◆ ice_disconnect()

void OpenDDS::ICE::EndpointManager::ice_disconnect ( const GuidSetType guids,
const ACE_INET_Addr addr 
)
inline

Definition at line 154 of file EndpointManager.h.

References OpenDDS::DCPS::WeakRcHandle< T >::lock(), and send().

Referenced by OpenDDS::ICE::Checklist::execute().

155  {
156  DCPS::RcHandle<Endpoint> e = endpoint.lock();
157  if (e) {
158  e->ice_disconnect(guids, addr);
159  }
160  }
RcHandle< T > lock() const
Definition: RcObject.h:188
DCPS::WeakRcHandle< Endpoint > const endpoint

◆ indication()

void OpenDDS::ICE::EndpointManager::indication ( const ACE_INET_Addr a_local_address,
const ACE_INET_Addr a_remote_address,
const STUN::Message a_message 
)
private

Definition at line 599 of file EndpointManager.cpp.

References ACE_ERROR, ACE_TEXT(), agent_info_, OpenDDS::STUN::BINDING, OpenDDS::STUN::Message::get_username(), OpenDDS::STUN::Message::has_fingerprint(), OpenDDS::STUN::Message::has_message_integrity(), LM_WARNING, OpenDDS::STUN::Message::method, OpenDDS::ICE::AgentInfo::password, OpenDDS::STUN::Message::unknown_comprehension_required_attributes(), OpenDDS::ICE::AgentInfo::username, username_to_checklist_, and OpenDDS::STUN::Message::verify_message_integrity().

Referenced by receive().

602 {
603  std::string username;
604 
605  if (!a_message.get_username(username)) {
606  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::indication: WARNING No USERNAME attribute\n")));
607  return;
608  }
609 
610  if (!a_message.has_message_integrity()) {
611  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::indication: WARNING No MESSAGE_INTEGRITY attribute\n")));
612  return;
613  }
614 
615  size_t idx = username.find(':');
616 
617  if (idx == std::string::npos) {
618  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::indication: WARNING USERNAME does not contain a colon\n")));
619  return;
620  }
621 
622  if (username.substr(0, idx) != agent_info_.username) {
623  // We expect this to happen.
624  return;
625  }
626 
627  const std::string remote_username = username.substr(++idx);
628 
629  // Check the message_integrity.
630  if (!a_message.verify_message_integrity(agent_info_.password)) {
631  // We expect this to happen.
632  return;
633  }
634 
635  std::vector<STUN::AttributeType> unknown_attributes = a_message.unknown_comprehension_required_attributes();
636 
637  if (!unknown_attributes.empty()) {
638  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::indication: WARNING Unknown comprehension required attributes\n")));
639  return;
640  }
641 
642  if (!a_message.has_fingerprint()) {
643  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::indication: WARNING No FINGERPRINT attribute\n")));
644  return;
645  }
646 
647  switch (a_message.method) {
648  case STUN::BINDING: {
649  // Section 11
650  UsernameToChecklistType::const_iterator pos = username_to_checklist_.find(remote_username);
651 
652  if (pos != username_to_checklist_.end()) {
653  // We have a checklist.
654  pos->second->indication();
655  }
656  }
657  break;
658 
659  default:
660  // Unknown method. Stop processing.
661  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::indication: WARNING Unknown STUN method\n")));
662  break;
663  }
664 }
#define ACE_ERROR(X)
std::string password
Definition: Ice.h:78
ACE_TEXT("TCP_Factory")
UsernameToChecklistType username_to_checklist_
std::string username
Definition: Ice.h:77

◆ make_bad_request_error_response()

STUN::Message OpenDDS::ICE::EndpointManager::make_bad_request_error_response ( const STUN::Message a_message,
const std::string &  a_reason 
)
private

Definition at line 442 of file EndpointManager.cpp.

References agent_info_, OpenDDS::STUN::Message::append_attribute(), OpenDDS::STUN::BAD_REQUEST, OpenDDS::STUN::Message::class_, OpenDDS::STUN::TransactionId::data, OpenDDS::STUN::ERROR_RESPONSE, OpenDDS::STUN::make_error_code(), OpenDDS::STUN::make_fingerprint(), OpenDDS::STUN::make_message_integrity(), memcpy(), OpenDDS::STUN::Message::method, OpenDDS::ICE::AgentInfo::password, OpenDDS::STUN::Message::password, and OpenDDS::STUN::Message::transaction_id.

Referenced by request().

444 {
445  STUN::Message response;
446  response.class_ = STUN::ERROR_RESPONSE;
447  response.method = a_message.method;
448  memcpy(response.transaction_id.data, a_message.transaction_id.data, sizeof(a_message.transaction_id.data));
449  response.append_attribute(STUN::make_error_code(STUN::BAD_REQUEST, a_reason));
450  response.append_attribute(STUN::make_message_integrity());
451  response.password = agent_info_.password;
452  response.append_attribute(STUN::make_fingerprint());
453  return response;
454 }
std::string password
Definition: Ice.h:78
void * memcpy(void *t, const void *s, size_t len)
Attribute make_error_code(ACE_UINT16 code, const std::string &reason)
Definition: Stun.cpp:99
Attribute make_message_integrity()
Definition: Stun.cpp:92
Attribute make_fingerprint()
Definition: Stun.cpp:139
const ACE_UINT16 BAD_REQUEST
Definition: Stun.h:51

◆ make_unauthorized_error_response()

STUN::Message OpenDDS::ICE::EndpointManager::make_unauthorized_error_response ( const STUN::Message a_message)
private

Definition at line 456 of file EndpointManager.cpp.

References agent_info_, OpenDDS::STUN::Message::append_attribute(), OpenDDS::STUN::Message::class_, OpenDDS::STUN::TransactionId::data, OpenDDS::STUN::ERROR_RESPONSE, OpenDDS::STUN::make_error_code(), OpenDDS::STUN::make_fingerprint(), OpenDDS::STUN::make_message_integrity(), memcpy(), OpenDDS::STUN::Message::method, OpenDDS::ICE::AgentInfo::password, OpenDDS::STUN::Message::password, OpenDDS::STUN::Message::transaction_id, and OpenDDS::STUN::UNAUTHORIZED.

Referenced by request().

457 {
458  STUN::Message response;
459  response.class_ = STUN::ERROR_RESPONSE;
460  response.method = a_message.method;
461  memcpy(response.transaction_id.data, a_message.transaction_id.data, sizeof(a_message.transaction_id.data));
462  response.append_attribute(STUN::make_error_code(STUN::UNAUTHORIZED, "Unauthorized"));
463  response.append_attribute(STUN::make_message_integrity());
464  response.password = agent_info_.password;
465  response.append_attribute(STUN::make_fingerprint());
466  return response;
467 }
std::string password
Definition: Ice.h:78
void * memcpy(void *t, const void *s, size_t len)
Attribute make_error_code(ACE_UINT16 code, const std::string &reason)
Definition: Stun.cpp:99
Attribute make_message_integrity()
Definition: Stun.cpp:92
Attribute make_fingerprint()
Definition: Stun.cpp:139
const ACE_UINT16 UNAUTHORIZED
Definition: Stun.h:52

◆ make_unknown_attributes_error_response()

STUN::Message OpenDDS::ICE::EndpointManager::make_unknown_attributes_error_response ( const STUN::Message a_message,
const std::vector< STUN::AttributeType > &  a_unknown_attributes 
)
private

Definition at line 427 of file EndpointManager.cpp.

References agent_info_, OpenDDS::STUN::Message::append_attribute(), OpenDDS::STUN::Message::class_, OpenDDS::STUN::TransactionId::data, OpenDDS::STUN::ERROR_RESPONSE, OpenDDS::STUN::make_error_code(), OpenDDS::STUN::make_fingerprint(), OpenDDS::STUN::make_message_integrity(), OpenDDS::STUN::make_unknown_attributes(), memcpy(), OpenDDS::STUN::Message::method, OpenDDS::ICE::AgentInfo::password, OpenDDS::STUN::Message::password, OpenDDS::STUN::Message::transaction_id, and OpenDDS::STUN::UNKNOWN_ATTRIBUTE.

Referenced by request().

429 {
430  STUN::Message response;
431  response.class_ = STUN::ERROR_RESPONSE;
432  response.method = a_message.method;
433  memcpy(response.transaction_id.data, a_message.transaction_id.data, sizeof(a_message.transaction_id.data));
434  response.append_attribute(STUN::make_error_code(STUN::UNKNOWN_ATTRIBUTE, "Unknown Attributes"));
435  response.append_attribute(STUN::make_unknown_attributes(a_unknown_attributes));
436  response.append_attribute(STUN::make_message_integrity());
437  response.password = agent_info_.password;
438  response.append_attribute(STUN::make_fingerprint());
439  return response;
440 }
std::string password
Definition: Ice.h:78
void * memcpy(void *t, const void *s, size_t len)
Attribute make_unknown_attributes(const std::vector< AttributeType > &unknown_attributes)
Definition: Stun.cpp:108
const ACE_UINT16 UNKNOWN_ATTRIBUTE
Definition: Stun.h:53
Attribute make_error_code(ACE_UINT16 code, const std::string &reason)
Definition: Stun.cpp:99
Attribute make_message_integrity()
Definition: Stun.cpp:92
Attribute make_fingerprint()
Definition: Stun.cpp:139

◆ network_change()

void OpenDDS::ICE::EndpointManager::network_change ( )

Definition at line 816 of file EndpointManager.cpp.

References endpoint, OpenDDS::DCPS::WeakRcHandle< T >::lock(), and set_host_addresses().

817 {
818  DCPS::RcHandle<Endpoint> e = endpoint.lock();
819  if (e) {
820  set_host_addresses(e->host_addresses());
821  }
822 }
void set_host_addresses(const AddressListType &a_host_addresses)
RcHandle< T > lock() const
Definition: RcObject.h:188
DCPS::WeakRcHandle< Endpoint > const endpoint

◆ purge()

void OpenDDS::ICE::EndpointManager::purge ( void  )

Definition at line 832 of file EndpointManager.cpp.

References agent_info_listeners_, OPENDDS_END_VERSIONED_NAMESPACE_DECL, and username_to_checklist_.

833 {
835  for (UsernameToChecklistType::const_iterator pos = checklists.begin(), limit = checklists.end(); pos != limit; ++pos) {
836  pos->second->remove_guids();
837  }
838 
839  for (AgentInfoListenersType::const_iterator pos = agent_info_listeners_.begin(), limit = agent_info_listeners_.end(); pos != limit; ++pos) {
840  DCPS::RcHandle<AgentInfoListener> ail = pos->second.lock();
841  if (ail) {
842  ail->remove_agent_info(pos->first);
843  }
844  }
845 }
AgentInfoListenersType agent_info_listeners_
std::map< std::string, ChecklistPtr > UsernameToChecklistType
UsernameToChecklistType username_to_checklist_

◆ receive()

void OpenDDS::ICE::EndpointManager::receive ( const ACE_INET_Addr a_local_address,
const ACE_INET_Addr a_remote_address,
const STUN::Message a_message 
)

Definition at line 142 of file EndpointManager.cpp.

References ACE_ERROR, ACE_TEXT(), OpenDDS::STUN::Message::class_, OpenDDS::STUN::ERROR_RESPONSE, error_response(), OpenDDS::STUN::INDICATION, indication(), LM_WARNING, OpenDDS::STUN::REQUEST, request(), OpenDDS::STUN::SUCCESS_RESPONSE, and success_response().

145 {
146  switch (a_message.class_) {
147  case STUN::REQUEST:
148  request(a_local_address, a_remote_address, a_message);
149  return;
150 
151  case STUN::INDICATION:
152  indication(a_local_address, a_remote_address, a_message);
153  return;
154 
156  success_response(a_local_address, a_remote_address, a_message);
157  return;
158 
160  error_response(a_local_address, a_remote_address, a_message);
161  return;
162  }
163 
164  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::receive: WARNING Unknown STUN message class %d\n"), a_message.class_));
165 }
void indication(const ACE_INET_Addr &a_local_address, const ACE_INET_Addr &a_remote_address, const STUN::Message &a_message)
#define ACE_ERROR(X)
bool error_response(const STUN::Message &a_message)
bool success_response(const STUN::Message &a_message)
ACE_TEXT("TCP_Factory")
void request(const ACE_INET_Addr &a_local_address, const ACE_INET_Addr &a_remote_address, const STUN::Message &a_message)

◆ regenerate_agent_info()

void OpenDDS::ICE::EndpointManager::regenerate_agent_info ( bool  password_only)
private

Definition at line 238 of file EndpointManager.cpp.

References ACE_GUARD, agent_impl, agent_info(), agent_info_, agent_info_listeners_, OpenDDS::ICE::AgentInfo::candidates, OpenDDS::ICE::candidates_equal(), OpenDDS::ICE::candidates_sorted(), create_checklist(), foundations_, host_addresses_, OpenDDS::ICE::make_host_candidate(), OpenDDS::ICE::make_server_reflexive_candidate(), OpenDDS::ICE::AgentImpl::mutex, server_reflexive_address_, stun_server_address_, and username_to_checklist_.

Referenced by change_password(), set_host_addresses(), and set_server_reflexive_address().

239 {
240  if (!password_only) {
241  // Populate candidates.
242  agent_info_.candidates.clear();
243 
244  for (AddressListType::const_iterator pos = host_addresses_.begin(), limit = host_addresses_.end(); pos != limit; ++pos) {
245  agent_info_.candidates.push_back(make_host_candidate(*pos));
246 
250  }
251  }
252 
253  // Eliminate duplicates.
255  AgentInfo::CandidatesType::iterator last = std::unique(agent_info_.candidates.begin(), agent_info_.candidates.end(), candidates_equal);
256  agent_info_.candidates.erase(last, agent_info_.candidates.end());
257 
258  foundations_.clear();
259  for (AgentInfo::CandidatesType::const_iterator pos = agent_info_.candidates.begin(), limit = agent_info_.candidates.end(); pos != limit; ++pos) {
260  foundations_.insert(pos->foundation);
261  }
262 
263  // Start over.
265 
266  for (UsernameToChecklistType::const_iterator pos = old_checklists.begin(),
267  limit = old_checklists.end();
268  pos != limit; ++pos) {
269  ChecklistPtr old_checklist = pos->second;
270  AgentInfo const remote_agent_info = old_checklist->original_remote_agent_info();
271  GuidSetType const guids = old_checklist->guids();
272  old_checklist->remove_guids();
273  ChecklistPtr new_checklist = create_checklist(remote_agent_info);
274  new_checklist->add_guids(guids);
275  }
276  }
277 
278  {
279  // Propagate changed agent info.
280 
281  // Make a copy.
282  AgentInfoListenersType agent_info_listeners = agent_info_listeners_;
283  AgentInfo agent_info = agent_info_;
284 
285  // Release the lock.
288 
289  for (AgentInfoListenersType::const_iterator pos = agent_info_listeners.begin(),
290  limit = agent_info_listeners.end(); pos != limit; ++pos) {
291  DCPS::RcHandle<AgentInfoListener> ail = pos->second.lock();
292  if (ail) {
293  ail->update_agent_info(pos->first, agent_info);
294  }
295  }
296  }
297 }
ACE_Recursive_Thread_Mutex mutex
Definition: AgentImpl.h:100
#define ACE_GUARD(MUTEX, OBJ, LOCK)
std::set< GuidPair > GuidSetType
Definition: RTPS/ICE/Ice.h:39
const AgentInfo & agent_info() const
DCPS::RcHandle< Checklist > ChecklistPtr
Definition: Checklist.h:288
bool candidates_equal(const Candidate &x, const Candidate &y)
Definition: Ice.cpp:34
CandidatesType candidates
Definition: Ice.h:74
AgentInfoListenersType agent_info_listeners_
bool candidates_sorted(const Candidate &x, const Candidate &y)
Definition: Ice.cpp:21
ChecklistPtr create_checklist(const AgentInfo &a_remote_agent_info)
Candidate make_server_reflexive_candidate(const ACE_INET_Addr &address, const ACE_INET_Addr &base, const ACE_INET_Addr &server_address)
Definition: Ice.cpp:76
std::map< DCPS::GUID_t, DCPS::WeakRcHandle< AgentInfoListener >, DCPS::GUID_tKeyLessThan > AgentInfoListenersType
std::map< std::string, ChecklistPtr > UsernameToChecklistType
UsernameToChecklistType username_to_checklist_
Candidate make_host_candidate(const ACE_INET_Addr &address)
Definition: Ice.cpp:64

◆ remove_agent_info_listener()

void OpenDDS::ICE::EndpointManager::remove_agent_info_listener ( const DCPS::GUID_t a_local_guid)
inline

Definition at line 74 of file EndpointManager.h.

75  {
76  agent_info_listeners_.erase(a_local_guid);
77  }
AgentInfoListenersType agent_info_listeners_

◆ request()

void OpenDDS::ICE::EndpointManager::request ( const ACE_INET_Addr a_local_address,
const ACE_INET_Addr a_remote_address,
const STUN::Message a_message 
)
private

Definition at line 470 of file EndpointManager.cpp.

References ACE_ERROR, ACE_TEXT(), agent_info_, OpenDDS::STUN::Message::append_attribute(), OpenDDS::STUN::BINDING, OpenDDS::STUN::Message::class_, OpenDDS::STUN::TransactionId::data, deferred_triggered_checks_, OpenDDS::STUN::Message::get_priority(), OpenDDS::STUN::Message::get_username(), OpenDDS::STUN::Message::has_fingerprint(), OpenDDS::STUN::Message::has_ice_controlled(), OpenDDS::STUN::Message::has_ice_controlling(), OpenDDS::STUN::Message::has_message_integrity(), OpenDDS::STUN::Message::has_use_candidate(), OpenDDS::ICE::Configuration::instance(), LM_WARNING, make_bad_request_error_response(), OpenDDS::STUN::make_fingerprint(), OpenDDS::STUN::make_mapped_address(), OpenDDS::STUN::make_message_integrity(), make_unauthorized_error_response(), make_unknown_attributes_error_response(), OpenDDS::STUN::make_xor_mapped_address(), memcpy(), OpenDDS::STUN::Message::method, OpenDDS::ICE::AgentInfo::password, OpenDDS::STUN::Message::password, send(), OpenDDS::STUN::SUCCESS_RESPONSE, OpenDDS::STUN::Message::transaction_id, OpenDDS::STUN::Message::unknown_comprehension_required_attributes(), OpenDDS::ICE::AgentInfo::username, username_to_checklist_, and OpenDDS::STUN::Message::verify_message_integrity().

Referenced by receive().

473 {
474  std::string username;
475 
476  if (!a_message.get_username(username)) {
477  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::request: WARNING No USERNAME attribute\n")));
478  send(a_remote_address,
479  make_bad_request_error_response(a_message, "Bad Request: USERNAME must be present"));
480  return;
481  }
482 
483  if (!a_message.has_message_integrity()) {
484  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::request: WARNING No MESSAGE_INTEGRITY attribute\n")));
485  send(a_remote_address,
486  make_bad_request_error_response(a_message, "Bad Request: MESSAGE_INTEGRITY must be present"));
487  return;
488  }
489 
490  size_t idx = username.find(':');
491 
492  if (idx == std::string::npos) {
493  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::request: WARNING USERNAME does not contain a colon\n")));
494  send(a_remote_address,
495  make_bad_request_error_response(a_message, "Bad Request: USERNAME must be colon-separated"));
496  return;
497  }
498 
499  if (username.substr(0, idx) != agent_info_.username) {
500  // We expect this to happen.
501  send(a_remote_address,
503  return;
504  }
505 
506  const std::string remote_username = username.substr(++idx);
507 
508  // Check the message_integrity.
509  if (!a_message.verify_message_integrity(agent_info_.password)) {
510  // We expect this to happen.
511  send(a_remote_address,
513  return;
514  }
515 
516  std::vector<STUN::AttributeType> unknown_attributes = a_message.unknown_comprehension_required_attributes();
517 
518  if (!unknown_attributes.empty()) {
519  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::request: WARNING Unknown comprehension required attributes\n")));
520  send(a_remote_address,
521  make_unknown_attributes_error_response(a_message, unknown_attributes));
522  return;
523  }
524 
525  if (!a_message.has_fingerprint()) {
526  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::request: WARNING No FINGERPRINT attribute\n")));
527  send(a_remote_address,
528  make_bad_request_error_response(a_message, "Bad Request: FINGERPRINT must be present"));
529  return;
530  }
531 
532  if (!a_message.has_ice_controlled() && !a_message.has_ice_controlling()) {
533  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::request: WARNING No ICE_CONTROLLED/ICE_CONTROLLING attribute\n")));
534  send(a_remote_address,
535  make_bad_request_error_response(a_message, "Bad Request: Either ICE_CONTROLLED or ICE_CONTROLLING must be present"));
536  return;
537  }
538 
539  bool use_candidate = a_message.has_use_candidate();
540 
541  if (use_candidate && a_message.has_ice_controlled()) {
542  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::request: WARNING USE_CANDIDATE without ICE_CONTROLLED\n")));
543  send(a_remote_address,
544  make_bad_request_error_response(a_message, "Bad Request: USE_CANDIDATE can only be present when ICE_CONTROLLED is present"));
545  return;
546  }
547 
548  ACE_UINT32 priority;
549 
550  if (!a_message.get_priority(priority)) {
551  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::request: WARNING No PRIORITY attribute\n")));
552  send(a_remote_address,
553  make_bad_request_error_response(a_message, "Bad Request: PRIORITY must be present"));
554  return;
555  }
556 
557  switch (a_message.method) {
558  case STUN::BINDING: {
559  // 7.3
560  STUN::Message response;
561  response.class_ = STUN::SUCCESS_RESPONSE;
562  response.method = STUN::BINDING;
563  memcpy(response.transaction_id.data, a_message.transaction_id.data, sizeof(a_message.transaction_id.data));
564  response.append_attribute(STUN::make_mapped_address(a_remote_address));
565  response.append_attribute(STUN::make_xor_mapped_address(a_remote_address));
566  response.append_attribute(STUN::make_message_integrity());
567  response.password = agent_info_.password;
568  response.append_attribute(STUN::make_fingerprint());
569  send(a_remote_address, response);
570 
571  // 7.3.1.3
572  UsernameToChecklistType::const_iterator pos = username_to_checklist_.find(remote_username);
573 
574  if (pos != username_to_checklist_.end()) {
575  // We have a checklist.
576  ChecklistPtr checklist = pos->second;
577  checklist->generate_triggered_check(a_local_address, a_remote_address, priority, use_candidate);
578  }
579 
580  else {
581  std::pair<DeferredTriggeredChecksType::iterator, bool> x =
582  deferred_triggered_checks_.insert(std::make_pair(remote_username, DeferredTriggeredCheckListType()));
583  x.first->second.push_back(DeferredTriggeredCheck(
584  a_local_address, a_remote_address, priority, use_candidate,
585  MonotonicTimePoint::now() + ICE::Configuration::instance()->deferred_triggered_check_ttl()));
586  }
587  }
588  break;
589 
590  default:
591  // Unknown method. Stop processing.
592  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::request: WARNING Unknown STUN method\n")));
593  send(a_remote_address,
594  make_bad_request_error_response(a_message, "Bad Request: Unknown method"));
595  break;
596  }
597 }
#define ACE_ERROR(X)
Attribute make_mapped_address(const ACE_INET_Addr &addr)
Definition: Stun.cpp:76
Attribute make_xor_mapped_address(const ACE_INET_Addr &addr)
Definition: Stun.cpp:116
std::string password
Definition: Ice.h:78
void * memcpy(void *t, const void *s, size_t len)
DCPS::RcHandle< Checklist > ChecklistPtr
Definition: Checklist.h:288
static Configuration * instance()
Definition: Ice.cpp:109
void send(const ACE_INET_Addr &address, const STUN::Message &message)
Attribute make_message_integrity()
Definition: Stun.cpp:92
Attribute make_fingerprint()
Definition: Stun.cpp:139
ACE_TEXT("TCP_Factory")
std::deque< DeferredTriggeredCheck > DeferredTriggeredCheckListType
STUN::Message make_bad_request_error_response(const STUN::Message &a_message, const std::string &a_reason)
UsernameToChecklistType username_to_checklist_
std::string username
Definition: Ice.h:77
DeferredTriggeredChecksType deferred_triggered_checks_
STUN::Message make_unknown_attributes_error_response(const STUN::Message &a_message, const std::vector< STUN::AttributeType > &a_unknown_attributes)
STUN::Message make_unauthorized_error_response(const STUN::Message &a_message)

◆ send()

void OpenDDS::ICE::EndpointManager::send ( const ACE_INET_Addr address,
const STUN::Message message 
)

Definition at line 824 of file EndpointManager.cpp.

References endpoint, and OpenDDS::DCPS::WeakRcHandle< T >::lock().

Referenced by OpenDDS::ICE::Checklist::do_next_check(), OpenDDS::ICE::Checklist::execute(), request(), and server_reflexive_task().

825 {
826  DCPS::RcHandle<Endpoint> e = endpoint.lock();
827  if (e) {
828  e->send(address, message);
829  }
830 }
RcHandle< T > lock() const
Definition: RcObject.h:188
DCPS::WeakRcHandle< Endpoint > const endpoint

◆ server_reflexive_task()

void OpenDDS::ICE::EndpointManager::server_reflexive_task ( const DCPS::MonotonicTimePoint a_now)
private

Definition at line 299 of file EndpointManager.cpp.

References OpenDDS::STUN::Message::append_attribute(), OpenDDS::STUN::BINDING, binding_request_, OpenDDS::STUN::Message::class_, deferred_triggered_checks_, endpoint, OpenDDS::STUN::Message::generate_transaction_id(), OpenDDS::STUN::INDICATION, OpenDDS::ICE::Configuration::instance(), OpenDDS::DCPS::WeakRcHandle< T >::lock(), OpenDDS::STUN::make_fingerprint(), OpenDDS::STUN::Message::method, next_stun_server_address_, OpenDDS::STUN::REQUEST, requesting_, send(), send_count_, OpenDDS::ICE::Configuration::server_reflexive_indication_count(), and set_host_addresses().

300 {
301  // Request and maintain a server-reflexive address.
302  DCPS::RcHandle<Endpoint> e = endpoint.lock();
303 
304  if (e) {
305  next_stun_server_address_ = e->stun_server_address();
306  }
307 
309  binding_request_ = STUN::Message();
314 
316 
317  if (!requesting_ && send_count_ == ICE::Configuration::instance()->server_reflexive_indication_count() - 1) {
318  requesting_ = true;
319  }
320 
322  } else {
323  requesting_ = true;
324  send_count_ = 0;
325  }
326 
327  // Remove expired deferred checks.
328  for (DeferredTriggeredChecksType::iterator pos = deferred_triggered_checks_.begin(),
329  limit = deferred_triggered_checks_.end(); pos != limit;) {
330  DeferredTriggeredCheckListType& list = pos->second;
331 
332  while (!list.empty() && list.front().expiration_date < a_now) {
333  list.pop_front();
334  }
335 
336  if (list.empty()) {
337  deferred_triggered_checks_.erase(pos++);
338  } else {
339  ++pos;
340  }
341  }
342 
343  // Repopulate the host addresses.
344  if (e) {
345  set_host_addresses(e->host_addresses());
346  }
347 }
void append_attribute(const Attribute &attribute)
Definition: Stun.h:195
void set_host_addresses(const AddressListType &a_host_addresses)
RcHandle< T > lock() const
Definition: RcObject.h:188
static Configuration * instance()
Definition: Ice.cpp:109
void send(const ACE_INET_Addr &address, const STUN::Message &message)
Attribute make_fingerprint()
Definition: Stun.cpp:139
void generate_transaction_id()
Definition: Stun.cpp:606
std::deque< DeferredTriggeredCheck > DeferredTriggeredCheckListType
DCPS::WeakRcHandle< Endpoint > const endpoint
void server_reflexive_indication_count(size_t x)
Definition: RTPS/ICE/Ice.h:127
DeferredTriggeredChecksType deferred_triggered_checks_

◆ set_host_addresses()

void OpenDDS::ICE::EndpointManager::set_host_addresses ( const AddressListType &  a_host_addresses)
private

Definition at line 188 of file EndpointManager.cpp.

References host_addresses_, OPENDDS_ASSERT, and regenerate_agent_info().

Referenced by EndpointManager(), network_change(), and server_reflexive_task().

189 {
190  // Section IETF RFC 8445 5.1.1.1
191  AddressListType host_addresses;
192 
193  for (AddressListType::const_iterator pos = a_host_addresses.begin(), limit = a_host_addresses.end();
194  pos != limit; ++pos) {
195  OPENDDS_ASSERT(!pos->is_any());
196 
197  if (pos->is_loopback()) {
198  continue;
199  }
200 
201 #if ACE_HAS_IPV6
202  if (pos->is_ipv4_compat_ipv6()) {
203  continue;
204  }
205 
206  // TODO(jrw972): Include once supported in ACE.
207  // if (pos->is_sitelocal()) {
208  // continue;
209  // }
210 
211 #if !IPV6_V6ONLY
212  if (pos->is_ipv4_mapped_ipv6()) {
213  continue;
214  }
215 #endif
216 #endif
217 
218  host_addresses.push_back(*pos);
219  }
220 
221  if (host_addresses_ != host_addresses) {
222  host_addresses_ = host_addresses;
223  regenerate_agent_info(false);
224  }
225 }
void regenerate_agent_info(bool password_only)
#define OPENDDS_ASSERT(C)
Definition: Definitions.h:66

◆ set_responsible_checklist() [1/3]

void OpenDDS::ICE::EndpointManager::set_responsible_checklist ( const STUN::TransactionId a_transaction_id,
ChecklistPtr  a_checklist 
)
inline

Definition at line 93 of file EndpointManager.h.

References OPENDDS_ASSERT.

Referenced by OpenDDS::ICE::Checklist::add_guid(), OpenDDS::ICE::Checklist::Checklist(), and OpenDDS::ICE::Checklist::do_next_check().

94  {
95  OPENDDS_ASSERT(!transaction_id_to_checklist_.count(a_transaction_id));
96  transaction_id_to_checklist_[a_transaction_id] = a_checklist;
97  }
#define OPENDDS_ASSERT(C)
Definition: Definitions.h:66
TransactionIdToChecklistType transaction_id_to_checklist_

◆ set_responsible_checklist() [2/3]

void OpenDDS::ICE::EndpointManager::set_responsible_checklist ( const GuidPair a_guid_pair,
ChecklistPtr  a_checklist 
)
inline

Definition at line 108 of file EndpointManager.h.

References OPENDDS_ASSERT.

109  {
110  OPENDDS_ASSERT(!guid_pair_to_checklist_.count(a_guid_pair));
111  guid_pair_to_checklist_[a_guid_pair] = a_checklist;
112  }
#define OPENDDS_ASSERT(C)
Definition: Definitions.h:66
GuidPairToChecklistType guid_pair_to_checklist_

◆ set_responsible_checklist() [3/3]

void OpenDDS::ICE::EndpointManager::set_responsible_checklist ( const std::string &  a_username,
ChecklistPtr  a_checklist 
)
inline

Definition at line 123 of file EndpointManager.h.

References OPENDDS_ASSERT.

124  {
125  OPENDDS_ASSERT(!username_to_checklist_.count(a_username));
126  username_to_checklist_[a_username] = a_checklist;
127  }
#define OPENDDS_ASSERT(C)
Definition: Definitions.h:66
UsernameToChecklistType username_to_checklist_

◆ set_server_reflexive_address()

void OpenDDS::ICE::EndpointManager::set_server_reflexive_address ( const ACE_INET_Addr a_server_reflexive_address,
const ACE_INET_Addr a_stun_server_address 
)
private

Definition at line 227 of file EndpointManager.cpp.

References regenerate_agent_info(), server_reflexive_address_, and stun_server_address_.

Referenced by success_response().

229 {
230  if (server_reflexive_address_ != a_server_reflexive_address ||
231  stun_server_address_ != a_stun_server_address) {
232  server_reflexive_address_ = a_server_reflexive_address;
233  stun_server_address_ = a_stun_server_address;
234  regenerate_agent_info(false);
235  }
236 }
void regenerate_agent_info(bool password_only)

◆ start_ice()

void OpenDDS::ICE::EndpointManager::start_ice ( const DCPS::GUID_t a_local_guid,
const DCPS::GUID_t a_remote_guid,
const AgentInfo a_remote_agent_info 
)

Definition at line 51 of file EndpointManager.cpp.

References agent_info_, change_username(), create_checklist(), guid_pair_to_checklist_, OpenDDS::ICE::AgentInfo::password, OpenDDS::ICE::AgentInfo::username, and username_to_checklist_.

54 {
55  // Check for username collision.
56  if (a_remote_agent_info.username == agent_info_.username) {
58  }
59 
60  GuidPair guidp(a_local_guid, a_remote_guid);
61 
62  // Try to find by guid.
63  ChecklistPtr guid_checklist;
64  {
65  GuidPairToChecklistType::const_iterator pos = guid_pair_to_checklist_.find(guidp);
66 
67  if (pos != guid_pair_to_checklist_.end()) {
68  guid_checklist = pos->second;
69  }
70  }
71 
72  // Try to find by username.
73  ChecklistPtr username_checklist;
74  {
75  UsernameToChecklistType::const_iterator pos = username_to_checklist_.find(a_remote_agent_info.username);
76 
77  if (pos != username_to_checklist_.end()) {
78  username_checklist = pos->second;
79  }
80 
81  else {
82  username_checklist = create_checklist(a_remote_agent_info);
83  }
84  }
85 
86  if (guid_checklist != username_checklist) {
87  if (guid_checklist != 0) {
88  guid_checklist->remove_guid(guidp);
89  }
90 
91  username_checklist->add_guid(guidp);
92  }
93 
94  AgentInfo old_remote_agent_info = username_checklist->original_remote_agent_info();
95 
96  if (old_remote_agent_info == a_remote_agent_info) {
97  // No change.
98  return;
99  }
100 
101  old_remote_agent_info.password = a_remote_agent_info.password;
102 
103  if (old_remote_agent_info == a_remote_agent_info) {
104  // Password change.
105  username_checklist->set_remote_password(a_remote_agent_info.password);
106  return;
107  }
108 
109  // The remote agent changed its info without changing its username.
110  GuidSetType const guids = username_checklist->guids();
111  username_checklist->remove_guids();
112  username_checklist = create_checklist(a_remote_agent_info);
113  username_checklist->add_guids(guids);
114 }
std::set< GuidPair > GuidSetType
Definition: RTPS/ICE/Ice.h:39
DCPS::RcHandle< Checklist > ChecklistPtr
Definition: Checklist.h:288
ChecklistPtr create_checklist(const AgentInfo &a_remote_agent_info)
UsernameToChecklistType username_to_checklist_
std::string username
Definition: Ice.h:77
GuidPairToChecklistType guid_pair_to_checklist_

◆ stop_ice()

void OpenDDS::ICE::EndpointManager::stop_ice ( const DCPS::GUID_t local_guid,
const DCPS::GUID_t remote_guid 
)

Definition at line 116 of file EndpointManager.cpp.

References guid_pair_to_checklist_.

118 {
119  GuidPair guidp(a_local_guid, a_remote_guid);
120 
121  GuidPairToChecklistType::const_iterator pos = guid_pair_to_checklist_.find(guidp);
122 
123  if (pos != guid_pair_to_checklist_.end()) {
124  ChecklistPtr guid_checklist = pos->second;
125  guid_checklist->remove_guid(guidp);
126  }
127 }
DCPS::RcHandle< Checklist > ChecklistPtr
Definition: Checklist.h:288
GuidPairToChecklistType guid_pair_to_checklist_

◆ success_response() [1/2]

bool OpenDDS::ICE::EndpointManager::success_response ( const STUN::Message a_message)
private

Definition at line 349 of file EndpointManager.cpp.

References ACE_ERROR, ACE_TEXT(), binding_request_, OpenDDS::STUN::Message::get_mapped_address(), LM_WARNING, next_stun_server_address_, requesting_, send_count_, set_server_reflexive_address(), OpenDDS::STUN::Message::transaction_id, and OpenDDS::STUN::Message::unknown_comprehension_required_attributes().

Referenced by receive(), and success_response().

350 {
351  if (a_message.transaction_id != binding_request_.transaction_id) {
352  return false;
353  }
354 
355  std::vector<STUN::AttributeType> unknown_attributes = a_message.unknown_comprehension_required_attributes();
356 
357  if (!unknown_attributes.empty()) {
358  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::success_response: WARNING Unknown comprehension required attributes\n")));
359  return true;
360  }
361 
362  ACE_INET_Addr server_reflexive_address;
363 
364  if (a_message.get_mapped_address(server_reflexive_address)) {
365  set_server_reflexive_address(server_reflexive_address, next_stun_server_address_);
366  requesting_ = false;
367  send_count_ = 0;
368  }
369 
370  else {
371  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::success_response: WARNING No (XOR)_MAPPED_ADDRESS attribute\n")));
373  requesting_ = true;
374  send_count_ = 0;
375  }
376 
377  return true;
378 }
#define ACE_ERROR(X)
TransactionId transaction_id
Definition: Stun.h:186
ACE_TEXT("TCP_Factory")
void set_server_reflexive_address(const ACE_INET_Addr &a_server_reflexive_address, const ACE_INET_Addr &a_stun_server_address)

◆ success_response() [2/2]

void OpenDDS::ICE::EndpointManager::success_response ( const ACE_INET_Addr a_local_address,
const ACE_INET_Addr a_remote_address,
const STUN::Message a_message 
)
private

Definition at line 666 of file EndpointManager.cpp.

References ACE_ERROR, ACE_TEXT(), OpenDDS::STUN::BINDING, LM_WARNING, OpenDDS::STUN::Message::method, success_response(), OpenDDS::STUN::Message::transaction_id, and transaction_id_to_checklist_.

669 {
670  switch (a_message.method) {
671  case STUN::BINDING: {
672  if (success_response(a_message)) {
673  return;
674  }
675 
676  TransactionIdToChecklistType::const_iterator pos = transaction_id_to_checklist_.find(a_message.transaction_id);
677 
678  if (pos == transaction_id_to_checklist_.end()) {
679  // Probably a check that got cancelled.
680  return;
681  }
682 
683  // Checklist is responsible for updating the map.
684  // Checklist also checks for required parameters.
685  pos->second->success_response(a_local_address, a_remote_address, a_message);
686  }
687  break;
688 
689  default:
690  // Unknown method. Stop processing.
691  ACE_ERROR((LM_WARNING, ACE_TEXT("(%P|%t) EndpointManager::success_response: WARNING Unknown STUN method\n")));
692  break;
693  }
694 }
#define ACE_ERROR(X)
TransactionIdToChecklistType transaction_id_to_checklist_
bool success_response(const STUN::Message &a_message)
ACE_TEXT("TCP_Factory")

◆ unfreeze() [1/2]

void OpenDDS::ICE::EndpointManager::unfreeze ( )

Definition at line 768 of file EndpointManager.cpp.

References username_to_checklist_.

769 {
770  for (UsernameToChecklistType::const_iterator pos = username_to_checklist_.begin(),
771  limit = username_to_checklist_.end(); pos != limit; ++pos) {
772  pos->second->unfreeze();
773  }
774 }
UsernameToChecklistType username_to_checklist_

◆ unfreeze() [2/2]

void OpenDDS::ICE::EndpointManager::unfreeze ( const FoundationType a_foundation)

Definition at line 776 of file EndpointManager.cpp.

References username_to_checklist_.

777 {
778  for (UsernameToChecklistType::const_iterator pos = username_to_checklist_.begin(),
779  limit = username_to_checklist_.end(); pos != limit; ++pos) {
780  pos->second->unfreeze(a_foundation);
781  }
782 }
UsernameToChecklistType username_to_checklist_

◆ unset_responsible_checklist() [1/3]

void OpenDDS::ICE::EndpointManager::unset_responsible_checklist ( const STUN::TransactionId a_transaction_id,
ChecklistPtr  a_checklist 
)
inline

Definition at line 99 of file EndpointManager.h.

References OPENDDS_ASSERT.

Referenced by OpenDDS::ICE::Checklist::do_next_check(), OpenDDS::ICE::Checklist::error_response(), OpenDDS::ICE::Checklist::remove_guid(), OpenDDS::ICE::Checklist::succeeded(), and OpenDDS::ICE::Checklist::success_response().

100  {
101  TransactionIdToChecklistType::iterator pos = transaction_id_to_checklist_.find(a_transaction_id);
103  OPENDDS_ASSERT(pos->second == a_checklist);
104  ACE_UNUSED_ARG(a_checklist);
105  transaction_id_to_checklist_.erase(pos);
106  }
#define OPENDDS_ASSERT(C)
Definition: Definitions.h:66
TransactionIdToChecklistType transaction_id_to_checklist_

◆ unset_responsible_checklist() [2/3]

void OpenDDS::ICE::EndpointManager::unset_responsible_checklist ( const GuidPair a_guid_pair,
ChecklistPtr  a_checklist 
)
inline

Definition at line 114 of file EndpointManager.h.

References OPENDDS_ASSERT.

115  {
116  GuidPairToChecklistType::iterator pos = guid_pair_to_checklist_.find(a_guid_pair);
118  OPENDDS_ASSERT(pos->second == a_checklist);
119  ACE_UNUSED_ARG(a_checklist);
120  guid_pair_to_checklist_.erase(pos);
121  }
#define OPENDDS_ASSERT(C)
Definition: Definitions.h:66
GuidPairToChecklistType guid_pair_to_checklist_

◆ unset_responsible_checklist() [3/3]

void OpenDDS::ICE::EndpointManager::unset_responsible_checklist ( const std::string &  a_username,
ChecklistPtr  a_checklist 
)
inline

Definition at line 129 of file EndpointManager.h.

References OPENDDS_ASSERT.

130  {
131  UsernameToChecklistType::iterator pos = username_to_checklist_.find(a_username);
133  OPENDDS_ASSERT(pos->second == a_checklist);
134  ACE_UNUSED_ARG(a_checklist);
135  username_to_checklist_.erase(pos);
136  }
#define OPENDDS_ASSERT(C)
Definition: Definitions.h:66
UsernameToChecklistType username_to_checklist_

Member Data Documentation

◆ agent_impl

AgentImpl* const OpenDDS::ICE::EndpointManager::agent_impl

◆ agent_info_

AgentInfo OpenDDS::ICE::EndpointManager::agent_info_
private

◆ agent_info_listeners_

AgentInfoListenersType OpenDDS::ICE::EndpointManager::agent_info_listeners_
private

Definition at line 199 of file EndpointManager.h.

Referenced by purge(), and regenerate_agent_info().

◆ binding_request_

STUN::Message OpenDDS::ICE::EndpointManager::binding_request_
private

◆ change_password_task_

DCPS::RcHandle<ChangePasswordTask> OpenDDS::ICE::EndpointManager::change_password_task_
private

Definition at line 257 of file EndpointManager.h.

◆ deferred_triggered_checks_

DeferredTriggeredChecksType OpenDDS::ICE::EndpointManager::deferred_triggered_checks_
private

◆ endpoint

DCPS::WeakRcHandle<Endpoint> const OpenDDS::ICE::EndpointManager::endpoint

Definition at line 53 of file EndpointManager.h.

Referenced by EndpointManager(), network_change(), send(), and server_reflexive_task().

◆ foundations_

FoundationSet OpenDDS::ICE::EndpointManager::foundations_
private

Definition at line 174 of file EndpointManager.h.

Referenced by regenerate_agent_info().

◆ guid_pair_to_checklist_

GuidPairToChecklistType OpenDDS::ICE::EndpointManager::guid_pair_to_checklist_
private

◆ host_addresses_

AddressListType OpenDDS::ICE::EndpointManager::host_addresses_
private

Definition at line 169 of file EndpointManager.h.

Referenced by regenerate_agent_info(), and set_host_addresses().

◆ ice_tie_breaker_

ACE_UINT64 OpenDDS::ICE::EndpointManager::ice_tie_breaker_
private

Definition at line 172 of file EndpointManager.h.

Referenced by create_checklist(), and EndpointManager().

◆ next_stun_server_address_

ACE_INET_Addr OpenDDS::ICE::EndpointManager::next_stun_server_address_
private

Definition at line 179 of file EndpointManager.h.

Referenced by server_reflexive_task(), and success_response().

◆ requesting_

bool OpenDDS::ICE::EndpointManager::requesting_
private

Definition at line 177 of file EndpointManager.h.

Referenced by server_reflexive_task(), and success_response().

◆ send_count_

size_t OpenDDS::ICE::EndpointManager::send_count_
private

Definition at line 178 of file EndpointManager.h.

Referenced by server_reflexive_task(), and success_response().

◆ server_reflexive_address_

ACE_INET_Addr OpenDDS::ICE::EndpointManager::server_reflexive_address_
private

Definition at line 170 of file EndpointManager.h.

Referenced by regenerate_agent_info(), and set_server_reflexive_address().

◆ server_reflexive_task_

DCPS::RcHandle<ServerReflexiveTask> OpenDDS::ICE::EndpointManager::server_reflexive_task_
private

Definition at line 250 of file EndpointManager.h.

◆ stun_server_address_

ACE_INET_Addr OpenDDS::ICE::EndpointManager::stun_server_address_
private

Definition at line 171 of file EndpointManager.h.

Referenced by regenerate_agent_info(), and set_server_reflexive_address().

◆ transaction_id_to_checklist_

TransactionIdToChecklistType OpenDDS::ICE::EndpointManager::transaction_id_to_checklist_
private

Definition at line 192 of file EndpointManager.h.

Referenced by check_invariants(), error_response(), and success_response().

◆ username_to_checklist_

UsernameToChecklistType OpenDDS::ICE::EndpointManager::username_to_checklist_
private

The documentation for this struct was generated from the following files: