Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
Merge branch 'master' of framagit.org:simgrid/simgrid
authorMartin Quinson <martin.quinson@ens-rennes.fr>
Tue, 23 May 2023 18:57:11 +0000 (20:57 +0200)
committerMartin Quinson <martin.quinson@ens-rennes.fr>
Tue, 23 May 2023 18:57:11 +0000 (20:57 +0200)
1  2 
ChangeLog
include/simgrid/s4u/Activity.hpp
src/instr/instr_platform.cpp
src/kernel/resource/VirtualMachineImpl.cpp
src/s4u/s4u_Activity.cpp

diff --combined ChangeLog
+++ b/ChangeLog
@@@ -1,13 -1,15 +1,15 @@@
  SimGrid (3.32.1) not released yet (target december 22)
  
  General:
+  - SimGrid now requires a compiler with C++17 support for public headers too.
+    Sibling projects should upgrade their FindSimGrid.cmake
   - Remove the MSG API: its EOL was scheduled for 2020.
   - Remove the Java bindings: they were limited to the MSG interface.
   - On Windows, you now need to install WSL2 as the native builds are now disabled.
     It was not really working anyway.
   - Support for 32bits architecture is not tested anymore on our CI infrastructure.
     It may break in the future, but we think that nobody's using SimGrid on 32 bits.
-  - Remove the surf module. It was replaced by the kernel/models module, and that 
+  - Remove the surf module. It was replaced by the kernel/models module, and that
     refactoring took almost 10 years to properly complete.
  
  S4U:
     possible.
   - Allow to set a concurrency limit on disks and hosts, as it was already the case for links.
   - Rename Link::get_usage() to Link::get_load() for consistency with Host::
 + - Every signal now come with a static version that is invoked for every object of that class,
 +   and an instance version that is invoked for this specific object only. For example, 
 +   s4u::Actor::on_suspend_cb() adds a callback that is invoked for the suspend of any actor while
 +   s4u::Actor::on_this_suspend_cb() adds a callback for this specific actor only.
 + - Activity::on_suspended_cb() is renamed to Activity::on_suspend_cb(), and fired right before the suspend.
 + - Activity::on_resumed_cb() is renamed to Activity::on_resume_cb(), and fired right before the resume.
  
 -New plugin: Operation
 - - Operations are designed to represent workflows, i.e, graphs of repeatable Activities.
 - - Documentation: https://simgrid.frama.io/simgrid/Plugins.html#operation
 - - Examples: examples/cpp/operation-*
 -
 -New plugin: Battery
 - - Enable the management of batteries on hosts.
 - - Documentation: https://simgrid.frama.io/simgrid/Plugins.html#battery
 - - Examples: examples/cpp/battery-*
 +New S4U plugins:
 + - Operation: They are designed to represent workflows, i.e, graphs of repeatable Activities.
 +   See the examples under examples/cpp/operation-* and the documentation in the Plugins page.
 + - Battery: Enable the management of batteries on hosts.
 +   See the examples under examples/cpp/battery-* and the documentation in the Plugins page.
  
  Kernel:
   - optimize an internal datastructure (use a set instead of a list for ongoing activities),
@@@ -70,8 -70,8 +72,8 @@@ Model checking
   - Synchronize the MBI tests with upstream.
   - Show the full actor bactraces when replaying a MC trace (with model-check/replay)
     and the status of all actors on deadlocks in MC mode.
-  - The safety/stateless aspects of the MC are now enabled by default in all simgrid builds. 
-    Liveness and stateful aspects are still controled by the enabling_model-checking 
+  - The safety/stateless aspects of the MC are now enabled by default in all simgrid builds.
+    Liveness and stateful aspects are still controled by the enabling_model-checking
     configuration option.
   - Stateless model-checking is now usable on any system, including Mac OSX and ARM processors.
  
