summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTimo Lotterbach <timo.lotterbach@bmw-carit.de>2013-07-03 16:11:14 +0200
committerTimo Lotterbach <timo.lotterbach@bmw-carit.de>2013-07-05 12:56:48 +0200
commit1030fb671c247de746239f3fb679d7f86f511cdc (patch)
tree99234b2834f5df07090f3c1451dd8542b5452f25
parent6a580ea1b6137b7c229f04bc267eea9b5ee572f1 (diff)
downloadlayer_management-1030fb671c247de746239f3fb679d7f86f511cdc.tar.gz
Health: added thread dead-lock detection
Signed-off-by: Timo Lotterbach <timo.lotterbach@bmw-carit.de>
-rw-r--r--LayerManagerBase/include/ICommunicator.h6
-rw-r--r--LayerManagerBase/include/IHealthMonitor.h1
-rw-r--r--LayerManagerBase/include/IRenderer.h3
-rw-r--r--LayerManagerBase/include/Layermanager.h1
-rw-r--r--LayerManagerBase/include/PluginBase.h4
-rw-r--r--LayerManagerBase/src/Layermanager.cpp34
-rw-r--r--LayerManagerBase/src/PluginBase.cpp29
-rw-r--r--LayerManagerClient/ilmCommon/include/ilm_types.h1
-rw-r--r--LayerManagerPlugins/Communicators/GenericCommunicator/include/GenericCommunicator.h8
-rw-r--r--LayerManagerPlugins/Communicators/GenericCommunicator/src/GenericCommunicator.cpp35
-rw-r--r--LayerManagerPlugins/HealthMonitor/SystemdHealthMonitor/include/SystemdHealthMonitor.h3
-rw-r--r--LayerManagerPlugins/HealthMonitor/SystemdHealthMonitor/src/SystemdHealthMonitor.cpp19
-rw-r--r--LayerManagerPlugins/IpcModules/DbusIpcModule/src/message.c2
-rw-r--r--LayerManagerPlugins/Renderers/Base/include/BaseRenderer.h2
-rw-r--r--LayerManagerPlugins/Renderers/Base/src/BaseRenderer.cpp2
-rw-r--r--LayerManagerPlugins/Renderers/Graphic/include/WindowSystems/BaseWindowSystem.h3
-rw-r--r--LayerManagerPlugins/Renderers/Graphic/include/WindowSystems/X11WindowSystem.h5
-rw-r--r--LayerManagerPlugins/Renderers/Graphic/src/WindowSystems/X11WindowSystem.cpp46
-rw-r--r--LayerManagerPlugins/Renderers/Platform/X11GLESRenderer/include/X11GLESRenderer.h5
-rw-r--r--LayerManagerPlugins/Renderers/Platform/X11GLESRenderer/src/X11GLESRenderer.cpp13
-rw-r--r--LayerManagerPlugins/SceneProvider/ExampleSceneProvider/include/ExampleSceneProvider.h1
-rw-r--r--LayerManagerPlugins/SceneProvider/ExampleSceneProvider/src/ExampleSceneProvider.cpp7
22 files changed, 169 insertions, 61 deletions
diff --git a/LayerManagerBase/include/ICommunicator.h b/LayerManagerBase/include/ICommunicator.h
index 61b3053..0e70106 100644
--- a/LayerManagerBase/include/ICommunicator.h
+++ b/LayerManagerBase/include/ICommunicator.h
@@ -44,8 +44,9 @@ public:
/**
* \brief Start communication process, i.e. start specific listening process of communication method
* \ingroup CommunicatorAPI
+ * \param[in] maxIterationTimeInMS expected wakup time for health reporting in milliseconds (-1 to disable wakeup)
*/
- virtual bool start() = 0;
+ virtual bool start(int maxIterationTimeInMS) = 0;
/**
* \brief Stop communication. Stop sending command objects.
@@ -56,9 +57,8 @@ public:
/**
* \brief Process communication.
* \ingroup CommunicatorAPI
- * \param[in] timeout_ms timeout value in milliseconds
*/
- virtual void process(int timeout_ms) = 0;
+ virtual void process() = 0;
/**
* \brief Switch debug mode of this component on or off
diff --git a/LayerManagerBase/include/IHealthMonitor.h b/LayerManagerBase/include/IHealthMonitor.h
index fd0cf69..cdbcb75 100644
--- a/LayerManagerBase/include/IHealthMonitor.h
+++ b/LayerManagerBase/include/IHealthMonitor.h
@@ -33,6 +33,7 @@ public:
virtual t_ilm_bool start() = 0;
virtual t_ilm_bool stop() = 0;
+ virtual int getPluginReportIntervalInMs() = 0;
protected:
ICommandExecutor& mExecutor;
diff --git a/LayerManagerBase/include/IRenderer.h b/LayerManagerBase/include/IRenderer.h
index 4f6af20..bcdbda5 100644
--- a/LayerManagerBase/include/IRenderer.h
+++ b/LayerManagerBase/include/IRenderer.h
@@ -49,10 +49,11 @@ public:
* \param[in] width width of display handled by this renderer
* \param[in] height height of display handled by this renderer
* \param[in] displayName name of display handled by this renderer
+ * \param[in] maxIterationTimeInMS expected wakup time for health reporting in milliseconds (-1 to disable wakeup)
* \return TRUE: renderer was started successfully
* \return FALSE: renderer start failed
*/
- virtual bool start(int width, int height, const char* displayName) = 0;
+ virtual bool start(int width, int height, const char* displayName, int maxIterationDurationInMS) = 0;
/**
* \brief Stop rendering process (stop render loop)
diff --git a/LayerManagerBase/include/Layermanager.h b/LayerManagerBase/include/Layermanager.h
index 9db1642..44b96dd 100644
--- a/LayerManagerBase/include/Layermanager.h
+++ b/LayerManagerBase/include/Layermanager.h
@@ -89,6 +89,7 @@ private:
void stopAllCommunicators();
bool executeCommand(ICommand* commandToBeExecuted);
bool enqueueCommand(ICommand* commandToBeExecuted);
+ int getPluginReportIntervalInMs();
private:
Scene* m_pScene;
diff --git a/LayerManagerBase/include/PluginBase.h b/LayerManagerBase/include/PluginBase.h
index 20b956a..3437a08 100644
--- a/LayerManagerBase/include/PluginBase.h
+++ b/LayerManagerBase/include/PluginBase.h
@@ -38,7 +38,7 @@ public:
virtual HealthCondition pluginGetHealth();
protected:
- void pluginSetHealth(HealthCondition health);
+ virtual int getIterationCounter() = 0;
protected:
ICommandExecutor& mExecutor;
@@ -46,7 +46,7 @@ protected:
private:
PluginApi mApi;
- HealthCondition mHealth;
+ int m_previousIterationCounter;
};
#endif // __PLUGINBASE_H__
diff --git a/LayerManagerBase/src/Layermanager.cpp b/LayerManagerBase/src/Layermanager.cpp
index caee5e0..b5e36f8 100644
--- a/LayerManagerBase/src/Layermanager.cpp
+++ b/LayerManagerBase/src/Layermanager.cpp
@@ -34,6 +34,7 @@
#include <unistd.h>
#include <pthread.h>
#include <signal.h>
+#include <limits.h>
static const char* NO_SENDER_NAME = "unknown";
@@ -377,11 +378,37 @@ bool Layermanager::execute(ICommand* commandToBeExecuted)
return status;
}
+int Layermanager::getPluginReportIntervalInMs()
+{
+ int retVal = INT_MAX;
+ HealthMonitorList monitors;
+ m_pPluginManager->getHealthMonitorList(monitors);
+
+ if (0 == monitors.size())
+ {
+ retVal = -1;
+ }
+ else
+ {
+ HealthMonitorListIterator iter = monitors.begin();
+ HealthMonitorListIterator end = monitors.end();
+ for (; iter != end; ++iter)
+ {
+ IHealthMonitor* monitor = *iter;
+ int monitorInterval = monitor->getPluginReportIntervalInMs();
+ retVal = (monitorInterval < retVal ? monitorInterval : retVal);
+ }
+ }
+ return retVal;
+}
+
bool Layermanager::startAllRenderers(const int width, const int height,
const char *displayName)
{
bool allStarted = false;
+ int maxIterationDurationInMS = getPluginReportIntervalInMs();
+
RendererListIterator iter = m_pRendererList->begin();
RendererListIterator iterEnd = m_pRendererList->end();
for (; iter != iterEnd; ++iter)
@@ -389,7 +416,7 @@ bool Layermanager::startAllRenderers(const int width, const int height,
IRenderer* renderer = *iter;
if (renderer)
{
- allStarted = renderer->start(width, height, displayName);
+ allStarted = renderer->start(width, height, displayName, maxIterationDurationInMS);
}
if (renderer == NULL || allStarted == false)
{
@@ -433,6 +460,8 @@ bool Layermanager::startAllCommunicators()
{
bool allStarted = true;
+ int maxIterationDurationInMS = getPluginReportIntervalInMs();
+
CommunicatorListIterator communicatorIter = m_pCommunicatorList->begin();
CommunicatorListIterator communicatorIterEnd = m_pCommunicatorList->end();
@@ -441,7 +470,7 @@ bool Layermanager::startAllCommunicators()
ICommunicator *communicator = *communicatorIter;
if (communicator)
{
- allStarted &= communicator->start();
+ allStarted &= communicator->start(maxIterationDurationInMS);
}
else
{
@@ -560,6 +589,7 @@ HealthCondition Layermanager::getHealth()
{
IPlugin* monitoredPlugin = *iter;
returnValue = monitoredPlugin->pluginGetHealth();
+ LOG_INFO("Layermanager", "Plugin " << monitoredPlugin->pluginGetName() << " health: " << (returnValue == HealthRunning ? "Running" : "Dead"));
++iter;
}
diff --git a/LayerManagerBase/src/PluginBase.cpp b/LayerManagerBase/src/PluginBase.cpp
index 7f789a8..bdf0173 100644
--- a/LayerManagerBase/src/PluginBase.cpp
+++ b/LayerManagerBase/src/PluginBase.cpp
@@ -20,12 +20,13 @@
#include "PluginBase.h"
#include "ICommandExecutor.h"
#include "Scene.h"
+#include "Log.h"
PluginBase::PluginBase(ICommandExecutor& executor, Configuration& config, ilmPluginApi api)
: mExecutor(executor)
, mConfiguration(config)
, mApi(api)
-, mHealth(HealthStopped)
+, m_previousIterationCounter(0)
{
}
@@ -45,10 +46,24 @@ t_ilm_const_string PluginBase::pluginGetName() const
HealthCondition PluginBase::pluginGetHealth()
{
- return mHealth;
-}
+ HealthCondition health = HealthDead;
-void PluginBase::pluginSetHealth(HealthCondition health)
-{
- mHealth = health;
-}
+ int currentIterationCounter = getIterationCounter();
+
+ if (0 == currentIterationCounter)
+ {
+ // plugin has 0 iterations, so it is not running yet.
+ return HealthRunning;
+ }
+
+ if (m_previousIterationCounter != currentIterationCounter)
+ {
+ health = HealthRunning;
+ m_previousIterationCounter = currentIterationCounter;
+ }
+ else
+ {
+ LOG_ERROR(pluginGetName(), "Internal loop counter did not increase. Possible dead-lock detected.");
+ }
+ return health;
+} \ No newline at end of file
diff --git a/LayerManagerClient/ilmCommon/include/ilm_types.h b/LayerManagerClient/ilmCommon/include/ilm_types.h
index b27d988..8531bc7 100644
--- a/LayerManagerClient/ilmCommon/include/ilm_types.h
+++ b/LayerManagerClient/ilmCommon/include/ilm_types.h
@@ -282,6 +282,7 @@ typedef enum e_t_ilm_message_type
IpcMessageTypeDisconnect,
IpcMessageTypeNotification,
IpcMessageTypeError,
+ IpcMessageTypeTimeout,
IpcMessageTypeShutdown
} t_ilm_message_type;
diff --git a/LayerManagerPlugins/Communicators/GenericCommunicator/include/GenericCommunicator.h b/LayerManagerPlugins/Communicators/GenericCommunicator/include/GenericCommunicator.h
index fd9a2de..00e11e9 100644
--- a/LayerManagerPlugins/Communicators/GenericCommunicator/include/GenericCommunicator.h
+++ b/LayerManagerPlugins/Communicators/GenericCommunicator/include/GenericCommunicator.h
@@ -62,17 +62,17 @@ public:
virtual ~GenericCommunicator() {}
// from ICommunicator
- virtual bool start();
+ virtual bool start(int maxIterationTimeInMS);
virtual void stop();
- virtual void process(int timeout_ms);
+ virtual void process();
virtual void setdebug(bool onoff);
+ virtual int getIterationCounter();
// from ThreadBase
virtual t_ilm_bool threadMainLoop();
// from PluginBase
virtual t_ilm_const_string pluginGetName() const;
- virtual HealthCondition pluginGetHealth();
private:
void ServiceConnect(t_ilm_message message);
@@ -168,6 +168,8 @@ private:
CallBackTable m_callBackTable;
bool m_running;
unsigned long int mThreadId;
+ int m_iterationCounter;
+ int m_maxIterationDurationInMS;
};
#endif // __GENERICCOMMUNICATOR_H__
diff --git a/LayerManagerPlugins/Communicators/GenericCommunicator/src/GenericCommunicator.cpp b/LayerManagerPlugins/Communicators/GenericCommunicator/src/GenericCommunicator.cpp
index 8386cd1..7b4c7c1 100644
--- a/LayerManagerPlugins/Communicators/GenericCommunicator/src/GenericCommunicator.cpp
+++ b/LayerManagerPlugins/Communicators/GenericCommunicator/src/GenericCommunicator.cpp
@@ -94,6 +94,7 @@ GenericCommunicator::GenericCommunicator(ICommandExecutor& executor, Configurati
: ICommunicator(&executor)
, PluginBase(executor, config, Communicator_Api_v1)
, m_running(ILM_FALSE)
+, m_iterationCounter(0)
{
MethodTable manager_methods[] =
{
@@ -195,8 +196,10 @@ GenericCommunicator::GenericCommunicator(ICommandExecutor& executor, Configurati
mThreadId = pthread_self();
}
-bool GenericCommunicator::start()
+bool GenericCommunicator::start(int maxIterationTimeInMS)
{
+ m_maxIterationDurationInMS = maxIterationTimeInMS;
+
LOG_DEBUG("GenericCommunicator", "Starting up IpcModules.");
if (!loadIpcModule(&m_ipcModule))
@@ -214,7 +217,6 @@ bool GenericCommunicator::start()
LOG_DEBUG("GenericCommunicator", "Initializing IpcModule success.");
m_running = ILM_TRUE;
- pluginSetHealth(HealthRunning);
threadCreate();
threadInit();
@@ -233,12 +235,13 @@ void GenericCommunicator::stop()
{
m_ipcModule.destroy();
}
- pluginSetHealth(HealthStopped);
}
-void GenericCommunicator::process(int timeout_ms)
+void GenericCommunicator::process()
{
- t_ilm_message message = m_ipcModule.receive(timeout_ms);
+ ++m_iterationCounter;
+
+ t_ilm_message message = m_ipcModule.receive(m_maxIterationDurationInMS);
if (!message)
{
return;
@@ -308,6 +311,10 @@ void GenericCommunicator::process(int timeout_ms)
case IpcMessageTypeNone:
break;
+ case IpcMessageTypeTimeout:
+ LOG_INFO("GenericCommunicator", "no incoming message for " << m_maxIterationDurationInMS << "ms, force wakeup for health monitoring");
+ break;
+
default:
LOG_DEBUG("GenericCommunicator", "Received unknown data from "
<< m_executor->getSenderName(senderHandle)
@@ -317,6 +324,7 @@ void GenericCommunicator::process(int timeout_ms)
m_ipcModule.destroyMessage(message);
}
+
void GenericCommunicator::setdebug(bool onoff)
{
(void)onoff; // TODO: remove, only prevents warning
@@ -324,10 +332,15 @@ void GenericCommunicator::setdebug(bool onoff)
t_ilm_bool GenericCommunicator::threadMainLoop()
{
- process(-1);
+ process();
return ILM_TRUE;
}
+int GenericCommunicator::getIterationCounter()
+{
+ return m_iterationCounter;
+}
+
t_ilm_const_string GenericCommunicator::pluginGetName() const
{
return "GenericCommunicator";
@@ -2576,16 +2589,6 @@ void GenericCommunicator::sendNotification(GraphicalObject* object, t_ilm_notifi
}
}
-HealthCondition GenericCommunicator::pluginGetHealth()
-{
- HealthCondition health = PluginBase::pluginGetHealth();
- if (0 != pthread_kill(mThreadId, 0))
- {
- health = HealthDead;
- }
- return health;
-}
-
void GenericCommunicator::SetOptimizationMode(t_ilm_message message)
{
t_ilm_message response;
diff --git a/LayerManagerPlugins/HealthMonitor/SystemdHealthMonitor/include/SystemdHealthMonitor.h b/LayerManagerPlugins/HealthMonitor/SystemdHealthMonitor/include/SystemdHealthMonitor.h
index 21eb536..9aa27e2 100644
--- a/LayerManagerPlugins/HealthMonitor/SystemdHealthMonitor/include/SystemdHealthMonitor.h
+++ b/LayerManagerPlugins/HealthMonitor/SystemdHealthMonitor/include/SystemdHealthMonitor.h
@@ -32,9 +32,11 @@ public:
// from IHealthMonitor
virtual t_ilm_bool start();
virtual t_ilm_bool stop();
+ virtual int getPluginReportIntervalInMs();
//from PluginBase
virtual t_ilm_const_string pluginGetName() const;
+ virtual int getIterationCounter();
private:
void reportStartupComplete();
@@ -48,6 +50,7 @@ private:
private:
int mIntervalInMs;
+ int m_iterationCounter;
};
#endif // __SYSTEMDHEALTHMONITOR_H__
diff --git a/LayerManagerPlugins/HealthMonitor/SystemdHealthMonitor/src/SystemdHealthMonitor.cpp b/LayerManagerPlugins/HealthMonitor/SystemdHealthMonitor/src/SystemdHealthMonitor.cpp
index f63cd88..d965d75 100644
--- a/LayerManagerPlugins/HealthMonitor/SystemdHealthMonitor/src/SystemdHealthMonitor.cpp
+++ b/LayerManagerPlugins/HealthMonitor/SystemdHealthMonitor/src/SystemdHealthMonitor.cpp
@@ -31,6 +31,7 @@ SystemdHealthMonitor::SystemdHealthMonitor(ICommandExecutor& executor, Configura
: IHealthMonitor(executor, config)
, PluginBase(executor, config, HealthMonitor_Api_v1)
, mIntervalInMs(-1)
+, m_iterationCounter(0)
{
char* envVar = getenv("WATCHDOG_USEC");
if (envVar)
@@ -94,12 +95,28 @@ bool SystemdHealthMonitor::watchdogEnabled()
t_ilm_bool SystemdHealthMonitor::threadMainLoop()
{
- if (watchdogEnabled() && PluginBase::mExecutor.getHealth())
+ if (watchdogEnabled() && PluginBase::mExecutor.getHealth() == HealthRunning)
{
+ ++m_iterationCounter;
signalWatchdog();
usleep(mIntervalInMs * 1000);
}
return ILM_TRUE;
}
+int SystemdHealthMonitor::getPluginReportIntervalInMs()
+{
+ int result = -1;
+ if (watchdogEnabled())
+ {
+ result = mIntervalInMs / 2;
+ }
+ return result;
+}
+
+int SystemdHealthMonitor::getIterationCounter()
+{
+ return m_iterationCounter;
+}
+
DECLARE_LAYERMANAGEMENT_PLUGIN(SystemdHealthMonitor)
diff --git a/LayerManagerPlugins/IpcModules/DbusIpcModule/src/message.c b/LayerManagerPlugins/IpcModules/DbusIpcModule/src/message.c
index 49da87d..5b23cb5 100644
--- a/LayerManagerPlugins/IpcModules/DbusIpcModule/src/message.c
+++ b/LayerManagerPlugins/IpcModules/DbusIpcModule/src/message.c
@@ -280,7 +280,7 @@ t_ilm_message receive(t_ilm_int timeoutInMs)
break;
case 0: /* timeout */
- gpIncomingMessage->type = IpcMessageTypeNone;
+ gpIncomingMessage->type = IpcMessageTypeTimeout;
break;
default: /* message or shutdown */
diff --git a/LayerManagerPlugins/Renderers/Base/include/BaseRenderer.h b/LayerManagerPlugins/Renderers/Base/include/BaseRenderer.h
index f900f60..fccf8cb 100644
--- a/LayerManagerPlugins/Renderers/Base/include/BaseRenderer.h
+++ b/LayerManagerPlugins/Renderers/Base/include/BaseRenderer.h
@@ -32,7 +32,7 @@ public:
BaseRenderer(ICommandExecutor& executor, Configuration& config);
virtual ~BaseRenderer();
- bool start(int, int, const char*) = 0;
+ bool start(int, int, const char*, int) = 0;
void stop() = 0;
void setdebug(bool onoff);
diff --git a/LayerManagerPlugins/Renderers/Base/src/BaseRenderer.cpp b/LayerManagerPlugins/Renderers/Base/src/BaseRenderer.cpp
index d8a738d..a889359 100644
--- a/LayerManagerPlugins/Renderers/Base/src/BaseRenderer.cpp
+++ b/LayerManagerPlugins/Renderers/Base/src/BaseRenderer.cpp
@@ -30,7 +30,6 @@ BaseRenderer::BaseRenderer(ICommandExecutor& executor, Configuration& config)
{
LOG_DEBUG("BaseRenderer", "Creating Renderer");
m_pInputManager = new InputManager(m_pScene);
- pluginSetHealth(HealthRunning);
}
BaseRenderer::~BaseRenderer()
@@ -39,7 +38,6 @@ BaseRenderer::~BaseRenderer()
{
delete m_pInputManager;
}
- pluginSetHealth(HealthStopped);
}
uint BaseRenderer::getLayerTypeCapabilities(LayerType layerType)
diff --git a/LayerManagerPlugins/Renderers/Graphic/include/WindowSystems/BaseWindowSystem.h b/LayerManagerPlugins/Renderers/Graphic/include/WindowSystems/BaseWindowSystem.h
index 536a946..6c5354d 100644
--- a/LayerManagerPlugins/Renderers/Graphic/include/WindowSystems/BaseWindowSystem.h
+++ b/LayerManagerPlugins/Renderers/Graphic/include/WindowSystems/BaseWindowSystem.h
@@ -39,7 +39,7 @@ public:
{
}
- virtual bool start() = 0;
+ virtual bool start(int maxIterationDurationInMS) = 0;
virtual void stop() = 0;
virtual void allocatePlatformSurface(Surface *surface) = 0;
virtual void doScreenShot(std::string fileName) = 0;
@@ -47,7 +47,6 @@ public:
virtual void doScreenShotOfSurface(std::string fileName, const uint id, const uint layer_id) = 0;
virtual void finishFrame() { }
- unsigned long int mThreadId; // TODO: remove
protected:
virtual void ClearDamage();
InputManager* m_pInputManager;
diff --git a/LayerManagerPlugins/Renderers/Graphic/include/WindowSystems/X11WindowSystem.h b/LayerManagerPlugins/Renderers/Graphic/include/WindowSystems/X11WindowSystem.h
index adb37e2..c52f2ad 100644
--- a/LayerManagerPlugins/Renderers/Graphic/include/WindowSystems/X11WindowSystem.h
+++ b/LayerManagerPlugins/Renderers/Graphic/include/WindowSystems/X11WindowSystem.h
@@ -51,7 +51,7 @@ public:
GetVisualInfoFunction func = X11WindowSystem::getDefaultVisual);
virtual ~X11WindowSystem();
bool init(BaseGraphicSystem<Display*, Window>* sys);
- bool start();
+ bool start(int maxIterationDurationInMS);
void stop();
static XVisualInfo * getDefaultVisual(Display *dpy);
void signalRedrawEvent();
@@ -65,6 +65,7 @@ public:
void doScreenShot(std::string fileName);
void doScreenShotOfLayer(std::string fileName, const uint id);
void doScreenShotOfSurface(std::string fileName, const uint id, const uint layer_id);
+ int getIterationCounter();
private:
ScreenShotType takeScreenshot;
std::string screenShotFile;
@@ -91,6 +92,8 @@ private:
bool m_success;
X11WindowSystemStates m_systemState;
const char* m_displayEnvironment;
+ int m_iterationCounter;
+ int m_maxIterationDurationInMS;
protected:
Display* x11Display;
diff --git a/LayerManagerPlugins/Renderers/Graphic/src/WindowSystems/X11WindowSystem.cpp b/LayerManagerPlugins/Renderers/Graphic/src/WindowSystems/X11WindowSystem.cpp
index 9189cfa..4668e41 100644
--- a/LayerManagerPlugins/Renderers/Graphic/src/WindowSystems/X11WindowSystem.cpp
+++ b/LayerManagerPlugins/Renderers/Graphic/src/WindowSystems/X11WindowSystem.cpp
@@ -69,6 +69,7 @@ X11WindowSystem::X11WindowSystem(const char* displayname,
, m_success(false)
, m_systemState(IDLE_STATE)
, m_displayEnvironment(NULL)
+, m_iterationCounter(0)
, x11Display(0)
, renderThread(0)
, windowWidth(width)
@@ -865,14 +866,40 @@ init_complete:
this->graphicSystem->swapBuffers();
XFlush(this->x11Display);
+ // variables required for blocking of file descriptor using select()
+ int x11FD = ConnectionNumber(this->x11Display);
+ fd_set x11FDS;
+
while (this->m_running)
{
- XEvent event;
- // blocking wait for event
- XNextEvent(this->x11Display, &event);
- this->m_pScene->lockScene();
- switch (event.type)
+ ++m_iterationCounter;
+
+ FD_ZERO(&x11FDS);
+ FD_SET(x11FD, &x11FDS);
+
+ if (m_maxIterationDurationInMS > 0)
{
+ if (0 == XPending(this->x11Display))
+ {
+ // wait for event on file descriptor with timeout
+ struct timeval timeout;
+ timeout.tv_sec = m_maxIterationDurationInMS / 1000;
+ timeout.tv_usec = (m_maxIterationDurationInMS % 1000) * 1000;
+
+ if (0 == select(x11FD + 1, &x11FDS, NULL, NULL, &timeout))
+ {
+ LOG_INFO("X11WindowSystem", "no renderer event for " << m_maxIterationDurationInMS << "ms, force wakeup for health monitoring");
+ continue;
+ }
+ }
+ }
+
+ XEvent event;
+ // blocking wait for event
+ XNextEvent(this->x11Display, &event);
+ this->m_pScene->lockScene();
+ switch (event.type)
+ {
case CreateNotify:
{
if (this->debugMode)
@@ -1162,16 +1189,15 @@ bool X11WindowSystem::init(BaseGraphicSystem<Display*, Window>* base)
pthread_mutex_unlock(&init_lock);
return false;
}
- mThreadId = renderThread;
-
pthread_cond_wait(&init_condition, &init_lock);
pthread_mutex_unlock(&init_lock);
LOG_INFO("X11WindowSystem", "Initialization complete success :" << m_success);
return m_success;
}
-bool X11WindowSystem::start()
+bool X11WindowSystem::start(int maxIterationDurationInMS)
{
+ m_maxIterationDurationInMS = maxIterationDurationInMS;
bool result = true;
pthread_mutex_lock(&this->run_lock);
LOG_DEBUG("X11WindowSystem", "Startup");
@@ -1260,6 +1286,10 @@ void X11WindowSystem::doScreenShotOfSurface(std::string fileName, const uint id,
screenShotLayerID = layer_id;
}
+int X11WindowSystem::getIterationCounter()
+{
+ return m_iterationCounter;
+}
/**
diff --git a/LayerManagerPlugins/Renderers/Platform/X11GLESRenderer/include/X11GLESRenderer.h b/LayerManagerPlugins/Renderers/Platform/X11GLESRenderer/include/X11GLESRenderer.h
index bb56cff..7d97679 100644
--- a/LayerManagerPlugins/Renderers/Platform/X11GLESRenderer/include/X11GLESRenderer.h
+++ b/LayerManagerPlugins/Renderers/Platform/X11GLESRenderer/include/X11GLESRenderer.h
@@ -30,7 +30,7 @@ class X11GLESRenderer : public BaseRenderer
{
public:
X11GLESRenderer(ICommandExecutor& executor, Configuration& config);
- bool start(int, int, const char*);
+ bool start(int, int, const char*, int);
void stop();
void doScreenShot(std::string fileToSave);
void doScreenShotOfLayer(std::string fileToSave, uint id);
@@ -43,9 +43,9 @@ public:
Shader* createShader(const string* vertexName, const string* fragmentName);
virtual bool setOptimizationMode(OptimizationType id, OptimizationModeType mode);
virtual bool getOptimizationMode(OptimizationType id, OptimizationModeType *mode);
+ virtual int getIterationCounter();
// from PluginBase
- virtual HealthCondition pluginGetHealth();
virtual t_ilm_const_string pluginGetName() const;
private:
@@ -54,6 +54,7 @@ private:
uint m_width;
uint m_height;
ITextureBinder* m_binder;
+ int m_maxIterationDurationInMS;
};
#endif /* _X11GLESRENDERER_H_*/
diff --git a/LayerManagerPlugins/Renderers/Platform/X11GLESRenderer/src/X11GLESRenderer.cpp b/LayerManagerPlugins/Renderers/Platform/X11GLESRenderer/src/X11GLESRenderer.cpp
index 0f546ff..1b55ad4 100644
--- a/LayerManagerPlugins/Renderers/Platform/X11GLESRenderer/src/X11GLESRenderer.cpp
+++ b/LayerManagerPlugins/Renderers/Platform/X11GLESRenderer/src/X11GLESRenderer.cpp
@@ -38,7 +38,7 @@ X11GLESRenderer::X11GLESRenderer(ICommandExecutor& executor, Configuration& conf
LOG_DEBUG("X11GLESRenderer", "Creating Renderer");
}
-bool X11GLESRenderer::start(int width, int height, const char* displayname)
+bool X11GLESRenderer::start(int width, int height, const char* displayname, int maxIterationDurationInMS)
{
Display* nativeDisplayHandle = NULL;
EGLDisplay eglDisplayhandle = NULL;
@@ -82,7 +82,7 @@ bool X11GLESRenderer::start(int width, int height, const char* displayname)
{
m_pGraphicSystem->setTextureBinder(m_binder);
- if (!m_pWindowSystem->start())
+ if (!m_pWindowSystem->start(maxIterationDurationInMS))
{
goto fail; // TODO bad style
}
@@ -201,14 +201,9 @@ Shader* X11GLESRenderer::createShader(const string* vertexName, const string* fr
return result;
}
-HealthCondition X11GLESRenderer::pluginGetHealth()
+int X11GLESRenderer::getIterationCounter()
{
- HealthCondition health = PluginBase::pluginGetHealth();
- if (0 != pthread_kill(m_pWindowSystem->mThreadId, 0))
- {
- health = HealthDead;
- }
- return health;
+ return m_pWindowSystem->getIterationCounter();
}
DECLARE_LAYERMANAGEMENT_PLUGIN(X11GLESRenderer)
diff --git a/LayerManagerPlugins/SceneProvider/ExampleSceneProvider/include/ExampleSceneProvider.h b/LayerManagerPlugins/SceneProvider/ExampleSceneProvider/include/ExampleSceneProvider.h
index 3878c61..12ae532 100644
--- a/LayerManagerPlugins/SceneProvider/ExampleSceneProvider/include/ExampleSceneProvider.h
+++ b/LayerManagerPlugins/SceneProvider/ExampleSceneProvider/include/ExampleSceneProvider.h
@@ -41,6 +41,7 @@ public:
//from PluginBase
virtual t_ilm_const_string pluginGetName() const;
+ virtual int getIterationCounter();
protected:
ICommandExecutor& mExecutor;
diff --git a/LayerManagerPlugins/SceneProvider/ExampleSceneProvider/src/ExampleSceneProvider.cpp b/LayerManagerPlugins/SceneProvider/ExampleSceneProvider/src/ExampleSceneProvider.cpp
index cf548e3..9e02d03 100644
--- a/LayerManagerPlugins/SceneProvider/ExampleSceneProvider/src/ExampleSceneProvider.cpp
+++ b/LayerManagerPlugins/SceneProvider/ExampleSceneProvider/src/ExampleSceneProvider.cpp
@@ -148,4 +148,11 @@ t_ilm_const_string ExampleSceneProvider::pluginGetName() const
return "ExampleSceneProvider";
}
+int ExampleSceneProvider::getIterationCounter()
+{
+ // this plugin is one-shot and is not monitored.
+ static int dummyValue = 0;
+ return ++dummyValue;
+}
+
DECLARE_LAYERMANAGEMENT_PLUGIN(ExampleSceneProvider)