Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
New 'WiFi' routing, that makes it easier to specify WiFi network zones
authorMartin Quinson <martin.quinson@ens-rennes.fr>
Mon, 5 Oct 2020 09:57:21 +0000 (11:57 +0200)
committerMartin Quinson <martin.quinson@ens-rennes.fr>
Mon, 5 Oct 2020 09:58:40 +0000 (11:58 +0200)
14 files changed:
ChangeLog
MANIFEST.in
examples/platforms/wifi.xml
examples/s4u/network-wifi/s4u-network-wifi.cpp
include/simgrid/kernel/routing/WifiZone.hpp [new file with mode: 0644]
src/kernel/routing/WifiZone.cpp [new file with mode: 0644]
src/s4u/s4u_Host.cpp
src/surf/network_cm02.cpp
src/surf/sg_platf.cpp
teshsuite/surf/wifi_usage/wifi_usage.cpp
teshsuite/surf/wifi_usage/wifi_usage.tesh
teshsuite/surf/wifi_usage_decay/wifi_usage_decay.cpp
teshsuite/surf/wifi_usage_decay/wifi_usage_decay.tesh
tools/cmake/DefinePackages.cmake

index 3ccecb9..4bcc2e7 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -52,6 +52,9 @@ C interface:
 Simix:
  - Remove obsolete option --cfg=contexts/parallel-threshold.
 
