Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
Merge branch 'local changes'
authorMartin Quinson <martin.quinson@ens-rennes.fr>
Wed, 10 Feb 2021 21:45:23 +0000 (22:45 +0100)
committerMartin Quinson <martin.quinson@ens-rennes.fr>
Wed, 10 Feb 2021 21:45:23 +0000 (22:45 +0100)
24 files changed:
examples/c/CMakeLists.txt
examples/cpp/CMakeLists.txt
examples/python/CMakeLists.txt
examples/smpi/CMakeLists.txt
examples/smpi/smpi_s4u_masterworker/CMakeLists.txt
include/simgrid/s4u/Activity.hpp
include/simgrid/s4u/Exec.hpp
src/kernel/activity/ExecImpl.cpp
src/kernel/activity/ExecImpl.hpp
src/mc/api.cpp
src/mc/api.hpp
src/mc/checker/simgrid_mc.cpp
src/mc/mc_config.cpp
src/mc/mc_config.hpp
src/s4u/s4u_Comm.cpp
src/s4u/s4u_Exec.cpp
src/smpi/mpi/smpi_request.cpp
teshsuite/kernel/CMakeLists.txt
teshsuite/python/CMakeLists.txt
teshsuite/s4u/CMakeLists.txt
teshsuite/smpi/CMakeLists.txt
teshsuite/smpi/gh-139/gh-139.c
tools/cmake/Tests.cmake
tools/tesh/tesh.py

index cb98a17..5c833ff 100644 (file)
@@ -112,12 +112,12 @@ foreach(x
                   ${CMAKE_HOME_DIRECTORY}/examples/c/${x}/${x}.tesh)
 endforeach()
 
