ATLAS Offline Software
Loading...
Searching...
No Matches
Epos.cxx
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2025 CERN for the benefit of the ATLAS collaboration
3*/
4
5// ----------------------------------------------------------------------
6// Generators/Epos.cxx
7//
8// Description: Allows the user to generate epos events and store the result
9// in the Transient Store.
10//
11// AuthorList:
12// Sami Kama: Initial code.
13// Sebastian Piec: Adaptation for Epos 1.99.crmc.r2790.
14// Andrii Verbytskyi: 2.0.1+
15// ----------------------------------------------------------------------
16
17#include "GaudiKernel/MsgStream.h"
18#include "CLHEP/Random/RandFlat.h"
20
21#include "AtlasHepMC/GenEvent.h"
22#include "AtlasHepMC/HeavyIon.h"
25
26#include "Epos_i/Epos.h"
27#include "CRMChepevt.h"
28#define CRMC_STATIC
29#include "CRMCinterface.h"
30
31
32namespace {
33static std::string epos_rndm_stream = "EPOS_INIT";
34static CLHEP::HepRandomEngine* p_rndmEngine{};
35}
36
37extern "C" double atl_epos_rndm_( int* )
38{
39 return CLHEP::RandFlat::shoot(p_rndmEngine);
40}
41
42// ----------------------------------------------------------------------
43// Translations of DRanf.F, Ranfini.F, Rangen.F Fortran routines.
44// These replace the original Fortran source files.
45// ----------------------------------------------------------------------
46
47// dranf: returns a uniform double in (0,1), retrying on boundary values.
48extern "C" double dranf_( int* dummy )
49{
50 double r;
51 do {
52 r = atl_epos_rndm_( dummy );
53 } while ( r <= 0.0 || r >= 1.0 );
54 return r;
55}
56
57// ranfgt / ranfst: seed query/set stubs (no-op in this implementation).
58extern "C" void ranfgt_( double* /*seed*/ ) {}
59extern "C" void ranfst_( double* /*seed*/ ) {}
60
61// ranfini: random-number initialisation stub (no-op in this implementation).
62extern "C" void ranfini_( int* /*iseed*/, int* /*iseq*/, int* /*iqq*/ ) {}
63
64// rangen: single-precision wrapper around dranf_, retrying on boundary values.
65extern "C" float rangen_()
66{
67 int dummy = 0;
68 float r;
69 do {
70 r = static_cast<float>( dranf_( &dummy ) );
71 } while ( r <= 0.0f || r >= 1.0f );
72 return r;
73}
74
75// drangen: double-precision wrapper around dranf_.
76extern "C" double drangen_( double* dummy )
77{
78 int idummy = static_cast<int>( *dummy );
79 return dranf_( &idummy );
80}
81
82// ----------------------------------------------------------------------
83// Epos Fortran bindings.
84// ----------------------------------------------------------------------
85extern "C"
86{
87 // generator initialization
88 void crmc_init_f_( double &m_degymx, int &iSeed, int &model, int &itab, int &itypout, const char *paramFile, const char *output, int &lout);
89
90 void crmc_set_f_( int &nEvents,double &beamMomentum, double &targetMomentum, int &primaryParticle, int &targetParticle);
91
92 // event generation
93 void crmc_f_( int &iout, int &ievent, int &nParticles, double &impactParam, int &partPdg,
94 double &partPx, double &partPy, double &partPz, double &partEnergy, double &partMass, int &outstat );
95
96 // cross section info
97 void crmc_xsection_f_(double &xsigtot, double &xsigine, double &xsigela, double &xsigdd,
98 double &xsigsd, double &xsloela, double &xsigtotaa, double &xsigineaa, double &xsigelaaa);
99
100}
101// ----------------------------------------------------------------------
102Epos::Epos( const std::string &name, ISvcLocator *pSvcLocator ):
103 GenModule( name, pSvcLocator )
104{
105 m_interface = nullptr;
106 epos_rndm_stream = "EPOS_INIT";
107
108 declareProperty( "BeamMomentum", m_beamMomentum = -6500.0 ); // GeV
109 declareProperty( "TargetMomentum", m_targetMomentum = 6500.0 );
110 declareProperty( "Model", m_model = 7 ); // 0=EPOS 1.99 LHC, 1=EPOS 1.99
111 declareProperty( "PrimaryParticle", m_primaryParticle = 1 ); // 1=p, 12=C, 120=pi+, 207=Pb
112 declareProperty( "TargetParticle", m_targetParticle = 1 );
113 declareProperty( "ParamFile", m_paramFile = "crmc.param" );
114 declareProperty( "LheOutput", m_ilheout = 0 );
115 declareProperty( "LheFile", m_lheout = "epos.lhe" );
116 declareProperty( "TabCreate", m_itab = 0 );
117 declareProperty( "nEvents", m_nEvents = 5500 );
118 declareProperty( "maxCMEnergy", m_degymx = 13000.0 ); // maximum center-of-mass energy which will be call in the run [GeV]
119
120 m_events = 0; // current event number (counted by interface)
121 m_ievent = 0; // current event number counted by Epos
122 m_iout = 0; // output type (output)
123
124 // initialize internally used arrays
125 ATH_MSG_INFO( "max number of Particles " << kMaxParticles );
126 m_partID.resize (kMaxParticles);
127 m_partPx.resize (kMaxParticles);
128 m_partPy.resize (kMaxParticles);
129 m_partPz.resize (kMaxParticles);
131 m_partMass.resize (kMaxParticles);
132 m_partStat.resize (kMaxParticles);
133 for (size_t i = 0; i < kMaxParticles; ++i) {
134 m_partID[i] = 0;
135 m_partPx[i] = m_partPy[i] = m_partPz[i] = m_partEnergy[i] = m_partMass[i] = 0.0;
136 m_partStat[i] = 0;
137 }
138
139}
140
141// ----------------------------------------------------------------------
143{
144 ATH_MSG_INFO( " CRMC INITIALISING.\n" );
145 ATH_MSG_INFO( "signal_rocess_id 101-ND, 105-DD, 102-CD, 103 AB->XB, 104 AB->AX \n");
146
147 p_rndmEngine = getRandomEngineDuringInitialize(epos_rndm_stream, m_randomSeed, m_dsid); // NOT THREAD-SAFE
148 const long *sip = p_rndmEngine->getSeeds();
149 long int si1 = sip[0];
150
151 int iSeed = si1%1000000000; // FIXME ?
152 int lout = 50; //lenght of the output string (useful only for LHE output)
153 // initialise Epos and set up initial values
154
155 crmc_init_f_( m_degymx, iSeed, m_model, m_itab, m_ilheout, (m_paramFile + " ").c_str(), m_lheout.c_str(), lout);
157
158 epos_rndm_stream = "EPOS";
159
160 m_events = 0;
161
162 return StatusCode::SUCCESS;
163}
164
165// ----------------------------------------------------------------------
167{
168 // ATH_MSG_INFO( " EPOS Generating." );
169
170 //Re-seed the random number stream
171 long seeds[7];
172 const EventContext& ctx = Gaudi::Hive::currentContext();
173 ATHRNG::calculateSeedsMC21(seeds, epos_rndm_stream, ctx.eventID().event_number(), m_dsid, m_randomSeed);
174 p_rndmEngine->setSeeds(seeds, 0); // NOT THREAD-SAFE
175
176 // save the random number seeds in the event
177 const long *s = p_rndmEngine->getSeeds();
178 m_seeds.clear();
179 m_seeds.push_back(s[0]);
180 m_seeds.push_back(s[1]);
181
182 ++m_events;
183
184 // as in crmchep.h
185 int nParticles = 0;
186 double impactParameter = -1.0;
187
188 // generate event
189 crmc_f_( m_iout, m_ievent,nParticles, impactParameter, m_partID[0], m_partPx[0], m_partPy[0], m_partPz[0],
191
192 return StatusCode::SUCCESS;
193}
194
195// ----------------------------------------------------------------------
197{
198 ATH_MSG_INFO("EPOS finalizing.");
199
200 std::cout << "MetaData: generator = Epos " << std::endl;
201
202 // retrieve information about the total cross-section from Epos
203 double xsigtot, xsigine, xsigela, xsigdd, xsigsd, xsloela, xsigtotaa, xsigineaa, xsigelaaa;
204 xsigtot = xsigine = xsigela = xsigdd = xsigsd = xsloela = xsigtotaa = xsigineaa = xsigelaaa = 0.0;
205
206 crmc_xsection_f_(xsigtot, xsigine, xsigela, xsigdd, xsigsd, xsloela, xsigtotaa, xsigineaa, xsigelaaa);
207
208 xsigtot *= 1000000; // [mb] to [nb] conversion
209 std::cout << "MetaData: cross-section (nb) = " << xsigtot << std::endl;
210 xsigine *= 1000000; //[mb] to [nb] conversion
211 std::cout << "MetaData: cross-section inelastic (cut + projectile diffraction)[nb] = " << xsigine << std::endl;
212 xsigela *= 1000000; // [mb] to [nb] conversion
213 std::cout << "MetaData: cross-section elastic (includes target diffraction)[nb] = " << xsigela << std::endl;
214 xsigdd *= 1000000; // [mb] to [nb] conversion
215 std::cout << "MetaData: cross-section dd (nb) = " << xsigdd << std::endl;
216 xsigsd *= 1000000; // [mb] to [nb] conversion
217 std::cout << "MetaData: cross-section sd (nb) = " << xsigsd << std::endl;
218
219 // m_eposEventInfo.close();
220
221 return StatusCode::SUCCESS;
222}
223
224// ----------------------------------------------------------------------
226{
227 CRMChepevt<HepMC::GenParticlePtr, HepMC::GenVertexPtr, HepMC::FourVector, HepMC::GenEvent> hepevtconverter;
228 hepevtconverter.convert(*evt);
229 evt->set_event_number(m_events);
232 evt->weights().push_back(1.0);
233 m_runinfo = std::make_shared<HepMC3::GenRunInfo>();
234 std::vector<std::string> names = {"Default"};
235 m_runinfo->set_weight_names(names);
236 evt->set_run_info(m_runinfo);
237 evt->set_units(HepMC3::Units::MEV, HepMC3::Units::MM);
238
239 std::vector<HepMC::GenParticlePtr> beams;
240
241 for (auto p: *evt) {
242 if (p->status() == 4) {
243 beams.push_back(std::move(p));
244 }
245 }
246
247 if (beams.size() >= 2) {
248 evt->set_beam_particles(beams[0], beams[1]);
249 } else {
250 ATH_MSG_INFO( "EPOS event has only " << beams.size() << " beam particles" );
251 }
252
253 // Heavy Ion and Signal ID from Epos to HepMC
254
255 HepMC::GenHeavyIonPtr ion= std::make_shared<HepMC::GenHeavyIon>();
256 ion->Ncoll_hard=cevt_.kohevt;
257 ion->Npart_proj=cevt_.npjevt;
258 ion->Npart_targ=cevt_.ntgevt;
259 ion->Ncoll=cevt_.kolevt;
260 ion->spectator_neutrons=cevt_.npnevt + cevt_.ntnevt;
261 ion->spectator_protons=cevt_.nppevt + cevt_.ntpevt;
262 ion->N_Nwounded_collisions=-1;
263 ion->Nwounded_N_collisions=-1;
264 ion->Nwounded_Nwounded_collisions=-1;
265 ion->impact_parameter= cevt_.bimevt;
266 ion->event_plane_angle=cevt_.phievt;
267 ion->eccentricity=-1; //c2evt_.fglevt, //correct name but not defined
268 ion->sigma_inel_NN=1e9*hadr5_.sigine;
269
270 evt->set_heavy_ion(std::move(ion));
271
272 //an integer ID uniquely specifying the signal process (i.e. MSUB in Pythia)
273 // Epos 1-ND, 2-DD, 3-CD, 4 AB->XB, -4 AB->AX translated into signal_proces_id 101-ND, 105 - DD, 102 - CD, 103 -AB->XB, 104 AB->AX
274 int sig_id = -1;
275 switch (int(c2evt_.typevt))
276 {
277 case 1: sig_id = 101; break;
278 case -1: sig_id = 101; break;
279 case 2: sig_id = 105; break;
280 case -2: sig_id = 105; break;
281 case 3: sig_id = 102; break;
282 case -3: sig_id = 102; break;
283 case 4: sig_id = 103; break;
284 case -4: sig_id = 104; break;
285 default: ATH_MSG_INFO( "Signal ID not recognised for setting HEPEVT \n");
286 }
287
289
290 double xsigtot, xsigine, xsigela, xsigdd, xsigsd, xsloela, xsigtotaa, xsigineaa, xsigelaaa;
291 xsigtot = xsigine = xsigela = xsigdd = xsigsd = xsloela = xsigtotaa = xsigineaa = xsigelaaa = 0.0;
292 crmc_xsection_f_(xsigtot, xsigine, xsigela, xsigdd, xsigsd, xsloela, xsigtotaa, xsigineaa, xsigelaaa);
293 xsigtot *= 1000000; // [mb] to [nb] conversion
294 std::shared_ptr<HepMC3::GenCrossSection> xsec = std::make_shared<HepMC3::GenCrossSection>();
295 xsec->set_cross_section(xsigine, 0.0);
296 evt->set_cross_section(std::move(xsec));
297
298 return StatusCode::SUCCESS;
299}
300
#define ATH_MSG_INFO(x)
void crmc_f_(int &iout, int &ievent, int &nParticles, double &impactParam, int &partPdg, double &partPx, double &partPy, double &partPz, double &partEnergy, double &partMass, int &outstat)
double atl_epos_rndm_(int *)
Definition Epos.cxx:37
double drangen_(double *dummy)
Definition Epos.cxx:76
void crmc_set_f_(int &nEvents, double &beamMomentum, double &targetMomentum, int &primaryParticle, int &targetParticle)
void crmc_init_f_(double &m_degymx, int &iSeed, int &model, int &itab, int &itypout, const char *paramFile, const char *output, int &lout)
float rangen_()
Definition Epos.cxx:65
void crmc_xsection_f_(double &xsigtot, double &xsigine, double &xsigela, double &xsigdd, double &xsigsd, double &xsloela, double &xsigtotaa, double &xsigineaa, double &xsigelaaa)
void ranfgt_(double *)
Definition Epos.cxx:58
double dranf_(int *dummy)
Definition Epos.cxx:48
void ranfini_(int *, int *, int *)
Definition Epos.cxx:62
void ranfst_(double *)
Definition Epos.cxx:59
ATLAS-specific HepMC functions.
Gaudi::Details::PropertyBase & declareProperty(Gaudi::Property< T, V, H > &t)
int m_primaryParticle
Definition Epos.h:50
std::vector< double > m_partPy
Definition Epos.h:68
int m_nEvents
Definition Epos.h:56
std::string m_paramFile
Definition Epos.h:52
int m_itab
Definition Epos.h:54
int m_ilheout
Definition Epos.h:55
IntegerProperty m_dsid
Definition Epos.h:60
std::vector< int > m_partStat
Definition Epos.h:72
std::string m_lheout
Definition Epos.h:53
static const size_t kMaxParticles
Definition Epos.h:65
std::vector< double > m_partPx
Definition Epos.h:67
std::vector< double > m_partPz
Definition Epos.h:69
virtual StatusCode genInitialize()
For initializing the generator, if required.
Definition Epos.cxx:142
int m_model
Definition Epos.h:49
Epos(const std::string &name, ISvcLocator *pSvcLocator)
Definition Epos.cxx:102
int m_events
Definition Epos.h:42
double m_targetMomentum
Definition Epos.h:48
std::vector< long int > m_seeds
Definition Epos.h:74
double m_beamMomentum
Definition Epos.h:47
int m_ievent
Definition Epos.h:43
int m_targetParticle
Definition Epos.h:51
std::vector< int > m_partID
Definition Epos.h:66
virtual StatusCode genFinalize()
For finalising the generator, if required.
Definition Epos.cxx:196
CRMCinterface * m_interface
Definition Epos.h:40
virtual StatusCode fillEvt(HepMC::GenEvent *evt)
For filling the HepMC event object.
Definition Epos.cxx:225
virtual StatusCode callGenerator()
For calling the generator on each iteration of the event loop.
Definition Epos.cxx:166
std::vector< double > m_partEnergy
Definition Epos.h:70
double m_degymx
Definition Epos.h:57
std::vector< double > m_partMass
Definition Epos.h:71
int m_iout
Definition Epos.h:44
GenModule(const std::string &name, ISvcLocator *pSvcLocator)
Constructor.
Definition GenModule.cxx:14
CLHEP::HepRandomEngine * getRandomEngineDuringInitialize(const std::string &streamName, unsigned long int randomSeedOffset, unsigned int conditionsRun=1, unsigned int lbn=1) const
Definition GenModule.cxx:53
IntegerProperty m_randomSeed
Seed for random number engine.
Definition GenModule.h:84
std::shared_ptr< HepMC3::GenRunInfo > m_runinfo
The run info for HepMC3.
Definition GenModule.h:90
const int nEvents
int r
Definition globals.cxx:22
void calculateSeedsMC21(long *seeds, const std::string &algName, uint64_t ev, uint64_t run, uint64_t offset=0)
Set the random seed using a string (e.g.
HepMC3::GenHeavyIonPtr GenHeavyIonPtr
Definition HeavyIon.h:11
void set_signal_process_id(GenEvent *e, const int i=0)
Definition GenEvent.h:580
void set_random_states(GenEvent *e, std::vector< long int > &a)
Definition GenEvent.h:588
void fillBarcodesAttribute(GenEvent *e)
Definition GenEvent.h:393
HepMC3::GenEvent GenEvent
Definition GenEvent.h:39