File indexing completed on 2025-08-03 08:16:38
0001
0002
0003
0004
0005
0006 #include "HiMain1.h"
0007 #include "HiMain2.h"
0008 #include "HiParnt.h"
0009 #include "HiStrng.h"
0010 #include "HijCrdn.h"
0011 #include "HijJet1.h"
0012 #include "HijJet2.h"
0013 #include "HijJet4.h"
0014 #include "RanSeed.h"
0015
0016 #include <HepMC/GenEvent.h>
0017 #include <HepMC/GenParticle.h>
0018 #include <HepMC/GenVertex.h>
0019 #include <HepMC/IO_AsciiParticles.h>
0020 #include <HepMC/IO_GenEvent.h>
0021
0022 #include <CLHEP/Geometry/Point3D.h>
0023 #include <CLHEP/Random/MTwistEngine.h>
0024 #include <CLHEP/Random/RandFlat.h>
0025 #include <CLHEP/Random/RandomEngine.h>
0026 #include <CLHEP/Vector/LorentzVector.h>
0027
0028 #include <boost/algorithm/string.hpp>
0029 #include <boost/foreach.hpp>
0030 #include <boost/lexical_cast.hpp>
0031 #include <boost/property_tree/ptree.hpp>
0032 #include <boost/property_tree/xml_parser.hpp>
0033
0034 #include <cmath>
0035 #include <cstdlib>
0036 #include <iostream>
0037 #include <memory>
0038 #include <numeric>
0039 #include <random>
0040 #include <string>
0041 #include <vector>
0042
0043 #define f2cFortran
0044 #define gFortran
0045
0046 #include <cfortran.h>
0047
0048
0049
0050 PROTOCCALLSFSUB3(HIJING, hijing, STRING, FLOAT, FLOAT)
0051 #define HIJING(FRAME, BMIN0, BMAX0) \
0052 CCALLSFSUB3(HIJING, hijing, STRING, FLOAT, FLOAT, FRAME, BMIN0, BMAX0)
0053
0054 PROTOCCALLSFSUB8(HIJSET, hijset, FLOAT, STRING, STRING, STRING, INT, INT, INT, INT)
0055 #define HIJSET(EFRM, FRAME, PROJ, TARG, IAP, IZP, IAT, IZT) \
0056 CCALLSFSUB8(HIJSET, hijset, FLOAT, STRING, STRING, STRING, INT, INT, INT, INT, \
0057 EFRM, FRAME, PROJ, TARG, IAP, IZP, IAT, IZT)
0058
0059 void hijfst_control(int, const std::vector<std::string>&, const std::vector<float>&,const std::vector<int>&, const std::vector<float>&, const std::vector<float>&, const std::vector<float>&);
0060
0061 CLHEP::HepRandomEngine *engine;
0062
0063 float atl_ran(int *)
0064 {
0065 return (float) CLHEP::RandFlat::shoot(engine);
0066 }
0067
0068
0069 FCALLSCFUN1(FLOAT, atl_ran, ATL_RAN, atl_ran, PINT)
0070
0071 typedef HepGeom::Point3D<double> HepPoint3D;
0072 typedef HepMC::GenEvent::particle_iterator piter;
0073
0074 int fillEvent(HepMC::GenEvent *evt);
0075
0076
0077 HiParnt m_hiparnt;
0078
0079
0080 RanSeed m_ranseed;
0081
0082
0083 HiMain1 m_himain1;
0084 HiMain2 m_himain2;
0085 HijJet1 m_hijjet1;
0086 HijJet2 m_hijjet2;
0087 HijJet4 m_hijjet4;
0088 HiStrng m_histrng;
0089 HijCrdn m_hijcrdn;
0090
0091 float efrm;
0092 std::string m_frame;
0093 std::string m_proj;
0094 std::string m_targ;
0095 int iap;
0096 int iat;
0097 int izp;
0098 int izt;
0099 int spec;
0100 double m_vertexOffsetCut = 1.0E-7;
0101 bool keepSpectators;
0102
0103 int main(int argc, char **argv)
0104 {
0105 std::string config_filename = "sHijing.xml";
0106 std::string output;
0107 long randomSeed = 0;
0108 bool randomseed_set = false;
0109 unsigned int N = 1;
0110 bool NEvents_set = false;
0111 for (int i = 1; i < argc; ++i)
0112 {
0113 std::string optionstring = argv[i];
0114 if (optionstring == "-h")
0115 {
0116 std::cout << std::endl
0117 << "Usage: sHijing <config xmlfile [sHijing.xml]>" << std::endl;
0118 std::cout << std::endl;
0119 std::cout << "Parameters:" << std::endl;
0120 std::cout << "-n <number of events [1]>" << std::endl;
0121 std::cout << "-o <outputfile [sHijing.dat]>" << std::endl;
0122 std::cout << "-s <random seet [std::random_device]>" << std::endl;
0123 exit(0);
0124 }
0125 else if (optionstring == "-o")
0126 {
0127 if (i + 1 < argc)
0128 {
0129 output = argv[++i];
0130 }
0131 else
0132 {
0133 std::cout << "-o option requires one argument." << std::endl;
0134 exit(1);
0135 }
0136 continue;
0137 }
0138 else if (optionstring == "-s")
0139 {
0140 if (i + 1 < argc)
0141 {
0142 randomSeed = std::stol(argv[++i]);
0143 randomseed_set = true;
0144 }
0145 else
0146 {
0147 std::cout << "-s option requires one argument." << std::endl;
0148 exit(1);
0149 }
0150 continue;
0151 }
0152 else if (optionstring == "-n")
0153 {
0154 if (i + 1 < argc)
0155 {
0156 N = std::stoul(argv[++i]);
0157 NEvents_set = true;
0158 }
0159 else
0160 {
0161 std::cout << "-s option requires one argument." << std::endl;
0162 exit(1);
0163 }
0164 continue;
0165 }
0166 else
0167 {
0168 config_filename = argv[i];
0169 }
0170 }
0171 char frame[] = " ";
0172 char proj[] = " ";
0173 char targ[] = " ";
0174
0175 using boost::property_tree::ptree;
0176 boost::property_tree::iptree pt, null;
0177 std::ifstream config_file(config_filename);
0178
0179 if (config_file)
0180 {
0181
0182 read_xml(config_file, pt);
0183 std::cout << "using config file: " << config_filename << std::endl;
0184 }
0185 else
0186 {
0187 std::cout << "no xml config file - using internal values" << std::endl;
0188 }
0189 efrm = pt.get("HIJING.EFRM", 200.0);
0190 m_frame = pt.get("HIJING.FRAME", "CMS");
0191 m_proj = pt.get("HIJING.PROJ", "A");
0192 m_targ = pt.get("HIJING.TARG", "A");
0193 iap = pt.get("HIJING.IAP", 197);
0194 izp = pt.get("HIJING.IZP", 79);
0195 iat = pt.get("HIJING.IAT", 197);
0196 izt = pt.get("HIJING.IZT", 79);
0197 float bmin = pt.get("HIJING.BMIN", 0.0);
0198 float bmax = pt.get("HIJING.BMAX", 0.0);
0199 if (!NEvents_set)
0200 {
0201 N = pt.get("HIJING.N", 1);
0202 }
0203 keepSpectators = pt.get("HIJING.KEEP_SPECTATORS", 1);
0204 if (output.empty())
0205 {
0206 output = pt.get("HIJING.OUTPUT", "sHijing.dat");
0207 }
0208 if (!randomseed_set)
0209 {
0210 std::random_device rdev;
0211 randomSeed = pt.get("HIJING.RANDOM.SEED", rdev());
0212 }
0213 engine = new CLHEP::MTwistEngine(randomSeed);
0214
0215
0216 boost::property_tree::iptree &pr1 = pt.get_child("HIJING.HIPR1", null);
0217 BOOST_FOREACH (boost::property_tree::iptree::value_type &v, pr1)
0218 {
0219 int key = boost::lexical_cast<int>(v.first.data());
0220 float value = boost::lexical_cast<float>(v.second.data());
0221 m_hiparnt.hipr1(key) = value;
0222 }
0223 boost::property_tree::iptree &pr2 = pt.get_child("HIJING.IHPR2", null);
0224 BOOST_FOREACH (boost::property_tree::iptree::value_type &v, pr2)
0225 {
0226 int key = boost::lexical_cast<int>(v.first.data());
0227 int value = boost::lexical_cast<int>(v.second.data());
0228 m_hiparnt.ihpr2(key) = value;
0229 }
0230
0231 int fastjet_enable_p = 0;
0232 std::vector<std::string> algorithm_v;
0233 std::vector<float> R_v;
0234 std::vector<int> PID_v;
0235 std::vector<float> EtaMin_v;
0236 std::vector<float> EtaMax_v;
0237 std::vector<float> EtMin_v;
0238
0239 boost::property_tree::iptree &it = pt.get_child("HIJING.FASTJET", null);
0240 BOOST_FOREACH (boost::property_tree::iptree::value_type &v, it)
0241 {
0242 if (boost::to_upper_copy(v.first) != "ALGORITHM") continue;
0243 algorithm_v.push_back(boost::to_upper_copy(v.second.get("NAME", "ANTIKT")));
0244 R_v.push_back(v.second.get("R", 0.2));
0245 PID_v.push_back(v.second.get("PID", 2000000));
0246
0247 EtaMin_v.push_back(v.second.get("EtaMin", -2));
0248 EtaMax_v.push_back(v.second.get("EtaMax", 2));
0249 EtMin_v.push_back(v.second.get("EtMin", 5));
0250
0251 fastjet_enable_p = 1;
0252 }
0253 std::cout << "seed: " << randomSeed << std::endl;
0254 std::cout << "output: " << output << std::endl;
0255 std::cout << "Number of Events: " << N << std::endl;
0256
0257 hijfst_control(fastjet_enable_p, algorithm_v, R_v, PID_v, EtaMin_v, EtaMax_v, EtMin_v);
0258
0259
0260 m_frame.copy(frame, m_frame.size());
0261 m_proj.copy(proj, m_proj.size());
0262 m_targ.copy(targ, m_targ.size());
0263
0264 HIJSET(efrm, frame, proj, targ, iap, izp, iat, izt);
0265
0266
0267 HepMC::IO_GenEvent ascii_io(output.c_str(), std::ios::out);
0268 unsigned int events = 0;
0269 do
0270 {
0271 HIJING(frame, bmin, bmax);
0272
0273 if (m_himain1.ierrstat() != 0)
0274 {
0275 continue;
0276 }
0277 events++;
0278
0279 HepMC::GenEvent *evt = new HepMC::GenEvent();
0280 evt->use_units(HepMC::Units::GEV, HepMC::Units::MM);
0281 evt->set_event_number(events);
0282
0283 fillEvent(evt);
0284
0285 ascii_io << evt;
0286
0287 delete evt;
0288 } while (events < N);
0289
0290 return 0;
0291 }
0292
0293 int fillEvent(HepMC::GenEvent *evt)
0294 {
0295 int np = m_himain1.np();
0296 int nt = m_himain1.nt();
0297 int n0 = m_himain1.n0();
0298 int n01 = m_himain1.n01();
0299 int n10 = m_himain1.n10();
0300 int n11 = m_himain1.n11();
0301
0302
0303
0304
0305
0306
0307 int ncoll = n0 + n01 + n10 + n11;
0308
0309 int natt = m_himain1.natt();
0310 float b = m_hiparnt.hint1(19);
0311 float bphi = m_hiparnt.hint1(20);
0312
0313
0314 std::vector<float> x;
0315 std::vector<float> y;
0316 float tx, ty;
0317 float bbx = b * cos(bphi);
0318 float bby = b * sin(bphi);
0319
0320 for (int i = 0; i < m_hiparnt.ihnt2(1); i++)
0321 {
0322 if (m_histrng.nfp(i, 5) > 2)
0323 {
0324 tx = m_hijcrdn.yp(1, i) + bbx;
0325 ty = m_hijcrdn.yp(2, i) + bby;
0326 x.push_back(tx);
0327 y.push_back(ty);
0328
0329
0330 }
0331 }
0332 for (int i = 0; i < m_hiparnt.ihnt2(3); i++)
0333 {
0334 if (m_histrng.nft(i, 5) > 2)
0335 {
0336 tx = m_hijcrdn.yt(1, i);
0337 ty = m_hijcrdn.yt(2, i);
0338 x.push_back(tx);
0339 y.push_back(ty);
0340
0341
0342 }
0343 }
0344
0345 float e_part = 0.0;
0346 if (x.size() != 0)
0347 {
0348 float N = x.size();
0349 float xa = std::accumulate(x.begin(), x.end(), 0) / N;
0350 float ya = std::accumulate(y.begin(), y.end(), 0) / N;
0351
0352 float sxx = 0;
0353 float syy = 0;
0354 float sxy = 0;
0355 for (int i = 0; i < N; i++)
0356 {
0357 sxx += (x[i] - xa) * (x[i] - xa);
0358 syy += (y[i] - ya) * (y[i] - ya);
0359 sxy += (x[i] - xa) * (y[i] - ya);
0360 }
0361 sxx /= N;
0362 syy /= N;
0363 sxy /= N;
0364 e_part = std::sqrt((sxx - syy) * (sxx - syy) + 4 * sxy * sxy) / (sxx + syy);
0365 }
0366
0367
0368 HepMC::HeavyIon hi(1, np, nt, ncoll, 0, 0, n01, n10, n11, b, bphi, e_part, 42.0);
0369
0370 evt->set_heavy_ion(hi);
0371
0372
0373
0374
0375
0376
0377 bool keptHistory = (m_hiparnt.ihpr2(21) == 1);
0378
0379
0380 int numHijingPart = m_himain1.natt();
0381
0382
0383 std::vector<int> partOriginVertex_vec;
0384 std::vector<int> partDecayVertex_vec;
0385 std::vector<HepMC::GenParticle *> particleHepPartPtr_vec;
0386
0387 partOriginVertex_vec.assign(numHijingPart, 0);
0388 partDecayVertex_vec.assign(numHijingPart, -1);
0389 particleHepPartPtr_vec.assign(numHijingPart, (HepMC::GenParticle *) 0);
0390
0391
0392 std::vector<HepMC::GenVertex *> vertexPtrVec;
0393
0394
0395 CLHEP::HepLorentzVector newVertex;
0396 newVertex = CLHEP::HepLorentzVector(0., 0., 0., 0.);
0397 HepMC::GenVertex *v1 = new HepMC::GenVertex(newVertex);
0398
0399 evt->add_vertex(v1);
0400 vertexPtrVec.push_back(v1);
0401
0402 double eproj = (m_frame == "CMS") ? efrm / 2.0 : efrm;
0403 int proj_id = (m_proj == "A") ? 3000000 + iap : 2212;
0404 v1->add_particle_in(new HepMC::GenParticle(CLHEP::HepLorentzVector(0., 0., eproj, eproj),
0405 proj_id, 101));
0406
0407 double etarg = (m_frame == "CMS") ? efrm / 2.0 : efrm;
0408 int targ_id = (m_targ == "A") ? 3000000 + iap : 2212;
0409 v1->add_particle_in(new HepMC::GenParticle(CLHEP::HepLorentzVector(0., 0., -etarg, etarg),
0410 targ_id, 102));
0411
0412
0413 for (int i = 1; i <= natt; ++i)
0414 {
0415 if (m_himain2.katt(i, 4) == 103)
0416 {
0417
0418 CLHEP::HepLorentzVector jetP4(m_himain2.patt(i, 1),
0419 m_himain2.patt(i, 2),
0420 m_himain2.patt(i, 3),
0421 m_himain2.patt(i, 4));
0422 v1->add_particle_out(new HepMC::GenParticle(jetP4,
0423 m_himain2.katt(i, 1),
0424 m_himain2.katt(i, 4)));
0425
0426 continue;
0427 }
0428
0429
0430 if (!keepSpectators &&
0431 ((m_himain2.katt(i, 2) == 0) || (m_himain2.katt(i, 2)) == 10))
0432 continue;
0433
0434
0435 int parentIndex = m_himain2.katt(i, 3) - 1;
0436 int parentOriginIndex = 0;
0437 int parentDecayIndex = -1;
0438
0439
0440 if (parentIndex >= 0)
0441 {
0442 parentOriginIndex = partOriginVertex_vec[parentIndex];
0443 parentDecayIndex = partDecayVertex_vec[parentIndex];
0444 }
0445
0446
0447 CLHEP::HepLorentzVector particleStart(m_himain2.vatt(i, 1),
0448 m_himain2.vatt(i, 2),
0449 m_himain2.vatt(i, 3),
0450 m_himain2.vatt(i, 4));
0451
0452
0453 int particleVertexIndex = 0;
0454
0455
0456 if (keptHistory)
0457 {
0458
0459
0460 if (parentDecayIndex != -1)
0461 {
0462
0463 HepPoint3D vertex_pos(vertexPtrVec[parentDecayIndex]->point3d().x(),
0464 vertexPtrVec[parentDecayIndex]->point3d().y(),
0465 vertexPtrVec[parentDecayIndex]->point3d().z());
0466 double distance = vertex_pos.distance(particleStart.vect());
0467
0468 if (distance > m_vertexOffsetCut)
0469 {
0470 HepMC::GenVertex::particles_out_const_iterator iter;
0471 for (iter = vertexPtrVec[parentDecayIndex]->particles_out_const_begin();
0472 iter != vertexPtrVec[parentDecayIndex]->particles_out_const_end();
0473 iter++)
0474 {
0475 std::cout << (*iter)->barcode() << ", ";
0476 }
0477
0478 std::cout << std::endl;
0479 }
0480
0481
0482 particleVertexIndex = parentDecayIndex;
0483 }
0484 else
0485 {
0486
0487
0488
0489 HepPoint3D vertex_pos(vertexPtrVec[parentOriginIndex]->point3d().x(),
0490 vertexPtrVec[parentOriginIndex]->point3d().y(),
0491 vertexPtrVec[parentOriginIndex]->point3d().z());
0492 double distance = vertex_pos.distance(particleStart.vect());
0493
0494 if (distance > m_vertexOffsetCut && parentIndex == -1)
0495 {
0496
0497
0498
0499
0500 std::cout
0501 << "HIJING BUG:: Particle found with displaced vertex but no parent "
0502 << std::endl;
0503 }
0504 if (distance > m_vertexOffsetCut || parentOriginIndex != 0)
0505 {
0506
0507 HepMC::GenVertex *newVertex_p = new HepMC::GenVertex(particleStart);
0508
0509 evt->add_vertex(newVertex_p);
0510 vertexPtrVec.push_back(newVertex_p);
0511 particleVertexIndex = vertexPtrVec.size() - 1;
0512
0513
0514 partDecayVertex_vec[parentIndex] = particleVertexIndex;
0515
0516
0517 newVertex_p->add_particle_in(particleHepPartPtr_vec[parentIndex]);
0518 }
0519 else
0520 {
0521
0522 particleVertexIndex = parentOriginIndex;
0523 }
0524 }
0525 }
0526 else
0527 {
0528
0529 int foundVert = -1;
0530 for (unsigned int ivert = 0; ivert < vertexPtrVec.size(); ivert++)
0531 {
0532 HepPoint3D vertex_pos(vertexPtrVec[ivert]->point3d().x(),
0533 vertexPtrVec[ivert]->point3d().y(),
0534 vertexPtrVec[ivert]->point3d().z());
0535 double distance = vertex_pos.distance(particleStart.vect());
0536 if (distance < m_vertexOffsetCut)
0537 {
0538 foundVert = ivert;
0539 break;
0540 }
0541 }
0542
0543 if (foundVert == -1)
0544 {
0545
0546 HepMC::GenVertex *newVertex_p = new HepMC::GenVertex(particleStart);
0547
0548 evt->add_vertex(newVertex_p);
0549 vertexPtrVec.push_back(newVertex_p);
0550 particleVertexIndex = vertexPtrVec.size() - 1;
0551 }
0552 else
0553 {
0554 particleVertexIndex = foundVert;
0555 }
0556 }
0557
0558
0559 int particleId = m_himain2.katt(i, 1);
0560 int particleStatus = 1;
0561 if (m_himain2.katt(i, 4) == 11)
0562 {
0563 particleStatus = 2;
0564 }
0565
0566
0567 CLHEP::HepLorentzVector particleP4(m_himain2.patt(i, 1),
0568 m_himain2.patt(i, 2),
0569 m_himain2.patt(i, 3),
0570 m_himain2.patt(i, 4));
0571
0572 HepMC::GenParticle *newParticle_p = new HepMC::GenParticle(particleP4,
0573 particleId,
0574 particleStatus);
0575
0576
0577
0578
0579 particleHepPartPtr_vec[i - 1] = newParticle_p;
0580
0581
0582 vertexPtrVec[particleVertexIndex]->add_particle_out(newParticle_p);
0583 partOriginVertex_vec[i - 1] = particleVertexIndex;
0584 }
0585
0586 return 0;
0587 }