moved detectors and zmqSocket to unique pointers

This commit is contained in:
Erik Frojdh 2018-10-10 11:55:37 +02:00
parent 9ca163dfc9
commit d685cb8ff4
3 changed files with 55 additions and 60 deletions

View File

@ -57,15 +57,6 @@ multiSlsDetector::multiSlsDetector(int id, bool verify, bool update)
multiSlsDetector::~multiSlsDetector() { multiSlsDetector::~multiSlsDetector() {
// delete zmq sockets first
for (auto* it : zmqSocket)
delete it;
zmqSocket.clear();
for (auto* it : detectors)
delete it;
detectors.clear();
if (sharedMemory) { if (sharedMemory) {
sharedMemory->UnmapSharedMemory(thisMultiDetector); sharedMemory->UnmapSharedMemory(thisMultiDetector);
delete sharedMemory; delete sharedMemory;
@ -87,8 +78,8 @@ template <typename RT, typename... CT>
std::vector<RT> multiSlsDetector::serialCall(RT (slsDetector::*somefunc)(CT...), CT... Args) std::vector<RT> multiSlsDetector::serialCall(RT (slsDetector::*somefunc)(CT...), CT... Args)
{ {
std::vector<RT> result; std::vector<RT> result;
for (size_t idet = 0; idet < detectors.size(); ++idet) { for (auto& d: detectors) {
result.push_back(((*this)[idet]->*somefunc)(Args...)); result.push_back((d.get()->*somefunc)(Args...));
/* /*
if ((*this)[idet]->getErrorMask()) if ((*this)[idet]->getErrorMask())
setErrorMask(getErrorMask() | (1 << idet)); setErrorMask(getErrorMask() | (1 << idet));
@ -101,8 +92,8 @@ template <typename RT, typename... CT>
std::vector<RT> multiSlsDetector::parallelCall(RT (slsDetector::*somefunc)(CT...), CT... Args) std::vector<RT> multiSlsDetector::parallelCall(RT (slsDetector::*somefunc)(CT...), CT... Args)
{ {
std::vector<std::future<RT>> futures; std::vector<std::future<RT>> futures;
for (size_t idet = 0; idet < detectors.size(); ++idet) { for (auto &d : detectors) {
futures.push_back(std::async(std::launch::async, somefunc, (*this)[idet], Args...)); futures.push_back(std::async(std::launch::async, somefunc, d.get(), Args...));
/* /*
if ((*this)[idet]->getErrorMask()) if ((*this)[idet]->getErrorMask())
setErrorMask(getErrorMask() | (1 << idet)); setErrorMask(getErrorMask() | (1 << idet));
@ -118,11 +109,11 @@ std::vector<RT> multiSlsDetector::parallelCall(RT (slsDetector::*somefunc)(CT...
std::string multiSlsDetector::concatResultOrPos(std::string (slsDetector::*somefunc)(int), int pos) { std::string multiSlsDetector::concatResultOrPos(std::string (slsDetector::*somefunc)(int), int pos) {
if (pos >= 0 && pos < (int)detectors.size()) { if (pos >= 0 && pos < (int)detectors.size()) {
return (detectors[pos]->*somefunc)(pos); return (detectors[pos].get()->*somefunc)(pos);
} else { } else {
std::string s; std::string s;
for (auto* it : detectors) { for (auto& d : detectors) {
s += (it->*somefunc)(pos) + "+"; s += (d.get()->*somefunc)(pos) + "+";
} }
return s; return s;
} }
@ -239,8 +230,8 @@ int64_t multiSlsDetector::clearAllErrorMask(int detPos) {
// multi // multi
clearErrorMask(); clearErrorMask();
clearNotAddedList(); clearNotAddedList();
for (auto* it : detectors) for (auto& d : detectors)
it->clearErrorMask(); d->clearErrorMask();
return getErrorMask(); return getErrorMask();
} }
@ -300,19 +291,19 @@ int64_t multiSlsDetector::getId(idMode mode, int detPos) {
slsDetector* multiSlsDetector::getSlsDetector(int detPos) { slsDetector* multiSlsDetector::getSlsDetector(int detPos) {
return detectors[detPos]; return detectors[detPos].get();
} }
slsDetector *multiSlsDetector::operator()(int detPos) const { slsDetector *multiSlsDetector::operator()(int detPos) const {
return detectors[detPos]; return detectors[detPos].get();
} }
slsDetector* multiSlsDetector::operator[](int detPos) const { slsDetector* multiSlsDetector::operator[](int detPos) const {
//Providing access to detectors with range checking //Providing access to detectors with range checking
//throw exception if out of range //throw exception if out of range
if (detPos >= 0 && detPos < (int)detectors.size()) if (detPos >= 0 && detPos < (int)detectors.size())
return detectors[detPos]; return detectors[detPos].get();
else else
throw(std::range_error("Detector does not exist")); throw(std::range_error("Detector does not exist"));
} }
@ -357,17 +348,14 @@ void multiSlsDetector::freeSharedMemory(int detPos) {
// multi // multi
// clear zmq vector // clear zmq vector
for (auto* it : zmqSocket)
delete it;
zmqSocket.clear(); zmqSocket.clear();
// should be done before the detector list is deleted // should be done before the detector list is deleted
clearAllErrorMask(); clearAllErrorMask();
// clear sls detector vector shm // clear sls detector vector shm
for (auto* it : detectors) { for (auto& d : detectors) {
it->freeSharedMemory(); d->freeSharedMemory();
delete it;
} }
detectors.clear(); detectors.clear();
@ -399,8 +387,8 @@ std::string multiSlsDetector::getUserDetails() {
//type //type
sstream<< "\nType: "; sstream<< "\nType: ";
for (auto* it : detectors) { for (auto& d : detectors) {
sstream<< it->sgetDetectorsType() << "+"; sstream<< d->sgetDetectorsType() << "+";
} }
//PID //PID
@ -485,19 +473,13 @@ void multiSlsDetector::initializeDetectorStructure() {
void multiSlsDetector::initializeMembers(bool verify) { void multiSlsDetector::initializeMembers(bool verify) {
//multiSlsDetector //multiSlsDetector
for (auto* it : zmqSocket)
delete it;
zmqSocket.clear(); zmqSocket.clear();
// get objects from single det shared memory (open) // get objects from single det shared memory (open)
for (int i = 0; i < thisMultiDetector->numberOfDetectors; i++) { for (int i = 0; i < thisMultiDetector->numberOfDetectors; i++) {
try { try {
slsDetector* sdet = new slsDetector(detId, i, verify); detectors.push_back(sls::make_unique<slsDetector>(detId, i, verify));
detectors.push_back(sdet);
} catch (...) { } catch (...) {
// clear detectors list
for (auto* it : detectors)
delete it;
detectors.clear(); detectors.clear();
throw; throw;
} }
@ -602,8 +584,8 @@ void multiSlsDetector::addSlsDetector (std::string s) {
#ifdef VERBOSE #ifdef VERBOSE
std::cout << "Adding detector " << s << std::endl; std::cout << "Adding detector " << s << std::endl;
#endif #endif
for (auto* it : detectors) { for (auto& d : detectors) {
if (it->getHostname() == s) { if (d->getHostname() == s) {
std::cout << "Detector " << s << "already part of the multiDetector!" << std::endl std::cout << "Detector " << s << "already part of the multiDetector!" << std::endl
<< "Remove it before adding it back in a new position!" << std::endl; << "Remove it before adding it back in a new position!" << std::endl;
return; return;
@ -625,8 +607,11 @@ void multiSlsDetector::addSlsDetector (std::string s) {
int pos = (int)detectors.size(); int pos = (int)detectors.size();
slsDetector* sdet = new slsDetector(type, detId, pos, false); // slsDetector* sdet = new slsDetector(type, detId, pos, false);
detectors.push_back(sdet); // detectors.push_back(sdet);
detectors.push_back(sls::make_unique<slsDetector>(type, detId, pos, false));
thisMultiDetector->numberOfDetectors = detectors.size(); thisMultiDetector->numberOfDetectors = detectors.size();
detectors[pos]->setHostname(s.c_str()); // also updates client detectors[pos]->setHostname(s.c_str()); // also updates client
@ -878,8 +863,8 @@ void multiSlsDetector::updateOffsets() {
thisMultiDetector->numberOfChannel[0] * thisMultiDetector->numberOfChannel[0] *
thisMultiDetector->numberOfChannel[1]; thisMultiDetector->numberOfChannel[1];
for (auto* it : detectors) { for (auto& d : detectors) {
it->updateMultiSize(thisMultiDetector->numberOfDetector[0], d->updateMultiSize(thisMultiDetector->numberOfDetector[0],
thisMultiDetector->numberOfDetector[1]); thisMultiDetector->numberOfDetector[1]);
} }
} }
@ -1620,10 +1605,10 @@ int multiSlsDetector::setDynamicRange(int p, int detPos) {
thisMultiDetector->dataBytes = 0; thisMultiDetector->dataBytes = 0;
thisMultiDetector->dataBytesInclGapPixels = 0; thisMultiDetector->dataBytesInclGapPixels = 0;
thisMultiDetector->numberOfChannels = 0; thisMultiDetector->numberOfChannels = 0;
for (auto* it : detectors) { for (auto& d : detectors) {
thisMultiDetector->dataBytes += it->getDataBytes(); thisMultiDetector->dataBytes += d->getDataBytes();
thisMultiDetector->dataBytesInclGapPixels += it->getDataBytesInclGapPixels(); thisMultiDetector->dataBytesInclGapPixels += d->getDataBytesInclGapPixels();
thisMultiDetector->numberOfChannels += it->getTotalNumberOfChannels(); thisMultiDetector->numberOfChannels += d->getTotalNumberOfChannels();
} }
@ -2603,10 +2588,10 @@ int multiSlsDetector::getChanRegs(double* retval, bool fromDetector, int detPos)
int offset = 0; int offset = 0;
std::vector<int> r; std::vector<int> r;
for (auto* it : detectors) { for (auto& d : detectors) {
int nch = it->getTotalNumberOfChannels(); int nch = d->getTotalNumberOfChannels();
double result[nch]; double result[nch];
r.push_back(it->getChanRegs(result, fromDetector)); r.push_back(d->getChanRegs(result, fromDetector));
memcpy(retval + offset, result, nch * sizeof(double)); memcpy(retval + offset, result, nch * sizeof(double));
} }
return sls::minusOneIfDifferent(r); return sls::minusOneIfDifferent(r);
@ -2970,8 +2955,6 @@ int multiSlsDetector::createReceivingDataSockets(const bool destroy) {
if (destroy) { if (destroy) {
cprintf(MAGENTA, "Going to destroy data sockets\n"); cprintf(MAGENTA, "Going to destroy data sockets\n");
//close socket //close socket
for (auto* it : zmqSocket)
delete it;
zmqSocket.clear(); zmqSocket.clear();
client_downstream = false; client_downstream = false;
@ -2992,11 +2975,13 @@ int multiSlsDetector::createReceivingDataSockets(const bool destroy) {
uint32_t portnum = stoi(detectors[iSocket / numSocketsPerDetector]->getClientStreamingPort()); uint32_t portnum = stoi(detectors[iSocket / numSocketsPerDetector]->getClientStreamingPort());
portnum += (iSocket % numSocketsPerDetector); portnum += (iSocket % numSocketsPerDetector);
try { try {
ZmqSocket* z = new ZmqSocket( // ZmqSocket* z = new ZmqSocket(
detectors[iSocket / numSocketsPerDetector]->getClientStreamingIP().c_str(), // detectors[iSocket / numSocketsPerDetector]->getClientStreamingIP().c_str(),
portnum); // portnum);
zmqSocket.push_back(z); // zmqSocket.push_back(z);
printf("Zmq Client[%lu] at %s\n", iSocket, z->GetZmqServerAddress()); zmqSocket.push_back(sls::make_unique<ZmqSocket>(detectors[iSocket / numSocketsPerDetector]->getClientStreamingIP().c_str(),
portnum));
printf("Zmq Client[%lu] at %s\n", iSocket, zmqSocket.back()->GetZmqServerAddress());
} catch (...) { } catch (...) {
cprintf(RED, "Error: Could not create Zmq socket on port %d\n", portnum); cprintf(RED, "Error: Could not create Zmq socket on port %d\n", portnum);
createReceivingDataSockets(true); createReceivingDataSockets(true);
@ -3516,8 +3501,8 @@ int multiSlsDetector::setCTBPatLoops(int level, int& start, int& stop, int& n, i
// multi // multi
std::vector<int> r; std::vector<int> r;
for (auto* it : detectors) { for (auto& d : detectors) {
r.push_back(it->setCTBPatLoops(level, start, stop, n)); r.push_back(d->setCTBPatLoops(level, start, stop, n));
} }
return sls::allEqualTo(r, static_cast<int>(OK)) ? OK : FAIL; return sls::allEqualTo(r, static_cast<int>(OK)) ? OK : FAIL;
} }

View File

@ -14,6 +14,7 @@ class SharedMemory;
class ZmqSocket; class ZmqSocket;
class detectorData; class detectorData;
#include <memory>
#include <vector> #include <vector>
#include <string> #include <string>
#include <semaphore.h> #include <semaphore.h>
@ -1685,13 +1686,13 @@ private:
sharedMultiSlsDetector *thisMultiDetector; sharedMultiSlsDetector *thisMultiDetector;
/** pointers to the slsDetector structures */ /** pointers to the slsDetector structures */
std::vector <slsDetector*> detectors; std::vector <std::unique_ptr<slsDetector>> detectors;
/** data streaming (down stream) enabled in client (zmq sckets created) */ /** data streaming (down stream) enabled in client (zmq sckets created) */
bool client_downstream; bool client_downstream;
/** ZMQ Socket - Receiver to Client */ /** ZMQ Socket - Receiver to Client */
std::vector <ZmqSocket*> zmqSocket; std::vector <std::unique_ptr<ZmqSocket>> zmqSocket;
/** semaphore to let postprocessing thread continue for next scan/measurement */ /** semaphore to let postprocessing thread continue for next scan/measurement */

View File

@ -7,9 +7,18 @@
#include <type_traits> #include <type_traits>
#include <vector> #include <vector>
#include <sstream> #include <sstream>
#include <memory>
namespace sls { namespace sls {
// C++11 make_unique implementation for exeption safety
// already available as std::make_unique in C++14
template <typename T, typename... Args>
std::unique_ptr<T> make_unique(Args &&... args) {
return std::unique_ptr<T>(new T(std::forward<Args>(args)...));
}
template <typename T> template <typename T>
bool allEqual(const std::vector<T>& container) bool allEqual(const std::vector<T>& container)
{ {