+XML:
+ - New routing 'WiFi' that makes it easier to specify a wifi network zone.
+
 Fixed bugs (FG#.. -> FramaGit bugs; FG!.. -> FG merge requests)
  (FG: issues on Framagit; GF: issues on GForge; GH: issues on GitHub)
  - FG#41: Add sg_actor_create C interface
index 8b1f81f..ff8677f 100644 (file)
@@ -2006,6 +2006,7 @@ include include/simgrid/kernel/routing/NetZoneImpl.hpp
 include include/simgrid/kernel/routing/RoutedZone.hpp
 include include/simgrid/kernel/routing/TorusZone.hpp
 include include/simgrid/kernel/routing/VivaldiZone.hpp
+include include/simgrid/kernel/routing/WifiZone.hpp
 include include/simgrid/link.h
 include include/simgrid/mailbox.h
 include include/simgrid/modelchecker.h
@@ -2246,6 +2247,7 @@ include src/kernel/routing/NetZoneImpl.cpp
 include src/kernel/routing/RoutedZone.cpp
 include src/kernel/routing/TorusZone.cpp
 include src/kernel/routing/VivaldiZone.cpp
+include src/kernel/routing/WifiZone.cpp
 include src/mc/AddressSpace.hpp
 include src/mc/ModelChecker.cpp
 include src/mc/ModelChecker.hpp
index 85a7aed..9d054b2 100755 (executable)
@@ -4,31 +4,29 @@
 <platform version="4.1">
   <zone id="world" routing="Full">
 
-    <zone id="WIFI zone" routing="Cluster">
-        <!-- Two stations in the wifi zone -->
+    <zone id="WIFI zone" routing="Wifi">
+        <prop id="access_point" value="WIFI router" />
+       
+        <!-- Declare the stations of this wifi zone -->
         <host id="Station 1" speed="100.0Mf,50.0Mf,20.0Mf" />
         <host id="Station 2" speed="100.0Mf,50.0Mf,20.0Mf" />
 
-        <!-- Declare the wifi media after the hosts (so that the parser don't choke on an ambiguity between internal and leaf zones) -->
+        <!-- Declare the wifi media (after hosts because our parser is sometimes annoying) -->
         <link id="AP1" sharing_policy="WIFI" bandwidth="54Mbps,36Mbps,24Mbps" latency="0ms" />
        
-        <!-- Specify that stations use the WIFI link for every communication (incoming or outgoing) -->
-        <host_link id="Station 1" up="AP1" down="AP1"/>
-        <host_link id="Station 2" up="AP1" down="AP1"/>
-
         <router id="WIFI router"/>
     </zone>
 
 
     <!-- NODE1 AS -->
     <zone id="Wired zone" routing="Full">
-      <host id="NODE1" speed="100.0Mf,50.0Mf,20.0Mf" />
+      <host id="node1" speed="100.0Mf,50.0Mf,20.0Mf" />
     </zone>
     
 
     <!-- AS Routing -->
     <link id="Collector" sharing_policy="SHARED" bandwidth="100Mbps" latency="0ms" />
-    <zoneRoute src="WIFI zone" dst="Wired zone" gw_src="WIFI router" gw_dst="NODE1">
+    <zoneRoute src="WIFI zone" dst="Wired zone" gw_src="WIFI router" gw_dst="node1">
       <link_ctn id="Collector" />
     </zoneRoute>
     
index 57c896a..a4ac300 100644 (file)
@@ -6,7 +6,7 @@
 #include "simgrid/s4u.hpp"
 
 /* This example demonstrates how to use wifi links in SimGrid. Most of the interesting things happen in the
- * corresponding XML file.
+ * corresponding XML file: examples/platforms/wifi.xml
  */
 
 XBT_LOG_NEW_DEFAULT_CATEGORY(s4u_network_wifi, "Messages specific for this s4u example");
@@ -33,12 +33,14 @@ int main(int argc, char* argv[])
 
   e.load_platform(argv[1]);
 
+  /* Exchange a message between the 2 stations */
   auto mailbox  = simgrid::s4u::Mailbox::by_name("mailbox");
   auto station1 = simgrid::s4u::Host::by_name("Station 1");
   auto station2 = simgrid::s4u::Host::by_name("Station 2");
   simgrid::s4u::Actor::create("sender", station1, sender, mailbox, 1e7);
   simgrid::s4u::Actor::create("receiver", station2, receiver, mailbox);
 
+  /* Declare that the stations are not at the same distance from their AP */
   auto ap = simgrid::s4u::Link::by_name("AP1");
   ap->set_host_wifi_rate(station1, 1); // The host "Station 1" uses the second level of bandwidths on that AP
   ap->set_host_wifi_rate(station2, 0); // This is perfectly useless as level 0 is used by default
diff --git a/include/simgrid/kernel/routing/WifiZone.hpp b/include/simgrid/kernel/routing/WifiZone.hpp
new file mode 100644 (file)
index 0000000..2227093
--- /dev/null
@@ -0,0 +1,42 @@
+/* Copyright (c) 2013-2020. The SimGrid Team. All rights reserved.          */
+
+/* This program is free software; you can redistribute it and/or modify it
+ * under the terms of the license (GNU LGPL) which comes with this package. */
+
+#ifndef SIMGRID_ROUTING_WIFI_HPP_
+#define SIMGRID_ROUTING_WIFI_HPP_
+
+#include <simgrid/kernel/routing/RoutedZone.hpp>
+
+namespace simgrid {
+namespace kernel {
+namespace routing {
+
+/** @ingroup ROUTING_API
+ *  @brief NetZone modeling a Wifi zone
+ *
+ *  This routing has only one link, representing the wifi medium (ie, the air).
+ *  That link is used for all communications within the zone.
+ */
+class XBT_PRIVATE WifiZone : public RoutedZone {
+public:
+  explicit WifiZone(NetZoneImpl* father, const std::string& name, resource::NetworkModel* netmodel);
+  WifiZone(const WifiZone&) = delete;
+  WifiZone& operator=(const WifiZone) = delete;
+  ~WifiZone()                         = default;
+
+  void seal() override;
+  void get_local_route(NetPoint* src, NetPoint* dst, RouteCreationArgs* into, double* latency) override;
+  s4u::Link* create_link(const std::string& name, const std::vector<double>& bandwidths, double latency,
+                         s4u::Link::SharingPolicy policy,
+                         const std::unordered_map<std::string, std::string>* props) override;
+
+private:
+  resource::LinkImpl* wifi_link_ = nullptr; // Representing the air media (there is no such thing in NS-3)
+  NetPoint* access_point_        = nullptr; // Zone's gateway to the external world
+};
+} // namespace routing
+} // namespace kernel
+} // namespace simgrid
+
+#endif /* SIMGRID_ROUTING_WIFI_HPP_ */
diff --git a/src/kernel/routing/WifiZone.cpp b/src/kernel/routing/WifiZone.cpp
new file mode 100644 (file)
index 0000000..4c64420
--- /dev/null
@@ -0,0 +1,73 @@
+/* Copyright (c) 2009-2020. The SimGrid Team. All rights reserved.          */
+
+/* This program is free software; you can redistribute it and/or modify it
+ * under the terms of the license (GNU LGPL) which comes with this package. */
+
+#include "simgrid/kernel/routing/WifiZone.hpp"
+#include "simgrid/kernel/routing/NetPoint.hpp"
+#include "src/surf/network_interface.hpp"
+#include "src/surf/xml/platf_private.hpp"
+#include "surf/surf.hpp"
+
+#include <unordered_set>
+
+XBT_LOG_NEW_DEFAULT_SUBCATEGORY(surf_route_wifi, surf, "Routing part of surf");
+
+namespace simgrid {
+namespace kernel {
+namespace routing {
+WifiZone::WifiZone(NetZoneImpl* father, const std::string& name, resource::NetworkModel* netmodel)
+    : RoutedZone(father, name, netmodel)
+{
+}
+
+void WifiZone::seal()
+{
+  const char* AP_name = get_property("access_point");
+  if (AP_name != nullptr) {
+    access_point_ = sg_netpoint_by_name_or_null(AP_name);
+    xbt_assert(access_point_ != nullptr, "Access point '%s' of WIFI zone '%s' does not exist: no such host or router.",
+               AP_name, get_cname());
+    xbt_assert(access_point_->is_host() || access_point_->is_router(),
+               "Access point '%s' of WIFI zone '%s' must be either an host or a router.", AP_name, get_cname());
+  }
+}
+
+void WifiZone::get_local_route(NetPoint* src, NetPoint* dst, RouteCreationArgs* res, double* lat)
+{
+  XBT_DEBUG("full getLocalRoute from %s[%u] to %s[%u]", src->get_cname(), src->id(), dst->get_cname(), dst->id());
+
+  if (wifi_link_ != nullptr) {
+    // If src and dst are nodes, not access_point, we need to traverse the link twice
+    // Otherwise (if src or dst is access_poit), we need to traverse the link only once
+
+    if (src != access_point_) {
+      XBT_DEBUG("src %s is not our gateway", src->get_cname());
+      res->link_list.push_back(wifi_link_);
+      if (lat)
+        *lat += wifi_link_->get_latency();
+    }
+    if (dst != access_point_) {
+      XBT_DEBUG("dst %s is not our gateway", dst->get_cname());
+      res->link_list.push_back(wifi_link_);
+      if (lat)
+        *lat += wifi_link_->get_latency();
+    }
+  }
+}
+s4u::Link* WifiZone::create_link(const std::string& name, const std::vector<double>& bandwidths, double latency,
+                                 s4u::Link::SharingPolicy policy,
+                                 const std::unordered_map<std::string, std::string>* props)
+{
+  xbt_assert(wifi_link_ == nullptr,
+             "WIFI netzone %s contains more than one link. Please only declare one, the wifi link.", get_cname());
+  xbt_assert(policy == s4u::Link::SharingPolicy::WIFI, "Link %s in WIFI zone %s must follow the WIFI sharing policy.",
+             name.c_str(), get_cname());
+
+  auto s4u_link = NetZoneImpl::create_link(name, bandwidths, latency, policy, props);
+  wifi_link_    = s4u_link->get_impl();
+  return s4u_link;
+}
+} // namespace routing
+} // namespace kernel
+} // namespace simgrid
index 702b1c8..04d1f58 100644 (file)
@@ -164,7 +164,7 @@ void Host::route_to(const Host* dest, std::vector<kernel::resource::LinkImpl*>&
     XBT_CDEBUG(surf_route, "Route from '%s' to '%s' (latency: %f):", get_cname(), dest->get_cname(),
                (latency == nullptr ? -1 : *latency));
     for (auto const& link : links)
-      XBT_CDEBUG(surf_route, "Link %s", link->get_cname());
+      XBT_CDEBUG(surf_route, "  Link '%s'", link->get_cname());
   }
 }
 
index f6b424c..feccacf 100644 (file)
@@ -202,6 +202,13 @@ Action* NetworkCm02Model::communicate(s4u::Host* src, s4u::Host* dst, double siz
                "WIFI link. Did you call link->set_host_rate()?",
                src->get_cname(), dst->get_cname(), dst_wifi_link->get_cname(), dst->get_cname());
   }
