Arianna autonomous DAQ firmware
Dependencies: mbed SDFileSystemFilinfo AriSnProtocol NetServicesMin AriSnComm MODSERIAL PowerControlClkPatch DS1820OW
Diff: SnConfigFrame.h
- Revision:
- 0:664899e0b988
- Child:
- 1:e392595b4b76
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/SnConfigFrame.h Sat Jun 30 02:03:51 2012 +0000 @@ -0,0 +1,293 @@ +#ifndef SN_SnConfigFrame +#define SN_SnConfigFrame + +#include <stdint.h> +#include "SnConstants.h" +#include "SnBitUtils.h" + +class SnConfigFrame { + public: + static const uint32_t kMinCommWinPrdLowPwr; // exclusive min low power comm win period (s) + static const uint32_t kMaxCommWinPrdLowPwr; // exclusive max low power comm win period (s) + static const uint32_t kMinCommWinDurLowPwr; // exclusive min low power comm win duration (s) + static const uint32_t kMaxCommWinDurLowPwr; // exclusive max low power comm win duration (s) + static const uint8_t kConfLblLen=64; // length of configuration label char array (63+'\0') + + static const char* kDefConfFile; // default configuration file + + static const uint32_t kMaxSizeOf = + 1u + // the i/o version + + (8u*sizeof(uint32_t)) + (8u*sizeof(uint16_t)) + + (9u*sizeof(uint8_t)) + (2u*kNplas*sizeof(uint16_t)) + + (kConfLblLen*sizeof(uint8_t)); + + + enum EDatPackBit { + kSDcard = BIT(0), + kIrid = BIT(1), + kAfar = BIT(2), + kUSB = BIT(3) + }; + + enum ESendDataBit { + // can't use BIT(0)! (-0 = 0 => send nothing) + kAllFiles = BIT(1), // if bit=0 => send most recent file + kTimeout = BIT(2), // if bit=0 => ignore timeout + kDelete = BIT(3) // if bit=0 => do not delete sent files + }; + + // i/o version + static const int8_t kIOVers; // MUST BE INCREASED if any member var changes (==> also if kNchans, etc. change!) + + private: + // !! + // !! If any member variables change, update: SizeOf function and kIOVers value! (also if kNchans, etc. change!) + // !! + + // mbed mac address + static uint64_t fgMacAdr; // mbed mac address + // conf header + char fLabel[kConfLblLen]; // configuration label + uint32_t fConfTime; // cpu config time + uint32_t fRun; // run number + uint32_t fFirstEvt; // starting event number + uint8_t fStreamHiLoPlas; // (1byte bool) if true, add the separated hi/lo thresh PLA patterns to the i/o + // data packing + uint8_t fWvLoseLSB; // number of least significant bits to lose when packing waveform data + uint8_t fWvLoseMSB; // number of most significant bits to lose when packing waveform data + uint16_t fWvBaseline; // global baseline to use when packing data (useful to reduce clipping on the high end) + uint8_t fDatPackType; // type of data packing. OR'd bitword: if bit 1, will pack for writing. see EDatPackBit. default: always pack (all 1's) + // trigger setup + uint16_t fDAC[kNchans][kNfpgaDacs]; //[card id][dac id] values should be 0-4095 here (not checked tho) + uint8_t fNumPlas; // number of patterns to use. must be <= kNplas. + uint16_t fPLA[kNplas]; //[pattern id] (same for each card) + uint8_t fNumCardsMajLog; // number of cards participating in the MajLogic trigger (1 to 4) + uint8_t fEnableThermTrig; // (1byte bool) whether or not to allow thermal triggers + uint16_t fForceTrigPeriod; // number of seconds between force triggers (0=none) + uint16_t fHeartBeatPeriod; // number of seconds between heartbeats (0=none) + uint8_t fAmpsOn; // which amps are on (bit word. uint8_t => 8 amps max) + uint16_t fEvtThrtlPeriodMs; // throttle period to write events (ms) + // power + uint8_t fPowerMode; // power mode bit word + int16_t fBatVoltLowPwr; // battery level at which to switch to low power (not used?) + // communication + uint32_t fCommWinPeriod; // seconds between communication window startup (0=always on) + uint32_t fCommWinDuration; // seconds that communication window stays open (0=always open) + int16_t fCommSendData; // data to send during comm win (=0: none, >0=send up to x events from last file until comm win closes, <0=see ESendDataBit) + uint32_t fCommWinPrdLowPwr; // low power communication window period (seconds) (range enforced) + uint32_t fCommWinDurLowPwr; // low power communication window duration (seconds) (range enforced) + // watchdog + uint32_t fWatchDogPeriod; // number of seconds of inactivity for watchdog to issue a reset + + void SetHardDefaults(); + + static + uint32_t SizeOf(const bool streamHiLoPlas, const uint8_t lblLen) { + // private because it cannot be used to read from a buffer + // (the label length and fStreamHiLoPlas are not known a priori) + // returns the num of bytes needed to stream this object + // = size of member vars + 1 for i/o version + extra PLA strings (maybe) + uint32_t sz = kMaxSizeOf - kConfLblLen + lblLen; + if (streamHiLoPlas==false) { + static const uint32_t shlp = 2u*kNplas*sizeof(uint16_t); + sz -= shlp; + } + return sz; + } + + public: + SnConfigFrame() { Reset(); } + virtual ~SnConfigFrame() {} + + const char* GetLabel() const { return fLabel; } + uint32_t GetLabelStrLen() const { return strlen(fLabel); } + uint32_t GetRun() const { return fRun; } + uint32_t GetFirstEvt() const { return fFirstEvt; } + uint16_t GetEvtThrtlPeriodMs() const { return fEvtThrtlPeriodMs; } + uint16_t GetForceTrigPeriod() const { return fForceTrigPeriod; } + uint32_t GetWatchdogPeriod() const { return fWatchDogPeriod; } + uint16_t GetDac(const uint8_t ch, const uint8_t dn) const { return fDAC[ch][dn]; } + uint8_t GetNumPlas() const { return fNumPlas; } + uint16_t GetPla(const uint8_t pn) const { return fPLA[pn]; } + uint8_t GetNumCardsMajLog() const { return fNumCardsMajLog; } + bool IsThermTrigEnabled() const { return fEnableThermTrig!=0; } + bool IsEachAmpOn() const { + bool allon=true; + for (uint8_t i=0; (i<kNchans) && allon; i++) { + allon = (fAmpsOn & BIT(i))!=0; + } + return allon; + } + // TODO: allow check for individual amps, when they can be turned on individually + + uint32_t GetCommWinPeriod() const { return fCommWinPeriod; } + uint32_t GetCommWinDuration() const { return fCommWinDuration; } + int16_t GetCommSendData() const { return fCommSendData; } + + bool IsSendingAllFiles() const + { return (fCommSendData<0) && ((fCommSendData & kAllFiles)!=0); } + bool IsObeyingTimeout() const + { return (fCommSendData<0) && ((fCommSendData & kTimeout)!=0); } + bool IsDeletingFiles() const + { return (fCommSendData<0) && ((fCommSendData & kDelete)!=0); } + + + const char* GetOutFileName(const char* dir) const; + + // waveform packing info + uint16_t GetWvBaseline() const { return fWvBaseline; } + uint8_t GetWvLoseLSB() const { return fWvLoseLSB; } + uint8_t GetWvLoseMSB() const { return fWvLoseMSB; } + bool IsDatPackedFor(const EDatPackBit d) const { return (fDatPackType & d)!=0; } + void GetPackParsFor(const EDatPackBit d, + uint8_t& loseLSB, uint8_t& loseMSB, + uint16_t& wvBase) const; + + // i/o + template<class T> + void ReadFrom(T& b) { + // no check on the length of buf is done here + // that should be been done already + // + // must match WriteTo + + int8_t Rv=0; + b = SnBitUtils::ReadFrom(b, Rv); // i/o version + if (Rv>0) { + uint32_t llen=kConfLblLen; + b = SnBitUtils::ReadFrom(b, llen); + b = SnBitUtils::ReadFrom(b, fLabel, llen); + b = SnBitUtils::ReadFrom(b, fConfTime); + b = SnBitUtils::ReadFrom(b, fRun); + b = SnBitUtils::ReadFrom(b, fFirstEvt); + b = SnBitUtils::ReadFrom(b, fStreamHiLoPlas); + b = SnBitUtils::ReadFrom(b, fWvLoseLSB); + b = SnBitUtils::ReadFrom(b, fWvLoseMSB); + b = SnBitUtils::ReadFrom(b, fWvBaseline); + b = SnBitUtils::ReadFrom(b, fDatPackType); + uint16_t* dc = &(fDAC[0][0]); + for (uint16_t i=0; i<kTotDacs; i++, dc++) { + b = SnBitUtils::ReadFrom(b, *dc); + } + b = SnBitUtils::ReadFrom(b, fNumPlas); + uint16_t* pl = &(fPLA[0]); + for (uint8_t j=0; j<fNumPlas; j++, pl++) { + b = SnBitUtils::ReadFrom(b, *pl); + } + b = SnBitUtils::ReadFrom(b, fNumCardsMajLog); + b = SnBitUtils::ReadFrom(b, fEnableThermTrig); + b = SnBitUtils::ReadFrom(b, fForceTrigPeriod); + b = SnBitUtils::ReadFrom(b, fHeartBeatPeriod); + b = SnBitUtils::ReadFrom(b, fAmpsOn); + b = SnBitUtils::ReadFrom(b, fEvtThrtlPeriodMs); + b = SnBitUtils::ReadFrom(b, fPowerMode); + b = SnBitUtils::ReadFrom(b, fBatVoltLowPwr); + b = SnBitUtils::ReadFrom(b, fCommWinPeriod); + b = SnBitUtils::ReadFrom(b, fCommWinDuration); + b = SnBitUtils::ReadFrom(b, fCommSendData); + b = SnBitUtils::ReadFrom(b, fCommWinPrdLowPwr); + b = SnBitUtils::ReadFrom(b, fCommWinDurLowPwr); + b = SnBitUtils::ReadFrom(b, fWatchDogPeriod); + if (fStreamHiLoPlas!=0) { + pl = fPLA; + uint16_t hi, lo; + for (uint8_t j=0; j<fNumPlas; j++, pl++) { + GetHiLoPlas(*pl, hi, lo); + b = SnBitUtils::ReadFrom(b, hi); + b = SnBitUtils::ReadFrom(b, lo); + } + } + } + } + + template <class T> + void WriteTo(T& b) const { + // no check on the length of the buf is done here + // that should be done already + // + // must match ReadFromBuf + // + // intentionally not writing mac address here, so we don't have to read it in + + const uint32_t llen = strlen(fLabel); + + b = SnBitUtils::WriteTo(b, kIOVers); // i/o version + b = SnBitUtils::WriteTo(b, llen); + b = SnBitUtils::WriteTo(b, fLabel, llen); + b = SnBitUtils::WriteTo(b, fConfTime); + b = SnBitUtils::WriteTo(b, fRun); + b = SnBitUtils::WriteTo(b, fFirstEvt); + b = SnBitUtils::WriteTo(b, fStreamHiLoPlas); + b = SnBitUtils::WriteTo(b, fWvLoseLSB); + b = SnBitUtils::WriteTo(b, fWvLoseMSB); + b = SnBitUtils::WriteTo(b, fWvBaseline); + b = SnBitUtils::WriteTo(b, fDatPackType); + const uint16_t* dc = &(fDAC[0][0]); + for (uint16_t i=0; i<kTotDacs; i++, dc++) { + b = SnBitUtils::WriteTo(b, *dc); + } + b = SnBitUtils::WriteTo(b, fNumPlas); + const uint16_t* pl = &(fPLA[0]); + for (uint8_t j=0; j<fNumPlas; j++, pl++) { + b = SnBitUtils::WriteTo(b, *pl); + } + b = SnBitUtils::WriteTo(b, fNumCardsMajLog); + b = SnBitUtils::WriteTo(b, fEnableThermTrig); + b = SnBitUtils::WriteTo(b, fForceTrigPeriod); + b = SnBitUtils::WriteTo(b, fHeartBeatPeriod); + b = SnBitUtils::WriteTo(b, fAmpsOn); + b = SnBitUtils::WriteTo(b, fEvtThrtlPeriodMs); + b = SnBitUtils::WriteTo(b, fPowerMode); + b = SnBitUtils::WriteTo(b, fBatVoltLowPwr); + b = SnBitUtils::WriteTo(b, fCommWinPeriod); + b = SnBitUtils::WriteTo(b, fCommWinDuration); + b = SnBitUtils::WriteTo(b, fCommSendData); + b = SnBitUtils::WriteTo(b, fCommWinPrdLowPwr); + b = SnBitUtils::WriteTo(b, fCommWinDurLowPwr); + b = SnBitUtils::WriteTo(b, fWatchDogPeriod); + if (fStreamHiLoPlas!=0) { + pl = fPLA; + uint16_t hi, lo; + for (uint8_t j=0; j<fNumPlas; j++, pl++) { + GetHiLoPlas(*pl, hi, lo); + b = SnBitUtils::WriteTo(b, hi); + b = SnBitUtils::WriteTo(b, lo); + } + } + } + + bool ReadFromFile(const char* cfile); + bool WriteToFile(const char* cfile) const; + + void Reset() { + memset(fLabel, 0, sizeof(char)*kConfLblLen); + if (ReadFromFile(kDefConfFile)==false) { + // couldn't get default. use hardcoded version. + SetHardDefaults(); + } + } + + uint32_t SizeOf() const { + // returns the num of bytes needed to stream this object + // = size of member vars + 1 for i/o version + extra PLA strings (maybe) + // + length of label string + return SizeOf(fStreamHiLoPlas!=0, strlen(fLabel)); + } + + static void SetMacAddress(); + static uint64_t GetMacAddress() { + if (fgMacAdr==0) { + SetMacAddress(); + } + return fgMacAdr; + } + + static uint32_t GetLabelMaxLen() { return kConfLblLen; } + + static void GetHiLoPlas(const uint16_t pla, + uint16_t& hiPla, + uint16_t& loPla, + const bool r2l=false); +}; + +#endif // SN_SnConfigFrame