[DEV] add some interface to create concurence acces on stating

This commit is contained in:
Edouard DUPIN 2015-09-01 22:48:02 +02:00
parent 718b0b0964
commit 78666947ce
5 changed files with 179 additions and 5 deletions

59
gale/Thread.cpp Normal file
View File

@ -0,0 +1,59 @@
/**
* @author Edouard DUPIN
*
* @copyright 2011, Edouard DUPIN, all right reserved
*
* @license APACHE v2.0 (see license file)
*/
#include <gale/Thread.h>
#include <gale/debug.h>
#include <unistd.h>
#include <gale/context/Context.h>
gale::Thread::Thread() :
m_state(state_stop),
m_thread(nullptr) {
}
gale::Thread::~Thread() {
delete m_thread;
m_thread = nullptr;
}
void gale::Thread::start() {
if (m_state == state_stop) {
m_state = state_starting;
m_thread = new std11::thread(&gale::Thread::threadCall, this);
// set priority
// set association with the gale context ...
gale::contextRegisterThread(m_thread);
m_state = state_running;
}
}
void gale::Thread::stop() {
if (m_state != state_running) {
return;
}
m_state = state_stopping;
m_thread->join();
gale::contextUnRegisterThread(m_thread);
delete m_thread;
m_thread = nullptr;
m_state = state_stop;
}
void gale::Thread::threadCall() {
while (m_state != state_stopping) {
if (m_state == state_starting) {
usleep(1000);
continue;
}
if (onThreadCall() == true) {
return;
}
}
}

49
gale/Thread.h Normal file
View File

@ -0,0 +1,49 @@
/**
* @author Edouard DUPIN
*
* @copyright 2011, Edouard DUPIN, all right reserved
*
* @license APACHE v2.0 (see license file)
*/
#ifndef __GALE_THREAD_H__
#define __GALE_THREAD_H__
#include <etk/types.h>
#include <etk/thread/tools.h>
namespace gale {
/**
* @brief in the dimention class we store the data as the more usefull unit (pixel)
* but one case need to be dynamic the %, then when requested in % the register the % value
*/
class Thread {
private:
enum state {
state_stop,
state_starting,
state_running,
state_stopping
};
enum state m_state;
std11::thread* m_thread;
public:
/**
* @brief Constructor (default :0,0 mode pixel)
*/
Thread();
/**
* @brief Destructor
*/
virtual ~Thread();
void start();
void stop();
protected:
virtual bool onThreadCall() { return true; };
private:
void threadCall();
};
};
#endif

View File

@ -25,6 +25,7 @@
#include <gale/renderer/openGL/openGL.h>
#include <gale/context/Context.h>
#include <gale/resource/Manager.h>
#include <map>
@ -40,16 +41,69 @@ static std::mutex& mutexInterface() {
}
static gale::Context* l_curentInterface=nullptr;
static std11::mutex g_lockContextMap;
static std::map<std11::thread::id, gale::Context*>& getContextList() {
static std::map<std11::thread::id, gale::Context*> g_val;
return g_val;
}
gale::Context& gale::getContext() {
std::map<std11::thread::id, gale::Context*>& list = getContextList();
g_lockContextMap.lock();
std::map<std11::thread::id, gale::Context*>::iterator it = list.find(std11::this_thread::get_id());
gale::Context* out = nullptr;
if (it != list.end()) {
out = it->second;
}
g_lockContextMap.unlock();
#if DEBUG_LEVEL > 2
if(nullptr == l_curentInterface){
if(out ==nullptr){
GALE_CRITICAL("[CRITICAL] try acces at an empty interface");
}
#endif
return *l_curentInterface;
return *out;
}
static void setContext(gale::Context* _context) {
std::map<std11::thread::id, gale::Context*>& list = getContextList();
g_lockContextMap.lock();
std::map<std11::thread::id, gale::Context*>::iterator it = list.find(std11::this_thread::get_id());
if (it == list.end()) {
list.insert(std::pair<std11::thread::id, gale::Context*>(std11::this_thread::get_id(), _context));
} else {
it->second = _context;
}
g_lockContextMap.unlock();
}
void gale::contextRegisterThread(std11::thread* _thread) {
if (_thread == nullptr) {
return;
}
gale::Context* context = &gale::getContext();
std::map<std11::thread::id, gale::Context*>& list = getContextList();
g_lockContextMap.lock();
std::map<std11::thread::id, gale::Context*>::iterator it = list.find(_thread->get_id());
if (it == list.end()) {
list.insert(std::pair<std11::thread::id, gale::Context*>(_thread->get_id(), context));
} else {
it->second = context;
}
g_lockContextMap.unlock();
}
void gale::contextUnRegisterThread(std11::thread* _thread) {
if (_thread == nullptr) {
return;
}
std::map<std11::thread::id, gale::Context*>& list = getContextList();
g_lockContextMap.lock();
std::map<std11::thread::id, gale::Context*>::iterator it = list.find(_thread->get_id());
if (it != list.end()) {
list.erase(it);
}
g_lockContextMap.unlock();
}
void gale::Context::setInitImage(const std::string& _fileName) {
@ -64,7 +118,7 @@ void gale::Context::setInitImage(const std::string& _fileName) {
*/
void gale::Context::lockContext() {
mutexInterface().lock();
l_curentInterface = this;
setContext(this);
}
/**
@ -72,7 +126,7 @@ void gale::Context::lockContext() {
* @note this un-lock the main mutex
*/
void gale::Context::unLockContext() {
l_curentInterface = nullptr;
setContext(nullptr);
mutexInterface().unlock();
}

View File

@ -24,6 +24,7 @@
#include <gale/orientation.h>
#include <gale/context/clipBoard.h>
#include <gale/context/LoopAction.h>
#include <etk/thread/tools.h>
#define MAX_MANAGE_INPUT (15)
@ -310,6 +311,16 @@ namespace gale {
* @return current reference on the instance.
*/
Context& getContext();
/**
* @brief When a new thread is created, it is needed to register it in the gale context interface to permit to get the context associated on it ...
* @param[in] _thread generic C++11 thread handle
*/
void contextRegisterThread(std11::thread* _thread);
/**
* @brief Remove an associated thread
* @param[in] _thread generic C++11 thread handle
*/
void contextUnRegisterThread(std11::thread* _thread);
};
#endif

View File

@ -24,6 +24,7 @@ def create(target):
'gale/Dimension.cpp',
'gale/orientation.cpp',
'gale/Application.cpp',
'gale/Thread.cpp',
])
# context :