+std::vector<resource::StandardLinkImpl*> NetZoneImpl::get_link_list_impl(const std::vector<s4u::LinkInRoute>& link_list,
+ bool backroute) const
+{
+ std::vector<resource::StandardLinkImpl*> links;
+
+ for (const auto& link : link_list) {
+ if (link.get_link()->get_sharing_policy() != s4u::Link::SharingPolicy::SPLITDUPLEX) {
+ links.push_back(link.get_link()->get_impl());
+ continue;
+ }
+ // split-duplex links
+ const auto* sd_link = dynamic_cast<const s4u::SplitDuplexLink*>(link.get_link());
+ xbt_enforce(sd_link,
+ "Add_route: cast to SpliDuplexLink impossible. This should not happen, please contact SimGrid team");
+ resource::StandardLinkImpl* link_impl;
+ switch (link.get_direction()) {
+ case s4u::LinkInRoute::Direction::UP:
+ if (backroute)
+ link_impl = sd_link->get_link_down()->get_impl();
+ else
+ link_impl = sd_link->get_link_up()->get_impl();
+ break;
+ case s4u::LinkInRoute::Direction::DOWN:
+ if (backroute)
+ link_impl = sd_link->get_link_up()->get_impl();
+ else
+ link_impl = sd_link->get_link_down()->get_impl();
+ break;
+ default:
+ throw std::invalid_argument("Invalid add_route. Split-Duplex link without a direction: " +
+ link.get_link()->get_name());
+ }
+ links.push_back(link_impl);
+ }
+ return links;
+}
+
+resource::StandardLinkImpl* NetZoneImpl::get_link_by_name_or_null(const std::string& name) const
+{
+ if (auto link_it = links_.find(name); link_it != links_.end())
+ return link_it->second;
+
+ for (const auto* child : children_) {
+ if (auto* link = child->get_link_by_name_or_null(name))
+ return link;
+ }
+
+ return nullptr;
+}
+
+resource::SplitDuplexLinkImpl* NetZoneImpl::get_split_duplex_link_by_name_or_null(const std::string& name) const
+{
+ if (auto link_it = split_duplex_links_.find(name); link_it != split_duplex_links_.end())
+ return link_it->second.get();
+
+ for (const auto* child : children_) {
+ if (auto* link = child->get_split_duplex_link_by_name_or_null(name))
+ return link;
+ }
+
+ return nullptr;
+}
+
+resource::HostImpl* NetZoneImpl::get_host_by_name_or_null(const std::string& name) const
+{
+ if (auto host_it = hosts_.find(name); host_it != hosts_.end())
+ return host_it->second;
+
+ for (const auto* child : children_) {
+ if (auto* host = child->get_host_by_name_or_null(name))
+ return host;
+ }
+
+ return nullptr;
+}
+
+std::vector<s4u::Host*> NetZoneImpl::get_filtered_hosts(const std::function<bool(s4u::Host*)>& filter) const
+{
+ std::vector<s4u::Host*> filtered_list;
+ for (auto const& [_, host] : hosts_) {
+ s4u::Host* h = host->get_iface();
+ if (filter(h))
+ filtered_list.push_back(h);
+ /* Engine::get_hosts returns the VMs too */
+ for (auto* vm : h->get_impl()->get_vms()) {
+ if (filter(vm))
+ filtered_list.push_back(vm);
+ }
+ }
+
+ for (const auto* child : children_) {
+ auto child_links = child->get_filtered_hosts(filter);
+ filtered_list.insert(filtered_list.end(), std::make_move_iterator(child_links.begin()),
+ std::make_move_iterator(child_links.end()));
+ }
+ return filtered_list;
+}
+