00001
00002
00003
00004
00005
00006 #include "SimCalorimetry/EcalSelectiveReadoutAlgos/src/EcalSelectiveReadout.h"
00007 #include "DataFormats/EcalDetId/interface/EcalSubdetector.h"
00008 #include "DataFormats/EcalDetId/interface/EcalElectronicsId.h"
00009 #include "FWCore/Utilities/interface/EDMException.h"
00010 #include "FWCore/MessageLogger/interface/MessageLogger.h"
00011 #include <string>
00012 #include <iomanip>
00013 #include <cassert>
00014
00015
00016 using std::vector;
00017
00018 const char EcalSelectiveReadout::srpFlagMarker[] = {'.', 'S', 'N', 'C',
00019 '4', '5', '6', '7'};
00020
00021 EcalSelectiveReadout::EcalSelectiveReadout(int dEta_, int dPhi_):
00022 theTriggerMap(0), theElecMap(0), dEta(dEta_), dPhi(dPhi_) {
00023 }
00024
00025 void EcalSelectiveReadout::resetEeRuInterest(){
00026
00027 for(size_t iCap=0; iCap < nEndcaps; ++iCap){
00028 for(int iDccPhi = 0; iDccPhi < nDccPerEe; ++iDccPhi){
00029 for(int iDccCh = 0; iDccCh < maxDccChs; ++iDccCh){
00030 eeRuInterest_[iCap][iDccPhi][iDccCh] = UNKNOWN;
00031 }
00032 }
00033 }
00034 }
00035
00036 void
00037 EcalSelectiveReadout::runSelectiveReadout0(const ttFlag_t ttFlags[nTriggerTowersInEta][nTriggerTowersInPhi]) {
00038
00039
00040
00041
00042 classifyTriggerTowers(ttFlags);
00043
00044
00045 int nTriggerTowerE[] = {0, 0, 0, 0, 0, 0, 0, 0};
00046 int nTriggerTowerB[] = {0, 0, 0, 0, 0, 0, 0, 0};
00047
00048 static int ncall = 0;
00049 if(ncall < 10){
00050 ++ncall;
00051 for(size_t iPhi = 0; iPhi < nTriggerTowersInPhi; ++iPhi){
00052 for(size_t iEta = 0; iEta < nTriggerTowersInEta; ++iEta){
00053 if(iEta < nEndcapTriggerTowersInEta
00054 || iEta >= nBarrelTriggerTowersInEta + nEndcapTriggerTowersInEta){
00055
00056 ++nTriggerTowerE[towerInterest[iEta][iPhi]];
00057 } else{
00058 ++nTriggerTowerB[towerInterest[iEta][iPhi]];
00059 }
00060
00061 assert(towerInterest[iEta][iPhi] >= 0
00062 && towerInterest[iEta][iPhi] <= 0x7);
00063 }
00064 }
00065 edm::LogInfo("EcalSelectiveReadout")
00066 << "without forced bit + with forced bit set:\n"
00067 << nTriggerTowerB[LOWINTEREST] << " + "
00068 << nTriggerTowerB[LOWINTEREST | FORCED_MASK]
00069 << " low interest TT(s) in barrel\n"
00070 << nTriggerTowerB[SINGLE] << " + "
00071 << nTriggerTowerB[SINGLE | FORCED_MASK]
00072 << " single TT(s) in barrel\n"
00073 << nTriggerTowerB[NEIGHBOUR] << " + "
00074 << nTriggerTowerB[NEIGHBOUR | FORCED_MASK]
00075 << " neighbor interest TT(s) in barrel\n"
00076 << nTriggerTowerB[CENTER] << " + "
00077 << nTriggerTowerB[CENTER | FORCED_MASK]
00078 << " centre interest TT(s) in barrel\n"
00079 << nTriggerTowerE[LOWINTEREST] << " + "
00080 << nTriggerTowerE[LOWINTEREST | FORCED_MASK]
00081 << " low interest TT(s) in endcap\n"
00082 << nTriggerTowerE[SINGLE] << " + "
00083 << nTriggerTowerE[SINGLE | FORCED_MASK]
00084 << " single TT(s) in endcap\n"
00085 << nTriggerTowerE[NEIGHBOUR] << " + "
00086 << nTriggerTowerE[NEIGHBOUR | FORCED_MASK]
00087 << " neighbor TT(s) in endcap\n"
00088 << nTriggerTowerE[CENTER] << " + "
00089 << nTriggerTowerE[CENTER | FORCED_MASK]
00090 << " center TT(s) in endcap\n";
00091 }
00092
00093
00094
00095 resetEeRuInterest();
00096
00097 #ifndef ECALSELECTIVEREADOUT_NOGEOM
00098 const std::vector<DetId>& endcapDetIds = theGeometry->getValidDetIds(DetId::Ecal, EcalEndcap);
00099 for(std::vector<DetId>::const_iterator eeDetIdItr = endcapDetIds.begin();
00100 eeDetIdItr != endcapDetIds.end(); ++eeDetIdItr){
00101
00102
00103
00104
00105 EcalTrigTowerDetId trigTower = theTriggerMap->towerOf(*eeDetIdItr);
00106 assert(trigTower.rawId() != 0);
00107 EEDetId eeDetId(*eeDetIdItr);
00108 int iz = (eeDetId.zside() > 0) ? 1 : 0;
00109
00110
00111
00112 combineFlags(eeRuInterest(eeDetId), getTowerInterest(trigTower));
00113 }
00114 #else //ECALSELECTIVEREADOUT_NOGEOM defined
00115 EEDetId xtal;
00116 for(int iZ0=0; iZ0<2; ++iZ0){
00117 for(unsigned iX0=0; iX0<nEndcapXBins; ++iX0){
00118 for(unsigned iY0=0; iY0<nEndcapYBins; ++iY0){
00119
00120 if (!(xtal.validDetId(iX0+1, iY0+1, (iZ0>0?1:-1)))){
00121 continue;
00122 }
00123 xtal = EEDetId(iX0+1, iY0+1, (iZ0>0?1:-1));
00124
00125 if(39 <= iX0 && iX0 <= 60 && 45 <= iY0 && iY0 <= 54){
00126 continue;
00127 }
00128
00129
00130 EcalTrigTowerDetId trigTower = theTriggerMap->towerOf(xtal);
00131 assert(trigTower.rawId() != 0);
00132
00133
00134
00135 combineFlags(eeRuInterest(xtal), getTowerInterest(trigTower));
00136
00137 assert(0<= eeRuInterest(xtal) && eeRuInterest(xtal) <= 0x7);
00138
00139 }
00140 }
00141 }
00142 #endif //ECALSELECTIVEREADOUT_NOGEOM not defined
00143 }
00144
00145 EcalSelectiveReadout::towerInterest_t
00146 EcalSelectiveReadout::getCrystalInterest(const EBDetId & ebDetId) const
00147 {
00148 EcalTrigTowerDetId thisTower = theTriggerMap->towerOf(ebDetId);
00149 return getTowerInterest(thisTower);
00150 }
00151
00152
00153 EcalSelectiveReadout::towerInterest_t
00154 EcalSelectiveReadout::getCrystalInterest(const EEDetId & eeDetId) const
00155 {
00156
00157
00158
00159
00160 return const_cast<EcalSelectiveReadout*>(this)->eeRuInterest(eeDetId);
00161 }
00162
00163 EcalSelectiveReadout::towerInterest_t
00164 EcalSelectiveReadout::getSuperCrystalInterest(const EcalScDetId& scDetId) const
00165 {
00166 return const_cast<EcalSelectiveReadout*>(this)->eeRuInterest(scDetId);
00167 }
00168
00169 EcalSelectiveReadout::towerInterest_t&
00170 EcalSelectiveReadout::eeRuInterest(const EEDetId& eeDetId){
00171 const EcalElectronicsId& id = theElecMap->getElectronicsId(eeDetId);
00172 const int iZ0 = id.zside()>0 ? 1 : 0;
00173 const int iDcc0 = id.dccId()-1;
00174 const int iDccPhi0 = (iDcc0<9)?iDcc0:(iDcc0-45);
00175 const int iDccCh0 = id.towerId()-1;
00176 assert(0 <= iDccPhi0 && iDccPhi0 < nDccPerEe);
00177 assert(0 <= iDccCh0 && iDccCh0 < maxDccChs);
00178
00179 assert(eeRuInterest_[iZ0][iDccPhi0][iDccCh0] == UNKNOWN
00180 || (0<= eeRuInterest_[iZ0][iDccPhi0][iDccCh0]
00181 && eeRuInterest_[iZ0][iDccPhi0][iDccCh0] <=7));
00182
00183 return eeRuInterest_[iZ0][iDccPhi0][iDccCh0];
00184 }
00185
00186 EcalSelectiveReadout::towerInterest_t&
00187 EcalSelectiveReadout::eeRuInterest(const EcalScDetId& scDetId){
00188 std::pair<int, int> dccAndDccCh = theElecMap->getDCCandSC(scDetId);
00189 const int iZ0 = (scDetId.zside()>0) ? 1: 0;
00190 const int iDcc0 = dccAndDccCh.first-1;
00191 const int iDccPhi0 = (iDcc0<9)?iDcc0:(iDcc0-45);
00192 const int iDccCh0 = dccAndDccCh.second-1;
00193 assert(0 <= iDccPhi0 && iDccPhi0 <= nDccPerEe);
00194 assert(0 <= iDccCh0 && iDccCh0 <= maxDccChs);
00195
00196 assert(-1<= eeRuInterest_[iZ0][iDccPhi0][iDccCh0] && eeRuInterest_[iZ0][iDccPhi0][iDccCh0] <=7);
00197
00198 return eeRuInterest_[iZ0][iDccPhi0][iDccCh0];
00199 }
00200
00201
00202 EcalSelectiveReadout::towerInterest_t
00203 EcalSelectiveReadout::getTowerInterest(const EcalTrigTowerDetId & tower) const
00204 {
00205
00206 int iEta = tower.ieta()<0? tower.ieta() + nTriggerTowersInEta/2
00207 : tower.ieta() + nTriggerTowersInEta/2 -1;
00208 int iPhi = tower.iphi() - 1;
00209
00210 assert(-1 <= towerInterest[iEta][iPhi] && towerInterest[iEta][iPhi] < 8);
00211
00212 return towerInterest[iEta][iPhi];
00213 }
00214
00215 void
00216 EcalSelectiveReadout::classifyTriggerTowers(const ttFlag_t ttFlags[nTriggerTowersInEta][nTriggerTowersInPhi])
00217 {
00218
00219 for(int iEta=0; iEta < (int)nTriggerTowersInEta; ++iEta){
00220 for(int iPhi=0; iPhi < (int)nTriggerTowersInPhi; ++iPhi){
00221 towerInterest[iEta][iPhi] = LOWINTEREST;
00222 }
00223 }
00224
00225 for(int iEta=0; iEta < (int)nTriggerTowersInEta; ++iEta){
00226 for(int iPhi=0; iPhi < (int)nTriggerTowersInPhi; ++iPhi){
00227
00228 towerInterest[iEta][iPhi] = (towerInterest_t) (towerInterest[iEta][iPhi]
00229 | (ttFlags[iEta][iPhi] & FORCED_MASK)) ;
00230 if((ttFlags[iEta][iPhi] & ~FORCED_MASK) == TTF_HIGH_INTEREST){
00231
00232 towerInterest[iEta][iPhi] = CENTER;
00233
00234 for(int iEtaNeigh = std::max<int>(0,iEta-dEta);
00235 iEtaNeigh <= std::min<int>(nTriggerTowersInEta-1, iEta+dEta);
00236 ++iEtaNeigh){
00237 for(int iPhiNeigh = iPhi-dPhi;
00238 iPhiNeigh <= iPhi+dPhi;
00239 ++iPhiNeigh){
00240
00241
00242 int iPhiNeigh_ = iPhiNeigh%(int)nTriggerTowersInPhi;
00243 if(iPhiNeigh_<0) {
00244 iPhiNeigh_ += nTriggerTowersInPhi;
00245 }
00246 combineFlags(towerInterest[iEtaNeigh][iPhiNeigh_],
00247 NEIGHBOUR);
00248 }
00249 }
00250 } else if((ttFlags[iEta][iPhi] & ~FORCED_MASK) == TTF_MID_INTEREST){
00251 combineFlags(towerInterest[iEta][iPhi], SINGLE);
00252 }
00253 }
00254 }
00255
00256
00257
00258
00259
00260 const size_t innerEtas[] = {0, 1,
00261 nTriggerTowersInEta-2, nTriggerTowersInEta-1};
00262 for(size_t i=0; i < 4; ++i){
00263 size_t iEta = innerEtas[i];
00264 for(size_t iPhi = 0 ; iPhi < nTriggerTowersInPhi; iPhi+=2){
00265 const towerInterest_t srf = std::max(towerInterest[iEta][iPhi],
00266 towerInterest[iEta][iPhi+1]);
00267 towerInterest[iEta][iPhi] = srf;
00268 towerInterest[iEta][iPhi+1] = srf;
00269 }
00270 }
00271 }
00272
00273 void EcalSelectiveReadout::printHeader(std::ostream & os) const{
00274 os << "#SRP flag map\n#\n"
00275 "# +-->Phi/Y " << srpFlagMarker[0] << ": low interest\n"
00276 "# | " << srpFlagMarker[1] << ": single\n"
00277 "# | " << srpFlagMarker[2] << ": neighbour\n"
00278 "# V Eta/X " << srpFlagMarker[3] << ": center\n"
00279 "# " << srpFlagMarker[4] << ": forced low interest\n"
00280 "# " << srpFlagMarker[5] << ": forced single\n"
00281 "# " << srpFlagMarker[6] << ": forced neighbout\n"
00282 "# " << srpFlagMarker[7] << ": forced center\n"
00283 "#\n";
00284 }
00285
00286 void EcalSelectiveReadout::print(std::ostream & os) const
00287 {
00288
00289 printEndcap(0, os);
00290
00291
00292 printBarrel(os);
00293
00294
00295 printEndcap(1, os);
00296 }
00297
00298
00299 void EcalSelectiveReadout::printBarrel(std::ostream & os) const
00300 {
00301 for(size_t iEta = nEndcapTriggerTowersInEta;
00302 iEta < nEndcapTriggerTowersInEta
00303 + nBarrelTriggerTowersInEta;
00304 ++iEta){
00305 for(size_t iPhi = 0; iPhi < nTriggerTowersInPhi; ++iPhi){
00306 towerInterest_t srFlag
00307 = towerInterest[iEta][iPhi];
00308 os << srpFlagMarker[srFlag];
00309 }
00310 os << "\n";
00311 }
00312 }
00313
00314
00315 void EcalSelectiveReadout::printEndcap(int endcap, std::ostream & os) const
00316 {
00317 for(size_t iX=0; iX<nSupercrystalXBins; ++iX){
00318 for(size_t iY=0; iY<nSupercrystalYBins; ++iY){
00319 towerInterest_t srFlag;
00320 char c;
00321 if(!EcalScDetId::validDetId(iX+1,iY+1,endcap>=1?1:-1)){
00322
00323 c = ' ';
00324 } else{
00325 srFlag
00326 = getSuperCrystalInterest(EcalScDetId(iX+1, iY+1, endcap>=1?1:-1));
00327 c = srFlag==UNKNOWN ? '?' : srpFlagMarker[srFlag];
00328 }
00329 os << c;
00330 }
00331 os << "\n";
00332 }
00333 }
00334
00335
00336 std::ostream & operator<<(std::ostream & os, const EcalSelectiveReadout & selectiveReadout)
00337 {
00338 selectiveReadout.print(os);
00339 return os;
00340 }
00341
00342
00343 void
00344 EcalSelectiveReadout::printDccChMap(std::ostream& os) const{
00345 for(int i=-1; i<=68; ++i){
00346 if((i+1)%10==0) os << "//";
00347 os << std::setw(2) << i << ": " << (char)('0'+i);
00348 if(i%10==9) os << "\n"; else os << " ";
00349 }
00350
00351 os << "\n";
00352
00353 for(int endcap = 0; endcap < 2; ++endcap){
00354 os << "Sc2DCCch0: " << (endcap?"EE+":"EE-") << "\n";
00355 for(size_t iY=0; iY<nSupercrystalYBins; ++iY){
00356 os << "Sc2DCCch0: ";
00357 for(size_t iX=0; iX<nSupercrystalXBins; ++iX){
00358
00359 if(!EcalScDetId::validDetId(iX+1,iY+1,endcap>=1?1:-1)){
00360
00361 os << (char)('0'-1);
00362 } else{
00363
00364 os << (char)('0'+(theElecMap->getDCCandSC(EcalScDetId(iX+1, iY+1, endcap>0?1:-1)).second-1));
00365 }
00366 }
00367 os << "\n";
00368 }
00369 os << "\n";
00370 }
00371 os << "\n";
00372 }