From c642311b1135f0d4a8f55e5822d9c0b4fb8e5e5d Mon Sep 17 00:00:00 2001 From: adfaure Date: Wed, 15 Jun 2016 15:45:56 +0200 Subject: [PATCH 1/1] [s4u] add mutex --- examples/s4u/CMakeLists.txt | 3 +- examples/s4u/mutex/.gitignore | 1 + examples/s4u/mutex/s4u_mutex.cpp | 95 +++++++++++++++++++++++++++++++ examples/s4u/mutex/s4u_mutex.tesh | 12 ++++ include/simgrid/s4u.h | 1 + include/simgrid/s4u/mutex.hpp | 36 ++++++++++++ src/s4u/s4u_mutex.cpp | 31 ++++++++++ tools/cmake/DefinePackages.cmake | 2 + 8 files changed, 180 insertions(+), 1 deletion(-) create mode 100644 examples/s4u/mutex/.gitignore create mode 100644 examples/s4u/mutex/s4u_mutex.cpp create mode 100644 examples/s4u/mutex/s4u_mutex.tesh create mode 100644 include/simgrid/s4u/mutex.hpp create mode 100644 src/s4u/s4u_mutex.cpp diff --git a/examples/s4u/CMakeLists.txt b/examples/s4u/CMakeLists.txt index 686defdbf7..e90125ec7b 100644 --- a/examples/s4u/CMakeLists.txt +++ b/examples/s4u/CMakeLists.txt @@ -1,4 +1,4 @@ -foreach (example basic io) +foreach (example basic io mutex) add_executable (s4u_${example} ${example}/s4u_${example}.cpp) target_link_libraries(s4u_${example} simgrid) set_target_properties(s4u_${example} PROPERTIES RUNTIME_OUTPUT_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/${example}) @@ -13,3 +13,4 @@ set(txt_files ${txt_files} ${CMAKE_CURRENT_SOURCE_DIR}/README PARENT_SCO ADD_TESH_FACTORIES(s4u-basic "thread;ucontext;raw;boost" --setenv bindir=${CMAKE_BINARY_DIR}/examples/s4u/basic --cd ${CMAKE_HOME_DIRECTORY}/examples/s4u/basic s4u_basic.tesh) ADD_TESH_FACTORIES(s4u-io "thread;ucontext;raw;boost" --setenv bindir=${CMAKE_BINARY_DIR}/examples/s4u/io --cd ${CMAKE_HOME_DIRECTORY}/examples/s4u/io s4u_io.tesh) +ADD_TESH_FACTORIES(s4u-mutex "thread;ucontext;raw;boost" --setenv bindir=${CMAKE_BINARY_DIR}/examples/s4u/mutex --cd ${CMAKE_HOME_DIRECTORY}/examples/s4u/mutex s4u_mutex.tesh) diff --git a/examples/s4u/mutex/.gitignore b/examples/s4u/mutex/.gitignore new file mode 100644 index 0000000000..0ace5ca849 --- /dev/null +++ b/examples/s4u/mutex/.gitignore @@ -0,0 +1 @@ +s4u_actor diff --git a/examples/s4u/mutex/s4u_mutex.cpp b/examples/s4u/mutex/s4u_mutex.cpp new file mode 100644 index 0000000000..10c4f98f44 --- /dev/null +++ b/examples/s4u/mutex/s4u_mutex.cpp @@ -0,0 +1,95 @@ +/* Copyright (c) 2006-2015. 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 +#include + +#include "simgrid/s4u.h" + +#define NB_ACTOR 2 + +XBT_LOG_NEW_DEFAULT_CATEGORY(s4u_test, "a sample log category"); + +// simgrid::s4u::Mutex mtx; //FIXME generate error -> You must run MSG_init before using MSG + +//Create an actor as a c++ functor +class Worker { +simgrid::s4u::Mutex *pMtx; +int *pResults; +public: + Worker(int *res, simgrid::s4u::Mutex *mtx) : pMtx(mtx), 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(); + 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; +int *pResults; +public: + WorkerLockGuard(int *res, simgrid::s4u::Mutex *mtx) : pMtx(mtx), pResults(res) {}; + void operator()() { + + simgrid::s4u::this_actor::execute(1000); + + // Simply use the std::lock_guard like this + std::lock_guard lock(*pMtx); + + // then you are in a safe zone + XBT_INFO("Hello s4u, I'm ready to compute"); + // update the results + *pResults += 1; + XBT_INFO("I'm done, good bye"); + } +}; + +class MainActor { +public: + void operator()() { + int *res = new int; + simgrid::s4u::Mutex *mtx = new simgrid::s4u::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)); + else + workers[i] = new simgrid::s4u::Actor("worker", simgrid::s4u::Host::by_name("Tremblay"), Worker(res,mtx)); + } + + for (int i = 0; i < NB_ACTOR ; i++) { + delete workers[i]; + } + + simgrid::s4u::this_actor::sleep(10); + XBT_INFO("Results is -> %d", *res); + delete mtx; + } +}; + + +int main(int argc, char **argv) { + simgrid::s4u::Engine *e = new simgrid::s4u::Engine(&argc,argv); + e->loadPlatform("../../platforms/two_hosts.xml"); + new simgrid::s4u::Actor("main", simgrid::s4u::Host::by_name("Tremblay"), 0, MainActor()); + e->run(); + return 0; +} diff --git a/examples/s4u/mutex/s4u_mutex.tesh b/examples/s4u/mutex/s4u_mutex.tesh new file mode 100644 index 0000000000..e0f1040502 --- /dev/null +++ b/examples/s4u/mutex/s4u_mutex.tesh @@ -0,0 +1,12 @@ +#! ./tesh + +$ $SG_TEST_EXENV ${bindir:=.}/s4u_mutex +>[Tremblay:worker:(0) 0.000080] [s4u_test/INFO] Hello s4u, I'm ready to compute +>[Tremblay:worker:(0) 0.000080] [s4u_test/INFO] I'm done, good bye +>[Tremblay:worker:(0) 0.000080] [s4u_test/INFO] Hello s4u, I'm ready to compute +>[Tremblay:worker:(0) 0.000080] [s4u_test/INFO] I'm done, good bye +>[Jupiter:worker:(0) 0.000160] [s4u_test/INFO] Hello s4u, I'm ready to compute +>[Jupiter:worker:(0) 0.000160] [s4u_test/INFO] I'm done, good bye +>[Jupiter:worker:(0) 0.000160] [s4u_test/INFO] Hello s4u, I'm ready to compute +>[Jupiter:worker:(0) 0.000160] [s4u_test/INFO] I'm done, good bye +>[Tremblay:main:(0) 10.000000] [s4u_test/INFO] Results is -> 4 diff --git a/include/simgrid/s4u.h b/include/simgrid/s4u.h index 42cb73b837..dde320556b 100644 --- a/include/simgrid/s4u.h +++ b/include/simgrid/s4u.h @@ -11,6 +11,7 @@ #include "s4u/engine.hpp" #include "s4u/host.hpp" +#include "s4u/mutex.hpp" #include "s4u/Activity.hpp" #include "s4u/comm.hpp" diff --git a/include/simgrid/s4u/mutex.hpp b/include/simgrid/s4u/mutex.hpp new file mode 100644 index 0000000000..52accd1686 --- /dev/null +++ b/include/simgrid/s4u/mutex.hpp @@ -0,0 +1,36 @@ +/* Copyright (c) 2006-2015. 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_S4U_MUTEX_HPP +#define SIMGRID_S4U_MUTEX_HPP + +#include +#include "simgrid/simix.h" + + +namespace simgrid { +namespace s4u { + +XBT_PUBLIC_CLASS Mutex { + +public: + Mutex(); + ~Mutex() {}; + +protected: + +public: + + void lock(); + void unlock(); + bool try_lock(); + +private: + std::shared_ptr _mutex; + +}; +}} // namespace simgrid::s4u + +#endif /* SIMGRID_S4U_MUTEX_HPP */ diff --git a/src/s4u/s4u_mutex.cpp b/src/s4u/s4u_mutex.cpp new file mode 100644 index 0000000000..20f6ee2936 --- /dev/null +++ b/src/s4u/s4u_mutex.cpp @@ -0,0 +1,31 @@ +/* Copyright (c) 2006-2015. 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 "xbt/log.h" +#include "src/msg/msg_private.h" +#include "src/simix/smx_network_private.h" + +#include "simgrid/s4u/mutex.hpp" + + +using namespace simgrid; + +s4u::Mutex::Mutex() { + smx_mutex_t smx_mutex = simcall_mutex_init(); + _mutex = std::shared_ptr(smx_mutex, SIMIX_mutex_destroy ); +} + +void s4u::Mutex::lock() { + simcall_mutex_lock(_mutex.get()); +} + +void s4u::Mutex::unlock() { + simcall_mutex_unlock(_mutex.get()); +} + +bool s4u::Mutex::try_lock() { + return simcall_mutex_trylock(_mutex.get()); +} diff --git a/tools/cmake/DefinePackages.cmake b/tools/cmake/DefinePackages.cmake index eb8ef777c7..586f2aec7b 100644 --- a/tools/cmake/DefinePackages.cmake +++ b/tools/cmake/DefinePackages.cmake @@ -381,6 +381,7 @@ set(S4U_SRC src/s4u/s4u_file.cpp src/s4u/s4u_host.cpp src/s4u/s4u_mailbox.cpp + src/s4u/s4u_mutex.cpp src/s4u/s4u_storage.cpp ) @@ -644,6 +645,7 @@ set(headers_to_install include/simgrid/s4u/file.hpp include/simgrid/s4u/host.hpp include/simgrid/s4u/mailbox.hpp + include/simgrid/s4u/mutex.hpp include/simgrid/s4u/storage.hpp include/simgrid/s4u.h include/simgrid/plugins/energy.h -- 2.20.1