-ADD_TESH_FACTORIES(app-masterworker-multicore   "thread;ucontext;raw;boost" 
+ADD_TESH_FACTORIES(app-masterworker-multicore   "*"
                                                 --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/c/app-masterworker
                                                 --setenv bindir=${CMAKE_BINARY_DIR}/examples/c/app-masterworker
                                                 --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms
                                                ${CMAKE_HOME_DIRECTORY}/examples/c/app-masterworker/app-masterworker-multicore.tesh)
-ADD_TESH_FACTORIES(app-masterworker-vivaldi     "thread;ucontext;raw;boost" 
+ADD_TESH_FACTORIES(app-masterworker-vivaldi     "*"
                                                 --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/c/app-masterworker
                                                 --setenv bindir=${CMAKE_BINARY_DIR}/examples/c/app-masterworker
                                                 --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms
@@ -126,9 +126,9 @@ ADD_TESH_FACTORIES(app-masterworker-vivaldi     "thread;ucontext;raw;boost"
 if(CMAKE_SYSTEM_NAME STREQUAL "SunOS" AND CMAKE_SYSTEM_PROCESSOR STREQUAL "i386" AND CMAKE_SIZEOF_VOID_P EQUAL 8)
     # Thread-local storage (TLS) is needed for parallel execution, but it doesn't
     # play well with Ucontexts on 64bit SunOS (at least on x86_64).
-    set(parallel-factories "thread;raw;boost")
+    set(parallel-factories "^ucontext")
 else()
-    set(parallel-factories "thread;ucontext;raw;boost")
+    set(parallel-factories "*")
 endif()
 
 ADD_TESH_FACTORIES(c-app-bittorrent-parallel "raw" --cfg contexts/nthreads:4 ${CONTEXTS_SYNCHRO} 
index fc3d688..393f3f8 100644 (file)
@@ -12,7 +12,7 @@ set(_dht-kademlia_sources dht-kademlia/s4u-dht-kademlia.cpp dht-kademlia/s4u-dht
                           dht-kademlia/routing_table.cpp dht-kademlia/routing_table.hpp
                           dht-kademlia/answer.cpp dht-kademlia/answer.hpp dht-kademlia/message.hpp)
 
-set(_actor-stacksize_factories "raw;boost;ucontext") # Threads ignore modifications of the stack size
+set(_actor-stacksize_factories "^thread") # Threads ignore modifications of the stack size
 
 # The maestro-set example only works for threads and when not using windows.
 set(_maestro-set_factories "thread")
@@ -24,7 +24,7 @@ foreach (example mc-bugged1 mc-bugged2 mc-failing-assert mc-electric-fence)
   if(NOT SIMGRID_HAVE_MC)
     set(_${example}_disable 1)
   endif()
-  set(_${example}_factories "ucontext;raw;boost")
+  set(_${example}_factories "^thread")
 endforeach()
 
 if(SIMGRID_HAVE_MC)
@@ -92,7 +92,7 @@ foreach (example actor-create actor-daemon actor-exiting actor-join actor-kill
 
     # Use default factories unless specified otherwise
     if(NOT DEFINED _${example}_factories)
-      set(_${example}_factories "thread;ucontext;raw;boost")
+      set(_${example}_factories "*")
     endif()
 #    message("Factories of ${example}: ${_${example}_factories}")
 
@@ -161,9 +161,9 @@ ENDIF()
 if(CMAKE_SYSTEM_NAME STREQUAL "SunOS" AND CMAKE_SYSTEM_PROCESSOR STREQUAL "i386" AND CMAKE_SIZEOF_VOID_P EQUAL 8)
   # Thread-local storage (TLS) is needed for parallel execution, but it doesn't
   # play well with Ucontexts on 64bit SunOS (at least on x86_64).
-  set(parallel-factories "thread;raw;boost")
+  set(parallel-factories "^ucontext")
 else()
-  set(parallel-factories "thread;ucontext;raw;boost")
+  set(parallel-factories "*")
 endif()
 
 foreach(example app-bittorrent app-masterworkers 
@@ -178,12 +178,12 @@ endforeach()
 
 # ns3-tests
 if(SIMGRID_HAVE_NS3)
-  ADD_TESH_FACTORIES(s4u-network-ns3 "thread;ucontext;raw;boost"
+  ADD_TESH_FACTORIES(s4u-network-ns3 "*"
                                      --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/cpp
                                      --setenv bindir=${CMAKE_BINARY_DIR}/examples/cpp
                                      --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms
                                      ${CMAKE_HOME_DIRECTORY}/examples/cpp/network-ns3/s4u-network-ns3.tesh)
-  ADD_TESH_FACTORIES(s4u-network-ns3-wifi "thread;ucontext;raw;boost"
+  ADD_TESH_FACTORIES(s4u-network-ns3-wifi "*"
                                      --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/cpp
                                      --setenv bindir=${CMAKE_BINARY_DIR}/examples/cpp
                                      --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms
index fa32133..c7b515c 100644 (file)
@@ -5,7 +5,7 @@ foreach(example actor-create actor-daemon actor-join actor-kill actor-migrate ac
   set(examples_src  ${examples_src} ${CMAKE_CURRENT_SOURCE_DIR}/${example}/${example}.py)
 
   if(enable_python)
-    ADD_TESH_FACTORIES(python-${example} "thread;ucontext;raw;boost"
+    ADD_TESH_FACTORIES(python-${example} "*"
                                --setenv srcdir=${CMAKE_CURRENT_SOURCE_DIR}/${example}
                                --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms
                                --setenv pythoncmd=${PYTHON_EXECUTABLE}
index b72db9a..0e8feaa 100644 (file)
@@ -75,7 +75,7 @@ if(enable_smpi)
   # MC is currently broken with threads (deadlock => timeout)
   if(SIMGRID_HAVE_MC)
     ADD_TESH(smpi-mc-only-send-determinism --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/smpi/mc --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --cd ${CMAKE_BINARY_DIR}/examples/smpi/mc ${CMAKE_HOME_DIRECTORY}/examples/smpi/mc/only_send_deterministic.tesh)
-    ADD_TESH_FACTORIES(smpi-mc-sendsend "ucontext;raw;boost" --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/smpi/mc --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --cd ${CMAKE_BINARY_DIR}/examples/smpi/mc ${CMAKE_HOME_DIRECTORY}/examples/smpi/mc/sendsend.tesh)
+    ADD_TESH_FACTORIES(smpi-mc-sendsend "^thread" --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/smpi/mc --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --cd ${CMAKE_BINARY_DIR}/examples/smpi/mc ${CMAKE_HOME_DIRECTORY}/examples/smpi/mc/sendsend.tesh)
   endif()
 
   ADD_TESH(smpi-tracing        --setenv bindir=${CMAKE_BINARY_DIR}/examples/smpi/trace --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/smpi/trace --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --cd ${CMAKE_BINARY_DIR}/examples/smpi/trace ${CMAKE_HOME_DIRECTORY}/examples/smpi/trace/trace.tesh)
@@ -84,7 +84,7 @@ if(enable_smpi)
   ADD_TESH(smpi-replay         --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/smpi --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --cd ${CMAKE_BINARY_DIR}/examples/smpi ${CMAKE_HOME_DIRECTORY}/examples/smpi/replay/replay.tesh)
   ADD_TESH(smpi-replay-override-replayer --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/smpi --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --cd ${CMAKE_BINARY_DIR}/examples/smpi ${CMAKE_HOME_DIRECTORY}/examples/smpi/replay/replay-override-replayer.tesh)
   ADD_TESH(smpi-gemm        --setenv bindir=${CMAKE_BINARY_DIR}/examples/smpi/gemm --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/smpi/gemm --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --cd ${CMAKE_BINARY_DIR}/examples/smpi/gemm ${CMAKE_HOME_DIRECTORY}/examples/smpi/gemm/gemm.tesh)
-  ADD_TESH_FACTORIES(smpi-energy "thread;ucontext;raw;boost" --setenv bindir=${CMAKE_BINARY_DIR}/examples/smpi/energy --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/smpi/energy --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv bindir=${CMAKE_BINARY_DIR}/bin --cd ${CMAKE_BINARY_DIR}/examples/smpi/energy ${CMAKE_HOME_DIRECTORY}/examples/smpi/energy/energy.tesh)
+  ADD_TESH_FACTORIES(smpi-energy "*" --setenv bindir=${CMAKE_BINARY_DIR}/examples/smpi/energy --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/smpi/energy --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv bindir=${CMAKE_BINARY_DIR}/bin --cd ${CMAKE_BINARY_DIR}/examples/smpi/energy ${CMAKE_HOME_DIRECTORY}/examples/smpi/energy/energy.tesh)
 
   ADD_TESH(smpi-ampi --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/smpi --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --cd ${CMAKE_BINARY_DIR}/examples/smpi ${CMAKE_HOME_DIRECTORY}/examples/smpi/ampi_test/ampi_test.tesh)
 endif()
index 5ffc2c3..87e5dff 100644 (file)
@@ -3,7 +3,7 @@ if(enable_smpi)
 
   add_executable       (masterworker_mailbox_smpi EXCLUDE_FROM_ALL masterworker_mailbox_smpi.cpp)
   target_link_libraries(masterworker_mailbox_smpi simgrid)
-  ADD_TESH_FACTORIES(smpi-s4u-masterworker "thread;ucontext;raw;boost" --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/smpi/smpi_s4u_masterworker --cd ${CMAKE_BINARY_DIR}/examples/smpi/smpi_s4u_masterworker ${CMAKE_HOME_DIRECTORY}/examples/smpi/smpi_s4u_masterworker/s4u_smpi.tesh)
+  ADD_TESH_FACTORIES(smpi-s4u-masterworker "*" --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/smpi/smpi_s4u_masterworker --cd ${CMAKE_BINARY_DIR}/examples/smpi/smpi_s4u_masterworker ${CMAKE_HOME_DIRECTORY}/examples/smpi/smpi_s4u_masterworker/s4u_smpi.tesh)
   add_dependencies(tests masterworker_mailbox_smpi)
 endif()
 
index ab1e57b..878ddba 100644 (file)
@@ -6,10 +6,12 @@
 #ifndef SIMGRID_S4U_ACTIVITY_HPP
 #define SIMGRID_S4U_ACTIVITY_HPP
 
-#include "xbt/asserts.h"
+#include <xbt/asserts.h>
+#include <algorithm>
 #include <atomic>
 #include <set>
 #include <simgrid/forward.h>
+#include <stdexcept>
 #include <string>
 #include <vector>
 #include <xbt/signal.hpp>
@@ -51,10 +53,30 @@ protected:
 
   void add_successor(ActivityPtr a)
   {
+    if(this == a)
+      throw std::invalid_argument("Cannot be its own successor");
+    auto p = std::find_if(successors_.begin(), successors_.end(), [a](ActivityPtr const& i){ return i.get() == a.get(); });
+    if (p != successors_.end())
+      throw std::invalid_argument("Dependency already exists");
+
     successors_.push_back(a);
     a->dependencies_.insert({this});
   }
 
+  void remove_successor(ActivityPtr a)
+  {
+    if(this == a)
+      throw std::invalid_argument("Cannot ask to remove its from successors");
+
+    auto p = std::find_if(successors_.begin(), successors_.end(), [a](ActivityPtr const& i){ return i.get() == a.get(); });
+    if (p != successors_.end()){
+      successors_.erase(p);
+      a->dependencies_.erase({this});
+    } else
+      throw std::invalid_argument("Dependency does not exist. Can not be removed.");
+
+  }
+
 public:
   void vetoable_start()
   {
@@ -155,7 +177,11 @@ public:
     Activity::add_successor(a);
     return static_cast<AnyActivity*>(this);
   }
-
+  AnyActivity* remove_successor(ActivityPtr a)
+  {
+    Activity::remove_successor(a);
+    return static_cast<AnyActivity*>(this);
+  }
   AnyActivity* set_name(const std::string& name)
   {
     xbt_assert(get_state() == State::INITED, "Cannot change the name of an activity after its start");
index 6cb7870..72d0e2e 100644 (file)
@@ -30,6 +30,7 @@ namespace s4u {
  * @endrst
  */
 class XBT_PUBLIC Exec : public Activity_T<Exec> {
+  friend kernel::activity::ExecImpl;
   double priority_              = 1.0;
   double bound_                 = 0.0;
   double timeout_               = 0.0;
@@ -37,7 +38,11 @@ class XBT_PUBLIC Exec : public Activity_T<Exec> {
   std::vector<double> bytes_amounts_;
   std::vector<Host*> hosts_;
   bool parallel_ = false;
-  Exec();
+  double start_time_ = -1.0;
+  double finish_time_ = -1.0;
+
+protected:
+  explicit Exec(kernel::activity::ExecImplPtr pimpl);
 
 public:
   ~Exec() override = default;
@@ -77,8 +82,9 @@ public:
   Exec* cancel() override;
   Host* get_host() const;
   unsigned int get_host_number() const;
-  double get_start_time() const;
-  double get_finish_time() const;
+  double get_start_time() const { return start_time_; }
+  double get_finish_time() const { return finish_time_; }
+  void set_finish_time(double finish_time) { finish_time_ = finish_time; }
   double get_cost() const;
   bool is_parallel() const { return parallel_; }
   bool is_assigned() const override { return not hosts_.empty(); }
index 3e27a03..382ed6e 100644 (file)
@@ -3,6 +3,7 @@
 /* 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/s4u/Exec.hpp"
 #include "src/kernel/activity/ExecImpl.hpp"
 #include "simgrid/Exception.hpp"
 #include "simgrid/modelchecker.h"
@@ -57,6 +58,7 @@ namespace activity {
 
 ExecImpl::ExecImpl()
 {
+  piface_ = new s4u::Exec(this);
   actor::ActorImpl* self = actor::ActorImpl::self();
   if (self) {
     actor_ = self;
@@ -150,11 +152,12 @@ ExecImpl& ExecImpl::set_sharing_penalty(double sharing_penalty)
 
 void ExecImpl::post()
 {
+  xbt_assert(surf_action_ != nullptr);
   if (hosts_.size() == 1 && not hosts_.front()->is_on()) { /* FIXME: handle resource failure for parallel tasks too */
     /* If the host running the synchro failed, notice it. This way, the asking
      * process can be killed if it runs on that host itself */
     state_ = State::FAILED;
-  } else if (surf_action_ && surf_action_->get_state() == resource::Action::State::FAILED) {
+  } else if (surf_action_->get_state() == resource::Action::State::FAILED) {
     /* If the host running the synchro didn't fail, then the synchro was canceled */
     state_ = State::CANCELED;
   } else if (timeout_detector_ && timeout_detector_->get_state() == resource::Action::State::FINISHED) {
@@ -163,6 +166,8 @@ void ExecImpl::post()
     state_ = State::DONE;
   }
 
+  get_iface()->set_finish_time(surf_action_->get_finish_time());
+
   clean_action();
   timeout_detector_.reset();
   if (actor_) {
@@ -208,7 +213,6 @@ void ExecImpl::finish()
         simcall_execution_waitany_for__set__result(simcall, rank);
       }
     }
-
     switch (state_) {
       case State::DONE:
         /* do nothing, synchro done */
index 0f92c84..3782b7a 100644 (file)
@@ -6,6 +6,7 @@
 #ifndef SIMGRID_KERNEL_ACTIVITY_EXEC_HPP
 #define SIMGRID_KERNEL_ACTIVITY_EXEC_HPP
 
+#include "simgrid/s4u/Exec.hpp"
 #include "src/kernel/activity/ActivityImpl.hpp"
 #include "src/kernel/context/Context.hpp"
 #include "surf/surf.hpp"
@@ -23,9 +24,10 @@ class XBT_PUBLIC ExecImpl : public ActivityImpl_T<ExecImpl> {
   std::vector<s4u::Host*> hosts_;
   std::vector<double> flops_amounts_;
   std::vector<double> bytes_amounts_;
-
+  s4u::Exec* piface_;
 public:
   ExecImpl();
+  s4u::Exec* get_iface() { return piface_; }
 
   ExecImpl& set_timeout(double timeout) override;
   ExecImpl& set_bound(double bound);
index 684b9c9..8e4d30d 100644 (file)
@@ -18,7 +18,7 @@
 #include "src/smpi/include/smpi_request.hpp"
 #endif
 
-XBT_LOG_NEW_DEFAULT_SUBCATEGORY(Api, mc, "Logging specific to MC Fasade APIs ");
+XBT_LOG_NEW_DEFAULT_SUBCATEGORY(Api, mc, "Logging specific to MC Facade APIs ");
 
 using Simcall = simgrid::simix::Simcall;
 
@@ -631,9 +631,9 @@ smx_simcall_t Api::mc_state_choose_request(simgrid::mc::State* state) const
   return nullptr;
 }
 
-std::list<udpor_transition_t> Api::get_enabled_transitions(simgrid::mc::State* state)
+std::list<transition_detail_t> Api::get_enabled_transitions(simgrid::mc::State* state)
 {
-  std::list<udpor_transition_t> tr_list{};
+  std::list<transition_detail_t> tr_list{};
 
   for (auto& actor : mc_model_checker->get_remote_simulation().actors()) {
     auto actor_pid  = actor.copy.get_buffer()->get_pid();
@@ -646,22 +646,22 @@ std::list<udpor_transition_t> Api::get_enabled_transitions(simgrid::mc::State* s
     if (not simgrid::mc::actor_is_enabled(actor_impl))
       continue;
 
-    udpor_transition_t udpor_transition = std::unique_ptr<s_udpor_transition>(new s_udpor_transition());
+    transition_detail_t transition = std::unique_ptr<s_transition_detail>(new s_transition_detail());
     Simcall simcall_call                = actor_impl->simcall_.call_;
     smx_simcall_t simcall               = &actor_impl->simcall_;
-    udpor_transition->call_             = simcall_call;
+    transition->call_             = simcall_call;
     switch (simcall_call) {
       case Simcall::COMM_ISEND:
       case Simcall::COMM_IRECV: {
-        udpor_transition->mbox_remote_addr = get_mbox_remote_addr(simcall);
-        udpor_transition->comm_remote_addr = get_comm_remote_addr(simcall);
+        transition->mbox_remote_addr = get_mbox_remote_addr(simcall);
+        transition->comm_remote_addr = get_comm_remote_addr(simcall);
         break;
       }
 
       default:
         break;
     }
-    tr_list.emplace_back(std::move(udpor_transition));
+    tr_list.emplace_back(std::move(transition));
   }
   
   return tr_list;
index 3a92bc1..191a213 100644 (file)
@@ -18,14 +18,14 @@ namespace mc {
 /**
  * @brief Maintains the transition's information.
  */
-struct s_udpor_transition {
+struct s_transition_detail {
   simgrid::simix::Simcall call_ = simgrid::simix::Simcall::NONE;
   long issuer_id                = -1;
   RemotePtr<kernel::activity::MailboxImpl> mbox_remote_addr {}; // used to represent mailbox remote address for isend and ireceive transitions
   RemotePtr<kernel::activity::ActivityImpl> comm_remote_addr {}; // the communication this transition concerns (to be used only for isend, ireceive, wait and test)
 };
 
-typedef std::unique_ptr<s_udpor_transition> udpor_transition_t;
+typedef std::unique_ptr<s_transition_detail> transition_detail_t;
 
 /*
 ** This class aimes to implement FACADE APIs for simgrid. The FACADE layer sits between the CheckerSide
@@ -108,7 +108,7 @@ public:
   smx_simcall_t mc_state_choose_request(simgrid::mc::State* state) const;
 
   // UDPOR APIs
-  std::list<udpor_transition_t> get_enabled_transitions(simgrid::mc::State* state);
+  std::list<transition_detail_t> get_enabled_transitions(simgrid::mc::State* state);
 
   // SIMCALL APIs
   std::string request_to_string(smx_simcall_t req, int value, RequestType request_type) const;
index 015fb3d..455290e 100644 (file)
@@ -33,6 +33,8 @@ static std::unique_ptr<simgrid::mc::Checker> create_checker()
 {
   if (_sg_mc_comms_determinism || _sg_mc_send_determinism)
     return std::unique_ptr<simgrid::mc::Checker>(simgrid::mc::createCommunicationDeterminismChecker());
+  else if (_sg_mc_unfolding_checker)
+    return std::unique_ptr<simgrid::mc::Checker>(simgrid::mc::createUdporChecker());
   else if (_sg_mc_property_file.get().empty())
     return std::unique_ptr<simgrid::mc::Checker>(simgrid::mc::createSafetyChecker());
   else
index cfe3511..39c3491 100644 (file)
@@ -72,6 +72,13 @@ simgrid::config::Flag<bool> _sg_mc_send_determinism{
       _mc_cfg_cb_check("value to enable/disable the detection of send-determinism in the communications schemes");
     }};
 
+simgrid::config::Flag<bool> _sg_mc_unfolding_checker{
+    "model-check/unfolding-checker", "Whether to enable the unfolding-based dynamic partial order reduction to MPI programs",     
+    false,
+    [](bool) {
+      _mc_cfg_cb_check("value to to enable/disable the unfolding-based dynamic partial order reduction to MPI programs");
+    }};
+
 simgrid::config::Flag<std::string> _sg_mc_buffering{
     "smpi/buffering",
     "Buffering semantic to use for MPI (only used in MC)",
index f249c75..467a2b7 100644 (file)
@@ -15,6 +15,7 @@ extern XBT_PRIVATE simgrid::config::Flag<int> _sg_mc_checkpoint;
 extern XBT_PUBLIC simgrid::config::Flag<std::string> _sg_mc_property_file;
 extern XBT_PUBLIC simgrid::config::Flag<bool> _sg_mc_comms_determinism;
 extern XBT_PUBLIC simgrid::config::Flag<bool> _sg_mc_send_determinism;
+extern XBT_PUBLIC simgrid::config::Flag<bool> _sg_mc_unfolding_checker;
 extern XBT_PRIVATE simgrid::config::Flag<bool> _sg_mc_timeout;
 extern XBT_PRIVATE simgrid::config::Flag<int> _sg_mc_max_depth;
 extern "C" XBT_PUBLIC int _sg_mc_max_visited_states;
index 26fffb7..066f4f4 100644 (file)
@@ -38,8 +38,10 @@ int Comm::wait_any_for(const std::vector<CommPtr>* comms, double timeout)
   std::transform(begin(*comms), end(*comms), begin(rcomms),
                  [](const CommPtr& comm) { return static_cast<kernel::activity::CommImpl*>(comm->pimpl_.get()); });
   int changed_pos = simcall_comm_waitany(rcomms.data(), rcomms.size(), timeout);
-  if (changed_pos != -1)
+  if (changed_pos != -1) {
+    on_completion(*(comms->at(changed_pos)));
     comms->at(changed_pos)->release_dependencies();
+  }
   return changed_pos;
 }
 
index bc50765..09a5275 100644 (file)
@@ -17,14 +17,15 @@ namespace s4u {
 xbt::signal<void(Exec const&)> Exec::on_start;
 xbt::signal<void(Exec const&)> Exec::on_completion;
 
-Exec::Exec()
+Exec::Exec(kernel::activity::ExecImplPtr pimpl)
 {
-  pimpl_ = kernel::activity::ExecImplPtr(new kernel::activity::ExecImpl());
+  pimpl_ = pimpl;
 }
 
 ExecPtr Exec::init()
 {
-  return ExecPtr(new Exec());
+  auto pimpl = kernel::activity::ExecImplPtr(new kernel::activity::ExecImpl());
+  return ExecPtr(pimpl->get_iface());
 }
 
 Exec* Exec::wait()
@@ -52,8 +53,10 @@ int Exec::wait_any_for(std::vector<ExecPtr>* execs, double timeout)
                  [](const ExecPtr& exec) { return static_cast<kernel::activity::ExecImpl*>(exec->pimpl_.get()); });
 
   int changed_pos = simcall_execution_waitany_for(rexecs.data(), rexecs.size(), timeout);
-  if (changed_pos != -1)
+  if (changed_pos != -1) {
+    on_completion(*(execs->at(changed_pos)));
     execs->at(changed_pos)->release_dependencies();
+  }
   return changed_pos;
 }
 
@@ -70,20 +73,23 @@ Exec* Exec::cancel()
  */
 ExecPtr Exec::set_bound(double bound)
 {
-  xbt_assert(state_ == State::INITED, "Cannot change the bound of an exec after its start");
+  xbt_assert(state_ == State::INITED || state_ == State::STARTING,
+      "Cannot change the bound of an exec after its start");
   bound_ = bound;
   return this;
 }
 ExecPtr Exec::set_timeout(double timeout) // XBT_ATTRIB_DEPRECATED_v329
 {
-  xbt_assert(state_ == State::INITED, "Cannot change the bound of an exec after its start");
+  xbt_assert(state_ == State::INITED|| state_ == State::STARTING,
+      "Cannot change the bound of an exec after its start");
   timeout_ = timeout;
   return this;
 }
 
 ExecPtr Exec::set_flops_amount(double flops_amount)
 {
-  xbt_assert(state_ == State::INITED, "Cannot change the flop_amount of an exec after its start");
+  xbt_assert(state_ == State::INITED || state_ == State::STARTING,
+      "Cannot change the flop_amount of an exec after its start");
   flops_amounts_.assign(1, flops_amount);
   Activity::set_remaining(flops_amounts_.front());
   return this;
@@ -91,7 +97,8 @@ ExecPtr Exec::set_flops_amount(double flops_amount)
 
 ExecPtr Exec::set_flops_amounts(const std::vector<double>& flops_amounts)
 {
-  xbt_assert(state_ == State::INITED, "Cannot change the flops_amounts of an exec after its start");
+  xbt_assert(state_ == State::INITED || state_ == State::STARTING,
+      "Cannot change the flops_amounts of an exec after its start");
   flops_amounts_ = flops_amounts;
   parallel_      = true;
   return this;
@@ -99,7 +106,8 @@ ExecPtr Exec::set_flops_amounts(const std::vector<double>& flops_amounts)
 
 ExecPtr Exec::set_bytes_amounts(const std::vector<double>& bytes_amounts)
 {
-  xbt_assert(state_ == State::INITED, "Cannot change the bytes_amounts of an exec after its start");
+  xbt_assert(state_ == State::INITED || state_ == State::STARTING,
+      "Cannot change the bytes_amounts of an exec after its start");
   bytes_amounts_ = bytes_amounts;
   parallel_      = true;
   return this;
@@ -116,14 +124,6 @@ unsigned int Exec::get_host_number() const
 {
   return static_cast<kernel::activity::ExecImpl*>(pimpl_.get())->get_host_number();
 }
-double Exec::get_start_time() const
-{
-  return (pimpl_->surf_action_ == nullptr) ? -1 : pimpl_->surf_action_->get_start_time();
-}
-double Exec::get_finish_time() const
-{
-  return (pimpl_->surf_action_ == nullptr) ? -1 : pimpl_->surf_action_->get_finish_time();
-}
 double Exec::get_cost() const
 {
   return (pimpl_->surf_action_ == nullptr) ? -1 : pimpl_->surf_action_->get_cost();
@@ -205,6 +205,7 @@ Exec* Exec::start()
     pimpl_->suspend();
 
   state_ = State::STARTED;
+  start_time_ = pimpl_->surf_action_->get_start_time();
   on_start(*this);
   return this;
 }
index 2bea2e8..0758c70 100644 (file)
@@ -968,12 +968,11 @@ int Request::wait(MPI_Request * request, MPI_Status * status)
 
 int Request::waitany(int count, MPI_Request requests[], MPI_Status * status)
 {
-  std::vector<simgrid::kernel::activity::CommImpl*> comms;
-  comms.reserve(count);
   int index = MPI_UNDEFINED;
 
   if(count > 0) {
     // Wait for a request to complete
+    std::vector<simgrid::kernel::activity::CommImpl*> comms;
     std::vector<int> map;
     XBT_DEBUG("Wait for one of %d", count);
     for(int i = 0; i < count; i++) {
@@ -985,7 +984,7 @@ int Request::waitany(int count, MPI_Request requests[], MPI_Status * status)
           map.push_back(i);
         } else {
           // This is a finished detached request, let's return this one
-          comms.clear(); // so we free don't do the waitany call
+          comms.clear(); // don't do the waitany call afterwards
           index = i;
           finish_wait(&requests[i], status); // cleanup if refcount = 0
           if (requests[i] != MPI_REQUEST_NULL && (requests[i]->flags_ & MPI_REQ_NON_PERSISTENT))
@@ -996,13 +995,12 @@ int Request::waitany(int count, MPI_Request requests[], MPI_Status * status)
     }
     if (not comms.empty()) {
       XBT_DEBUG("Enter waitany for %zu comms", comms.size());
-      int i=MPI_UNDEFINED;
+      int i;
       try{
-        // this is not a detached send
         i = simcall_comm_waitany(comms.data(), comms.size(), -1);
       } catch (const Exception&) {
-        XBT_INFO("request %d cancelled ", i);
-        return i;
+        XBT_INFO("request cancelled");
+        i = -1;
       }
 
       // not MPI_UNDEFINED, as this is a simix return code
index fbcdafc..b4b7554 100644 (file)
@@ -10,15 +10,15 @@ endforeach()
 ## Add the easy tests: only simcall-generic for now
 foreach(x simcall-generic)
   set(tesh_files    ${tesh_files} ${CMAKE_CURRENT_SOURCE_DIR}/${x}/${x}.tesh)
-  ADD_TESH(tesh-${x} --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/kernel/${x} --setenv srcdir=${CMAKE_HOME_DIRECTORY} --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/kernel/${x} ${x}.tesh)
+  ADD_TESH_FACTORIES(tesh-${x} "*" --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/kernel/${x} --setenv srcdir=${CMAKE_HOME_DIRECTORY} --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/kernel/${x} ${x}.tesh)
 endforeach()
 
 ## Add the tests for stack-overflow
 set(tesh_files    ${tesh_files} ${CMAKE_CURRENT_SOURCE_DIR}/stack-overflow/stack-overflow.tesh)
 if (NOT enable_memcheck AND NOT enable_address_sanitizer AND NOT enable_thread_sanitizer)
-  ADD_TESH_FACTORIES(stack-overflow   "ucontext;raw;boost" --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/kernel/stack-overflow --setenv srcdir=${CMAKE_HOME_DIRECTORY} --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/kernel/stack-overflow stack-overflow.tesh)
+  ADD_TESH_FACTORIES(stack-overflow   "^thread" --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/kernel/stack-overflow --setenv srcdir=${CMAKE_HOME_DIRECTORY} --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/kernel/stack-overflow stack-overflow.tesh)
   if (WIN32)
-    SET_TESH_PROPERTIES(stack-overflow "ucontext;raw;boost" WILL_FAIL true)
+    SET_TESH_PROPERTIES(stack-overflow "^thread" WILL_FAIL true)
   endif()
 endif()
 
index 2375ad5..8d5aeb0 100644 (file)
@@ -4,7 +4,7 @@ foreach(example borken-context corrupt-stack)
   set(examples_src  ${examples_src} ${CMAKE_CURRENT_SOURCE_DIR}/${example}/${example}.py)
 
   if(enable_python)
-    ADD_TESH_FACTORIES(tesh-python-${example} "thread;ucontext;raw;boost"
+    ADD_TESH_FACTORIES(tesh-python-${example} "*"
                                --setenv srcdir=${CMAKE_CURRENT_SOURCE_DIR}/${example}
                                --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms
                                --setenv pythoncmd=${PYTHON_EXECUTABLE}
index 3dbef3b..1b2d59c 100644 (file)
@@ -30,7 +30,7 @@ foreach(x actor actor-autorestart actor-suspend
         cloud-interrupt-migration cloud-two-execs concurrent_rw
        vm-live-migration)
   set(tesh_files    ${tesh_files}    ${CMAKE_CURRENT_SOURCE_DIR}/${x}/${x}.tesh)
-  ADD_TESH_FACTORIES(tesh-s4u-${x} "thread;ucontext;raw;boost" --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/s4u/${x} --setenv srcdir=${CMAKE_HOME_DIRECTORY}/teshsuite/s4u/${x} --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --cd ${CMAKE_BINARY_DIR}/teshsuite/s4u/${x} ${CMAKE_HOME_DIRECTORY}/teshsuite/s4u/${x}/${x}.tesh)
+  ADD_TESH_FACTORIES(tesh-s4u-${x} "*" --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/s4u/${x} --setenv srcdir=${CMAKE_HOME_DIRECTORY}/teshsuite/s4u/${x} --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --cd ${CMAKE_BINARY_DIR}/teshsuite/s4u/${x} ${CMAKE_HOME_DIRECTORY}/teshsuite/s4u/${x}/${x}.tesh)
 endforeach()
 
 foreach(x basic-link-test host-on-off host-on-off-actors host-on-off-recv is-router listen_async pid storage_client_server trace-integration)
index 411911d..912613e 100644 (file)
@@ -61,20 +61,20 @@ set(bin_files       ${bin_files}    ${CMAKE_CURRENT_SOURCE_DIR}/hostfile
 
 if(enable_smpi)
   if(NOT WIN32)
-    ADD_TESH_FACTORIES(tesh-smpi-macro-shared "thread;ucontext;raw;boost" --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/smpi/macro-shared --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/smpi/macro-shared macro-shared.tesh)
-    ADD_TESH_FACTORIES(tesh-smpi-auto-shared "thread;ucontext;raw;boost" --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/smpi/auto-shared --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/smpi/auto-shared auto-shared.tesh)
-    ADD_TESH_FACTORIES(tesh-smpi-macro-partial-shared "thread;ucontext;raw;boost" --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/smpi/macro-partial-shared --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/smpi/macro-partial-shared macro-partial-shared.tesh)
-    ADD_TESH_FACTORIES(tesh-smpi-macro-partial-shared-communication "thread;ucontext;raw;boost" --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/smpi/macro-partial-shared-communication --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/smpi/macro-partial-shared-communication macro-partial-shared-communication.tesh)
+    ADD_TESH_FACTORIES(tesh-smpi-macro-shared "*" --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/smpi/macro-shared --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/smpi/macro-shared macro-shared.tesh)
+    ADD_TESH_FACTORIES(tesh-smpi-auto-shared "*" --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/smpi/auto-shared --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/smpi/auto-shared auto-shared.tesh)
+    ADD_TESH_FACTORIES(tesh-smpi-macro-partial-shared "*" --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/smpi/macro-partial-shared --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/smpi/macro-partial-shared macro-partial-shared.tesh)
+    ADD_TESH_FACTORIES(tesh-smpi-macro-partial-shared-communication "*" --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/smpi/macro-partial-shared-communication --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/smpi/macro-partial-shared-communication macro-partial-shared-communication.tesh)
   endif()
 
   foreach(x coll-allgather coll-allgatherv coll-allreduce coll-alltoall coll-alltoallv coll-barrier coll-bcast
             coll-gather coll-reduce coll-reduce-scatter coll-scatter macro-sample pt2pt-dsend pt2pt-pingpong
            type-hvector type-indexed type-struct type-vector bug-17132 timers io-simple io-simple-at io-all io-all-at io-shared io-ordered topo-cart-sub)
-    ADD_TESH_FACTORIES(tesh-smpi-${x} "thread;ucontext;raw;boost" --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/smpi/${x} --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/smpi/${x} ${x}.tesh)
+    ADD_TESH_FACTORIES(tesh-smpi-${x} "*" --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/smpi/${x} --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/smpi/${x} ${x}.tesh)
   endforeach()
 
   if(SMPI_FORTRAN)
-    ADD_TESH_FACTORIES(tesh-smpi-fort_args "thread;ucontext;raw;boost" --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/smpi/fort_args --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/smpi/fort_args fort_args.tesh)
+    ADD_TESH_FACTORIES(tesh-smpi-fort_args "*" --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv srcdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/smpi/fort_args --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/smpi/fort_args fort_args.tesh)
   endif()
 
   foreach (ALLGATHER 2dmesh 3dmesh bruck GB loosely_lr NTSLR NTSLR_NB pair rdb  rhv ring SMP_NTS smp_simple spreading_simple
@@ -145,7 +145,7 @@ if(enable_smpi)
   # Simple privatization tests
   if(HAVE_PRIVATIZATION)
     foreach(PRIVATIZATION dlopen mmap)
-      ADD_TESH_FACTORIES(tesh-smpi-privatization-${PRIVATIZATION}  "thread;ucontext;raw;boost" --setenv privatization=${PRIVATIZATION} --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/smpi/privatization --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/smpi/privatization privatization.tesh)
+      ADD_TESH_FACTORIES(tesh-smpi-privatization-${PRIVATIZATION}  "*" --setenv privatization=${PRIVATIZATION} --setenv platfdir=${CMAKE_HOME_DIRECTORY}/examples/platforms --setenv bindir=${CMAKE_BINARY_DIR}/teshsuite/smpi/privatization --cd ${CMAKE_HOME_DIRECTORY}/teshsuite/smpi/privatization privatization.tesh)
     endforeach()
   endif()
 endif()
index f1a9c57..e570b8b 100644 (file)
@@ -40,7 +40,7 @@ static void thread_create_wrapper(XBT_ATTRIB_UNUSED int argc, XBT_ATTRIB_UNUSED
 
 static void mpi_thread_create(const char* name, void* (*f)(void*), void* param)
 {
-  struct threadwrap* threadwrap = (struct threadwrap*)malloc(sizeof(*threadwrap));
+  struct threadwrap* threadwrap = xbt_malloc(sizeof(*threadwrap));
   threadwrap->f                 = f;
   threadwrap->param             = param;
   sg_actor_t actor              = sg_actor_init(name, sg_host_self());
@@ -50,7 +50,7 @@ static void mpi_thread_create(const char* name, void* (*f)(void*), void* param)
 
 static void mythread_create(const char* name, MPI_Request* req, int rank)
 {
-  struct param* param = (struct param*)malloc(sizeof(*param));
+  struct param* param = xbt_malloc(sizeof(*param));
   param->req          = req;
   param->rank         = rank;
   mpi_thread_create(name, req_wait, param);
index 3375fcf..c6f7138 100644 (file)
@@ -50,25 +50,53 @@ MACRO(ADD_TESH NAME)
   endif()
 ENDMACRO()
 
+# Build a list variable named FACTORIES_LIST with the given arguments, but:
+# - replace wildcard "*" with all known factories
+# - if the list begins with "^", take the complement
+# - finally remove unsupported factories
+#
+# Used by ADD_TESH_FACTORIES, and SET_TESH_PROPERTIES
+MACRO(SETUP_FACTORIES_LIST)
+  set(ALL_KNOWN_FACTORIES "thread;boost;raw;ucontext")
+
+  if("${ARGV}" STREQUAL "*")    # take all known factories
+    SET(FACTORIES_LIST ${ALL_KNOWN_FACTORIES})
+  elseif("${ARGV}" MATCHES "^\\^") # exclude given factories
+    SET(FACTORIES_LIST ${ALL_KNOWN_FACTORIES})
+    STRING(SUBSTRING "${ARGV}" 1 -1 EXCLUDED)
+    LIST(REMOVE_ITEM FACTORIES_LIST ${EXCLUDED})
+  else()                        # take given factories
+    SET(FACTORIES_LIST "${ARGV}")
+  endif()
+
+  # Exclude unsupported factories. Threads are always available, thanks to C++11 threads.
+  if(NOT HAVE_BOOST_CONTEXTS)
+    LIST(REMOVE_ITEM FACTORIES_LIST "boost")
+  endif()
+  if(NOT HAVE_RAW_CONTEXTS)
+    LIST(REMOVE_ITEM FACTORIES_LIST "raw")
+  endif()
+  if(NOT HAVE_UCONTEXT_CONTEXTS)
+    LIST(REMOVE_ITEM FACTORIES_LIST "ucontext")
+  endif()
+
+  # Check that there is no unknown factory
+  FOREACH(FACTORY ${FACTORIES_LIST})
+    if(NOT FACTORY IN_LIST ALL_KNOWN_FACTORIES)
+      message(FATAL_ERROR "Unknown factory: ${FACTORY}")
+    endif()
+  ENDFOREACH()
+ENDMACRO()
+
 MACRO(ADD_TESH_FACTORIES NAME FACTORIES)
   SET(ARGR ${ARGV})
   LIST(REMOVE_AT ARGR 0) # remove name
   FOREACH(I ${FACTORIES}) # remove all factories
     LIST(REMOVE_AT ARGR 0)
   ENDFOREACH()
-  FOREACH(FACTORY ${FACTORIES})
-    if ((${FACTORY} STREQUAL "thread" ) OR # Always available, thanks to C++11 threads
-        (${FACTORY} STREQUAL "boost" AND HAVE_BOOST_CONTEXTS) OR
-        (${FACTORY} STREQUAL "raw" AND HAVE_RAW_CONTEXTS) OR
-        (${FACTORY} STREQUAL "ucontext" AND HAVE_UCONTEXT_CONTEXTS))
-      ADD_TESH("${NAME}-${FACTORY}" "--cfg" "contexts/factory:${FACTORY}" ${ARGR})
-    endif()
-    if ((NOT ${FACTORY} STREQUAL "thread") AND 
-        (NOT ${FACTORY} STREQUAL "boost") AND
-       (NOT ${FACTORY} STREQUAL "raw") AND
-       (NOT ${FACTORY} STREQUAL "ucontext"))
-       message(FATAL_ERROR "Cannot add a tesh for an unknown factory: ${FACTORY}")
-    endif()
+  SETUP_FACTORIES_LIST(${FACTORIES})
+  FOREACH(FACTORY ${FACTORIES_LIST})
+    ADD_TESH("${NAME}-${FACTORY}" "--cfg" "contexts/factory:${FACTORY}" ${ARGR})
   ENDFOREACH()
 ENDMACRO()
 
@@ -78,13 +106,9 @@ MACRO(SET_TESH_PROPERTIES NAME FACTORIES)
   FOREACH(I ${FACTORIES}) # remove all factories
     LIST(REMOVE_AT ARGR 0)
   ENDFOREACH()
-  FOREACH(FACTORY ${FACTORIES})
-    if ((${FACTORY} STREQUAL "thread" ) OR # Always available, thanks to C++11 threads
-        (${FACTORY} STREQUAL "boost" AND HAVE_BOOST_CONTEXTS) OR
-        (${FACTORY} STREQUAL "raw" AND HAVE_RAW_CONTEXTS) OR
-        (${FACTORY} STREQUAL "ucontext" AND HAVE_UCONTEXT_CONTEXTS))
-      set_tests_properties("${NAME}-${FACTORY}" PROPERTIES ${ARGR})
-    endif()
+  SETUP_FACTORIES_LIST(${FACTORIES})
+  FOREACH(FACTORY ${FACTORIES_LIST})
+    set_tests_properties("${NAME}-${FACTORY}" PROPERTIES ${ARGR})
   ENDFOREACH()
 ENDMACRO()      
 
index abcc01d..9f0ef53 100755 (executable)
@@ -95,14 +95,6 @@ def setenv(arg):
 def expandvars2(path):
     return re.sub(r'(?<!\\)\$[A-Za-z_][A-Za-z0-9_]*', '', os.path.expandvars(path))
 
-
-# https://github.com/Cadair/jupyter_environment_kernels/issues/10
-try:
-    FileNotFoundError
-except NameError:
-    # py2
-    FileNotFoundError = OSError
-
 ##############
 #
 # Cleanup on signal
@@ -286,17 +278,16 @@ class Cmd(object):
     # Return False if nothing has been ran.
 
     def run_if_possible(self):
-        if self.can_run():
-            if self.background:
-                lock = _thread.allocate_lock()
-                lock.acquire()
-                TeshState().add_thread(lock)
-                _thread.start_new_thread(Cmd._run, (self, lock))
-            else:
-                self._run()
-            return True
-        else:
+        if not self.can_run():
             return False
+        if self.background:
+            lock = _thread.allocate_lock()
+            lock.acquire()
+            TeshState().add_thread(lock)
+            _thread.start_new_thread(Cmd._run, (self, lock))
+        else:
+            self._run()
+        return True
 
     def _run(self, lock=None):
         # Python threads loose the cwd
@@ -490,15 +481,15 @@ class Cmd(object):
                 return_code = max(2, return_code)
                 print('\n'.join(logs))
                 return
-            else:
-                logs.append("Test suite `{file}': NOK (<{cmd}> got signal {sig})".format(
-                    file=FileReader().filename, cmd=cmdName,
-                    sig=SIGNALS_TO_NAMES_DICT[-proc.returncode]))
-                if lock is not None:
-                    lock.release()
-                return_code = max(max(-proc.returncode, 1), return_code)
-                print('\n'.join(logs))
-                return
+
+            logs.append("Test suite `{file}': NOK (<{cmd}> got signal {sig})".format(
+                file=FileReader().filename, cmd=cmdName,
+                sig=SIGNALS_TO_NAMES_DICT[-proc.returncode]))
+            if lock is not None:
+                lock.release()
+            return_code = max(max(-proc.returncode, 1), return_code)
+            print('\n'.join(logs))
+            return
 
         if lock is not None:
             lock.release()