From: Gabriel Corona Date: Wed, 15 Jun 2016 14:44:44 +0000 (+0200) Subject: [s4u] Use simix simix::Mutex refcount support for s4u::Mutex X-Git-Tag: v3_14~987^2~4^2~1 X-Git-Url: http://info.iut-bm.univ-fcomte.fr/pub/gitweb/simgrid.git/commitdiff_plain/5f11cdef5b0309cb622f9280488f85fa213e8c1f [s4u] Use simix simix::Mutex refcount support for s4u::Mutex --- diff --git a/examples/s4u/mutex/s4u_mutex.cpp b/examples/s4u/mutex/s4u_mutex.cpp index 10c4f98f44..222deae251 100644 --- a/examples/s4u/mutex/s4u_mutex.cpp +++ b/examples/s4u/mutex/s4u_mutex.cpp @@ -16,40 +16,39 @@ XBT_LOG_NEW_DEFAULT_CATEGORY(s4u_test, "a sample log category"); //Create an actor as a c++ functor class Worker { -simgrid::s4u::Mutex *pMtx; + simgrid::s4u::Mutex mutex_; int *pResults; public: - Worker(int *res, simgrid::s4u::Mutex *mtx) : pMtx(mtx), pResults(res) {}; + Worker(int *res, simgrid::s4u::Mutex mutex) : + mutex_(std::move(mutex)), pResults(res) {}; // Define the code of the actor void operator()() { // Do the calculation simgrid::s4u::this_actor::execute(1000); - // lock the mutex before enter in th critical section - pMtx->lock(); + // lock the mutex before enter in the critical section + std::lock_guard lock(mutex_); XBT_INFO("Hello s4u, I'm ready to compute"); // And finaly add it to the results *pResults += 1; XBT_INFO("I'm done, good bye"); - - //Then unlock the mutex, so other threads will be able to update their results - pMtx->unlock(); } }; // This class is an example of how to use lock_guard with simgrid mutex class WorkerLockGuard { -simgrid::s4u::Mutex *pMtx; + simgrid::s4u::Mutex mutex_; int *pResults; public: - WorkerLockGuard(int *res, simgrid::s4u::Mutex *mtx) : pMtx(mtx), pResults(res) {}; + WorkerLockGuard(int *res, simgrid::s4u::Mutex mutex) : + mutex_(std::move(mutex)), pResults(res) {}; void operator()() { simgrid::s4u::this_actor::execute(1000); // Simply use the std::lock_guard like this - std::lock_guard lock(*pMtx); + std::lock_guard lock(mutex_); // then you are in a safe zone XBT_INFO("Hello s4u, I'm ready to compute"); @@ -63,16 +62,20 @@ class MainActor { public: void operator()() { int *res = new int; - simgrid::s4u::Mutex *mtx = new simgrid::s4u::Mutex(); + simgrid::s4u::Mutex mutex; *res = 0; simgrid::s4u::Actor* workers[NB_ACTOR*2]; for (int i = 0; i < NB_ACTOR * 2 ; i++) { // To create a worker use the static method simgrid::s4u::Actor. if((i % 2) == 0 ) - workers[i] = new simgrid::s4u::Actor("worker", simgrid::s4u::Host::by_name("Jupiter"), WorkerLockGuard(res,mtx)); + workers[i] = new simgrid::s4u::Actor("worker", + simgrid::s4u::Host::by_name("Jupiter"), + WorkerLockGuard(res, mutex)); else - workers[i] = new simgrid::s4u::Actor("worker", simgrid::s4u::Host::by_name("Tremblay"), Worker(res,mtx)); + workers[i] = new simgrid::s4u::Actor("worker", + simgrid::s4u::Host::by_name("Tremblay"), + Worker(res,mutex)); } for (int i = 0; i < NB_ACTOR ; i++) { @@ -81,7 +84,6 @@ public: simgrid::s4u::this_actor::sleep(10); XBT_INFO("Results is -> %d", *res); - delete mtx; } }; diff --git a/include/simgrid/s4u/mutex.hpp b/include/simgrid/s4u/mutex.hpp index 52accd1686..da7c3df863 100644 --- a/include/simgrid/s4u/mutex.hpp +++ b/include/simgrid/s4u/mutex.hpp @@ -6,30 +6,55 @@ #ifndef SIMGRID_S4U_MUTEX_HPP #define SIMGRID_S4U_MUTEX_HPP +#include + +#include #include #include "simgrid/simix.h" - namespace simgrid { namespace s4u { XBT_PUBLIC_CLASS Mutex { public: - Mutex(); - ~Mutex() {}; - -protected: + Mutex() : + mutex_(simcall_mutex_init()) {} + Mutex(simgrid::simix::Mutex* mutex) : mutex_(SIMIX_mutex_dup(mutex)) {} + ~Mutex() + { + SIMIX_mutex_destroy(mutex_); + } + + // Copy+move (with the copy-and-swap idiom): + Mutex(Mutex const& mutex) : mutex_(SIMIX_mutex_dup(mutex.mutex_)) {} + friend void swap(Mutex& first, Mutex& second) + { + using std::swap; + swap(first.mutex_, second.mutex_); + } + Mutex& operator=(Mutex mutex) + { + swap(*this, mutex); + return *this; + } + Mutex(Mutex&& mutex) : mutex_(nullptr) + { + swap(*this, mutex); + } + + bool valid() const + { + return mutex_ != nullptr; + } public: - void lock(); void unlock(); bool try_lock(); private: - std::shared_ptr _mutex; - + simgrid::simix::Mutex* mutex_; }; }} // namespace simgrid::s4u diff --git a/src/s4u/s4u_mutex.cpp b/src/s4u/s4u_mutex.cpp index 20f6ee2936..e64bfd4f60 100644 --- a/src/s4u/s4u_mutex.cpp +++ b/src/s4u/s4u_mutex.cpp @@ -10,22 +10,20 @@ #include "simgrid/s4u/mutex.hpp" +namespace simgrid { +namespace s4u { -using namespace simgrid; - -s4u::Mutex::Mutex() { - smx_mutex_t smx_mutex = simcall_mutex_init(); - _mutex = std::shared_ptr(smx_mutex, SIMIX_mutex_destroy ); +void Mutex::lock() { + simcall_mutex_lock(mutex_); } -void s4u::Mutex::lock() { - simcall_mutex_lock(_mutex.get()); +void Mutex::unlock() { + simcall_mutex_unlock(mutex_); } -void s4u::Mutex::unlock() { - simcall_mutex_unlock(_mutex.get()); +bool Mutex::try_lock() { + return simcall_mutex_trylock(mutex_); } -bool s4u::Mutex::try_lock() { - return simcall_mutex_trylock(_mutex.get()); +} } diff --git a/src/simix/smx_process.cpp b/src/simix/smx_process.cpp index 836d2d0ae8..b47211a5d4 100644 --- a/src/simix/smx_process.cpp +++ b/src/simix/smx_process.cpp @@ -136,9 +136,12 @@ namespace simix { Process::~Process() { delete this->context; - xbt_dict_free(&this->properties); - xbt_fifo_free(this->comms); - xbt_dynar_free(&this->on_exit); + if (this->properties) + xbt_dict_free(&this->properties); + if (this->comms != nullptr) + xbt_fifo_free(this->comms); + if (this->on_exit) + xbt_dynar_free(&this->on_exit); } void create_maestro(std::function code)