Back to home page

Project CMSSW displayed by LXR

 
 

    


File indexing completed on 2024-06-13 03:23:53

0001 #include "L1Trigger/L1TMuonOverlapPhase1/interface/Omtf/GoldenPatternWithStat.h"
0002 #include "L1Trigger/L1TMuonOverlapPhase1/interface/Omtf/OMTFConfiguration.h"
0003 #include "L1Trigger/L1TMuonOverlapPhase1/interface/Omtf/OMTFReconstruction.h"
0004 #include "L1Trigger/L1TMuonOverlapPhase1/interface/Omtf/ProcessorBase.h"
0005 #include "L1Trigger/L1TMuonOverlapPhase1/interface/Omtf/XMLConfigReader.h"
0006 #include "L1Trigger/L1TMuonOverlapPhase1/interface/Omtf/XMLEventWriter.h"
0007 #include "L1Trigger/L1TMuonOverlapPhase1/interface/ProcConfigurationBase.h"
0008 #include "L1Trigger/L1TMuonOverlapPhase1/interface/Tools/CandidateSimMuonMatcher.h"
0009 #include "L1Trigger/L1TMuonOverlapPhase1/interface/Tools/DataROOTDumper2.h"
0010 #include "L1Trigger/L1TMuonOverlapPhase1/interface/Tools/EventCapture.h"
0011 #include "L1Trigger/L1TMuonOverlapPhase1/interface/Tools/PatternGenerator.h"
0012 
0013 #include "CondFormats/DataRecord/interface/L1TMuonOverlapParamsRcd.h"
0014 #include "CondFormats/L1TObjects/interface/L1TMuonOverlapParams.h"
0015 #include "DataFormats/L1Trigger/interface/BXVector.h"
0016 #include "DataFormats/Provenance/interface/EventID.h"
0017 #include "FWCore/Common/interface/EventBase.h"
0018 #include "FWCore/Framework/interface/EventSetupRecord.h"
0019 #include "FWCore/MessageLogger/interface/MessageLogger.h"
0020 #include "FWCore/ParameterSet/interface/FileInPath.h"
0021 #include "FWCore/Utilities/interface/Exception.h"
0022 
0023 #include <iostream>
0024 #include <memory>
0025 #include <string>
0026 #include <vector>
0027 /////////////////////////////////////////////////////
0028 /////////////////////////////////////////////////////
0029 OMTFReconstruction::OMTFReconstruction(const edm::ParameterSet& parameterSet, MuStubsInputTokens& muStubsInputTokens)
0030     : edmParameterSet(parameterSet),
0031       muStubsInputTokens(muStubsInputTokens),
0032       omtfConfig(new OMTFConfiguration()),
0033       omtfProc(nullptr),
0034       m_OMTFConfigMaker(nullptr) {
0035   bxMin = edmParameterSet.exists("bxMin") ? edmParameterSet.getParameter<int>("bxMin") : 0;
0036   bxMax = edmParameterSet.exists("bxMax") ? edmParameterSet.getParameter<int>("bxMax") : 0;
0037 
0038   edm::LogVerbatim("OMTFReconstruction") << "running emulation for the bxMin " << bxMin << " - bxMax " << bxMax
0039                                          << std::endl;
0040 }
0041 /////////////////////////////////////////////////////
0042 /////////////////////////////////////////////////////
0043 OMTFReconstruction::~OMTFReconstruction() {}
0044 
0045 /////////////////////////////////////////////////////
0046 /////////////////////////////////////////////////////
0047 void OMTFReconstruction::beginJob() {
0048   inputMaker = std::make_unique<OMTFinputMaker>(
0049       edmParameterSet, muStubsInputTokens, omtfConfig.get(), std::make_unique<OmtfAngleConverter>());
0050 }
0051 /////////////////////////////////////////////////////
0052 /////////////////////////////////////////////////////
0053 void OMTFReconstruction::endJob() {
0054   for (auto& obs : observers) {
0055     obs->endJob();
0056   }
0057 }
0058 
0059 /////////////////////////////////////////////////////
0060 /////////////////////////////////////////////////////
0061 void OMTFReconstruction::beginRun(edm::Run const& run,
0062                                   edm::EventSetup const& eventSetup,
0063                                   edm::ESGetToken<L1TMuonOverlapParams, L1TMuonOverlapParamsRcd>& omtfParamsEsToken,
0064                                   const MuonGeometryTokens& muonGeometryTokens,
0065                                   const edm::ESGetToken<MagneticField, IdealMagneticFieldRecord>& magneticFieldEsToken,
0066                                   const edm::ESGetToken<Propagator, TrackingComponentsRecord>& propagatorEsToken) {
0067   std::string processorType = "OMTFProcessor";  //GoldenPatternWithStat GoldenPattern
0068   if (edmParameterSet.exists("processorType")) {
0069     processorType = edmParameterSet.getParameter<std::string>("processorType");
0070   }
0071 
0072   bool buildPatternsFromXml = (edmParameterSet.exists("patternsXMLFile") || edmParameterSet.exists("patternsXMLFiles"));
0073 
0074   bool readConfigFromXml = edmParameterSet.exists("configXMLFile");
0075 
0076   if (buildPatternsFromXml != readConfigFromXml)
0077     throw cms::Exception(
0078         "OMTFReconstruction::beginRun: buildPatternsFromXml != readConfigFromXml -  both patternsXMLFiles and "
0079         "configXMLFile should be defined (or not) for the simOmtDigis or simOmtfPhase2Digis");
0080 
0081   edm::LogVerbatim("OMTFReconstruction") << "OMTFReconstruction::beginRun " << run.id()
0082                                          << " buildPatternsFromXml: " << buildPatternsFromXml << std::endl;
0083 
0084   //if the buildPatternsFromXml == false - we are making the omtfConfig and omtfProc for every run,
0085   //as the configuration my change between the runs,
0086   if (buildPatternsFromXml == false) {
0087     if (omtfParamsRecordWatcher.check(eventSetup)) {
0088       edm::LogVerbatim("OMTFReconstruction") << "retrieving omtfParams from EventSetup" << std::endl;
0089 
0090       const L1TMuonOverlapParams* omtfParamsFromES = &(eventSetup.getData(omtfParamsEsToken));
0091       if (!omtfParamsFromES) {
0092         edm::LogError("OMTFReconstruction") << "Could not retrieve omtfParams from Event Setup" << std::endl;
0093         throw cms::Exception("OMTFReconstruction::beginRun: Could not retrieve omtfParams from Event Setup");
0094       }
0095 
0096       omtfConfig->configure(omtfParamsFromES);
0097 
0098       //the parameters can be overwritten from the python config
0099       omtfConfig->configureFromEdmParameterSet(edmParameterSet);
0100 
0101       inputMaker->initialize(edmParameterSet, eventSetup, muonGeometryTokens);
0102 
0103       //patterns from the edm::EventSetup are reloaded every beginRun
0104       //therefore OMTFProcessor is re-created here
0105       edm::LogVerbatim("OMTFReconstruction") << "getting patterns from EventSetup" << std::endl;
0106       if (processorType == "OMTFProcessor") {
0107         omtfProc = std::make_unique<OMTFProcessor<GoldenPattern> >(
0108             omtfConfig.get(), edmParameterSet, eventSetup, omtfParamsFromES);
0109         omtfProc->printInfo();
0110       }
0111     }
0112   }
0113 
0114   //if buildPatternsFromXml == true - the entire configuration (patterns and hwToLogicLayer) comes from phyton,
0115   //so we read it only once, at the beginning of the first run, not every run
0116   if (omtfProc == nullptr && buildPatternsFromXml) {
0117     std::string fName = edmParameterSet.getParameter<edm::FileInPath>("configXMLFile").fullPath();
0118 
0119     edm::LogVerbatim("OMTFReconstruction")
0120         << "OMTFReconstruction::beginRun - reading config from file: " << fName << std::endl;
0121 
0122     XMLConfigReader xmlConfigReader;
0123     xmlConfigReader.setConfigFile(fName);
0124 
0125     omtfParams.reset(new L1TMuonOverlapParams());
0126     xmlConfigReader.readConfig(omtfParams.get());
0127 
0128     //getPatternsVersion() parses the entire patterns xml - si it is very inefficient
0129     //moreover, PatternsVersion is not used anywhere
0130     //Therefore we we dont use xmlPatternReader.getPatternsVersion(); but set patternsVersion to 0
0131     unsigned int patternsVersion = 0;
0132     unsigned int fwVersion = omtfParams->fwVersion();
0133     omtfParams->setFwVersion((fwVersion << 16) + patternsVersion);
0134 
0135     omtfConfig->configure(omtfParams.get());
0136 
0137     //the parameters can be overwritten from the python config
0138     omtfConfig->configureFromEdmParameterSet(edmParameterSet);
0139 
0140     inputMaker->initialize(edmParameterSet, eventSetup, muonGeometryTokens);
0141 
0142     //reading patterns from the xml----------------------------------------------------------
0143     std::vector<std::string> patternsXMLFiles;
0144 
0145     if (edmParameterSet.exists("patternsXMLFile")) {
0146       patternsXMLFiles.push_back(edmParameterSet.getParameter<edm::FileInPath>("patternsXMLFile").fullPath());
0147     } else if (edmParameterSet.exists("patternsXMLFiles")) {
0148       for (const auto& it : edmParameterSet.getParameter<std::vector<edm::ParameterSet> >("patternsXMLFiles")) {
0149         patternsXMLFiles.push_back(it.getParameter<edm::FileInPath>("patternsXMLFile").fullPath());
0150       }
0151     }
0152 
0153     for (auto& patternsXMLFile : patternsXMLFiles)
0154       edm::LogVerbatim("OMTFReconstruction") << "reading patterns from " << patternsXMLFile << std::endl;
0155 
0156     std::string patternType = "GoldenPattern";  //GoldenPatternWithStat GoldenPattern
0157     if (edmParameterSet.exists("patternType")) {
0158       patternType = edmParameterSet.getParameter<std::string>("patternType");
0159     }
0160 
0161     if (patternType == "GoldenPattern") {
0162       if (processorType == "OMTFProcessor") {
0163         if (omtfParams) {
0164           omtfProc = std::make_unique<OMTFProcessor<GoldenPattern> >(
0165               omtfConfig.get(),
0166               edmParameterSet,
0167               eventSetup,
0168               xmlConfigReader.readPatterns<GoldenPattern>(*omtfParams, patternsXMLFiles, false));
0169         } else {  //in principle should not happen
0170           throw cms::Exception("OMTFReconstruction::beginRun: omtfParams is nullptr");
0171         }
0172       }
0173 
0174       edm::LogVerbatim("OMTFReconstruction") << "OMTFProcessor constructed. processorType " << processorType
0175                                              << ". GoldenPattern type: " << patternType << std::endl;
0176     } else if (patternType == "GoldenPatternWithStat") {
0177       //pattern generation is only possible if the processor is constructed only once per job
0178       //PatternGenerator modifies the patterns!!!
0179       if (processorType == "OMTFProcessor") {
0180         if (omtfParams) {
0181           omtfProc = std::make_unique<OMTFProcessor<GoldenPatternWithStat> >(
0182               omtfConfig.get(),
0183               edmParameterSet,
0184               eventSetup,
0185               xmlConfigReader.readPatterns<GoldenPatternWithStat>(*omtfParams, patternsXMLFiles, false));
0186         } else {  //in principle should not happen
0187           throw cms::Exception("OMTFReconstruction::beginRun: omtfParams is nullptr");
0188         }
0189       }
0190     } else {
0191       throw cms::Exception("OMTFReconstruction::beginRun: unknown GoldenPattern type: " + patternType);
0192     }
0193 
0194     omtfProc->printInfo();
0195   }
0196 
0197   addObservers(muonGeometryTokens, magneticFieldEsToken, propagatorEsToken);
0198 
0199   for (auto& obs : observers) {
0200     obs->beginRun(eventSetup);
0201   }
0202 }
0203 
0204 void OMTFReconstruction::addObservers(
0205     const MuonGeometryTokens& muonGeometryTokens,
0206     const edm::ESGetToken<MagneticField, IdealMagneticFieldRecord>& magneticFieldEsToken,
0207     const edm::ESGetToken<Propagator, TrackingComponentsRecord>& propagatorEsToken) {
0208   if (!observers.empty())  //assuring it is done only at the first run
0209     return;
0210 
0211   edm::LogVerbatim("OMTFReconstruction") << "OMTFReconstruction::addObservers " << std::endl;
0212 
0213   //omtfConfig is created at constructor, and is not re-created at the the start of the run, so this is OK
0214   if (edmParameterSet.exists("dumpResultToXML")) {
0215     if (edmParameterSet.getParameter<bool>("dumpResultToXML"))
0216       observers.emplace_back(std::make_unique<XMLEventWriter>(
0217           omtfConfig.get(), edmParameterSet.getParameter<std::string>("XMLDumpFileName")));
0218   }
0219 
0220   CandidateSimMuonMatcher* candidateSimMuonMatcher = nullptr;
0221 
0222   if (edmParameterSet.exists("candidateSimMuonMatcher")) {
0223     if (edmParameterSet.getParameter<bool>("candidateSimMuonMatcher")) {
0224       observers.emplace_back(std::make_unique<CandidateSimMuonMatcher>(
0225           edmParameterSet, omtfConfig.get(), magneticFieldEsToken, propagatorEsToken));
0226       candidateSimMuonMatcher = static_cast<CandidateSimMuonMatcher*>(observers.back().get());
0227     }
0228   }
0229 
0230   auto omtfProcGoldenPat = dynamic_cast<OMTFProcessor<GoldenPattern>*>(omtfProc.get());
0231   if (omtfProcGoldenPat) {
0232     if (edmParameterSet.exists("eventCaptureDebug"))
0233       if (edmParameterSet.getParameter<bool>("eventCaptureDebug")) {
0234         observers.emplace_back(std::make_unique<EventCapture>(
0235             edmParameterSet, omtfConfig.get(), candidateSimMuonMatcher, muonGeometryTokens
0236             //&(omtfProcGoldenPat->getPatterns() ),
0237             //watch out, will crash if the proc is re-constructed from the DB after L1TMuonOverlapParamsRcd change
0238             ));
0239       }
0240 
0241     if (edmParameterSet.exists("dumpHitsToROOT") && edmParameterSet.getParameter<bool>("dumpHitsToROOT")) {
0242       //std::string rootFileName = edmParameterSet.getParameter<std::string>("dumpHitsFileName");
0243       if (candidateSimMuonMatcher == nullptr) {
0244         edm::LogVerbatim("OMTFReconstruction")
0245             << "dumpHitsToROOT needs candidateSimMuonMatcher, but it is null " << std::endl;
0246         throw cms::Exception("dumpHitsToROOT needs candidateSimMuonMatcher, but it is null");
0247       }
0248       observers.emplace_back(
0249           std::make_unique<DataROOTDumper2>(edmParameterSet, omtfConfig.get(), candidateSimMuonMatcher));
0250     }
0251   }
0252 
0253   auto omtfProcGoldenPatWithStat = dynamic_cast<OMTFProcessor<GoldenPatternWithStat>*>(omtfProc.get());
0254   if (omtfProcGoldenPatWithStat) {
0255     if (edmParameterSet.exists("eventCaptureDebug"))
0256       if (edmParameterSet.getParameter<bool>("eventCaptureDebug")) {
0257         observers.emplace_back(std::make_unique<EventCapture>(
0258             edmParameterSet, omtfConfig.get(), candidateSimMuonMatcher, muonGeometryTokens
0259             //&(omtfProcGoldenPat->getPatterns() ),
0260             //watch out, will crash if the proc is re-constructed from the DB after L1TMuonOverlapParamsRcd change
0261             ));
0262       }
0263 
0264     if (edmParameterSet.exists("generatePatterns") && edmParameterSet.getParameter<bool>("generatePatterns")) {
0265       observers.emplace_back(std::make_unique<PatternGenerator>(
0266           edmParameterSet, omtfConfig.get(), omtfProcGoldenPatWithStat->getPatterns(), candidateSimMuonMatcher));
0267       edm::LogVerbatim("OMTFReconstruction") << "generatePatterns: true " << std::endl;
0268     }
0269   }
0270 }
0271 /////////////////////////////////////////////////////
0272 /////////////////////////////////////////////////////
0273 std::unique_ptr<l1t::RegionalMuonCandBxCollection> OMTFReconstruction::reconstruct(const edm::Event& iEvent,
0274                                                                                    const edm::EventSetup& evSetup) {
0275   LogTrace("l1tOmtfEventPrint") << "\n" << __FUNCTION__ << ":" << __LINE__ << " iEvent " << iEvent.id().event() << endl;
0276   inputMaker->loadAndFilterDigis(iEvent);
0277 
0278   for (auto& obs : observers) {
0279     obs->observeEventBegin(iEvent);
0280   }
0281 
0282   std::unique_ptr<l1t::RegionalMuonCandBxCollection> candidates = std::make_unique<l1t::RegionalMuonCandBxCollection>();
0283   candidates->setBXRange(bxMin, bxMax);
0284 
0285   ///The order is important: first put omtf_pos candidates, then omtf_neg.
0286   for (int bx = bxMin; bx <= bxMax; bx++) {
0287     for (unsigned int iProcessor = 0; iProcessor < omtfConfig->nProcessors(); ++iProcessor) {
0288       std::vector<l1t::RegionalMuonCand> candMuons =
0289           omtfProc->run(iProcessor, l1t::tftype::omtf_pos, bx, inputMaker.get(), observers);
0290 
0291       //fill outgoing collection
0292       for (auto& candMuon : candMuons) {
0293         candidates->push_back(bx, candMuon);
0294       }
0295     }
0296 
0297     for (unsigned int iProcessor = 0; iProcessor < omtfConfig->nProcessors(); ++iProcessor) {
0298       std::vector<l1t::RegionalMuonCand> candMuons =
0299           omtfProc->run(iProcessor, l1t::tftype::omtf_neg, bx, inputMaker.get(), observers);
0300 
0301       //fill outgoing collection
0302       for (auto& candMuon : candMuons) {
0303         candidates->push_back(bx, candMuon);
0304       }
0305     }
0306 
0307     //edm::LogInfo("OMTFReconstruction") <<"OMTF:  Number of candidates in BX="<<bx<<": "<<candidates->size(bx) << std::endl;;
0308   }
0309 
0310   for (auto& obs : observers) {
0311     obs->observeEventEnd(iEvent, candidates);
0312   }
0313 
0314   return candidates;
0315 }
0316 
0317 /////////////////////////////////////////////////////
0318 /////////////////////////////////////////////////////