88// system include files
99#include < memory>
1010#include < cmath>
11+ #include < tinyxml2.h>
1112
1213// user include files
1314#include " FWCore/Framework/interface/Frameworkfwd.h"
2324#include " Geometry/Records/interface/TrackerDigiGeometryRecord.h"
2425#include " Geometry/TrackerGeometryBuilder/interface/TrackerGeometry.h"
2526
27+ #include " CommonTools/MVAUtils/interface/TMVAZipReader.h"
28+
2629// TrajectorySeed
2730#include " DataFormats/TrajectorySeed/interface/TrajectorySeed.h"
2831#include " DataFormats/TrajectorySeed/interface/TrajectorySeedCollection.h"
@@ -44,6 +47,7 @@ class MuonHLTSeedMVAClassifier : public edm::stream::EDProducer<> {
4447 ~MuonHLTSeedMVAClassifier () override = default ;
4548
4649 static void fillDescriptions (edm::ConfigurationDescriptions& descriptions);
50+ bool checkMVAFileConsistency (const std::string& weightsFileFullPath, bool isFromL1) const ;
4751
4852private:
4953 void produce (edm::Event&, const edm::EventSetup&) override ;
@@ -87,33 +91,67 @@ class MuonHLTSeedMVAClassifier : public edm::stream::EDProducer<> {
8791 const reco::RecoChargedCandidateCollection& l2Muons);
8892};
8993
94+ bool MuonHLTSeedMVAClassifier::checkMVAFileConsistency (const std::string& weightsFileFullPath,
95+ const bool isFromL1) const {
96+ tinyxml2::XMLDocument xmlDoc;
97+ if (reco::details::hasEnding (weightsFileFullPath, " .xml" )) {
98+ xmlDoc.LoadFile (weightsFileFullPath.c_str ());
99+ } else {
100+ edm::LogError (" MuonHLTSeedMVAClassifier" ) << " unsupported file extension, it should be a .xml file!" ;
101+ return false ;
102+ }
103+ tinyxml2::XMLElement* root = xmlDoc.FirstChildElement (" MethodSetup" );
104+ if (root == nullptr ) {
105+ edm::LogError (" MuonHLTSeedMVAClassifier" ) << " could not retrieve the MethodSetup node from XML file!" ;
106+ return false ;
107+ }
108+
109+ const auto & vars = root->FirstChildElement (" Variables" );
110+ size_t n = 0 ;
111+ if (vars != nullptr ) {
112+ for (tinyxml2::XMLElement* e = vars->FirstChildElement (" Variable" ); e != nullptr ;
113+ e = e->NextSiblingElement (" Variable" )) {
114+ ++n;
115+ }
116+ } else {
117+ edm::LogError (" MuonHLTSeedMVAClassifier" ) << " could not retrieve the Variables node from XML file!" ;
118+ return false ;
119+ }
120+
121+ LogTrace (" MuonHLTSeedMVAClassifier" ) << " MVA file:" << weightsFileFullPath.c_str () << " n Var:" << n;
122+ bool condition = (isFromL1 && (n == inputIndexes::kLastL1 )) || (!isFromL1 && (n == inputIndexes::kLastL2 ));
123+ return condition;
124+ }
125+
90126MuonHLTSeedMVAClassifier::MuonHLTSeedMVAClassifier (const edm::ParameterSet& iConfig)
91127 : seedToken_(consumes<TrajectorySeedCollection>(iConfig.getParameter<edm::InputTag>(" src" ))),
92128 l1MuonToken_(consumes<l1t::MuonBxCollection>(iConfig.getParameter<edm::InputTag>(" L1Muon" ))),
93129 l2MuonToken_(consumes<reco::RecoChargedCandidateCollection>(iConfig.getParameter<edm::InputTag>(" L2Muon" ))),
94130 trackerGeometryToken_(esConsumes<TrackerGeometry, TrackerDigiGeometryRecord>()),
95-
96131 rejectAll_(iConfig.getParameter<bool >(" rejectAll" )),
97132 isFromL1_(iConfig.getParameter<bool >(" isFromL1" )),
98-
99- mvaFileB_(iConfig.getParameter<edm::FileInPath>(isFromL1_ ? " mvaFileBL1" : " mvaFileBL2" )),
100- mvaFileE_(iConfig.getParameter<edm::FileInPath>(isFromL1_ ? " mvaFileEL1" : " mvaFileEL2" )),
101-
102- mvaScaleMeanB_(iConfig.getParameter<std::vector<double >>(isFromL1_ ? " mvaScaleMeanBL1" : " mvaScaleMeanBL2" )),
103- mvaScaleStdB_(iConfig.getParameter<std::vector<double >>(isFromL1_ ? " mvaScaleStdBL1" : " mvaScaleStdBL2" )),
104- mvaScaleMeanE_(iConfig.getParameter<std::vector<double >>(isFromL1_ ? " mvaScaleMeanEL1" : " mvaScaleMeanEL2" )),
105- mvaScaleStdE_(iConfig.getParameter<std::vector<double >>(isFromL1_ ? " mvaScaleStdEL1" : " mvaScaleStdEL2" )),
106-
133+ mvaFileB_(iConfig.getParameter<edm::FileInPath>(" mvaFileB" )),
134+ mvaFileE_(iConfig.getParameter<edm::FileInPath>(" mvaFileE" )),
135+ mvaScaleMeanB_(iConfig.getParameter<std::vector<double >>(" mvaScaleMeanB" )),
136+ mvaScaleStdB_(iConfig.getParameter<std::vector<double >>(" mvaScaleStdB" )),
137+ mvaScaleMeanE_(iConfig.getParameter<std::vector<double >>(" mvaScaleMeanE" )),
138+ mvaScaleStdE_(iConfig.getParameter<std::vector<double >>(" mvaScaleStdE" )),
107139 doSort_(iConfig.getParameter<bool >(" doSort" )),
108140 nSeedsMaxB_(iConfig.getParameter<int >(" nSeedsMaxB" )),
109141 nSeedsMaxE_(iConfig.getParameter<int >(" nSeedsMaxE" )),
110-
111142 etaEdge_(iConfig.getParameter<double >(" etaEdge" )),
112143 mvaCutB_(iConfig.getParameter<double >(" mvaCutB" )),
113144 mvaCutE_(iConfig.getParameter<double >(" mvaCutE" )),
114-
115145 minL1Qual_(iConfig.getParameter<int >(" minL1Qual" )),
116146 baseScore_(iConfig.getParameter<double >(" baseScore" )) {
147+ const auto & mvaFileBPath = mvaFileB_.fullPath ();
148+ const auto & mvaFileEPath = mvaFileE_.fullPath ();
149+
150+ if (!checkMVAFileConsistency (mvaFileBPath, isFromL1_) || !checkMVAFileConsistency (mvaFileEPath, isFromL1_)) {
151+ throw cms::Exception (" ConfigurationError" ) << " MVA files appear to be not consistent with the value of isFromL1 "
152+ " parameter.\n Please check your configuration." ;
153+ }
154+
117155 if (!rejectAll_) {
118156 mvaEstimator_ = std::make_pair (
119157 std::make_unique<SeedMvaEstimator>(mvaFileB_, mvaScaleMeanB_, mvaScaleStdB_, isFromL1_, minL1Qual_),
@@ -247,22 +285,14 @@ void MuonHLTSeedMVAClassifier::fillDescriptions(edm::ConfigurationDescriptions&
247285 desc.add <bool >(" rejectAll" , false );
248286 desc.add <bool >(" isFromL1" , false );
249287
250- desc.add <edm::FileInPath>(" mvaFileBL1 " ,
288+ desc.add <edm::FileInPath>(" mvaFileB " ,
251289 edm::FileInPath (" RecoMuon/TrackerSeedGenerator/data/xgb_Run3_Iter2FromL1Seeds_barrel.xml" ));
252- desc.add <edm::FileInPath>(" mvaFileEL1 " ,
290+ desc.add <edm::FileInPath>(" mvaFileE " ,
253291 edm::FileInPath (" RecoMuon/TrackerSeedGenerator/data/xgb_Run3_Iter2FromL1Seeds_endcap.xml" ));
254- desc.add <edm::FileInPath>(" mvaFileBL2" ,
255- edm::FileInPath (" RecoMuon/TrackerSeedGenerator/data/xgb_Run3_Iter2Seeds_barrel.xml" ));
256- desc.add <edm::FileInPath>(" mvaFileEL2" ,
257- edm::FileInPath (" RecoMuon/TrackerSeedGenerator/data/xgb_Run3_Iter2Seeds_endcap.xml" ));
258- desc.add <std::vector<double >>(" mvaScaleMeanBL1" , {0 ., 0 ., 0 ., 0 ., 0 ., 0 ., 0 ., 0 .});
259- desc.add <std::vector<double >>(" mvaScaleStdBL1" , {1 ., 1 ., 1 ., 1 ., 1 ., 1 ., 1 ., 1 .});
260- desc.add <std::vector<double >>(" mvaScaleMeanEL1" , {0 ., 0 ., 0 ., 0 ., 0 ., 0 ., 0 ., 0 .});
261- desc.add <std::vector<double >>(" mvaScaleStdEL1" , {1 ., 1 ., 1 ., 1 ., 1 ., 1 ., 1 ., 1 .});
262- desc.add <std::vector<double >>(" mvaScaleMeanBL2" , {0 ., 0 ., 0 ., 0 ., 0 ., 0 ., 0 ., 0 ., 0 ., 0 .});
263- desc.add <std::vector<double >>(" mvaScaleStdBL2" , {1 ., 1 ., 1 ., 1 ., 1 ., 1 ., 1 ., 1 ., 1 ., 1 .});
264- desc.add <std::vector<double >>(" mvaScaleMeanEL2" , {0 ., 0 ., 0 ., 0 ., 0 ., 0 ., 0 ., 0 ., 0 ., 0 .});
265- desc.add <std::vector<double >>(" mvaScaleStdEL2" , {1 ., 1 ., 1 ., 1 ., 1 ., 1 ., 1 ., 1 ., 1 ., 1 .});
292+ desc.add <std::vector<double >>(" mvaScaleMeanB" , {0 ., 0 ., 0 ., 0 ., 0 ., 0 ., 0 ., 0 .});
293+ desc.add <std::vector<double >>(" mvaScaleStdB" , {1 ., 1 ., 1 ., 1 ., 1 ., 1 ., 1 ., 1 .});
294+ desc.add <std::vector<double >>(" mvaScaleMeanE" , {0 ., 0 ., 0 ., 0 ., 0 ., 0 ., 0 ., 0 .});
295+ desc.add <std::vector<double >>(" mvaScaleStdE" , {1 ., 1 ., 1 ., 1 ., 1 ., 1 ., 1 ., 1 .});
266296
267297 desc.add <bool >(" doSort" , false );
268298 desc.add <int >(" nSeedsMaxB" , 1e6 );
0 commit comments