Added explicit base class declaration
[u/mrichter/AliRoot.git] / STEER / AliRun.cxx
CommitLineData
99d554c8 1/**************************************************************************
2 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
3 * *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
6 * *
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 **************************************************************************/
15
acd84897 16/* $Id$ */
99d554c8 17
fe4da5cc 18///////////////////////////////////////////////////////////////////////////////
19// //
20// Control class for Alice C++ //
21// Only one single instance of this class exists. //
22// The object is created in main program aliroot //
23// and is pointed by the global gAlice. //
24// //
8494b010 25// -Supports the list of all Alice Detectors (fModules). //
fe4da5cc 26// -Supports the list of particles (fParticles). //
27// -Supports the Trees. //
28// -Supports the geometry. //
29// -Supports the event display. //
30//Begin_Html
31/*
1439f98e 32<img src="picts/AliRunClass.gif">
fe4da5cc 33*/
34//End_Html
35//Begin_Html
36/*
1439f98e 37<img src="picts/alirun.gif">
fe4da5cc 38*/
39//End_Html
40// //
41///////////////////////////////////////////////////////////////////////////////
42
88cb7938 43#include <Riostream.h>
94de3818 44#include <stdio.h>
98490ea9 45#include <stdlib.h>
94de3818 46#include <string.h>
47
88cb7938 48#include <TBRIK.h>
49#include <TBrowser.h>
50#include <TCint.h>
51#include <TFile.h>
52#include <TFolder.h>
53#include <TGeometry.h>
54#include <TKey.h>
55#include <TNode.h>
56#include <TObjectTable.h>
57#include <TParticle.h>
58#include <TROOT.h>
59#include <TRandom.h>
60#include <TRandom3.h>
61#include <TSystem.h>
62#include <TTree.h>
63#include <TVirtualMC.h>
98490ea9 64
65#include "AliConfig.h"
66#include "AliDetector.h"
fe4da5cc 67#include "AliDisplay.h"
88cb7938 68#include "AliGenEventHeader.h"
98490ea9 69#include "AliGenerator.h"
70#include "AliHeader.h"
88cb7938 71#include "AliHit.h"
dffd31ef 72#include "AliLego.h"
98490ea9 73#include "AliLegoGenerator.h"
88cb7938 74#include "AliLoader.h"
98490ea9 75#include "AliMCQA.h"
aee8290b 76#include "AliMagFC.h"
77#include "AliMagFCM.h"
78#include "AliMagFDM.h"
141f90e3 79#include "AliPDG.h"
98490ea9 80#include "AliRun.h"
88cb7938 81#include "AliRunLoader.h"
98490ea9 82#include "AliStack.h"
2b22f272 83#include "AliTrackReference.h"
fe4da5cc 84
fe4da5cc 85AliRun *gAlice;
86
fe4da5cc 87ClassImp(AliRun)
88
e2afb3b6 89//_______________________________________________________________________
90AliRun::AliRun():
91 fRun(0),
92 fEvent(0),
93 fEventNrInRun(0),
94 fEventsPerRun(0),
95 fDebug(0),
e2afb3b6 96 fModules(0),
97 fGeometry(0),
98 fDisplay(0),
99 fTimer(),
100 fField(0),
101 fMC(0),
102 fImedia(0),
103 fNdets(0),
104 fTrRmax(1.e10),
105 fTrZmax(1.e10),
106 fGenerator(0),
107 fInitDone(kFALSE),
108 fLego(0),
109 fPDGDB(0), //Particle factory object
110 fHitLists(0),
111 fEventEnergy(0),
112 fSummEnergy(0),
113 fSum2Energy(0),
114 fConfigFunction("\0"),
115 fRandom(0),
116 fMCQA(0),
117 fTransParName("\0"),
2b22f272 118 fRunLoader(0x0),
119 fTrackReferences(0)
fe4da5cc 120{
121 //
122 // Default constructor for AliRun
123 //
88cb7938 124 AliConfig::Instance();//skowron 29 Feb 2002
125 //ensures that the folder structure is build
e2afb3b6 126}
127
128//_______________________________________________________________________
129AliRun::AliRun(const AliRun& arun):
130 TVirtualMCApplication(arun),
131 fRun(0),
132 fEvent(0),
133 fEventNrInRun(0),
134 fEventsPerRun(0),
135 fDebug(0),
e2afb3b6 136 fModules(0),
137 fGeometry(0),
138 fDisplay(0),
139 fTimer(),
140 fField(0),
141 fMC(0),
142 fImedia(0),
143 fNdets(0),
144 fTrRmax(1.e10),
145 fTrZmax(1.e10),
146 fGenerator(0),
147 fInitDone(kFALSE),
148 fLego(0),
149 fPDGDB(0), //Particle factory object
150 fHitLists(0),
151 fEventEnergy(0),
152 fSummEnergy(0),
153 fSum2Energy(0),
154 fConfigFunction("\0"),
155 fRandom(0),
156 fMCQA(0),
2b22f272 157 fTransParName("\0"),
158 fTrackReferences(new TClonesArray("AliTrackReference", 100)),
88cb7938 159 fRunLoader(0x0)
e2afb3b6 160{
161 //
162 // Copy constructor for AliRun
163 //
164 arun.Copy(*this);
fe4da5cc 165}
166
167//_____________________________________________________________________________
e2afb3b6 168AliRun::AliRun(const char *name, const char *title):
169 TVirtualMCApplication(name,title),
170 fRun(0),
171 fEvent(0),
172 fEventNrInRun(0),
173 fEventsPerRun(0),
174 fDebug(0),
e2afb3b6 175 fModules(new TObjArray(77)), // Support list for the Detectors
176 fGeometry(0),
177 fDisplay(0),
178 fTimer(),
179 fField(0),
180 fMC(gMC),
181 fImedia(new TArrayI(1000)),
182 fNdets(0),
183 fTrRmax(1.e10),
184 fTrZmax(1.e10),
185 fGenerator(0),
186 fInitDone(kFALSE),
187 fLego(0),
188 fPDGDB(TDatabasePDG::Instance()), //Particle factory object!
189 fHitLists(new TList()), // Create HitLists list
190 fEventEnergy(0),
191 fSummEnergy(0),
192 fSum2Energy(0),
193 fConfigFunction("Config();"),
194 fRandom(new TRandom3()),
195 fMCQA(0),
196 fTransParName("\0"),
88cb7938 197 fRunLoader(0x0)
fe4da5cc 198{
199 //
200 // Constructor for the main processor.
201 // Creates the geometry
202 // Creates the list of Detectors.
203 // Creates the list of particles.
204 //
e2afb3b6 205
fe4da5cc 206 gAlice = this;
65fb704d 207
208 // Set random number generator
e2afb3b6 209 gRandom = fRandom;
2ab0c725 210
211 if (gSystem->Getenv("CONFIG_SEED")) {
e2afb3b6 212 gRandom->SetSeed(static_cast<UInt_t>(atoi(gSystem->Getenv("CONFIG_SEED"))));
2ab0c725 213 }
e2afb3b6 214
215 // Add to list of browsable
fe4da5cc 216 gROOT->GetListOfBrowsables()->Add(this,name);
fe4da5cc 217 // Create the TNode geometry for the event display
fe4da5cc 218 BuildSimpleGeometry();
219
fe4da5cc 220 // Create default mag field
221 SetField();
e2afb3b6 222
fe4da5cc 223 // Prepare the tracking medium lists
e2afb3b6 224 for(Int_t i=0;i<1000;i++) (*fImedia)[i]=-99;
9e1a0ddb 225
e2afb3b6 226 // Add particle list to configuration
9e1a0ddb 227 AliConfig::Instance()->Add(fPDGDB);
e2afb3b6 228
229 // Set transport parameters
65fb704d 230 SetTransPar();
fe4da5cc 231}
232
aee8290b 233
e2afb3b6 234//_______________________________________________________________________
fe4da5cc 235AliRun::~AliRun()
236{
237 //
2ab0c725 238 // Default AliRun destructor
fe4da5cc 239 //
88cb7938 240 gROOT->GetListOfBrowsables()->Remove(this);
241
242 if (fRunLoader)
243 {
244 TFolder* evfold = fRunLoader->GetEventFolder();
245 TFolder* modfold = dynamic_cast<TFolder*>(evfold->FindObjectAny(AliConfig::GetModulesFolderName()));
246 TIter next(fModules);
247 AliModule *mod;
248 while((mod = (AliModule*)next()))
249 {
250 modfold->Remove(mod);
251 }
252 }
253
fe4da5cc 254 delete fImedia;
255 delete fField;
f5bc1485 256 // delete fMC;
257 delete gMC; gMC=0;
fe4da5cc 258 delete fGeometry;
259 delete fDisplay;
260 delete fGenerator;
261 delete fLego;
8494b010 262 if (fModules) {
263 fModules->Delete();
264 delete fModules;
fe4da5cc 265 }
88cb7938 266
1cedd08a 267 delete fHitLists;
c222d2b0 268 delete fPDGDB;
e460afec 269 delete fMCQA;
2b22f272 270 // Delete track references
271 if (fTrackReferences) {
272 fTrackReferences->Delete();
273 delete fTrackReferences;
274 fTrackReferences = 0;
275 }
276
fe4da5cc 277}
278
e2afb3b6 279//_______________________________________________________________________
280void AliRun::Copy(AliRun &) const
281{
282 Fatal("Copy","Not implemented!\n");
283}
284
285//_______________________________________________________________________
fe4da5cc 286void AliRun::AddHit(Int_t id, Int_t track, Int_t *vol, Float_t *hits) const
287{
288 //
289 // Add a hit to detector id
290 //
8494b010 291 TObjArray &dets = *fModules;
e2afb3b6 292 if(dets[id]) dynamic_cast<AliModule*>(dets[id])->AddHit(track,vol,hits);
fe4da5cc 293}
294
e2afb3b6 295//_______________________________________________________________________
fe4da5cc 296void AliRun::AddDigit(Int_t id, Int_t *tracks, Int_t *digits) const
297{
298 //
299 // Add digit to detector id
300 //
8494b010 301 TObjArray &dets = *fModules;
e2afb3b6 302 if(dets[id]) dynamic_cast<AliModule*>(dets[id])->AddDigit(tracks,digits);
fe4da5cc 303}
304
e2afb3b6 305//_______________________________________________________________________
fe4da5cc 306void AliRun::Browse(TBrowser *b)
307{
308 //
309 // Called when the item "Run" is clicked on the left pane
310 // of the Root browser.
311 // It displays the Root Trees and all detectors.
312 //
88cb7938 313 //detectors are in folders anyway
65fb704d 314 b->Add(fMCQA,"AliMCQA");
fe4da5cc 315}
316
e2afb3b6 317//_______________________________________________________________________
fe4da5cc 318void AliRun::Build()
319{
320 //
321 // Initialize Alice geometry
322 // Dummy routine
323 //
324}
325
e2afb3b6 326//_______________________________________________________________________
fe4da5cc 327void AliRun::BuildSimpleGeometry()
328{
329 //
330 // Create a simple TNode geometry used by Root display engine
331 //
332 // Initialise geometry
333 //
334 fGeometry = new TGeometry("AliceGeom","Galice Geometry for Hits");
335 new TMaterial("void","Vacuum",0,0,0); //Everything is void
336 TBRIK *brik = new TBRIK("S_alice","alice volume","void",2000,2000,3000);
337 brik->SetVisibility(0);
338 new TNode("alice","alice","S_alice");
339}
340
e2afb3b6 341//_______________________________________________________________________
fe4da5cc 342void AliRun::CleanDetectors()
343{
344 //
345 // Clean Detectors at the end of event
346 //
88cb7938 347 fRunLoader->CleanDetectors();
fe4da5cc 348}
349
e2afb3b6 350//_______________________________________________________________________
116cbefd 351Int_t AliRun::DistancetoPrimitive(Int_t, Int_t) const
fe4da5cc 352{
353 //
354 // Return the distance from the mouse to the AliRun object
355 // Dummy routine
356 //
357 return 9999;
358}
359
e2afb3b6 360//_______________________________________________________________________
94de3818 361void AliRun::DumpPart (Int_t i) const
fe4da5cc 362{
363 //
364 // Dumps particle i in the stack
365 //
88cb7938 366 if (fRunLoader->Stack())
367 fRunLoader->Stack()->DumpPart(i);
fe4da5cc 368}
369
e2afb3b6 370//_______________________________________________________________________
94de3818 371void AliRun::DumpPStack () const
fe4da5cc 372{
373 //
374 // Dumps the particle stack
375 //
88cb7938 376 if (fRunLoader->Stack())
377 fRunLoader->Stack()->DumpPStack();
fe4da5cc 378}
379
e2afb3b6 380//_______________________________________________________________________
d8408e76 381void AliRun::SetField(AliMagF* magField)
382{
383 // Set Magnetic Field Map
384 fField = magField;
385 fField->ReadField();
386}
387
e2afb3b6 388//_______________________________________________________________________
fe4da5cc 389void AliRun::SetField(Int_t type, Int_t version, Float_t scale,
390 Float_t maxField, char* filename)
391{
392 //
393 // Set magnetic field parameters
394 // type Magnetic field transport flag 0=no field, 2=helix, 3=Runge Kutta
395 // version Magnetic field map version (only 1 active now)
396 // scale Scale factor for the magnetic field
397 // maxField Maximum value for the magnetic field
398
399 //
400 // --- Sanity check on mag field flags
fe4da5cc 401 if(fField) delete fField;
402 if(version==1) {
d8408e76 403 fField = new AliMagFC("Map1"," ",type,scale,maxField);
f1b9d7c3 404 } else if(version<=2) {
d8408e76 405 fField = new AliMagFCM("Map2-3",filename,type,scale,maxField);
fe4da5cc 406 fField->ReadField();
f1b9d7c3 407 } else if(version==3) {
d8408e76 408 fField = new AliMagFDM("Map4",filename,type,scale,maxField);
f1b9d7c3 409 fField->ReadField();
fe4da5cc 410 } else {
23370b7a 411 Warning("SetField","Invalid map %d\n",version);
fe4da5cc 412 }
413}
88cb7938 414
415//_____________________________________________________________________________
416
417void AliRun::InitLoaders()
418{
419 //creates list of getters
420 if (GetDebug()) Info("InitLoaders","");
421 TIter next(fModules);
422 AliModule *mod;
423 while((mod = (AliModule*)next()))
424 {
425 AliDetector *det = dynamic_cast<AliDetector*>(mod);
426 if (det)
427 {
428 if (GetDebug()) Info("InitLoaders"," Adding %s ",det->GetName());
429 fRunLoader->AddLoader(det);
430 }
431 }
432 if (GetDebug()) Info("InitLoaders","Done");
433}
434//_____________________________________________________________________________
435
fe4da5cc 436void AliRun::FinishRun()
437{
438 //
439 // Called at the end of the run.
440 //
88cb7938 441
88cb7938 442 if(fLego)
443 {
444 if (GetDebug()) Info("FinishRun"," Finish Lego");
445 fRunLoader->CdGAFile();
446 fLego->FinishRun();
447 }
8e70f139 448
fe4da5cc 449 // Clean detector information
8494b010 450 TIter next(fModules);
451 AliModule *detector;
e2afb3b6 452 while((detector = dynamic_cast<AliModule*>(next()))) {
88cb7938 453 if (GetDebug()) Info("FinishRun"," %s->FinishRun()",detector->GetName());
fe4da5cc 454 detector->FinishRun();
455 }
456
457 //Output energy summary tables
88cb7938 458 if (GetDebug()) Info("FinishRun"," EnergySummary()");
fe4da5cc 459 EnergySummary();
fe4da5cc 460
88cb7938 461 if (GetDebug()) Info("FinishRun"," fRunLoader->WriteHeader(OVERWRITE)");
462 fRunLoader->WriteHeader("OVERWRITE");
682a4a95 463
88cb7938 464 // Write AliRun info and all detectors parameters
465 fRunLoader->CdGAFile();
466 Write(0,TObject::kOverwrite);//write AliRun
467 fRunLoader->Write(0,TObject::kOverwrite);//write RunLoader itself
468
fe4da5cc 469 // Clean tree information
88cb7938 470 if (GetDebug()) Info("FinishRun"," fRunLoader->Stack()->FinishRun()");
471 fRunLoader->Stack()->FinishRun();
9e1a0ddb 472
88cb7938 473 // Clean detector information
474 if (GetDebug()) Info("FinishRun"," fGenerator->FinishRun()");
6df200c3 475 fGenerator->FinishRun();
f0f6f856 476 fRunLoader->Synchronize();
fe4da5cc 477}
478
e2afb3b6 479//_______________________________________________________________________
fe4da5cc 480void AliRun::FlagTrack(Int_t track)
481{
9e1a0ddb 482 // Delegate to stack
fe4da5cc 483 //
88cb7938 484 fRunLoader->Stack()->FlagTrack(track);
fe4da5cc 485}
486
e2afb3b6 487//_______________________________________________________________________
fe4da5cc 488void AliRun::EnergySummary()
489{
490 //
491 // Print summary of deposited energy
492 //
493
fe4da5cc 494 Int_t ndep=0;
495 Float_t edtot=0;
496 Float_t ed, ed2;
497 Int_t kn, i, left, j, id;
aee8290b 498 const Float_t kzero=0;
88cb7938 499 Int_t ievent=fRunLoader->GetHeader()->GetEvent()+1;
fe4da5cc 500 //
501 // Energy loss information
502 if(ievent) {
503 printf("***************** Energy Loss Information per event (GEV) *****************\n");
875c717b 504 for(kn=1;kn<fEventEnergy.GetSize();kn++) {
505 ed=fSummEnergy[kn];
fe4da5cc 506 if(ed>0) {
875c717b 507 fEventEnergy[ndep]=kn;
fe4da5cc 508 if(ievent>1) {
509 ed=ed/ievent;
875c717b 510 ed2=fSum2Energy[kn];
fe4da5cc 511 ed2=ed2/ievent;
aee8290b 512 ed2=100*TMath::Sqrt(TMath::Max(ed2-ed*ed,kzero))/ed;
fe4da5cc 513 } else
514 ed2=99;
875c717b 515 fSummEnergy[ndep]=ed;
e2afb3b6 516 fSum2Energy[ndep]=TMath::Min(static_cast<Float_t>(99.),TMath::Max(ed2,kzero));
fe4da5cc 517 edtot+=ed;
518 ndep++;
519 }
520 }
521 for(kn=0;kn<(ndep-1)/3+1;kn++) {
522 left=ndep-kn*3;
523 for(i=0;i<(3<left?3:left);i++) {
524 j=kn*3+i;
875c717b 525 id=Int_t (fEventEnergy[j]+0.1);
526 printf(" %s %10.3f +- %10.3f%%;",gMC->VolName(id),fSummEnergy[j],fSum2Energy[j]);
fe4da5cc 527 }
528 printf("\n");
529 }
530 //
531 // Relative energy loss in different detectors
532 printf("******************** Relative Energy Loss per event ********************\n");
533 printf("Total energy loss per event %10.3f GeV\n",edtot);
534 for(kn=0;kn<(ndep-1)/5+1;kn++) {
535 left=ndep-kn*5;
536 for(i=0;i<(5<left?5:left);i++) {
537 j=kn*5+i;
875c717b 538 id=Int_t (fEventEnergy[j]+0.1);
539 printf(" %s %10.3f%%;",gMC->VolName(id),100*fSummEnergy[j]/edtot);
fe4da5cc 540 }
541 printf("\n");
542 }
543 for(kn=0;kn<75;kn++) printf("*");
544 printf("\n");
545 }
546 //
547 // Reset the TArray's
875c717b 548 // fEventEnergy.Set(0);
549 // fSummEnergy.Set(0);
550 // fSum2Energy.Set(0);
fe4da5cc 551}
552
e2afb3b6 553//_______________________________________________________________________
eb1b8d29 554void AliRun::Announce() const
555{
556 //
37d06d5b 557 // Announce the current version of AliRoot
558 //
559 printf("%70s",
560 "****************************************************************\n");
561 printf("%6s","*");printf("%64s","*\n");
562
563 printf("%6s","*");
88cb7938 564 printf(" You are running AliRoot version NewIO\n");
37d06d5b 565
566 printf("%6s","*");
567 printf(" The cvs tag for the current program is $Name$\n");
568
569 printf("%6s","*");printf("%64s","*\n");
570 printf("%70s",
571 "****************************************************************\n");
eb1b8d29 572}
573
574//_______________________________________________________________________
94de3818 575AliModule *AliRun::GetModule(const char *name) const
fe4da5cc 576{
577 //
578 // Return pointer to detector from name
579 //
e2afb3b6 580 return dynamic_cast<AliModule*>(fModules->FindObject(name));
fe4da5cc 581}
582
e2afb3b6 583//_______________________________________________________________________
94de3818 584AliDetector *AliRun::GetDetector(const char *name) const
a68348e9 585{
586 //
587 // Return pointer to detector from name
588 //
e2afb3b6 589 return dynamic_cast<AliDetector*>(fModules->FindObject(name));
a68348e9 590}
591
e2afb3b6 592//_______________________________________________________________________
94de3818 593Int_t AliRun::GetModuleID(const char *name) const
fe4da5cc 594{
595 //
596 // Return galice internal detector identifier from name
597 //
23370b7a 598 Int_t i=-1;
599 TObject *mod=fModules->FindObject(name);
600 if(mod) i=fModules->IndexOf(mod);
601 return i;
fe4da5cc 602}
603
e2afb3b6 604//_______________________________________________________________________
fe4da5cc 605Int_t AliRun::GetEvent(Int_t event)
606{
88cb7938 607//
608// Reloads data containers in folders # event
609// Set branch addresses
610//
611 if (fRunLoader == 0x0)
612 {
613 Error("GetEvent","RunLoader is not set. Can not load data.");
614 return -1;
615 }
616/*****************************************/
617/**** P R E R E L O A D I N G ****/
618/*****************************************/
619// Reset existing structures
fe4da5cc 620 ResetHits();
aab9c8d5 621 ResetTrackReferences();
fe4da5cc 622 ResetDigits();
2ab0c725 623 ResetSDigits();
50a6540a 624
88cb7938 625/*****************************************/
626/**** R E L O A D ****/
627/*****************************************/
aab9c8d5 628
88cb7938 629 fRunLoader->GetEvent(event);
b9d0a01d 630
88cb7938 631/*****************************************/
632/**** P O S T R E L O A D I N G ****/
633/*****************************************/
82711e7a 634
fe4da5cc 635 // Set Trees branch addresses
8494b010 636 TIter next(fModules);
637 AliModule *detector;
88cb7938 638 while((detector = dynamic_cast<AliModule*>(next())))
639 {
640 detector->SetTreeAddress();
641 }
642
643 return fRunLoader->GetHeader()->GetNtrack();
fe4da5cc 644}
645
e2afb3b6 646//_______________________________________________________________________
fe4da5cc 647TGeometry *AliRun::GetGeometry()
648{
649 //
650 // Import Alice geometry from current file
651 // Return pointer to geometry object
652 //
e2afb3b6 653 if (!fGeometry) fGeometry = dynamic_cast<TGeometry*>(gDirectory->Get("AliceGeom"));
fe4da5cc 654 //
655 // Unlink and relink nodes in detectors
656 // This is bad and there must be a better way...
657 //
fe4da5cc 658
8494b010 659 TIter next(fModules);
660 AliModule *detector;
e2afb3b6 661 while((detector = dynamic_cast<AliModule*>(next()))) {
fe4da5cc 662 TList *dnodes=detector->Nodes();
663 Int_t j;
664 TNode *node, *node1;
665 for ( j=0; j<dnodes->GetSize(); j++) {
e2afb3b6 666 node = dynamic_cast<TNode*>(dnodes->At(j));
52d0ab00 667 node1 = fGeometry->GetNode(node->GetName());
fe4da5cc 668 dnodes->Remove(node);
669 dnodes->AddAt(node1,j);
670 }
671 }
672 return fGeometry;
673}
674
e2afb3b6 675//_______________________________________________________________________
9e1a0ddb 676Int_t AliRun::GetPrimary(Int_t track) const
fe4da5cc 677{
678 //
679 // return number of primary that has generated track
680 //
88cb7938 681 return fRunLoader->Stack()->GetPrimary(track);
fe4da5cc 682}
683
e2afb3b6 684//_______________________________________________________________________
fe4da5cc 685void AliRun::MediaTable()
686{
687 //
688 // Built media table to get from the media number to
689 // the detector id
690 //
88cb7938 691
ad51aeb0 692 Int_t kz, nz, idt, lz, i, k, ind;
693 // Int_t ibeg;
fe4da5cc 694 TObjArray &dets = *gAlice->Detectors();
8494b010 695 AliModule *det;
fe4da5cc 696 //
697 // For all detectors
698 for (kz=0;kz<fNdets;kz++) {
699 // If detector is defined
e2afb3b6 700 if((det=dynamic_cast<AliModule*>(dets[kz]))) {
ad51aeb0 701 TArrayI &idtmed = *(det->GetIdtmed());
702 for(nz=0;nz<100;nz++) {
fe4da5cc 703 // Find max and min material number
ad51aeb0 704 if((idt=idtmed[nz])) {
fe4da5cc 705 det->LoMedium() = det->LoMedium() < idt ? det->LoMedium() : idt;
706 det->HiMedium() = det->HiMedium() > idt ? det->HiMedium() : idt;
707 }
708 }
709 if(det->LoMedium() > det->HiMedium()) {
710 det->LoMedium() = 0;
711 det->HiMedium() = 0;
712 } else {
713 if(det->HiMedium() > fImedia->GetSize()) {
ad51aeb0 714 Error("MediaTable","Increase fImedia from %d to %d",
715 fImedia->GetSize(),det->HiMedium());
fe4da5cc 716 return;
717 }
718 // Tag all materials in rage as belonging to detector kz
719 for(lz=det->LoMedium(); lz<= det->HiMedium(); lz++) {
720 (*fImedia)[lz]=kz;
721 }
722 }
723 }
724 }
725 //
726 // Print summary table
727 printf(" Traking media ranges:\n");
728 for(i=0;i<(fNdets-1)/6+1;i++) {
729 for(k=0;k< (6<fNdets-i*6?6:fNdets-i*6);k++) {
730 ind=i*6+k;
e2afb3b6 731 det=dynamic_cast<AliModule*>(dets[ind]);
fe4da5cc 732 if(det)
733 printf(" %6s: %3d -> %3d;",det->GetName(),det->LoMedium(),
734 det->HiMedium());
735 else
736 printf(" %6s: %3d -> %3d;","NULL",0,0);
737 }
738 printf("\n");
739 }
740}
741
e2afb3b6 742//_______________________________________________________________________
fe4da5cc 743void AliRun::SetGenerator(AliGenerator *generator)
744{
745 //
746 // Load the event generator
747 //
ee1dd322 748 if(!fGenerator) fGenerator = generator;
749}
750
e2afb3b6 751//_______________________________________________________________________
ee1dd322 752void AliRun::ResetGenerator(AliGenerator *generator)
753{
754 //
755 // Load the event generator
756 //
b13db077 757 if(fGenerator)
838edcaf 758 if(generator)
759 Warning("ResetGenerator","Replacing generator %s with %s\n",
760 fGenerator->GetName(),generator->GetName());
761 else
762 Warning("ResetGenerator","Replacing generator %s with NULL\n",
763 fGenerator->GetName());
b13db077 764 fGenerator = generator;
fe4da5cc 765}
766
e2afb3b6 767//_______________________________________________________________________
768void AliRun::SetTransPar(const char *filename)
65fb704d 769{
37d06d5b 770 //
771 // Sets the file name for transport parameters
772 //
65fb704d 773 fTransParName = filename;
774}
775
e2afb3b6 776//_______________________________________________________________________
777void AliRun::SetBaseFile(const char *filename)
2ab0c725 778{
39de14fb 779 fBaseFileName = filename;
2ab0c725 780}
781
e2afb3b6 782//_______________________________________________________________________
65fb704d 783void AliRun::ReadTransPar()
fe4da5cc 784{
785 //
786 // Read filename to set the transport parameters
787 //
788
fe4da5cc 789
aee8290b 790 const Int_t kncuts=10;
791 const Int_t knflags=11;
792 const Int_t knpars=kncuts+knflags;
793 const char kpars[knpars][7] = {"CUTGAM" ,"CUTELE","CUTNEU","CUTHAD","CUTMUO",
fe4da5cc 794 "BCUTE","BCUTM","DCUTE","DCUTM","PPCUTM","ANNI",
795 "BREM","COMP","DCAY","DRAY","HADR","LOSS",
796 "MULS","PAIR","PHOT","RAYL"};
797 char line[256];
ad51aeb0 798 char detName[7];
fe4da5cc 799 char* filtmp;
aee8290b 800 Float_t cut[kncuts];
801 Int_t flag[knflags];
fe4da5cc 802 Int_t i, itmed, iret, ktmed, kz;
803 FILE *lun;
804 //
805 // See whether the file is there
65fb704d 806 filtmp=gSystem->ExpandPathName(fTransParName.Data());
fe4da5cc 807 lun=fopen(filtmp,"r");
808 delete [] filtmp;
809 if(!lun) {
65fb704d 810 Warning("ReadTransPar","File %s does not exist!\n",fTransParName.Data());
fe4da5cc 811 return;
812 }
813 //
9e1a0ddb 814 if(fDebug) {
815 printf(" "); for(i=0;i<60;i++) printf("*"); printf("\n");
816 printf(" *%59s\n","*");
817 printf(" * Please check carefully what you are doing!%10s\n","*");
818 printf(" *%59s\n","*");
819 }
fe4da5cc 820 //
821 while(1) {
822 // Initialise cuts and flags
aee8290b 823 for(i=0;i<kncuts;i++) cut[i]=-99;
824 for(i=0;i<knflags;i++) flag[i]=-99;
fe4da5cc 825 itmed=0;
826 for(i=0;i<256;i++) line[i]='\0';
827 // Read up to the end of line excluded
828 iret=fscanf(lun,"%[^\n]",line);
829 if(iret<0) {
830 //End of file
831 fclose(lun);
9e1a0ddb 832 if(fDebug){
833 printf(" *%59s\n","*");
834 printf(" "); for(i=0;i<60;i++) printf("*"); printf("\n");
835 }
fe4da5cc 836 return;
837 }
838 // Read the end of line
839 fscanf(lun,"%*c");
840 if(!iret) continue;
841 if(line[0]=='*') continue;
842 // Read the numbers
ad51aeb0 843 iret=sscanf(line,"%s %d %f %f %f %f %f %f %f %f %f %f %d %d %d %d %d %d %d %d %d %d %d",
844 detName,&itmed,&cut[0],&cut[1],&cut[2],&cut[3],&cut[4],&cut[5],&cut[6],&cut[7],&cut[8],
845 &cut[9],&flag[0],&flag[1],&flag[2],&flag[3],&flag[4],&flag[5],&flag[6],&flag[7],
846 &flag[8],&flag[9],&flag[10]);
fe4da5cc 847 if(!iret) continue;
848 if(iret<0) {
849 //reading error
65fb704d 850 Warning("ReadTransPar","Error reading file %s\n",fTransParName.Data());
fe4da5cc 851 continue;
852 }
ad51aeb0 853 // Check that the module exist
854 AliModule *mod = GetModule(detName);
855 if(mod) {
856 // Get the array of media numbers
857 TArrayI &idtmed = *mod->GetIdtmed();
858 // Check that the tracking medium code is valid
859 if(0<=itmed && itmed < 100) {
860 ktmed=idtmed[itmed];
861 if(!ktmed) {
65fb704d 862 Warning("ReadTransPar","Invalid tracking medium code %d for %s\n",itmed,mod->GetName());
ad51aeb0 863 continue;
fe4da5cc 864 }
ad51aeb0 865 // Set energy thresholds
aee8290b 866 for(kz=0;kz<kncuts;kz++) {
ad51aeb0 867 if(cut[kz]>=0) {
9e1a0ddb 868 if(fDebug) printf(" * %-6s set to %10.3E for tracking medium code %4d for %s\n",
aee8290b 869 kpars[kz],cut[kz],itmed,mod->GetName());
870 gMC->Gstpar(ktmed,kpars[kz],cut[kz]);
ad51aeb0 871 }
fe4da5cc 872 }
ad51aeb0 873 // Set transport mechanisms
aee8290b 874 for(kz=0;kz<knflags;kz++) {
ad51aeb0 875 if(flag[kz]>=0) {
9e1a0ddb 876 if(fDebug) printf(" * %-6s set to %10d for tracking medium code %4d for %s\n",
aee8290b 877 kpars[kncuts+kz],flag[kz],itmed,mod->GetName());
878 gMC->Gstpar(ktmed,kpars[kncuts+kz],Float_t(flag[kz]));
ad51aeb0 879 }
880 }
881 } else {
65fb704d 882 Warning("ReadTransPar","Invalid medium code %d *\n",itmed);
ad51aeb0 883 continue;
fe4da5cc 884 }
885 } else {
9e1a0ddb 886 if(fDebug) printf("%s::ReadTransParModule: %s not present\n",ClassName(),detName);
fe4da5cc 887 continue;
888 }
889 }
890}
88cb7938 891//_____________________________________________________________________________
fe4da5cc 892
88cb7938 893void AliRun::BeginEvent()
fe4da5cc 894{
895 //
88cb7938 896 // Clean-up previous event
897 // Energy scores
898 if (GetDebug())
899 {
900 Info("BeginEvent",">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
901 Info("BeginEvent",">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
902 Info("BeginEvent",">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
903 Info("BeginEvent"," BEGINNING EVENT ");
904 Info("BeginEvent",">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
905 Info("BeginEvent",">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
906 Info("BeginEvent",">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>");
907 }
908
909 /*******************************/
910 /* Clean after eventual */
911 /* previous event */
912 /*******************************/
9e1a0ddb 913
2ab0c725 914
88cb7938 915 //Set the next event in Run Loader -> Cleans trees (TreeK and all trees in detectors),
916 fRunLoader->SetEventNumber(++fEventNrInRun);// sets new files, cleans the previous event stuff, if necessary, etc.,
917 if (GetDebug()) Info("BeginEvent","EventNr is %d",fEventNrInRun);
918
919 fEventEnergy.Reset();
920 // Clean detector information
9e1a0ddb 921
88cb7938 922 if (fRunLoader->Stack())
923 fRunLoader->Stack()->Reset();//clean stack -> tree is unloaded
924 else
925 fRunLoader->MakeStack();//or make a new one
926
927 if (GetDebug()) Info("BeginEvent"," fRunLoader->MakeTree(K)");
928 fRunLoader->MakeTree("K");
929 if (GetDebug()) Info("BeginEvent"," gMC->SetStack(fRunLoader->Stack())");
930 gMC->SetStack(fRunLoader->Stack());//Was in InitMC - but was moved here
931 //because we don't have guarantee that
932 //stack pointer is not going to change from event to event
933 //since it bellobgs to header and is obtained via RunLoader
934 //
935 // Reset all Detectors & kinematics & make/reset trees
936 //
937
938 fRunLoader->GetHeader()->Reset(fRun,fEvent,fEventNrInRun);
939// fRunLoader->WriteKinematics("OVERWRITE"); is there any reason to rewrite here since MakeTree does so
aab9c8d5 940
88cb7938 941 if (GetDebug()) Info("BeginEvent"," fRunLoader->MakeTrackRefsContainer()");
942 fRunLoader->MakeTrackRefsContainer();//for insurance
aab9c8d5 943
88cb7938 944 if (GetDebug()) Info("BeginEvent"," ResetHits()");
945 ResetHits();
946 if (GetDebug()) Info("BeginEvent"," fRunLoader->MakeTree(H)");
947 fRunLoader->MakeTree("H");
9e1a0ddb 948
fe4da5cc 949 //
88cb7938 950 if(fLego)
951 {
952 fLego->BeginEvent();
953 return;
954 }
955
956 //create new branches and SetAdresses
8494b010 957 TIter next(fModules);
958 AliModule *detector;
88cb7938 959 while((detector = (AliModule*)next()))
960 {
961 if (GetDebug()) Info("BeginEvent"," %s->MakeBranch(H)",detector->GetName());
962 detector->MakeBranch("H");
963 if (GetDebug()) Info("BeginEvent"," %s->MakeBranchTR()",detector->GetName());
964 detector->MakeBranchTR();
965 if (GetDebug()) Info("BeginEvent"," %s->SetTreeAddress()",detector->GetName());
966 detector->SetTreeAddress();
967 }
2b22f272 968 // make branch for AliRun track References
969 TTree * treeTR = fRunLoader->TreeTR();
970 if (treeTR){
971 // make branch for central track references
972 if (!fTrackReferences) fTrackReferences = new TClonesArray("AliTrackReference",0);
973 TBranch *branch;
974 branch = treeTR->Branch("AliRun",&fTrackReferences);
975 branch->SetAddress(&fTrackReferences);
976 }
977 //
fe4da5cc 978}
979
e2afb3b6 980//_______________________________________________________________________
37d06d5b 981TParticle* AliRun::Particle(Int_t i) const
2ab0c725 982{
88cb7938 983 if (fRunLoader)
984 if (fRunLoader->Stack())
985 return fRunLoader->Stack()->Particle(i);
986 return 0x0;
fe4da5cc 987}
988
e2afb3b6 989//_______________________________________________________________________
fe4da5cc 990void AliRun::ResetDigits()
991{
992 //
993 // Reset all Detectors digits
994 //
8494b010 995 TIter next(fModules);
996 AliModule *detector;
e2afb3b6 997 while((detector = dynamic_cast<AliModule*>(next()))) {
fe4da5cc 998 detector->ResetDigits();
999 }
1000}
1001
e2afb3b6 1002//_______________________________________________________________________
2ab0c725 1003void AliRun::ResetSDigits()
1004{
1005 //
1006 // Reset all Detectors digits
1007 //
1008 TIter next(fModules);
1009 AliModule *detector;
e2afb3b6 1010 while((detector = dynamic_cast<AliModule*>(next()))) {
2ab0c725 1011 detector->ResetSDigits();
1012 }
1013}
1014
e2afb3b6 1015//_______________________________________________________________________
fe4da5cc 1016void AliRun::ResetHits()
1017{
1018 //
1019 // Reset all Detectors hits
1020 //
8494b010 1021 TIter next(fModules);
1022 AliModule *detector;
e2afb3b6 1023 while((detector = dynamic_cast<AliModule*>(next()))) {
fe4da5cc 1024 detector->ResetHits();
1025 }
1026}
e2afb3b6 1027//_______________________________________________________________________
88cb7938 1028
2b22f272 1029void AliRun::AddTrackReference(Int_t label){
1030 //
1031 // add a trackrefernce to the list
1032 if (!fTrackReferences) {
1033 cerr<<"Container trackrefernce not active\n";
1034 return;
1035 }
1036 Int_t nref = fTrackReferences->GetEntriesFast();
1037 TClonesArray &lref = *fTrackReferences;
1038 new(lref[nref]) AliTrackReference(label);
1039}
1040
1041
1042
aab9c8d5 1043void AliRun::ResetTrackReferences()
1044{
1045 //
2b22f272 1046 // Reset all references
aab9c8d5 1047 //
2b22f272 1048 if (fTrackReferences) fTrackReferences->Clear();
1049
aab9c8d5 1050 TIter next(fModules);
1051 AliModule *detector;
e2afb3b6 1052 while((detector = dynamic_cast<AliModule*>(next()))) {
aab9c8d5 1053 detector->ResetTrackReferences();
1054 }
1055}
2b22f272 1056
1057void AliRun::RemapTrackReferencesIDs(Int_t *map)
1058{
1059 //
1060 // Remapping track reference
1061 // Called at finish primary
1062 //
1063 if (!fTrackReferences) return;
1064 for (Int_t i=0;i<fTrackReferences->GetEntries();i++){
1065 AliTrackReference * ref = dynamic_cast<AliTrackReference*>(fTrackReferences->UncheckedAt(i));
1066 if (ref) {
1067 Int_t newID = map[ref->GetTrack()];
1068 if (newID>=0) ref->SetTrack(newID);
1069 else {
1070 //ref->SetTrack(-1);
1071 ref->SetBit(kNotDeleted,kFALSE);
1072 fTrackReferences->RemoveAt(i);
1073 }
1074 }
1075 }
1076 fTrackReferences->Compress();
1077}
1078
1079
1080
e2afb3b6 1081//_______________________________________________________________________
88cb7938 1082
fe4da5cc 1083void AliRun::ResetPoints()
1084{
1085 //
1086 // Reset all Detectors points
1087 //
8494b010 1088 TIter next(fModules);
1089 AliModule *detector;
e2afb3b6 1090 while((detector = dynamic_cast<AliModule*>(next()))) {
fe4da5cc 1091 detector->ResetPoints();
1092 }
1093}
e2afb3b6 1094//_______________________________________________________________________
88cb7938 1095
b9d0a01d 1096void AliRun::InitMC(const char *setup)
1097{
1098 //
1099 // Initialize the Alice setup
1100 //
37d06d5b 1101 Announce();
1102
b9d0a01d 1103 if(fInitDone) {
1104 Warning("Init","Cannot initialise AliRun twice!\n");
1105 return;
1106 }
1107
1108 gROOT->LoadMacro(setup);
1109 gInterpreter->ProcessLine(fConfigFunction.Data());
1110
1111 // Register MC in configuration
1112 AliConfig::Instance()->Add(gMC);
88cb7938 1113
1114 InitLoaders();
1115
1116 fRunLoader->MakeTree("E");
1117 fRunLoader->LoadKinematics("RECREATE");
1118 fRunLoader->LoadTrackRefs("RECREATE");
1119 fRunLoader->LoadHits("all","RECREATE");
1120
1121
1122 fRunLoader->CdGAFile();
b9d0a01d 1123
1124 gMC->DefineParticles(); //Create standard MC particles
141f90e3 1125 AliPDG::AddParticlesToPdgDataBase();
b9d0a01d 1126
1127 TObject *objfirst, *objlast;
1128
1129 fNdets = fModules->GetLast()+1;
1130
1131 //
1132 //=================Create Materials and geometry
1133 gMC->Init();
1134
1135 // Added also after in case of interactive initialisation of modules
1136 fNdets = fModules->GetLast()+1;
1137
88cb7938 1138 TIter next(fModules);
1139 AliModule *detector;
1140 while((detector = dynamic_cast<AliModule*>(next())))
1141 {
1142 objlast = gDirectory->GetList()->Last();
b9d0a01d 1143
88cb7938 1144 // Add Detector histograms in Detector list of histograms
1145 if (objlast) objfirst = gDirectory->GetList()->After(objlast);
1146 else objfirst = gDirectory->GetList()->First();
1147 while (objfirst)
1148 {
b9d0a01d 1149 detector->Histograms()->Add(objfirst);
1150 objfirst = gDirectory->GetList()->After(objfirst);
1151 }
1152 }
1153 ReadTransPar(); //Read the cuts for all materials
1154
1155 MediaTable(); //Build the special IMEDIA table
1156
1157 //Initialise geometry deposition table
1158 fEventEnergy.Set(gMC->NofVolumes()+1);
1159 fSummEnergy.Set(gMC->NofVolumes()+1);
1160 fSum2Energy.Set(gMC->NofVolumes()+1);
1161
1162 //Compute cross-sections
1163 gMC->BuildPhysics();
1164
1165 //Write Geometry object to current file.
88cb7938 1166 fRunLoader->WriteGeometry();
b9d0a01d 1167
1168 fInitDone = kTRUE;
1169
1170 fMCQA = new AliMCQA(fNdets);
1171
b9d0a01d 1172 //
1173 // Save stuff at the beginning of the file to avoid file corruption
1174 Write();
88cb7938 1175 fEventNrInRun = -1; //important - we start Begin event from increasing current number in run
b9d0a01d 1176}
1177
e2afb3b6 1178//_______________________________________________________________________
88cb7938 1179
875c717b 1180void AliRun::RunMC(Int_t nevent, const char *setup)
fe4da5cc 1181{
1182 //
1183 // Main function to be called to process a galice run
1184 // example
1185 // Root > gAlice.Run();
1186 // a positive number of events will cause the finish routine
1187 // to be called
1188 //
88cb7938 1189 fEventsPerRun = nevent;
fe4da5cc 1190 // check if initialisation has been done
875c717b 1191 if (!fInitDone) InitMC(setup);
fe4da5cc 1192
fe4da5cc 1193 // Create the Root Tree with one branch per detector
88cb7938 1194 //Hits moved to begin event -> now we are crating separate tree for each event
fe4da5cc 1195
875c717b 1196 gMC->ProcessRun(nevent);
1197
fe4da5cc 1198 // End of this run, close files
80762cb1 1199 if(nevent>0) FinishRun();
fe4da5cc 1200}
1201
e2afb3b6 1202//_______________________________________________________________________
27f087a9 1203void AliRun::RunReco(const char *selected, Int_t first, Int_t last)
d47c658f 1204{
1205 //
1206 // Main function to be called to reconstruct Alice event
27f087a9 1207 //
88cb7938 1208 Int_t nev = fRunLoader->GetNumberOfEvents();
1209 if (GetDebug()) Info("RunReco","Found %d events",nev);
27f087a9 1210 Int_t nFirst = first;
88cb7938 1211 Int_t nLast = (last < 0)? nev : last;
27f087a9 1212
1213 for (Int_t nevent = nFirst; nevent <= nLast; nevent++) {
88cb7938 1214 if (GetDebug()) Info("RunReco","Processing event %d",nevent);
9e1a0ddb 1215 GetEvent(nevent);
9e1a0ddb 1216 Digits2Reco(selected);
1217 }
d47c658f 1218}
1219
e2afb3b6 1220//_______________________________________________________________________
2ab0c725 1221
1222void AliRun::Hits2Digits(const char *selected)
1223{
9e1a0ddb 1224
d47c658f 1225 // Convert Hits to sumable digits
1226 //
9e1a0ddb 1227 for (Int_t nevent=0; nevent<gAlice->TreeE()->GetEntries(); nevent++) {
1228 GetEvent(nevent);
9e1a0ddb 1229 Hits2SDigits(selected);
1230 SDigits2Digits(selected);
1231 }
2ab0c725 1232}
1233
d47c658f 1234
e2afb3b6 1235//_______________________________________________________________________
2ab0c725 1236
d47c658f 1237void AliRun::Tree2Tree(Option_t *option, const char *selected)
2ab0c725 1238{
1239 //
d47c658f 1240 // Function to transform the content of
1241 //
1242 // - TreeH to TreeS (option "S")
1243 // - TreeS to TreeD (option "D")
1244 // - TreeD to TreeR (option "R")
1245 //
1246 // If multiple options are specified ("SDR"), transformation will be done in sequence for
1247 // selected detector and for all detectors if none is selected (detector string
1248 // can contain blank separated list of detector names).
2ab0c725 1249
2ab0c725 1250
5cf7bbad 1251 const char *oS = strstr(option,"S");
1252 const char *oD = strstr(option,"D");
1253 const char *oR = strstr(option,"R");
2ab0c725 1254
9e1a0ddb 1255 TObjArray *detectors = Detectors();
2ab0c725 1256
1257 TIter next(detectors);
1258
d47c658f 1259 AliDetector *detector = 0;
2ab0c725 1260
88cb7938 1261 while((detector = dynamic_cast<AliDetector*>(next()))) {
d47c658f 1262 if (selected)
2ab0c725 1263 if (strcmp(detector->GetName(),selected)) continue;
88cb7938 1264 if (detector->IsActive())
1265 {
1266
1267 AliLoader* loader = detector->GetLoader();
1268 if (loader == 0x0) continue;
1269
1270 if (oS)
1271 {
1272 if (GetDebug()) Info("Tree2Tree","Processing Hits2SDigits for %s ...",detector->GetName());
1273 loader->LoadHits("read");
1274 if (loader->TreeS() == 0x0) loader->MakeTree("S");
1275 detector->MakeBranch(option);
1276 detector->SetTreeAddress();
1277 detector->Hits2SDigits();
1278 loader->UnloadHits();
1279 loader->UnloadSDigits();
1280 }
1281 if (oD)
1282 {
1283 if (GetDebug()) Info("Tree2Tree","Processing SDigits2Digits for %s ...",detector->GetName());
1284 loader->LoadSDigits("read");
1285 if (loader->TreeD() == 0x0) loader->MakeTree("D");
1286 detector->MakeBranch(option);
1287 detector->SetTreeAddress();
1288 detector->SDigits2Digits();
1289 loader->UnloadSDigits();
1290 loader->UnloadDigits();
1291 }
1292 if (oR)
1293 {
1294 if (GetDebug()) Info("Tree2Tree","Processing Digits2Reco for %s ...",detector->GetName());
1295 loader->LoadDigits("read");
1296 if (loader->TreeR() == 0x0) loader->MakeTree("R");
1297 detector->MakeBranch(option);
1298 detector->SetTreeAddress();
1299 detector->Digits2Reco();
1300 loader->UnloadDigits();
1301 loader->UnloadRecPoints();
1302
1303 }
1304 }
1305 }
2ab0c725 1306}
1307
e2afb3b6 1308//_______________________________________________________________________
0a520a66 1309void AliRun::RunLego(const char *setup, Int_t nc1, Float_t c1min,
1310 Float_t c1max,Int_t nc2,Float_t c2min,Float_t c2max,
1311 Float_t rmin,Float_t rmax,Float_t zmax, AliLegoGenerator* gener)
fe4da5cc 1312{
1313 //
1314 // Generates lego plots of:
1315 // - radiation length map phi vs theta
1316 // - radiation length map phi vs eta
1317 // - interaction length map
1318 // - g/cm2 length map
1319 //
1320 // ntheta bins in theta, eta
1321 // themin minimum angle in theta (degrees)
1322 // themax maximum angle in theta (degrees)
1323 // nphi bins in phi
1324 // phimin minimum angle in phi (degrees)
1325 // phimax maximum angle in phi (degrees)
1326 // rmin minimum radius
1327 // rmax maximum radius
1328 //
1329 //
1330 // The number of events generated = ntheta*nphi
1331 // run input parameters in macro setup (default="Config.C")
1332 //
1333 // Use macro "lego.C" to visualize the 3 lego plots in spherical coordinates
1334 //Begin_Html
1335 /*
1439f98e 1336 <img src="picts/AliRunLego1.gif">
fe4da5cc 1337 */
1338 //End_Html
1339 //Begin_Html
1340 /*
1439f98e 1341 <img src="picts/AliRunLego2.gif">
fe4da5cc 1342 */
1343 //End_Html
1344 //Begin_Html
1345 /*
1439f98e 1346 <img src="picts/AliRunLego3.gif">
fe4da5cc 1347 */
1348 //End_Html
1349 //
1350
1351 // check if initialisation has been done
875c717b 1352 if (!fInitDone) InitMC(setup);
2cacde38 1353 // Save current generator
838edcaf 1354 AliGenerator *gen=Generator();
2cacde38 1355 // If runloader has been initialized, set the number of events per file to nc1 * nc2
1356 if (fRunLoader) fRunLoader->SetNumberOfEventsPerFile(nc1 * nc2);
0a520a66 1357 // Set new generator
1358 if (!gener) gener = new AliLegoGenerator();
1359 ResetGenerator(gener);
1360 //
1361 // Configure Generator
1362 gener->SetRadiusRange(rmin, rmax);
1363 gener->SetZMax(zmax);
1364 gener->SetCoor1Range(nc1, c1min, c1max);
1365 gener->SetCoor2Range(nc2, c2min, c2max);
1366
1367
b13db077 1368 //Create Lego object
0a520a66 1369 fLego = new AliLego("lego",gener);
b13db077 1370
dffd31ef 1371 //Prepare MC for Lego Run
1372 gMC->InitLego();
1373
b13db077 1374 //Run Lego Object
0a520a66 1375
b9d0a01d 1376 //gMC->ProcessRun(nc1*nc2+1);
1377 gMC->ProcessRun(nc1*nc2);
fe4da5cc 1378
1379 // Create only the Root event Tree
88cb7938 1380 fRunLoader->MakeTree("E");
fe4da5cc 1381
1382 // End of this run, close files
80762cb1 1383 FinishRun();
0a520a66 1384 // Restore current generator
1385 ResetGenerator(gen);
838edcaf 1386 // Delete Lego Object
1387 delete fLego; fLego=0;
fe4da5cc 1388}
1389
e2afb3b6 1390//_______________________________________________________________________
94de3818 1391void AliRun::SetConfigFunction(const char * config)
1392{
1393 //
1394 // Set the signature of the function contained in Config.C to configure
1395 // the run
1396 //
1397 fConfigFunction=config;
1398}
1399
e2afb3b6 1400//_______________________________________________________________________
fe4da5cc 1401void AliRun::SetCurrentTrack(Int_t track)
1402{
1403 //
1404 // Set current track number
1405 //
88cb7938 1406 fRunLoader->Stack()->SetCurrentTrack(track);
fe4da5cc 1407}
1408
e2afb3b6 1409//_______________________________________________________________________
642f15cf 1410void AliRun::PushTrack(Int_t done, Int_t parent, Int_t pdg, Float_t *pmom,
88cb7938 1411 Float_t *vpos, Float_t *polar, Float_t tof,
1412 TMCProcess mech, Int_t &ntr, Float_t weight, Int_t is)
fe4da5cc 1413{
9e1a0ddb 1414// Delegate to stack
1415//
642f15cf 1416 fRunLoader->Stack()->PushTrack(done, parent, pdg, pmom, vpos, polar, tof,
88cb7938 1417 mech, ntr, weight, is);
fe4da5cc 1418}
1419
e2afb3b6 1420//_______________________________________________________________________
642f15cf 1421void AliRun::PushTrack(Int_t done, Int_t parent, Int_t pdg,
89bbad6f 1422 Double_t px, Double_t py, Double_t pz, Double_t e,
1423 Double_t vx, Double_t vy, Double_t vz, Double_t tof,
1424 Double_t polx, Double_t poly, Double_t polz,
98490ea9 1425 TMCProcess mech, Int_t &ntr, Float_t weight, Int_t is)
89bbad6f 1426{
9e1a0ddb 1427 // Delegate to stack
89bbad6f 1428 //
642f15cf 1429 fRunLoader->Stack()->PushTrack(done, parent, pdg, px, py, pz, e, vx, vy, vz, tof,
88cb7938 1430 polx, poly, polz, mech, ntr, weight, is);
89bbad6f 1431}
1432
e2afb3b6 1433//_______________________________________________________________________
4d69d91e 1434void AliRun::SetHighWaterMark(const Int_t nt)
1435{
1436 //
1437 // Set high water mark for last track in event
88cb7938 1438 fRunLoader->Stack()->SetHighWaterMark(nt);
4d69d91e 1439}
1440
e2afb3b6 1441//_______________________________________________________________________
fe4da5cc 1442void AliRun::KeepTrack(const Int_t track)
1443{
1444 //
9e1a0ddb 1445 // Delegate to stack
fe4da5cc 1446 //
88cb7938 1447 fRunLoader->Stack()->KeepTrack(track);
fe4da5cc 1448}
1449
b9d0a01d 1450//
1451// MC Application
1452//
1453
e2afb3b6 1454//_______________________________________________________________________
b9d0a01d 1455void AliRun::ConstructGeometry()
1456{
1457 //
1458 // Create modules, materials, geometry
1459 //
1460
1461 TStopwatch stw;
1462 TIter next(fModules);
1463 AliModule *detector;
88cb7938 1464 if (GetDebug()) Info("ConstructGeometry","Geometry creation:");
e2afb3b6 1465 while((detector = dynamic_cast<AliModule*>(next()))) {
b9d0a01d 1466 stw.Start();
1467 // Initialise detector materials and geometry
1468 detector->CreateMaterials();
1469 detector->CreateGeometry();
1470 printf("%10s R:%.2fs C:%.2fs\n",
88cb7938 1471 detector->GetName(),stw.RealTime(),stw.CpuTime());
b9d0a01d 1472 }
1473}
1474
e2afb3b6 1475//_______________________________________________________________________
b9d0a01d 1476void AliRun::InitGeometry()
1477{
1478 //
1479 // Initialize detectors and display geometry
1480 //
1481
1482 printf("Initialisation:\n");
1483 TStopwatch stw;
1484 TIter next(fModules);
1485 AliModule *detector;
e2afb3b6 1486 while((detector = dynamic_cast<AliModule*>(next()))) {
b9d0a01d 1487 stw.Start();
1488 // Initialise detector and display geometry
1489 detector->Init();
1490 detector->BuildGeometry();
1491 printf("%10s R:%.2fs C:%.2fs\n",
1492 detector->GetName(),stw.RealTime(),stw.CpuTime());
1493 }
1494
1495}
e2afb3b6 1496//_______________________________________________________________________
88cb7938 1497
b9d0a01d 1498void AliRun::GeneratePrimaries()
1499{
1500 //
1501 // Generate primary particles and fill them in the stack.
1502 //
1503
1504 Generator()->Generate();
1505}
e2afb3b6 1506//_______________________________________________________________________
b9d0a01d 1507
b9d0a01d 1508void AliRun::BeginPrimary()
1509{
1510 //
1511 // Called at the beginning of each primary track
1512 //
1513
1514 // Reset Hits info
1515 gAlice->ResetHits();
1516 gAlice->ResetTrackReferences();
1517
1518}
1519
e2afb3b6 1520//_______________________________________________________________________
b9d0a01d 1521void AliRun::PreTrack()
1522{
88cb7938 1523 TObjArray &dets = *fModules;
1524 AliModule *module;
1525
1526 for(Int_t i=0; i<=fNdets; i++)
1527 if((module = dynamic_cast<AliModule*>(dets[i])))
1528 module->PreTrack();
1529
1530 fMCQA->PreTrack();
b9d0a01d 1531}
1532
e2afb3b6 1533//_______________________________________________________________________
b9d0a01d 1534void AliRun::Stepping()
fe4da5cc 1535{
1536 //
1537 // Called at every step during transport
1538 //
1539
b9d0a01d 1540 Int_t id = DetFromMate(gMC->GetMedium());
2cacde38 1541
b9d0a01d 1542 if (id < 0) return;
1543
fe4da5cc 1544 //
1545 // --- If lego option, do it and leave
b13db077 1546 if (fLego)
fe4da5cc 1547 fLego->StepManager();
b13db077 1548 else {
1549 Int_t copy;
1550 //Update energy deposition tables
875c717b 1551 AddEnergyDeposit(gMC->CurrentVolID(copy),gMC->Edep());
2b22f272 1552 //
1553 // write tracke reference for track which is dissapearing - MI
1554 if (gMC->IsTrackDisappeared()) {
1555 if (gMC->Etot()>0.05) AddTrackReference(GetCurrentTrackNumber());
1556 }
1557
b13db077 1558 //Call the appropriate stepping routine;
e2afb3b6 1559 AliModule *det = dynamic_cast<AliModule*>(fModules->At(id));
3f754d83 1560 if(det && det->StepManagerIsEnabled()) {
65fb704d 1561 fMCQA->StepManager(id);
1562 det->StepManager();
1563 }
fe4da5cc 1564 }
fe4da5cc 1565}
1566
e2afb3b6 1567//_______________________________________________________________________
b9d0a01d 1568void AliRun::PostTrack()
1569{
88cb7938 1570 TObjArray &dets = *fModules;
1571 AliModule *module;
1572
1573 for(Int_t i=0; i<=fNdets; i++)
1574 if((module = dynamic_cast<AliModule*>(dets[i])))
1575 module->PostTrack();
b9d0a01d 1576}
1577
e2afb3b6 1578//_______________________________________________________________________
b9d0a01d 1579void AliRun::FinishPrimary()
1580{
1581 //
1582 // Called at the end of each primary track
1583 //
1584
1585 // static Int_t count=0;
1586 // const Int_t times=10;
1587 // This primary is finished, purify stack
88cb7938 1588 fRunLoader->Stack()->PurifyKine();
b9d0a01d 1589
1590 TIter next(fModules);
1591 AliModule *detector;
e2afb3b6 1592 while((detector = dynamic_cast<AliModule*>(next()))) {
b9d0a01d 1593 detector->FinishPrimary();
88cb7938 1594 if(detector->GetLoader())
1595 {
1596 detector->GetLoader()->TreeH()->Fill();
1597 }
b9d0a01d 1598 }
1599
88cb7938 1600 // Write out track references if any
1601 if (fRunLoader->TreeTR())
1602 {
1603 fRunLoader->TreeTR()->Fill();
1604 }
b9d0a01d 1605}
1606
e2afb3b6 1607//_______________________________________________________________________
b9d0a01d 1608void AliRun::FinishEvent()
1609{
1610 //
1611 // Called at the end of the event.
1612 //
1613
1614 //
1615 if(fLego) fLego->FinishEvent();
1616
88cb7938 1617 TIter next(fModules);
1618 AliModule *detector;
1619 while((detector = dynamic_cast<AliModule*>(next()))) {
1620 detector->FinishEvent();
1621 }
1622
b9d0a01d 1623 //Update the energy deposit tables
1624 Int_t i;
88cb7938 1625 for(i=0;i<fEventEnergy.GetSize();i++)
1626 {
b9d0a01d 1627 fSummEnergy[i]+=fEventEnergy[i];
1628 fSum2Energy[i]+=fEventEnergy[i]*fEventEnergy[i];
88cb7938 1629 }
b9d0a01d 1630
88cb7938 1631 AliHeader* header = fRunLoader->GetHeader();
1632 AliStack* stack = fRunLoader->Stack();
1633 if ( (header == 0x0) || (stack == 0x0) )
1634 {//check if we got header and stack. If not cry and exit aliroot
1635 Fatal("AliRun","Can not get the stack or header from LOADER");
1636 return;//never reached
1637 }
b9d0a01d 1638 // Update Header information
88cb7938 1639 header->SetNprimary(stack->GetNprimary());
1640 header->SetNtrack(stack->GetNtrack());
b9d0a01d 1641
1642
1643 // Write out the kinematics
88cb7938 1644 stack->FinishEvent();
b9d0a01d 1645
1646 // Write out the event Header information
88cb7938 1647 TTree* treeE = fRunLoader->TreeE();
1648 if (treeE)
1649 {
1650 header->SetStack(stack);
1651 treeE->Fill();
1652 }
1653 else
1654 {
1655 Error("FinishEvent","Can not get TreeE from RL");
1656 }
b9d0a01d 1657
88cb7938 1658 fRunLoader->WriteKinematics("OVERWRITE");
1659 fRunLoader->WriteTrackRefs("OVERWRITE");
1660 fRunLoader->WriteHits("OVERWRITE");
1661
1662 if (GetDebug())
1663 {
1664 Info("FinishEvent","<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<");
1665 Info("FinishEvent","<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<");
1666 Info("FinishEvent","<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<");
1667 Info("FinishEvent"," FINISHING EVENT ");
1668 Info("FinishEvent","<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<");
1669 Info("FinishEvent","<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<");
1670 Info("FinishEvent","<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<");
1671 }
b9d0a01d 1672}
1673
e2afb3b6 1674//_______________________________________________________________________
b9d0a01d 1675void AliRun::Field(const Double_t* x, Double_t *b) const
1676{
88cb7938 1677 Float_t xfloat[3];
1678 for (Int_t i=0; i<3; i++) xfloat[i] = x[i];
1679
1680 if (Field()) {
1681 Float_t bfloat[3];
1682 Field()->Field(xfloat,bfloat);
1683 for (Int_t j=0; j<3; j++) b[j] = bfloat[j];
1684 }
1685 else {
1686 printf("No mag field defined!\n");
1687 b[0]=b[1]=b[2]=0.;
1688 }
b9d0a01d 1689
1690}
1691
1692//
1693// End of MC Application
1694//
1695
e2afb3b6 1696//_______________________________________________________________________
fe4da5cc 1697void AliRun::Streamer(TBuffer &R__b)
1698{
eef4b160 1699 // Stream an object of class AliRun.
2ab0c725 1700
7e90ff59 1701 if (R__b.IsReading()) {
1702 if (!gAlice) gAlice = this;
7e90ff59 1703 AliRun::Class()->ReadBuffer(R__b, this);
7e90ff59 1704 gROOT->GetListOfBrowsables()->Add(this,"Run");
eef4b160 1705
7e90ff59 1706 gRandom = fRandom;
1707 } else {
eef4b160 1708 AliRun::Class()->WriteBuffer(R__b, this);
1709 }
2ab0c725 1710}
1711
9e1a0ddb 1712
e2afb3b6 1713//_______________________________________________________________________
642f15cf 1714Int_t AliRun::GetCurrentTrackNumber() const {
9e1a0ddb 1715 //
1716 // Returns current track
1717 //
642f15cf 1718 return fRunLoader->Stack()->GetCurrentTrackNumber();
9e1a0ddb 1719}
1720
e2afb3b6 1721//_______________________________________________________________________
9e1a0ddb 1722Int_t AliRun::GetNtrack() const {
1723 //
1724 // Returns number of tracks in stack
1725 //
88cb7938 1726 return fRunLoader->Stack()->GetNtrack();
9e1a0ddb 1727}
88cb7938 1728//_______________________________________________________________________
9e1a0ddb 1729
e2afb3b6 1730//_______________________________________________________________________
37d06d5b 1731TObjArray* AliRun::Particles() const {
9e1a0ddb 1732 //
1733 // Returns pointer to Particles array
1734 //
88cb7938 1735 if (fRunLoader)
1736 if (fRunLoader->Stack())
1737 return fRunLoader->Stack()->Particles();
1738 return 0x0;
9e1a0ddb 1739}
27f087a9 1740
88cb7938 1741//___________________________________________________________________________
b9d0a01d 1742
e2afb3b6 1743//_______________________________________________________________________
27f087a9 1744void AliRun::SetGenEventHeader(AliGenEventHeader* header)
1745{
88cb7938 1746 fRunLoader->GetHeader()->SetGenEventHeader(header);
27f087a9 1747}
b9d0a01d 1748
88cb7938 1749//___________________________________________________________________________
0592d1ca 1750
88cb7938 1751Int_t AliRun::GetEvNumber() const
1752{
1753//Returns number of current event
1754 if (fRunLoader == 0x0)
1755 {
1756 Error("GetEvent","RunLoader is not set. Can not load data.");
1757 return -1;
1758 }
0592d1ca 1759
88cb7938 1760 return fRunLoader->GetEventNumber();
0592d1ca 1761}
b9d0a01d 1762
88cb7938 1763void AliRun::SetRunLoader(AliRunLoader* rloader)
0592d1ca 1764{
88cb7938 1765 fRunLoader = rloader;
1766 if (fRunLoader == 0x0) return;
1767
1768 TString evfoldname;
1769 TFolder* evfold = fRunLoader->GetEventFolder();
1770 if (evfold) evfoldname = evfold->GetName();
1771 else Warning("SetRunLoader","Did not get Event Folder from Run Loader");
1772
1773 if ( fRunLoader->GetAliRun() )
1774 {//if alrun already exists in folder
1775 if (fRunLoader->GetAliRun() != this )
1776 {//and is different than this - crash
1777 Fatal("AliRun","AliRun is already in Folder and it is not this object");
1778 return;//pro forma
1779 }//else do nothing
1780 }
1781 else
1782 {
1783 evfold->Add(this);//Post this AliRun to Folder
1784 }
1785
1786 TIter next(fModules);
1787 AliModule *module;
1788 while((module = (AliModule*)next()))
1789 {
1790 if (evfold) AliConfig::Instance()->Add(module,evfoldname);
1791 AliDetector* detector = dynamic_cast<AliDetector*>(module);
1792 if (detector)
1793 {
1794 AliLoader* loader = fRunLoader->GetLoader(detector);
1795 if (loader == 0x0)
1796 {
1797 Error("SetRunLoader","Can not get loader for detector %s",detector->GetName());
1798 }
1799 else
1800 {
1801 if (GetDebug()) Info("SetRunLoader","Setting loader for detector %s",detector->GetName());
1802 detector->SetLoader(loader);
1803 }
0592d1ca 1804 }
88cb7938 1805 }
0592d1ca 1806}
1807
88cb7938 1808void AliRun::AddModule(AliModule* mod)
7a16e9cc 1809{
88cb7938 1810 if (mod == 0x0) return;
1811 if (strlen(mod->GetName()) == 0) return;
1812 if (GetModuleID(mod->GetName()) >= 0) return;
1813
1814 if (GetDebug()) Info("AddModule","%s",mod->GetName());
1815 if (fRunLoader == 0x0) AliConfig::Instance()->Add(mod);
1816 else AliConfig::Instance()->Add(mod,fRunLoader->GetEventFolder()->GetName());
7a16e9cc 1817
88cb7938 1818 Modules()->Add(mod);
7a16e9cc 1819}