File indexing completed on 2025-01-21 01:39:48
0001
0002
0003
0004
0005
0006
0007
0008
0009 #ifndef gen_GeneratorFilter_h
0010 #define gen_GeneratorFilter_h
0011
0012 #include <memory>
0013 #include <string>
0014 #include <vector>
0015
0016 #include "HepMC3/GenEvent.h"
0017
0018 #include "FWCore/Concurrency/interface/SharedResourceNames.h"
0019 #include "FWCore/Framework/interface/one/EDFilter.h"
0020 #include "FWCore/Framework/interface/Event.h"
0021 #include "FWCore/Framework/interface/EventSetup.h"
0022 #include "FWCore/Framework/interface/FileBlock.h"
0023 #include "FWCore/Framework/interface/LuminosityBlock.h"
0024 #include "FWCore/Framework/interface/MakerMacros.h"
0025 #include "FWCore/Framework/interface/Run.h"
0026 #include "FWCore/Framework/interface/ConsumesCollector.h"
0027 #include "FWCore/ParameterSet/interface/ParameterSet.h"
0028 #include "FWCore/ServiceRegistry/interface/RandomEngineSentry.h"
0029 #include "FWCore/Utilities/interface/EDMException.h"
0030 #include "CLHEP/Random/RandomEngine.h"
0031
0032
0033
0034
0035 #include "SimDataFormats/GeneratorProducts/interface/HepMCProduct.h"
0036 #include "SimDataFormats/GeneratorProducts/interface/HepMC3Product.h"
0037 #include "SimDataFormats/GeneratorProducts/interface/GenRunInfoProduct.h"
0038 #include "SimDataFormats/GeneratorProducts/interface/GenLumiInfoHeader.h"
0039 #include "SimDataFormats/GeneratorProducts/interface/GenLumiInfoProduct.h"
0040 #include "SimDataFormats/GeneratorProducts/interface/GenEventInfoProduct.h"
0041 #include "SimDataFormats/GeneratorProducts/interface/GenEventInfoProduct3.h"
0042
0043 namespace edm {
0044 template <class HAD, class DEC>
0045 class GeneratorFilter : public one::EDFilter<EndRunProducer,
0046 BeginLuminosityBlockProducer,
0047 EndLuminosityBlockProducer,
0048 one::WatchLuminosityBlocks,
0049 one::SharedResources> {
0050 public:
0051 typedef HAD Hadronizer;
0052 typedef DEC Decayer;
0053
0054
0055
0056 explicit GeneratorFilter(ParameterSet const& ps);
0057
0058 ~GeneratorFilter() override;
0059
0060 bool filter(Event& e, EventSetup const& es) override;
0061 void endRunProduce(Run&, EventSetup const&) override;
0062 void beginLuminosityBlock(LuminosityBlock const&, EventSetup const&) override;
0063 void beginLuminosityBlockProduce(LuminosityBlock&, EventSetup const&) override;
0064 void endLuminosityBlock(LuminosityBlock const&, EventSetup const&) override;
0065 void endLuminosityBlockProduce(LuminosityBlock&, EventSetup const&) override;
0066 void preallocThreads(unsigned int iThreads) override;
0067
0068 private:
0069
0070 void init(ParameterSet const& ps);
0071
0072 Hadronizer hadronizer_;
0073
0074 Decayer* decayer_ = nullptr;
0075 unsigned int nEventsInLumiBlock_ = 0;
0076 unsigned int nThreads_{1};
0077 bool initialized_ = false;
0078 unsigned int ivhepmc = 2;
0079 };
0080
0081
0082
0083
0084
0085 template <class HAD, class DEC>
0086 GeneratorFilter<HAD, DEC>::GeneratorFilter(ParameterSet const& ps) : hadronizer_(ps) {
0087 init(ps);
0088 }
0089
0090 template <class HAD, class DEC>
0091 void GeneratorFilter<HAD, DEC>::init(ParameterSet const& ps) {
0092
0093
0094
0095
0096
0097
0098
0099
0100
0101 ivhepmc = hadronizer_.getVHepMC();
0102
0103 std::vector<std::string> const& sharedResources = hadronizer_.sharedResources();
0104 for (auto const& resource : sharedResources) {
0105 usesResource(resource);
0106 }
0107
0108 if (ps.exists("ExternalDecays")) {
0109
0110 ParameterSet ps1 = ps.getParameter<ParameterSet>("ExternalDecays");
0111 decayer_ = new Decayer(ps1, consumesCollector());
0112
0113 std::vector<std::string> const& sharedResourcesDec = decayer_->sharedResources();
0114 for (auto const& resource : sharedResourcesDec) {
0115 usesResource(resource);
0116 }
0117 }
0118
0119
0120
0121 if (sharedResources.empty() && (!decayer_ || decayer_->sharedResources().empty())) {
0122 usesResource(edm::uniqueSharedResourceName());
0123 }
0124
0125 if (ivhepmc == 2) {
0126 produces<edm::HepMCProduct>("unsmeared");
0127 produces<GenEventInfoProduct>();
0128 } else if (ivhepmc == 3) {
0129 produces<edm::HepMC3Product>("unsmeared");
0130 produces<GenEventInfoProduct3>();
0131 }
0132 produces<GenLumiInfoHeader, edm::Transition::BeginLuminosityBlock>();
0133 produces<GenLumiInfoProduct, edm::Transition::EndLuminosityBlock>();
0134 produces<GenRunInfoProduct, edm::Transition::EndRun>();
0135 }
0136
0137 template <class HAD, class DEC>
0138 GeneratorFilter<HAD, DEC>::~GeneratorFilter() {
0139 if (decayer_)
0140 delete decayer_;
0141 }
0142
0143 template <class HAD, class DEC>
0144 void GeneratorFilter<HAD, DEC>::preallocThreads(unsigned int iThreads) {
0145 nThreads_ = iThreads;
0146 }
0147
0148 template <class HAD, class DEC>
0149 bool GeneratorFilter<HAD, DEC>::filter(Event& ev, EventSetup const& ) {
0150 RandomEngineSentry<HAD> randomEngineSentry(&hadronizer_, ev.streamID());
0151 RandomEngineSentry<DEC> randomEngineSentryDecay(decayer_, ev.streamID());
0152
0153
0154
0155 bool passEvtGenSelector = false;
0156 std::unique_ptr<HepMC::GenEvent> event(nullptr);
0157 std::unique_ptr<HepMC3::GenEvent> event3(nullptr);
0158
0159 while (!passEvtGenSelector) {
0160 event.reset();
0161 event3.reset();
0162 hadronizer_.setEDMEvent(ev);
0163
0164 if (!hadronizer_.generatePartonsAndHadronize())
0165 return false;
0166
0167
0168
0169
0170
0171
0172
0173 if (!hadronizer_.decay())
0174 return false;
0175
0176 event = hadronizer_.getGenEvent();
0177 event3 = hadronizer_.getGenEvent3();
0178 if (ivhepmc == 2 && !event.get())
0179 return false;
0180 if (ivhepmc == 3 && !event3.get())
0181 return false;
0182
0183
0184
0185
0186 if (decayer_) {
0187 if (ivhepmc == 2) {
0188 auto t = decayer_->decay(event.get());
0189 if (t != event.get()) {
0190 event.reset(t);
0191 }
0192 }
0193 if (ivhepmc == 3) {
0194 auto t = decayer_->decay(event3.get());
0195 if (t != event3.get()) {
0196 event3.reset(t);
0197 }
0198 }
0199 }
0200 if (ivhepmc == 2 && !event.get())
0201 return false;
0202 if (ivhepmc == 3 && !event3.get())
0203 return false;
0204
0205 passEvtGenSelector = hadronizer_.select(event.get());
0206 }
0207
0208
0209
0210
0211
0212 if (ivhepmc == 2)
0213 hadronizer_.resetEvent(std::move(event));
0214 else if (ivhepmc == 3)
0215 hadronizer_.resetEvent3(std::move(event3));
0216
0217
0218
0219
0220 if (!hadronizer_.residualDecay())
0221 return false;
0222
0223 hadronizer_.finalizeEvent();
0224
0225 event = hadronizer_.getGenEvent();
0226 event3 = hadronizer_.getGenEvent3();
0227 if (ivhepmc == 2) {
0228 if (!event.get())
0229 return false;
0230 event->set_event_number(ev.id().event());
0231
0232 } else if (ivhepmc == 3) {
0233 if (!event3.get())
0234 return false;
0235 event3->set_event_number(ev.id().event());
0236 }
0237
0238
0239
0240
0241 if (ivhepmc == 2) {
0242 auto genEventInfo = hadronizer_.getGenEventInfo();
0243 if (!genEventInfo.get()) {
0244
0245 genEventInfo.reset(new GenEventInfoProduct(event.get()));
0246 }
0247
0248 ev.put(std::move(genEventInfo));
0249
0250 std::unique_ptr<HepMCProduct> bare_product(new HepMCProduct());
0251 bare_product->addHepMCData(event.release());
0252 ev.put(std::move(bare_product), "unsmeared");
0253
0254 } else if (ivhepmc == 3) {
0255 auto genEventInfo3 = hadronizer_.getGenEventInfo3();
0256 if (!genEventInfo3.get()) {
0257
0258 genEventInfo3.reset(new GenEventInfoProduct3(event3.get()));
0259 }
0260
0261 ev.put(std::move(genEventInfo3));
0262
0263 std::unique_ptr<HepMC3Product> bare_product(new HepMC3Product());
0264 bare_product->addHepMCData(event3.release());
0265 ev.put(std::move(bare_product), "unsmeared");
0266 }
0267
0268 nEventsInLumiBlock_++;
0269 return true;
0270 }
0271
0272 template <class HAD, class DEC>
0273 void GeneratorFilter<HAD, DEC>::endRunProduce(Run& r, EventSetup const&) {
0274
0275
0276
0277
0278
0279 if (initialized_) {
0280 hadronizer_.statistics();
0281
0282 if (decayer_)
0283 decayer_->statistics();
0284 }
0285
0286 std::unique_ptr<GenRunInfoProduct> griproduct(new GenRunInfoProduct(hadronizer_.getGenRunInfo()));
0287 r.put(std::move(griproduct));
0288 }
0289
0290 template <class HAD, class DEC>
0291 void GeneratorFilter<HAD, DEC>::beginLuminosityBlock(LuminosityBlock const& lumi, EventSetup const& es) {}
0292
0293 template <class HAD, class DEC>
0294 void GeneratorFilter<HAD, DEC>::beginLuminosityBlockProduce(LuminosityBlock& lumi, EventSetup const& es) {
0295 nEventsInLumiBlock_ = 0;
0296 RandomEngineSentry<HAD> randomEngineSentry(&hadronizer_, lumi.index());
0297 RandomEngineSentry<DEC> randomEngineSentryDecay(decayer_, lumi.index());
0298
0299 hadronizer_.randomizeIndex(lumi, randomEngineSentry.randomEngine());
0300 hadronizer_.generateLHE(lumi, randomEngineSentry.randomEngine(), nThreads_);
0301
0302 if (!hadronizer_.readSettings(0))
0303 throw edm::Exception(errors::Configuration)
0304 << "Failed to read settings for the hadronizer " << hadronizer_.classname() << " \n";
0305
0306 if (decayer_) {
0307 decayer_->init(es);
0308 if (!hadronizer_.declareStableParticles(decayer_->operatesOnParticles()))
0309 throw edm::Exception(errors::Configuration)
0310 << "Failed to declare stable particles in hadronizer " << hadronizer_.classname() << "\n";
0311 if (!hadronizer_.declareSpecialSettings(decayer_->specialSettings()))
0312 throw edm::Exception(errors::Configuration)
0313 << "Failed to declare special settings in hadronizer " << hadronizer_.classname() << "\n";
0314 }
0315
0316 if (!hadronizer_.initializeForInternalPartons())
0317 throw edm::Exception(errors::Configuration)
0318 << "Failed to initialize hadronizer " << hadronizer_.classname() << " for internal parton generation\n";
0319
0320 std::unique_ptr<GenLumiInfoHeader> genLumiInfoHeader(hadronizer_.getGenLumiInfoHeader());
0321 lumi.put(std::move(genLumiInfoHeader));
0322 initialized_ = true;
0323 }
0324
0325 template <class HAD, class DEC>
0326 void GeneratorFilter<HAD, DEC>::endLuminosityBlock(LuminosityBlock const&, EventSetup const&) {
0327 hadronizer_.cleanLHE();
0328 }
0329
0330 template <class HAD, class DEC>
0331 void GeneratorFilter<HAD, DEC>::endLuminosityBlockProduce(LuminosityBlock& lumi, EventSetup const&) {
0332 hadronizer_.statistics();
0333 if (decayer_)
0334 decayer_->statistics();
0335
0336 GenRunInfoProduct genRunInfo = GenRunInfoProduct(hadronizer_.getGenRunInfo());
0337 std::vector<GenLumiInfoProduct::ProcessInfo> GenLumiProcess;
0338 const GenRunInfoProduct::XSec& xsec = genRunInfo.internalXSec();
0339 GenLumiInfoProduct::ProcessInfo temp;
0340 temp.setProcess(0);
0341 temp.setLheXSec(xsec.value(), xsec.error());
0342 temp.setNPassPos(nEventsInLumiBlock_);
0343 temp.setNPassNeg(0);
0344 temp.setNTotalPos(nEventsInLumiBlock_);
0345 temp.setNTotalNeg(0);
0346 temp.setTried(nEventsInLumiBlock_, nEventsInLumiBlock_, nEventsInLumiBlock_);
0347 temp.setSelected(nEventsInLumiBlock_, nEventsInLumiBlock_, nEventsInLumiBlock_);
0348 temp.setKilled(nEventsInLumiBlock_, nEventsInLumiBlock_, nEventsInLumiBlock_);
0349 temp.setAccepted(0, -1, -1);
0350 temp.setAcceptedBr(0, -1, -1);
0351 GenLumiProcess.push_back(temp);
0352
0353 std::unique_ptr<GenLumiInfoProduct> genLumiInfo(new GenLumiInfoProduct());
0354 genLumiInfo->setHEPIDWTUP(-1);
0355 genLumiInfo->setProcessInfo(GenLumiProcess);
0356
0357 lumi.put(std::move(genLumiInfo));
0358
0359 nEventsInLumiBlock_ = 0;
0360 }
0361 }
0362
0363 #endif