Commit 7dbf716c authored by dino's avatar dino
Browse files

Update to (my) last version with (too) many changes spread around, which are difficult to describe.

git-svn-id: svn://gal-serv.lnl.infn.it/agata/trunk/narval_emulator@929 170316e4-aea8-4b27-aad4-0380ec0519c9
parent 543b7614
This diff is collapsed.
......@@ -3,6 +3,7 @@
#include "ADFConfig.h"
#include <memory.h>
#include <vector>
#include "commonDefs.h"
#ifdef EEB_LOCALSPECTRA
......@@ -10,18 +11,20 @@
#endif
#include "cycleServer.h"
const UInt_t dataSize = 10*1024*1024; // size of input queues
const UInt_t maxHalfBuffs = 2; // max number of input half-buffers held in queue
const UInt_t maxErrors = 40; // max number "errors"
const UInt_t queueSize = 4*1024*1024; // size of input queues in sizeof(Int_t) units
const UInt_t maxHalfBuffs = 2; // max number of input half-buffers held in queue
const UInt_t maxErrors = 0; // max number "errors" which is equivalent to a timeout (0==infinite)
class EventQueue
{
public:
EventQueue() :
inpKey(0),
tstFirst(0), tstLast(0), evnFirst(0), evnLast(0),
indFirst(0), indLast(0), indNext(0), numEvts(0),
endCount(0), errCount(0), totCount(0), statChan(0), maxSize(5)
endCount(0), errCount(0), totCount(0), statChan(0),
maxInputSize(0), maxQueueSize(0), badKeys(0)
{
memset(data, 0, sizeof(data));
}
......@@ -49,13 +52,14 @@ public:
return data[indFirst+1];
}
bool Add(UInt_t * i4dat, UInt_t n4dat, Int_t tstCorr = 0);
bool Eod(); // insert a frame with the highest possible timestamp
UInt_t moveOut(UInt_t *dest);
void Error(int ich);
UInt_t Size()
UInt_t UsedSize()
{
return indNext-indFirst;
}
bool hasDat() {
bool hasData() {
return indFirst < indNext;
}
bool isEmpty()
......@@ -63,20 +67,24 @@ public:
return indFirst >= indNext;
}
UInt_t data[dataSize]; // the data
ULong64_t tstFirst; // timestamp of first event in queue
ULong64_t tstLast; // timestamp of last event in queue
UInt_t evnFirst; // evnumber of first event in queue
UInt_t evnLast; // evnumber of last event in queue
UInt_t indFirst; // index of first event in data
UInt_t indLast; // index of last event in data
UInt_t indNext; // one past the last data item
UInt_t numEvts; // number of events in queue
UInt_t endCount; // counts the number of shifts to the bottom of the queue
UInt_t errCount; // counts the number of errors (decided by EventBuilder)
UInt_t totCount; // total number of events passed to the output
UInt_t statChan; // good (>threshold) number of events
UInt_t maxSize; // maximum size of added data in Add() (initialized to just one key)
UInt_t inpKey; // the only valid key for this chain
UInt_t data[queueSize]; // the data
ULong64_t tstFirst; // timestamp of first event in queue
ULong64_t tstLast; // timestamp of last event in queue
UInt_t evnFirst; // evnumber of first event in queue
UInt_t evnLast; // evnumber of last event in queue
UInt_t indFirst; // index of first event in data
UInt_t indLast; // index of last event in data
UInt_t indNext; // one past the last data item
UInt_t numEvts; // number of events in queue
UInt_t endCount; // counts the number of shifts to the bottom of the queue
UInt_t errCount; // counts the number of errors (decided by EventBuilder)
UInt_t totCount; // total number of events passed to the output
UInt_t statChan; // good (>threshold) number of events
UInt_t maxInputSize; // maximum size of added data in Add()
UInt_t maxQueueSize; // maximum size of added data in Add()
UInt_t badKeys; // number of frames not matching inpKey
std::string fName; // EventBuilder/EventMerger
};
class EventBuilder
......@@ -96,20 +104,27 @@ public:
Bool_t useEventNumber;
ULong64_t timeout;
ULong64_t tsumbus;
UInt_t minFold; // counting only gammas (inpKey1)
UInt_t minFold;
Bool_t verbose;
Bool_t bMerger;
Bool_t bBuilder; // used as EventBuilder
Bool_t bMerger; // used as EventMerger
std::string fActualClass;
std::vector<std::string> sKeyIn;
std::vector<unsigned int> uKeyIn;
std::string sKeyOut;
unsigned int uKeyOut;
Bool_t obufFull; // mark the case with the output buffer full
UInt_t nchains;
UInt_t gevCount; // total number of events in the event-builder
UInt_t bevCount; // total number of events in the merger
UInt_t nevCount; // total number of events in the event-builder
UInt_t oevCount; // number of events from the event-builder in this call
EventQueue *evq;
UInt_t *statKey1;
UInt_t *statKey2;
UInt_t *statKeys;
UInt_t *iqueSize;
Bool_t *isGood;
......@@ -119,30 +134,21 @@ public:
UInt_t errState;
UInt_t noBuild1;
UInt_t noBuild2;
UInt_t numKeys;
#ifdef EEB_LOCALSPECTRA
nDhistGroup hGroup; // used to record the pointers of all defined nDhist spectra
#endif //EEB_LOCALSPECTRA
cycleServer cServer; // manager of cyclic operations for event builder
cycleServer cServer2; // manager of cyclic operations for event merger
cycleServer cServer; // manager of cyclic operations for EventBuilder or EventMerger
#ifdef EEB_LOCALSPECTRA
nDhist<unsigned int> *specTdiff;
#endif //EEB_LOCALSPECTRA
ULong64_t tstKey1, tstKey2;
UInt_t inpKey1, inpKey2;
UInt_t outKey1, outKey2;
UInt_t numKey1, numKey2;
UInt_t numBad, badKey;
UInt_t *mBuff; // the buffer for the fake merger;
UInt_t mSize;
public:
EventBuilder(int nch = 1);
EventBuilder(unsigned int nch = 1, int type = 0);
virtual ~EventBuilder();
......@@ -153,14 +159,20 @@ public:
return evq[ichain].isEmpty();
}
bool isReady(int ichain)
bool isReady(int ichain) ///////// ?????????????
{
// 1) refill only if empty
//return evq[ichain].isEmpty();
// 2) refill if not too full
UInt_t size = evq[ichain].Size();
return 2*size <= maxHalfBuffs*evq[ichain].maxSize;
UInt_t size = evq[ichain].UsedSize(); // in sizeof(Int_t) units
return 2*size <= maxHalfBuffs*evq[ichain].maxInputSize;
}
bool isReady(int ichain, unsigned int isize)
{
UInt_t size = evq[ichain].UsedSize();
return (size + isize/sizeof(UInt_t) + 1) <= queueSize;
}
void PrintStat();
......@@ -174,9 +186,9 @@ public:
unsigned int *used_osize,
unsigned int *error_code);
void makeMerged (void *obuffer, unsigned int osize,
unsigned int *used_osize,
unsigned int *error_code);
//void makeMerged (void *obuffer, unsigned int osize,
// unsigned int *used_osize,
// unsigned int *error_code);
static void process_config(const Char_t *, UInt_t *);
virtual void process_initialise (UInt_t *error_code);
......@@ -188,6 +200,9 @@ public:
private:
void GetParameters(UInt_t *error_code);
bool InitAsBuilder();
bool InitAsMerger();
bool InitKeys(unsigned int nv);
};
#endif // EVENTBUILDER_H_INCLUDED
......@@ -47,20 +47,16 @@
/////////////////////////////////////////////////////
//#define NRV_ONLINE // One of the two symbols must be defined, but this
//#define NRV_OFFLINE // can of course be done in the project or makefile
//#define NRV_OFFLINE // can of course be done in the project or makefile (e.g. for narval: make library PCI_EXPRESS=-DNRV_ONLINE)
#if (!defined(NRV_ONLINE) && !defined(NRV_OFFLINE)) || (defined(NRV_ONLINE) && defined(NRV_OFFLINE))
#error Please define just one of the two macros: NRV_ONLINE or NRV_OFFLINE
#endif
#ifdef NRV_ONLINE
#if defined(_WIN32) || defined(_WIN64) || defined(_MSC_VER) || defined(__CYGWIN__)
#if (OS_TYPE != OS_LINUX)
#error The online version can only be built on Linux
#endif
#ifdef OS_TYPE
#undef OS_TYPE
#endif
#define OS_TYPE OS_LINUX
#endif
///////////////////////////////////////////////
......@@ -75,7 +71,7 @@ const unsigned long long tst1second = 100000000;
// events after which to write spectra and perform cyclic checks
const unsigned int defaultCycleEvts = 10000;
const unsigned int defaultCycleTime = 1200; //in (timpestamp) seconds
const unsigned int defaultCycleTime = 600; //in (timpestamp) seconds
//const float RAD2DEG = float( 180./acos(-1.) );
const float RAD2DEG = float(57.29577951308232286464772187173366546630859375);
......@@ -89,7 +85,7 @@ const int defTraceLengthPSA = 60;
// default trigger point used by PreprocessingFilter and PSAFilter
const int defTriggerSample = 10; // 60-10 useful samples passed to the PSA
// this random generator is just sufficient for un-digitizing samples
// this is a poor random generator, but sufficient for un-digitizing samples
#define dRAND() ( rand()/(RAND_MAX+1.0) )
#define fRAND() ( rand()/(RAND_MAX+1.f) )
......@@ -114,7 +110,7 @@ const int defTriggerSample = 10; // 60-10 useful samples passed to the PS
/////////////////////////////////////
//#define PPF_NO_ADF // PreprocessingFilter does not use ADF to decode/code the IO buffers (still working??)
//#define PPF_CHECK_EE_ES // Discard event if CC energy too different from energy derived from trace amplitude
//#define PPF_CHECK_EE_ES // Discard event if CC energy is too different from energy derived from trace amplitude
#define PPF_LOCALSPECTRA // enable nDhist spectra
//#define PPF_FromGRU_ // enable GRU/ViGRU
......@@ -122,9 +118,9 @@ const int defTriggerSample = 10; // 60-10 useful samples passed to the PS
//////// PSAFilter ////////
///////////////////////////
//#define TCOUNT 2 // number of threads to use to decompose signals (commented or <1 ==> nothreads)
#define TMODULO 100 // how many events are distributed to each thread
#define USEADAPTIVE // to use the coarse-fine grid searh
//#define PSA_THREADED // enable splitting the PSA algorithm into parallel threads
#define TCOUNT 3 // default number of threads used to decompose signals (if PSA_THREADED enabled)
#define TMODULO 100 // how many events are distributed to each thread
#define PSA_LOCALSPECTRA // enable nDhist spectra
//#define PSA_FromGRU_ // enable GRU/ViGRU
......@@ -135,7 +131,7 @@ const int defTriggerSample = 10; // 60-10 useful samples passed to the PS
//#define AF_PRISMA // processing of PRISMA
//#define AF_DANTE // processing of DANTE ==> still to be adjusted
//#define AF_HELENA // processing of the Helena detectors for the neutron test
//#define AF_ROOTTREE
//#define AF_ROOTTREE // Enable the root tree in this actor
#define AF_LOCALSPECTRA // enable nDhist spectra
//#define AF_FromGRU_ // enable GRU/ViGRU
......@@ -144,11 +140,11 @@ const int defTriggerSample = 10; // 60-10 useful samples passed to the PS
////////////////////////////
#define NDETS 15 // max acceptable value of crystal_id is NDETS-1 (to limit size of spectra!!)
//#define WRITE_INPUT_HITS // Write input hits into Oft_Hits (AgataMC/mgt ascii file)
//#define EXTENDED_OUTPUT // Oft_Hits contain also timestamp and eventnumber
//#define EXTENDED_OUTPUT // Mgt_Hits (if requested in PSAFilter.conf) contain also timestamp and eventnumber
//#define WRITE_TRACKED // Write the tracked gammas into the Oft_TrackedEnergies ascii file
//#define NTIMING 1 // processing of the Helena detectors for the neutron test
//#define TF_ROOTTREE
//#define TF_ROOTTREE // Enable the root tree in this actor
//#define TREE_INPUT_HITS // Write input hits into the root tree
#define TF_LOCALSPECTRA // enable nDhist spectra
//#define TF_FromGRU_ // enable GRU/ViGRU
......@@ -156,30 +152,55 @@ const int defTriggerSample = 10; // 60-10 useful samples passed to the PS
////// The WinCtest Emulator //////
///////////////////////////////////
#define EEB_LOCALSPECTRA // enable nDhist spectra in the emulator event builder
#define EEB_LOCALSPECTRA // enable nDhist spectra in the event builder of the emulator
//////////////////////////////////////
// common treatment of LOCALSPECTRA //
//#define EXCLUDE_LOCALSPECTRA // to exclude all of them at once
#ifdef EXCLUDE_LOCALSPECTRA
# ifdef CP_LOCALSPECTRA
# undef CP_LOCALSPECTRA
# endif
# ifdef PPF_LOCALSPECTRA
# undef PPF_LOCALSPECTRA
# endif
# ifdef PSA_LOCALSPECTRA
# undef PSA_LOCALSPECTRA
# endif
# ifdef AF_LOCALSPECTRA
# undef AF_LOCALSPECTRA
# endif
# ifdef TF_LOCALSPECTRA
# undef TF_LOCALSPECTRA
# endif
# ifdef EEB_LOCALSPECTRA
# undef EEB_LOCALSPECTRA
# endif
#endif
#if defined(CP_LOCALSPECTRA) ||\
defined(PPF_LOCALSPECTRA) ||\
defined(PSA_LOCALSPECTRA) ||\
defined(AF_LOCALSPECTRA) ||\
defined(TF_LOCALSPECTRA) ||\
defined(EEB_LOCALSPECTRA) &&\
!defined(LOCALSPECTRA)
#define LOCALSPECTRA // needed by cycleServer if any individual one is enabled
defined(EEB_LOCALSPECTRA)
# define LOCALSPECTRA // needed by cycleServer if any individual one is enabled
#endif
//#define COUT_LOCKED // to avoid mixing printouts from parallel threads
//////////////////////////////////////////////
// a global lock on printouts (may be slow) //
//////////////////////////////////////////////
//#if (OS_TYPE != OS_WINDOWS) || defined(WIN64)
//# ifdef COUT_LOCKED
//# undef COUT_LOCKED
//# endif
//#endif
#if OS_TYPE == OS_WINDOWS
//# define COUT_LOCKED
#endif
#if defined(COUT_LOCKED)
# include <boost/thread/mutex.hpp>
# define LOCK_COUT boost::mutex::scoped_lock lock(ioMutex);
extern boost::mutex ioMutex; // normally defined in WinCtest.cpp
extern boost::mutex ioMutex; // the mutex is defined in WinCtest.cpp
#else
# define LOCK_COUT ;
#endif
......
......@@ -70,7 +70,7 @@ unsigned int cycleServer::ExecLong()
return actions; // to avoid useless re-writing
#ifdef LOCALSPECTRA
if( hGroup->write(true, false) ) {
if( hGroup->write(false, true) ) {
actions |= 1;
}
#endif //LOCALSPECTRA
......
......@@ -21,7 +21,7 @@ protected:
std::string padString;
unsigned int padSize;
int ndim;
int size[4];
int size[5];
int lentot;
int counts;
bool initialized;
......@@ -46,14 +46,14 @@ const char *NameOfType( double *) { return "D"; }
nDhist_t() {
ndim = 0;
size[0] = size[1] = size[2] = size[3] = 0;
size[0] = size[1] = size[2] = size[3] = size[4] = 0;
lentot = 0;
padSize = 20;
initialized = false;
tname = NULL;
tsize = 0;
}
void setup(int dim1, int dim2 = 0, int dim3 = 0, int dim4 = 0) {
void setup(int dim1, int dim2 = 0, int dim3 = 0, int dim4 = 0, int dim5 = 0) {
initialized = false;
ndim = 0;
if(dim1) {
......@@ -64,6 +64,8 @@ const char *NameOfType( double *) { return "D"; }
size[ndim++] = dim3;
if(dim4)
size[ndim++] = dim4;
if(dim5)
size[ndim++] = dim5;
}
}
}
......@@ -245,6 +247,16 @@ public:
tname = NameOfType(data);
tsize = sizeof(T);
}
nDhist(unsigned int dim1, unsigned int dim2, unsigned int dim3, unsigned int dim4, unsigned int dim5) {
data = NULL;
setup(dim1, dim2, dim3, dim4, dim5);
if(ndim == 5) {
initialized = true;
reset();
}
tname = NameOfType(data);
tsize = sizeof(T);
}
virtual ~nDhist() {
remove();
}
......@@ -298,6 +310,18 @@ public:
data[jj]++;
counts++;
}
void incr(int n0, int n1, int n2, int n3, int n4) {
if(!initialized) return;
if(n0 < 0 || n0 >= size[0]) return;
if(n1 < 0 || n1 >= size[1]) return;
if(n2 < 0 || n2 >= size[2]) return;
if(n3 < 0 || n3 >= size[3]) return;
if(n4 < 0) n4 = 0;
else if(n4 >= size[4]) n4 = size[4]-1;
int jj = (((n0*size[1] + n1)*size[2] + n2)*size[3] + n3)*size[4] + n4;
data[jj]++;
counts++;
}
// off-range discarded
void Incr(int n0) {
if(!initialized) return;
......@@ -333,6 +357,17 @@ public:
data[jj]++;
counts++;
}
void Incr(int n0, int n1, int n2, int n3, int n4) {
if(!initialized) return;
if(n0 < 0 || n0 >= size[0]) return;
if(n1 < 0 || n1 >= size[1]) return;
if(n2 < 0 || n2 >= size[2]) return;
if(n3 < 0 || n3 >= size[3]) return;
if(n4 < 0 || n4 >= size[4]) return;
int jj = (((n0*size[1] + n1)*size[2] + n2)*size[3] + n3)*size[4] + n4;
data[jj]++;
counts++;
}
// Set channel value off-range discarded
void Set(int n0, T val) {
if(!initialized) return;
......@@ -368,6 +403,17 @@ public:
data[jj] = val;
counts++;
}
void Incr(int n0, int n1, int n2, int n3, int n4, T val) {
if(!initialized) return;
if(n0 < 0 || n0 >= size[0]) return;
if(n1 < 0 || n1 >= size[1]) return;
if(n2 < 0 || n2 >= size[2]) return;
if(n3 < 0 || n3 >= size[3]) return;
if(n4 < 0 || n4 >= size[4]) return;
int jj = (((n0*size[1] + n1)*size[2] + n2)*size[3] + n3)*size[4] + n4;
data[jj] = val;
counts++;
}
// get pointer to data
T *getData() {
if(!initialized) return NULL;
......@@ -391,6 +437,14 @@ public:
if(n2 < 0 || n2 >= size[2]) return NULL;
return data + ((n0*size[1] + n1)*size[2] + n2)*size[3];
}
T *getData(int n0, int n1, int n2, int n3) {
if(!initialized) return NULL;
if(n0 < 0 || n0 >= size[0]) return NULL;
if(n1 < 0 || n1 >= size[1]) return NULL;
if(n2 < 0 || n2 >= size[2]) return NULL;
if(n3 < 0 || n3 >= size[3]) return NULL;
return data + (((n0*size[1] + n1)*size[2] + n2)*size[3] + n3)*size[4];
}
// get data
T getValue(int n0) {
if(!initialized) return 0;
......@@ -422,6 +476,16 @@ public:
int jj = ((n0*size[1] + n1)*size[2] + n2)*size[3] + n3;
return data[jj];
}
T getValue(int n0, int n1, int n2, int n3, int n4) {
if(!initialized) return 0;
if(n0 < 0 || n0 >= size[0]) return 0;
if(n1 < 0 || n1 >= size[1]) return 0;
if(n2 < 0 || n2 >= size[2]) return 0;
if(n3 < 0 || n3 >= size[3]) return 0;
if(n4 < 0 || n4 >= size[4]) return 0;
int jj = (((n0*size[1] + n1)*size[2] + n2)*size[3] + n3)*size[4] + n4;
return data[jj];
}
bool write(FILE *fp, bool doErase = false) {
if(!initialized) {
......@@ -434,8 +498,8 @@ public:
return (ii == lentot) ? true : false;
}
bool write(bool verbose, bool erase = false) {
return nDhist_t::write(verbose, erase);
bool write(bool erase = false, bool verbose = true) {
return nDhist_t::write(erase, verbose);
}
};
......@@ -478,7 +542,7 @@ public:
// }
// return state;
//}
bool write(bool verbose = true, bool erase = false) {
bool write(bool erase = false, bool verbose = true) {
bool state = true;
unsigned int pad = 0;
if(verbose) {
......
......@@ -30,6 +30,7 @@ fTrigger("data:ranc0")
fConfPath = GetConfPath();
fOdirPrefix.clear();
fPRISMALUTFile.clear();
fTstampFile.clear();
fVerbose = false;
fEnergyGain = 1.f; // gain of energy spectra
......@@ -61,6 +62,14 @@ fTrigger("data:ranc0")
fInblock.SetModeIO(ConfAgent::kRead);
fOublock.SetModeIO(ConfAgent::kWrite);
fTstampFILE = NULL;
fFromFile = false;
fEvnumber = 0;
fTimestamp = 0;
fTolerance = 0;
fCount = 0;
}
AncillaryFilter::~AncillaryFilter()
......@@ -151,9 +160,30 @@ void AncillaryFilter::process_initialise ( UInt_t *error_code )
// state set to kIdle so that the data can be treated
fFrameIO.SetStatus(BaseFrameIO::kIdle);
// version specific initialization
// version-specific initialization
*error_code = AlgoSpecificInitialise();
if(fTstampFile.size()) {
fTstampFile = fConfPath+fTstampFile;
if( (fTstampFILE = fopen(fTstampFile.c_str(),"r")) == NULL) {
cout << "Error opening " << fTstampFile << endl;
*error_code = 133;
return;
}
cout << "Opened timestamp file " << fTstampFile << endl;
fTimestamp = 0x0FFFFFFFFFFFFFFF;
int nn = fscanf(fTstampFILE, "%d %lld", &fEvnumber, &fTimestamp);
if(nn != 2) {
cout << "Error reading " << fTstampFile << endl;
*error_code = 134;
return;
}
cout << "First evnumber " << fEvnumber << endl;
cout << "First timestamp " << fTimestamp << endl;
fCount = 1;
fFromFile = true;
}
cServer.SetCommandFile(fConfPath+gMotherClass+".live");
#ifdef AF_LOCALSPECTRA
cServer.SetHistGroup(&hGroup);
......@@ -191,7 +221,7 @@ void AncillaryFilter::GetParameters(UInt_t *error_code)
ok = data.size() > 0;
gActualClass = data;
}
else if( stringEq(keyw, "WriteDataDir") || stringEq(keyw, "WriteDataPrefix") ) {
else if( stringEq(keyw, "SaveDataDir") || stringEq(keyw, "WriteDataDir") || stringEq(keyw, "WriteDataPrefix") ) {
ok = data.size() > 0;
fOdirPrefix = data;
forceTailSlash(fOdirPrefix);
......@@ -208,6 +238,14 @@ void AncillaryFilter::GetParameters(UInt_t *error_code)
ok = data.size() > 0;
fPRISMAManager = data;
}
else if( stringEq(keyw, "TstampFile") ) {
ok = data.size() > 0;
string value1, value2;
stringSplit(data, " \t", value1, value2);
fTstampFile = value1;
if(value2.size())
fTolerance = atoi(value2.c_str());
}
else if( stringEq(keyw, "DanteChan") ) {
ok = 3 == sscanf(data.c_str(), "%d %d %d ", &fDanteChT, &fDanteChX, &fDanteChY);
}
......@@ -256,7 +294,7 @@ void AncillaryFilter::GetParameters(UInt_t *error_code)
}
// this file contains the definition of the Converters
// and calibration coefficients
// and calibration coefficients. The method is invoked by the daughter class
bool AncillaryFilter::Decodesetup()
{
if(!setupFile.size()) {
......@@ -449,6 +487,15 @@ UInt_t AncillaryFilter::ProcessBlock (ADF::FrameBlock &in, ADF::FrameBlock &out)
break;
}
//if((timestamp%3) == 0) {
// cout << "# " << evnumber << " " << timestamp << endl;
//}
if(fFromFile) {
if(!CheckTstamp())
continue;
}
if( (theStatus = Process()) ) { // process the input buffer
if(theStatus < 0)
continue;
......@@ -609,6 +656,45 @@ Int_t AncillaryFilter::SetOutput(