Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
New implementation for bandwidth factors
authorBruno Donassolo <bruno.donassolo@inria.fr>
Thu, 27 May 2021 14:57:57 +0000 (16:57 +0200)
committerBruno Donassolo <bruno.donassolo@inria.fr>
Tue, 1 Jun 2021 14:34:08 +0000 (16:34 +0200)
Bandwidth factors are now implemented at the Action level, reducing the
speed that an action advances (e.g. the number of bytes transmitted).

In the past, the factor took place at the maxmin system, limiting the
amount of resources a communication could use.

For example, a bw factor of 0.97 (default for LV08 network model) was
reflected by reducing the link capacity to 0.97*C. So, a 100MBs link had
97MBs capacity in the maxmin system.

Now, a communication alone using this link may use the 100MBs, but after
one second, it'll transmit only 97MB of data.

NOTE: This change may impact the timing of your experiments.

include/simgrid/kernel/resource/Action.hpp
src/instr/instr_platform.cpp
src/kernel/resource/Action.cpp
src/kernel/resource/Model.cpp
src/plugins/link_energy_wifi.cpp
src/plugins/vm/VirtualMachineImpl.cpp
src/surf/cpu_interface.cpp
src/surf/disk_s19.cpp
src/surf/network_cm02.cpp
src/surf/ptask_L07.cpp

