CMS 3D CMS Logo

/afs/cern.ch/work/a/aaltunda/public/www/CMSSW_6_2_5/src/SimCalorimetry/EcalTrigPrimAlgos/interface/EcalTrigPrimFunctionalAlgo.h

Go to the documentation of this file.
00001 #ifndef EcalTrigPrimFunctionalAlgo_h
00002 #define EcalTrigPrimFunctionalAlgo_h
00003 
00018 #include <sys/time.h>
00019 #include <iostream>
00020 #include <vector>
00021 
00022 #include "Geometry/CaloTopology/interface/EcalTrigTowerConstituentsMap.h"
00023 
00024 #include "SimCalorimetry/EcalTrigPrimAlgos/interface/EcalFenixStrip.h"
00025 #include "SimCalorimetry/EcalTrigPrimAlgos/interface/EcalFenixTcp.h"
00026 
00027 #include "DataFormats/Common/interface/SortedCollection.h"
00028 #include "DataFormats/EcalDigi/interface/EcalDigiCollections.h"
00029 
00030 #include "FWCore/Framework/interface/EventSetup.h"
00031 #include "FWCore/Framework/interface/ESHandle.h"
00032 
00033 #include <map>
00034 #include <utility>
00035 
00039 class EcalTrigTowerDetId;
00040 class ETPCoherenceTest;
00041 class EcalTriggerPrimitiveSample;
00042 class CaloSubdetectorGeometry;
00043 class EBDataFrame;
00044 class EEDataFrame;
00045 class EcalElectronicsMapping;
00046 
00047  
00048 class EcalTrigPrimFunctionalAlgo
00049 {  
00050  public:
00051   
00052   explicit EcalTrigPrimFunctionalAlgo(const edm::EventSetup & setup, int binofmax, bool tcpFormat, bool barrelOnly, bool debug, bool famos);
00053 
00054   virtual ~EcalTrigPrimFunctionalAlgo();
00055 
00056   void run(const edm::EventSetup &, const EBDigiCollection *col, EcalTrigPrimDigiCollection & result, EcalTrigPrimDigiCollection & resultTcp);
00057   void run(const edm::EventSetup&,  const EEDigiCollection *col, EcalTrigPrimDigiCollection & result, EcalTrigPrimDigiCollection & resultTcp);
00058   void run_part1_EB(EBDigiCollection const * col);
00059   void run_part1_EE(EEDigiCollection const * col);
00060   template <class Coll> 
00061     void run_part2(const edm::EventSetup &, Coll const * col, 
00062                    std::vector<std::vector<std::pair<int,std::vector<typename Coll::Digi> > > > &towerMap,
00063                    EcalTrigPrimDigiCollection & result,
00064                    EcalTrigPrimDigiCollection & resultTcp);
00065 
00066   void setPointers(const EcalTPGLinearizationConst *ecaltpLin,const EcalTPGPedestals *ecaltpPed,const EcalTPGSlidingWindow * ecaltpgSlidW,const EcalTPGWeightIdMap * ecaltpgWeightMap,const EcalTPGWeightGroup * ecaltpgWeightGroup,const EcalTPGFineGrainStripEE * ecaltpgFgStripEE, const EcalTPGCrystalStatus * ecaltpgBadX, const EcalTPGStripStatus * ecaltpgStripStatus)  {
00067     estrip_->setPointers(ecaltpPed,ecaltpLin,ecaltpgWeightMap,ecaltpgWeightGroup,ecaltpgSlidW,ecaltpgFgStripEE,ecaltpgBadX,ecaltpgStripStatus);
00068 
00069   }
00070   void setPointers2(  const EcalTPGFineGrainEBGroup * ecaltpgFgEBGroup,
00071                       const EcalTPGLutGroup * ecaltpgLutGroup,
00072                       const EcalTPGLutIdMap * ecaltpgLut,
00073                       const EcalTPGFineGrainEBIdMap * ecaltpgFineGrainEB,
00074                       const EcalTPGFineGrainTowerEE * ecaltpgFineGrainTowerEE,
00075                       const EcalTPGTowerStatus * ecaltpgBadTT,
00076                       const EcalTPGSpike * ecaltpgSpike){
00077    
00078   etcp_->setPointers(ecaltpgFgEBGroup,ecaltpgLutGroup,ecaltpgLut,ecaltpgFineGrainEB,ecaltpgFineGrainTowerEE,ecaltpgBadTT,ecaltpgSpike);
00079   }
00080 
00081  private:
00082 
00083   void init(const edm::EventSetup&);
00084   template <class T>  
00085     void initStructures(std::vector<std::vector<std::pair<int,std::vector<T> > > > & towMap);
00086   template <class T> 
00087     void clean(std::vector<std::vector<std::pair<int,std::vector<T> > > > &towerMap);
00088   template <class Coll> 
00089     void fillMap(Coll const * col, std::vector<std::vector<std::pair<int,std::vector<typename Coll::Digi> > > > &towerMap);
00090   int findStripNr(const EBDetId &id);
00091   int findStripNr(const EEDetId &id);
00092 
00093   // FIXME: temporary until hashedIndex works alsom for endcap
00094   int getIndex(const  EBDigiCollection *, EcalTrigTowerDetId& id) {return id.hashedIndex();}
00095   // mind that eta is continuous between barrel+endcap
00096   int getIndex(const  EEDigiCollection *, EcalTrigTowerDetId& id) {
00097     int ind=(id.ietaAbs()-18)*72 + id.iphi();
00098     if (id.zside()<0) ind+=792;
00099     return ind;
00100   }
00101 
00102   EcalFenixStrip * estrip_;
00103   EcalFenixTcp * etcp_;
00104 
00105   edm::ESHandle<EcalTrigTowerConstituentsMap> eTTmap_;
00106   const CaloSubdetectorGeometry *theEndcapGeometry;
00107   const EcalElectronicsMapping* theMapping_;
00108 
00109   float threshold;
00110 
00111   int binOfMaximum_;
00112   int maxNrSamples_;
00113 
00114   bool tcpFormat_;
00115   bool barrelOnly_;
00116   bool debug_;  
00117   bool famos_;  
00118 
00119   static const unsigned int nrSamples_; //nr samples to write, should not be changed since by convention the size means that it is coming from simulation
00120   static const unsigned int maxNrSamplesOut_; //to be placed in the intermediate samples
00121   static const unsigned int maxNrTowers_; //would be better to get from somewhere..
00122   static const unsigned int maxNrTPs_; //would be better to get from somewhere..
00123 
00124   int nrTowers_;   // nr of towers found by fillmap method
00125 
00126   // data structures kept during the whole run
00127   std::vector<std::vector<int> > striptp_;
00128   std::vector<std::vector<std::pair<int,std::vector<EBDataFrame> > > > towerMapEB_;
00129   std::vector<std::vector<std::pair<int,std::vector<EEDataFrame> > > > towerMapEE_;
00130   std::vector<std::pair<int,EcalTrigTowerDetId> > hitTowers_;
00131   std::vector<EcalTriggerPrimitiveSample> towtp_;
00132   std::vector<EcalTriggerPrimitiveSample> towtp2_;
00133 
00134   enum {nbMaxStrips_=5};
00135   enum {nbMaxXtals_=5};
00136 };
00137 
00138 //=================================== implementations =============================================
00139 
00140 template <class Coll> 
00141 void EcalTrigPrimFunctionalAlgo::run_part2(const edm::EventSetup &setup,Coll const * col, std::vector<std::vector<std::pair<int,std::vector<typename Coll::Digi> > > > &towerMap,
00142                                            EcalTrigPrimDigiCollection & result,
00143                                            EcalTrigPrimDigiCollection & resultTcp)
00144 {
00145   typedef typename Coll::Digi Digi;
00146  
00147   // prepare writing of TP-s
00148 
00149   int firstSample = binOfMaximum_-1 -nrSamples_/2;
00150   int lastSample = binOfMaximum_-1 +nrSamples_/2;
00151   int nrTP=0;
00152   std::vector<typename Coll::Digi> dummy;
00153   EcalTriggerPrimitiveDigi tptow[2];
00154   EcalTriggerPrimitiveDigi tptowTcp[2];
00155   
00156   estrip_->getFGVB()->setbadStripMissing(false);
00157 
00158   for(int itow=0;itow<nrTowers_;++itow) 
00159     {
00160 
00161       int index=hitTowers_[itow].first;
00162       const EcalTrigTowerDetId &thisTower=hitTowers_[itow].second;
00163 
00164       // loop over all strips assigned to this trigger tower
00165       int nstr=0;
00166       for(unsigned int i = 0; i < towerMap[itow].size();++i)
00167         {
00168           std::vector<Digi> &df = (towerMap[index])[i].second;//vector of dataframes for this strip, size; nr of crystals/strip
00169 
00170           if ((towerMap[index])[i].first > 0) {  
00171             estrip_->process(setup,df,(towerMap[index])[i].first,striptp_[nstr++]);
00172           }
00173         }//loop over strips in one tower
00174 
00175       bool isInInnerRings=false;
00176       if (thisTower.subDet()==EcalEndcap && (thisTower.ietaAbs()==27 || thisTower.ietaAbs()==28 )) isInInnerRings=true;
00177       etcp_->process(setup,dummy,striptp_,nstr,towtp_,towtp2_,isInInnerRings,thisTower);
00178 
00179       // prepare TP-s
00180       // special treatment for 2 inner endcap rings
00181       int nrTowers;
00182       if (isInInnerRings)
00183         {
00184           nrTowers=2;
00185           int phi=2*((thisTower.iphi()-1)/2);
00186           tptow[0]=EcalTriggerPrimitiveDigi(EcalTrigTowerDetId(thisTower.zside(),thisTower.subDet(),thisTower.ietaAbs(),phi+1));
00187           tptow[1]=EcalTriggerPrimitiveDigi(EcalTrigTowerDetId(thisTower.zside(),thisTower.subDet(),thisTower.ietaAbs(),phi+2));
00188 
00189           if (tcpFormat_){
00190             tptowTcp[0]=EcalTriggerPrimitiveDigi(EcalTrigTowerDetId(thisTower.zside(),thisTower.subDet(),thisTower.ietaAbs(),phi+1));
00191             tptowTcp[1]=EcalTriggerPrimitiveDigi(EcalTrigTowerDetId(thisTower.zside(),thisTower.subDet(),thisTower.ietaAbs(),phi+2));
00192           }
00193         }else {
00194           nrTowers=1;
00195           tptow[0]=EcalTriggerPrimitiveDigi(thisTower);
00196           if (tcpFormat_)   tptowTcp[0]=EcalTriggerPrimitiveDigi(thisTower);
00197         }
00198 
00199       // now fill in
00200       for (int nrt=0;nrt<nrTowers;nrt++) {
00201         (tptow[nrt]).setSize(nrSamples_);
00202         if (towtp_.size()<nrSamples_)  {  //FIXME: only once
00203           edm::LogWarning("") <<"Too few samples produced, nr is "<<towtp_.size();
00204           break;
00205         }
00206         int isam=0;
00207         for (int i=firstSample;i<=lastSample;++i) {
00208           tptow[nrt].setSample(isam++,EcalTriggerPrimitiveSample(towtp_[i]));
00209         }
00210         nrTP++; 
00211         LogDebug("EcalTPG") <<" For tower "<<itow<<" created TP nr "<<nrTP<<" with Et "<<tptow[nrt].compressedEt();
00212         result.push_back(tptow[nrt]);
00213       }
00214 
00215       if (tcpFormat_) {
00216 
00217         for (int nrt=0;nrt<nrTowers;nrt++) {
00218           tptowTcp[nrt].setSize(nrSamples_);
00219           if (towtp2_.size()<nrSamples_)  {  //FIXME: only once
00220             edm::LogWarning("") <<"Too few samples produced, nr is "<<towtp2_.size();
00221             break;
00222           }
00223           int isam=0;
00224           for (int i=firstSample;i<=lastSample;++i) {
00225             if (nrTowers<=1)  tptowTcp[nrt].setSample(isam++,EcalTriggerPrimitiveSample(towtp2_[i]));
00226             else {
00227               int et=towtp2_[i].compressedEt()/2;
00228               tptowTcp[nrt].setSample(isam++,EcalTriggerPrimitiveSample(et,towtp2_[i].fineGrain(),towtp2_[i].ttFlag()));
00229             }
00230           }
00231           resultTcp.push_back(tptowTcp[nrt]);
00232         }
00233       }
00234     } 
00235   return;
00236 }
00237 
00238 template <class Coll> 
00239 void EcalTrigPrimFunctionalAlgo::fillMap(Coll const * col, 
00240                                          std::vector<std::vector<std::pair<int,std::vector<typename Coll::Digi> > > > &towerMap)
00241 {
00242   typedef typename Coll::Digi Digi;
00243 
00244   // implementation for Barrel and Endcap
00245 
00246   if (col) {
00247     nrTowers_=0;
00248     LogDebug("EcalTPG") <<"Fill mapping, Collection size = "<<col->size();
00249     for(unsigned int i = 0; i < col->size() ; ++i) {
00250       Digi samples((*col)[i]); 
00251       EcalTrigTowerDetId coarser=(*eTTmap_).towerOf(samples.id());
00252       int index=getIndex(col,coarser);
00253       int stripnr=findStripNr(samples.id());
00254 
00255       int filled=0;
00256       for (unsigned int ij=0;ij<towerMap[index].size();++ij) filled+=towerMap[index][ij].first;
00257       if (!filled) {
00258         hitTowers_[nrTowers_++]=std::pair <int,EcalTrigTowerDetId>(index,coarser);
00259       }
00260 
00261       //FIXME: temporary protection
00262       int ncryst=towerMap[index][stripnr-1].first;
00263       if (ncryst>=nbMaxXtals_ ) {
00264         edm::LogError("EcalTrigPrimFunctionAlgo")<<"! Too many xtals for TT "<<coarser<<" stripnr "<<stripnr<<" xtalid "<<samples.id() ;
00265         continue;
00266       }
00267       ((towerMap[index])[stripnr-1].second)[ncryst]=samples;
00268       (towerMap[index])[stripnr-1].first++;
00269     }
00270   
00271     LogDebug("EcalTPG")<<"fillMap"<<"[EcalTrigPrimFunctionalAlgo] (found " 
00272                        << col->size() << " frames in "<< towerMap.size() << " towers) ";
00273   }
00274   else {
00275     LogDebug("EcalTPG")<<"FillMap - FillMap Collection size=0 !!!!";
00276   }
00277 }
00278 
00279 template <class T> 
00280 void EcalTrigPrimFunctionalAlgo::clean( std::vector<std::vector<std::pair<int,std::vector<T> > > > & towMap) {  
00281   // clean internal data structures
00282   for (unsigned int i=0;i<maxNrTowers_;++i) 
00283     for (int j=0;j<nbMaxStrips_ ;++j) (towMap[i])[j].first=0;
00284   return;
00285 }
00286  
00287 template <class T> 
00288 void EcalTrigPrimFunctionalAlgo::initStructures( std::vector<std::vector<std::pair<int,std::vector<T> > > > & towMap) {  
00289   //initialise internal data structures
00290 
00291   std::vector <T> vec0(nbMaxXtals_ );
00292   std::vector<std::pair<int,std::vector<T> > > vec1(nbMaxStrips_);
00293   for (int i=0;i<nbMaxStrips_ ;++i) vec1[i]=std::pair<int,std::vector<T> >(0,vec0);
00294   towMap.resize(maxNrTowers_); 
00295   for (unsigned int i=0;i<maxNrTowers_;++i) towMap[i]=vec1;
00296   
00297   std::vector<int> vecint(maxNrSamples_);
00298   striptp_.resize(nbMaxStrips_);
00299   for (int i=0;i<nbMaxStrips_;++i) striptp_[i]=vecint;
00300   
00301 }
00302 
00303 #endif