1 /**************************************************************************
2 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
7 * Permission to use, copy, modify and distribute this software and its *
8 * documentation strictly for non-commercial purposes is hereby granted *
9 * without fee, provided that the above copyright notice appears in all *
10 * copies and that both the copyright notice and this permission notice *
11 * appear in the supporting documentation. The authors make no claims *
12 * about the suitability of this software for any purpose. It is *
13 * provided "as is" without express or implied warranty. *
14 **************************************************************************/
18 Revision 1.5 2000/05/20 14:49:48 fca
19 Call gdebug at the end of gustep
21 Revision 1.4 2000/04/26 10:17:32 fca
22 Changes in Lego for G4 compatibility
24 Revision 1.3 2000/04/07 11:12:35 fca
25 G4 compatibility changes
27 Revision 1.2 2000/02/29 19:11:17 fca
28 Move gucode into AliGeant3.cxx
30 Revision 1.1 2000/02/23 16:25:25 fca
31 AliVMC and AliGeant3 classes introduced
32 ReadEuclid moved from AliRun to AliModule
36 #include <TParticle.h>
38 #include "AliGeant3.h"
41 #include "AliCallf77.h"
45 # define rxgtrak rxgtrak_
46 # define rxstrak rxstrak_
47 # define rxkeep rxkeep_
48 # define rxouth rxouth_
51 # define rxgtrak RXGTRAK
52 # define rxstrak RXSTRAK
53 # define rxkeep RXKEEP
54 # define rxouth RXOUTH
59 AliGeant3::AliGeant3(const char *title) :
62 void AliGeant3::FinishGeometry()
64 TGeant3::FinishGeometry();
65 //Create the color table
69 //____________________________________________________________________________
70 void AliGeant3::Init()
73 //=================Create Materials and geometry
74 TObjArray *modules = gAlice->Modules();
77 while((detector = (AliModule*)next())) {
78 // Initialise detector materials and geometry
79 detector->CreateMaterials();
80 detector->CreateGeometry();
81 detector->BuildGeometry();
85 //Terminate building of geometry
89 //____________________________________________________________________________
90 void AliGeant3::ProcessRun(Int_t nevent)
92 Int_t todo = TMath::Abs(nevent);
93 for (Int_t i=0; i<todo; i++) {
94 // Process one run (one run = one event)
97 gAlice->FinishEvent();
101 void AliGeant3::ProcessEvent()
108 //_____________________________________________________________________________
109 void AliGeant3::SetColors()
112 // Set the colors for all the volumes
113 // this is done sequentially for all volumes
114 // based on the number of their medium
117 Int_t jvolum=fGclink->jvolum;
118 //Int_t jtmed=fGclink->jtmed;
119 //Int_t jmate=fGclink->jmate;
120 Int_t nvolum=fGcnum->nvolum;
123 // Now for all the volumes
124 for(kv=1;kv<=nvolum;kv++) {
125 // Get the tracking medium
126 Int_t itm=Int_t (fZq[fZlq[jvolum-kv]+4]);
128 //Int_t ima=Int_t (fZq[fZlq[jtmed-itm]+6]);
130 //Float_t z=fZq[fZlq[jmate-ima]+7];
132 //icol = Int_t(z)%6+2;
133 //icol = 17+Int_t(z*150./92.);
136 strncpy(name,(char*)&fZiq[jvolum+kv],4);
138 Gsatt(name,"COLO",icol);
142 //_____________________________________________________________________________
144 // Interfaces to Fortran
146 //_____________________________________________________________________________
148 extern "C" void type_of_call rxgtrak (Int_t &mtrack, Int_t &ipart, Float_t *pmom,
149 Float_t &e, Float_t *vpos, Float_t *polar,
153 // Fetches next track from the ROOT stack for transport. Called by the
154 // modified version of GTREVE.
156 // Track number in the ROOT stack. If MTRACK=0 no
157 // mtrack more tracks are left in the stack to be
159 // ipart Particle code in the GEANT conventions.
160 // pmom[3] Particle momentum in GeV/c
161 // e Particle energy in GeV
162 // vpos[3] Particle position
163 // tof Particle time of flight in seconds
166 gAlice->GetNextTrack(mtrack, pdg, pmom, e, vpos, polar, tof);
167 ipart = gMC->IdFromPDG(pdg);
171 //_____________________________________________________________________________
172 extern "C" void type_of_call
174 rxstrak (Int_t &keep, Int_t &parent, Int_t &ipart, Float_t *pmom,
175 Float_t *vpos, Float_t &tof, const char* cmech, Int_t &ntr, const int cmlen)
177 rxstrak (Int_t &keep, Int_t &parent, Int_t &ipart, Float_t *pmom,
178 Float_t *vpos, Float_t &tof, const char* cmech, const int cmlen,
183 // Fetches next track from the ROOT stack for transport. Called by GUKINE
186 // Status of the track. If keep=0 the track is put
187 // keep on the ROOT stack but it is not fetched for
189 // parent Parent track. If parent=0 the track is a primary.
190 // In GUSTEP the routine is normally called to store
191 // secondaries generated by the current track whose
192 // ROOT stack number is MTRACK (common SCKINE.
193 // ipart Particle code in the GEANT conventions.
194 // pmom[3] Particle momentum in GeV/c
195 // vpos[3] Particle position
196 // tof Particle time of flight in seconds
198 // cmech (CHARACTER*10) Particle origin. This field is user
199 // defined and it is not used inside the GALICE code.
200 // ntr Number assigned to the particle in the ROOT stack.
203 Float_t polar[3]={0.,0.,0.};
204 for(int i=0; i<10 && i<cmlen; i++) mecha[i]=cmech[i];
206 Int_t pdg=gMC->PDGFromId(ipart);
207 gAlice->SetTrack(keep, parent-1, pdg, pmom, vpos, polar, tof, mecha, ntr);
211 //_____________________________________________________________________________
212 extern "C" void type_of_call rxkeep(const Int_t &n)
214 if( NULL==gAlice ) exit(1);
216 if( n<=0 || n>gAlice->Particles()->GetEntries() )
218 printf(" Bad index n=%d must be 0<n<=%d\n",
219 n,gAlice->Particles()->GetEntries());
223 ((TParticle*)(gAlice->Particles()->UncheckedAt(n-1)))->SetBit(kKeepBit);
226 //_____________________________________________________________________________
227 extern "C" void type_of_call rxouth ()
230 // Called by Gtreve at the end of each primary track
232 gAlice->FinishPrimary();
237 # define gudigi gudigi_
238 # define guhadr guhadr_
239 # define guout guout_
240 # define guphad guphad_
241 # define gudcay gudcay_
242 # define guiget guiget_
243 # define guinme guinme_
244 # define guinti guinti_
245 # define gunear gunear_
246 # define guskip guskip_
247 # define guview guview_
248 # define gupara gupara_
249 # define gudtim gudtim_
250 # define guplsh guplsh_
251 # define gutrev gutrev_
252 # define gutrak gutrak_
253 # define guswim guswim_
254 # define gufld gufld_
255 # define gustep gustep_
256 # define gukine gukine_
257 # define uglast uglast_
259 # define gheish gheish_
260 # define flufin flufin_
261 # define gfmfin gfmfin_
262 # define gpghei gpghei_
263 # define fldist fldist_
264 # define gfmdis gfmdis_
265 # define ghelx3 ghelx3_
266 # define ghelix ghelix_
267 # define grkuta grkuta_
268 # define gtrack gtrack_
269 # define gtreveroot gtreveroot_
270 # define glast glast_
273 # define gudigi GUDIGI
274 # define guhadr GUHADR
276 # define guphad GUPHAD
277 # define gudcay GUDCAY
278 # define guiget GUIGET
279 # define guinme GUINME
280 # define guinti GUINTI
281 # define gunear GUNEAR
282 # define guskip GUSKIP
283 # define guview GUVIEW
284 # define gupara GUPARA
285 # define gudtim GUDTIM
286 # define guplsh GUPLSH
287 # define gutrev GUTREV
288 # define gutrak GUTRAK
289 # define guswim GUSWIM
291 # define gustep GUSTEP
292 # define gukine GUKINE
293 # define uglast UGLAST
295 # define gheish GHEISH
296 # define flufin FLUFIN
297 # define gfmfin GFMFIN
298 # define gpghei GPGHEI
299 # define fldist FLDIST
300 # define gfmdis GFMDIS
301 # define ghelx3 GHELX3
302 # define ghelix GHELIX
303 # define grkuta GRKUTA
304 # define gtrack GTRACK
305 # define gtreveroot GTREVEROOT
310 extern "C" type_of_call void gheish();
311 extern "C" type_of_call void flufin();
312 extern "C" type_of_call void gfmfin();
313 extern "C" type_of_call void gpghei();
314 extern "C" type_of_call void fldist();
315 extern "C" type_of_call void gfmdis();
316 extern "C" type_of_call void ghelx3(Float_t&, Float_t&, Float_t*, Float_t*);
317 extern "C" type_of_call void ghelix(Float_t&, Float_t&, Float_t*, Float_t*);
318 extern "C" type_of_call void grkuta(Float_t&, Float_t&, Float_t*, Float_t*);
319 extern "C" type_of_call void gtrack();
320 extern "C" type_of_call void gtreveroot();
321 extern "C" type_of_call void glast();
323 extern "C" type_of_call {
325 //______________________________________________________________________
329 // ******************************************************************
331 // * User routine to digitize one event *
333 // * ==>Called by : GTRIG *
335 // ******************************************************************
340 //______________________________________________________________________
344 // ******************************************************************
346 // * User routine to generate one hadronic interaction *
348 // * ==>Called by : GTHADR,GTNEUT *
350 // ******************************************************************
353 // ------------------------------------------------------------------
355 TGeant3* geant3 = (TGeant3*) gMC;
356 Int_t ihadr=geant3->Gcphys()->ihadr;
357 if (ihadr<4) gheish();
358 else if (ihadr==4) flufin();
362 //______________________________________________________________________
366 // ******************************************************************
368 // * User routine called at the end of each event *
370 // * ==>Called by : GTRIG *
372 // ******************************************************************
375 // ------------------------------------------------------------------
379 //______________________________________________________________________
383 // ******************************************************************
385 // * User routine to compute Hadron. inter. probabilities *
387 // * ==>Called by : GTHADR,GTNEUT *
389 // ******************************************************************
392 // ------------------------------------------------------------------
394 TGeant3* geant3 = (TGeant3*) gMC;
395 Int_t ihadr=geant3->Gcphys()->ihadr;
396 if (ihadr<4) gpghei();
397 else if (ihadr==4) fldist();
401 //______________________________________________________________________
405 // ******************************************************************
407 // * User routine to decay particles *
409 // * ==>Called by : GDECAY *
411 // ******************************************************************
414 // ------------------------------------------------------------------
418 //______________________________________________________________________
419 void guiget(Int_t&, Int_t&, Int_t&)
422 // ******************************************************************
424 // * User routine for interactive control of GEANT *
426 // * ==>Called by : <GXINT>, GINCOM *
428 // ******************************************************************
431 // ------------------------------------------------------------------
435 //______________________________________________________________________
436 void guinme(Float_t*, Int_t&, Float_t*, Int_t& IYES)
439 // **********************************************
441 // * USER ROUTINE TO PROVIDE GINME FUNCTION *
442 // * FOR ALL USER SHAPES IDENTIFIED BY THE *
443 // * SHAPE NUMBER SH. POINT IS GIVEN IN X *
444 // * THE PARAMETERS ARE GIVEN IN P. IYES IS *
445 // * RETURNED 1 IF POINT IS IN, 0 IF POINT *
446 // * IS OUT AND LESS THAN ZERO IF SHAPE *
447 // * NUMBER IS NOT SUPPORTED. *
449 // * ==>Called by : GINME *
451 // **********************************************
456 //______________________________________________________________________
460 // ******************************************************************
462 // * User routine for interactive version *
464 // * ==>Called by : <GXINT>, GINTRI *
466 // ******************************************************************
469 // ------------------------------------------------------------------
473 //______________________________________________________________________
474 void gunear(Int_t&, Int_t&, Float_t*, Int_t&)
477 // ******************************************************************
480 // * ISEARC to identify the given volume *
481 // * ICALL to identify the calling routine *
484 // * X coordinates (+direction for ICALL=2) *
485 // * JNEAR address of default list of neighbours *
486 // * (list to be overwriten by user) *
488 // * Called by : GFTRAC, GINVOL, GTMEDI, GTNEXT, GNEXT, GMEDIA *
490 // ******************************************************************
493 // ------------------------------------------------------------------
497 //______________________________________________________________________
498 void guskip(Int_t& ISKIP)
501 // ******************************************************************
503 // * User routine to skip unwanted tracks *
505 // * Called by : GSSTAK *
506 // * Author : F.Bruyant *
508 // ******************************************************************
511 // ------------------------------------------------------------------
516 //______________________________________________________________________
517 void guswim(Float_t& CHARGE, Float_t& STEP, Float_t* VECT, Float_t* VOUT)
520 // ******************************************************************
522 // * User routine to control tracking of one track *
523 // * in a magnetic field *
525 // * ==>Called by : GTELEC,GTHADR,GTMUON *
527 // ******************************************************************
530 // ------------------------------------------------------------------
532 TGeant3* geant3 = (TGeant3*) gMC;
533 Int_t ifield=geant3->Gctmed()->ifield;
534 Float_t fieldm=geant3->Gctmed()->fieldm;
537 Float_t fldcharge = fieldm*CHARGE;
538 ghelx3(fldcharge,STEP,VECT,VOUT);
540 else if (ifield==2) ghelix(CHARGE,STEP,VECT,VOUT);
541 else grkuta(CHARGE,STEP,VECT,VOUT);
544 //______________________________________________________________________
545 void guview(Int_t&, Int_t&, DEFCHARD, Int_t& DEFCHARL)
548 // ******************************************************************
550 // * User routine for interactive version *
552 // * ==>Called by : <GXINT>, GINC1 *
554 // ******************************************************************
557 // ------------------------------------------------------------------
561 //______________________________________________________________________
565 // ******************************************************************
567 // * User routine called every time a particle falls below *
568 // * parametrization threshold. This routine should create *
569 // * the parametrization stack, and, when this is full, *
570 // * parametrize the shower and track the geantinos. *
572 // * ==>Called by : GTRACK *
574 // ******************************************************************
577 // ------------------------------------------------------------------
581 //______________________________________________________________________
582 Float_t gudtim(Float_t&, Float_t&, Int_t&, Int_t&)
585 // ******************************************************************
587 // * User function called by GCDRIF to return drift time *
589 // * ==>Called by : GCDRIF *
591 // ******************************************************************
594 // ------------------------------------------------------------------
600 //______________________________________________________________________
601 Float_t guplsh(Int_t&, Int_t&)
604 // ******************************************************************
607 // * ==>Called by : GLISUR *
609 // ******************************************************************
612 // ------------------------------------------------------------------
615 //*** By default this defines perfect smoothness
619 //______________________________________________________________________
623 // ******************************************************************
625 // * User routine to control tracking of one track *
627 // * ==>Called by : GTREVE *
629 // ******************************************************************
632 // ------------------------------------------------------------------
634 Int_t ndet = gAlice->Modules()->GetLast();
635 TObjArray &dets = *gAlice->Modules();
639 for(i=0; i<=ndet; i++)
640 if((module = (AliModule*)dets[i]))
645 for(i=0; i<=ndet; i++)
646 if((module = (AliModule*)dets[i]))
650 //______________________________________________________________________
654 // ******************************************************************
656 // * User routine to control tracking of one event *
658 // * ==>Called by : GTRIG *
660 // ******************************************************************
663 // ------------------------------------------------------------------
669 //______________________________________________________________________
670 void gufld(Float_t *x, Float_t *b)
672 if(gAlice->Field()) {
673 gAlice->Field()->Field(x,b);
675 printf("No mag field defined!\n");
680 //______________________________________________________________________
684 // ******************************************************************
686 // * User routine called at the end of each tracking step *
687 // * INWVOL is different from 0 when the track has reached *
688 // * a volume boundary *
689 // * ISTOP is different from 0 if the track has stopped *
691 // * ==>Called by : GTRACK *
693 // ******************************************************************
699 Int_t ipp, jk, id, nt;
700 Float_t polar[3]={0,0,0};
704 TGeant3* geant3 = (TGeant3*) gMC;
706 // Stop particle if outside user defined tracking region
707 gMC->TrackPosition(x);
708 r=TMath::Sqrt(x[0]*x[0]+x[1]*x[1]);
709 if (r > gAlice->TrackingRmax() || TMath::Abs(x[2]) > gAlice->TrackingZmax()) {
713 // --- Add new created particles
714 if (gMC->NSecondaries() > 0) {
715 chproc=gMC->ProdProcess();
716 for (jk = 0; jk < geant3->Gcking()->ngkine; ++jk) {
717 ipp = Int_t (geant3->Gcking()->gkin[jk][4]+0.5);
718 // --- Skip neutrinos!
720 gAlice->SetTrack(1,gAlice->CurrentTrack(),gMC->PDGFromId(ipp), geant3->Gcking()->gkin[jk],
721 geant3->Gckin3()->gpos[jk], polar,geant3->Gctrak()->tofg, chproc, nt);
725 // Cherenkov photons here
726 if ( geant3->Gckin2()->ngphot ) {
727 for (jk = 0; jk < geant3->Gckin2()->ngphot; ++jk) {
728 mom[0]=geant3->Gckin2()->xphot[jk][3]*geant3->Gckin2()->xphot[jk][6];
729 mom[1]=geant3->Gckin2()->xphot[jk][4]*geant3->Gckin2()->xphot[jk][6];
730 mom[2]=geant3->Gckin2()->xphot[jk][5]*geant3->Gckin2()->xphot[jk][6];
731 gAlice->SetTrack(1, gAlice->CurrentTrack(), gMC->PDGFromId(50),
733 geant3->Gckin2()->xphot[jk], //position
734 &geant3->Gckin2()->xphot[jk][7], //polarisation
735 geant3->Gckin2()->xphot[jk][10], //time of flight
739 // --- Particle leaving the setup ?
740 if (!gMC->IsTrackOut())
741 if ((id=gAlice->DetFromMate(geant3->Gctmed()->numed)) >= 0) gAlice->StepManager(id);
743 // --- Standard GEANT debug routine
744 if(geant3->Gcflag()->idebug) geant3->Gdebug();
747 //______________________________________________________________________
751 // ******************************************************************
753 // * Read or Generates Kinematics for primary tracks *
755 // * ==>Called by : GTRIG *
757 // ******************************************************************
760 // ------------------------------------------------------------------
762 gAlice->Generator()->Generate();
766 //______________________________________________________________________
770 // ******************************************************************
772 // * User routine called at the end of the run *
774 // * ==>Called by : GRUN *
776 // ******************************************************************