]> git.uio.no Git - u/mrichter/AliRoot.git/blame - STEER/AliRun.cxx
Updading according to changes in STEER
[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
fb17acd4 16/* $Header$ */
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
94de3818 43#include <stdio.h>
98490ea9 44#include <stdlib.h>
94de3818 45#include <string.h>
46
98490ea9 47#include "Riostream.h"
48#include "TBRIK.h"
49#include "TBrowser.h"
50#include "TCint.h"
51#include "TFile.h"
52#include "TFolder.h"
53#include "TGeometry.h"
98490ea9 54#include "TNode.h"
1578254f 55#include "TParticle.h"
98490ea9 56#include "TRandom3.h"
57#include "TROOT.h"
58#include "TSystem.h"
59#include "TTree.h"
60
61#include "AliConfig.h"
62#include "AliDetector.h"
fe4da5cc 63#include "AliDisplay.h"
98490ea9 64#include "AliGenerator.h"
65#include "AliHeader.h"
dffd31ef 66#include "AliLego.h"
98490ea9 67#include "AliLegoGenerator.h"
68#include "AliMCQA.h"
aee8290b 69#include "AliMagFC.h"
70#include "AliMagFCM.h"
71#include "AliMagFDM.h"
141f90e3 72#include "AliPDG.h"
98490ea9 73#include "AliRun.h"
74#include "AliStack.h"
fe4da5cc 75
fe4da5cc 76AliRun *gAlice;
77
fe4da5cc 78ClassImp(AliRun)
79
e2afb3b6 80//_______________________________________________________________________
81AliRun::AliRun():
82 fRun(0),
83 fEvent(0),
84 fEventNrInRun(0),
85 fEventsPerRun(0),
86 fDebug(0),
87 fHeader(0),
88 fTreeD(0),
89 fTreeS(0),
90 fTreeH(0),
91 fTreeTR(0),
92 fTreeE(0),
93 fTreeR(0),
94 fModules(0),
95 fGeometry(0),
96 fDisplay(0),
97 fTimer(),
98 fField(0),
99 fMC(0),
100 fImedia(0),
101 fNdets(0),
102 fTrRmax(1.e10),
103 fTrZmax(1.e10),
104 fGenerator(0),
105 fInitDone(kFALSE),
106 fLego(0),
107 fPDGDB(0), //Particle factory object
108 fHitLists(0),
109 fEventEnergy(0),
110 fSummEnergy(0),
111 fSum2Energy(0),
112 fConfigFunction("\0"),
113 fRandom(0),
114 fMCQA(0),
115 fTransParName("\0"),
116 fBaseFileName("\0"),
117 fStack(0),
118 fTreeDFileName(""),
119 fTreeDFile(0),
120 fTreeSFileName(""),
121 fTreeSFile(0),
122 fTreeRFileName(""),
123 fTreeRFile(0)
fe4da5cc 124{
125 //
126 // Default constructor for AliRun
127 //
e2afb3b6 128}
129
130//_______________________________________________________________________
131AliRun::AliRun(const AliRun& arun):
132 TVirtualMCApplication(arun),
133 fRun(0),
134 fEvent(0),
135 fEventNrInRun(0),
136 fEventsPerRun(0),
137 fDebug(0),
138 fHeader(0),
139 fTreeD(0),
140 fTreeS(0),
141 fTreeH(0),
142 fTreeTR(0),
143 fTreeE(0),
144 fTreeR(0),
145 fModules(0),
146 fGeometry(0),
147 fDisplay(0),
148 fTimer(),
149 fField(0),
150 fMC(0),
151 fImedia(0),
152 fNdets(0),
153 fTrRmax(1.e10),
154 fTrZmax(1.e10),
155 fGenerator(0),
156 fInitDone(kFALSE),
157 fLego(0),
158 fPDGDB(0), //Particle factory object
159 fHitLists(0),
160 fEventEnergy(0),
161 fSummEnergy(0),
162 fSum2Energy(0),
163 fConfigFunction("\0"),
164 fRandom(0),
165 fMCQA(0),
166 fTransParName("\0"),
167 fBaseFileName("\0"),
168 fStack(0),
169 fTreeDFileName(""),
170 fTreeDFile(0),
171 fTreeSFileName(""),
172 fTreeSFile(0),
173 fTreeRFileName(""),
174 fTreeRFile(0)
175{
176 //
177 // Copy constructor for AliRun
178 //
179 arun.Copy(*this);
fe4da5cc 180}
181
182//_____________________________________________________________________________
e2afb3b6 183AliRun::AliRun(const char *name, const char *title):
184 TVirtualMCApplication(name,title),
185 fRun(0),
186 fEvent(0),
187 fEventNrInRun(0),
188 fEventsPerRun(0),
189 fDebug(0),
190 fHeader(new AliHeader()),
191 fTreeD(0),
192 fTreeS(0),
193 fTreeH(0),
194 fTreeTR(0),
195 fTreeE(0),
196 fTreeR(0),
197 fModules(new TObjArray(77)), // Support list for the Detectors
198 fGeometry(0),
199 fDisplay(0),
200 fTimer(),
201 fField(0),
202 fMC(gMC),
203 fImedia(new TArrayI(1000)),
204 fNdets(0),
205 fTrRmax(1.e10),
206 fTrZmax(1.e10),
207 fGenerator(0),
208 fInitDone(kFALSE),
209 fLego(0),
210 fPDGDB(TDatabasePDG::Instance()), //Particle factory object!
211 fHitLists(new TList()), // Create HitLists list
212 fEventEnergy(0),
213 fSummEnergy(0),
214 fSum2Energy(0),
215 fConfigFunction("Config();"),
216 fRandom(new TRandom3()),
217 fMCQA(0),
218 fTransParName("\0"),
219 fBaseFileName("\0"),
220 fStack(new AliStack(10000)), //Particle stack
221 fTreeDFileName(""),
222 fTreeDFile(0),
223 fTreeSFileName(""),
224 fTreeSFile(0),
225 fTreeRFileName(""),
226 fTreeRFile(0)
fe4da5cc 227{
228 //
229 // Constructor for the main processor.
230 // Creates the geometry
231 // Creates the list of Detectors.
232 // Creates the list of particles.
233 //
e2afb3b6 234
fe4da5cc 235 gAlice = this;
65fb704d 236
237 // Set random number generator
e2afb3b6 238 gRandom = fRandom;
2ab0c725 239
240 if (gSystem->Getenv("CONFIG_SEED")) {
e2afb3b6 241 gRandom->SetSeed(static_cast<UInt_t>(atoi(gSystem->Getenv("CONFIG_SEED"))));
2ab0c725 242 }
e2afb3b6 243
244 // Add to list of browsable
fe4da5cc 245 gROOT->GetListOfBrowsables()->Add(this,name);
e2afb3b6 246
fe4da5cc 247 // Create the TNode geometry for the event display
fe4da5cc 248 BuildSimpleGeometry();
249
fe4da5cc 250 // Create default mag field
251 SetField();
e2afb3b6 252
fe4da5cc 253 // Prepare the tracking medium lists
e2afb3b6 254 for(Int_t i=0;i<1000;i++) (*fImedia)[i]=-99;
9e1a0ddb 255
e2afb3b6 256 // Add particle list to configuration
9e1a0ddb 257 AliConfig::Instance()->Add(fPDGDB);
e2afb3b6 258
259 // Set transport parameters
65fb704d 260 SetTransPar();
fe4da5cc 261}
262
aee8290b 263
e2afb3b6 264//_______________________________________________________________________
fe4da5cc 265AliRun::~AliRun()
266{
267 //
2ab0c725 268 // Default AliRun destructor
fe4da5cc 269 //
7a16e9cc 270 TFile *curfil =0;
271 if(fTreeE)curfil=fTreeE->GetCurrentFile();
fe4da5cc 272 delete fImedia;
273 delete fField;
875c717b 274 delete fMC;
fe4da5cc 275 delete fGeometry;
276 delete fDisplay;
277 delete fGenerator;
278 delete fLego;
279 delete fTreeD;
fe4da5cc 280 delete fTreeH;
aab9c8d5 281 delete fTreeTR;
fe4da5cc 282 delete fTreeE;
283 delete fTreeR;
2ab0c725 284 delete fTreeS;
8494b010 285 if (fModules) {
286 fModules->Delete();
287 delete fModules;
fe4da5cc 288 }
9e1a0ddb 289 delete fStack;
1cedd08a 290 delete fHitLists;
c222d2b0 291 delete fPDGDB;
e460afec 292 delete fMCQA;
9e1a0ddb 293 delete fHeader;
7a16e9cc 294 // avoid to delete TFile objects not owned by this object
295 // avoid multiple deletions
296 if(curfil == fTreeDFile) fTreeDFile=0;
297 if(curfil == fTreeSFile) fTreeSFile=0;
298 if(curfil == fTreeRFile) fTreeRFile=0;
299 if(fTreeSFile == fTreeDFile) fTreeSFile=0;
300 if(fTreeRFile == fTreeDFile) fTreeRFile=0;
301 if(fTreeRFile == fTreeSFile) fTreeRFile=0;
302 if(fTreeDFile){
303 if(fTreeDFile->IsOpen())fTreeDFile->Close();
304 delete fTreeDFile;
305 }
306 if(fTreeSFile){
307 if(fTreeSFile->IsOpen())fTreeSFile->Close();
308 delete fTreeSFile;
309 }
310 if(fTreeRFile){
311 if(fTreeRFile->IsOpen())fTreeRFile->Close();
312 delete fTreeRFile;
313 }
314 if (gROOT->GetListOfBrowsables())
315 gROOT->GetListOfBrowsables()->Remove(this);
b9d0a01d 316
317 gAlice=0;
fe4da5cc 318}
319
e2afb3b6 320//_______________________________________________________________________
321void AliRun::Copy(AliRun &) const
322{
323 Fatal("Copy","Not implemented!\n");
324}
325
326//_______________________________________________________________________
fe4da5cc 327void AliRun::AddHit(Int_t id, Int_t track, Int_t *vol, Float_t *hits) const
328{
329 //
330 // Add a hit to detector id
331 //
8494b010 332 TObjArray &dets = *fModules;
e2afb3b6 333 if(dets[id]) dynamic_cast<AliModule*>(dets[id])->AddHit(track,vol,hits);
fe4da5cc 334}
335
e2afb3b6 336//_______________________________________________________________________
fe4da5cc 337void AliRun::AddDigit(Int_t id, Int_t *tracks, Int_t *digits) const
338{
339 //
340 // Add digit to detector id
341 //
8494b010 342 TObjArray &dets = *fModules;
e2afb3b6 343 if(dets[id]) dynamic_cast<AliModule*>(dets[id])->AddDigit(tracks,digits);
fe4da5cc 344}
345
e2afb3b6 346//_______________________________________________________________________
fe4da5cc 347void AliRun::Browse(TBrowser *b)
348{
349 //
350 // Called when the item "Run" is clicked on the left pane
351 // of the Root browser.
352 // It displays the Root Trees and all detectors.
353 //
9e1a0ddb 354 if(!fStack) fStack=fHeader->Stack();
355 TTree* pTreeK = fStack->TreeK();
356
357 if (pTreeK) b->Add(pTreeK,pTreeK->GetName());
fe4da5cc 358 if (fTreeH) b->Add(fTreeH,fTreeH->GetName());
aab9c8d5 359 if (fTreeTR) b->Add(fTreeTR,fTreeH->GetName());
fe4da5cc 360 if (fTreeD) b->Add(fTreeD,fTreeD->GetName());
361 if (fTreeE) b->Add(fTreeE,fTreeE->GetName());
362 if (fTreeR) b->Add(fTreeR,fTreeR->GetName());
2ab0c725 363 if (fTreeS) b->Add(fTreeS,fTreeS->GetName());
fe4da5cc 364
8494b010 365 TIter next(fModules);
366 AliModule *detector;
e2afb3b6 367 while((detector = dynamic_cast<AliModule*>(next()))) {
fe4da5cc 368 b->Add(detector,detector->GetName());
369 }
65fb704d 370 b->Add(fMCQA,"AliMCQA");
fe4da5cc 371}
372
e2afb3b6 373//_______________________________________________________________________
fe4da5cc 374void AliRun::Build()
375{
376 //
377 // Initialize Alice geometry
378 // Dummy routine
379 //
380}
381
e2afb3b6 382//_______________________________________________________________________
fe4da5cc 383void AliRun::BuildSimpleGeometry()
384{
385 //
386 // Create a simple TNode geometry used by Root display engine
387 //
388 // Initialise geometry
389 //
390 fGeometry = new TGeometry("AliceGeom","Galice Geometry for Hits");
391 new TMaterial("void","Vacuum",0,0,0); //Everything is void
392 TBRIK *brik = new TBRIK("S_alice","alice volume","void",2000,2000,3000);
393 brik->SetVisibility(0);
394 new TNode("alice","alice","S_alice");
395}
396
e2afb3b6 397//_______________________________________________________________________
fe4da5cc 398void AliRun::CleanDetectors()
399{
400 //
401 // Clean Detectors at the end of event
402 //
8494b010 403 TIter next(fModules);
404 AliModule *detector;
e2afb3b6 405 while((detector = dynamic_cast<AliModule*>(next()))) {
fe4da5cc 406 detector->FinishEvent();
407 }
408}
409
e2afb3b6 410//_______________________________________________________________________
116cbefd 411Int_t AliRun::DistancetoPrimitive(Int_t, Int_t) const
fe4da5cc 412{
413 //
414 // Return the distance from the mouse to the AliRun object
415 // Dummy routine
416 //
417 return 9999;
418}
419
e2afb3b6 420//_______________________________________________________________________
94de3818 421void AliRun::DumpPart (Int_t i) const
fe4da5cc 422{
423 //
424 // Dumps particle i in the stack
425 //
9e1a0ddb 426 fStack->DumpPart(i);
fe4da5cc 427}
428
e2afb3b6 429//_______________________________________________________________________
94de3818 430void AliRun::DumpPStack () const
fe4da5cc 431{
432 //
433 // Dumps the particle stack
434 //
9e1a0ddb 435 fStack->DumpPStack();
fe4da5cc 436}
437
e2afb3b6 438//_______________________________________________________________________
d8408e76 439void AliRun::SetField(AliMagF* magField)
440{
441 // Set Magnetic Field Map
442 fField = magField;
443 fField->ReadField();
444}
445
e2afb3b6 446//_______________________________________________________________________
fe4da5cc 447void AliRun::SetField(Int_t type, Int_t version, Float_t scale,
448 Float_t maxField, char* filename)
449{
450 //
451 // Set magnetic field parameters
452 // type Magnetic field transport flag 0=no field, 2=helix, 3=Runge Kutta
453 // version Magnetic field map version (only 1 active now)
454 // scale Scale factor for the magnetic field
455 // maxField Maximum value for the magnetic field
456
457 //
458 // --- Sanity check on mag field flags
fe4da5cc 459 if(fField) delete fField;
460 if(version==1) {
d8408e76 461 fField = new AliMagFC("Map1"," ",type,scale,maxField);
f1b9d7c3 462 } else if(version<=2) {
d8408e76 463 fField = new AliMagFCM("Map2-3",filename,type,scale,maxField);
fe4da5cc 464 fField->ReadField();
f1b9d7c3 465 } else if(version==3) {
d8408e76 466 fField = new AliMagFDM("Map4",filename,type,scale,maxField);
f1b9d7c3 467 fField->ReadField();
fe4da5cc 468 } else {
23370b7a 469 Warning("SetField","Invalid map %d\n",version);
fe4da5cc 470 }
471}
fe4da5cc 472
e2afb3b6 473//_______________________________________________________________________
fe4da5cc 474void AliRun::FinishRun()
475{
476 //
477 // Called at the end of the run.
478 //
479
dffd31ef 480 //
481 if(fLego) fLego->FinishRun();
8e70f139 482
fe4da5cc 483 // Clean detector information
8494b010 484 TIter next(fModules);
485 AliModule *detector;
e2afb3b6 486 while((detector = dynamic_cast<AliModule*>(next()))) {
fe4da5cc 487 detector->FinishRun();
488 }
489
490 //Output energy summary tables
491 EnergySummary();
2ab0c725 492
493 TFile *file = fTreeE->GetCurrentFile();
494
aee8290b 495 file->cd();
2ab0c725 496
51e0e89d 497 fTreeE->Write(0,TObject::kOverwrite);
fe4da5cc 498
2ab0c725 499 // Write AliRun info and all detectors parameters
d47c658f 500 Write(0,TObject::kOverwrite);
682a4a95 501
fe4da5cc 502 // Clean tree information
9e1a0ddb 503
504 fStack->FinishRun();
505
d2ecd553 506 if (fTreeH) {
507 delete fTreeH; fTreeH = 0;
508 }
aab9c8d5 509 if (fTreeTR) {
510 delete fTreeTR; fTreeTR = 0;
511 }
d2ecd553 512 if (fTreeD) {
513 delete fTreeD; fTreeD = 0;
514 }
515 if (fTreeR) {
516 delete fTreeR; fTreeR = 0;
517 }
7e90ff59 518// if (fTreeE) {
519// delete fTreeE; fTreeE = 0;
520// }
9e1a0ddb 521 if (fTreeS) {
522 delete fTreeS; fTreeS = 0;
523 }
6df200c3 524 fGenerator->FinishRun();
525
fe4da5cc 526 // Close output file
aee8290b 527 file->Write();
fe4da5cc 528}
529
e2afb3b6 530//_______________________________________________________________________
fe4da5cc 531void AliRun::FlagTrack(Int_t track)
532{
9e1a0ddb 533 // Delegate to stack
fe4da5cc 534 //
9e1a0ddb 535 fStack->FlagTrack(track);
fe4da5cc 536}
537
e2afb3b6 538//_______________________________________________________________________
fe4da5cc 539void AliRun::EnergySummary()
540{
541 //
542 // Print summary of deposited energy
543 //
544
fe4da5cc 545 Int_t ndep=0;
546 Float_t edtot=0;
547 Float_t ed, ed2;
548 Int_t kn, i, left, j, id;
aee8290b 549 const Float_t kzero=0;
9e1a0ddb 550 Int_t ievent=fHeader->GetEvent()+1;
fe4da5cc 551 //
552 // Energy loss information
553 if(ievent) {
554 printf("***************** Energy Loss Information per event (GEV) *****************\n");
875c717b 555 for(kn=1;kn<fEventEnergy.GetSize();kn++) {
556 ed=fSummEnergy[kn];
fe4da5cc 557 if(ed>0) {
875c717b 558 fEventEnergy[ndep]=kn;
fe4da5cc 559 if(ievent>1) {
560 ed=ed/ievent;
875c717b 561 ed2=fSum2Energy[kn];
fe4da5cc 562 ed2=ed2/ievent;
aee8290b 563 ed2=100*TMath::Sqrt(TMath::Max(ed2-ed*ed,kzero))/ed;
fe4da5cc 564 } else
565 ed2=99;
875c717b 566 fSummEnergy[ndep]=ed;
e2afb3b6 567 fSum2Energy[ndep]=TMath::Min(static_cast<Float_t>(99.),TMath::Max(ed2,kzero));
fe4da5cc 568 edtot+=ed;
569 ndep++;
570 }
571 }
572 for(kn=0;kn<(ndep-1)/3+1;kn++) {
573 left=ndep-kn*3;
574 for(i=0;i<(3<left?3:left);i++) {
575 j=kn*3+i;
875c717b 576 id=Int_t (fEventEnergy[j]+0.1);
577 printf(" %s %10.3f +- %10.3f%%;",gMC->VolName(id),fSummEnergy[j],fSum2Energy[j]);
fe4da5cc 578 }
579 printf("\n");
580 }
581 //
582 // Relative energy loss in different detectors
583 printf("******************** Relative Energy Loss per event ********************\n");
584 printf("Total energy loss per event %10.3f GeV\n",edtot);
585 for(kn=0;kn<(ndep-1)/5+1;kn++) {
586 left=ndep-kn*5;
587 for(i=0;i<(5<left?5:left);i++) {
588 j=kn*5+i;
875c717b 589 id=Int_t (fEventEnergy[j]+0.1);
590 printf(" %s %10.3f%%;",gMC->VolName(id),100*fSummEnergy[j]/edtot);
fe4da5cc 591 }
592 printf("\n");
593 }
594 for(kn=0;kn<75;kn++) printf("*");
595 printf("\n");
596 }
597 //
598 // Reset the TArray's
875c717b 599 // fEventEnergy.Set(0);
600 // fSummEnergy.Set(0);
601 // fSum2Energy.Set(0);
fe4da5cc 602}
603
e2afb3b6 604//_______________________________________________________________________
94de3818 605AliModule *AliRun::GetModule(const char *name) const
fe4da5cc 606{
607 //
608 // Return pointer to detector from name
609 //
e2afb3b6 610 return dynamic_cast<AliModule*>(fModules->FindObject(name));
fe4da5cc 611}
612
e2afb3b6 613//_______________________________________________________________________
94de3818 614AliDetector *AliRun::GetDetector(const char *name) const
a68348e9 615{
616 //
617 // Return pointer to detector from name
618 //
e2afb3b6 619 return dynamic_cast<AliDetector*>(fModules->FindObject(name));
a68348e9 620}
621
e2afb3b6 622//_______________________________________________________________________
94de3818 623Int_t AliRun::GetModuleID(const char *name) const
fe4da5cc 624{
625 //
626 // Return galice internal detector identifier from name
627 //
23370b7a 628 Int_t i=-1;
629 TObject *mod=fModules->FindObject(name);
630 if(mod) i=fModules->IndexOf(mod);
631 return i;
fe4da5cc 632}
633
e2afb3b6 634//_______________________________________________________________________
fe4da5cc 635Int_t AliRun::GetEvent(Int_t event)
636{
637 //
638 // Connect the Trees Kinematics and Hits for event # event
639 // Set branch addresses
640 //
fe4da5cc 641
642 // Reset existing structures
fe4da5cc 643 ResetHits();
aab9c8d5 644 ResetTrackReferences();
fe4da5cc 645 ResetDigits();
2ab0c725 646 ResetSDigits();
fe4da5cc 647
648 // Delete Trees already connected
ccf7a81f 649 if (fTreeH) { delete fTreeH; fTreeH = 0;}
aab9c8d5 650 if (fTreeTR) { delete fTreeTR; fTreeTR = 0;}
ccf7a81f 651 if (fTreeD) { delete fTreeD; fTreeD = 0;}
652 if (fTreeR) { delete fTreeR; fTreeR = 0;}
653 if (fTreeS) { delete fTreeS; fTreeS = 0;}
59fe9bd2 654
9e1a0ddb 655 // Create the particle stack
656 if (fHeader) delete fHeader;
657 fHeader = 0;
658
59fe9bd2 659 // Get header from file
9e1a0ddb 660 if(fTreeE) {
661 fTreeE->SetBranchAddress("Header", &fHeader);
ccf7a81f 662
663 if (!fTreeE->GetEntry(event)) {
664 Error("GetEvent","Cannot find event:%d\n",event);
665 return -1;
666 }
9e1a0ddb 667 }
ccf7a81f 668 else {
9e1a0ddb 669 Error("GetEvent","Cannot find Header Tree (TE)\n");
ccf7a81f 670 return -1;
671 }
9e1a0ddb 672
ccf7a81f 673 // Get the stack from the header, set fStack to 0 if it
674 // fails to get event
9e1a0ddb 675 //
2ab0c725 676 TFile *file = fTreeE->GetCurrentFile();
fe4da5cc 677 char treeName[20];
6df200c3 678
2ab0c725 679 file->cd();
680
50a6540a 681 if (fStack) delete fStack;
682 fStack = fHeader->Stack();
683 if (fStack) {
684 if (!fStack->GetEvent(event)) fStack = 0;
685 }
686
fe4da5cc 687 // Get Hits Tree header from file
688 sprintf(treeName,"TreeH%d",event);
e2afb3b6 689 fTreeH = dynamic_cast<TTree*>(gDirectory->Get(treeName));
2057d00a 690 if (!fTreeH) {
b9d0a01d 691 Warning("GetEvent","cannot find Hits Tree for event:%d\n",event);
2057d00a 692 }
693
aab9c8d5 694 // Get TracReferences Tree header from file
695 sprintf(treeName,"TreeTR%d",event);
e2afb3b6 696 fTreeTR = dynamic_cast<TTree*>(gDirectory->Get(treeName));
aab9c8d5 697 if (!fTreeTR) {
3d8c4988 698 Warning("GetEvent","cannot find TrackReferences Tree for event:%d\n",event);
aab9c8d5 699 }
700
7a16e9cc 701 // get current file name and compare with names containing trees S,D,R
e2afb3b6 702 TString curfilname=static_cast<TString>(fTreeE->GetCurrentFile()->GetName());
7a16e9cc 703 if(fTreeDFileName==curfilname)fTreeDFileName="";
704 if(fTreeSFileName==curfilname)fTreeSFileName="";
705 if(fTreeRFileName==curfilname)fTreeRFileName="";
b9d0a01d 706
fe4da5cc 707 // Get Digits Tree header from file
708 sprintf(treeName,"TreeD%d",event);
b9d0a01d 709
7a16e9cc 710 if (!fTreeDFile && fTreeDFileName != "") {
711 InitTreeFile("D",fTreeDFileName);
712 }
713 if (fTreeDFile) {
e2afb3b6 714 fTreeD = dynamic_cast<TTree*>(fTreeDFile->Get(treeName));
7a16e9cc 715 } else {
e2afb3b6 716 fTreeD = dynamic_cast<TTree*>(file->Get(treeName));
7a16e9cc 717 }
fe4da5cc 718 if (!fTreeD) {
2ab0c725 719 // Warning("GetEvent","cannot find Digits Tree for event:%d\n",event);
fe4da5cc 720 }
7a16e9cc 721 if(fTreeDFileName != ""){
722 if(fTreeDFileName==fTreeSFileName) {
723 fTreeSFileName = "";
724 fTreeSFile = fTreeDFile;
725 }
726 if(fTreeDFileName==fTreeRFileName) {
727 fTreeRFileName = "";
728 fTreeRFile = fTreeDFile;
729 }
730 }
82711e7a 731
732 file->cd();
733
734 // Get SDigits Tree header from file
735 sprintf(treeName,"TreeS%d",event);
7a16e9cc 736 if (!fTreeSFile && fTreeSFileName != "") {
737 InitTreeFile("S",fTreeSFileName);
738 }
739 if (fTreeSFile) {
e2afb3b6 740 fTreeS = dynamic_cast<TTree*>(fTreeSFile->Get(treeName));
7a16e9cc 741 } else {
e2afb3b6 742 fTreeS = dynamic_cast<TTree*>(gDirectory->Get(treeName));
7a16e9cc 743 }
82711e7a 744 if (!fTreeS) {
745 // Warning("GetEvent","cannot find SDigits Tree for event:%d\n",event);
746 }
747
7a16e9cc 748 if(fTreeSFileName != ""){
749 if(fTreeSFileName==fTreeRFileName){
750 fTreeRFileName = "";
751 fTreeRFile = fTreeSFile;
752 }
753 }
754
2ab0c725 755 file->cd();
fe4da5cc 756
757 // Get Reconstruct Tree header from file
758 sprintf(treeName,"TreeR%d",event);
7a16e9cc 759 if (!fTreeRFile && fTreeRFileName != "") {
760 InitTreeFile("R",fTreeRFileName);
761 }
762 if(fTreeRFile) {
e2afb3b6 763 fTreeR = dynamic_cast<TTree*>(fTreeRFile->Get(treeName));
7a16e9cc 764 } else {
e2afb3b6 765 fTreeR = dynamic_cast<TTree*>(gDirectory->Get(treeName));
7a16e9cc 766 }
fe4da5cc 767 if (!fTreeR) {
768 // printf("WARNING: cannot find Reconstructed Tree for event:%d\n",event);
769 }
2ab0c725 770
771 file->cd();
fe4da5cc 772
773 // Set Trees branch addresses
8494b010 774 TIter next(fModules);
775 AliModule *detector;
e2afb3b6 776 while((detector = dynamic_cast<AliModule*>(next()))) {
fe4da5cc 777 detector->SetTreeAddress();
778 }
9e1a0ddb 779
fa85c972 780 fEvent=event; //MI change
781
eef4b160 782 return fHeader->GetNtrack();
fe4da5cc 783}
784
e2afb3b6 785//_______________________________________________________________________
fe4da5cc 786TGeometry *AliRun::GetGeometry()
787{
788 //
789 // Import Alice geometry from current file
790 // Return pointer to geometry object
791 //
e2afb3b6 792 if (!fGeometry) fGeometry = dynamic_cast<TGeometry*>(gDirectory->Get("AliceGeom"));
fe4da5cc 793 //
794 // Unlink and relink nodes in detectors
795 // This is bad and there must be a better way...
796 //
fe4da5cc 797
8494b010 798 TIter next(fModules);
799 AliModule *detector;
e2afb3b6 800 while((detector = dynamic_cast<AliModule*>(next()))) {
fe4da5cc 801 TList *dnodes=detector->Nodes();
802 Int_t j;
803 TNode *node, *node1;
804 for ( j=0; j<dnodes->GetSize(); j++) {
e2afb3b6 805 node = dynamic_cast<TNode*>(dnodes->At(j));
52d0ab00 806 node1 = fGeometry->GetNode(node->GetName());
fe4da5cc 807 dnodes->Remove(node);
808 dnodes->AddAt(node1,j);
809 }
810 }
811 return fGeometry;
812}
813
e2afb3b6 814//_______________________________________________________________________
9e1a0ddb 815Int_t AliRun::GetPrimary(Int_t track) const
fe4da5cc 816{
817 //
818 // return number of primary that has generated track
819 //
9e1a0ddb 820 return fStack->GetPrimary(track);
fe4da5cc 821}
822
e2afb3b6 823//_______________________________________________________________________
fe4da5cc 824void AliRun::MediaTable()
825{
826 //
827 // Built media table to get from the media number to
828 // the detector id
829 //
ad51aeb0 830 Int_t kz, nz, idt, lz, i, k, ind;
831 // Int_t ibeg;
fe4da5cc 832 TObjArray &dets = *gAlice->Detectors();
8494b010 833 AliModule *det;
fe4da5cc 834 //
835 // For all detectors
836 for (kz=0;kz<fNdets;kz++) {
837 // If detector is defined
e2afb3b6 838 if((det=dynamic_cast<AliModule*>(dets[kz]))) {
ad51aeb0 839 TArrayI &idtmed = *(det->GetIdtmed());
840 for(nz=0;nz<100;nz++) {
fe4da5cc 841 // Find max and min material number
ad51aeb0 842 if((idt=idtmed[nz])) {
fe4da5cc 843 det->LoMedium() = det->LoMedium() < idt ? det->LoMedium() : idt;
844 det->HiMedium() = det->HiMedium() > idt ? det->HiMedium() : idt;
845 }
846 }
847 if(det->LoMedium() > det->HiMedium()) {
848 det->LoMedium() = 0;
849 det->HiMedium() = 0;
850 } else {
851 if(det->HiMedium() > fImedia->GetSize()) {
ad51aeb0 852 Error("MediaTable","Increase fImedia from %d to %d",
853 fImedia->GetSize(),det->HiMedium());
fe4da5cc 854 return;
855 }
856 // Tag all materials in rage as belonging to detector kz
857 for(lz=det->LoMedium(); lz<= det->HiMedium(); lz++) {
858 (*fImedia)[lz]=kz;
859 }
860 }
861 }
862 }
863 //
864 // Print summary table
865 printf(" Traking media ranges:\n");
866 for(i=0;i<(fNdets-1)/6+1;i++) {
867 for(k=0;k< (6<fNdets-i*6?6:fNdets-i*6);k++) {
868 ind=i*6+k;
e2afb3b6 869 det=dynamic_cast<AliModule*>(dets[ind]);
fe4da5cc 870 if(det)
871 printf(" %6s: %3d -> %3d;",det->GetName(),det->LoMedium(),
872 det->HiMedium());
873 else
874 printf(" %6s: %3d -> %3d;","NULL",0,0);
875 }
876 printf("\n");
877 }
878}
879
e2afb3b6 880//_______________________________________________________________________
fe4da5cc 881void AliRun::SetGenerator(AliGenerator *generator)
ee1dd322 882{
883 //
884 // Load the event generator
885 //
886 if(!fGenerator) fGenerator = generator;
887}
888
e2afb3b6 889//_______________________________________________________________________
ee1dd322 890void AliRun::ResetGenerator(AliGenerator *generator)
fe4da5cc 891{
892 //
893 // Load the event generator
894 //
b13db077 895 if(fGenerator)
838edcaf 896 if(generator)
897 Warning("ResetGenerator","Replacing generator %s with %s\n",
898 fGenerator->GetName(),generator->GetName());
899 else
900 Warning("ResetGenerator","Replacing generator %s with NULL\n",
901 fGenerator->GetName());
b13db077 902 fGenerator = generator;
fe4da5cc 903}
904
e2afb3b6 905//_______________________________________________________________________
906void AliRun::SetTransPar(const char *filename)
65fb704d 907{
908 fTransParName = filename;
909}
910
e2afb3b6 911//_______________________________________________________________________
912void AliRun::SetBaseFile(const char *filename)
2ab0c725 913{
39de14fb 914 fBaseFileName = filename;
2ab0c725 915}
916
e2afb3b6 917//_______________________________________________________________________
65fb704d 918void AliRun::ReadTransPar()
fe4da5cc 919{
920 //
921 // Read filename to set the transport parameters
922 //
923
fe4da5cc 924
aee8290b 925 const Int_t kncuts=10;
926 const Int_t knflags=11;
927 const Int_t knpars=kncuts+knflags;
928 const char kpars[knpars][7] = {"CUTGAM" ,"CUTELE","CUTNEU","CUTHAD","CUTMUO",
fe4da5cc 929 "BCUTE","BCUTM","DCUTE","DCUTM","PPCUTM","ANNI",
930 "BREM","COMP","DCAY","DRAY","HADR","LOSS",
931 "MULS","PAIR","PHOT","RAYL"};
932 char line[256];
ad51aeb0 933 char detName[7];
fe4da5cc 934 char* filtmp;
aee8290b 935 Float_t cut[kncuts];
936 Int_t flag[knflags];
fe4da5cc 937 Int_t i, itmed, iret, ktmed, kz;
938 FILE *lun;
939 //
940 // See whether the file is there
65fb704d 941 filtmp=gSystem->ExpandPathName(fTransParName.Data());
fe4da5cc 942 lun=fopen(filtmp,"r");
943 delete [] filtmp;
944 if(!lun) {
65fb704d 945 Warning("ReadTransPar","File %s does not exist!\n",fTransParName.Data());
fe4da5cc 946 return;
947 }
948 //
9e1a0ddb 949 if(fDebug) {
950 printf(" "); for(i=0;i<60;i++) printf("*"); printf("\n");
951 printf(" *%59s\n","*");
952 printf(" * Please check carefully what you are doing!%10s\n","*");
953 printf(" *%59s\n","*");
954 }
fe4da5cc 955 //
956 while(1) {
957 // Initialise cuts and flags
aee8290b 958 for(i=0;i<kncuts;i++) cut[i]=-99;
959 for(i=0;i<knflags;i++) flag[i]=-99;
fe4da5cc 960 itmed=0;
961 for(i=0;i<256;i++) line[i]='\0';
962 // Read up to the end of line excluded
963 iret=fscanf(lun,"%[^\n]",line);
964 if(iret<0) {
965 //End of file
966 fclose(lun);
9e1a0ddb 967 if(fDebug){
968 printf(" *%59s\n","*");
969 printf(" "); for(i=0;i<60;i++) printf("*"); printf("\n");
970 }
fe4da5cc 971 return;
972 }
973 // Read the end of line
974 fscanf(lun,"%*c");
975 if(!iret) continue;
976 if(line[0]=='*') continue;
977 // Read the numbers
ad51aeb0 978 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",
979 detName,&itmed,&cut[0],&cut[1],&cut[2],&cut[3],&cut[4],&cut[5],&cut[6],&cut[7],&cut[8],
980 &cut[9],&flag[0],&flag[1],&flag[2],&flag[3],&flag[4],&flag[5],&flag[6],&flag[7],
981 &flag[8],&flag[9],&flag[10]);
fe4da5cc 982 if(!iret) continue;
983 if(iret<0) {
984 //reading error
65fb704d 985 Warning("ReadTransPar","Error reading file %s\n",fTransParName.Data());
fe4da5cc 986 continue;
987 }
ad51aeb0 988 // Check that the module exist
989 AliModule *mod = GetModule(detName);
990 if(mod) {
991 // Get the array of media numbers
992 TArrayI &idtmed = *mod->GetIdtmed();
993 // Check that the tracking medium code is valid
994 if(0<=itmed && itmed < 100) {
995 ktmed=idtmed[itmed];
996 if(!ktmed) {
65fb704d 997 Warning("ReadTransPar","Invalid tracking medium code %d for %s\n",itmed,mod->GetName());
ad51aeb0 998 continue;
fe4da5cc 999 }
ad51aeb0 1000 // Set energy thresholds
aee8290b 1001 for(kz=0;kz<kncuts;kz++) {
ad51aeb0 1002 if(cut[kz]>=0) {
9e1a0ddb 1003 if(fDebug) printf(" * %-6s set to %10.3E for tracking medium code %4d for %s\n",
aee8290b 1004 kpars[kz],cut[kz],itmed,mod->GetName());
1005 gMC->Gstpar(ktmed,kpars[kz],cut[kz]);
ad51aeb0 1006 }
fe4da5cc 1007 }
ad51aeb0 1008 // Set transport mechanisms
aee8290b 1009 for(kz=0;kz<knflags;kz++) {
ad51aeb0 1010 if(flag[kz]>=0) {
9e1a0ddb 1011 if(fDebug) printf(" * %-6s set to %10d for tracking medium code %4d for %s\n",
aee8290b 1012 kpars[kncuts+kz],flag[kz],itmed,mod->GetName());
1013 gMC->Gstpar(ktmed,kpars[kncuts+kz],Float_t(flag[kz]));
ad51aeb0 1014 }
1015 }
1016 } else {
65fb704d 1017 Warning("ReadTransPar","Invalid medium code %d *\n",itmed);
ad51aeb0 1018 continue;
fe4da5cc 1019 }
1020 } else {
9e1a0ddb 1021 if(fDebug) printf("%s::ReadTransParModule: %s not present\n",ClassName(),detName);
fe4da5cc 1022 continue;
1023 }
1024 }
1025}
1026
2ab0c725 1027
e2afb3b6 1028//_______________________________________________________________________
9e1a0ddb 1029void AliRun::MakeTree(Option_t *option, const char *file)
fe4da5cc 1030{
1031 //
1032 // Create the ROOT trees
1033 // Loop on all detectors to create the Root branch (if any)
1034 //
1035
b13db077 1036 char hname[30];
fe4da5cc 1037 //
1038 // Analyse options
5cf7bbad 1039 const char *oK = strstr(option,"K");
1040 const char *oH = strstr(option,"H");
aab9c8d5 1041 const char *oTR = strstr(option,"T");
5cf7bbad 1042 const char *oE = strstr(option,"E");
1043 const char *oD = strstr(option,"D");
1044 const char *oR = strstr(option,"R");
1045 const char *oS = strstr(option,"S");
fe4da5cc 1046 //
9e1a0ddb 1047
1048 TDirectory *cwd = gDirectory;
1049
1050 TBranch *branch = 0;
2ab0c725 1051
9e1a0ddb 1052 if (oK) fStack->MakeTree(fEvent, file);
1053
1054 if (oE && !fTreeE) {
1055 fTreeE = new TTree("TE","Header");
62016442 1056 // branch = fTreeE->Branch("Header", "AliHeader", &fHeader, 4000, 0);
21e74529 1057 branch = fTreeE->Branch("Header", "AliHeader", &fHeader, 4000, 0);
9e1a0ddb 1058 branch->SetAutoDelete(kFALSE);
e2afb3b6 1059 TFolder *folder = dynamic_cast<TFolder *>(gROOT->FindObjectAny("/Folders/RunMC/Event/Header"));
9e1a0ddb 1060 if (folder) folder->Add(fHeader);
1061// branch = fTreeE->Branch("Stack","AliStack", &fStack, 4000, 0);
1062// branch->SetAutoDelete(kFALSE);
1063// if (folder) folder->Add(fStack);
1064 fTreeE->Write(0,TObject::kOverwrite);
b13db077 1065 }
9e1a0ddb 1066
1067 if (file && branch) {
1068 char * outFile = new char[strlen(gAlice->GetBaseFile())+strlen(file)+2];
1069 sprintf(outFile,"%s/%s",GetBaseFile(),file);
1070 branch->SetFile(outFile);
1071 TIter next( branch->GetListOfBranches());
e2afb3b6 1072 while ((branch=dynamic_cast<TBranch*>(next()))) {
9e1a0ddb 1073 branch->SetFile(outFile);
1074 }
1075 if (GetDebug()>1)
1076 printf("* MakeBranch * Diverting Branch %s to file %s\n", branch->GetName(),file);
1077 cwd->cd();
1078 delete outFile;
1079 }
1080
aee8290b 1081 if (oH && !fTreeH) {
b13db077 1082 sprintf(hname,"TreeH%d",fEvent);
1083 fTreeH = new TTree(hname,"Hits");
1084 fTreeH->SetAutoSave(1000000000); //no autosave
9e1a0ddb 1085 fTreeH->Write(0,TObject::kOverwrite);
b13db077 1086 }
aab9c8d5 1087
1088 if (oTR && !fTreeTR) {
1089 sprintf(hname,"TreeTR%d",fEvent);
1090 fTreeTR = new TTree(hname,"TrackReferences");
1091 fTreeTR->SetAutoSave(1000000000); //no autosave
1092 fTreeTR->Write(0,TObject::kOverwrite);
1093 }
1094
aee8290b 1095 if (oD && !fTreeD) {
b13db077 1096 sprintf(hname,"TreeD%d",fEvent);
1097 fTreeD = new TTree(hname,"Digits");
9e1a0ddb 1098 fTreeD->Write(0,TObject::kOverwrite);
b13db077 1099 }
2ab0c725 1100 if (oS && !fTreeS) {
1101 sprintf(hname,"TreeS%d",fEvent);
1102 fTreeS = new TTree(hname,"SDigits");
9e1a0ddb 1103 fTreeS->Write(0,TObject::kOverwrite);
2ab0c725 1104 }
aee8290b 1105 if (oR && !fTreeR) {
b13db077 1106 sprintf(hname,"TreeR%d",fEvent);
1107 fTreeR = new TTree(hname,"Reconstruction");
9e1a0ddb 1108 fTreeR->Write(0,TObject::kOverwrite);
b13db077 1109 }
9e1a0ddb 1110
fe4da5cc 1111 //
1112 // Create a branch for hits/digits for each detector
1113 // Each branch is a TClonesArray. Each data member of the Hits classes
1114 // will be in turn a subbranch of the detector master branch
8494b010 1115 TIter next(fModules);
1116 AliModule *detector;
e2afb3b6 1117 while((detector = dynamic_cast<AliModule*>(next()))) {
b9d0a01d 1118 if (oH) detector->MakeBranch(option,file);
aab9c8d5 1119 if (oTR) detector->MakeBranchTR(option,file);
fe4da5cc 1120 }
fe4da5cc 1121}
1122
e2afb3b6 1123//_______________________________________________________________________
b5c5eebc 1124TParticle* AliRun::Particle(Int_t i)
2ab0c725 1125{
9e1a0ddb 1126 return fStack->Particle(i);
fe4da5cc 1127}
1128
e2afb3b6 1129//_______________________________________________________________________
b9d0a01d 1130void AliRun::ResetDigits()
fe4da5cc 1131{
1132 //
b9d0a01d 1133 // Reset all Detectors digits
fe4da5cc 1134 //
b9d0a01d 1135 TIter next(fModules);
1136 AliModule *detector;
e2afb3b6 1137 while((detector = dynamic_cast<AliModule*>(next()))) {
b9d0a01d 1138 detector->ResetDigits();
1139 }
1140}
1141
e2afb3b6 1142//_______________________________________________________________________
b9d0a01d 1143void AliRun::ResetSDigits()
1144{
dffd31ef 1145 //
b9d0a01d 1146 // Reset all Detectors digits
9e1a0ddb 1147 //
b9d0a01d 1148 TIter next(fModules);
1149 AliModule *detector;
e2afb3b6 1150 while((detector = dynamic_cast<AliModule*>(next()))) {
b9d0a01d 1151 detector->ResetSDigits();
1152 }
1153}
dffd31ef 1154
e2afb3b6 1155//_______________________________________________________________________
b9d0a01d 1156void AliRun::ResetHits()
1157{
dffd31ef 1158 //
b9d0a01d 1159 // Reset all Detectors hits
1160 //
1161 TIter next(fModules);
1162 AliModule *detector;
e2afb3b6 1163 while((detector = dynamic_cast<AliModule*>(next()))) {
b9d0a01d 1164 detector->ResetHits();
dffd31ef 1165 }
b9d0a01d 1166}
dffd31ef 1167
e2afb3b6 1168//_______________________________________________________________________
b9d0a01d 1169void AliRun::ResetTrackReferences()
1170{
59fe9bd2 1171 //
b9d0a01d 1172 // Reset all Detectors hits
1173 //
1174 TIter next(fModules);
1175 AliModule *detector;
e2afb3b6 1176 while((detector = dynamic_cast<AliModule*>(next()))) {
b9d0a01d 1177 detector->ResetTrackReferences();
1178 }
1179}
9e1a0ddb 1180
e2afb3b6 1181//_______________________________________________________________________
b9d0a01d 1182void AliRun::ResetPoints()
fe4da5cc 1183{
1184 //
b9d0a01d 1185 // Reset all Detectors points
fe4da5cc 1186 //
8494b010 1187 TIter next(fModules);
1188 AliModule *detector;
e2afb3b6 1189 while((detector = dynamic_cast<AliModule*>(next()))) {
b9d0a01d 1190 detector->ResetPoints();
fe4da5cc 1191 }
1192}
1193
e2afb3b6 1194//_______________________________________________________________________
b9d0a01d 1195void AliRun::InitMC(const char *setup)
2ab0c725 1196{
1197 //
b9d0a01d 1198 // Initialize the Alice setup
2ab0c725 1199 //
2ab0c725 1200
b9d0a01d 1201 if(fInitDone) {
1202 Warning("Init","Cannot initialise AliRun twice!\n");
1203 return;
fe4da5cc 1204 }
b9d0a01d 1205
1206 gROOT->LoadMacro(setup);
1207 gInterpreter->ProcessLine(fConfigFunction.Data());
fe4da5cc 1208
b9d0a01d 1209 // Register MC in configuration
1210 AliConfig::Instance()->Add(gMC);
1211 gMC->SetStack(fStack);
aab9c8d5 1212
b9d0a01d 1213 gMC->DefineParticles(); //Create standard MC particles
141f90e3 1214 AliPDG::AddParticlesToPdgDataBase();
aab9c8d5 1215
b9d0a01d 1216 TObject *objfirst, *objlast;
1217
1218 fNdets = fModules->GetLast()+1;
aab9c8d5 1219
fe4da5cc 1220 //
b9d0a01d 1221 //=================Create Materials and geometry
1222 gMC->Init();
1223
1224 // Added also after in case of interactive initialisation of modules
1225 fNdets = fModules->GetLast()+1;
1226
1227 TIter next(fModules);
1228 AliModule *detector;
e2afb3b6 1229 while((detector = dynamic_cast<AliModule*>(next()))) {
b9d0a01d 1230 detector->SetTreeAddress();
1231 objlast = gDirectory->GetList()->Last();
1232
1233 // Add Detector histograms in Detector list of histograms
1234 if (objlast) objfirst = gDirectory->GetList()->After(objlast);
1235 else objfirst = gDirectory->GetList()->First();
1236 while (objfirst) {
1237 detector->Histograms()->Add(objfirst);
1238 objfirst = gDirectory->GetList()->After(objfirst);
1239 }
1240 }
1241 ReadTransPar(); //Read the cuts for all materials
1242
1243 MediaTable(); //Build the special IMEDIA table
1244
1245 //Initialise geometry deposition table
1246 fEventEnergy.Set(gMC->NofVolumes()+1);
1247 fSummEnergy.Set(gMC->NofVolumes()+1);
1248 fSum2Energy.Set(gMC->NofVolumes()+1);
1249
1250 //Compute cross-sections
1251 gMC->BuildPhysics();
1252
1253 //Write Geometry object to current file.
1254 fGeometry->Write();
1255
1256 fInitDone = kTRUE;
1257
1258 fMCQA = new AliMCQA(fNdets);
1259
1260 AliConfig::Instance();
1261 //
1262 // Save stuff at the beginning of the file to avoid file corruption
1263 Write();
fe4da5cc 1264}
1265
e2afb3b6 1266//_______________________________________________________________________
875c717b 1267void AliRun::RunMC(Int_t nevent, const char *setup)
fe4da5cc 1268{
1269 //
1270 // Main function to be called to process a galice run
1271 // example
1272 // Root > gAlice.Run();
1273 // a positive number of events will cause the finish routine
1274 // to be called
1275 //
6df200c3 1276 fEventsPerRun = nevent;
fe4da5cc 1277 // check if initialisation has been done
875c717b 1278 if (!fInitDone) InitMC(setup);
fe4da5cc 1279
fe4da5cc 1280 // Create the Root Tree with one branch per detector
2ab0c725 1281
b9d0a01d 1282 MakeTree("ESDRT");
d47c658f 1283
2ab0c725 1284 if (gSystem->Getenv("CONFIG_SPLIT_FILE")) {
39de14fb 1285 MakeTree("K","Kine.root");
1286 MakeTree("H","Hits.root");
2ab0c725 1287 } else {
d47c658f 1288 MakeTree("KH");
2ab0c725 1289 }
fe4da5cc 1290
875c717b 1291 gMC->ProcessRun(nevent);
1292
fe4da5cc 1293 // End of this run, close files
80762cb1 1294 if(nevent>0) FinishRun();
fe4da5cc 1295}
1296
e2afb3b6 1297//_______________________________________________________________________
27f087a9 1298void AliRun::RunReco(const char *selected, Int_t first, Int_t last)
d47c658f 1299{
1300 //
1301 // Main function to be called to reconstruct Alice event
27f087a9 1302 //
1303 cout << "Found "<< gAlice->TreeE()->GetEntries() << "events" << endl;
1304 Int_t nFirst = first;
e2afb3b6 1305 Int_t nLast = (last < 0)? static_cast<Int_t>(gAlice->TreeE()->GetEntries()) : last;
27f087a9 1306
1307 for (Int_t nevent = nFirst; nevent <= nLast; nevent++) {
1308 cout << "Processing event "<< nevent << endl;
9e1a0ddb 1309 GetEvent(nevent);
1310 // MakeTree("R");
1311 Digits2Reco(selected);
1312 }
d47c658f 1313}
1314
e2afb3b6 1315//_______________________________________________________________________
2ab0c725 1316
1317void AliRun::Hits2Digits(const char *selected)
1318{
9e1a0ddb 1319
d47c658f 1320 // Convert Hits to sumable digits
1321 //
9e1a0ddb 1322 for (Int_t nevent=0; nevent<gAlice->TreeE()->GetEntries(); nevent++) {
1323 GetEvent(nevent);
1324 // MakeTree("D");
1325 Hits2SDigits(selected);
1326 SDigits2Digits(selected);
1327 }
2ab0c725 1328}
1329
d47c658f 1330
e2afb3b6 1331//_______________________________________________________________________
2ab0c725 1332
d47c658f 1333void AliRun::Tree2Tree(Option_t *option, const char *selected)
2ab0c725 1334{
1335 //
d47c658f 1336 // Function to transform the content of
1337 //
1338 // - TreeH to TreeS (option "S")
1339 // - TreeS to TreeD (option "D")
1340 // - TreeD to TreeR (option "R")
1341 //
1342 // If multiple options are specified ("SDR"), transformation will be done in sequence for
1343 // selected detector and for all detectors if none is selected (detector string
1344 // can contain blank separated list of detector names).
2ab0c725 1345
2ab0c725 1346
5cf7bbad 1347 const char *oS = strstr(option,"S");
1348 const char *oD = strstr(option,"D");
1349 const char *oR = strstr(option,"R");
2ab0c725 1350
9e1a0ddb 1351 TObjArray *detectors = Detectors();
2ab0c725 1352
1353 TIter next(detectors);
1354
d47c658f 1355 AliDetector *detector = 0;
2ab0c725 1356
1357 TDirectory *cwd = gDirectory;
1358
3e4186da 1359 TObject *obj;
1360
d47c658f 1361 char outFile[32];
2ab0c725 1362
3e4186da 1363 while((obj = next())) {
1364 if (!dynamic_cast<AliModule*>(obj))
1365 Fatal("Tree2Tree","Wrong type in fModules array\n");
1366 if (!(detector = dynamic_cast<AliDetector*>(obj))) continue;
d47c658f 1367 if (selected)
2ab0c725 1368 if (strcmp(detector->GetName(),selected)) continue;
3e4186da 1369 if (!detector->IsActive()) continue;
1370 if (gSystem->Getenv("CONFIG_SPLIT_FILE")) {
9e1a0ddb 1371 if (oS) {
3e4186da 1372 sprintf(outFile,"SDigits.%s.root",detector->GetName());
1373 detector->MakeBranch("S",outFile);
1374 }
9e1a0ddb 1375 if (oD) {
3e4186da 1376 sprintf(outFile,"Digits.%s.root",detector->GetName());
1377 detector->MakeBranch("D",outFile);
1378 }
9e1a0ddb 1379 if (oR) {
3e4186da 1380 sprintf(outFile,"Reco.%s.root",detector->GetName());
1381 detector->MakeBranch("R",outFile);
1382 }
1383 } else {
1384 detector->MakeBranch(option);
1385 }
1386
1387 cwd->cd();
1388
1389 if (oS) {
1390 cout << "Hits2SDigits: Processing " << detector->GetName() << "..." << endl;
1391 detector->Hits2SDigits();
1392 }
1393 if (oD) {
1394 cout << "SDigits2Digits: Processing " << detector->GetName() << "..." << endl;
1395 detector->SDigits2Digits();
1396 }
1397 if (oR) {
1398 cout << "Digits2Reco: Processing " << detector->GetName() << "..." << endl;
1399 detector->Digits2Reco();
1400 }
1401
1402 cwd->cd();
1403 }
2ab0c725 1404}
1405
e2afb3b6 1406//_______________________________________________________________________
0a520a66 1407void AliRun::RunLego(const char *setup, Int_t nc1, Float_t c1min,
1408 Float_t c1max,Int_t nc2,Float_t c2min,Float_t c2max,
1409 Float_t rmin,Float_t rmax,Float_t zmax, AliLegoGenerator* gener)
fe4da5cc 1410{
1411 //
1412 // Generates lego plots of:
1413 // - radiation length map phi vs theta
1414 // - radiation length map phi vs eta
1415 // - interaction length map
1416 // - g/cm2 length map
1417 //
1418 // ntheta bins in theta, eta
1419 // themin minimum angle in theta (degrees)
1420 // themax maximum angle in theta (degrees)
1421 // nphi bins in phi
1422 // phimin minimum angle in phi (degrees)
1423 // phimax maximum angle in phi (degrees)
1424 // rmin minimum radius
1425 // rmax maximum radius
1426 //
1427 //
1428 // The number of events generated = ntheta*nphi
1429 // run input parameters in macro setup (default="Config.C")
1430 //
1431 // Use macro "lego.C" to visualize the 3 lego plots in spherical coordinates
1432 //Begin_Html
1433 /*
1439f98e 1434 <img src="picts/AliRunLego1.gif">
fe4da5cc 1435 */
1436 //End_Html
1437 //Begin_Html
1438 /*
1439f98e 1439 <img src="picts/AliRunLego2.gif">
fe4da5cc 1440 */
1441 //End_Html
1442 //Begin_Html
1443 /*
1439f98e 1444 <img src="picts/AliRunLego3.gif">
fe4da5cc 1445 */
1446 //End_Html
1447 //
1448
1449 // check if initialisation has been done
875c717b 1450 if (!fInitDone) InitMC(setup);
838edcaf 1451 //Save current generator
1452 AliGenerator *gen=Generator();
1453
0a520a66 1454 // Set new generator
1455 if (!gener) gener = new AliLegoGenerator();
1456 ResetGenerator(gener);
1457 //
1458 // Configure Generator
1459 gener->SetRadiusRange(rmin, rmax);
1460 gener->SetZMax(zmax);
1461 gener->SetCoor1Range(nc1, c1min, c1max);
1462 gener->SetCoor2Range(nc2, c2min, c2max);
1463
1464
b13db077 1465 //Create Lego object
0a520a66 1466 fLego = new AliLego("lego",gener);
b13db077 1467
dffd31ef 1468 //Prepare MC for Lego Run
1469 gMC->InitLego();
1470
b13db077 1471 //Run Lego Object
0a520a66 1472
b9d0a01d 1473 //gMC->ProcessRun(nc1*nc2+1);
1474 gMC->ProcessRun(nc1*nc2);
fe4da5cc 1475
1476 // Create only the Root event Tree
80762cb1 1477 MakeTree("E");
fe4da5cc 1478
1479 // End of this run, close files
80762cb1 1480 FinishRun();
0a520a66 1481 // Restore current generator
1482 ResetGenerator(gen);
838edcaf 1483 // Delete Lego Object
1484 delete fLego; fLego=0;
fe4da5cc 1485}
1486
e2afb3b6 1487//_______________________________________________________________________
94de3818 1488void AliRun::SetConfigFunction(const char * config)
1489{
1490 //
1491 // Set the signature of the function contained in Config.C to configure
1492 // the run
1493 //
1494 fConfigFunction=config;
1495}
1496
e2afb3b6 1497//_______________________________________________________________________
fe4da5cc 1498void AliRun::SetCurrentTrack(Int_t track)
1499{
1500 //
1501 // Set current track number
1502 //
9e1a0ddb 1503 fStack->SetCurrentTrack(track);
fe4da5cc 1504}
1505
e2afb3b6 1506//_______________________________________________________________________
1578254f 1507void AliRun::SetTrack(Int_t done, Int_t parent, Int_t pdg, Float_t *pmom,
fe4da5cc 1508 Float_t *vpos, Float_t *polar, Float_t tof,
98490ea9 1509 TMCProcess mech, Int_t &ntr, Float_t weight, Int_t is)
fe4da5cc 1510{
9e1a0ddb 1511// Delegate to stack
1512//
b9d0a01d 1513
1514 fStack->SetTrack(done, parent, pdg, pmom, vpos, polar, tof,
1515 mech, ntr, weight, is);
fe4da5cc 1516}
1517
e2afb3b6 1518//_______________________________________________________________________
89bbad6f 1519void AliRun::SetTrack(Int_t done, Int_t parent, Int_t pdg,
1520 Double_t px, Double_t py, Double_t pz, Double_t e,
1521 Double_t vx, Double_t vy, Double_t vz, Double_t tof,
1522 Double_t polx, Double_t poly, Double_t polz,
98490ea9 1523 TMCProcess mech, Int_t &ntr, Float_t weight, Int_t is)
89bbad6f 1524{
9e1a0ddb 1525 // Delegate to stack
89bbad6f 1526 //
9e1a0ddb 1527 fStack->SetTrack(done, parent, pdg, px, py, pz, e, vx, vy, vz, tof,
47c8bcbe 1528 polx, poly, polz, mech, ntr, weight, is);
9e1a0ddb 1529
89bbad6f 1530}
1531
e2afb3b6 1532//_______________________________________________________________________
4d69d91e 1533void AliRun::SetHighWaterMark(const Int_t nt)
1534{
1535 //
1536 // Set high water mark for last track in event
9e1a0ddb 1537 fStack->SetHighWaterMark(nt);
4d69d91e 1538}
1539
e2afb3b6 1540//_______________________________________________________________________
fe4da5cc 1541void AliRun::KeepTrack(const Int_t track)
1542{
1543 //
9e1a0ddb 1544 // Delegate to stack
fe4da5cc 1545 //
9e1a0ddb 1546 fStack->KeepTrack(track);
fe4da5cc 1547}
1548
b9d0a01d 1549//
1550// MC Application
1551//
1552
e2afb3b6 1553//_______________________________________________________________________
b9d0a01d 1554void AliRun::ConstructGeometry()
1555{
1556 //
1557 // Create modules, materials, geometry
1558 //
1559
1560 TStopwatch stw;
1561 TIter next(fModules);
1562 AliModule *detector;
1563 printf("Geometry creation:\n");
e2afb3b6 1564 while((detector = dynamic_cast<AliModule*>(next()))) {
b9d0a01d 1565 stw.Start();
1566 // Initialise detector materials and geometry
1567 detector->CreateMaterials();
1568 detector->CreateGeometry();
1569 printf("%10s R:%.2fs C:%.2fs\n",
1570 detector->GetName(),stw.RealTime(),stw.CpuTime());
1571 }
1572}
1573
e2afb3b6 1574//_______________________________________________________________________
b9d0a01d 1575void AliRun::InitGeometry()
1576{
1577 //
1578 // Initialize detectors and display geometry
1579 //
1580
1581 printf("Initialisation:\n");
1582 TStopwatch stw;
1583 TIter next(fModules);
1584 AliModule *detector;
e2afb3b6 1585 while((detector = dynamic_cast<AliModule*>(next()))) {
b9d0a01d 1586 stw.Start();
1587 // Initialise detector and display geometry
1588 detector->Init();
1589 detector->BuildGeometry();
1590 printf("%10s R:%.2fs C:%.2fs\n",
1591 detector->GetName(),stw.RealTime(),stw.CpuTime());
1592 }
1593
1594}
1595
e2afb3b6 1596//_______________________________________________________________________
b9d0a01d 1597void AliRun::GeneratePrimaries()
1598{
1599 //
1600 // Generate primary particles and fill them in the stack.
1601 //
1602
1603 Generator()->Generate();
1604}
1605
e2afb3b6 1606//_______________________________________________________________________
b9d0a01d 1607void AliRun::BeginEvent()
1608{
1609 // Clean-up previous event
1610 // Energy scores
1611 fEventEnergy.Reset();
1612 // Clean detector information
1613 CleanDetectors();
1614 // Reset stack info
1615 fStack->Reset();
1616
1617
1618 //
1619 // Reset all Detectors & kinematics & trees
1620 //
1621 char hname[30];
1622 //
1623 // Initialise event header
1624 fHeader->Reset(fRun,fEvent,fEventNrInRun);
1625 //
1626 fStack->BeginEvent(fEvent);
1627
1628 //
1629 if(fLego) {
1630 fLego->BeginEvent();
1631 return;
1632 }
1633
1634 //
1635
1636 ResetHits();
1637 ResetTrackReferences();
1638 ResetDigits();
1639 ResetSDigits();
1640
1641
1642 if(fTreeH) {
1643 fTreeH->Reset();
1644 sprintf(hname,"TreeH%d",fEvent);
1645 fTreeH->SetName(hname);
1646 }
1647
1648 if(fTreeTR) {
1649 fTreeTR->Reset();
1650 sprintf(hname,"TreeTR%d",fEvent);
1651 fTreeTR->SetName(hname);
1652 }
1653
1654 if(fTreeD) {
1655 fTreeD->Reset();
1656 sprintf(hname,"TreeD%d",fEvent);
1657 fTreeD->SetName(hname);
1658 fTreeD->Write(0,TObject::kOverwrite);
1659 }
1660 if(fTreeS) {
1661 fTreeS->Reset();
1662 sprintf(hname,"TreeS%d",fEvent);
1663 fTreeS->SetName(hname);
1664 fTreeS->Write(0,TObject::kOverwrite);
1665 }
1666 if(fTreeR) {
1667 fTreeR->Reset();
1668 sprintf(hname,"TreeR%d",fEvent);
1669 fTreeR->SetName(hname);
1670 fTreeR->Write(0,TObject::kOverwrite);
1671 }
1672}
1673
e2afb3b6 1674//_______________________________________________________________________
b9d0a01d 1675void AliRun::BeginPrimary()
1676{
1677 //
1678 // Called at the beginning of each primary track
1679 //
1680
1681 // Reset Hits info
1682 gAlice->ResetHits();
1683 gAlice->ResetTrackReferences();
1684
1685}
1686
e2afb3b6 1687//_______________________________________________________________________
b9d0a01d 1688void AliRun::PreTrack()
1689{
116cbefd 1690 //
1691 // Method called before each track
1692 //
1693 TObjArray &dets = *fModules;
1694 AliModule *module;
1695
1696 for(Int_t i=0; i<=fNdets; i++)
1697 if((module = dynamic_cast<AliModule*>(dets[i])))
1698 module->PreTrack();
1699
1700 fMCQA->PreTrack();
b9d0a01d 1701}
1702
e2afb3b6 1703//_______________________________________________________________________
b9d0a01d 1704void AliRun::Stepping()
fe4da5cc 1705{
1706 //
1707 // Called at every step during transport
1708 //
1709
b9d0a01d 1710 Int_t id = DetFromMate(gMC->GetMedium());
1711 if (id < 0) return;
1712
fe4da5cc 1713 //
1714 // --- If lego option, do it and leave
b13db077 1715 if (fLego)
fe4da5cc 1716 fLego->StepManager();
b13db077 1717 else {
1718 Int_t copy;
1719 //Update energy deposition tables
875c717b 1720 AddEnergyDeposit(gMC->CurrentVolID(copy),gMC->Edep());
fe4da5cc 1721
b13db077 1722 //Call the appropriate stepping routine;
e2afb3b6 1723 AliModule *det = dynamic_cast<AliModule*>(fModules->At(id));
3f754d83 1724 if(det && det->StepManagerIsEnabled()) {
65fb704d 1725 fMCQA->StepManager(id);
1726 det->StepManager();
1727 }
fe4da5cc 1728 }
fe4da5cc 1729}
1730
e2afb3b6 1731//_______________________________________________________________________
b9d0a01d 1732void AliRun::PostTrack()
1733{
116cbefd 1734 //
1735 // Called after a track has been trasported
1736 //
1737 TObjArray &dets = *fModules;
1738 AliModule *module;
1739
1740 for(Int_t i=0; i<=fNdets; i++)
1741 if((module = dynamic_cast<AliModule*>(dets[i])))
1742 module->PostTrack();
b9d0a01d 1743}
1744
e2afb3b6 1745//_______________________________________________________________________
b9d0a01d 1746void AliRun::FinishPrimary()
1747{
1748 //
1749 // Called at the end of each primary track
1750 //
1751
1752 // static Int_t count=0;
1753 // const Int_t times=10;
1754 // This primary is finished, purify stack
1755 fStack->PurifyKine();
1756
1757 TIter next(fModules);
1758 AliModule *detector;
e2afb3b6 1759 while((detector = dynamic_cast<AliModule*>(next()))) {
b9d0a01d 1760 detector->FinishPrimary();
1761 }
1762
1763 // Write out hits if any
1764 if (gAlice->TreeH()) {
1765 gAlice->TreeH()->Fill();
1766 }
1767
1768 // Write out hits if any
1769 if (gAlice->TreeTR()) {
1770 gAlice->TreeTR()->Fill();
1771 }
1772
1773 //
1774 // if(++count%times==1) gObjectTable->Print();
1775}
1776
e2afb3b6 1777//_______________________________________________________________________
b9d0a01d 1778void AliRun::FinishEvent()
1779{
1780 //
1781 // Called at the end of the event.
1782 //
1783
1784 //
1785 if(fLego) fLego->FinishEvent();
1786
1787 //Update the energy deposit tables
1788 Int_t i;
1789 for(i=0;i<fEventEnergy.GetSize();i++) {
1790 fSummEnergy[i]+=fEventEnergy[i];
1791 fSum2Energy[i]+=fEventEnergy[i]*fEventEnergy[i];
1792 }
1793
1794
1795
1796 // Update Header information
1797
1798 fHeader->SetNprimary(fStack->GetNprimary());
1799 fHeader->SetNtrack(fStack->GetNtrack());
1800
1801
1802 // Write out the kinematics
1803 fStack->FinishEvent();
1804
1805 // Write out the event Header information
1806 if (fTreeE) {
1807 fHeader->SetStack(fStack);
1808 fTreeE->Fill();
1809 }
1810
1811
1812 // Write Tree headers
1813 TTree* pTreeK = fStack->TreeK();
1814 if (pTreeK) pTreeK->Write(0,TObject::kOverwrite);
1815 if (fTreeH) fTreeH->Write(0,TObject::kOverwrite);
1816 if (fTreeTR) fTreeTR->Write(0,TObject::kOverwrite);
1817
1818 ++fEvent;
1819 ++fEventNrInRun;
1820}
1821
e2afb3b6 1822//_______________________________________________________________________
b9d0a01d 1823void AliRun::Field(const Double_t* x, Double_t *b) const
1824{
116cbefd 1825 //
1826 // Returns the magnetic field at point x[3]
1827 // Units are kGauss
1828 //
1829 Float_t xfloat[3];
1830 for (Int_t i=0; i<3; i++) xfloat[i] = x[i];
1831
1832 if (Field()) {
1833 Float_t bfloat[3];
1834 Field()->Field(xfloat,bfloat);
1835 for (Int_t j=0; j<3; j++) b[j] = bfloat[j];
1836 }
1837 else {
1838 printf("No mag field defined!\n");
1839 b[0]=b[1]=b[2]=0.;
1840 }
b9d0a01d 1841
1842}
1843
1844//
1845// End of MC Application
1846//
1847
e2afb3b6 1848//_______________________________________________________________________
fe4da5cc 1849void AliRun::Streamer(TBuffer &R__b)
1850{
eef4b160 1851 // Stream an object of class AliRun.
2ab0c725 1852
7e90ff59 1853 if (R__b.IsReading()) {
1854 if (!gAlice) gAlice = this;
eef4b160 1855
7e90ff59 1856 AliRun::Class()->ReadBuffer(R__b, this);
1857 //
1858 gROOT->GetListOfBrowsables()->Add(this,"Run");
eef4b160 1859
e2afb3b6 1860 fTreeE = dynamic_cast<TTree*>(gDirectory->Get("TE"));
7e90ff59 1861 if (fTreeE) {
eef4b160 1862 fTreeE->SetBranchAddress("Header", &fHeader);
b9d0a01d 1863 }
7e90ff59 1864 else Error("Streamer","cannot find Header Tree\n");
b9d0a01d 1865
7e90ff59 1866 fTreeE->GetEntry(0);
7e90ff59 1867 gRandom = fRandom;
1868 } else {
eef4b160 1869 AliRun::Class()->WriteBuffer(R__b, this);
1870 }
2ab0c725 1871}
1872
9e1a0ddb 1873
e2afb3b6 1874//_______________________________________________________________________
9e1a0ddb 1875Int_t AliRun::CurrentTrack() const {
1876 //
1877 // Returns current track
1878 //
1879 return fStack->CurrentTrack();
1880}
1881
e2afb3b6 1882//_______________________________________________________________________
9e1a0ddb 1883Int_t AliRun::GetNtrack() const {
1884 //
1885 // Returns number of tracks in stack
1886 //
1887 return fStack->GetNtrack();
1888}
1889
e2afb3b6 1890//_______________________________________________________________________
9e1a0ddb 1891TObjArray* AliRun::Particles() {
1892 //
1893 // Returns pointer to Particles array
1894 //
1895 return fStack->Particles();
1896}
1897
e2afb3b6 1898//_______________________________________________________________________
9e1a0ddb 1899TTree* AliRun::TreeK() {
1900 //
1901 // Returns pointer to the TreeK array
1902 //
1903 return fStack->TreeK();
1904}
27f087a9 1905
b9d0a01d 1906
e2afb3b6 1907//_______________________________________________________________________
27f087a9 1908void AliRun::SetGenEventHeader(AliGenEventHeader* header)
1909{
1910 fHeader->SetGenEventHeader(header);
1911}
b9d0a01d 1912
e2afb3b6 1913//_______________________________________________________________________
7a16e9cc 1914TFile* AliRun::InitFile(TString fileName)
1915{
1916//
1917// create the file where the whole tree will be saved
1918//
1919 TDirectory *wd = gDirectory;
1920 TFile* file = TFile::Open(fileName,"update");
1921 gDirectory = wd;
1922 if (!file->IsOpen()) {
1923 Error("Cannot open file, %s\n",fileName);
1924 return 0;
1925 }
1926 return file;
1927}
1928
e2afb3b6 1929//_______________________________________________________________________
7a16e9cc 1930TFile* AliRun::InitTreeFile(Option_t *option, TString fileName)
1931{
1932 //
1933 // create the file where one of the following trees will be saved
1934 // trees: S,D,R
0592d1ca 1935 // WARNING: by default these trees are saved on the file on which
1936 // hits are stored. If you divert one of these trees, you cannot restore
1937 // it to the original file (usually galice.root) in the same aliroot session
7a16e9cc 1938 Bool_t oS = (strstr(option,"S")!=0);
1939 Bool_t oR = (strstr(option,"R")!=0);
1940 Bool_t oD = (strstr(option,"D")!=0);
0592d1ca 1941 Int_t choice[3];
1942 for (Int_t i=0; i<3; i++) choice[i] = 0;
1943 if(oS)choice[0] = 1;
1944 if(oD)choice[1] = 1;
1945 if(oR)choice[2] = 1;
1946
7a16e9cc 1947 TFile *ptr=0;
0592d1ca 1948
1949 if(!(oS || oR || oD))return ptr;
1950
1951 Int_t active[3];
1952 for (Int_t i=0; i<3; i++) active[i] = 0;
1953 if(fTreeSFileName != "") active[0] = 1;
1954 if(fTreeDFileName != "") active[1] = 1;
1955 if(fTreeDFileName != "") active[2] = 1;
1956
1957 Bool_t alreadyopen1 = kFALSE;
1958 Bool_t alreadyopen2 = kFALSE;
1959
1960 if(oS){
1961 // if already active and same name with non-null ptr
1962 if(active[0]==1 && fileName == fTreeSFileName && fTreeSFile){
1963 Warning("InitTreeFile","File %s already opened",fTreeSFileName.Data());
7a16e9cc 1964 ptr = fTreeSFile;
1965 }
0592d1ca 1966 else {
1967 // if already active with different name with non-null ptr
1968 if(active[0]==1 && fileName != fTreeSFileName && fTreeSFile){
1969 // close the active files and also the other possible files in option
1970 CloseTreeFile(option);
1971 }
1972 fTreeSFileName = fileName;
1973 alreadyopen1 =
1974 (active[1] == 1 && fTreeDFileName == fTreeSFileName && fTreeDFile);
1975 alreadyopen2 =
1976 (active[2] == 1 && fTreeRFileName == fTreeSFileName && fTreeRFile);
1977 if(!(alreadyopen1 || alreadyopen2)){
1978 ptr = InitFile(fileName);
1979 fTreeSFile = ptr;
7a16e9cc 1980 }
0592d1ca 1981 else {
1982 if(alreadyopen1){fTreeSFile = fTreeDFile; ptr = fTreeSFile;}
1983 if(alreadyopen2){fTreeSFile = fTreeRFile; ptr = fTreeSFile;}
1984 }
1985 if(choice[1] == 1) { fTreeDFileName = fileName; fTreeDFile = ptr;}
1986 if(choice[2] == 1) { fTreeRFileName = fileName; fTreeRFile = ptr;}
1987 }
1988 return ptr;
1989 }
1990
1991 if(oD){
1992 // if already active and same name with non-null ptr
1993 if(active[1]==1 && fileName == fTreeDFileName && fTreeDFile){
1994 Warning("InitTreeFile","File %s already opened",fTreeDFileName.Data());
7a16e9cc 1995 ptr = fTreeDFile;
1996 }
0592d1ca 1997 else {
1998 // if already active with different name with non-null ptr
1999 if(active[1]==1 && fileName != fTreeDFileName && fTreeDFile){
2000 // close the active files and also the other possible files in option
2001 CloseTreeFile(option);
2002 }
2003 fTreeDFileName = fileName;
2004 alreadyopen1 =
2005 (active[0] == 1 && fTreeSFileName == fTreeDFileName && fTreeSFile);
2006 alreadyopen2 =
2007 (active[2] == 1 && fTreeRFileName == fTreeDFileName && fTreeRFile);
2008 if(!(alreadyopen1 || alreadyopen2)){
2009 ptr = InitFile(fileName);
2010 fTreeDFile = ptr;
2011 }
2012 else {
2013 if(alreadyopen1){fTreeDFile = fTreeSFile; ptr = fTreeDFile;}
2014 if(alreadyopen2){fTreeDFile = fTreeRFile; ptr = fTreeDFile;}
7a16e9cc 2015 }
0592d1ca 2016 if(choice[2] == 1) { fTreeRFileName = fileName; fTreeRFile = ptr;}
2017 }
2018 return ptr;
2019 }
2020
2021 if(oR){
2022 // if already active and same name with non-null ptr
2023 if(active[2]==1 && fileName == fTreeRFileName && fTreeRFile){
2024 Warning("InitTreeFile","File %s already opened",fTreeRFileName.Data());
7a16e9cc 2025 ptr = fTreeRFile;
2026 }
0592d1ca 2027 else {
2028 // if already active with different name with non-null ptr
2029 if(active[2]==1 && fileName != fTreeRFileName && fTreeRFile){
2030 // close the active files and also the other possible files in option
2031 CloseTreeFile(option);
2032 }
2033 fTreeRFileName = fileName;
2034 alreadyopen1 =
2035 (active[1] == 1 && fTreeDFileName == fTreeRFileName && fTreeDFile);
2036 alreadyopen2 =
2037 (active[0]== 1 && fTreeSFileName == fTreeRFileName && fTreeSFile);
2038 if(!(alreadyopen1 || alreadyopen2)){
2039 ptr = InitFile(fileName);
2040 fTreeRFile = ptr;
2041 }
2042 else {
2043 if(alreadyopen1){fTreeRFile = fTreeDFile; ptr = fTreeRFile;}
2044 if(alreadyopen2){fTreeRFile = fTreeSFile; ptr = fTreeRFile;}
2045 }
2046 }
2047 return ptr;
7a16e9cc 2048 }
b16a1b1e 2049 return 0;
0592d1ca 2050}
b9d0a01d 2051
e2afb3b6 2052//_______________________________________________________________________
b9d0a01d 2053void AliRun::PrintTreeFile()
2054{
2055 //
2056 // prints the file names and pointer associated to S,D,R trees
2057 //
2058 cout<<"===================================================\n";
2059 TFile *file = fTreeE->GetCurrentFile();
2060 TString curfilname="";
e2afb3b6 2061 if(file)curfilname=static_cast<TString>(file->GetName());
b9d0a01d 2062 cout<<" Current tree file name: "<<curfilname<<endl;
2063 cout<<"Pointer: "<<file<<endl;
2064 cout<<" Tree S File name: "<<fTreeSFileName<<endl;
2065 cout<<"Pointer: "<<fTreeSFile<<endl<<endl;
2066 cout<<" Tree D File name: "<<fTreeDFileName<<endl;
2067 cout<<"Pointer: "<<fTreeDFile<<endl<<endl;
2068 cout<<" Tree R File name: "<<fTreeRFileName<<endl;
2069 cout<<"Pointer: "<<fTreeRFile<<endl<<endl;
2070 cout<<"===================================================\n";
2071}
e2afb3b6 2072//_______________________________________________________________________
0592d1ca 2073void AliRun::CloseTreeFile(Option_t *option)
2074{
2075 //
2076 // closes the file containing the tree specified in option
2077 // (S,D,R)
2078 //
2079 Bool_t oS = (strstr(option,"S")!=0);
2080 Bool_t oR = (strstr(option,"R")!=0);
2081 Bool_t oD = (strstr(option,"D")!=0);
2082 Bool_t none = !(oS || oR || oD);
2083 if(none)return;
2084 if(oS){
2085 fTreeSFileName = "";
2086 if(fTreeSFile){
2087 if(!((fTreeSFile == fTreeDFile) || (fTreeSFile == fTreeRFile)) &&
2088 fTreeSFile->IsOpen()){
2089 fTreeSFile->Close();
2090 delete fTreeSFile;
2091 }
2092 }
2093 fTreeSFile = 0;
2094 }
2095 if(oD){
2096 fTreeDFileName = "";
2097 if(fTreeDFile){
2098 if(!((fTreeDFile == fTreeRFile) || (fTreeDFile == fTreeSFile)) &&
2099 fTreeDFile->IsOpen()){
2100 fTreeDFile->Close();
2101 delete fTreeDFile;
2102 }
2103 }
2104 fTreeDFile = 0;
2105 }
2106 if(oR){
2107 fTreeRFileName = "";
2108 if(fTreeRFile){
2109 if(!((fTreeRFile == fTreeSFile) || (fTreeRFile == fTreeDFile)) &&
2110 fTreeRFile->IsOpen()){
2111 fTreeRFile->Close();
2112 delete fTreeRFile;
2113 }
2114 }
2115 fTreeRFile = 0;
2116 }
2117}
2118
e2afb3b6 2119//_______________________________________________________________________
7a16e9cc 2120void AliRun::MakeTree(Option_t *option, TFile *file)
2121{
2122 //
2123 // Create some trees in the separate file
2124 //
2125 const char *oD = strstr(option,"D");
2126 const char *oR = strstr(option,"R");
2127 const char *oS = strstr(option,"S");
2128
2129 TDirectory *cwd = gDirectory;
2130 char hname[30];
2131
2132 if (oD) {
2133 delete fTreeD;
2134 sprintf(hname,"TreeD%d",fEvent);
2135 file->cd();
2136 fTreeD = static_cast<TTree*>(file->Get("hname"));
2137 if (!fTreeD) {
2138 fTreeD = new TTree(hname,"Digits");
2139 fTreeD->Write(0,TObject::kOverwrite);
2140 }
2141 cwd->cd();
2142 }
2143 if (oS) {
2144 delete fTreeS;
2145 sprintf(hname,"TreeS%d",fEvent);
2146 file->cd();
2147 fTreeS = static_cast<TTree*>(file->Get("hname"));
2148 if (!fTreeS) {
2149 fTreeS = new TTree(hname,"SDigits");
2150 fTreeS->Write(0,TObject::kOverwrite);
2151 }
2152 cwd->cd();
2153 }
2154
2155 if (oR) {
2156 delete fTreeR;
2157 sprintf(hname,"TreeR%d",fEvent);
2158 file->cd();
2159 fTreeR = static_cast<TTree*>(file->Get("hname"));
2160 if (!fTreeR) {
2161 fTreeR = new TTree(hname,"RecPoint");
2162 fTreeR->Write(0,TObject::kOverwrite);
2163 }
2164 cwd->cd();
2165 }
2166}