From ac6fcda1795157fb47f65376764ddfe606ce3035 Mon Sep 17 00:00:00 2001
From: Maxime Graulich <maxime.graulich@gmail.com>
Date: Wed, 17 Dec 2014 17:09:28 +0000
Subject: [PATCH] ONELAB2: multi-thread for FLTK when server is remote

---
 contrib/onelab2/GmshNetworkClient.cpp | 48 +++++++++++++++++++++++++--
 contrib/onelab2/GmshNetworkClient.h   |  1 +
 contrib/onelab2/OnelabDatabase.cpp    |  5 ++-
 contrib/onelab2/OnelabDatabase.h      | 30 ++++++++---------
 4 files changed, 64 insertions(+), 20 deletions(-)

diff --git a/contrib/onelab2/GmshNetworkClient.cpp b/contrib/onelab2/GmshNetworkClient.cpp
index 71b5a6fed1..93f7f7e956 100644
--- a/contrib/onelab2/GmshNetworkClient.cpp
+++ b/contrib/onelab2/GmshNetworkClient.cpp
@@ -3,9 +3,51 @@
 #include "GmshNetworkClient.h"
 #ifdef HAVE_FLTK
 #include "onelab2Group.h"
+#include "GmshMessage.h"
 
 void GmshNetworkClient::setCallback(onelabGroup *cb) {_cb_obj = cb;}
-void GmshNetworkClient::onNewParameter(onelab::parameter *p){if(_cb_obj) _cb_obj->addParameter(*p);}
-void GmshNetworkClient::onUpdateParameter(onelab::parameter *p){if(_cb_obj) _cb_obj->updateParameter(*p);}
-void GmshNetworkClient::onRemoveParameter(onelab::parameter *p){if(_cb_obj) _cb_obj->removeParameter(*p);}
+void GmshNetworkClient::onNewParameter(onelab::parameter *p)
+{
+  if(_cb_obj) {
+    Fl::lock();
+    _cb_obj->addParameter(*p);
+    Fl::unlock();
+  }
+  Fl::awake((void *)NULL);
+}
+void GmshNetworkClient::onUpdateParameter(onelab::parameter *p)
+{
+  if(_cb_obj) {
+    Fl::lock();
+    _cb_obj->updateParameter(*p);
+    Fl::unlock();
+  }
+  Fl::awake((void *)NULL);
+}
+void GmshNetworkClient::onRemoveParameter(onelab::parameter *p)
+{
+  if(_cb_obj) {
+    Fl::lock();
+    _cb_obj->removeParameter(*p);
+    Fl::unlock();
+  }
+  Fl::awake((void *)NULL);
+}
+void GmshNetworkClient::onMessage(const std::string & name, const std::string &message, int level)
+{
+  Fl::lock();
+  switch(level) {
+    case OnelabAttrMessage::Info:
+      Msg::Direct("Info    : %s - %s", name.c_str(), message.c_str());
+      break;
+    case OnelabAttrMessage::Warning:
+      Msg::Warning("%s - %s", name.c_str(), message.c_str());
+      break;
+    case OnelabAttrMessage::Error:
+      Msg::Error("%s - %s", name.c_str(), message.c_str());
+      break;
+  }
+  Fl::unlock();
+  Fl::awake((void *)NULL);
+}
 #endif
diff --git a/contrib/onelab2/GmshNetworkClient.h b/contrib/onelab2/GmshNetworkClient.h
index 3ba86cd6ba..8af71336b7 100644
--- a/contrib/onelab2/GmshNetworkClient.h
+++ b/contrib/onelab2/GmshNetworkClient.h
@@ -26,6 +26,7 @@ public:
 	void onNewParameter(onelab::parameter *p);
   void onUpdateParameter(onelab::parameter *p);
   void onRemoveParameter(onelab::parameter *p);
+  void onMessage(const std::string &name, const std::string &message, int level);
 #else
 	GmshNetworkClient(std::string name) : OnelabNetworkClient(name) {}
 	GmshNetworkClient(std::string name, unsigned int ip, unsigned short port) : OnelabNetworkClient(name, ip, port) {}
