| Fast DDS Version 3.3.0 Fast DDS

Loading...
Searching...
No Matches
LocatorSelector.hpp
1// Copyright 2019 Proyectos y Sistemas de Mantenimiento SL (eProsima).
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7// http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14
18
19#ifndef FASTDDS_RTPS_COMMON__LOCATORSELECTOR_HPP
20#define FASTDDS_RTPS_COMMON__LOCATORSELECTOR_HPP
21
22#include <fastdds/rtps/common/LocatorSelectorEntry.hpp>
23#include <fastdds/rtps/common/Guid.hpp>
24#include <fastdds/rtps/common/Locator.hpp>
25#include <fastdds/rtps/common/LocatorsIterator.hpp>
26#include <fastdds/utils/collections/ResourceLimitedVector.hpp>
27#include <fastdds/utils/IPLocator.hpp>
28
29#include <algorithm>
30
31 namespace eprosima {
32 namespace fastdds {
33 namespace rtps {
34
54 class LocatorSelector
55{
56 public:
57
63 LocatorSelector(
64 const ResourceLimitedContainerConfig& entries_allocation)
65 : entries_(entries_allocation)
66 , selections_(entries_allocation)
67 , last_state_(entries_allocation)
68 {
69 }
70
74 void clear()
75 {
76 entries_.clear();
77 selections_.clear();
78 last_state_.clear();
79 }
80
86 bool add_entry(
87 LocatorSelectorEntry* entry)
88 {
89 return entries_.push_back(entry) != nullptr;
90 }
91
96 bool remove_entry(
97 const GUID_t& guid)
98 {
99 return entries_.remove_if(
100 [&guid](LocatorSelectorEntry* entry)
101 {
102 return entry->remote_guid == guid;
103 });
104 }
105
111 void reset(
112 bool enable_all)
113 {
114 last_state_.clear();
115 for (LocatorSelectorEntry* entry : entries_)
116 {
117 last_state_.push_back(entry->enabled ? 1 : 0);
118 entry->enable(enable_all);
119 }
120 }
121
127 void enable(
128 const GUID_t& guid)
129 {
130 for (LocatorSelectorEntry* entry : entries_)
131 {
132 if (entry->remote_guid == guid)
133 {
134 entry->enabled = true;
135 break;
136 }
137 }
138 }
139
145 bool state_has_changed() const
146 {
147 if (entries_.size() != last_state_.size())
148 {
149 return true;
150 }
151
152 for (size_t i = 0; i < entries_.size(); ++i)
153 {
154 if (last_state_.at(i) != (entries_.at(i)->enabled ? 1 : 0))
155 {
156 return true;
157 }
158 }
159
160 return false;
161 }
162
166 void selection_start()
167 {
168 selections_.clear();
169 for (LocatorSelectorEntry* entry : entries_)
170 {
171 entry->reset();
172 }
173 }
174
182 ResourceLimitedVector<LocatorSelectorEntry*>& transport_starts()
183 {
184 for (LocatorSelectorEntry* entry : entries_)
185 {
186 entry->transport_should_process = entry->enabled;
187 }
188
189 return entries_;
190 }
191
197 void select(
198 size_t index)
199 {
200 if (index < entries_.size() &&
201 std::find(selections_.begin(), selections_.end(), index) == selections_.end())
202 {
203 selections_.push_back(index);
204 }
205 }
206
212 size_t selected_size() const
213 {
214 size_t result = 0;
215
216 for (size_t index : selections_)
217 {
218 LocatorSelectorEntry* entry = entries_.at(index);
219 result += entry->state.multicast.size();
220 result += entry->state.unicast.size();
221 }
222
223 return result;
224 }
225
233 bool is_selected(
234 const Locator_t locator) const
235 {
236 if (IPLocator::isMulticast(locator))
237 {
238 for (size_t index : selections_)
239 {
240 LocatorSelectorEntry* entry = entries_.at(index);
241 for (size_t loc_index : entry->state.multicast)
242 {
243 if (entry->multicast.at(loc_index) == locator)
244 {
245 return true;
246 }
247 }
248 }
249 }
250 else
251 {
252 for (size_t index : selections_)
253 {
254 LocatorSelectorEntry* entry = entries_.at(index);
255 for (size_t loc_index : entry->state.unicast)
256 {
257 if (entry->unicast.at(loc_index) == locator)
258 {
259 return true;
260 }
261 }
262 }
263 }
264 return false;
265 }
266
274 template<class UnaryPredicate>
275 void for_each(
276 UnaryPredicate action) const
277 {
278 for (size_t index : selections_)
279 {
280 LocatorSelectorEntry* entry = entries_.at(index);
281 for (size_t loc_index : entry->state.multicast)
282 {
283 action(entry->multicast.at(loc_index));
284 }
285 for (size_t loc_index : entry->state.unicast)
286 {
287 action(entry->unicast.at(loc_index));
288 }
289 }
290 }
291
292 struct IteratorIndex
293 {
294 size_t selections_index;
295 size_t state_index;
296 bool state_multicast_done;
297 Locator_t* locator;
298 };
299
300 class iterator :
301 public LocatorsIterator
302 {
303 // use of std::iterator to introduce the following aliases is deprecated
304 using iterator_category = std::input_iterator_tag;
305 using value_type = Locator_t;
306 using difference_type = IteratorIndex;
307 using pointer = Locator_t*;
308 using reference = Locator_t&;
309
310 const LocatorSelector& locator_selector_;
311 IteratorIndex current_;
312
313 void go_to_next_entry()
314 {
315 // While entries selected
316 while (++current_.selections_index < locator_selector_.selections_.size())
317 {
318 LocatorSelectorEntry* entry =
319 locator_selector_.entries_.at(locator_selector_.selections_[current_.selections_index]);
320
321 // No multicast locators in this entry
322 if (entry->state.multicast.size() == 0)
323 {
324 // But there's unicast
325 if (entry->state.unicast.size() > 0)
326 {
327 current_.locator = &entry->unicast[entry->state.unicast.at(0)];
328 return;
329 }
330 }
331 else // process multicast
332 {
333 current_.state_multicast_done = false;
334 current_.locator = &entry->multicast[entry->state.multicast.at(0)];
335 return;
336 }
337 }
338
339 current_.locator = nullptr;
340 }
341
342 public:
343
344 enum class Position
345 {
346 Begin,
347 End
348 };
349
350 explicit iterator(
351 const LocatorSelector& locator_selector,
352 Position index_pos)
353 : locator_selector_(locator_selector)
354 {
355 current_ = {(std::numeric_limits<size_t>::max)(), 0, true, nullptr};
356
357 if (index_pos == Position::Begin)
358 {
359 go_to_next_entry();
360 }
361 }
362
363 iterator(
364 const iterator& other)
365 : locator_selector_(other.locator_selector_)
366 , current_(other.current_)
367 {
368 }
369
370 iterator& operator ++()
371 {
372 // Shouldn't call ++ when index already at the end
373 assert(current_.selections_index < locator_selector_.selections_.size());
374
375 LocatorSelectorEntry* entry =
376 locator_selector_.entries_.at(locator_selector_.selections_[current_.selections_index]);
377
378 // Index at unicast locators
379 if (current_.state_multicast_done)
380 {
381 // No more unicast locators selected
382 if (++current_.state_index >= entry->state.unicast.size())
383 {
384 current_.state_index = 0;
385 go_to_next_entry();
386 }
387 else // current unicast locator
388 {
389 current_.locator = &entry->unicast[entry->state.unicast.at(current_.state_index)];
390 }
391 }
392 else // Index at multicast locators
393 {
394 // No more multicast locators selected
395 if (++current_.state_index >= entry->state.multicast.size())
396 {
397 // Reset index to process unicast
398 current_.state_multicast_done = true;
399 current_.state_index = 0;
400 // No unicast locators
401 if (current_.state_index >= entry->state.unicast.size())
402 {
403 go_to_next_entry();
404 }
405 else // current unicast locator
406 {
407 current_.locator = &entry->unicast[entry->state.unicast.at(current_.state_index)];
408 }
409 }
410 else // current multicast locator
411 {
412 current_.locator = &entry->multicast[entry->state.multicast.at(current_.state_index)];
413 }
414 }
415
416 return *this;
417 }
418
419 bool operator ==(
420 const LocatorsIterator& other) const
421 {
422 return *this == static_cast<const iterator&>(other);
423 }
424
425 bool operator !=(
426 const LocatorsIterator& other) const
427 {
428 return !(*this == other);
429 }
430
431 bool operator ==(
432 const iterator& other) const
433 {
434 return (current_.locator == other.current_.locator);
435 }
436
437 bool operator !=(
438 const iterator& other) const
439 {
440 return !(*this == other);
441 }
442
443 pointer operator ->() const
444 {
445 return current_.locator;
446 }
447
448 reference operator *() const
449 {
450 return *current_.locator;
451 }
452
453 };
454
455 iterator begin() const
456 {
457 return iterator(*this, iterator::Position::Begin);
458 }
459
460 iterator end() const
461 {
462 return iterator(*this, iterator::Position::End);
463 }
464
465 private:
466
468 ResourceLimitedVector<LocatorSelectorEntry*> entries_;
470 ResourceLimitedVector<size_t> selections_;
472 ResourceLimitedVector<int> last_state_;
473};
474
475} // namespace rtps
476} // namespace fastdds
477} // namespace eprosima
478
479#endif // FASTDDS_RTPS_COMMON__LOCATORSELECTOR_HPP
eprosima::fastdds::ResourceLimitedVector
Resource limited wrapper of std::vector.
Definition ResourceLimitedVector.hpp:59
eprosima::fastdds::ResourceLimitedVector::size
size_type size() const noexcept
Definition ResourceLimitedVector.hpp:479
eprosima::fastdds::ResourceLimitedVector::at
reference at(size_type pos)
Wrappers to other basic vector methods.
Definition ResourceLimitedVector.hpp:370
eprosima::fastdds::rtps::IPLocator::isMulticast
static FASTDDS_EXPORTED_API bool isMulticast(const Locator_t &locator)
Checks if the locator has a multicast IP address.
eprosima::fastdds::rtps::Locator_t
Class Locator_t, uniquely identifies a communication channel for a particular transport.
Definition Locator.hpp:71
eprosima::fastdds::rtps::LocatorSelector::iterator
Definition LocatorSelector.hpp:302
eprosima::fastdds::rtps::LocatorSelector::iterator::iterator
iterator(const iterator &other)
Definition LocatorSelector.hpp:363
eprosima::fastdds::rtps::LocatorSelector::iterator::operator!=
bool operator!=(const LocatorsIterator &other) const
Not equal to operator.
Definition LocatorSelector.hpp:425
eprosima::fastdds::rtps::LocatorSelector::iterator::iterator
iterator(const LocatorSelector &locator_selector, Position index_pos)
Definition LocatorSelector.hpp:350
eprosima::fastdds::rtps::LocatorSelector::iterator::operator==
bool operator==(const LocatorsIterator &other) const
Equal to operator.
Definition LocatorSelector.hpp:419
eprosima::fastdds::rtps::LocatorSelector::iterator::operator*
reference operator*() const
Dereference operator.
Definition LocatorSelector.hpp:448
eprosima::fastdds::rtps::LocatorSelector::iterator::Position
Position
Definition LocatorSelector.hpp:345
eprosima::fastdds::rtps::LocatorSelector::iterator::Position::Begin
@ Begin
Definition LocatorSelector.hpp:346
eprosima::fastdds::rtps::LocatorSelector::iterator::Position::End
@ End
Definition LocatorSelector.hpp:347
eprosima::fastdds::rtps::LocatorSelector::iterator::operator++
iterator & operator++()
Increment operator.
Definition LocatorSelector.hpp:370
eprosima::fastdds::rtps::LocatorSelector::iterator::operator->
pointer operator->() const
Definition LocatorSelector.hpp:443
eprosima::fastdds::rtps::LocatorSelector::begin
iterator begin() const
Definition LocatorSelector.hpp:455
eprosima::fastdds::rtps::LocatorSelector::LocatorSelector
LocatorSelector(const ResourceLimitedContainerConfig &entries_allocation)
Construct a LocatorSelector.
Definition LocatorSelector.hpp:63
eprosima::fastdds::rtps::LocatorSelector::select
void select(size_t index)
Marks an entry as selected.
Definition LocatorSelector.hpp:197
eprosima::fastdds::rtps::LocatorSelector::selected_size
size_t selected_size() const
Count the number of selected locators.
Definition LocatorSelector.hpp:212
eprosima::fastdds::rtps::LocatorSelector::remove_entry
bool remove_entry(const GUID_t &guid)
Remove an entry from this selector.
Definition LocatorSelector.hpp:96
eprosima::fastdds::rtps::LocatorSelector::end
iterator end() const
Definition LocatorSelector.hpp:460
eprosima::fastdds::rtps::LocatorSelector::transport_starts
ResourceLimitedVector< LocatorSelectorEntry * > & transport_starts()
Called when the selection algorithm starts for a specific transport.
Definition LocatorSelector.hpp:182
eprosima::fastdds::rtps::LocatorSelector::state_has_changed
bool state_has_changed() const
Check if enabling state has changed.
Definition LocatorSelector.hpp:145
eprosima::fastdds::rtps::LocatorSelector::add_entry
bool add_entry(LocatorSelectorEntry *entry)
Add an entry to this selector.
Definition LocatorSelector.hpp:86
eprosima::fastdds::rtps::LocatorSelector::selection_start
void selection_start()
Reset the selection state of the selector.
Definition LocatorSelector.hpp:166
eprosima::fastdds::rtps::LocatorSelector::for_each
void for_each(UnaryPredicate action) const
Performs an action on each selected locator.
Definition LocatorSelector.hpp:275
eprosima::fastdds::rtps::LocatorSelector::enable
void enable(const GUID_t &guid)
Enable an entry given its GUID.
Definition LocatorSelector.hpp:127
eprosima::fastdds::rtps::LocatorSelector::clear
void clear()
Clears all internal data.
Definition LocatorSelector.hpp:74
eprosima::fastdds::rtps::LocatorSelector::reset
void reset(bool enable_all)
Reset the enabling state of the selector.
Definition LocatorSelector.hpp:111
eprosima::fastdds::rtps::LocatorSelector::is_selected
bool is_selected(const Locator_t locator) const
Check if a locator is present in the selections of this object.
Definition LocatorSelector.hpp:233
eprosima::fastdds::rtps
Contains the RTPS protocol implementation.
eprosima::fastdds
eprosima
eProsima namespace.
eprosima::fastdds::ResourceLimitedContainerConfig
Specifies the configuration of a resource limited collection.
Definition ResourceLimitedContainerConfig.hpp:36
eprosima::fastdds::rtps::GUID_t
Structure GUID_t, entity identifier, unique in DDS-RTPS Domain.
Definition Guid.hpp:40
eprosima::fastdds::rtps::LocatorSelector::IteratorIndex
Definition LocatorSelector.hpp:293
eprosima::fastdds::rtps::LocatorSelector::IteratorIndex::selections_index
size_t selections_index
Definition LocatorSelector.hpp:294
eprosima::fastdds::rtps::LocatorSelector::IteratorIndex::state_index
size_t state_index
Definition LocatorSelector.hpp:295
eprosima::fastdds::rtps::LocatorSelector::IteratorIndex::state_multicast_done
bool state_multicast_done
Definition LocatorSelector.hpp:296
eprosima::fastdds::rtps::LocatorSelector::IteratorIndex::locator
Locator_t * locator
Definition LocatorSelector.hpp:297
eprosima::fastdds::rtps::LocatorSelectorEntry::EntryState::unicast
ResourceLimitedVector< size_t > unicast
Unicast locators selection state.
Definition LocatorSelectorEntry.hpp:60
eprosima::fastdds::rtps::LocatorSelectorEntry::EntryState::multicast
ResourceLimitedVector< size_t > multicast
Multicast locators selection state.
Definition LocatorSelectorEntry.hpp:62
eprosima::fastdds::rtps::LocatorSelectorEntry
An entry for the LocatorSelector.
Definition LocatorSelectorEntry.hpp:39
eprosima::fastdds::rtps::LocatorSelectorEntry::unicast
ResourceLimitedVector< Locator_t > unicast
List of unicast locators to send data to the remote entity.
Definition LocatorSelectorEntry.hpp:136
eprosima::fastdds::rtps::LocatorSelectorEntry::multicast
ResourceLimitedVector< Locator_t > multicast
List of multicast locators to send data to the remote entity.
Definition LocatorSelectorEntry.hpp:138
eprosima::fastdds::rtps::LocatorSelectorEntry::remote_guid
GUID_t remote_guid
GUID of the remote entity.
Definition LocatorSelectorEntry.hpp:134
eprosima::fastdds::rtps::LocatorSelectorEntry::state
EntryState state
State of the entry.
Definition LocatorSelectorEntry.hpp:140
eprosima::fastdds::rtps::LocatorsIterator
Provides a Locator's iterator interface that can be used by different Locator's containers.
Definition LocatorsIterator.hpp:33