This commit is contained in:
maliakal_d 2019-06-12 10:40:56 +02:00
parent b922b79232
commit afb6d6bf3a
5 changed files with 141 additions and 129 deletions

View File

@ -65,9 +65,11 @@ set(HEADERS
include/qTabDebugging.h include/qTabDebugging.h
include/qTabDeveloper.h include/qTabDeveloper.h
include/qTabMessages.h include/qTabMessages.h
../slsSupportLib/include/versionAPI.h
include/qServer.h include/qServer.h
../slsDetectorSoftware/include ../slsDetectorSoftware/include
../slsSupportLib/include/versionAPI.h
../slsSupportLib/include/ServerSocket.h
../slsSupportLib/include/ServerInterface2.h
) )
set(RESOURCES set(RESOURCES
include/icons.qrc include/icons.qrc

View File

@ -20,6 +20,28 @@ class qDefs : public QWidget {
#define GOODBYE -200 #define GOODBYE -200
/** function enums */
enum qFuncNames {
QF_GET_DETECTOR_STATUS,
QF_START_ACQUISITION,
QF_STOP_ACQUISITION,
QF_START_AND_READ_ALL,
QF_EXIT_SERVER,
QF_NUM_FUNCTIONS
};
const char* getQFunctionNameFromEnum(enum qFuncNames func) {
switch (func) {
case QF_GET_DETECTOR_STATUS: return "QF_GET_DETECTOR_STATUS";
case QF_START_ACQUISITION: return "QF_START_ACQUISITION";
case QF_STOP_ACQUISITION: return "QF_STOP_ACQUISITION";
case QF_START_AND_READ_ALL: return "QF_START_AND_READ_ALL";
case QF_EXIT_SERVER: return "QF_EXIT_SERVER";
case QF_NUM_FUNCTIONS: return "QF_NUM_FUNCTIONS";
default: return "Unknown Function";
}
};
/** Success or FAIL */ /** Success or FAIL */
enum { OK, FAIL }; enum { OK, FAIL };

View File

@ -1,14 +1,14 @@
#pragma once #pragma once
#include "qDefs.h"
#include "ServerSocket.h"
class qDetectorMain; class qDetectorMain;
class ServerInterface2;
class multiSlsDetector;
class ServerSocket;
class ServerInterface;
#include <vector> #include <vector>
#include <future>
class qServer : public QWidget, public virtual slsDetectorDefs { class qServer : public QWidget {
Q_OBJECT Q_OBJECT
public: public:
@ -19,26 +19,24 @@ class qServer : public QWidget, public virtual slsDetectorDefs {
private: private:
void FunctionTable(); void FunctionTable();
void DecodeFunction(ServerSocket *sock); void DecodeFunction(sls::ServerInterface2 *socket);
void ShutDownSockets(); void ServerThread(bool isControlServer);
void ServerThread(ServerSocket* sock); void GetStatus(sls::ServerInterface2* socket);
void GetStatus(ServerSocket* sock); void StartAcquisition(sls::ServerInterface2* socket);
void StartAcquisition(ServerSocket* sock); void StopsAcquisition(sls::ServerInterface2* socket);
void StopsAcquisition(ServerSocket* sock); void Acquire(sls::ServerInterface2* socket);
void Acquire(ServerSocket* sock); void ExitServer(sls::ServerInterface2* socket);
void ExitServer(ServerSocket* sock);
/** function list */
typedef int (qServer::*some_func_t)(ServerSocket*);
typedef std::vector<some_func_t> sflist;
bool guiServerRunning;
bool threadStarted;
void (qServer::*flist[qDefs::QF_NUM_FUNCTIONS])(sls::ServerInterface2 &socket);
qDetectorMain *mainTab; qDetectorMain *mainTab;
bool tcpThreadCreated{false};
bool killTCPServerThread{false};
std::future<void> controlStatus;
std::future<void> stopStatus;
int controlPort; int controlPort;
int stopPort; int stopPort;
ServerSocket *controlSocket; std::unique_ptr<sls::ServerSocket> controlSocket{nullptr};
ServerSocket *stopSocket; std::unique_ptr<sls::ServerSocket> stopSocket{nullptr};
signals: signals:
// to update the Listening to Gui check box // to update the Listening to Gui check box

View File

@ -1,8 +1,7 @@
#include "qServer.h" #include "qServer.h"
#include "qDefs.h"
#include "qDetectorMain.h" #include "qDetectorMain.h"
#include "ServerSocket.h" #include "ServerInterface2.h"
#include "string_utils.h" #include "string_utils.h"
#include <iostream> #include <iostream>
@ -10,8 +9,7 @@
#include <future> #include <future>
qServer::qServer(qDetectorMain *t) qServer::qServer(qDetectorMain *t)
: guiServerRunning(false), threadStarted(false), mainTab(t), : mainTab(t), controlPort(DEFAULT_GUI_PORTNO), stopPort(DEFAULT_GUI_PORTNO + 1),
controlPort(DEFAULT_GUI_PORTNO), stopPort(DEFAULT_GUI_PORTNO + 1),
controlSocket(nullptr), stopSocket(nullptr) { controlSocket(nullptr), stopSocket(nullptr) {
FILE_LOG(logDEBUG) << "Client Server ready"; FILE_LOG(logDEBUG) << "Client Server ready";
} }
@ -19,107 +17,106 @@ qServer::qServer(qDetectorMain *t)
qServer::~qServer() {} qServer::~qServer() {}
void qServer::FunctionTable() { void qServer::FunctionTable() {
sflist.push_back(&qServer::GetStatus); flist[qDefs::QF_GET_DETECTOR_STATUS] = &qServer::GetStatus;
sflist.push_back(&qServer::StartAcquisition); flist[qDefs::QF_START_ACQUISITION] = &qServer::StartAcquisition;
sflist.push_back(&qServer::StopsAcquisition); flist[qDefs::QF_STOP_ACQUISITION] = &qServer::StopsAcquisition;
sflist.push_back(&qServer::Acquire); flist[qDefs::QF_START_AND_READ_ALL] = &qServer::Acquire;
sflist.push_back(&qServer::ExitServer); flist[qDefs::QF_EXIT_SERVER] = &qServer::ExitServer;
} }
int qServer::DecodeFunction(ServerSocket *sock) { void qServer::DecodeFunction(sls::ServerInterface2 *socket) {
int ret = qDefs::FAIL; qFuncNames fnum;
int fnum = 0; socket.Receive(fnum);
int n = sock->ReceiveDataOnly(&fnum, sizeof(fnum));
if (n <= 0) { if (fnum < 0 || fnum >= QF_NUM_FUNCTIONS) {
FILE_LOG(logDEBUG3) << "Received " << n << " bytes"; throw RuntimeError("Unrecognized Function enum " + std::to_string(fnum) + "\n");
throw sls::RuntimeError("Could not read socket");
} }
// unrecognized function FILE_LOG(logDEBUG1) << "calling function fnum: " << fnum << " ("
if (fnum < 0 && fnum >= qDefs::NUM_GUI_FUNCS) { << slsDetectorDefs::getQFunctionNameFromEnum(fnum) << ")";
ret = qDefs::FAIL; (this->*flist[fnum])(socket);
char mess[MAX_STR_LENGTH] = {}; FILE_LOG(logDEBUG1) << "Function " << getQFunctionNameFromEnum(fnum) << " finished";
sls::strcpy_safe(mess, "Unrecognized function");
// will throw an exception
sock->SendResult(ret, nullptr, 0, mess);
}
// calling function
FILE_LOG(logDEBUG1) << "calling function fnum: " << fnum;
ret = (this->*sflist[fnum])(sock);
return ret;
}
void qServer::ShutDownSockets() {
guiServerRunning = false;
if (controlSocket) {
controlSocket->shutDownSocket();
delete controlSocket;
controlSocket = nullptr;
}
if (stopSocket) {
stopSocket->shutDownSocket();
delete stopSocket;
stopSocket = nullptr;
}
} }
void qServer::CreateServers() { void qServer::CreateServers() {
if (!guiServerRunning) { if (!tcpThreadCreated) {
FILE_LOG(logINFO) << "Starting Gui Servers"; FILE_LOG(logINFO) << "Starting Gui Servers";
guiServerRunning = true; tcpThreadCreated = true;
try { try {
// start control server // start control server
controlSocket = new ServerSocket(controlPort); controlStatus = std::async(std::launch::async, ServerThread, true);
std::async(std::launch::async, ServerThread, controlSocket); FILE_LOG(logDEBUG) << "Gui control server thread created successfully.";
FILE_LOG(logDEBUG)
<< "Gui control server thread created successfully.";
// start stop server // start stop server
stopSocket = new ServerSocket(stopPort); stopStatus = std::async(std::launch::async, ServerThread, false);
std::async(std::launch::async, ServerThread, stopSocket); FILE_LOG(logDEBUG) << "Gui stop server thread created successfully.";
FILE_LOG(logDEBUG)
<< "Gui stop server thread created successfully.";
} catch (...) { } catch (...) {
ShutDownSockets(); std::string mess = "Could not create Gui TCP servers";
std::string message = "Can't create gui control server thread"; FILE_LOG(logERROR) << mess;
FILE_LOG(logERROR) << message;
qDefs::Message(qDefs::WARNING, message, "qServer::CreateServers"); qDefs::Message(qDefs::WARNING, message, "qServer::CreateServers");
DestroyServers();
} }
} }
} }
void qServer::DestroyServers() { void qServer::DestroyServers() {
if (guiServerRunning) { if (tcpThreadCreated) {
FILE_LOG(logINFO) << "Stopping Gui Servers"; FILE_LOG(logINFO) << "Shutting down Gui TCP Sockets";
ShutDownSockets(); killTCPServerThread = true;
if (controlSocket)
controlSocket->shutDownSocket();
if (stopSocket)
stopSocket->shutDownSocket();
controlStatus.wait();
stopStatus.wait();
tcpThreadCreated = false;
killTCPServerThread = false;
FILE_LOG(logDEBUG) << "Server threads stopped successfully."; FILE_LOG(logDEBUG) << "Server threads stopped successfully.";
} }
} }
void qServer::ServerThread(ServerSocket* sock) { void qServer::ServerThread(isControlServer) {
FILE_LOG(logDEBUG) << "Starting Gui Server at port " << sock->getPort(); sls::ServerSocket* sock = nullptr;
if (isControl) {
FILE_LOG(logDEBUG) << "Starting Gui Server (Control port: " << controlPort << ")";
controlSocket = sls::make_unique<sls::ServerSocket>(controlPort);
sock = controlSocket;
} else {
FILE_LOG(logDEBUG) << "Starting Gui Server (Stop port: " << stopPort << ")";
stopSocket = sls::make_unique<sls::ServerSocket>(stopPort);
sock = stopSocket;
}
while (guiServerRunning)) { while (true) {
try{ try{
sock->accept(); auto socket = sock->accept();
if (DecodeFunction(sock) == GOODBYE) { try{
guiServerRunning = false; decode_function(socket);
} catch(const sls::NonCriticalError &e) {
if (strstr(e.what(), "exit")) {
FILE_LOG(logINFO) << "Exiting " << (isControlServer ? "Control" : "Stop") << "Server";
break;
} }
sock->close(); char mess[MAX_STR_LENGTH];
sls::strcpy_safe(mess, e.what());
socket.Send(FAIL);
socket.Send(mess);
}
} catch (const sls::NonCriticalError &e) {
FILE_LOG(logERROR) << "Accept failed";
}
// Destroy server
if (killTCPServerThread) {
FILE_LOG(logINFO) << "Exiting " << (isControlServer ? "Control" : "Stop") << "Server";
break;
} }
// any fails will throw an exception, which will be displayed at client side. Ignore here
catch (...) {}
} }
FILE_LOG(logDEBUG) << "Stopped gui server thread"; FILE_LOG(logDEBUG) << "Stopped gui server thread";
// stop port is closed last
if (sock->getPort() == stopPort)
emit ServerStoppedSignal();
} }
int qServer::GetStatus(ServerSocket* sock) { void qServer::GetStatus(sls::ServerInterface2* socket) {
slsDetectorDefs::runStatus status = slsDetectorDefs::ERROR; slsDetectorDefs::runStatus status = slsDetectorDefs::ERROR;
int progress = 0; int progress = 0;
if (myMainTab->isPlotRunning()) if (myMainTab->isPlotRunning())
@ -129,43 +126,36 @@ int qServer::GetStatus(ServerSocket* sock) {
progress = myMainTab->GetProgress(); progress = myMainTab->GetProgress();
int ret = qDefs::OK int retvals[2] = {static_cast<int>(status), progress};
int retvals[2] = {static_cast<int>(retval), progress}; socket.SendResult(retvals);
sock->SendResult(ret, retvals, sizeof(retvals), nullptr);
return ret;
} }
int qServer::StartAcquisition(ServerSocket* sock) { void qServer::StartAcquisition(sls::ServerInterface2* socket) {
char mess[MAX_STR_LENGTH] = {}; if (myMainTab->StartStopAcquisitionFromClient(true) == slsDetectorDefs::FAIL) {
sls::strcpy_safe(mess, "Could not start acquistion in Gui"); throw sls::NonCriticalError("Could not start acquistion in Gui");
int ret = myMainTab->StartStopAcquisitionFromClient(true); }
sock->SendResult(ret, nullptr, 0, mess); socket.Send(slsDetectorDefs::OK);
return ret;
} }
int qServer::StopsAcquisition(ServerSocket* sock) { void qServer::StopsAcquisition(sls::ServerInterface2* socket) {
char mess[MAX_STR_LENGTH] = {}; if (myMainTab->StartStopAcquisitionFromClient(false) == slsDetectorDefs::FAIL) {
sls::strcpy_safe(mess, "Could not stop acquistion in Gui"); throw sls::NonCriticalError("Could not stop acquistion in Gui");
int ret = myMainTab->StartStopAcquisitionFromClient(false); }
sock->SendResult(ret, nullptr, 0, mess); socket.Send(slsDetectorDefs::OK);
return ret;
} }
int qServer::Acquire(ServerSocket* sock) { void qServer::Acquire(sls::ServerInterface2* socket) {
char mess[MAX_STR_LENGTH] = {}; if (myMainTab->StartStopAcquisitionFromClient(true) == slsDetectorDefs::FAIL) {
sls::strcpy_safe(mess, "Could not start blocking acquistion in Gui"); throw sls::NonCriticalError("Could not start blocking acquistion in Gui");
int ret = myMainTab->StartStopAcquisitionFromClient(true); }
// blocking // blocking
usleep(5000); usleep(5000);
while (myMainTab->isPlotRunning()) while (myMainTab->isPlotRunning()) {
; usleep(5000);
sock->SendResult(ret, nullptr, 0, mess); }
return ret; socket.Send(slsDetectorDefs::OK);
} }
int qServer::ExitServer(ServerSocket* sock) { void qServer::ExitServer(sls::ServerInterface2* socket) {
DestroyServers(); throw sls::NonCriticalError("Server exited");
int ret = qDefs::OK;
sock->SendResult(ret, nullptr, 0, mess);
return GOODBYE;
} }

View File

@ -128,7 +128,7 @@ void slsReceiverTCPIPInterface::startTCPServer() {
pthread_exit(nullptr); pthread_exit(nullptr);
} }
} catch (const RuntimeError &e) { } catch (const RuntimeError &e) {
std::cout << "Accept failed\n"; FILE_LOG(logERROR) << "Accept failed";
} }
// if user entered exit // if user entered exit