+  if (route.size() > 2)
+    for (unsigned i = 1; i < route.size() - 1; i++)
+      xbt_assert(route.at(i)->get_sharing_policy() != s4u::Link::SharingPolicy::WIFI,
+                 "Link '%s' is a WIFI link. It can only be at the beginning or the end of the route from '%s' to '%s', "
+                 "not in between (it is at position %u out of %zu). "
+                 "Did you declare an access_point in your WIFI zones?",
+                 route.at(i)->get_cname(), src->get_cname(), dst->get_cname(), i + 1, route.size());
 
   NetworkCm02Action* action;
   if (src_wifi_link == nullptr && dst_wifi_link == nullptr)
index 8cd7bce..af9b3eb 100644 (file)
@@ -15,6 +15,7 @@
 #include "simgrid/kernel/routing/NetZoneImpl.hpp"
 #include "simgrid/kernel/routing/TorusZone.hpp"
 #include "simgrid/kernel/routing/VivaldiZone.hpp"
+#include "simgrid/kernel/routing/WifiZone.hpp"
 #include "simgrid/s4u/Engine.hpp"
 #include "src/include/simgrid/sg_config.hpp"
 #include "src/include/surf/surf.hpp"
@@ -606,8 +607,10 @@ simgrid::kernel::routing::NetZoneImpl* sg_platf_new_Zone_begin(const simgrid::ke
       new_zone = new simgrid::kernel::routing::EmptyZone(current_routing, zone->id, netmodel);
   } else if (strcasecmp(zone->routing.c_str(),"Vivaldi") == 0) {
       new_zone = new simgrid::kernel::routing::VivaldiZone(current_routing, zone->id, netmodel);
+  } else if (strcasecmp(zone->routing.c_str(), "Wifi") == 0) {
+    new_zone = new simgrid::kernel::routing::WifiZone(current_routing, zone->id, netmodel);
   } else {
-      xbt_die("Not a valid model!");
+    xbt_die("Not a valid model!");
   }
 
   if (current_routing == nullptr) { /* it is the first one */
index 19e1741..9116697 100644 (file)
@@ -32,7 +32,7 @@ static void main_dispatcher()
     XBT_INFO("  mu = 1 / [ 1/1 * 1/54Mbps ] = 5.4e+07");
     XBT_INFO("  simulation_time = 1000*8 / mu = 0.0001481481s");
   }
