GENIEGenerator
Loading...
Searching...
No Matches
PhotonRESWdecPythia8.cxx
Go to the documentation of this file.
1//____________________________________________________________________________
2/*
3 Copyright (c) 2003-2025, The GENIE Collaboration
4 For the full text of the license visit http://copyright.genie-mc.org
5
6 Alfonso Garcia <aagarciasoto \at km3net.de>
7 IFIC (Valencia)
8*/
9//____________________________________________________________________________
10
12
13//___________________________________________________________________________
15EventRecordVisitorI("genie::PhotonRESWdecPythia8")
16{
17 this->Initialize();
18 born = new Born();
19}
20//___________________________________________________________________________
22EventRecordVisitorI("genie::PhotonRESWdecPythia8", config)
23{
24 this->Initialize();
25 born = new Born();
26}
27//___________________________________________________________________________
32//____________________________________________________________________________
34{
35
36 if(!this->Wdecay(event)) {
37 LOG("PhotonRESGenerator", pWARN) << "W decayer failed!";
38 event->EventFlags()->SetBitNumber(kHadroSysGenErr, true);
40 exception.SetReason("Could not simulate the W decay system");
41 exception.SwitchOnFastForward();
42 throw exception;
43 return;
44 }
45
46}
47//___________________________________________________________________________
49#ifdef __GENIE_PYTHIA8_ENABLED__
50 event // avoid unused variable warning if PYTHIA8 is not enabled
51#endif
52) const
53{
54
55#ifdef __GENIE_PYTHIA8_ENABLED__
56 Interaction * interaction = event->Summary();
57 const InitialState & init_state = interaction->InitState();
58
59 //incoming v & struck particle & remnant nucleus
60 GHepParticle * nu = event->Probe();
61 GHepParticle * el = event->HitNucleon();
62
63 GHepParticle * target = event -> TargetNucleus();
64 if(target) event->AddParticle(target->Pdg(), kIStFinalStateNuclearRemnant, 1,-1,-1,-1, *(target->P4()), *(target->X4()) );
65
66 TVector3 unit_nu = nu->P4()->Vect().Unit();
67
68 int probepdg = init_state.ProbePdg();
69
70 long double Mtarget = init_state.Tgt().HitNucMass();
71 long double mlout = interaction->FSPrimLepton()->Mass(); //mass of charged lepton
72
73 long double Enuin = init_state.ProbeE(kRfLab);
74 long double s = born->GetS(Mtarget,Enuin);
75
76 long double n1 = interaction->Kine().GetKV(kKVn1);
77 long double n2 = interaction->Kine().GetKV(kKVn2);
78
79 long double costhCM = n1;
80 long double sinthCM = sqrtl(1-costhCM*costhCM);
81
82 long double xmin = fQ2PDFmin/2./Enuin/Mtarget;
83 long double x = expl( logl(xmin) + (logl(1.0)-logl(xmin))*n2 );
84 long double s_r = s*x;
85
86 // Boost velocity CM -> LAB
87 long double EnuinCM = sqrtl(s_r)/2.;
88 long double beta = (powl(Enuin,2)-powl(EnuinCM,2))/(powl(Enuin,2)+powl(EnuinCM,2));
89
90 // Final state primary lepton PDG code
91 int pdgl = interaction->FSPrimLeptonPdg();
92 assert(pdgl!=0);
93
94 if ( pdg::IsElectron(TMath::Abs(pdgl)) || pdg::IsMuon(TMath::Abs(pdgl)) || pdg::IsTau(TMath::Abs(pdgl)) ) {
95
96 long double ElpoutCM = (s_r+mlout*mlout)/sqrtl(s_r)/2.;
97 long double EnuoutCM = (s_r-mlout*mlout)/sqrtl(s_r)/2.;
98 LongLorentzVector p4_lpout( 0., EnuoutCM*sinthCM, EnuoutCM*costhCM, ElpoutCM );
99 LongLorentzVector p4_nuout( 0., -EnuoutCM*sinthCM, -EnuoutCM*costhCM, EnuoutCM );
100
101 p4_lpout.BoostZ(beta);
102 p4_nuout.BoostZ(beta);
103
104 TLorentzVector p4lp_o( (double)p4_lpout.Px(), (double)p4_lpout.Py(), (double)p4_lpout.Pz(), (double)p4_lpout.E() );
105 TLorentzVector p4nu_o( (double)p4_nuout.Px(), (double)p4_nuout.Py(), (double)p4_nuout.Pz(), (double)p4_nuout.E() );
106
107 // Randomize transverse components
109 double phi = 2* kPi * rnd->RndLep().Rndm();
110 p4lp_o.RotateZ(phi);
111 p4nu_o.RotateZ(phi);
112
113 //rotate from LAB=[0,0,Ev,Ev]->[px,py,pz,E]
114 p4lp_o.RotateUz(unit_nu);
115 p4nu_o.RotateUz(unit_nu);
116
117 int pdgvout = 0;
118 if ( pdg::IsElectron(pdgl) ) pdgvout = kPdgAntiNuE;
119 else if ( pdg::IsPositron(pdgl) ) pdgvout = kPdgNuE;
120 else if ( pdg::IsMuon(pdgl) ) pdgvout = kPdgAntiNuMu;
121 else if ( pdg::IsAntiMuon(pdgl) ) pdgvout = kPdgNuMu;
122 else if ( pdg::IsTau(pdgl) ) pdgvout = kPdgAntiNuTau;
123 else if ( pdg::IsAntiTau(pdgl) ) pdgvout = kPdgNuTau;
124
125 int pdgboson = pdg::IsNeutrino(probepdg) ? kPdgWP : kPdgWM;
126
127 // Create a GHepParticle and add it to the event record
128 event->AddParticle( pdgboson, kIStDecayedState, 0, -1, 5, 6, *nu->P4()+*el->P4(), *(nu->X4()) ); //W [mothers: nuebar_in,e_in][daugthers: nulbar_out,lp_out]
129 event->AddParticle( pdgl, kIStStableFinalState, 4, -1, -1, -1, p4lp_o, *(nu->X4()) );
130 event->AddParticle( pdgvout, kIStStableFinalState, 4, -1, -1, -1, p4nu_o, *(nu->X4()) );
131 event->Summary()->KinePtr()->SetFSLeptonP4(p4lp_o);
132
133 }
134 else {
135
136
137 //We have to initialize Pythia8 everytime we generate a new event
138 //And we have to change the seed because it would regenerate the same event
139 //if we dont do it.
141 Pythia8::Event fEvent;
142 if (pdg::IsNeutrino(probepdg)) {
143 fPythiaP->settings.mode("Random:seed", rnd->RndLep().Integer(100000000));
144 fPythiaP->settings.parm("Beams:eCM",sqrtl(s_r));
145 fPythiaP->init();
146 fPythiaP->next();
147 // fPythiaP->event.list();
148 // fPythiaP->stat();
149 fEvent = fPythiaP->event;
150 }
151 else {
152 fPythiaN->settings.mode("Random:seed", rnd->RndLep().Integer(100000000));
153 fPythiaN->settings.parm("Beams:eCM",sqrtl(s_r));
154 fPythiaN->init();
155 fPythiaN->next();
156 // fPythiaN->event.list();
157 // fPythiaN->stat();
158 fEvent = fPythiaN->event;
159 }
160
161 int np = fEvent.size();
162 assert(np>0);
163
164 for (int i = 5; i < np; i++) { // ignore first entry -> system + input particles
165
166 int pdgc = fEvent[i].id();
167 if (!PDGLibrary::Instance()->Find(pdgc)) continue; // some intermediate particles not part of genie tables
168
169 int ks = fEvent[i].status();
170
171 LongLorentzVector p4longo(fEvent[i].px(), fEvent[i].py(), fEvent[i].pz(), fEvent[i].e());
172 p4longo.BoostZ(beta);
173
174 TLorentzVector p4o( (double)p4longo.Px(), (double)p4longo.Py(), (double)p4longo.Pz(), (double)p4longo.E() );
175 p4o.RotateUz(unit_nu);
176
177 double massPDG = PDGLibrary::Instance()->Find(pdgc)->Mass();
178 if ( ks>0 && p4o.E()<massPDG ) {
179 LOG("PhotonRESGenerator", pWARN) << "Putting at rest one stable particle generated by PYTHIA because E < m";
180 LOG("PhotonRESGenerator", pWARN) << "PDG = " << pdgc << " // State = " << ks;
181 LOG("PhotonRESGenerator", pWARN) << "E = " << p4o.E() << " // |p| = " << TMath::Sqrt(p4o.P());
182 LOG("PhotonRESGenerator", pWARN) << "p = [ " << p4o.Px() << " , " << p4o.Py() << " , " << p4o.Pz() << " ]";
183 LOG("PhotonRESGenerator", pWARN) << "m = " << p4o.M() << " // mpdg = " << massPDG;
184 p4o.SetXYZT(0,0,0,massPDG);
185 }
186
187 // copy final state particles to the event record
189
190 // fix numbering scheme used for mother/daughter assignments
191 int firstmother = -1;
192 int lastmother = -1;
193 int firstchild = -1;
194 int lastchild = -1;
195
196 if ( fEvent[i].mother1() == 3 ) { //produced W boson: mother will be the incoming neutrino
197 firstmother = 0;
198 firstchild = fEvent[i].daughter1() - 3;
199 lastchild = fEvent[i].daughter2() - 3;
200 }
201 else { //rest
202 firstmother = fEvent[i].mother1() - 3; //shift to match boson position
203 firstchild = fEvent[i].daughter1() - 3;
204 lastchild = fEvent[i].daughter2() - 3;
205 }
206
207 double vx = nu->X4()->X() + fEvent[i].xProd()*1e12; //pythia gives position in [mm] while genie uses [fm]
208 double vy = nu->X4()->Y() + fEvent[i].yProd()*1e12;
209 double vz = nu->X4()->Z() + fEvent[i].zProd()*1e12;
210 double vt = nu->X4()->T() + fEvent[i].tProd()*(units::millimeter/units::second);
211 TLorentzVector pos( vx, vy, vz, vt );
212
213 event->AddParticle(pdgc, ist, firstmother, lastmother, firstchild, lastchild, p4o, pos );
214 }
215
216 }
217
218 return true;
219#else
220 return false;
221#endif
222
223}
224//___________________________________________________________________________
230//____________________________________________________________________________
236//____________________________________________________________________________
238{
239
240#ifdef __GENIE_PYTHIA8_ENABLED__
241 GetParam( "SSBarSuppression", fSSBarSuppression );
242 GetParam( "GaussianPt2", fGaussianPt2 );
243 GetParam( "NonGaussianPt2Tail", fNonGaussianPt2Tail );
244 GetParam( "RemainingEnergyCutoff", fRemainingECutoff );
245 GetParam( "DiQuarkSuppression", fDiQuarkSuppression );
246 GetParam( "LightVMesonSuppression", fLightVMesonSuppression );
247 GetParam( "SVMesonSuppression", fSVMesonSuppression );
248 GetParam( "Lunda", fLunda );
249 GetParam( "Lundb", fLundb );
250 GetParam( "LundaDiq", fLundaDiq );
251
252 GetParam( "Q2Grid-Min", fQ2PDFmin );
253
254 fPythiaP->settings.parm("StringFlav:probStoUD", fSSBarSuppression);
255 fPythiaP->settings.parm("Diffraction:primKTwidth", fGaussianPt2);
256 fPythiaP->settings.parm("StringPT:enhancedFraction", fNonGaussianPt2Tail);
257 fPythiaP->settings.parm("StringFragmentation:stopMass", fRemainingECutoff);
258 fPythiaP->settings.parm("StringFlav:probQQtoQ", fDiQuarkSuppression);
259 fPythiaP->settings.parm("StringFlav:mesonUDvector", fLightVMesonSuppression);
260 fPythiaP->settings.parm("StringFlav:mesonSvector", fSVMesonSuppression);
261 fPythiaP->settings.parm("StringZ:aLund", fLunda);
262 fPythiaP->settings.parm("StringZ:bLund", fLundb);
263 fPythiaP->settings.parm("StringZ:aExtraDiquark", fLundaDiq);
264
265 fPythiaN->settings.parm("StringFlav:probStoUD", fSSBarSuppression);
266 fPythiaN->settings.parm("Diffraction:primKTwidth", fGaussianPt2);
267 fPythiaN->settings.parm("StringPT:enhancedFraction", fNonGaussianPt2Tail);
268 fPythiaN->settings.parm("StringFragmentation:stopMass", fRemainingECutoff);
269 fPythiaN->settings.parm("StringFlav:probQQtoQ", fDiQuarkSuppression);
270 fPythiaN->settings.parm("StringFlav:mesonUDvector", fLightVMesonSuppression);
271 fPythiaN->settings.parm("StringFlav:mesonSvector", fSVMesonSuppression);
272 fPythiaN->settings.parm("StringZ:aLund", fLunda);
273 fPythiaN->settings.parm("StringZ:bLund", fLundb);
274 fPythiaN->settings.parm("StringZ:aExtraDiquark", fLundaDiq);
275
276 // Same default mass of the W boson in pythia8 and genie, so no need to change in pythia8
277 // No problem with energy conservation W and top decays, so no need to set the width to 0
278
279 // Important for not decaying too early!!!
280 // Copy of the method from Decayer class to have a consistent treatment.
281 // The idea is to not decay in this stage what we dont want to decay in Decayer.
282 // Hadronization -> Decayer
283 //------------------------------
284 // Decay -> Decay
285 // Undecay -> Undecay
286 // Undecay -> Decay
287 // Decay -> Undecay -> This is the problematic one
288 // So we loop over all the particles for which we inhibit decay in the config file
289 // for the Decayer stage and we inhibit it also at hadronization.
290 // This is not need in LeptonHadronization and PhotonCOH because they use the
291 // Pythia8Singleton class which already defines the decays consistently
292 //
293 RgKeyList klist = GetConfig().FindKeys("DecayParticleWithCode=");
294 RgKeyList::const_iterator kiter = klist.begin();
295 for( ; kiter != klist.end(); ++kiter) {
296 RgKey key = *kiter;
297 bool decay = GetConfig().GetBool(key);
298 vector<string> kv = utils::str::Split(key,"=");
299 int pdg_code = atoi(kv[1].c_str());
300 if(!decay) {
301 LOG("PhotonRESGenerator", pDEBUG) << "Configured to inhibit decays for " << pdg_code;
302 auto pdentryP = fPythiaP->particleData.particleDataEntryPtr(pdg_code);
303 for (int ichan=0; ichan<=pdentryP->sizeChannels()-1; ++ichan) {
304 int onMode = pdentryP->channel(ichan).onMode();
305 bool is_particle = (pdg_code>0);
306 switch ( onMode ) {
307 case 0: // off for particles & antiparticles
308 break; // already off
309 case 1: // on for both particle & antiparticle
310 onMode = (is_particle ? 3 : 2);
311 break;
312 case 2: // on for particle only
313 onMode = (is_particle ? 0 : 2);
314 break;
315 case 3: // on for antiparticle only
316 onMode = (is_particle ? 3 : 0);
317 break;
318 }
319 pdentryP->channel(ichan).onMode(onMode);
320 }
321
322 auto pdentryN = fPythiaN->particleData.particleDataEntryPtr(pdg_code);
323 for (int ichan=0; ichan<=pdentryN->sizeChannels()-1; ++ichan) {
324 int onMode = pdentryN->channel(ichan).onMode();
325 bool is_particle = (pdg_code>0);
326 switch ( onMode ) {
327 case 0: // off for particles & antiparticles
328 break; // already off
329 case 1: // on for both particle & antiparticle
330 onMode = (is_particle ? 3 : 2);
331 break;
332 case 2: // on for particle only
333 onMode = (is_particle ? 0 : 2);
334 break;
335 case 3: // on for antiparticle only
336 onMode = (is_particle ? 3 : 0);
337 break;
338 }
339 pdentryN->channel(ichan).onMode(onMode);
340 }
341
342 }
343 }
344
345 //Important: We dont initialize Pythia8 here because it must be done event by event. See above
346#endif
347
348}
349//____________________________________________________________________________
351{
352
353#ifdef __GENIE_PYTHIA8_ENABLED__
354 //One cool feature of having independent Pythia8 instances
355 //We can define our intial state with the proper setting (i.e. disabling decays)
356 //without affecting other classes of GENIE that also use Pythia8
357
358 fPythiaP = new Pythia8::Pythia();
359 fPythiaP->readString("Print:quiet = on");
360 fPythiaP->readString("Random:setSeed = on");
361 fPythiaP->readString("WeakSingleBoson:ffbar2ffbar(s:W) = on");
362 fPythiaP->readString("PDF:lepton = off");
363 fPythiaP->readString("24:onMode = off");
364 fPythiaP->readString("24:onIfAny = 1 2 3 4 5"); //enable W->hadron only
365 fPythiaP->readString("Beams:idA = 12");
366 fPythiaP->readString("Beams:idB = -11");
367
368 fPythiaN = new Pythia8::Pythia();
369 fPythiaN->readString("Print:quiet = on");
370 fPythiaN->readString("Random:setSeed = on");
371 fPythiaN->readString("WeakSingleBoson:ffbar2ffbar(s:W) = on");
372 fPythiaN->readString("PDF:lepton = off");
373 fPythiaN->readString("24:onMode = off");
374 fPythiaN->readString("24:onIfAny = 1 2 3 4 5"); //enable W->hadron only
375 fPythiaN->readString("Beams:idA = -12");
376 fPythiaN->readString("Beams:idB = 11");
377#endif
378
379}
#define pDEBUG
Definition Messenger.h:63
#define LOG(stream, priority)
A macro that returns the requested log4cpp::Category appending a string (using the FILE,...
Definition Messenger.h:96
#define pWARN
Definition Messenger.h:60
string RgKey
virtual const Registry & GetConfig(void) const
bool GetParam(const RgKey &name, T &p, bool is_top_call=true) const
virtual void Configure(const Registry &config)
Definition Algorithm.cxx:62
Born level nu-electron cross section.
Definition Born.h:26
STDHEP-like event record entry that can fit a particle or a nucleus.
int Pdg(void) const
const TLorentzVector * P4(void) const
const TLorentzVector * X4(void) const
GENIE's GHEP MC event record.
Definition GHepRecord.h:45
Initial State information.
const Target & Tgt(void) const
int ProbePdg(void) const
double ProbeE(RefFrame_t rf) const
Summary information for an interaction.
Definition Interaction.h:56
const Kinematics & Kine(void) const
Definition Interaction.h:71
int FSPrimLeptonPdg(void) const
final state primary lepton pdg
TParticlePDG * FSPrimLepton(void) const
final state primary lepton
const InitialState & InitState(void) const
Definition Interaction.h:69
double GetKV(KineVar_t kv) const
static PDGLibrary * Instance(void)
TParticlePDG * Find(int pdgc, bool must_exist=true)
bool Wdecay(GHepRecord *event) const
double fLundaDiq
adjustment of Lund a for di-quark
double fNonGaussianPt2Tail
non gaussian pt2 tail parameterization
double fSSBarSuppression
ssbar suppression
void ProcessEventRecord(GHepRecord *event) const
double fGaussianPt2
gaussian pt2 distribution width
void Configure(const Registry &config)
double fLundb
Lund b parameter.
double fLightVMesonSuppression
light vector meson suppression
double fSVMesonSuppression
strange vector meson suppression
double fDiQuarkSuppression
di-quark suppression parameter
double fRemainingECutoff
remaining E cutoff stopping fragmentation
double fLunda
Lund a parameter.
A singleton holding random number generator classes. All random number generation in GENIE should tak...
Definition RandomGen.h:29
static RandomGen * Instance()
Access instance.
Definition RandomGen.cxx:74
TRandom3 & RndLep(void) const
rnd number generator used by final state primary lepton generators
Definition RandomGen.h:62
A registry. Provides the container for algorithm configuration parameters.
Definition Registry.h:65
RgKeyList FindKeys(RgKey key_part) const
create list with all keys containing 'key_part'
Definition Registry.cxx:840
RgBool GetBool(RgKey key) const
Definition Registry.cxx:460
double HitNucMass(void) const
Definition Target.cxx:233
An exception thrown by EventRecordVisitorI when the normal processing sequence has to be disrupted (f...
const double e
bool IsTau(int pdgc)
Definition PDGUtils.cxx:208
bool IsNeutrino(int pdgc)
Definition PDGUtils.cxx:110
bool IsPositron(int pdgc)
Definition PDGUtils.cxx:193
bool IsElectron(int pdgc)
Definition PDGUtils.cxx:188
bool IsAntiTau(int pdgc)
Definition PDGUtils.cxx:213
bool IsAntiMuon(int pdgc)
Definition PDGUtils.cxx:203
bool IsMuon(int pdgc)
Definition PDGUtils.cxx:198
static constexpr double millimeter
Definition Units.h:41
static constexpr double second
Definition Units.h:37
Simple functions for loading and reading nucleus dependent keys from config files.
vector< string > Split(string input, string delim)
@ kIStFinalStateNuclearRemnant
Definition GHepStatus.h:38
@ kIStDISPreFragmHadronicState
Definition GHepStatus.h:35
@ kIStStableFinalState
Definition GHepStatus.h:30
@ kIStDecayedState
Definition GHepStatus.h:32
vector< RgKey > RgKeyList
Definition Registry.h:50
const int kPdgWM
Definition PDGCodes.h:192
const int kPdgAntiNuE
Definition PDGCodes.h:29
enum genie::EGHepStatus GHepStatus_t
const int kPdgAntiNuTau
Definition PDGCodes.h:33
@ kKVn2
Definition KineVar.h:62
@ kKVn1
Definition KineVar.h:61
const int kPdgNuE
Definition PDGCodes.h:28
const int kPdgNuTau
Definition PDGCodes.h:32
@ kRfLab
Definition RefFrame.h:26
const int kPdgAntiNuMu
Definition PDGCodes.h:31
const int kPdgWP
Definition PDGCodes.h:191
const int kPdgNuMu
Definition PDGCodes.h:30
@ kHadroSysGenErr
Definition GHepFlags.h:32