/******************************************************************** * The Data Acquisition Backbone Core (DABC) ******************************************************************** * Copyright (C) 2009- * GSI Helmholtzzentrum fuer Schwerionenforschung GmbH * Planckstr. 1 * 64291 Darmstadt * Germany * Contact: http://dabc.gsi.de ******************************************************************** * This software can be used under the GPL license agreements as stated * in LICENSE.txt file which is part of the distribution. ********************************************************************/ #ifndef ROC_CombinerModule #define ROC_CombinerModule #include "dabc/ModuleAsync.h" #include "dabc/Pointer.h" #include "roc/BoardsVector.h" #include "roc/CombinerModule.h" #include "mbs/Iterator.h" #include namespace roc { extern const char* xmlBnetMode; // true if combiner works within bnet environment extern const char* xmlSkipErrorData; // if true, error data will be skipped extern const char* xmlIgnoreMissingEpoch; // workaround for fail FEET readout extern const char* xmlSyncNumber; // specified sync channel, used for synchronization extern const char* xmlSyncScaleDown; // identifies scale down of sync events extern const char* xmlSpillRoc; extern const char* xmlSpillAux; extern const char* xmlCalibrationPeriod; extern const char* xmlCalibrationLength; extern const char* xmlThrottleAux; extern const char* xmlGet4ResetPeriod; // reset period of all GET4 chips extern const char* xmlGet4ResetLimit; // how often automatic reset is allowed when GET4 error is detected class CombinerModule : public dabc::ModuleAsync { public: CombinerModule(const char* name, dabc::Command cmd); virtual ~CombinerModule(); virtual void BeforeModuleStart(); virtual void ProcessInputEvent(dabc::Port* port); virtual void ProcessOutputEvent(dabc::Port* port); virtual void ProcessTimerEvent(dabc::Timer* timer); protected: enum { MaxGet4 = 16, MaxGet4Ch = 4 }; struct InputRec { unsigned rocid; int format; bool isudp; // indicate if optic or Ethernet transport are attached uint32_t curr_epoch; bool iscurrepoch; unsigned curr_nbuf; unsigned curr_indx; uint32_t prev_epoch; // previous epoch marker bool isprev; unsigned prev_nbuf; // id of buffer where epoch is started unsigned prev_indx; // index inside buffer where epoch found uint32_t prev_evnt; // sync event number uint32_t prev_stamp; // sync time stamp uint32_t next_epoch; // number of the next epoch bool isnext; // unsigned next_nbuf; // id of buffer where epoch is started unsigned next_indx; // index inside buffer where epoch found uint32_t next_evnt; // sync event number uint32_t next_stamp; // sync time stamp bool nummbssync; // indicate how many mbs sync data we had uint32_t firstmbssync; // value of first found mbssync unsigned data_length; // length of data between prev and next event bool isready; // indicate if epoch and next are defined and ready for combining bool use; // use input for combining bool data_err; // event numbers are wrong dabc::Pointer ptr; // used in combining unsigned nbuf; // used in combining uint32_t epoch; // original epoch used in combining unsigned stamp; // corrected stamp value in combining unsigned stamp_shift; // (shift to event begin) uint64_t last_thottle_tm; // last time, when threshold state was changed bool last_throttle_state; // last state of throttle signal (on/off) uint32_t lastEpoch2[MaxGet4]; // last epoch2 for each get4 int get4EdgeCnt[MaxGet4][MaxGet4Ch]; // edge counter for each get4 channel int get4EdgeErrs[MaxGet4][MaxGet4Ch]; // number of errors when consequent same adges more than 3 uint64_t get4LastTm[MaxGet4][MaxGet4Ch]; // last time stamp on each channel (disregard edge) int get4AllCnt[MaxGet4][MaxGet4Ch]; // counter of all sign changes int get4ErrCnt[MaxGet4][MaxGet4Ch]; // counter of suspicious sign changes unsigned lastEpoch2SyncErr[MaxGet4]; // last error difference between epoch2 when sync=1 bool canCheckGet4[MaxGet4]; // indicate if we could analyze data of GET4, on after first sync bool canCheckAnyGet4; // true if any get4 can be checked, disabled after reconfig until sys message is available bool isrocid() const { return rocid!=0xffffffff; } bool IsDifferentRocId(unsigned id, bool& iserr) { iserr = false; if (rocid==id) return false; // in case of udp channel any different rocid is error if (isudp) { iserr = true; return true; } iserr = true; return true; } unsigned can_skip_buf() { return isprev ? prev_nbuf : 0; } void did_skip_buf(unsigned cnt) { curr_nbuf -= cnt; if (isprev) prev_nbuf -= cnt; if (isnext) next_nbuf -= cnt; } InputRec() : rocid(0xffffffff), format(formatEth1), isudp(true), curr_epoch(0), iscurrepoch(false), curr_nbuf(0), curr_indx(0), prev_epoch(0), isprev(false), prev_nbuf(0), prev_indx(0), prev_evnt(0), prev_stamp(0), next_epoch(0), isnext(false), next_nbuf(0), next_indx(0), next_evnt(0), next_stamp(0), nummbssync(0), firstmbssync(0), data_length(0), isready(false), use(false), data_err(false), ptr(), nbuf(0), epoch(0), stamp(0), stamp_shift(0), last_thottle_tm(0), last_throttle_state(false) { for (int n=0;n fInp; dabc::Buffer fOutBuf; dabc::Pointer f_outptr; int fSpillRoc; // roc number, where spill on/off signal is connected int fSpillAux; // number of Aux channel where spill on/off signal is measured bool fSpillState; // current state of spill, known by module uint64_t fLastSpillTime; // last time when spill signal was seen double fCalibrationPeriod; // how often trigger mode should be started double fCalibrationLength; // how long calibration should be switched on dabc::TimeStamp fLastCalibrationTime; // last time when trigger was caused double fGet4ResetPeriod; // period how often reset of Get4 should be performed int fThrottleAux; // defines AUX signal, which analyzed at throttled std::list fExtraMessages; bool fFlushFlag; // boolean, indicate if buffer should be flushed in next timeout double fGet4ResetLimit; // how often get4 can be reseted dabc::TimeStamp fLastGet4ResetTm; // time when reset was send to application bool fDetectGet4Problem; }; } #endif