-  run_ping_test("Station 1", "NODE1", 1000);
+  run_ping_test("Station 1", "node1", 1000);
 
   XBT_INFO("TEST: Send from a station to another station on the same AP.");
   XBT_INFO("------------------------------------------------------------");
@@ -53,7 +53,7 @@ int main(int argc, char** argv)
 {
   simgrid::s4u::Engine engine(&argc, argv);
   engine.load_platform(argv[1]);
-  simgrid::s4u::Actor::create("dispatcher", simgrid::s4u::Host::by_name("NODE1"), main_dispatcher);
+  simgrid::s4u::Actor::create("dispatcher", simgrid::s4u::Host::by_name("node1"), main_dispatcher);
   engine.run();
 
   return 0;
index 007fa0c..68e67a5 100644 (file)
@@ -9,7 +9,7 @@ $ ${bindir:=.}/wifi_usage ${platfdir}/wifi.xml --log=root.fmt=%m%n
 > We should thus have:
 >   mu = 1 / [ 1/1 * 1.05/54Mbps ] = 51428571
 >   simulation_time = 1000*8 / mu = 0.0001555556s (rounded to 0.000156s in SimGrid)
-> Actual result: Sending 1000 bytes from 'Station 1' to 'NODE1' takes 0.000156 seconds.
+> Actual result: Sending 1000 bytes from 'Station 1' to 'node1' takes 0.000156 seconds.
 >
 >
 > TEST: Send from a station to another station on the same AP.
@@ -31,7 +31,7 @@ $ ${bindir:=.}/wifi_usage ${platfdir}/wifi.xml --log=root.fmt=%m%n --cfg=network
 > We should thus have:
 >   mu = 1 / [ 1/1 * 1/54Mbps ] = 5.4e+07
 >   simulation_time = 1000*8 / mu = 0.0001481481s
-> Actual result: Sending 1000 bytes from 'Station 1' to 'NODE1' takes 0.000148 seconds.
+> Actual result: Sending 1000 bytes from 'Station 1' to 'node1' takes 0.000148 seconds.
 >
 >
 > TEST: Send from a station to another station on the same AP.
index 65a1cde..d8fe620 100644 (file)
@@ -34,7 +34,7 @@ static void main_dispatcher()
     XBT_INFO("  mu = 1 / [ 1/1 * 1/49.00487Mbps ] = 49004870");
     XBT_INFO("  simulation_time = 1000*8 / mu = 0.0001632491s (rounded to 0.000163s in SimGrid)");
   }
