00001
00002 #include "DataFormats/MuonDetId/interface/CSCDetId.h"
00003 #include "EventFilter/CSCRawToDigi/interface/CSCCFEBData.h"
00004 #include "EventFilter/CSCRawToDigi/interface/CSCCFEBTimeSlice.h"
00005 #include "EventFilter/CSCRawToDigi/interface/CSCBadCFEBTimeSlice.h"
00006 #include "DataFormats/CSCDigi/interface/CSCStripDigi.h"
00007 #include "DataFormats/CSCDigi/interface/CSCCFEBStatusDigi.h"
00008 #include "FWCore/MessageLogger/interface/MessageLogger.h"
00009 #include <cassert>
00010
00011 CSCCFEBData::CSCCFEBData(unsigned number, unsigned short * buf)
00012 : theSize(0), boardNumber_(number), theNumberOfSamples(0) {
00013
00014
00015 unsigned pos = 0;
00016
00017 unsigned maxSamples = 8;
00018 theSliceStarts.reserve(8);
00019 while(theNumberOfSamples < maxSamples) {
00020
00021 CSCBadCFEBTimeSlice * badSlice
00022 = reinterpret_cast<CSCBadCFEBTimeSlice *>(buf+pos);
00023 if(badSlice->check()) {
00024
00025 theSliceStarts.push_back(std::pair<int, bool>(pos, false));
00026 pos += badSlice->sizeInWords();
00027
00028 bWords.push_back(badSlice->word(1).data());
00029 }
00030 else {
00031
00032 CSCCFEBTimeSlice * goodSlice
00033 = reinterpret_cast<CSCCFEBTimeSlice *>(buf+pos);
00034 if(goodSlice->check()) {
00035
00036 theSliceStarts.push_back(std::pair<int, bool>(pos, true));
00037
00038
00039 maxSamples = goodSlice->sixteenSamples() ? 16 : 8;
00040 pos += goodSlice->sizeInWords();
00041 }
00042 else {
00043 LogTrace ("CSCCFEBData|CSCRawToDigi")
00044 << "CORRUPT CFEB DATA slice " << theNumberOfSamples << std::hex << " "
00045 << *(buf+pos+3) << " " << *(buf+pos+2) << " " << *(buf+pos+1) << " "<< *(buf+pos);
00046
00047 pos += 100;
00048 }
00049 }
00050 ++theNumberOfSamples;
00051 }
00052 theSize = pos;
00053 memcpy(theData, buf, theSize*2);
00054 }
00055
00056
00057 CSCCFEBData::CSCCFEBData(unsigned number, bool sixteenSamples)
00058 : boardNumber_(number), theNumberOfSamples(sixteenSamples ? 16 : 8)
00059 {
00060 theSliceStarts.reserve(theNumberOfSamples);
00061
00062
00063 CSCCFEBSCAControllerWord scaWord;
00064 scaWord.ts_flag = sixteenSamples;
00065
00066
00067 CSCCFEBTimeSlice slice;
00068 slice.setControllerWord(scaWord);
00069
00070 for(unsigned i = 0; i < theNumberOfSamples; ++i)
00071 {
00072 unsigned short * pos = theData+i*100;
00073 memcpy(pos, &slice, 200);
00074 theSliceStarts.push_back(std::pair<int,bool>(i*100, true));
00075 }
00076 theSize = theNumberOfSamples*100;
00077 }
00078
00079 void CSCCFEBData::add(const CSCStripDigi & digi, int layer)
00080 {
00081 std::vector<int> scaCounts = digi.getADCCounts();
00082 for(unsigned itime = 0; itime < theNumberOfSamples; ++itime)
00083 {
00084 unsigned channel = (digi.getStrip()-1) % 16 + 1;
00085 unsigned value = scaCounts[itime] & 0xFFF;
00086
00087 const CSCCFEBTimeSlice * slice = timeSlice(itime);
00088 assert(slice != 0);
00089 slice->timeSample(layer, channel)->adcCounts = value;
00090 }
00091 }
00092
00093 const CSCCFEBTimeSlice * CSCCFEBData::timeSlice(unsigned i) const
00094 {
00095 const CSCCFEBTimeSlice * result;
00096 assert(i < theNumberOfSamples);
00097 std::pair<int,bool> start = theSliceStarts[i];
00098
00099 if(!start.second)
00100 {
00101 result = 0;
00102 }
00103 else
00104 {
00105 result = reinterpret_cast<const CSCCFEBTimeSlice *>(theData+start.first);
00106 }
00107 return result;
00108 }
00109
00110
00111 unsigned CSCCFEBData::adcCounts(unsigned layer, unsigned channel, unsigned timeBin) const
00112 {
00113 unsigned result = 0;
00114 const CSCCFEBTimeSlice * slice = timeSlice(timeBin);
00115
00116 if(slice) result = slice->timeSample(layer, channel)->adcCounts;
00117 return result;
00118 }
00119 unsigned CSCCFEBData::adcOverflow(unsigned layer, unsigned channel, unsigned timeBin) const
00120 {
00121 unsigned result = 0;
00122 const CSCCFEBTimeSlice * slice = timeSlice(timeBin);
00123
00124 if(slice) result = slice->timeSample(layer, channel)->adcOverflow;
00125 return result;
00126 }
00127 unsigned CSCCFEBData::controllerData(unsigned layer, unsigned channel, unsigned timeBin) const
00128 {
00129 unsigned result = 0;
00130 const CSCCFEBTimeSlice * slice = timeSlice(timeBin);
00131
00132 if(slice) result = slice->timeSample(layer, channel)->controllerData;
00133 return result;
00134 }
00135
00136 unsigned CSCCFEBData::overlappedSampleFlag(unsigned layer, unsigned channel, unsigned timeBin) const
00137 {
00138 unsigned result = 0;
00139 const CSCCFEBTimeSlice * slice = timeSlice(timeBin);
00140
00141 if(slice) result = slice->timeSample(layer, channel)->overlappedSampleFlag;
00142 return result;
00143 }
00144 unsigned CSCCFEBData::errorstat(unsigned layer, unsigned channel, unsigned timeBin) const
00145 {
00146 unsigned result = 0;
00147 const CSCCFEBTimeSlice * slice = timeSlice(timeBin);
00148
00149 if(slice) result = slice->timeSample(layer, channel)->errorstat;
00150 return result;
00151 }
00152
00153
00154 CSCCFEBStatusDigi CSCCFEBData::statusDigi() const
00155 {
00159
00160 std::vector<uint16_t> crcWords(nTimeSamples());
00161 std::vector<uint16_t> contrWords(nTimeSamples());
00162
00163 if (nTimeSamples()==0)
00164 {
00165 LogTrace("CSCCFEBData|CSCRawToDigi") << "nTimeSamples is zero - CFEB data corrupt?";
00166 }
00167 else
00168 {
00169 for(unsigned itime = 0; itime < nTimeSamples(); ++itime) {
00170 const CSCCFEBTimeSlice * slice = timeSlice(itime);
00171
00172 if (slice) crcWords[itime] = slice->get_crc();
00173 if (slice)
00174 {
00175 int layer=1;
00176 for(unsigned i = 0; i < 16; ++i)
00177 {
00178 contrWords[itime] |= slice->timeSample(i*6+layer-1)->controllerData << i;
00179 }
00180 }
00181
00182 }
00183 }
00184
00185 CSCCFEBStatusDigi result(boardNumber_+1, crcWords, contrWords, bWords);
00186 return result;
00187 }
00188
00189
00190
00191 void CSCCFEBData::digis(uint32_t idlayer, std::vector<CSCStripDigi> & result )
00192 {
00193
00194
00195 result.reserve(16);
00196 std::vector<int> sca(nTimeSamples());
00197 std::vector<uint16_t> overflow(nTimeSamples());
00198 std::vector<uint16_t> overlap(nTimeSamples());
00199 std::vector<uint16_t> errorfl(nTimeSamples());
00200
00201 bool me1a = (CSCDetId::station(idlayer)==1) && (CSCDetId::ring(idlayer)==4);
00202 bool zplus = (CSCDetId::endcap(idlayer) == 1);
00203 bool me1b = (CSCDetId::station(idlayer)==1) && (CSCDetId::ring(idlayer)==1);
00204
00205 unsigned layer = CSCDetId::layer(idlayer);
00206
00207 for(unsigned ichannel = 1; ichannel <= 16; ++ichannel)
00208 {
00209 if (nTimeSamples()==0)
00210 {
00211 LogTrace("CSCCFEBData|CSCRawToDigi") << "nTimeSamples is zero - CFEB data corrupt?";
00212 break;
00213 }
00214
00215 for(unsigned itime = 0; itime < nTimeSamples(); ++itime)
00216 {
00217 const CSCCFEBTimeSlice * slice = timeSlice(itime);
00218 if (slice)
00219 {
00220 CSCCFEBDataWord * word;
00221 word = slice->timeSample(layer, ichannel);
00222 if (word)
00223 {
00224 sca[itime] = word->adcCounts;
00225 overflow[itime] = word->adcOverflow;
00226 overlap[itime] = word->overlappedSampleFlag;
00227 errorfl[itime] = word->errorstat;
00228 }
00229 }
00230 }
00231 if (sca.empty())
00232 {
00233 LogTrace("CSCCFEBData|CSCRawToDigi") << "ADC counts empty - CFEB data corrupt?";
00234 break;
00235 }
00236 int strip = ichannel + 16*boardNumber_;
00237 if ( me1a ) strip = strip%64;
00238 if ( me1a && zplus ) { strip = 17-strip; }
00239 if ( me1b && !zplus) { strip = 65 - strip;}
00240 result.push_back(CSCStripDigi(strip, sca, overflow, overlap, errorfl));
00241 }
00242 }
00243
00244
00245
00246 std::vector<CSCStripDigi> CSCCFEBData::digis(unsigned idlayer)
00247 {
00248
00249 std::vector<CSCStripDigi> result;
00250 uint32_t layer= idlayer;
00251 digis(layer, result);
00252 return result;
00253 }
00254
00255
00256
00257 bool CSCCFEBData::check() const
00258 {
00259 bool result = true;
00260 for(unsigned i = 0; i < theNumberOfSamples; ++i)
00261 {
00262 const CSCCFEBTimeSlice * slice = timeSlice(i);
00263 if(slice==0 || !timeSlice(i)->check()) result = false;
00264 }
00265 return result;
00266 }
00267
00268 std::ostream & operator<<(std::ostream & os, const CSCCFEBData & data)
00269 {
00270 os << "printing CFEB data sample by sample " << std::endl;
00271 for(unsigned ilayer = 1; ilayer <= 6; ++ilayer)
00272 {
00273 for(unsigned channel = 1; channel <= 16; ++channel)
00274 {
00275 unsigned strip = channel + data.boardNumber_*16;
00276 os << "Strip " << strip << " ";
00277 for(unsigned timeBin = 0; timeBin < data.nTimeSamples(); ++timeBin)
00278 {
00279 os << data.adcCounts(ilayer, channel, timeBin) << " " ;
00280 }
00281 os << std::endl;
00282 }
00283 }
00284 return os;
00285 }
00286
00287 std::vector < std::vector<CSCStripDigi> > CSCCFEBData::stripDigis()
00288 {
00289 std::vector < std::vector<CSCStripDigi> > result;
00290 for (int layer = 1; layer <= 6; ++layer)
00291 {
00292 result.push_back(digis(layer));
00293 }
00294 return result;
00295 }
00296