1 /**************************************************************************
2 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
7 * Permission to use, copy, modify and distribute this software and its *
8 * documentation strictly for non-commercial purposes is hereby granted *
9 * without fee, provided that the above copyright notice appears in all *
10 * copies and that both the copyright notice and this permission notice *
11 * appear in the supporting documentation. The authors make no claims *
12 * about the suitability of this software for any purpose. It is *
13 * provided "as is" without express or implied warranty. *
14 **************************************************************************/
18 ///////////////////////////////////////////////////////////////////////////////
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. //
25 // -Supports the list of all Alice Detectors (fModules). //
26 // -Supports the list of particles (fParticles). //
27 // -Supports the Trees. //
28 // -Supports the geometry. //
29 // -Supports the event display. //
32 <img src="picts/AliRunClass.gif">
37 <img src="picts/alirun.gif">
41 ///////////////////////////////////////////////////////////////////////////////
45 #include <TDatabasePDG.h>
46 #include <TGeometry.h>
52 #include <TVirtualMC.h>
54 #include "AliDetector.h"
55 #include "AliDisplay.h"
56 #include "AliHeader.h"
58 #include "AliLegoGenerator.h"
61 #include "AliMagFCM.h"
62 #include "AliMagFDM.h"
72 //_______________________________________________________________________
89 fPDGDB(0), //Particle factory object
90 fConfigFunction("\0"),
95 // Default constructor for AliRun
97 AliConfig::Instance();//skowron 29 Feb 2002
98 //ensures that the folder structure is build
101 //_______________________________________________________________________
102 AliRun::AliRun(const AliRun& arun):
119 fPDGDB(0), //Particle factory object
120 fConfigFunction("\0"),
125 // Copy constructor for AliRun
130 //_____________________________________________________________________________
131 AliRun::AliRun(const char *name, const char *title):
138 fModules(new TObjArray(77)), // Support list for the Detectors
148 fPDGDB(TDatabasePDG::Instance()), //Particle factory object!
149 fConfigFunction("Config();"),
150 fRandom(new TRandom3()),
154 // Constructor for the main processor.
155 // Creates the geometry
156 // Creates the list of Detectors.
157 // Creates the list of particles.
162 // Set random number generator
165 if (gSystem->Getenv("CONFIG_SEED")) {
166 gRandom->SetSeed(static_cast<UInt_t>(atoi(gSystem->Getenv("CONFIG_SEED"))));
169 // Add to list of browsable
170 gROOT->GetListOfBrowsables()->Add(this,name);
171 // Create the TNode geometry for the event display
172 BuildSimpleGeometry();
174 // Create default mag field
177 // Add particle list to configuration
178 AliConfig::Instance()->Add(fPDGDB);
183 //_______________________________________________________________________
187 // Default AliRun destructor
189 gROOT->GetListOfBrowsables()->Remove(this);
193 TFolder* evfold = fRunLoader->GetEventFolder();
194 TFolder* modfold = dynamic_cast<TFolder*>(evfold->FindObjectAny(AliConfig::GetModulesFolderName()));
195 TIter next(fModules);
197 while((mod = (AliModule*)next()))
199 modfold->Remove(mod);
218 //_______________________________________________________________________
219 void AliRun::Copy(AliRun &) const
221 Fatal("Copy","Not implemented!\n");
224 //_______________________________________________________________________
228 // Initialize Alice geometry
233 //_______________________________________________________________________
234 void AliRun::BuildSimpleGeometry()
237 // Create a simple TNode geometry used by Root display engine
239 // Initialise geometry
241 fGeometry = new TGeometry("AliceGeom","Galice Geometry for Hits");
242 new TMaterial("void","Vacuum",0,0,0); //Everything is void
243 TBRIK *brik = new TBRIK("S_alice","alice volume","void",2000,2000,3000);
244 brik->SetVisibility(0);
245 new TNode("alice","alice","S_alice");
248 //_______________________________________________________________________
249 void AliRun::CleanDetectors()
252 // Clean Detectors at the end of event
254 fRunLoader->CleanDetectors();
257 //_______________________________________________________________________
258 void AliRun::ResetHits()
263 //_______________________________________________________________________
264 AliGenerator* AliRun::Generator() const
266 return fMCApp->Generator();
269 //_______________________________________________________________________
270 void AliRun::SetField(AliMagF* magField)
272 // Set Magnetic Field Map
277 //_______________________________________________________________________
278 void AliRun::SetField(Int_t type, Int_t version, Float_t scale,
279 Float_t maxField, char* filename)
282 // Set magnetic field parameters
283 // type Magnetic field transport flag 0=no field, 2=helix, 3=Runge Kutta
284 // version Magnetic field map version (only 1 active now)
285 // scale Scale factor for the magnetic field
286 // maxField Maximum value for the magnetic field
289 // --- Sanity check on mag field flags
290 if(fField) delete fField;
292 fField = new AliMagFC("Map1"," ",type,scale,maxField);
293 } else if(version<=2) {
294 fField = new AliMagFCM("Map2-3",filename,type,scale,maxField);
296 } else if(version==3) {
297 fField = new AliMagFDM("Map4",filename,type,scale,maxField);
300 Warning("SetField","Invalid map %d\n",version);
304 //_____________________________________________________________________________
306 void AliRun::InitLoaders()
308 //creates list of getters
309 if (GetDebug()) Info("InitLoaders","");
310 TIter next(fModules);
312 while((mod = (AliModule*)next()))
314 AliDetector *det = dynamic_cast<AliDetector*>(mod);
317 if (GetDebug()) Info("InitLoaders"," Adding %s ",det->GetName());
318 fRunLoader->AddLoader(det);
321 if (GetDebug()) Info("InitLoaders","Done");
323 //_____________________________________________________________________________
325 void AliRun::FinishRun()
328 // Called at the end of the run.
333 if (GetDebug()) Info("FinishRun"," Finish Lego");
334 fRunLoader->CdGAFile();
338 // Clean detector information
339 TIter next(fModules);
341 while((detector = dynamic_cast<AliModule*>(next()))) {
342 if (GetDebug()) Info("FinishRun"," %s->FinishRun()",detector->GetName());
343 detector->FinishRun();
346 if (GetDebug()) Info("FinishRun"," fRunLoader->WriteHeader(OVERWRITE)");
347 fRunLoader->WriteHeader("OVERWRITE");
349 // Write AliRun info and all detectors parameters
350 fRunLoader->CdGAFile();
351 Write(0,TObject::kOverwrite);//write AliRun
352 fRunLoader->Write(0,TObject::kOverwrite);//write RunLoader itself
354 // Clean tree information
355 if (GetDebug()) Info("FinishRun"," fRunLoader->Stack()->FinishRun()");
356 fRunLoader->Stack()->FinishRun();
358 if(fMCApp) fMCApp->FinishRun();
360 fRunLoader->Synchronize();
363 //_______________________________________________________________________
364 void AliRun::Announce() const
367 // Announce the current version of AliRoot
370 "****************************************************************\n");
371 printf("%6s","*");printf("%64s","*\n");
374 printf(" You are running AliRoot version NewIO\n");
377 printf(" The cvs tag for the current program is $Name$\n");
379 printf("%6s","*");printf("%64s","*\n");
381 "****************************************************************\n");
384 //_______________________________________________________________________
385 AliModule *AliRun::GetModule(const char *name) const
388 // Return pointer to detector from name
390 return dynamic_cast<AliModule*>(fModules->FindObject(name));
393 //_______________________________________________________________________
394 AliDetector *AliRun::GetDetector(const char *name) const
397 // Return pointer to detector from name
399 return dynamic_cast<AliDetector*>(fModules->FindObject(name));
402 //_______________________________________________________________________
403 Int_t AliRun::GetModuleID(const char *name) const
406 // Return galice internal detector identifier from name
409 TObject *mod=fModules->FindObject(name);
410 if(mod) i=fModules->IndexOf(mod);
414 //_______________________________________________________________________
415 Int_t AliRun::GetEvent(Int_t event)
418 // Reloads data containers in folders # event
419 // Set branch addresses
421 if (fRunLoader == 0x0)
423 Error("GetEvent","RunLoader is not set. Can not load data.");
426 /*****************************************/
427 /**** P R E R E L O A D I N G ****/
428 /*****************************************/
429 // Reset existing structures
431 fMCApp->ResetTrackReferences();
435 /*****************************************/
436 /**** R E L O A D ****/
437 /*****************************************/
439 fRunLoader->GetEvent(event);
441 /*****************************************/
442 /**** P O S T R E L O A D I N G ****/
443 /*****************************************/
445 // Set Trees branch addresses
446 TIter next(fModules);
448 while((detector = dynamic_cast<AliModule*>(next())))
450 detector->SetTreeAddress();
453 return fRunLoader->GetHeader()->GetNtrack();
456 //_______________________________________________________________________
457 TGeometry *AliRun::GetGeometry()
460 // Import Alice geometry from current file
461 // Return pointer to geometry object
463 if (!fGeometry) fGeometry = dynamic_cast<TGeometry*>(gDirectory->Get("AliceGeom"));
465 // Unlink and relink nodes in detectors
466 // This is bad and there must be a better way...
469 TIter next(fModules);
471 while((detector = dynamic_cast<AliModule*>(next()))) {
472 TList *dnodes=detector->Nodes();
475 for ( j=0; j<dnodes->GetSize(); j++) {
476 node = dynamic_cast<TNode*>(dnodes->At(j));
477 node1 = fGeometry->GetNode(node->GetName());
478 dnodes->Remove(node);
479 dnodes->AddAt(node1,j);
485 //_______________________________________________________________________
486 void AliRun::SetBaseFile(const char *filename)
488 fBaseFileName = filename;
491 //_______________________________________________________________________
492 void AliRun::ResetDigits()
495 // Reset all Detectors digits
497 TIter next(fModules);
499 while((detector = dynamic_cast<AliModule*>(next()))) {
500 detector->ResetDigits();
504 //_______________________________________________________________________
505 void AliRun::ResetSDigits()
508 // Reset all Detectors digits
510 TIter next(fModules);
512 while((detector = dynamic_cast<AliModule*>(next()))) {
513 detector->ResetSDigits();
518 //_______________________________________________________________________
520 void AliRun::ResetPoints()
523 // Reset all Detectors points
525 TIter next(fModules);
527 while((detector = dynamic_cast<AliModule*>(next()))) {
528 detector->ResetPoints();
531 //_______________________________________________________________________
533 void AliRun::InitMC(const char *setup)
536 // Initialize ALICE Simulation run
541 Warning("Init","Cannot initialise AliRun twice!\n");
545 fMCApp=new AliMC(GetName(),GetTitle());
547 gROOT->LoadMacro(setup);
548 gInterpreter->ProcessLine(fConfigFunction.Data());
550 fRunLoader->CdGAFile();
552 AliPDG::AddParticlesToPdgDataBase();
554 fNdets = fModules->GetLast()+1;
556 // Added also after in case of interactive initialisation of modules
557 fNdets = fModules->GetLast()+1;
559 TIter next(fModules);
560 for(Int_t i=0; i<fNdets; ++i)
562 TObject *objfirst, *objlast;
563 AliModule *detector=dynamic_cast<AliModule*>(fModules->At(i));
564 objlast = gDirectory->GetList()->Last();
566 // Add Detector histograms in Detector list of histograms
567 if (objlast) objfirst = gDirectory->GetList()->After(objlast);
568 else objfirst = gDirectory->GetList()->First();
571 detector->Histograms()->Add(objfirst);
572 objfirst = gDirectory->GetList()->After(objfirst);
578 //Must be here because some MCs (G4) adds detectors here and not in Config.C
580 fRunLoader->MakeTree("E");
583 fRunLoader->LoadKinematics("RECREATE");
584 fRunLoader->LoadTrackRefs("RECREATE");
585 fRunLoader->LoadHits("all","RECREATE");
589 // Save stuff at the beginning of the file to avoid file corruption
590 fRunLoader->CdGAFile();
592 fEventNrInRun = -1; //important - we start Begin event from increasing current number in run
595 //_______________________________________________________________________
597 void AliRun::RunMC(Int_t nevent, const char *setup)
600 // Main function to be called to process a galice run
602 // Root > gAlice.Run();
603 // a positive number of events will cause the finish routine
606 fEventsPerRun = nevent;
607 // check if initialisation has been done
608 if (!fInitDone) InitMC(setup);
610 // Create the Root Tree with one branch per detector
611 //Hits moved to begin event -> now we are crating separate tree for each event
613 gMC->ProcessRun(nevent);
615 // End of this run, close files
616 if(nevent>0) FinishRun();
619 //_______________________________________________________________________
620 void AliRun::RunReco(const char *selected, Int_t first, Int_t last)
623 // Main function to be called to reconstruct Alice event
625 Int_t nev = fRunLoader->GetNumberOfEvents();
626 if (GetDebug()) Info("RunReco","Found %d events",nev);
627 Int_t nFirst = first;
628 Int_t nLast = (last < 0)? nev : last;
630 for (Int_t nevent = nFirst; nevent <= nLast; nevent++) {
631 if (GetDebug()) Info("RunReco","Processing event %d",nevent);
633 Digits2Reco(selected);
637 //_______________________________________________________________________
639 void AliRun::Hits2Digits(const char *selected)
642 // Convert Hits to sumable digits
644 for (Int_t nevent=0; nevent<gAlice->TreeE()->GetEntries(); nevent++) {
646 Hits2SDigits(selected);
647 SDigits2Digits(selected);
652 //_______________________________________________________________________
654 void AliRun::Tree2Tree(Option_t *option, const char *selected)
657 // Function to transform the content of
659 // - TreeH to TreeS (option "S")
660 // - TreeS to TreeD (option "D")
661 // - TreeD to TreeR (option "R")
663 // If multiple options are specified ("SDR"), transformation will be done in sequence for
664 // selected detector and for all detectors if none is selected (detector string
665 // can contain blank separated list of detector names).
668 const char *oS = strstr(option,"S");
669 const char *oD = strstr(option,"D");
670 const char *oR = strstr(option,"R");
672 TObjArray *detectors = Detectors();
674 TIter next(detectors);
676 AliDetector *detector = 0;
678 while((detector = dynamic_cast<AliDetector*>(next()))) {
680 if (strcmp(detector->GetName(),selected)) continue;
681 if (detector->IsActive())
684 AliLoader* loader = detector->GetLoader();
685 if (loader == 0x0) continue;
689 if (GetDebug()) Info("Tree2Tree","Processing Hits2SDigits for %s ...",detector->GetName());
690 loader->LoadHits("read");
691 if (loader->TreeS() == 0x0) loader->MakeTree("S");
692 detector->MakeBranch(option);
693 detector->SetTreeAddress();
694 detector->Hits2SDigits();
695 loader->UnloadHits();
696 loader->UnloadSDigits();
700 if (GetDebug()) Info("Tree2Tree","Processing SDigits2Digits for %s ...",detector->GetName());
701 loader->LoadSDigits("read");
702 if (loader->TreeD() == 0x0) loader->MakeTree("D");
703 detector->MakeBranch(option);
704 detector->SetTreeAddress();
705 detector->SDigits2Digits();
706 loader->UnloadSDigits();
707 loader->UnloadDigits();
711 if (GetDebug()) Info("Tree2Tree","Processing Digits2Reco for %s ...",detector->GetName());
712 loader->LoadDigits("read");
713 if (loader->TreeR() == 0x0) loader->MakeTree("R");
714 detector->MakeBranch(option);
715 detector->SetTreeAddress();
716 detector->Digits2Reco();
717 loader->UnloadDigits();
718 loader->UnloadRecPoints();
725 //_______________________________________________________________________
726 void AliRun::RunLego(const char *setup, Int_t nc1, Float_t c1min,
727 Float_t c1max,Int_t nc2,Float_t c2min,Float_t c2max,
728 Float_t rmin,Float_t rmax,Float_t zmax, AliLegoGenerator* gener)
731 // Generates lego plots of:
732 // - radiation length map phi vs theta
733 // - radiation length map phi vs eta
734 // - interaction length map
735 // - g/cm2 length map
737 // ntheta bins in theta, eta
738 // themin minimum angle in theta (degrees)
739 // themax maximum angle in theta (degrees)
741 // phimin minimum angle in phi (degrees)
742 // phimax maximum angle in phi (degrees)
743 // rmin minimum radius
744 // rmax maximum radius
747 // The number of events generated = ntheta*nphi
748 // run input parameters in macro setup (default="Config.C")
750 // Use macro "lego.C" to visualize the 3 lego plots in spherical coordinates
753 <img src="picts/AliRunLego1.gif">
758 <img src="picts/AliRunLego2.gif">
763 <img src="picts/AliRunLego3.gif">
768 // check if initialisation has been done
769 // If runloader has been initialized, set the number of events per file to nc1 * nc2
772 if (!gener) gener = new AliLegoGenerator();
774 // Configure Generator
775 gener->SetRadiusRange(rmin, rmax);
776 gener->SetZMax(zmax);
777 gener->SetCoor1Range(nc1, c1min, c1max);
778 gener->SetCoor2Range(nc2, c2min, c2max);
782 fLego = new AliLego("lego",gener);
784 if (!fInitDone) InitMC(setup);
785 //Save current generator
787 AliGenerator *gen=fMCApp->Generator();
788 fMCApp->ResetGenerator(gener);
789 //Prepare MC for Lego Run
794 if (fRunLoader) fRunLoader->SetNumberOfEventsPerFile(nc1 * nc2);
795 //gMC->ProcessRun(nc1*nc2+1);
796 gMC->ProcessRun(nc1*nc2);
798 // End of this run, close files
800 // Restore current generator
801 fMCApp->ResetGenerator(gen);
802 // Delete Lego Object
803 delete fLego; fLego=0;
806 //_______________________________________________________________________
807 void AliRun::SetConfigFunction(const char * config)
810 // Set the signature of the function contained in Config.C to configure
813 fConfigFunction=config;
820 //_______________________________________________________________________
821 void AliRun::Field(const Double_t* x, Double_t *b) const
824 for (Int_t i=0; i<3; i++) xfloat[i] = x[i];
828 Field()->Field(xfloat,bfloat);
829 for (Int_t j=0; j<3; j++) b[j] = bfloat[j];
832 printf("No mag field defined!\n");
839 // End of MC Application
842 //_______________________________________________________________________
843 void AliRun::Streamer(TBuffer &R__b)
845 // Stream an object of class AliRun.
847 if (R__b.IsReading()) {
848 if (!gAlice) gAlice = this;
849 AliRun::Class()->ReadBuffer(R__b, this);
850 gROOT->GetListOfBrowsables()->Add(this,"Run");
854 AliRun::Class()->WriteBuffer(R__b, this);
857 //_______________________________________________________________________
859 void AliRun::SetGenEventHeader(AliGenEventHeader* header)
861 fRunLoader->GetHeader()->SetGenEventHeader(header);
863 //_______________________________________________________________________
865 Int_t AliRun::GetEvNumber() const
867 //Returns number of current event
868 if (fRunLoader == 0x0)
870 Error("GetEvent","RunLoader is not set. Can not load data.");
874 return fRunLoader->GetEventNumber();
876 //_______________________________________________________________________
878 void AliRun::SetRunLoader(AliRunLoader* rloader)
880 fRunLoader = rloader;
881 if (fRunLoader == 0x0) return;
884 TFolder* evfold = fRunLoader->GetEventFolder();
885 if (evfold) evfoldname = evfold->GetName();
886 else Warning("SetRunLoader","Did not get Event Folder from Run Loader");
888 if ( fRunLoader->GetAliRun() )
889 {//if alrun already exists in folder
890 if (fRunLoader->GetAliRun() != this )
891 {//and is different than this - crash
892 Fatal("AliRun","AliRun is already in Folder and it is not this object");
898 evfold->Add(this);//Post this AliRun to Folder
901 TIter next(fModules);
903 while((module = (AliModule*)next()))
905 if (evfold) AliConfig::Instance()->Add(module,evfoldname);
906 AliDetector* detector = dynamic_cast<AliDetector*>(module);
909 AliLoader* loader = fRunLoader->GetLoader(detector);
912 Error("SetRunLoader","Can not get loader for detector %s",detector->GetName());
916 if (GetDebug()) Info("SetRunLoader","Setting loader for detector %s",detector->GetName());
917 detector->SetLoader(loader);
923 void AliRun::AddModule(AliModule* mod)
925 if (mod == 0x0) return;
926 if (strlen(mod->GetName()) == 0) return;
927 if (GetModuleID(mod->GetName()) >= 0) return;
929 if (GetDebug()) Info("AddModule","%s",mod->GetName());
930 if (fRunLoader == 0x0) AliConfig::Instance()->Add(mod);
931 else AliConfig::Instance()->Add(mod,fRunLoader->GetEventFolder()->GetName());