Rework for mutex safety and RAII compliance

This commit is contained in:
hinger_v 2025-02-10 20:01:36 +01:00
parent 8a5bd21ecc
commit fb77bc7f1d

View File

@ -61,8 +61,9 @@ class singlePhotonDetector : public analogDetector<uint16_t> {
clusterSize(csize), clusterSizeY(csize), c2(1), c3(1), clusters(NULL), clusterSize(csize), clusterSizeY(csize), c2(1), c3(1), clusters(NULL),
quad(UNDEFINED_QUADRANT), tot(0), quadTot(0), ownsMutex(true) { // The original object owns the mutex { quad(UNDEFINED_QUADRANT), tot(0), quadTot(0), ownsMutex(true) { // The original object owns the mutex {
fm = new pthread_mutex_t; //fm = new pthread_mutex_t;
pthread_mutex_init(fm, NULL); //pthread_mutex_init(fm, NULL);
fm = new std::mutex();
eventMask = new eventType *[ny]; eventMask = new eventType *[ny];
// val=new double*[ny]; // val=new double*[ny];
@ -94,7 +95,7 @@ class singlePhotonDetector : public analogDetector<uint16_t> {
delete[] eventMask; delete[] eventMask;
if (ownsMutex) { if (ownsMutex) {
if (fm) { if (fm) {
pthread_mutex_destroy(fm); // Destroy the mutex //pthread_mutex_destroy(fm); // Destroy the mutex (not necessary with std::mutex)
delete fm; // Free the memory allocated for the mutex delete fm; // Free the memory allocated for the mutex
fm = nullptr; // Set the pointer to nullptr to avoid dangling pointer fm = nullptr; // Set the pointer to nullptr to avoid dangling pointer
} }
@ -130,6 +131,7 @@ class singlePhotonDetector : public analogDetector<uint16_t> {
c3 = sqrt(clusterSizeY * clusterSize); c3 = sqrt(clusterSizeY * clusterSize);
clusters = new single_photon_hit[nx * ny]; clusters = new single_photon_hit[nx * ny];
//std::copy(orig->clusters, orig->clusters + (nx * ny), clusters); //possibly superfluous
// cluster=clusters; // cluster=clusters;
@ -154,8 +156,9 @@ class singlePhotonDetector : public analogDetector<uint16_t> {
singlePhotonDetector(singlePhotonDetector const& other) singlePhotonDetector(singlePhotonDetector const& other)
: analogDetector<uint16_t>(other), ownsMutex(true) { : analogDetector<uint16_t>(other), ownsMutex(true) {
fm = new pthread_mutex_t; // create a new mutex //fm = new pthread_mutex_t; // create a new mutex
pthread_mutex_init(fm, NULL); //pthread_mutex_init(fm, NULL);
fm = new std::mutex(); // New unique mutex per copy
nDark = other.nDark; nDark = other.nDark;
myFile = other.myFile; myFile = other.myFile;
@ -733,13 +736,14 @@ class singlePhotonDetector : public analogDetector<uint16_t> {
void writeClusters(int fn) { void writeClusters(int fn) {
if (myFile) { if (myFile) {
// cout << "++" << endl; // cout << "++" << endl;
pthread_mutex_lock(fm); //pthread_mutex_lock(fm); // This is dangerous! What if writeClusters() throws? Then the mutex is never unlocked!
std::lock_guard<std::mutex> lock(*fm); // safer, RAII-based locking
// cout <<"**********************************"<< fn << " " << // cout <<"**********************************"<< fn << " " <<
// nphFrame << endl; // nphFrame << endl;
writeClusters(myFile, clusters, nphFrame, fn); writeClusters(myFile, clusters, nphFrame, fn);
// for (int i=0; i<nphFrame; i++) // for (int i=0; i<nphFrame; i++)
// (clusters+i)->write(myFile); // (clusters+i)->write(myFile);
pthread_mutex_unlock(fm); //pthread_mutex_unlock(fm); // unsafe
// cout << "--" << endl; // cout << "--" << endl;
} }
}; };
@ -777,7 +781,14 @@ class singlePhotonDetector : public analogDetector<uint16_t> {
ema = eMax; ema = eMax;
}; };
void setMutex(pthread_mutex_t *m) { fm = m; }; //void setMutex(pthread_mutex_t *m) { fm = m; };
void setMutex(std::mutex* m) {
if (ownsMutex && fm) {
delete fm; // Cleanup old mutex
}
fm = m;
ownsMutex = false;
};
protected: protected:
int nDark; /**< number of frames to be used at the beginning of the dataset int nDark; /**< number of frames to be used at the beginning of the dataset
@ -799,7 +810,8 @@ class singlePhotonDetector : public analogDetector<uint16_t> {
int nphFrame; int nphFrame;
// double **val; // double **val;
pthread_mutex_t* fm; // Pointer to the shared mutex //pthread_mutex_t* fm; // Pointer to the shared mutex
std::mutex* fm; // Pointer to the shared (or unique) mutex (safer version)
bool ownsMutex; // Flag to indicate ownership bool ownsMutex; // Flag to indicate ownership
}; };