index fb24935..aac2b9e 100644 (file)
@@ -72,6 +72,7 @@ class XBT_PUBLIC Action {
   activity::ActivityImpl* activity_ = nullptr;
 
   /* LMM */
+  double factor_           = 1.0; /**< Factor for effective rate = var->get_value() * factor_ */
   double last_update_      = 0;
   double last_value_       = 0;
   lmm::Variable* variable_ = nullptr;
@@ -244,6 +245,23 @@ public:
   double get_last_update() const { return last_update_; }
   void set_last_update();
 
+  /**
+   * @brief Set a factor for this action
+   *
+   * Defines a multiplicative factor for the consumption of the underlying resource.
+   *
+   * @param factor Multiplicative factor for this action (e.g. 0.97)
+   */
+  void set_rate_factor(double factor) { factor_ = factor; }
+  /**
+   * @brief Get the effective consumption rate of the resource
+   *
+   * The rate is based on the sharing given by the maxmin system underneath.
+   * However, it depends on the factor defined for this action.
+   *
+   * So, the effective rate is equal to var->get_value() * factor_
+   */
+  double get_rate() const;
   double get_last_value() const { return last_value_; }
   void set_last_value(double val) { last_value_ = val; }
   void set_suspend_state(Action::SuspendStates state) { suspended_ = state; }
index 08b0fb1..6db1c3b 100644 (file)
@@ -336,7 +336,7 @@ static void on_action_state_change(kernel::resource::Action const& action,
   auto n = static_cast<unsigned>(action.get_variable()->get_number_of_constraint());
 
   for (unsigned i = 0; i < n; i++) {
-    double value = action.get_variable()->get_value() * action.get_variable()->get_constraint_weight(i);
+    double value = action.get_rate() * action.get_variable()->get_constraint_weight(i);
     /* Beware of composite actions: ptasks put links and cpus together. Extra pb: we cannot dynamic_cast from void* */
     kernel::resource::Resource* resource = action.get_variable()->get_constraint(i)->get_id();
     const kernel::resource::CpuImpl* cpu = dynamic_cast<kernel::resource::CpuImpl*>(resource);
index 338a5ab..825578b 100644 (file)
@@ -96,6 +96,11 @@ double Action::get_bound() const
   return variable_ ? variable_->get_bound() : 0;
 }
 
+double Action::get_rate() const
+{
+  return variable_ ? variable_->get_value() * factor_ : 0;
+}
+
 void Action::set_bound(double bound)
 {
   XBT_IN("(%p,%g)", this, bound);
index b37c3b8..905ac2d 100644 (file)
@@ -68,7 +68,7 @@ double Model::next_occurring_event_lazy(double now)
     action->update_remains_lazy(now);
 
     double min   = -1;
-    double share = action->get_variable()->get_value();
+    double share = action->get_rate();
 
     if (share > 0) {
       double time_to_completion;
@@ -117,7 +117,7 @@ double Model::next_occurring_event_full(double /*now*/)
   double min = -1;
 
   for (Action& action : *get_started_action_set()) {
-    double value = action.get_variable()->get_value();
+    double value = action.get_rate();
     if (value > 0) {
       if (action.get_remains() > 0)
         value = action.get_remains_no_update() / value;
index 8a227c3..f9332d1 100644 (file)
@@ -143,11 +143,10 @@ void LinkEnergyWifi::update(const kernel::resource::NetworkAction&)
   double durUsage = 0;
   while (const auto* var = wifi_link->get_constraint()->get_variable(&elem)) {
     auto* action = static_cast<kernel::resource::NetworkWifiAction*>(var->get_id());
-    XBT_DEBUG("cost: %f action value: %f link rate 1: %f link rate 2: %f", action->get_cost(),
-              action->get_variable()->get_value(), wifi_link->get_host_rate(&action->get_src()),
-              wifi_link->get_host_rate(&action->get_dst()));
+    XBT_DEBUG("cost: %f action value: %f link rate 1: %f link rate 2: %f", action->get_cost(), action->get_rate(),
+              wifi_link->get_host_rate(&action->get_src()), wifi_link->get_host_rate(&action->get_dst()));
 
-    if (action->get_variable()->get_value() != 0.0) {
+    if (action->get_rate() != 0.0) {
       auto it = flowTmp.find(action);
 
       // if the flow has not been registered, initialize it: 0 bytes sent, and not updated since its creation timestamp
@@ -161,7 +160,7 @@ void LinkEnergyWifi::update(const kernel::resource::NetworkAction&)
        * If this is longer than the duration since the previous update, active duration = now - previous_update
        */
       double du = // durUsage on the current flow
-          (action->get_cost() - it->second.first) / action->get_variable()->get_value();
+          (action->get_cost() - it->second.first) / action->get_rate();
 
       if(du > surf_get_clock()-it->second.second)
         du = surf_get_clock()-it->second.second;
@@ -171,7 +170,7 @@ void LinkEnergyWifi::update(const kernel::resource::NetworkAction&)
         durUsage = du;
 
       // update the amount of data already sent by the flow
-      it->second.first += du*action->get_variable()->get_value();
+      it->second.first += du * action->get_rate();
       it->second.second =  surf_get_clock();
 
       // important: if the transmission finished, remove it (needed for performance and multi-message flows)
index 08ea671..61e2e33 100644 (file)
@@ -159,7 +159,7 @@ double VMModel::next_occurring_event(double now)
     const kernel::resource::CpuImpl* cpu = ws_vm->pimpl_cpu;
 
     // solved_value below is X1 in comment above: what this VM got in the sharing on the PM
-    double solved_value = ws_vm->get_vm_impl()->get_action()->get_variable()->get_value();
+    double solved_value = ws_vm->get_vm_impl()->get_action()->get_rate();
     XBT_DEBUG("assign %f to vm %s @ pm %s", solved_value, ws_vm->get_cname(), ws_vm->get_pm()->get_cname());
 
     kernel::lmm::System* vcpu_system = cpu->get_model()->get_maxmin_system();
index bfa0af4..24f37a8 100644 (file)
@@ -36,7 +36,7 @@ void CpuModel::update_actions_state_full(double /*now*/, double delta)
     auto& action = static_cast<CpuAction&>(*it);
     ++it; // increment iterator here since the following calls to action.finish() may invalidate it
 
-    action.update_remains(action.get_variable()->get_value() * delta);
+    action.update_remains(action.get_rate() * delta);
     action.update_max_duration(delta);
 
     if (((action.get_remains_no_update() <= 0) && (action.get_variable()->get_penalty() > 0)) ||
@@ -159,7 +159,7 @@ void CpuAction::update_remains_lazy(double now)
   }
 
   set_last_update();
-  set_last_value(get_variable()->get_value());
+  set_last_value(get_rate());
 }
 
 xbt::signal<void(CpuAction const&, Action::State)> CpuAction::on_state_change;
index 22d9dbd..aa2d0ec 100644 (file)
@@ -41,7 +41,7 @@ void DiskS19Model::update_actions_state(double /*now*/, double delta)
   for (auto it = std::begin(*get_started_action_set()); it != std::end(*get_started_action_set());) {
     auto& action = *it;
     ++it; // increment iterator here since the following calls to action.finish() may invalidate it
-    action.update_remains(rint(action.get_variable()->get_value() * delta));
+    action.update_remains(rint(action.get_rate() * delta));
     action.update_max_duration(delta);
 
     if (((action.get_remains_no_update() <= 0) && (action.get_variable()->get_penalty() > 0)) ||
index 8e1c76d..a11156a 100644 (file)
@@ -187,7 +187,7 @@ void NetworkCm02Model::update_actions_state_full(double /*now*/, double delta)
        */
       action.update_remains(action.get_remains());
     }
-    action.update_remains(action.get_variable()->get_value() * delta);
+    action.update_remains(action.get_rate() * delta);
 
     if (action.get_max_duration() != NO_MAX_DURATION)
       action.update_max_duration(delta);
@@ -338,6 +338,10 @@ void NetworkCm02Model::comm_action_set_bounds(const s4u::Host* src, const s4u::H
   } else {
     bw_factor = get_bandwidth_factor(size);
   }
+  xbt_assert(bw_factor != 0, "Invalid param for comm %s -> %s. Bandwidth factor cannot be 0", src->get_cname(),
+             dst->get_cname());
+  action->set_rate_factor(bw_factor);
+
   /* get mininum bandwidth among links in the route and multiply by correct factor
    * ignore wi-fi links, they're not considered for bw_factors */
   double bandwidth_bound = -1.0;
@@ -347,12 +351,13 @@ void NetworkCm02Model::comm_action_set_bounds(const s4u::Host* src, const s4u::H
     if (bandwidth_bound == -1.0 || l->get_bandwidth() < bandwidth_bound)
       bandwidth_bound = l->get_bandwidth();
   }
-  bandwidth_bound *= bw_factor;
 
+  /* increase rate given by user considering the factor, since the actual rate will be
+   * modified by it */
+  rate = rate / bw_factor;
   /* the bandwidth is determined by the minimum between flow and user's defined rate */
   if (rate >= 0 && rate < bandwidth_bound)
     bandwidth_bound = rate;
-
   action->set_user_bound(bandwidth_bound);
 
   action->lat_current_ = action->latency_;
@@ -439,7 +444,7 @@ NetworkCm02Link::NetworkCm02Link(const std::string& name, double bandwidth, kern
 {
   bandwidth_.scale = 1.0;
   bandwidth_.peak  = bandwidth;
-  this->set_constraint(system->constraint_new(this, sg_bandwidth_factor * bandwidth));
+  this->set_constraint(system->constraint_new(this, bandwidth));
 }
 
 void NetworkCm02Link::apply_event(kernel::profile::Event* triggered, double value)
@@ -471,8 +476,7 @@ void NetworkCm02Link::set_bandwidth(double value)
 {
   bandwidth_.peak = value;
 
-  get_model()->get_maxmin_system()->update_constraint_bound(get_constraint(),
-                                                            sg_bandwidth_factor * (bandwidth_.peak * bandwidth_.scale));
+  get_model()->get_maxmin_system()->update_constraint_bound(get_constraint(), (bandwidth_.peak * bandwidth_.scale));
 
   LinkImpl::on_bandwidth_change();
 
@@ -555,7 +559,7 @@ void NetworkCm02Action::update_remains_lazy(double now)
   }
 
   set_last_update();
-  set_last_value(get_variable()->get_value());
+  set_last_value(get_rate());
 }
 
 } // namespace resource
index e6e51fc..30a4f9e 100644 (file)
@@ -105,9 +105,8 @@ void HostL07Model::update_actions_state(double /*now*/, double delta)
         action.set_last_update();
       }
     }
-    XBT_DEBUG("Action (%p) : remains (%g) updated by %g.", &action, action.get_remains(),
-              action.get_variable()->get_value() * delta);
-    action.update_remains(action.get_variable()->get_value() * delta);
+    XBT_DEBUG("Action (%p) : remains (%g) updated by %g.", &action, action.get_remains(), action.get_rate() * delta);
+    action.update_remains(action.get_rate() * delta);
     action.update_max_duration(delta);
 
     XBT_DEBUG("Action (%p) : remains (%g).", &action, action.get_remains());