00001 #include "SimCalorimetry/HcalTrigPrimProducers/src/HcalTTPDigiProducer.h"
00002
00003 #include "DataFormats/HcalDigi/interface/HFDataFrame.h"
00004 #include "DataFormats/HcalDetId/interface/HcalSubdetector.h"
00005 #include "DataFormats/HcalDigi/interface/HcalDigiCollections.h"
00006 #include "CalibFormats/HcalObjects/interface/HcalTPGRecord.h"
00007 #include "CalibFormats/HcalObjects/interface/HcalTPGCoder.h"
00008 #include "DataFormats/Common/interface/Handle.h"
00009 #include "FWCore/Framework/interface/ESHandle.h"
00010 #include "FWCore/MessageLogger/interface/MessageLogger.h"
00011 #include <cstdio>
00012
00013
00014 const int HcalTTPDigiProducer::inputs_[] = { 30,66,4,44,4,44,0,68,
00015 0,68,16,48,16,48,6,46,
00016 6,46,2,70,2,70,18,50,
00017 18,50,12,40,12,40,8,52,
00018 8,52,20,36,20,36,14,42,
00019 14,42,10,54,10,54,22,38,
00020 22,38,24,56,24,56,32,60,
00021 32,60,28,64,28,64,26,58,
00022 26,58,34,62,34,62,30,66 } ;
00023
00024 HcalTTPDigiProducer::HcalTTPDigiProducer(const edm::ParameterSet& ps)
00025 {
00026 hfDigis_ = ps.getParameter<edm::InputTag>("HFDigiCollection") ;
00027 maskedChannels_ = ps.getParameter< std::vector<unsigned int> >("maskedChannels") ;
00028 bit_[0] = ps.getParameter<std::string>("defTT8") ;
00029 bit_[1] = ps.getParameter<std::string>("defTT9") ;
00030 bit_[2] = ps.getParameter<std::string>("defTT10") ;
00031 bit_[3] = ps.getParameter<std::string>("defTTLocal") ;
00032
00033 for (int i=0; i<4; i++) {
00034 nHits_[i] = -1 ; nHFp_[i] = -1 ; nHFm_[i] = -1 ;
00035 pReq_[i] = ' ' ; mReq_[i] = ' ' ; pmLogic_[i] = ' ' ;
00036 calc_[i] = sscanf(bit_[i].c_str(),"hits>=%d:hfp%c=%d%chfm%c=%d",
00037 &(nHits_[i]),&(pReq_[i]),&(nHFp_[i]),
00038 &(pmLogic_[i]),&(mReq_[i]),&(nHFm_[i])) ;
00039 if ( calc_[i] == 1 ) {
00040 if ( nHits_[i] < 0 )
00041 throw cms::Exception("HcalTTPDigiProducer")
00042 << "Unable to read logic for technical trigger" ;
00043 } else if ( calc_[i] == 6 ) {
00044 if ( nHits_[i] < 0 || nHFp_[i] < 0 || nHFm_[i] < 0 )
00045 throw cms::Exception("HcalTTPDigiProducer")
00046 << "Unable to read logic for technical trigger" ;
00047 if ( (pReq_[i] != '>' && pReq_[i] != '<') ||
00048 (mReq_[i] != '>' && mReq_[i] != '<') ||
00049 (pmLogic_[i] != ':' && pmLogic_[i] != '|') )
00050 throw cms::Exception("HcalTTPDigiProducer")
00051 << "Technical Trigger logic must obey the following format:\n"
00052 "\"hits>=[A1]:hfp[B1]=[A2][C]hfm[B2]=[A3]\",\n"
00053 "or \"hits>=[A1]\",\n"
00054 "with A# >= 0, B# = (</>) and C = (:/|)" ;
00055 } else {
00056 throw cms::Exception("HcalTTPDigiProducer")
00057 << "Unable to read logic for technical trigger" ;
00058 }
00059 }
00060
00061 id_ = ps.getUntrackedParameter<int>("id",-1) ;
00062 samples_ = ps.getParameter<int>("samples") ;
00063 presamples_ = ps.getParameter<int>("presamples") ;
00064 iEtaMin_ = ps.getParameter<int>("iEtaMin") ;
00065 iEtaMax_ = ps.getParameter<int>("iEtaMax") ;
00066 threshold_ = ps.getParameter<unsigned int>("threshold") ;
00067 fwAlgo_ = ps.getParameter<int>("fwAlgorithm") ;
00068
00069 SoI_ = ps.getParameter<int>("HFSoI") ;
00070
00071 if ( samples_ > 8 ) {
00072 samples_ = 8 ;
00073 edm::LogWarning("HcalTTPDigiProducer") << "Samples forced to maximum value of 8" ;
00074 }
00075 if ( presamples_ - SoI_ > 0 ) {
00076 presamples_ = SoI_ ;
00077 edm::LogWarning("HcalTTPDigiProducer") << "Presamples reset to HF SoI value" ;
00078 }
00079
00080 for (unsigned int i=0; i<maskedChannels_.size(); i++) {
00081 HcalDetId id(maskedChannels_.at(i)) ;
00082 if ( !id.validDetId(HcalForward,id.ieta(),id.iphi(),id.depth()) )
00083 throw cms::Exception("HcalTTPDigiProducer") << "Invalid HCAL Det ID" ;
00084 }
00085
00086 produces<HcalTTPDigiCollection>();
00087 }
00088
00089
00090 HcalTTPDigiProducer::~HcalTTPDigiProducer() {
00091 }
00092
00093 bool HcalTTPDigiProducer::isMasked(HcalDetId id) {
00094
00095 for ( unsigned int i=0; i<maskedChannels_.size(); i++ )
00096 if ( id.rawId() == maskedChannels_.at(i) ) return true ;
00097 return false ;
00098 }
00099
00100 bool HcalTTPDigiProducer::decision(int nP, int nM, int bit) {
00101
00102 bool pOK = false ; bool mOK = false ;
00103 if ( (nP + nM) < nHits_[bit] ) return false ;
00104 if ( calc_[bit] == 1 ) return ( (nP + nM) >= nHits_[bit] ) ;
00105
00106 if ( pReq_[bit] == '>' ) pOK = ( nP >= nHFp_[bit] ) ;
00107 else if ( pReq_[bit] == '<' ) pOK = ( nP <= nHFp_[bit] ) ;
00108
00109 if ( mReq_[bit] == '>' ) mOK = ( nM >= nHFm_[bit] ) ;
00110 else if ( mReq_[bit] == '<' ) mOK = ( nM <= nHFm_[bit] ) ;
00111
00112 if ( pmLogic_[bit] == ':' ) return ( pOK && mOK ) ;
00113 else if ( pmLogic_[bit] == '|' ) return ( pOK || mOK ) ;
00114
00115
00116 edm::LogWarning("HcalTTPDigiProducer") << "Trigger logic exhausted. Returning false" ;
00117 return false ;
00118 }
00119
00120 void HcalTTPDigiProducer::produce(edm::Event& e, const edm::EventSetup& eventSetup) {
00121
00122
00123 edm::Handle<HFDigiCollection> hfDigiCollection ;
00124 e.getByLabel(hfDigis_,hfDigiCollection) ;
00125 edm::ESHandle<HcalTPGCoder> inputCoder ;
00126 eventSetup.get<HcalTPGRecord>().get(inputCoder) ;
00127
00128
00129 std::auto_ptr<HcalTTPDigiCollection> ttpResult(new HcalTTPDigiCollection()) ;
00130
00131
00132 uint16_t trigInputs[40] ;
00133 int nP[8] ; int nM[8] ;
00134 for (int i=0; i<8; i++) {
00135 nP[i] = 0 ; nM[i] = 0 ;
00136 for (int j=0; j<5; j++) trigInputs[j*8+i] = 0 ;
00137 }
00138 for (HFDigiCollection::const_iterator theDigi=hfDigiCollection->begin();
00139 theDigi!=hfDigiCollection->end(); theDigi++) {
00140 HcalDetId id = HcalDetId(theDigi->id()) ;
00141 if ( isMasked(id) ) continue ;
00142 if ( id.ietaAbs() < iEtaMin_ || id.ietaAbs() > iEtaMax_ ) continue ;
00143
00144 IntegerCaloSamples samples(id,theDigi->size()) ;
00145 inputCoder->adc2Linear(*theDigi,samples) ;
00146
00147 for (int relSample=-presamples_; relSample<(samples_-presamples_); relSample++) {
00148 if ( samples[SoI_+relSample] >= threshold_ ) {
00149 int linSample = presamples_ + relSample ;
00150 int offset = (-1+id.zside())/2 ;
00151 int shift = inputs_[id.iphi()+offset] ;
00152 int group = 0 ;
00153 while ( shift >= 16 ) { shift -= 16 ; group++ ; }
00154 if ( !(trigInputs[(linSample*8)+group]&(1<<shift)) )
00155 ( id.ieta() > 0 ) ? ( nP[linSample]++) : ( nM[linSample]++ ) ;
00156 trigInputs[(linSample*8)+group] |= (1<<shift) ;
00157 }
00158 }
00159 }
00160
00161
00162 uint8_t trigOutput[8] ;
00163 uint32_t algoDepBits[8] ;
00164 HcalTTPDigi ttpDigi(id_,samples_,presamples_,0,fwAlgo_,0) ;
00165 for (int linSample=0; linSample<8; linSample++) {
00166 trigOutput[linSample] = 0 ; algoDepBits[linSample] = 0 ;
00167 if ( linSample<samples_) {
00168 for (int j=0; j<4; j++)
00169 trigOutput[linSample] |= (decision(nP[linSample],nM[linSample],j)<<j) ;
00170 int nT = nP[linSample] + nM[linSample] ;
00171
00172
00173
00174 if ( fwAlgo_ == 1 ) algoDepBits[linSample] = (nT&0x7F) | ((nP[linSample]&0x3F)<<7) | ((nM[linSample]&0x3F)<<13) ;
00175 ttpDigi.setSample((linSample-presamples_),&trigInputs[linSample*8],algoDepBits[linSample],trigOutput[linSample]) ;
00176 }
00177 }
00178 ttpResult->push_back( ttpDigi ) ;
00179
00180
00181 e.put(ttpResult);
00182 }
00183