00001 #include "EventFilter/CSCRawToDigi/interface/CSCALCTHeader.h"
00002 #include "EventFilter/CSCRawToDigi/interface/CSCDMBHeader.h"
00003 #include "DataFormats/MuonDetId/interface/CSCDetId.h"
00004 #include "EventFilter/CSCRawToDigi/src/bitset_append.h"
00005 #include "EventFilter/CSCRawToDigi/src/cscPackerCompare.h"
00006 #include <iomanip>
00007
00008 bool CSCALCTHeader::debug=false;
00009 short unsigned int CSCALCTHeader::firmwareVersion=2006;
00010
00011 CSCALCTHeader::CSCALCTHeader(int chamberType)
00012 : header2006(chamberType)
00013 {
00014 memcpy(theOriginalBuffer, &header2006, header2006.sizeInWords()*2);
00015
00016 }
00017
00018 CSCALCTHeader::CSCALCTHeader(const unsigned short * buf) {
00023 static unsigned short int collisionMaskWordcount[7] = { 8, 8,12,16,16,24,28};
00024 static unsigned short int hotChannelMaskWordcount[7] = {18,18,24,36,36,48,60};
00025
00026
00028 if (buf[0]==0xDB0A) {
00029 firmwareVersion=2007;
00030 }
00031 else if ( (buf[0]&0xF800)==0x6000 ) {
00032 firmwareVersion=2006;
00033 }
00034 else {
00035 edm::LogError("CSCALCTHeader|CSCRawToDigi") << "failed to determine ALCT firmware version!!";
00036 }
00037
00038 LogTrace("CSCALCTHeader|CSCRawToDigi") << "firmware version - " << firmwareVersion;
00039
00041 switch (firmwareVersion) {
00042 case 2006:
00043 memcpy(&header2006, buf, header2006.sizeInWords()*2);
00044 buf +=header2006.sizeInWords();
00045 memcpy(&alcts2006, buf, alcts2006.sizeInWords()*2);
00046 buf +=alcts2006.sizeInWords();
00047 break;
00048
00049 case 2007:
00050 memcpy(&header2007, buf, header2007.sizeInWords()*2);
00051 buf +=header2007.sizeInWords();
00052 sizeInWords2007_ = header2007.sizeInWords();
00054 if (header2007.configPresent==1) {
00055 memcpy(&virtexID, buf, virtexID.sizeInWords()*2);
00056 buf +=virtexID.sizeInWords();
00057 sizeInWords2007_ = virtexID.sizeInWords();
00058 memcpy(&configRegister, buf, configRegister.sizeInWords()*2);
00059 buf +=configRegister.sizeInWords();
00060 sizeInWords2007_ += configRegister.sizeInWords();
00061
00062 collisionMasks.resize(collisionMaskWordcount[header2007.boardType]);
00063 for (unsigned int i=0; i<collisionMaskWordcount[header2007.boardType]; ++i){
00064 memcpy(&collisionMasks[i], buf, collisionMasks[i].sizeInWords()*2);
00065 buf += collisionMasks[i].sizeInWords();
00066 sizeInWords2007_ += collisionMasks[i].sizeInWords();
00067 }
00068
00069 hotChannelMasks.resize(hotChannelMaskWordcount[header2007.boardType]);
00070 for (unsigned int i=0; i<hotChannelMaskWordcount[header2007.boardType]; ++i) {
00071 memcpy(&hotChannelMasks[i], buf, hotChannelMasks[i].sizeInWords()*2);
00072 buf += hotChannelMasks[i].sizeInWords();
00073 sizeInWords2007_ += hotChannelMasks[i].sizeInWords();
00074 }
00075 }
00076
00077 alcts.resize(header2007.lctBins*2);
00078 for (unsigned int i=0; i<header2007.lctBins*2; ++i) {
00079 memcpy(&alcts[i], buf, alcts[i].sizeInWords()*2);
00080 buf += alcts[i].sizeInWords();
00081 sizeInWords2007_ += alcts[i].sizeInWords();
00082 }
00083 break;
00084
00085 default:
00086 edm::LogError("CSCALCTHeader|CSCRawToDigi")
00087 <<"couldn't construct: ALCT firmware version is bad/not defined!";
00088 break;
00089 }
00090
00092 if ((firmwareVersion==2006)||(firmwareVersion==2007))
00093 memcpy(theOriginalBuffer, buf-sizeInWords(), sizeInWords()*2);
00094
00095 }
00096
00097
00098 CSCALCTHeader::CSCALCTHeader(const CSCALCTStatusDigi & digi){
00099 CSCALCTHeader(digi.header());
00100 }
00101
00102 void CSCALCTHeader::setEventInformation(const CSCDMBHeader & dmb) {
00103 header2006.setEventInformation(dmb);
00104 }
00105
00106
00107 unsigned short CSCALCTHeader::nLCTChipRead() const {
00108 if(firmwareVersion == 2006) {
00109 return header2006.nLCTChipRead();
00110 }
00111 else {
00112
00113
00114
00115
00116 }
00117 return 0;
00118 }
00119
00120
00121 std::vector<CSCALCTDigi> CSCALCTHeader::ALCTDigis() const
00122 {
00123 std::vector<CSCALCTDigi> result;
00124 result.reserve(alcts.size());
00125
00126 switch (firmwareVersion) {
00127 case 2006:
00128 {
00129 result = alcts2006.ALCTDigis();
00130 break;
00131 }
00132 case 2007:
00133 {
00134 for (unsigned int i=0; i<alcts.size(); ++i) {
00135 CSCALCTDigi digi(alcts[i].valid, alcts[i].quality, alcts[i].accel, alcts[i].pattern,
00136 alcts[i].keyWire, (int)i/2, i%2+1);
00137 result.push_back(digi);
00138 }
00139 break;
00140 }
00141 default:
00142 edm::LogError("CSCALCTHeader|CSCRawToDigi")
00143 <<"Empty Digis: ALCT firmware version is bad/not defined!";
00144 break;
00145 }
00146 for(unsigned i = 0; i < result.size(); ++i) {result[i].setFullBX(BXNCount());}
00147 return result;
00148
00149 }
00150
00151
00152 void CSCALCTHeader::add(const std::vector<CSCALCTDigi> & digis)
00153 {
00154 if(firmwareVersion != 2006) {
00155 throw cms::Exception("CSCDigi2Raw")
00156 << "The ALCTDigis do not live in the ALCT header past the 2006 firmware version";
00157 }
00158 alcts2006.add(digis);
00159 }
00160
00161
00162 boost::dynamic_bitset<> CSCALCTHeader::pack()
00163 {
00164 boost::dynamic_bitset<> result;
00165 if(firmwareVersion == 2006)
00166 {
00167 boost::dynamic_bitset<> header
00168 = bitset_utilities::ushortToBitset(header2006.sizeInWords()*16,
00169 (unsigned short *) &header2006);
00170 boost::dynamic_bitset<> alcts
00171 = bitset_utilities::ushortToBitset(alcts2006.sizeInWords()*16,
00172 (unsigned short *) &alcts2006);
00173 result = bitset_utilities::append(header, alcts);
00174
00175 }
00176 return result;
00177 }
00178
00179
00180
00181 void CSCALCTHeader::selfTest()
00182 {
00183
00184 for(int station = 1; station <= 4; ++station)
00185 {
00186 CSCDetId detId(1, station, 1, 1, 0);
00187 CSCALCTDigi alct0(true, 1, 1, 1, 10, 6, 1);
00188 CSCALCTDigi alct1(true, 1, 1, 0, 11, 6, 2);
00189
00190 std::vector<CSCALCTDigi> oldAlcts;
00191 oldAlcts.push_back(alct0);
00192 oldAlcts.push_back(alct1);
00193 CSCALCTHeader alctHeader(detId.iChamberType());
00194
00195 alctHeader.add(oldAlcts);
00196
00197 std::vector<CSCALCTDigi> alcts = alctHeader.ALCTDigis();
00198 assert(alcts[0] == alct0);
00199 assert(alcts[1] == alct1);
00200
00201 cscClassPackerCompare(alctHeader);
00202
00203 }
00204 }
00205
00206 std::ostream & operator<<(std::ostream & os, const CSCALCTHeader & header)
00207 {
00208 os << "ALCT HEADER CSCID " << header.CSCID()
00209 << " L1ACC " << header.L1Acc() << std::endl;
00210 os << " time samples " << header.NTBins() << std::endl;
00211 return os;
00212 }
00213
00214