@@@ -672,7 -672,7 +674,7 @@@ The Release release (the French lockdow
  
  Important user-visible changes:
   - SimGrid now requires a compiler with C++14 support.
-    Sibling projects should upgrade their FindSimgrid.cmake
+    Sibling projects should upgrade their FindSimGrid.cmake
   - Surf precision default value is now 1e-9, instead of 1e-5. This was changed as
     several users had difficulties to understand issues when using high bandwidth or
     small latency events. The new value was already the default for SMPI and
@@@ -51,6 -51,7 +51,7 @@@ public
    bool has_no_successor() const { return successors_.empty(); }
    const std::set<ActivityPtr>& get_dependencies() const { return dependencies_; }
    const std::vector<ActivityPtr>& get_successors() const { return successors_; }
+   virtual void fire_this_completion() const = 0;
  
  protected:
    Activity()  = default;
  
  private:
    static xbt::signal<void(Activity&)> on_veto;
-   static xbt::signal<void(Activity const&)> on_completion;
 -  static xbt::signal<void(Activity const&)> on_suspended;
 -  static xbt::signal<void(Activity const&)> on_resumed;
 +  static xbt::signal<void(Activity const&)> on_suspend;
 +  static xbt::signal<void(Activity const&)> on_resume;
  
  public:
    /*! Add a callback fired each time that the activity fails to start because of a veto (e.g., unsolved dependency or no
     * resource assigned) */
    static void on_veto_cb(const std::function<void(Activity&)>& cb) { on_veto.connect(cb); }
-   /*! Add a callback fired when the activity completes (either normally, cancelled or failed) */
-   static void on_completion_cb(const std::function<void(Activity const&)>& cb) { on_completion.connect(cb); }
    /*! Add a callback fired when the activity is suspended */
 -  static void on_suspended_cb(const std::function<void(Activity const&)>& cb) { on_suspended.connect(cb); }
 +  static void on_suspend_cb(const std::function<void(Activity const&)>& cb)
 +  {
 +    on_suspend.connect(cb);
 +  }
    /*! Add a callback fired when the activity is resumed after being suspended */
 -  static void on_resumed_cb(const std::function<void(Activity const&)>& cb) { on_resumed.connect(cb); }
 +  static void on_resume_cb(const std::function<void(Activity const&)>& cb)
 +  {
 +    on_resume.connect(cb);
 +  }
 +
 +  XBT_ATTRIB_DEPRECATED_v334("Please use on_suspend_cb() instead") static void on_suspended_cb(
 +      const std::function<void(Activity const&)>& cb)
 +  {
 +    on_suspend.connect(cb);
 +  }
 +  XBT_ATTRIB_DEPRECATED_v334("Please use on_resume_cb() instead") static void on_resumed_cb(
 +      const std::function<void(Activity const&)>& cb)
 +  {
 +    on_resume.connect(cb);
 +  }
  
    XBT_ATTRIB_DEPRECATED_v334("All start() are vetoable now. Please use start() ") void vetoable_start()
    {
      // released by the on_completion() callbacks.
      ActivityPtr keepalive(this);
      state_ = state;
-     on_completion(*this);
+     fire_this_completion();
      if (state == State::FINISHED)
        release_dependencies();
    }
@@@ -258,6 -239,10 +256,10 @@@ template <class AnyActivity> class Acti
    std::string tracing_category_ = "";
  
  public:
+   inline static xbt::signal<void(AnyActivity const&)> on_completion;
+   /*! Add a callback fired when the activity completes (either normally, cancelled or failed) */
+   static void on_completion_cb(const std::function<void(AnyActivity const&)>& cb) { on_completion.connect(cb); }
    AnyActivity* add_successor(ActivityPtr a)
    {
      Activity::add_successor(a);
  
    AnyActivity* set_tracing_category(const std::string& category)
    {
-     xbt_assert(get_state() == State::INITED, "Cannot change the tracing category of an activity after its start");
+     xbt_assert(get_state() == State::INITED || get_state() == State::STARTING,
+                "Cannot change the tracing category of an activity after its start");
      tracing_category_ = category;
      return static_cast<AnyActivity*>(this);
    }
  
    AnyActivity* cancel() { return static_cast<AnyActivity*>(Activity::cancel()); }
    AnyActivity* wait() { return wait_for(-1.0); }
-   virtual AnyActivity* wait_for(double timeout) { return static_cast<AnyActivity*>(Activity::wait_for(timeout)); }
+   virtual AnyActivity* wait_for(double timeout) {
+     return static_cast<AnyActivity*>(Activity::wait_for(timeout));
+   }
  
  #ifndef DOXYGEN
    /* The refcounting is done in the ancestor class, Activity, but we want each of the classes benefiting of the CRTP
@@@ -14,7 -14,6 +14,7 @@@
  #include <xbt/graph.h>
  
  #include "src/instr/instr_private.hpp"
 +#include "src/kernel/activity/ExecImpl.hpp"
  #include "src/kernel/resource/CpuImpl.hpp"
  #include "src/kernel/resource/NetworkModel.hpp"
  
@@@ -348,6 -347,15 +348,15 @@@ static void on_host_creation(s4u::Host 
      root->get_type()->by_name_or_create("MIGRATE_LINK", mpi, mpi);
      mpi->by_name_or_create<StateType>("MIGRATE_STATE");
    }
+    if (TRACE_actor_is_enabled()) {
+     auto* host_type = container->get_type();
+     auto* state     = host_type->by_name_or_create<StateType>("HOST_STATE");
+     state->set_calling_container(container);
+     state->add_entity_value("receive", "1 0 0");
+     state->add_entity_value("send", "0 0 1");
+     state->add_entity_value("execute", "0 1 1");
+   }
  }
  
  static void on_action_state_change(kernel::resource::Action const& action,
        resource_set_utilization("HOST", "speed_used", cpu->get_cname(), action.get_category(), value,
                                 action.get_last_update(), simgrid_get_clock() - action.get_last_update());
  
 -    if (const auto* link = dynamic_cast<kernel::resource::StandardLinkImpl*>(resource))
 +    else if (const auto* link = dynamic_cast<kernel::resource::StandardLinkImpl*>(resource))
        resource_set_utilization("LINK", "bandwidth_used", link->get_cname(), action.get_category(), value,
                                 action.get_last_update(), simgrid_get_clock() - action.get_last_update());
    }
  }
  
 +static void on_activity_suspend_resume(s4u::Activity const& activity)
 +{
 +  on_action_state_change(*activity.get_impl()->model_action_, /*ignored*/ kernel::resource::Action::State::STARTED);
 +}
 +
  static void on_platform_created()
  {
    currentContainer.clear();
@@@ -468,10 -471,8 +477,10 @@@ void define_callbacks(
  
    s4u::NetZone::on_creation_cb(on_netzone_creation);
  
 -  kernel::resource::CpuAction::on_state_change.connect(on_action_state_change);
 +  s4u::Host::on_exec_state_change_cb(on_action_state_change);
    s4u::Link::on_communication_state_change_cb(on_action_state_change);
 +  s4u::Activity::on_suspend_cb(on_activity_suspend_resume);
 +  s4u::Activity::on_resume_cb(on_activity_suspend_resume);
  
    if (TRACE_actor_is_enabled()) {
      s4u::Actor::on_creation_cb(on_actor_creation);
      });
      s4u::Actor::on_wake_up_cb(
          [](s4u::Actor const& actor) { Container::by_name(instr_pid(actor))->get_state("ACTOR_STATE")->pop_event(); });
-     s4u::Exec::on_start_cb([](s4u::Exec const&) {
-       Container::by_name(instr_pid(*s4u::Actor::self()))->get_state("ACTOR_STATE")->push_event("execute");
+     s4u::Exec::on_start_cb([](s4u::Exec const& e) {
+       std::string pid = instr_pid(*s4u::Actor::self());
+       if (pid == "-0") //Exec is launched directly by Maestro, use the host as container
+         Container::by_name(e.get_host()->get_name())->get_state("HOST_STATE")->push_event("execute");
+       else
+         Container::by_name(pid)->get_state("ACTOR_STATE")->push_event("execute");
      });
-     s4u::Activity::on_completion_cb([](const s4u::Activity&) {
-       Container::by_name(instr_pid(*s4u::Actor::self()))->get_state("ACTOR_STATE")->pop_event();
+     s4u::Exec::on_completion_cb([](const s4u::Exec& e) {
+       std::string pid = instr_pid(*s4u::Actor::self());
+       if (pid == "-0") //Exec is launched directly by Maestro, use the host as container
+         Container::by_name(e.get_host()->get_name())->get_state("HOST_STATE")->pop_event();
+       else
+         Container::by_name(pid)->get_state("ACTOR_STATE")->pop_event();
+     });
+     s4u::Comm::on_completion_cb([](const s4u::Comm& c) {
+       std::string pid = instr_pid(*s4u::Actor::self());
+       if (pid == "-0") { //Comm is launched directly by Maestro, use the host as container
+           Container::by_name(c.get_source()->get_name())->get_state("HOST_STATE")->pop_event();
+           Container::by_name(c.get_destination()->get_name())->get_state("HOST_STATE")->pop_event();
+       } else
+         Container::by_name(pid)->get_state("ACTOR_STATE")->pop_event();
      });
-     s4u::Comm::on_send_cb([](s4u::Comm const&) {
-       Container::by_name(instr_pid(*s4u::Actor::self()))->get_state("ACTOR_STATE")->push_event("send");
+     s4u::Comm::on_send_cb([](s4u::Comm const& c) {
+       std::string pid = instr_pid(*s4u::Actor::self());
+       if (pid == "-0") //Comm is launched directly by Maestro, use the host as container
+         Container::by_name(c.get_source()->get_name())->get_state("HOST_STATE")->push_event("send");
+       else
+         Container::by_name(pid)->get_state("ACTOR_STATE")->push_event("send");
      });
-     s4u::Comm::on_recv_cb([](s4u::Comm const&) {
-       Container::by_name(instr_pid(*s4u::Actor::self()))->get_state("ACTOR_STATE")->push_event("receive");
+     s4u::Comm::on_recv_cb([](s4u::Comm const& c) {
+       std::string pid = instr_pid(*s4u::Actor::self());
+       if (pid == "-0") //Comm is launched directly by Maestro, use the host as container
+         Container::by_name(c.get_destination()->get_name())->get_state("HOST_STATE")->push_event("receive");
+       else
+         Container::by_name(pid)->get_state("ACTOR_STATE")->push_event("receive");
      });
      s4u::Actor::on_host_change_cb(on_actor_host_change);
    }
            ->get_state("MPI_STATE")
            ->push_event("computing", new CpuTIData("compute", exec.get_cost()));
      });
-     s4u::Activity::on_completion_cb([](const s4u::Activity&) {
+     s4u::Exec::on_completion_cb([](const s4u::Exec&) {
        Container::by_name("rank-" + std::to_string(s4u::Actor::self()->get_pid()))->get_state("MPI_STATE")->pop_event();
      });
    }
@@@ -79,17 -79,14 +79,14 @@@ static void add_active_exec(s4u::Exec c
    }
  }
  
- static void remove_active_exec(s4u::Activity const& task)
+ static void remove_active_exec(s4u::Exec const& exec)
  {
-   const auto* exec = dynamic_cast<s4u::Exec const*>(&task);
-   if (exec == nullptr)
+   if (not exec.is_assigned())
      return;
-   if (not exec->is_assigned())
-     return;
-   const s4u::VirtualMachine* vm = dynamic_cast<s4u::VirtualMachine*>(exec->get_host());
+   const s4u::VirtualMachine* vm = dynamic_cast<s4u::VirtualMachine*>(exec.get_host());
    if (vm != nullptr) {
      VirtualMachineImpl* vm_impl = vm->get_vm_impl();
-     for (int i = 1; i <= exec->get_thread_count(); i++)
+     for (int i = 1; i <= exec.get_thread_count(); i++)
        vm_impl->remove_active_exec();
      vm_impl->update_action_weight();
    }
@@@ -125,9 -122,9 +122,9 @@@ VMModel::VMModel(const std::string& nam
  {
    s4u::Host::on_state_change_cb(host_state_change);
    s4u::Exec::on_start_cb(add_active_exec);
-   s4u::Activity::on_completion_cb(remove_active_exec);
+   s4u::Exec::on_completion_cb(remove_active_exec);
 -  s4u::Activity::on_resumed_cb(add_active_activity);
 -  s4u::Activity::on_suspended_cb(remove_active_activity);
 +  s4u::Activity::on_resume_cb(add_active_activity);
 +  s4u::Activity::on_suspend_cb(remove_active_activity);
  }
  
  double VMModel::next_occurring_event(double now)
diff --combined src/s4u/s4u_Activity.cpp
@@@ -25,9 -25,8 +25,8 @@@ template class xbt::Extendable<s4u::Act
  namespace s4u {
  
  xbt::signal<void(Activity&)> Activity::on_veto;
- xbt::signal<void(Activity const&)> Activity::on_completion;
 -xbt::signal<void(Activity const&)> Activity::on_suspended;
 -xbt::signal<void(Activity const&)> Activity::on_resumed;
 +xbt::signal<void(Activity const&)> Activity::on_suspend;
 +xbt::signal<void(Activity const&)> Activity::on_resume;
  
  std::set<Activity*>* Activity::vetoed_activities_ = nullptr;