-  run_ping_test("Station 1", "NODE1", 1000);
+  run_ping_test("Station 1", "node1", 1000);
 
   XBT_INFO("TEST: Send from a station to another station on the same AP.");
   XBT_INFO("------------------------------------------------------------");
@@ -57,7 +57,7 @@ int main(int argc, char** argv)
 {
   simgrid::s4u::Engine engine(&argc, argv);
   engine.load_platform(argv[1]);
-  simgrid::s4u::Actor::create("dispatcher", simgrid::s4u::Host::by_name("NODE1"), main_dispatcher);
+  simgrid::s4u::Actor::create("dispatcher", simgrid::s4u::Host::by_name("node1"), main_dispatcher);
   engine.run();
 
   return 0;
index 810c997..f1208fd 100644 (file)
@@ -10,7 +10,7 @@ $ ${bindir:=.}/wifi_usage_decay ${platfdir}/wifi.xml --log=root.fmt=%m%n
 > We should thus have:
 >   mu = 1 / [ 1/1 * 1.05/49.00487Mbps ] = 46671305
 >   simulation_time = 1000*8 / mu = 0.0001714115 (rounded to 0.000171s in SimGrid)
-> Actual result: Sending 1000 bytes from 'Station 1' to 'NODE1' takes 0.000171 seconds.
+> Actual result: Sending 1000 bytes from 'Station 1' to 'node1' takes 0.000171 seconds.
 >
 >
 > TEST: Send from a station to another station on the same AP.
@@ -34,7 +34,7 @@ $ ${bindir:=.}/wifi_usage_decay ${platfdir}/wifi.xml --log=root.fmt=%m%n --cfg=n
 > We should thus have:
 >   mu = 1 / [ 1/1 * 1/49.00487Mbps ] = 49004870
 >   simulation_time = 1000*8 / mu = 0.0001632491s (rounded to 0.000163s in SimGrid)
-> Actual result: Sending 1000 bytes from 'Station 1' to 'NODE1' takes 0.000163 seconds.
+> Actual result: Sending 1000 bytes from 'Station 1' to 'node1' takes 0.000163 seconds.
 >
 >
 > TEST: Send from a station to another station on the same AP.
index 739760d..78a29f2 100644 (file)
@@ -342,6 +342,7 @@ set(SURF_SRC
   src/kernel/routing/TorusZone.cpp
   src/kernel/routing/RoutedZone.cpp
   src/kernel/routing/VivaldiZone.cpp
+  src/kernel/routing/WifiZone.cpp
 
   src/kernel/EngineImpl.cpp
   src/kernel/EngineImpl.hpp
@@ -745,6 +746,7 @@ set(headers_to_install
   include/simgrid/kernel/routing/RoutedZone.hpp
   include/simgrid/kernel/routing/TorusZone.hpp
   include/simgrid/kernel/routing/VivaldiZone.hpp
+  include/simgrid/kernel/routing/WifiZone.hpp
 
   include/smpi/mpi.h
   include/smpi/sampi.h