diff --git a/contrib/onelab2/OnelabDatabase.cpp b/contrib/onelab2/OnelabDatabase.cpp
index 8ff5dd031a..ea4d7a6991 100644
--- a/contrib/onelab2/OnelabDatabase.cpp
+++ b/contrib/onelab2/OnelabDatabase.cpp
@@ -22,7 +22,10 @@ DWORD WINAPI OnelabDatabase_listen(LPVOID arg)
         OnelabDatabase::instance()->networkClientHaveToStop(true);
         return NULL;
       case OnelabProtocol::OnelabMessage:
-        Msg::Info("Message from onelab"); // TODO
+        if(msg.attrs.size()==1 && msg.attrs[0]->getAttributeType() == OnelabAttrMessage::attributeType()) {
+          OnelabNetworkClient *gui = OnelabDatabase::instance()->getNetworkClient();
+          if(gui) gui->onMessage("Server", ((OnelabAttrMessage *)msg.attrs[0])->getMessage(), ((OnelabAttrMessage *)msg.attrs[0])->getLevel());
+        }
         break;
       case OnelabProtocol::OnelabResponse:
       case OnelabProtocol::OnelabUpdate:
diff --git a/contrib/onelab2/OnelabDatabase.h b/contrib/onelab2/OnelabDatabase.h
index 5e7db5312a..011ea82958 100644
--- a/contrib/onelab2/OnelabDatabase.h
+++ b/contrib/onelab2/OnelabDatabase.h
@@ -93,6 +93,8 @@ public:
         return _client;
       }
       else {
+        delete _client;
+        _client = NULL;
         return NULL;
       }
     }
@@ -106,6 +108,7 @@ public:
     }
     return NULL;
   }
+  GmshNetworkClient *getNetworkClient(){return _client;}
   void networkClientHaveToStop(bool haveToStop) {_haveToStop = haveToStop;}
   bool networkClientHaveToStop() {return _haveToStop;}
   void haveToDo(const std::string action) {_action = action;}
@@ -163,10 +166,6 @@ public:
     OnelabProtocol msg(OnelabProtocol::OnelabAction);
     if(client.size()) {
       std::cout << "try to " << action << ' ' << client <<  std::endl;
-      onelab::string o(client + "/Action", action);
-      o.setVisible(false);
-      o.setNeverChanged(true);
-      set(o);
       if(_client && ((OnelabLocalClient *)_client)->getName() == client) {
         if(client == "Gmsh") onelabUtils::runGmshClient(action, true);
       }
@@ -188,22 +187,21 @@ public:
       run(action, "Gmsh");
 
       // iterate over all other clients
-      std::string solver = "";
-      if(CTX::instance()->solverToRun >= 0) solver = opt_solver_name(CTX::instance()->solverToRun, GMSH_GET, "");
-      if(_client) {
-        std::cout << "server is remote" << std::endl;
-        if(CTX::instance()->solverToRun >= 0) run(action, solver);
-        else {
+      if(CTX::instance()->solverToRun >= 0) {
+        std::string solver = opt_solver_name(CTX::instance()->solverToRun, GMSH_GET, "");
+        run(action, solver);
+      }
+      else {
+        if(_client) {
+          std::cout << "server is remote" << std::endl;
           msg.attrs.push_back(new OnelabAttrAction(action, client));
           int size = msg.encodeMsg(buff, 1024);
           sendbytes(buff, size);
         }
-        return true;
-      }
-      else {
-        std::cout << "server is local" << std::endl;
-        if(CTX::instance()->solverToRun >= 0) OnelabServer::instance()->performAction(action, solver);
-        else OnelabServer::instance()->performAction(action, client);
+        else {
+          std::cout << "server is local" << std::endl;
+          OnelabServer::instance()->performAction(action, client);
+        }
         return true;
       }
     }
-- 
GitLab