EventGenerator.cxx
Go to the documentation of this file.
1 //____________________________________________________________________________
2 /*
3  Copyright (c) 2003-2020, The GENIE Collaboration
4  For the full text of the license visit http://copyright.genie-mc.org
5 
6  Costas Andreopoulos <constantinos.andreopoulos \at cern.ch>
7  University of Liverpool & STFC Rutherford Appleton Laboratory
8 */
9 //____________________________________________________________________________
10 
11 #include <cassert>
12 #include <sstream>
13 #include <cstdlib>
14 #include <algorithm>
15 
16 #include <TMath.h>
17 #include <TBits.h>
18 #include <TSystem.h>
19 #include <TStopwatch.h>
20 
33 
34 using std::ostringstream;
35 
36 using namespace genie;
37 using namespace genie::utils;
38 using namespace genie::controls;
39 using namespace genie::exceptions;
40 
41 //___________________________________________________________________________
43 EventGeneratorI("genie::EventGenerator")
44 {
45  this->Init();
46 }
47 //___________________________________________________________________________
49 EventGeneratorI("genie::EventGenerator", config)
50 {
51  this->Init();
52 }
53 //___________________________________________________________________________
55 {
56  delete fWatch;
57  delete fFiltUnphysMask;
58 
59  if(fEVGModuleVec) delete fEVGModuleVec;
60  if(fEVGTime) delete fEVGTime;
61  if(fVldContext) delete fVldContext;
62 }
63 //___________________________________________________________________________
65 {
66  LOG("EventGenerator", pNOTICE) << "Generating Event...";
67 
68  //-- Clear previous virtual list folder
69  LOG("EventGenerator", pNOTICE) << "Clearing the GHepVirtualListFolder";
71  vlfolder->Clear();
72 
73  //-- Clean previous history + add the bootstrap record in the buffer
75  fRecHistory.AddSnapshot(-1, event_rec);
76 
77  //-- Initialize evg thread control flags
78  bool ffwd = false;
79  unsigned int nexceptions = 0;
80 
81  //-- Reset stop-watch
82  fWatch->Reset();
83 
84  string mesgh = "Event generation thread: " + this->Id().Key() +
85  " -> Running module: ";
86 
87  //-- Loop over the event record processing modules
88  int istep=0;
90 
91  for(miter = fEVGModuleVec->begin();
92  miter != fEVGModuleVec->end(); ++miter)
93  {
94  const EventRecordVisitorI * visitor = *miter; // generation module
95 
96  string mesg = mesgh + visitor->Id().Key();
97  LOG("EventGenerator", pNOTICE)
98  << utils::print::PrintFramedMesg(mesg,0,'~');
99  if(ffwd) {
100  LOG("EventGenerator", pNOTICE)
101  << "Fast Forward flag was set - Skipping processing step!";
102  continue;
103  }
104  try
105  {
106  fWatch->Start();
107  visitor->ProcessEventRecord(event_rec);
108  fWatch->Stop();
109  fRecHistory.AddSnapshot(istep, event_rec);
110  (*fEVGTime)[istep] = fWatch->CpuTime(); // sec
111  }
113  {
114  LOG("EventGenerator", pNOTICE)
115  << "An exception was thrown and caught by EventGenerator!";
116  LOG("EventGenerator", pNOTICE) << exception;
117 
118  nexceptions++;
119  if ( nexceptions > kMaxEVGThreadExceptions ) {
120  LOG("EventGenerator", pFATAL)
121  << "Caught max allowed number (" << kMaxEVGThreadExceptions
122  << ") of EVGThreadExceptions/thread. Aborting";
123  LOG("EventGenerator", pFATAL) << "Event : \n" << *event_rec ;
124  exit(1);
125  }
126 
127  //
128  // What should I do with this exception?
129  // Check whether the user wants to get this unphysical event anyway
130  // If not, follow instructions coming with the expection thrown:
131  // Either step back to a particular processing step and try re-generating
132  // the event or pass it through
133  //
134 
135  // check whether user wants this type of unphysical events passed through
136  bool accept = event_rec->Accept();
137  if(accept) {
138  LOG("EventGenerator", pWARN)
139  << "An unphysical event was generated and was accepted by the user";
140  break;
141  } else {
142  LOG("EventGenerator", pWARN)
143  << "An unphysical event was generated and was rejected";
144  }
145 
146  // now, follow instructions contained in the exception itself
147 
148  // make sure we are not asked to go at both directions...
149  assert( !(exception.FastForward() && exception.StepBack()) );
150 
151  ffwd = exception.FastForward();
152  if(exception.StepBack()) {
153 
154  // get return step (if return_step > current_step just ignore it)
155  if(exception.ReturnStep() >= 0 && exception.ReturnStep() <= istep) {
156 
157  int rstep = exception.ReturnStep();
158  LOG("EventGenerator", pNOTICE)
159  << "Return at processing step " << rstep;
160  advance(miter, rstep-istep-1);
161  istep = rstep;
162 
163  // restore the event record as it was just before the processing
164  // step we are about to return to
165  LOG("EventGenerator", pNOTICE)
166  << "Restoring GHEP as it was just before the return step";
167  event_rec->ResetRecord();
168  istep--;
169  GHepRecord * snapshot = fRecHistory[istep];
171  event_rec->Copy(*snapshot);
172  } // valid-return-step
173  } // step-back
174  } // catch exception
175 
176  istep++;
177  }
178 
179  LOG("EventGenerator", pNOTICE)
180  << utils::print::PrintFramedMesg("Thread Summary",0,'*');
181  LOG("EventGenerator", pNOTICE)
182  << "The EventRecord was visited by all EventRecordVisitors";
183 
184  LOG("EventGenerator", pINFO) << "** Event generation timing info **";
185  istep=0;
186  for(miter = fEVGModuleVec->begin();
187  miter != fEVGModuleVec->end(); ++miter){
188  const EventRecordVisitorI * visitor = *miter;
189 
190  BLOG("EventGenerator", pINFO)
191  << "module " << visitor->Id().Key() << " -> ~"
192  << TMath::Max(0.,(*fEVGTime)[istep++]) << " s";
193  }
194  LOG("EventGenerator", pNOTICE) << "Done generating event!";
195 }
196 //___________________________________________________________________________
198 {
199  return fIntListGen;
200 }
201 //___________________________________________________________________________
203 {
204  return fXSecModel;
205 }
206 //___________________________________________________________________________
208 {
209  Algorithm::Configure(config);
210  this->LoadConfig();
211 }
212 //___________________________________________________________________________
213 void EventGenerator::Configure(string param_set)
214 {
215  Algorithm::Configure(param_set);
216 
217  AddLowRegistry( AlgConfigPool::Instance() -> GlobalParameterList(), false ) ;
218 
219  this->LoadConfig();
220 }
221 //___________________________________________________________________________
223 {
224  return *fVldContext;
225 }
226 //___________________________________________________________________________
228 {
229  fWatch = new TStopwatch;
230  fVldContext = 0;
231  fEVGModuleVec = 0;
232  fEVGTime = 0;
233  fXSecModel = 0;
234  fIntListGen = 0;
235 
236  fFiltUnphysMask = new TBits(GHepFlags::NFlags());
237  fFiltUnphysMask->ResetAllBits(false);
238 
239  if (gSystem->Getenv("GUNPHYSMASK")) {
240  unsigned int i=0;
241  const char * bitfield = gSystem->Getenv("GUNPHYSMASK");
242 
243  while(bitfield[i]) {
244  bool flag = (bitfield[i]=='1');
245 
246  if(i<GHepFlags::NFlags()) fFiltUnphysMask->SetBitNumber(i,flag);
247  i++;
248  }
249  }
250  LOG("EventGenerator", pDEBUG)
251  << "Initializing unphysical event mask (" << GHepFlags::NFlags()
252  << "->0) = " << *fFiltUnphysMask;
253 }
254 //___________________________________________________________________________
256 {
257  if(fEVGModuleVec) delete fEVGModuleVec;
258  if(fEVGTime) delete fEVGTime;
259  if(fVldContext) delete fVldContext;
260 
261  LOG("EventGenerator", pDEBUG) << "Loading the generator validity context";
262 
263  string encoded_vld_context ;
264  GetParam("VldContext", encoded_vld_context ) ;
265  fVldContext = new GVldContext;
266  fVldContext->Decode( encoded_vld_context );
267 
268  LOG("EventGenerator", pDEBUG) << "Loading the event generation modules";
269 
270  int nsteps ;
271  GetParam("NModules", nsteps) ;
272  if(nsteps == 0) {
273  LOG("EventGenerator", pFATAL)
274  << "EventGenerator configuration declares null visitor list!";
275  }
276  assert(nsteps>0);
277 
278  fEVGModuleVec = new vector<const EventRecordVisitorI *> (nsteps);
279  fEVGTime = new vector<double>(nsteps);
280 
281  for(int istep = 0; istep < nsteps; istep++) {
282 
283  ostringstream keystream;
284  keystream << "Module-" << istep;
285  RgKey key = keystream.str();
286 
287  RgAlg temp_alg ;
288  GetParam( key, temp_alg ) ;
289 
290  SLOG("EventGenerator", pINFO)
291  << " -- Loading module " << istep << " : " << temp_alg ;
292 
293  const EventRecordVisitorI * visitor =
294  dynamic_cast<const EventRecordVisitorI *>(this->SubAlg(key));
295 
296  (*fEVGModuleVec)[istep] = visitor;
297  (*fEVGTime)[istep] = 0;
298  }
299 
300  //-- load the interaction list generator
301  RgKey ikey = "ILstGen";
302  RgAlg ialg ;
303  GetParam( ikey, ialg ) ;
304  LOG("EventGenerator", pINFO)
305  << " -- Loading the interaction list generator: " << ialg;
306  fIntListGen =
307  dynamic_cast<const InteractionListGeneratorI *> (this->SubAlg(ikey));
308  assert(fIntListGen);
309 
310  //-- load the cross section model
311  RgKey xkey = "XSecModel@" + this->Id().Key();
312  RgAlg xalg ;
313  GetParam( xkey, xalg ) ;
314  LOG("EventGenerator", pINFO)
315  << " -- Loading the cross section model: " << xalg;
316  fXSecModel =
317  dynamic_cast<const XSecAlgorithmI *> (
318  this -> SubAlg( xkey ) ) ;
319  assert(fXSecModel);
320 }
321 //___________________________________________________________________________
322 
323 
Cross Section Calculation Interface.
virtual void Copy(const GHepRecord &record)
Definition: GHepRecord.cxx:899
GHepRecordHistory fRecHistory
event record history
THE MAIN GENIE PROJECT NAMESPACE
Definition: AlgCmp.h:25
virtual void ProcessEventRecord(GHepRecord *event_rec) const =0
TBits * fFiltUnphysMask
mask for allowing unphysical events to pass through (if requested)
const InteractionListGeneratorI * IntListGenerator(void) const
Defines the InteractionListGeneratorI interface. Concrete implementations of this interface generate ...
Defines the EventRecordVisitorI interface. Concrete implementations of this interface use the &#39;Visito...
#define pFATAL
Definition: Messenger.h:56
Defines the EventGeneratorI interface.
void ProcessEventRecord(GHepRecord *event_rec) const
vector< double > * fEVGTime
module timing info
intermediate_table::const_iterator const_iterator
#define BLOG(stream, priority)
A macro that returns the requested log4cpp::Category appending no additional information.
Definition: Messenger.h:212
TStopwatch * fWatch
stopwatch for module timing
void Configure(const Registry &config)
GENIE-defined C++ exceptions.
GVldContext * fVldContext
validity context
void PurgeRecentHistory(int start_step)
An exception thrown by EventRecordVisitorI when the normal processing sequence has to be disrupted (f...
static unsigned int NFlags(void)
Definition: GHepFlags.h:76
virtual bool Accept(void) const
Definition: GHepRecord.cxx:939
#define LOG(stream, priority)
A macro that returns the requested log4cpp::Category appending a string (using the FILE...
Definition: Messenger.h:96
def key(type, name=None)
Definition: graph.py:13
static Config * config
Definition: config.cpp:1054
virtual void Configure(const Registry &config)
Definition: Algorithm.cxx:62
void AddSnapshot(int step, GHepRecord *r)
#define pINFO
Definition: Messenger.h:62
virtual void ResetRecord(void)
Definition: GHepRecord.cxx:866
A singleton class to manage all named GHepVirtualLists.
static GHepVirtualListFolder * Instance(void)
Misc GENIE control constants.
#define pWARN
Definition: Messenger.h:60
virtual const AlgId & Id(void) const
Get algorithm ID.
Definition: Algorithm.h:97
string RgKey
A registry. Provides the container for algorithm configuration parameters.
Definition: Registry.h:65
vector< const EventRecordVisitorI * > * fEVGModuleVec
list of modules
string PrintFramedMesg(string mesg, unsigned int nl=1, const char f='*')
Definition: PrintUtils.cxx:164
static const unsigned int kMaxEVGThreadExceptions
Definition: Controls.h:33
int AddLowRegistry(Registry *rp, bool owns=true)
add registry with lowest priority, also update ownership
Definition: Algorithm.cxx:641
const GVldContext & ValidityContext(void) const
#define pNOTICE
Definition: Messenger.h:61
bool GetParam(const RgKey &name, T &p, bool is_top_call=true) const
const XSecAlgorithmI * CrossSectionAlg(void) const
#define SLOG(stream, priority)
A macro that returns the requested log4cpp::Category appending a short string (using the FUNCTION and...
Definition: Messenger.h:84
GENIE&#39;s GHEP MC event record.
Definition: GHepRecord.h:45
string Key(void) const
Definition: AlgId.h:46
const InteractionListGeneratorI * fIntListGen
generates list of handled interactions
Root of GENIE utility namespaces.
cet::coded_exception< error, detail::translate > exception
Definition: exception.h:33
Validity Context for an Event Generator.
Definition: GVldContext.h:37
static AlgConfigPool * Instance()
#define pDEBUG
Definition: Messenger.h:63
void Decode(string encoded_values)
Definition: GVldContext.cxx:42
const XSecAlgorithmI * fXSecModel
xsec model for events handled by thread
const Algorithm * SubAlg(const RgKey &registry_key) const
Definition: Algorithm.cxx:345