PYTHIA  8.316
HeavyIons.h
1 // HeavyIons.h is a part of the PYTHIA event generator.
2 // Copyright (C) 2025 Torbjorn Sjostrand.
3 // PYTHIA is licenced under the GNU GPL v2 or later, see COPYING for details.
4 // Please respect the MCnet Guidelines, see GUIDELINES for details.
5 
6 // This file contains the definition of the HeavyIons class which
7 // Provides Pythia with infrastructure to combine several nucleon
8 // collisions into a single heavy ion collision event. This file also
9 // includes the definition of the Angantyr class which implements the
10 // default model for heavy ion collisions in Pythia.
11 
12 #ifndef Pythia8_HeavyIons_H
13 #define Pythia8_HeavyIons_H
14 
15 #include "Pythia8/HIInfo.h"
16 #include "Pythia8/PhysicsBase.h"
17 
18 namespace Pythia8 {
19 
20 // Forward declaration of the Pythia class.
21 class Pythia;
22 
23 //==========================================================================
24 
25 // HeavyIons contains several standard Pythia objects to allow for
26 // the combination of different kinds of nucleon-nucleon events into
27 // a heavy ion collision event. The actual model for doing this must
28 // be implemented in a subclass overriding the the virtual'init()'
29 // and 'next()' functions.
30 
31 class HeavyIons : public PhysicsBase {
32 
33 public:
34 
35  // The constructor needs a reference to the main Pythia object to
36  // which it will belong. A HeavyIons object cannot belong to more
37  // than one main Pythia object.
38  HeavyIons(Pythia& mainPythiaIn)
39  : mainPythiaPtr(&mainPythiaIn), HIHooksPtr(0),
40  pythia(vector<Pythia*>(1, &mainPythiaIn)) {
41  }
42 
43  // Destructor.
44  virtual ~HeavyIons() {}
45 
46  // Virtual function to be implemented in a subclass. This will be
47  // called in the beginning of the Pythia::init function if the mode
48  // HeavyIon:mode is set non zero. The return value should be true
49  // if this object is able to handle the requested collision
50  // type. If false Pythia::init will set HeavyIon:mode to zero but
51  // will try to cope anyway.
52  virtual bool init() = 0;
53 
54  // Virtual function to be implemented in a subclass. This will be
55  // called in the beginning of the Pythia::next function if
56  // HeavyIon:mode is set non zero. After the call, Pythia::next will
57  // return immediately with the return value of this function.
58  virtual bool next() = 0;
59 
60  // Static function to allow Pythia to duplicate some setting names
61  // to be used for secondary Pythia objects.
62  static void addSpecialSettings(Settings& settings);
63 
64  // Return true if the beams in the Primary Pythia object contains
65  // heavy ions.
66  static bool isHeavyIon(Settings& settings);
67 
68  // Possibility to pass in pointer for special heavy ion user hooks.
69  bool setHIUserHooksPtr(HIUserHooksPtr userHooksPtrIn) {
70  HIHooksPtr = userHooksPtrIn; return true;
71  }
72 
73  // Set beam kinematics.
74  virtual bool setKinematics(double /*eCMIn*/) {
75  loggerPtr->ERROR_MSG("method not implemented for this heavy ion model");
76  return false; }
77  virtual bool setKinematics(double /*eAIn*/, double /*eBIn*/) {
78  loggerPtr->ERROR_MSG("method not implemented for this heavy ion model");
79  return false; }
80  virtual bool setKinematics(double, double, double, double, double, double) {
81  loggerPtr->ERROR_MSG("method not implemented for this heavy ion model");
82  return false; }
83  virtual bool setKinematics(Vec4, Vec4) {
84  loggerPtr->ERROR_MSG("method not implemented for this heavy ion model");
85  return false; }
86 
87  // Set beam particles.
88  virtual bool setBeamIDs(int /*idAIn*/, int /*idBIn*/ = 0) {
89  loggerPtr->ERROR_MSG("method not implemented for this heavy ion model");
90  return false; }
91 
92  // The HIInfo object contains information about the last generated heavy
93  // ion event as well as overall statistics of the generated events.
95 
96  // Print out statistics.
97  virtual void stat();
98 
99 protected:
100 
101  // Update the cross section in the main Pythia Info object using
102  // information in the hiInfo object.
103  void updateInfo();
104 
105  // If subclasses has additional Pythia objects for generating
106  // minimum bias nucleon collisions and the main Pythia object is
107  // set up to generated a hard signal process, this function can be
108  // used to clear all selected processes in a clone of the main
109  // Pythia object.
110  void clearProcessLevel(Pythia& pyt);
111 
112  // Duplicate setting on the form match: to settings on the form HImatch:
113  static void setupSpecials(Settings& settings, string match);
114 
115  // Copy settings on the form HImatch: to the corresponding match:
116  // in the given Pythia object.
117  static void setupSpecials(Pythia& p, string match);
118 
119  // Save current beam configuration.
120  int idProj, idTarg;
121 
122  // This is the pointer to the main Pythia object to which this
123  // object is assigned.
125 
126  // Object containing information on inclusive pp cross sections to
127  // be used in Glauber calculations in subclasses.
129 
130  // Optional HIUserHooks object able to modify the behavior of the
131  // HeavyIon model.
132  HIUserHooksPtr HIHooksPtr;
133 
134  // The internal Pythia objects. Index zero will always correspond
135  // to the mainPythiaPtr.
136  vector<Pythia *> pythia;
137 
138  // The names associated with the secondary pythia objects.
139  vector<string> pythiaNames;
140 
141  // The Info objects associated to the secondary Pythia objects.
142  vector<Info*> info;
143 
144  // Helper class to gain access to the Info object in a Pythia
145  // instance.
146  struct InfoGrabber : public UserHooks {
147 
148  // Only one function: return the info object.
150  return infoPtr;
151  }
152 
153  };
154 
155 };
156 
157 //==========================================================================
158 
159 // The default HeavyIon model in Pythia.
160 
161 class Angantyr : public HeavyIons {
162 
163 public:
164 
165  // Enumerate the different internal Pythia objects.
167  HADRON = 0, // For hadronization only.
168  MBIAS = 1, // Minimum Bias processed.
169  SASD = 2, // Single diffractive as one side of non-diffractive.
170  SIGPP = 3, // Optional object for signal processes (pp).
171  SIGPN = 4, // Optional object for signal processes (pn).
172  SIGNP = 5, // Optional object for signal processes (np).
173  SIGNN = 6, // Optional object for signal processes (nn).
174  ALL = 7 // Indicates all objects.
175  };
176 
177 public:
178 
179  // The constructor needs a reference to the main Pythia object to
180  // which it will belong. A Angantyr object cannot belong to more
181  // than one main Pythia object.
182  Angantyr(Pythia& mainPythiaIn);
183 
184  virtual ~Angantyr();
185 
186  // Initialize Angantyr.
187  virtual bool init() override;
188 
189  // Produce a collision involving heavy ions.
190  virtual bool next() override;
191 
192  // Set UserHooks for specific (or ALL) internal Pythia objects.
193  bool setUserHooksPtr(PythiaObject sel, UserHooksPtr userHooksPtrIn);
194 
195  // Set beam kinematics.
196  bool setKinematicsCM();
197  bool setKinematics(double eCMIn) override;
198  bool setKinematics(double eAIn, double eBIn) override;
199  bool setKinematics(double, double, double, double, double, double) override;
200  bool setKinematics(Vec4, Vec4) override;
201  bool setKinematics();
202 
203  // Set beam IDs.
204  bool setBeamIDs(int idAIn, int idBIn = 0) override;
205 
206  // Make sure the correct information is available irrespective of frame type.
207  void unifyFrames();
208 
209  // Print the Angantyr banner.
210  void banner() const;
211 
212  // Subcollisions for the current event.
214  return subColls; }
215 
216  // Get the underlying subcollision model.
218  return *collPtr.get(); }
219 
220  SubCollisionModel* subCollPtr() {
221  return collPtr.get();
222  }
223 
224  // Get the underlying impact parameter generator.
226  return *bGenPtr.get(); }
227 
228  // Projectile nucleus configuration for the current event.
229  const Nucleus& projectile() const {
230  return proj; }
231 
232  // Target nucleus configuration for the current event.
233  const Nucleus& target() const {
234  return targ; }
235 
236  // The underlying projectile nucleus model.
237  const NucleusModel& projectileModel() const {
238  return *projPtr.get(); }
239 
240  // The underlying target nucleus model.
241  const NucleusModel& targetModel() const {
242  return *targPtr.get(); }
243 
244  // Hadronic cross sections used by the subcollision model.
245  const SigmaTotal sigmaNN() const {
246  return sigTotNN; }
247 
248 protected:
249 
250  virtual void onInitInfoPtr() override {
252 
253  // Figure out what beams the user want.
254  void setBeamKinematics(int idA, int idB);
255 
256  // Initiaize a specific Pythia object and optionally run a number
257  // of events to get a handle of the cross section.
258  bool init(PythiaObject sel, string name, int n = 0);
259 
260  // Setup an EventInfo object from a Pythia instance.
261  EventInfo mkEventInfo(Pythia &, Info &, const SubCollision * coll = 0);
262 
263  // Generate events from the internal Pythia oblects;
264  EventInfo getSignal(const SubCollision& coll);
265  EventInfo getND() { return getMBIAS(0, 101); }
266  EventInfo getND(const SubCollision& coll) { return getMBIAS(&coll, 101); }
267  EventInfo getEl(const SubCollision& coll) { return getMBIAS(&coll, 102); }
268  EventInfo getSDP(const SubCollision& coll) { return getMBIAS(&coll, 103); }
269  EventInfo getSDT(const SubCollision& coll) { return getMBIAS(&coll, 104); }
270  EventInfo getDD(const SubCollision& coll) { return getMBIAS(&coll, 105); }
271  EventInfo getCD(const SubCollision& coll) { return getMBIAS(&coll, 106); }
272  EventInfo getSDabsP(const SubCollision& coll)
273  { return getSASD(&coll, 103); }
274  EventInfo getSDabsT(const SubCollision& coll)
275  { return getSASD(&coll, 104); }
276  EventInfo getMBIAS(const SubCollision * coll, int procid);
277  EventInfo getSASD(const SubCollision * coll, int procid);
278 
279  bool genAbs(SubCollisionSet& subCollsIn, list<EventInfo>& subEventsIn);
280  void addSASD(const SubCollisionSet& subCollsIn);
281  bool addDD(const SubCollisionSet& subCollsIn, list<EventInfo>& subEventsIn);
282  bool addSD(const SubCollisionSet& subCollsIn, list<EventInfo>& subEventsIn);
283  void addSDsecond(const SubCollisionSet& subCollsIn);
284  bool addCD(const SubCollisionSet& subCollsIn, list<EventInfo>& subEventsIn);
285  void addCDsecond(const SubCollisionSet& subCollsIn);
286  bool addEL(const SubCollisionSet& subCollsIn, list<EventInfo>& subEventsIn);
287  void addELsecond(const SubCollisionSet& subCollsIn);
288 
289  void resetEvent();
290  bool buildEvent(list<EventInfo>& subEventsIn);
291 
292  bool setupFullCollision(EventInfo& ei, const SubCollision& coll,
293  Nucleon::Status projStatus, Nucleon::Status targStatus);
294  bool isRemnant(const EventInfo& ei, int i, int past = 1 ) const {
295  int statNow = ei.event[i].status()*past;
296  if ( statNow == 63 ) return true;
297  if ( statNow > 70 && statNow < 80 )
298  return isRemnant(ei, ei.event[i].mother1(), -1);
299  return false;
300  }
301  bool fixIsoSpin(EventInfo& ei);
302  EventInfo& shiftEvent(EventInfo& ei);
303  static int getBeam(Event& ev, int i);
304 
305  // Generate a single diffractive
306  bool nextSASD(int proc);
307 
308  // Add a diffractive event to an exsisting one. Optionally connect
309  // the colours of the added event to the original.
310  bool addNucleonExcitation(EventInfo& orig, EventInfo& add,
311  bool colConnect = false);
312 
313  // Find the recoilers in the current event to conserve energy and
314  // momentum in addNucleonExcitation.
315  vector<int> findRecoilers(const Event& e, bool tside, int beam, int end,
316  const Vec4& pdiff, const Vec4& pbeam);
317 
318  // Add a sub-event to the final event record.
319  void addSubEvent(Event& evnt, Event& sub);
320  static void addJunctions(Event& evnt, Event& sub, int coloff);
321 
322  // Add a nucleus remnant to the given event. Possibly introducing
323  // a new particle type.
324  bool addNucleusRemnants();
325 
326 public:
327 
328  // Helper function to construct two transformations that would give
329  // the vectors p1 and p2 the total four momentum of p1p + p2p.
330  static bool
331  getTransforms(Vec4 p1, Vec4 p2, const Vec4& p1p,
332  pair<RotBstMatrix,RotBstMatrix>& R12);
333  static double mT2(const Vec4& p) { return p.pPos()*p.pNeg(); }
334  static double mT(const Vec4& p) { return sqrt(max(mT2(p), 0.0)); }
335 
336 private:
337 
338  // Private UserHooks class to select a specific process.
339  struct ProcessSelectorHook: public UserHooks {
340 
341  ProcessSelectorHook(): proc(0), b(-1.0) {}
342 
343  // Yes we can veto event after process-level selection.
344  virtual bool canVetoProcessLevel() {
345  return true;
346  }
347 
348  // Veto any unwanted process.
349  virtual bool doVetoProcessLevel(Event&) {
350  return proc > 0 && infoPtr->code() != proc;
351  }
352 
353  // Can set the overall impact parameter for the MPI treatment.
354  virtual bool canSetImpactParameter() const {
355  return b >= 0.0;
356  }
357 
358  // Set the overall impact parameter for the MPI treatment.
359  virtual double doSetImpactParameter() {
360  return b;
361  }
362 
363  // The wanted process;
364  int proc;
365 
366  // The selected b-value.
367  double b;
368 
369  };
370 
371  // Holder class to temporarily select a specific process
372  struct HoldProcess {
373 
374  // Set the given process for the given hook object.
375  HoldProcess(shared_ptr<ProcessSelectorHook> hook, int proc,
376  double b = -1.0) : saveHook(hook), saveProc(hook->proc), saveB(hook->b) {
377  hook->proc = proc;
378  hook->b = b;
379  }
380 
381  // Reset the process of the hook object given in the constructor.
382  ~HoldProcess() {
383  if ( saveHook ) {
384  saveHook->proc = saveProc;
385  saveHook->b = saveB;
386  }
387  }
388 
389  // The hook object.
390  shared_ptr<ProcessSelectorHook> saveHook;
391 
392  // The previous process of the hook object.
393  int saveProc;
394 
395  // The previous b-value of the hook object.
396  double saveB;
397 
398  };
399 
400  // The process selector for standard minimum bias processes.
401  shared_ptr<ProcessSelectorHook> selectMB;
402 
403  // The process selector for the SASD object.
404  shared_ptr<ProcessSelectorHook> selectSASD;
405 
406 private:
407 
408  static const int MAXTRY = 999;
409  static const int MAXEVSAVE = 999;
410 
411  // Flag set if there is a specific signal process specified beyond
412  // minimum bias.
413  bool hasSignal;
414 
415  // Whether to do hadronization and hadron level effects.
416  bool doHadronLevel;
417 
418  // Flag to determine whether to do single diffractive test.
419  bool doSDTest;
420 
421  // Flag to determine whether to do only Glauber modelling.
422  bool glauberOnly;
423 
424  // All subcollisions in current collision.
425  SubCollisionSet subColls;
426 
427  // The underlying SubCollisionModel for generating nucleon-nucleon
428  // subcollisions.
429  shared_ptr<SubCollisionModel> collPtr;
430 
431  // The impact parameter generator.
432  shared_ptr<ImpactParameterGenerator> bGenPtr;
433 
434  // The projectile and target nuclei in the current collision.
435  Nucleus proj;
436  Nucleus targ;
437 
438  // The underlying nucleus model for generating nuclons inside the
439  // projectile and target nucleus.
440  shared_ptr<NucleusModel> projPtr;
441  shared_ptr<NucleusModel> targPtr;
442 
443  // Flag to indicate whether variable energy is enabled.
444  bool doVarECM;
445 
446  // Different choices in choosing recoilers when adding
447  // diffractively excited nucleon.
448  int recoilerMode;
449 
450  // Different choices for handling impact parameters.
451  int bMode;
452 
453  // Critical internal error, abort the event.
454  bool doAbort;
455 
456 };
457 
458 //==========================================================================
459 
460 } // end namespace Pythia8
461 
462 #endif // Pythia8_HeavyIons_H
virtual bool init()=0
const SubCollisionModel & subCollisionModel() const
Get the underlying subcollision model.
Definition: HeavyIons.h:217
const NucleusModel & targetModel() const
The underlying target nucleus model.
Definition: HeavyIons.h:241
const SubCollisionSet & subCollisions() const
Subcollisions for the current event.
Definition: HeavyIons.h:213
Definition: PhysicsBase.h:26
void registerSubObject(PhysicsBase &pb)
Register a sub object that should have its information in sync with this.
Definition: PhysicsBase.cc:57
HeavyIons(Pythia &mainPythiaIn)
Definition: HeavyIons.h:38
Definition: Info.h:45
The Event class holds all info on the generated event.
Definition: Event.h:408
Definition: HINucleusModel.h:152
vector< Info * > info
The Info objects associated to the secondary Pythia objects.
Definition: HeavyIons.h:142
static bool isHeavyIon(Settings &settings)
Check the settings and return false of there are no heavy ion beams.
Definition: HeavyIons.cc:299
Definition: SigmaTotal.h:141
const NucleusModel & projectileModel() const
The underlying projectile nucleus model.
Definition: HeavyIons.h:237
static void setupSpecials(Settings &settings, string match)
Duplicate setting on the form match: to settings on the form HImatch:
Definition: HeavyIons.cc:33
Definition: HINucleusModel.h:187
const ImpactParameterGenerator impactParameterGenerator() const
Get the underlying impact parameter generator.
Definition: HeavyIons.h:225
Definition: HISubCollisionModel.h:511
const Nucleus & target() const
Target nucleus configuration for the current event.
Definition: HeavyIons.h:233
void clearProcessLevel(Pythia &pyt)
Definition: HeavyIons.cc:117
The SubCollisionSet gives a set of subcollisions between two nuclei.
Definition: HISubCollisionModel.h:88
int idProj
Save current beam configuration.
Definition: HeavyIons.h:120
HIUserHooksPtr HIHooksPtr
Definition: HeavyIons.h:132
virtual ~HeavyIons()
Destructor.
Definition: HeavyIons.h:44
Event event
The Event object.
Definition: HIBasics.h:33
virtual bool next()=0
const Nucleus & projectile() const
Projectile nucleus configuration for the current event.
Definition: HeavyIons.h:229
Definition: HISubCollisionModel.h:130
Definition: HeavyIons.h:146
virtual void onInitInfoPtr() override
Definition: HeavyIons.h:250
PythiaObject
Enumerate the different internal Pythia objects.
Definition: HeavyIons.h:166
vector< string > pythiaNames
The names associated with the secondary pythia objects.
Definition: HeavyIons.h:139
static void addSpecialSettings(Settings &settings)
The abstract HeavyIons class.
Definition: HeavyIons.cc:25
Pythia * mainPythiaPtr
Definition: HeavyIons.h:124
Definition: HISubCollisionModel.h:30
virtual bool canVetoProcessLevel()
Possibility to veto event after process-level selection.
Definition: UserHooks.h:60
virtual bool canSetImpactParameter() const
Can set the overall impact parameter for the MPI treatment.
Definition: UserHooks.h:235
bool setHIUserHooksPtr(HIUserHooksPtr userHooksPtrIn)
Possibility to pass in pointer for special heavy ion user hooks.
Definition: HeavyIons.h:69
Info * getInfo()
Only one function: return the info object.
Definition: HeavyIons.h:149
Status
Enum for specifying the status of a nucleon.
Definition: HINucleusModel.h:33
Class for storing Events and Info objects.
Definition: HIBasics.h:25
const SigmaTotal sigmaNN() const
Hadronic cross sections used by the subcollision model.
Definition: HeavyIons.h:245
Logger * loggerPtr
Pointer to logger.
Definition: PhysicsBase.h:91
SigmaTotal sigTotNN
Definition: HeavyIons.h:128
virtual bool setKinematics(double)
Set beam kinematics.
Definition: HeavyIons.h:74
Header for classes to set beam momentum and interaction vertex spread.
Definition: Analysis.h:20
The Pythia class contains the top-level routines to generate an event.
Definition: Pythia.h:72
HIInfo hiInfo
Definition: HeavyIons.h:94
Info * infoPtr
Definition: PhysicsBase.h:82
virtual bool setBeamIDs(int, int=0)
Set beam particles.
Definition: HeavyIons.h:88
UserHooks is base class for user access to program execution.
Definition: UserHooks.h:32
vector< Pythia * > pythia
Definition: HeavyIons.h:136
virtual bool doVetoProcessLevel(Event &)
Definition: UserHooks.h:64
Definition: HeavyIons.h:31
virtual void stat()
Print out statistics.
Definition: HeavyIons.cc:176
void updateInfo()
Update the Info object in the main Pythia object.
Definition: HeavyIons.cc:146
Definition: Basics.h:32
The default HeavyIon model in Pythia.
Definition: HeavyIons.h:161
Definition: HIInfo.h:27
Definition: Settings.h:196
virtual double doSetImpactParameter()
Set the overall impact parameter for the MPI treatment.
Definition: UserHooks.h:238