Back to home page

Project CMSSW displayed by LXR

 
 

    


File indexing completed on 2024-04-06 12:10:39

0001 #include <vector>
0002 #include <map>
0003 #include <set>
0004 #include <algorithm>
0005 
0006 #include "FWCore/ParameterSet/interface/FileInPath.h"
0007 #include "DataFormats/FEDRawData/interface/FEDNumbering.h"
0008 #include "DataFormats/FEDRawData/interface/FEDHeader.h"
0009 #include "DataFormats/FEDRawData/interface/FEDTrailer.h"
0010 #include "DataFormats/EcalDetId/interface/EcalDetIdCollections.h"
0011 #include "FWCore/Utilities/interface/CRC16.h"
0012 
0013 #include "EventFilter/ESDigiToRaw/src/ESDataFormatterV4.h"
0014 
0015 using namespace std;
0016 using namespace edm;
0017 
0018 const int ESDataFormatterV4::bDHEAD = 2;
0019 const int ESDataFormatterV4::bDH = 6;
0020 const int ESDataFormatterV4::bDEL = 24;
0021 const int ESDataFormatterV4::bDERR = 8;
0022 const int ESDataFormatterV4::bDRUN = 24;
0023 const int ESDataFormatterV4::bDRUNTYPE = 32;
0024 const int ESDataFormatterV4::bDTRGTYPE = 16;
0025 const int ESDataFormatterV4::bDCOMFLAG = 8;
0026 const int ESDataFormatterV4::bDORBIT = 32;
0027 const int ESDataFormatterV4::bDVMAJOR = 8;
0028 const int ESDataFormatterV4::bDVMINOR = 8;
0029 const int ESDataFormatterV4::bDCH = 4;
0030 const int ESDataFormatterV4::bDOPTO = 8;
0031 
0032 const int ESDataFormatterV4::sDHEAD = 28;
0033 const int ESDataFormatterV4::sDH = 24;
0034 const int ESDataFormatterV4::sDEL = 0;
0035 const int ESDataFormatterV4::sDERR = bDEL + sDEL;
0036 const int ESDataFormatterV4::sDRUN = 0;
0037 const int ESDataFormatterV4::sDRUNTYPE = 0;
0038 const int ESDataFormatterV4::sDTRGTYPE = 0;
0039 const int ESDataFormatterV4::sDCOMFLAG = bDTRGTYPE + sDTRGTYPE;
0040 const int ESDataFormatterV4::sDORBIT = 0;
0041 const int ESDataFormatterV4::sDVMINOR = 8;
0042 const int ESDataFormatterV4::sDVMAJOR = bDVMINOR + sDVMINOR;
0043 const int ESDataFormatterV4::sDCH = 0;
0044 const int ESDataFormatterV4::sDOPTO = 16;
0045 
0046 const int ESDataFormatterV4::bKEC = 8;  // KCHIP packet event counter
0047 const int ESDataFormatterV4::bKFLAG2 = 8;
0048 const int ESDataFormatterV4::bKBC = 12;  // KCHIP packet bunch counter
0049 const int ESDataFormatterV4::bKFLAG1 = 4;
0050 const int ESDataFormatterV4::bKET = 1;
0051 const int ESDataFormatterV4::bKCRC = 1;
0052 const int ESDataFormatterV4::bKCE = 1;
0053 const int ESDataFormatterV4::bKID = 16;
0054 const int ESDataFormatterV4::bFIBER = 6;  // Fiber number
0055 const int ESDataFormatterV4::bKHEAD1 = 2;
0056 const int ESDataFormatterV4::bKHEAD2 = 2;
0057 const int ESDataFormatterV4::bKHEAD = 4;
0058 
0059 const int ESDataFormatterV4::sKEC = 16;
0060 const int ESDataFormatterV4::sKFLAG2 = 16;
0061 const int ESDataFormatterV4::sKBC = 0;
0062 const int ESDataFormatterV4::sKFLAG1 = 24;
0063 const int ESDataFormatterV4::sKET = 0;
0064 const int ESDataFormatterV4::sKCRC = bKET + sKET;
0065 const int ESDataFormatterV4::sKCE = bKCRC + sKCRC;
0066 const int ESDataFormatterV4::sKID = 0;
0067 const int ESDataFormatterV4::sFIBER = bKID + sKID + 1;
0068 const int ESDataFormatterV4::sKHEAD1 = bFIBER + sFIBER + 2;
0069 const int ESDataFormatterV4::sKHEAD2 = bKHEAD1 + sKHEAD1;
0070 const int ESDataFormatterV4::sKHEAD = 28;
0071 
0072 const int ESDataFormatterV4::bADC0 = 16;
0073 const int ESDataFormatterV4::bADC1 = 16;
0074 const int ESDataFormatterV4::bADC2 = 16;
0075 const int ESDataFormatterV4::bPACE = 2;
0076 const int ESDataFormatterV4::bSTRIP = 5;
0077 const int ESDataFormatterV4::bE0 = 1;
0078 const int ESDataFormatterV4::bE1 = 1;
0079 const int ESDataFormatterV4::bHEAD = 4;
0080 
0081 const int ESDataFormatterV4::sADC0 = 0;
0082 const int ESDataFormatterV4::sADC1 = bADC0 + sADC0;
0083 const int ESDataFormatterV4::sADC2 = 0;
0084 const int ESDataFormatterV4::sSTRIP = bADC2 + sADC2;
0085 const int ESDataFormatterV4::sPACE = bSTRIP + sSTRIP;
0086 const int ESDataFormatterV4::sE0 = bSTRIP + sSTRIP + 1;
0087 const int ESDataFormatterV4::sE1 = bE0 + sE0;
0088 const int ESDataFormatterV4::sHEAD = 28;
0089 
0090 const int ESDataFormatterV4::bOEMUTTCEC = 32;
0091 const int ESDataFormatterV4::bOEMUTTCBC = 16;
0092 const int ESDataFormatterV4::bOEMUKEC = 8;
0093 const int ESDataFormatterV4::bOHEAD = 4;
0094 
0095 const int ESDataFormatterV4::sOEMUTTCEC = 0;
0096 const int ESDataFormatterV4::sOEMUTTCBC = 0;
0097 const int ESDataFormatterV4::sOEMUKEC = 16;
0098 const int ESDataFormatterV4::sOHEAD = 28;
0099 
0100 ESDataFormatterV4::ESDataFormatterV4(const ParameterSet& ps) : ESDataFormatter(ps) {
0101   lookup_ = ps.getUntrackedParameter<FileInPath>("LookupTable");
0102 
0103   // initialize look-up table
0104   for (int i = 0; i < 2; ++i)
0105     for (int j = 0; j < 2; ++j)
0106       for (int k = 0; k < 40; ++k)
0107         for (int m = 0; m < 40; m++) {
0108           fedId_[i][j][k][m] = -1;
0109           kchipId_[i][j][k][m] = -1;
0110           paceId_[i][j][k][m] = -1;
0111           bundleId_[i][j][k][m] = -1;
0112           fiberId_[i][j][k][m] = -1;
0113           optoId_[i][j][k][m] = -1;
0114         }
0115 
0116   for (int i = 0; i < 56; ++i) {
0117     for (int j = 0; j < 3; ++j)
0118       fedIdOptoRx_[i][j] = false;
0119   }
0120 
0121   for (int i = 0; i < 56; ++i) {
0122     for (int j = 0; j < 3; ++j)
0123       for (int k = 0; k < 12; k++)
0124         fedIdOptoRxFiber_[i][j][k] = false;
0125   }
0126 
0127   // read in look-up table
0128   int nLines, iz, ip, ix, iy, fed, kchip, pace, bundle, fiber, optorx;
0129   ifstream file;
0130   file.open(lookup_.fullPath().c_str());
0131   if (file.is_open()) {
0132     file >> nLines;
0133 
0134     for (int i = 0; i < nLines; ++i) {
0135       int fedId = -1;
0136       file >> iz >> ip >> ix >> iy >> fed >> kchip >> pace >> bundle >> fiber >> optorx;
0137 
0138       fedId = fedId_[(3 - iz) / 2 - 1][ip - 1][ix - 1][iy - 1] = fed;
0139       kchipId_[(3 - iz) / 2 - 1][ip - 1][ix - 1][iy - 1] = kchip;
0140       paceId_[(3 - iz) / 2 - 1][ip - 1][ix - 1][iy - 1] = pace - 1;
0141       bundleId_[(3 - iz) / 2 - 1][ip - 1][ix - 1][iy - 1] = bundle;
0142       fiberId_[(3 - iz) / 2 - 1][ip - 1][ix - 1][iy - 1] = fiber;
0143       optoId_[(3 - iz) / 2 - 1][ip - 1][ix - 1][iy - 1] = optorx;
0144 
0145       if (fedId < FEDNumbering::MINPreShowerFEDID || fedId > FEDNumbering::MAXPreShowerFEDID) {
0146         if (debug_)
0147           cout << "ESDataFormatterV4::ESDataFormatterV4 : fedId value : " << fedId
0148                << " out of ES range, at lookup table line : " << i << endl;
0149       } else if (optorx < 1 || optorx > 3) {
0150         if (debug_)
0151           cout << "ESDataFormatterV4::ESDataFormatterV4 : optorx value : " << optorx
0152                << " out of ES range, at lookup table line : " << i << endl;
0153       } else {  // all good ..
0154         int fedidx = fed - FEDNumbering::MINPreShowerFEDID;
0155         fedIdOptoRx_[fedidx][optorx - 1] = true;
0156         if (fiber > 0 && fiber < 13) {
0157           fedIdOptoRxFiber_[fedidx][optorx - 1][fiber - 1] = true;
0158         } else {
0159           if (debug_)
0160             cout << "ESDataFormatterV4::ESDataFormatterV4 : fiber value : " << fiber
0161                  << " out of ES range, at lookup table line : " << i << endl;
0162         }
0163       }
0164     }
0165 
0166   } else {
0167     if (debug_)
0168       cout << "ESDataFormatterV4::ESDataFormatterV4 : Look up table file can not be found in "
0169            << lookup_.fullPath().c_str() << endl;
0170   }
0171 
0172   file.close();
0173 }
0174 
0175 ESDataFormatterV4::~ESDataFormatterV4() {}
0176 
0177 struct ltfiber {
0178   bool operator()(const pair<int, int> s1, const pair<int, int> s2) const { return (s1.second < s2.second); }
0179 };
0180 
0181 bool ltstrip(const ESDataFormatterV4::Word64& s1, const ESDataFormatterV4::Word64& s2) {
0182   ESDataFormatterV4::Word64 PACESTRIP_MASK = 0x00ff000000000000ull;
0183   ESDataFormatterV4::Word64 PACESTRIP_OFFSET = 48ull;
0184 
0185   ESDataFormatterV4::Word64 val1 = (s1 & PACESTRIP_MASK) >> PACESTRIP_OFFSET;
0186   ESDataFormatterV4::Word64 val2 = (s2 & PACESTRIP_MASK) >> PACESTRIP_OFFSET;
0187 
0188   return (val1 < val2);
0189 }
0190 
0191 void ESDataFormatterV4::DigiToRaw(int fedId, Digis& digis, FEDRawData& fedRawData, Meta_Data const& meta_data) const {
0192   int ts[3] = {0, 0, 0};
0193   Word32 word1, word2;
0194   Word64 word;
0195   int numberOfStrips = 0;
0196 
0197   int optorx_ch_counts[3][12];
0198 
0199   int kchip, pace, optorx, fiber;
0200   map<int, vector<Word64> > map_data;
0201   vector<Word64> words;
0202 
0203   vector<Word32> testVector;
0204 
0205   set<pair<int, int>, ltfiber> set_of_kchip_fiber_in_optorx[3];
0206 
0207   map_data.clear();
0208 
0209   // clean optorx channel status fields:
0210   for (int i = 0; i < 3; ++i)
0211     for (int j = 0; j < 12; ++j)
0212       optorx_ch_counts[i][j] = 0;
0213 
0214   const DetDigis& detDigis = digis[fedId];
0215 
0216   if (debug_) {
0217     cout << "ESDataFormatterV4::DigiToRaw : FEDID : " << fedId << " size of detDigis : " << detDigis.size() << endl;
0218   }
0219 
0220   for (DetDigis::const_iterator it = detDigis.begin(); it != detDigis.end(); ++it) {
0221     const ESDataFrame& dataframe = (*it);
0222     const ESDetId& detId = dataframe.id();
0223 
0224     for (int is = 0; is < dataframe.size(); ++is)
0225       ts[is] = dataframe.sample(is).adc();
0226 
0227     kchip = kchipId_[(3 - detId.zside()) / 2 - 1][detId.plane() - 1][detId.six() - 1][detId.siy() - 1];
0228     pace = paceId_[(3 - detId.zside()) / 2 - 1][detId.plane() - 1][detId.six() - 1][detId.siy() - 1];
0229 
0230     if (debug_)
0231       cout << "Si : " << detId.zside() << " " << detId.plane() << " " << detId.six() << " " << detId.siy() << " "
0232            << detId.strip() << " (" << kchip << "," << pace << ") " << ts[0] << " " << ts[1] << " " << ts[2] << endl;
0233 
0234     // convert strip number from detector id to electronics id
0235     int siz = detId.zside();
0236     int sip = detId.plane();
0237     int six = detId.six();
0238     int siy = detId.siy();
0239     int sistrip = detId.strip();
0240     if (siz == 1 && sip == 1 && siy <= 20)
0241       sistrip = 33 - sistrip;
0242     if (siz == 1 && sip == 2 && six > 20)
0243       sistrip = 33 - sistrip;
0244     if (siz == -1 && sip == 1 && siy > 20)
0245       sistrip = 33 - sistrip;
0246     if (siz == -1 && sip == 2 && six <= 20)
0247       sistrip = 33 - sistrip;
0248 
0249     word1 = (ts[1] << sADC1) | (ts[0] << sADC0);
0250     word2 = (0xc << sHEAD) | (pace << sPACE) | ((sistrip - 1) << sSTRIP) | (ts[2] << sADC2);
0251     word = (Word64(word2) << 32) | Word64(word1);
0252 
0253     map_data[kchip].push_back(word);
0254 
0255     optorx = optoId_[(3 - detId.zside()) / 2 - 1][detId.plane() - 1][detId.six() - 1][detId.siy() - 1];
0256     fiber = fiberId_[(3 - detId.zside()) / 2 - 1][detId.plane() - 1][detId.six() - 1][detId.siy() - 1];
0257 
0258     optorx_ch_counts[optorx - 1][fiber - 1]++;  // increment number of strip hits on fiber status field ;
0259 
0260     set<pair<int, int>, ltfiber>& theSet = set_of_kchip_fiber_in_optorx[optorx - 1];
0261     theSet.insert(pair<int, int>(kchip, fiber));
0262 
0263     // mark global strip number in this FED
0264     ++numberOfStrips;
0265   }
0266 
0267   for (int iopto = 0; iopto < 3; ++iopto) {
0268     if (fedIdOptoRx_[fedId - FEDNumbering::MINPreShowerFEDID][iopto]) {
0269       word2 = (0x6 << sOHEAD) | (meta_data.kchip_ec << sOEMUKEC) | (meta_data.kchip_bc << sOEMUTTCBC);
0270       word1 = (meta_data.kchip_ec << sOEMUTTCEC);
0271       word = (Word64(word2) << 32) | Word64(word1);
0272       if (debug_)
0273         cout << "OPTORX: " << print(word) << endl;
0274       words.push_back(word);
0275 
0276       set<pair<int, int>, ltfiber>& theSet = set_of_kchip_fiber_in_optorx[iopto];
0277 
0278       if (debug_) {
0279         cout << "ESDataFormatterV4::DigiToRaw : FEDID : " << fedId << " size of  set_of_kchip_fiber_in_optorx[" << iopto
0280              << "] : " << theSet.size() << endl;
0281       }
0282 
0283       set<pair<int, int>, ltfiber>::const_iterator kit = theSet.begin();
0284 
0285       while (kit != theSet.end()) {
0286         const pair<int, int>& kchip_fiber = (*kit);
0287 
0288         if (debug_)
0289           cout << "KCHIP : " << kchip_fiber.first << " FIBER: " << kchip_fiber.second << endl;
0290 
0291         if (fedIdOptoRxFiber_[fedId - FEDNumbering::MINPreShowerFEDID][iopto][kchip_fiber.second - 1]) {
0292           // Set all PACEs enabled for MC
0293           word1 = (0 << sKFLAG1) | (0xf << sKFLAG2) | (((kchip_fiber.first << 2) | 0x02) << sKID);
0294           word2 = (0x9 << sKHEAD) | (meta_data.kchip_ec << sKEC) | (meta_data.kchip_bc << sKBC);
0295 
0296           word = (Word64(word2) << 32) | Word64(word1);
0297           if (debug_)
0298             cout << "KCHIP : " << print(word) << endl;
0299 
0300           words.push_back(word);
0301 
0302           vector<Word64>& data = map_data[kchip_fiber.first];
0303 
0304           // sort against stripid field, as hardware gives this order to strip data :
0305           sort(data.begin(), data.end(), ltstrip);
0306 
0307           for (unsigned int id = 0; id < data.size(); ++id) {
0308             if (debug_)
0309               cout << "Data  : " << print(data[id]) << endl;
0310             words.push_back(data[id]);
0311           }
0312         }
0313         ++kit;
0314       }
0315     }
0316   }
0317 
0318   int dataSize = (words.size() + 8) * sizeof(Word64);
0319 
0320   vector<Word64> DCCwords;
0321 
0322   word2 = (3 << sDHEAD) | (1 << sDH) | (meta_data.run_number << sDRUN);
0323   word1 = (numberOfStrips << sDEL) | (0xff << sDERR);
0324   word = (Word64(word2) << 32) | Word64(word1);
0325   DCCwords.push_back(word);
0326 
0327   word2 = (3 << sDHEAD) | (2 << sDH);
0328   word1 = 0;
0329   word = (Word64(word2) << 32) | Word64(word1);
0330   DCCwords.push_back(word);
0331 
0332   word2 = (3 << sDHEAD) | (3 << sDH) | (4 << sDVMAJOR) | (3 << sDVMINOR);
0333   word1 = (meta_data.orbit_number << sDORBIT);
0334   word = (Word64(word2) << 32) | Word64(word1);
0335   DCCwords.push_back(word);
0336 
0337   for (int iopto = 0; iopto < 3; ++iopto) {
0338     // N optorx module header word:
0339     word1 = 0;
0340     if (fedIdOptoRx_[fedId - FEDNumbering::MINPreShowerFEDID][iopto]) {
0341       word2 = (3 << sDHEAD) | ((iopto + 4) << sDH) | (0x80 << sDOPTO);
0342       int ich = 0;
0343       for (ich = 0; ich < 4; ++ich) {
0344         int chStatus = (optorx_ch_counts[iopto][ich + 8] > 0) ? 0xe : 0xd;
0345         chStatus = (fedIdOptoRxFiber_[fedId - FEDNumbering::MINPreShowerFEDID][iopto][ich + 8]) ? chStatus : 0x00;
0346         word2 |= (chStatus << (ich * 4));  //
0347       }
0348 
0349       for (ich = 0; ich < 8; ++ich) {
0350         int chStatus = (optorx_ch_counts[iopto][ich] > 0) ? 0xe : 0xd;
0351         chStatus = (fedIdOptoRxFiber_[fedId - FEDNumbering::MINPreShowerFEDID][iopto][ich]) ? chStatus : 0x00;
0352         word1 |= (chStatus << (ich * 4));
0353       }
0354     } else
0355       word2 = (3 << sDHEAD) | ((iopto + 4) << sDH) | (0x00 << sDOPTO);
0356 
0357     word = (Word64(word2) << 32) | Word64(word1);
0358     DCCwords.push_back(word);
0359   }
0360 
0361   // Output (data size in Bytes)
0362   // FEDRawData * rawData = new FEDRawData(dataSize);
0363   fedRawData.resize(dataSize);
0364 
0365   Word64* w = reinterpret_cast<Word64*>(fedRawData.data());
0366 
0367   // header
0368   FEDHeader::set(reinterpret_cast<unsigned char*>(w), trgtype_, meta_data.lv1, meta_data.bx, fedId);
0369   w++;
0370 
0371   // ES-DCC
0372   for (unsigned int i = 0; i < DCCwords.size(); ++i) {
0373     if (debug_)
0374       cout << "DCC  : " << print(DCCwords[i]) << endl;
0375     *w = DCCwords[i];
0376     w++;
0377   }
0378 
0379   // event data
0380   for (unsigned int i = 0; i < words.size(); ++i) {
0381     *w = words[i];
0382     w++;
0383   }
0384 
0385   // trailer
0386   FEDTrailer::set(reinterpret_cast<unsigned char*>(w),
0387                   dataSize / sizeof(Word64),
0388                   evf::compute_crc(fedRawData.data(), dataSize),
0389                   0,
0390                   0);
0391 }