File indexing completed on 2024-11-01 06:11:53
0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020 #include <memory>
0021
0022
0023 #include "FWCore/Framework/interface/Frameworkfwd.h"
0024 #include "FWCore/Framework/interface/stream/EDProducer.h"
0025
0026 #include "FWCore/Framework/interface/Event.h"
0027 #include "FWCore/Framework/interface/MakerMacros.h"
0028
0029 #include "FWCore/ParameterSet/interface/ParameterSet.h"
0030
0031 #include "DataFormats/EcalDigi/interface/EcalDigiCollections.h"
0032 #include "DataFormats/HcalDigi/interface/HcalDigiCollections.h"
0033
0034 #include "L1Trigger/L1TCaloLayer1/src/UCTLayer1.hh"
0035 #include "L1Trigger/L1TCaloLayer1/src/UCTCrate.hh"
0036 #include "L1Trigger/L1TCaloLayer1/src/UCTCard.hh"
0037 #include "L1Trigger/L1TCaloLayer1/src/UCTRegion.hh"
0038 #include "L1Trigger/L1TCaloLayer1/src/UCTTower.hh"
0039
0040 #include "L1Trigger/L1TCaloLayer1/src/UCTGeometry.hh"
0041 #include "L1Trigger/L1TCaloLayer1/src/UCTLogging.hh"
0042
0043 #include "DataFormats/L1TCalorimeter/interface/CaloTower.h"
0044 #include "DataFormats/L1CaloTrigger/interface/L1CaloCollections.h"
0045 #include "DataFormats/L1CaloTrigger/interface/L1CaloRegion.h"
0046
0047 #include "L1Trigger/L1TCalorimeter/interface/CaloTools.h"
0048
0049 #include "L1Trigger/L1TCaloLayer1/src/L1TCaloLayer1FetchLUTs.hh"
0050
0051 using namespace l1t;
0052 using namespace l1tcalo;
0053
0054
0055
0056
0057
0058 class L1TCaloLayer1 : public edm::stream::EDProducer<> {
0059 public:
0060 explicit L1TCaloLayer1(const edm::ParameterSet&);
0061
0062 static void fillDescriptions(edm::ConfigurationDescriptions& descriptions);
0063
0064 private:
0065 void produce(edm::Event&, const edm::EventSetup&) override;
0066
0067 void beginRun(edm::Run const&, edm::EventSetup const&) override;
0068
0069
0070
0071 edm::EDGetTokenT<EcalTrigPrimDigiCollection> ecalTPSource;
0072 edm::EDGetTokenT<HcalTrigPrimDigiCollection> hcalTPSource;
0073 edm::EDPutTokenT<CaloTowerBxCollection> towerPutToken;
0074 edm::EDPutTokenT<L1CaloRegionCollection> regionPutToken;
0075 const L1TCaloLayer1FetchLUTsTokens lutsTokens;
0076
0077 std::vector<std::array<std::array<std::array<uint32_t, nEtBins>, nCalSideBins>, nCalEtaBins>> ecalLUT;
0078 std::vector<std::array<std::array<std::array<uint32_t, nEtBins>, nCalSideBins>, nCalEtaBins>> hcalLUT;
0079 std::vector<std::array<std::array<uint32_t, nEtBins>, nHfEtaBins>> hfLUT;
0080 std::vector<unsigned long long int> hcalFBLUT;
0081
0082 std::vector<unsigned int> ePhiMap;
0083 std::vector<unsigned int> hPhiMap;
0084 std::vector<unsigned int> hfPhiMap;
0085
0086 std::vector<std::shared_ptr<UCTTower>> twrList;
0087
0088 bool useLSB;
0089 bool useCalib;
0090 bool useECALLUT;
0091 bool useHCALLUT;
0092 bool useHFLUT;
0093 bool useHCALFBLUT;
0094 bool verbose;
0095 bool unpackHcalMask;
0096 bool unpackEcalMask;
0097 int fwVersion;
0098
0099 std::unique_ptr<UCTLayer1> layer1;
0100 };
0101
0102
0103
0104
0105
0106
0107
0108
0109
0110
0111
0112
0113 L1TCaloLayer1::L1TCaloLayer1(const edm::ParameterSet& iConfig)
0114 : ecalTPSource(consumes<EcalTrigPrimDigiCollection>(iConfig.getParameter<edm::InputTag>("ecalToken"))),
0115 hcalTPSource(consumes<HcalTrigPrimDigiCollection>(iConfig.getParameter<edm::InputTag>("hcalToken"))),
0116 towerPutToken{produces<CaloTowerBxCollection>()},
0117 regionPutToken{produces<L1CaloRegionCollection>()},
0118 lutsTokens{esConsumes<edm::Transition::BeginRun>(),
0119 esConsumes<edm::Transition::BeginRun>(),
0120 esConsumes<edm::Transition::BeginRun>()},
0121 ePhiMap(72 * 2, 0),
0122 hPhiMap(72 * 2, 0),
0123 hfPhiMap(72 * 2, 0),
0124 useLSB(iConfig.getParameter<bool>("useLSB")),
0125 useCalib(iConfig.getParameter<bool>("useCalib")),
0126 useECALLUT(iConfig.getParameter<bool>("useECALLUT")),
0127 useHCALLUT(iConfig.getParameter<bool>("useHCALLUT")),
0128 useHFLUT(iConfig.getParameter<bool>("useHFLUT")),
0129 useHCALFBLUT(iConfig.getParameter<bool>("useHCALFBLUT")),
0130 verbose(iConfig.getUntrackedParameter<bool>("verbose")),
0131 unpackHcalMask(iConfig.getParameter<bool>("unpackHcalMask")),
0132 unpackEcalMask(iConfig.getParameter<bool>("unpackEcalMask")),
0133 fwVersion(iConfig.getParameter<int>("firmwareVersion")) {
0134
0135 layer1 = std::make_unique<UCTLayer1>(fwVersion);
0136
0137 vector<UCTCrate*> crates = layer1->getCrates();
0138 for (uint32_t crt = 0; crt < crates.size(); crt++) {
0139 vector<UCTCard*> cards = crates[crt]->getCards();
0140 for (uint32_t crd = 0; crd < cards.size(); crd++) {
0141 vector<UCTRegion*> regions = cards[crd]->getRegions();
0142 for (uint32_t rgn = 0; rgn < regions.size(); rgn++) {
0143 vector<std::shared_ptr<UCTTower>> towers = regions[rgn]->getTowers();
0144 for (uint32_t twr = 0; twr < towers.size(); twr++) {
0145 twrList.push_back(towers[twr]);
0146 }
0147 }
0148 }
0149 }
0150
0151
0152
0153 std::sort(twrList.begin(), twrList.end(), [](std::shared_ptr<UCTTower> a, std::shared_ptr<UCTTower> b) {
0154 return CaloTools::caloTowerHash(a->caloEta(), a->caloPhi()) < CaloTools::caloTowerHash(b->caloEta(), b->caloPhi());
0155 });
0156 }
0157
0158
0159
0160
0161
0162
0163 void L1TCaloLayer1::produce(edm::Event& iEvent, const edm::EventSetup& iSetup) {
0164 using namespace edm;
0165
0166 edm::Handle<EcalTrigPrimDigiCollection> ecalTPs;
0167 iEvent.getByToken(ecalTPSource, ecalTPs);
0168 edm::Handle<HcalTrigPrimDigiCollection> hcalTPs;
0169 iEvent.getByToken(hcalTPSource, hcalTPs);
0170
0171 CaloTowerBxCollection towersColl;
0172 L1CaloRegionCollection rgnCollection;
0173
0174 if (!layer1->clearEvent()) {
0175 LOG_ERROR << "UCT: Failed to clear event" << std::endl;
0176 return;
0177 }
0178
0179 for (const auto& ecalTp : *ecalTPs) {
0180 if (unpackEcalMask && ((ecalTp.sample(0).raw() >> 13) & 0x1))
0181 continue;
0182 int caloEta = ecalTp.id().ieta();
0183 int caloPhi = ecalTp.id().iphi();
0184 int et = ecalTp.compressedEt();
0185 bool fgVeto = ecalTp.fineGrain();
0186 UCTTowerIndex t = UCTTowerIndex(caloEta, caloPhi);
0187 if (!layer1->setECALData(t, fgVeto, et)) {
0188 LOG_ERROR << "UCT: Failed loading an ECAL tower" << std::endl;
0189 return;
0190 }
0191 }
0192
0193 if (hcalTPs.isValid()) {
0194 for (const auto& hcalTp : *hcalTPs) {
0195 if (unpackHcalMask && ((hcalTp.sample(0).raw() >> 13) & 0x1))
0196 continue;
0197 int caloEta = hcalTp.id().ieta();
0198 uint32_t absCaloEta = std::abs(caloEta);
0199
0200 if (absCaloEta == 29) {
0201 continue;
0202 }
0203
0204 else if (hcalTp.id().version() == 0 && absCaloEta > 29) {
0205 continue;
0206 } else if (absCaloEta <= 41) {
0207 int caloPhi = hcalTp.id().iphi();
0208 int et = hcalTp.SOI_compressedEt();
0209 bool fg = hcalTp.t0().fineGrain(0);
0210 bool fg2 = hcalTp.t0().fineGrain(1);
0211 bool fg3 = hcalTp.t0().fineGrain(2);
0212 bool fg4 = hcalTp.t0().fineGrain(3);
0213
0214 if (caloPhi <= 72) {
0215 UCTTowerIndex t = UCTTowerIndex(caloEta, caloPhi);
0216 uint32_t featureBits = 0;
0217 if (absCaloEta > 29) {
0218 if (fg)
0219 featureBits |= 0b01;
0220
0221 if (fg2)
0222 featureBits |= 0b10;
0223 } else if (absCaloEta < 16)
0224 featureBits |= (fg | ((!fg2) & (fg3 | fg4)));
0225 if (!layer1->setHCALData(t, featureBits, et)) {
0226 LOG_ERROR << "caloEta = " << caloEta << "; caloPhi =" << caloPhi << std::endl;
0227 LOG_ERROR << "UCT: Failed loading an HCAL tower" << std::endl;
0228 return;
0229 }
0230 } else {
0231 LOG_ERROR << "Illegal Tower: caloEta = " << caloEta << "; caloPhi =" << caloPhi << "; et = " << et
0232 << std::endl;
0233 }
0234 } else {
0235 LOG_ERROR << "Illegal Tower: caloEta = " << caloEta << std::endl;
0236 }
0237 }
0238 }
0239
0240
0241 if (!layer1->process()) {
0242 LOG_ERROR << "UCT: Failed to process layer 1" << std::endl;
0243 }
0244
0245 int theBX = 0;
0246
0247 for (uint32_t twr = 0; twr < twrList.size(); twr++) {
0248 CaloTower caloTower;
0249 caloTower.setHwPt(twrList[twr]->et());
0250 caloTower.setHwEtRatio(twrList[twr]->er());
0251 caloTower.setHwQual(twrList[twr]->miscBits());
0252 caloTower.setHwEta(twrList[twr]->caloEta());
0253 caloTower.setHwPhi(twrList[twr]->caloPhi());
0254 caloTower.setHwEtEm(twrList[twr]->getEcalET());
0255 caloTower.setHwEtHad(twrList[twr]->getHcalET());
0256 towersColl.push_back(theBX, caloTower);
0257 }
0258
0259 iEvent.emplace(towerPutToken, std::move(towersColl));
0260
0261 UCTGeometry g;
0262 vector<UCTCrate*> crates = layer1->getCrates();
0263 for (uint32_t crt = 0; crt < crates.size(); crt++) {
0264 vector<UCTCard*> cards = crates[crt]->getCards();
0265 for (uint32_t crd = 0; crd < cards.size(); crd++) {
0266 vector<UCTRegion*> regions = cards[crd]->getRegions();
0267 for (uint32_t rgn = 0; rgn < regions.size(); rgn++) {
0268 uint32_t rawData = regions[rgn]->rawData();
0269 uint32_t regionData = rawData & 0x0000FFFF;
0270 uint32_t crate = regions[rgn]->getCrate();
0271 uint32_t card = regions[rgn]->getCard();
0272 uint32_t region = regions[rgn]->getRegion();
0273 bool negativeEta = regions[rgn]->isNegativeEta();
0274 uint32_t rPhi = g.getUCTRegionPhiIndex(crate, card);
0275 if (region < NRegionsInCard) {
0276 uint32_t rEta =
0277 10 -
0278 region;
0279 if (!negativeEta)
0280 rEta = 11 + region;
0281 rgnCollection.push_back(L1CaloRegion((uint16_t)regionData, (unsigned)rEta, (unsigned)rPhi, (int16_t)0));
0282 }
0283 }
0284 }
0285 }
0286 iEvent.emplace(regionPutToken, std::move(rgnCollection));
0287 }
0288
0289
0290 void L1TCaloLayer1::beginRun(const edm::Run& iRun, const edm::EventSetup& iSetup) {
0291 if (!L1TCaloLayer1FetchLUTs(lutsTokens,
0292 iSetup,
0293 ecalLUT,
0294 hcalLUT,
0295 hfLUT,
0296 hcalFBLUT,
0297 ePhiMap,
0298 hPhiMap,
0299 hfPhiMap,
0300 useLSB,
0301 useCalib,
0302 useECALLUT,
0303 useHCALLUT,
0304 useHFLUT,
0305 useHCALFBLUT,
0306 fwVersion)) {
0307 LOG_ERROR << "L1TCaloLayer1::beginRun: failed to fetch LUTS - using unity" << std::endl;
0308
0309
0310
0311
0312 std::array<std::array<std::array<uint32_t, nEtBins>, nCalSideBins>, nCalEtaBins> eCalLayer1EtaSideEtArray = {};
0313 std::array<std::array<std::array<uint32_t, nEtBins>, nCalSideBins>, nCalEtaBins> hCalLayer1EtaSideEtArray = {};
0314 std::array<std::array<uint32_t, nEtBins>, nHfEtaBins> hfLayer1EtaEtArray = {};
0315 for (uint32_t i = 0; i < nCalEtaBins; i++) {
0316 for (uint32_t j = 0; j < nCalSideBins; j++) {
0317 for (uint32_t k = 0; k < nEtBins; k++) {
0318 eCalLayer1EtaSideEtArray[i][j][k] = 0xFFFFFFFF;
0319 hCalLayer1EtaSideEtArray[i][j][k] = 0xFFFFFFFF;
0320 }
0321 }
0322 }
0323 for (uint32_t i = 0; i < nHfEtaBins; i++) {
0324 for (uint32_t j = 0; j < nEtBins; j++) {
0325 hfLayer1EtaEtArray[i][j] = 0xFFFFFFFF;
0326 }
0327 }
0328 ecalLUT.push_back(eCalLayer1EtaSideEtArray);
0329 hcalLUT.push_back(hCalLayer1EtaSideEtArray);
0330 hfLUT.push_back(hfLayer1EtaEtArray);
0331 }
0332 for (uint32_t twr = 0; twr < twrList.size(); twr++) {
0333
0334 int iphi = twrList[twr]->caloPhi();
0335 int ieta = twrList[twr]->caloEta();
0336 if (ieta < 0) {
0337 iphi -= 1;
0338 } else {
0339 iphi += 71;
0340 }
0341 twrList[twr]->setECALLUT(&ecalLUT[ePhiMap[iphi]]);
0342 twrList[twr]->setHCALLUT(&hcalLUT[hPhiMap[iphi]]);
0343 twrList[twr]->setHFLUT(&hfLUT[hfPhiMap[iphi]]);
0344 }
0345 }
0346
0347
0348 void L1TCaloLayer1::fillDescriptions(edm::ConfigurationDescriptions& descriptions) {
0349
0350
0351
0352 edm::ParameterSetDescription desc;
0353 desc.add<edm::InputTag>("ecalToken", edm::InputTag("simEcalTriggerPrimitiveDigis"));
0354 desc.add<edm::InputTag>("hcalToken", edm::InputTag("simHcalTriggerPrimitiveDigis"));
0355 desc.add<bool>("useLSB", true);
0356 desc.add<bool>("useCalib", true);
0357 desc.add<bool>("useECALLUT", true);
0358 desc.add<bool>("useHCALLUT", true);
0359 desc.add<bool>("useHFLUT", true);
0360 desc.add<bool>("useHCALFBLUT", false);
0361 desc.addUntracked<bool>("verbose", false);
0362 desc.add<bool>("unpackEcalMask", false);
0363 desc.add<bool>("unpackHcalMask", false);
0364 desc.add<int>("firmwareVersion", 1);
0365 descriptions.addDefault(desc);
0366 }
0367
0368
0369 DEFINE_FWK_MODULE(L1TCaloLayer1);
0370