Coverity fixes
[u/mrichter/AliRoot.git] / STEER / AliConfig.cxx
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
16 /* $Id$ */
17
18 //  Description:
19 //  This class is responsible for creating folder structure
20 //  All stuff of aliroot sits in one folder with name defined by
21 //  fgkTopFolderName data wich do not very trough event to event are
22 //  sitting in directly in "top folder" all data which changes from
23 //  event to event are sitting in one folder (which has more subfolders)
24 //  Idea is to have more than one event in folder structure which allows
25 //  usage of standard procedures in merging
26 //  Add(AliDetector*) calls Add(AliModule*) as AliDetector is a AliModule
27 //  as well and should be listed in module list
28
29 #include <TDatabasePDG.h>
30 #include <TFolder.h>
31 #include <TInterpreter.h>
32 #include <TObjString.h>
33 #include <TROOT.h>
34 #include <TString.h>
35 #include <TSystem.h>
36 #include <TTask.h>
37 #include <TVirtualMC.h>
38
39 #include "AliConfig.h"
40 #include "AliDetector.h"
41 #include "AliGenerator.h" 
42 #include "AliLoader.h"
43 #include "AliLog.h"
44
45 enum 
46  {
47   kDetTaskQA = 0,
48   kDetTaskSDigitizer,
49   kDetTaskDigitizer,
50   kDetTaskRecontructioner,
51   kDetTaskTracker,
52   kDetTaskPID,
53   kDetTaskLast
54  };
55
56 enum
57  {
58    kDetFolderData = 0,
59    kDetFolderCalibration,
60    kDetFolderAligmnet,
61    kDetFolderQA,
62    kDetFolderLast
63  };
64 ClassImp(AliConfig)
65
66 AliConfig* AliConfig::fgInstance = 0;
67
68 //0 level folder
69 const TString AliConfig::fgkTopFolderName("Folders");
70
71 //1st level folder
72 const TString AliConfig::fgkTasksFolderName("Tasks"); //task folder, commn
73 const TString AliConfig::fgkConstantsFolderName("Constants");
74 const TString AliConfig::fgkDefaultEventFolderName("Event");  //default folder for event, always used except merging
75
76 //2st level folder
77 //subfolder of event folder
78 const TString AliConfig::fgkDataFolderName("Data");//folder for data (hits, digits, points, tracks) grouped by detectors
79 const TString AliConfig::fgkModuleFolderName("Modules");//folder with modules objects
80 const TString AliConfig::fgkConditionsFolderName("Conditions");//folder with conditions (mag. field etc.)
81 const TString AliConfig::fgkConfigurationFolderName("Configuration");//folder with configuration (setup) of the detector
82 const TString AliConfig::fgkHeaderFolderName("Header");//folder with header and other MC information
83
84 //Tasks names, goes into fgkTasksFolderName folder
85 const TString AliConfig::fgkDigitizerTaskName("Digitizer");
86 const TString AliConfig::fgkSDigitizerTaskName("SDigitizer");
87 const TString AliConfig::fgkReconstructionerTaskName("Reconstructioner");
88 const TString AliConfig::fgkTrackerTaskName("Tracker");
89 const TString AliConfig::fgkPIDTaskName("PIDTask");//;=) PIDer???
90 const TString AliConfig::fgkQATaskName("QAtask");
91
92 //3rd level folder
93 //fgkConditionsFolderName subfolders
94 const TString AliConfig::fgkCalibrationFolderName("Calibration");
95 const TString AliConfig::fgkAligmentFolderName("Aligment");
96 const TString AliConfig::fgkQAFolderName("QAout");
97   
98 //3rd level folder
99 //fgkConfigurationFolderName subfolders
100 const TString AliConfig::fgkFieldFolderName("Field");
101 const TString AliConfig::fgkGeneratorsFolderName("Generators");
102 const TString AliConfig::fgkVirtualMCFolderName("VirtualMC");
103
104
105 const TString AliConfig::fgkPDGFolderName("Constants/DatabasePDG");//folder with PDG Database
106 const TString AliConfig::fgkGeneratorFolderName("Configuration/Generators");//folder with generators
107 const TString AliConfig::fgkMCFolderName("Configuration/VirtualMC");
108
109 //____________________________________________________________________________
110 AliConfig* AliConfig::Instance ()
111 {
112   //
113   // Instance method for singleton class
114   //
115    if(fgInstance == 0) 
116     {
117      fgInstance = new AliConfig (fgkTopFolderName,"Alice data exchange board");
118     }
119    return fgInstance;
120 }
121 //____________________________________________________________________________
122
123 AliConfig::AliConfig(const char *name, const char *title): 
124   TNamed(name,title), 
125   fTopFolder(gROOT->GetRootFolder()->AddFolder(name,title)),
126   fTaskFolder(fTopFolder->AddFolder(fgkTasksFolderName, "ALICE Tasks")),
127   fConstFolder(0x0),
128   fDetectorTask(0x0),
129   fDetectorFolder(new TString[kDetFolderLast+1])
130 {
131 // Constructor
132
133   //Main AliRoot Folder
134   if (fTopFolder == 0x0)
135    {
136      AliFatal("Can not create Top Alice Folder.");
137      return;//never reached
138    }
139   fTopFolder->SetOwner();
140   
141   fDetectorFolder[kDetFolderData] = fgkDataFolderName;
142   fDetectorFolder[kDetFolderCalibration] = fgkConditionsFolderName+"/"+fgkCalibrationFolderName;
143   fDetectorFolder[kDetFolderAligmnet] = fgkConditionsFolderName+"/"+fgkAligmentFolderName;
144   fDetectorFolder[kDetFolderQA] = fgkConditionsFolderName+"/"+fgkQAFolderName;
145   fDetectorFolder[kDetFolderLast] = "";
146   
147   gROOT->GetListOfBrowsables()->Add(fTopFolder, name);
148
149   //Constants folder
150   fConstFolder = fTopFolder->AddFolder (fgkConstantsFolderName, "Constant parameters");
151   fConstFolder->AddFolder("DatabasePDG", "PDG database");
152   
153   // Add the tasks to //Folders
154   
155   TTask * qa = new TTask(fgkQATaskName, "Alice QA tasks");
156   fTaskFolder->Add(qa); 
157   TTask * sd = new TTask(fgkSDigitizerTaskName, "Alice SDigitizer") ;
158   fTaskFolder->Add(sd); 
159   TTask * di = new TTask(fgkDigitizerTaskName, "Alice Digitizer") ;
160   fTaskFolder->Add(di); 
161   TTask * re = new TTask(fgkReconstructionerTaskName, "Alice Reconstructioner") ;
162   fTaskFolder->Add(re); 
163   TTask * tr = new TTask(fgkTrackerTaskName,"Alice Tracker");
164   fTaskFolder->Add(tr);
165   TTask * pid = new TTask(fgkPIDTaskName,"Alice Particle Identification Task");
166   fTaskFolder->Add(pid);
167   fDetectorTask    =  new TString[kDetTaskLast+1];
168   
169   fDetectorTask[kDetTaskQA] = fgkQATaskName;
170   fDetectorTask[kDetTaskSDigitizer] = fgkSDigitizerTaskName;
171   fDetectorTask[kDetTaskDigitizer] =  fgkDigitizerTaskName;
172   fDetectorTask[kDetTaskRecontructioner] = fgkReconstructionerTaskName;
173   fDetectorTask[kDetTaskTracker] = fgkTrackerTaskName;
174   fDetectorTask[kDetTaskPID] = fgkPIDTaskName;
175   fDetectorTask[kDetTaskLast] = "";
176
177   fgInstance=this;
178 }
179
180 //____________________________________________________________________________
181 AliConfig::~AliConfig()
182
183   // destructor
184   delete [] fDetectorFolder ;  
185   delete [] fDetectorTask;
186   if (fTopFolder)
187    {
188     fTopFolder->SetOwner();
189     delete fTopFolder; 
190    }
191 }
192 //____________________________________________________________________________
193
194 void AliConfig::AddInFolder (const char *dir, TObject *obj)
195 {
196   // Adds object "obj" to folder "dir"
197   TFolder *folder = dynamic_cast<TFolder *>(fTopFolder->FindObject(dir));
198   if (folder)
199     folder->Add (static_cast<TObject *>(obj));
200 }
201 //____________________________________________________________________________
202
203 Int_t AliConfig::AddSubTask(const char *taskname, const char* name,const char* title)
204 {
205 //Create new task named 'name' and titled 'title' 
206 //as a subtask of the task named 'taskname'
207
208    AliDebug(1, Form("Try to get folder named %s",taskname));
209    TObject* obj = fTopFolder->FindObject(taskname);
210    TTask * task = (obj)?dynamic_cast<TTask*>(obj):0x0;
211    if (task)
212      {
213       AliDebug(1, "          Got");
214       TTask * subtask = static_cast<TTask*>(task->GetListOfTasks()->FindObject(name));
215       if (!subtask) 
216         {
217           subtask = new TTask(name,title);
218           task->Add(subtask);
219         }
220       else
221        {
222          AliWarning(Form("Task named \"%s\" already exists in Task %s",name,taskname));
223        }
224      }
225    else
226      {
227        AliError(Form("Can not find task %s to put a new task in.",taskname));
228        return 1;
229      }
230   return 0;
231 }
232
233 //____________________________________________________________________________
234 TObject* AliConfig::FindInFolder (const char *dir, const char *name)
235 {
236   // Finds object with name "name" in folder "dir"
237   if(!name) return(fTopFolder->FindObject(name));
238   TFolder * folder = dynamic_cast<TFolder *>(fTopFolder->FindObject(dir));
239   if (!folder) return (NULL);
240   return(folder->FindObject(name));
241 }
242
243 //____________________________________________________________________________
244 void    AliConfig::Add (AliGenerator * obj,const char* eventfolder)
245 {
246   // Adds generator "obj" to the event folder "eventfolder"
247   TString path(eventfolder);
248   path = path + "/" + fgkGeneratorsFolderName;
249   AddInFolder(path,obj);
250 }
251
252 //____________________________________________________________________________
253 void AliConfig::Add (TVirtualMC * obj,const char* eventfolder)
254 {
255   // Adds TVirtualMC object to the event folder
256   TString path(eventfolder);
257   path = path + "/" + fgkMCFolderName;
258   AddInFolder(path, obj);
259 }
260
261 //____________________________________________________________________________
262 void  AliConfig::Add (TDatabasePDG * obj)
263 {
264   // Adds TDataBase object
265   AddInFolder(fgkPDGFolderName, obj);
266 }
267
268 //____________________________________________________________________________
269 void AliConfig::Add(AliModule* obj,const char* eventfolder)
270 {
271   // Adds module to the event folder
272   TString path(eventfolder);
273   path = path + "/" + fgkModuleFolderName;
274   AliDebug(1, Form("module name = %s, Ev. Fold. Name is %s.",
275                    obj->GetName(),eventfolder));
276   AddInFolder(path, obj);
277 }
278 //____________________________________________________________________________
279
280 Int_t AliConfig::AddDetector(TFolder* evntfolder, const char *name, const char* title)
281 {
282 //creates folders and tasks for the detector 'name'
283  Int_t retval;//returned value
284  retval = CreateDetectorFolders(evntfolder,name,title);
285  if (retval)
286   {
287     AliError(Form("CreateDetectorFolders returned error for detector %s",name));
288     return retval;
289   }
290  return 0; 
291 }
292 //____________________________________________________________________________
293
294 Int_t AliConfig::AddDetector(const char* evntfoldername,const char *name, const char* title)
295 {
296 //creates folders and tasks for the detector 'name'
297  Int_t retval;//returned value
298  retval = CreateDetectorFolders(evntfoldername,name,title);
299  if (retval)
300   {
301     AliError(Form("CreateDetectorFolders returned error for detector %s",name));
302     return retval;
303   }
304 // retval = CreateDetectorTasks(name,title);
305 // if (retval)
306 //  {
307 //    Error("AddDetector","CreateDetectorTasks returned error for detector %s",name);
308 //    return retval;
309 //  }
310  return 0; 
311 }
312 //____________________________________________________________________________
313
314 void  AliConfig::Add(AliDetector * obj,const char* eventfolder)
315 {
316   // Adds new AliDetector objest to the correspondent event folder
317   AliDebug(1, Form("detector name = %s, Ev. Fold. Name is %s.",
318                    obj->GetName(),eventfolder));
319
320   TObject* foundobj = GetTopFolder()->FindObject(eventfolder);
321   TFolder* evfolder = (foundobj)?dynamic_cast<TFolder*>(foundobj):0x0;
322   if (evfolder == 0x0)
323    {
324      AliFatal(Form("Can not find folder %s while adding detector %s",eventfolder,obj->GetName()));
325      return;
326    } 
327   CreateDetectorFolders(evfolder, obj->GetName(), obj->GetTitle());
328   
329 //  CreateDetectorTasks(obj->GetName(),obj->GetTitle());
330
331 }
332 //____________________________________________________________________________
333
334 Int_t  AliConfig::CreateDetectorFolders(const char* evntfoldername,const char *name, const char* title)
335 {
336 //creates a folders for detector named 'name' and titled 'title'
337 //in a event folder named 'evntfoldername'
338 //list of folder names where new folders are created is defined in fDetectorFolder array 
339 //detector folders are named 'name' and titled 'title' as well
340
341  TFolder* evfolder = dynamic_cast<TFolder*>(GetTopFolder()->FindObject(evntfoldername));
342  if (evfolder == 0x0)
343   {
344    AliError(Form("Can not find folder %s while adding detector %s",evntfoldername,name));
345    return 1;
346   }
347  return CreateDetectorFolders(evfolder,name,title);
348 }
349 //____________________________________________________________________________
350 Int_t  AliConfig::CreateDetectorFolders(TFolder* evntfolder,const char *name, const char* title)
351 {
352 //creates a folders for detector named 'name' and titled 'title'
353 //in a event folder 'evntfolder'
354 //list of folder names where new folders are created is defined in fDetectorFolder array 
355 //detector folders are named 'name' and titled 'title' as well
356 //Here we add only detector not an modules
357  
358  Int_t tmp;
359  Int_t i = 0;//iterator
360  while(!fDetectorFolder[i].IsNull())
361   {
362     tmp = AddSubFolder(evntfolder,fDetectorFolder[i],name,title);
363     if (tmp)
364      {
365       AliError(Form("Failed to create subfolder of %s for detector %s",fDetectorFolder[i].Data(),name));
366       return 1;
367      }
368     i++;
369   }
370  return 0;
371 }
372 //____________________________________________________________________________
373 Int_t AliConfig::CreateDetectorTasks(const char *name, const char* title)
374 {
375   // Creates new detector's task "name"
376    Int_t i = 0;
377    Int_t tmp;
378    while (i < kDetTaskLast)
379     {
380       tmp = AddSubTask(fgkTasksFolderName+"/"+fDetectorTask[i],
381                        name+fDetectorTask[i],(fDetectorTask[i]+" for ")+title);
382       if (tmp)
383        {
384          AliError(Form("Error occured while creating task for %s in %s.",
385                        name,fDetectorTask[i-1].Data()));
386          return 1;
387        }
388       i++;
389     }
390    return 0;
391 }
392
393 /*****************************************************************************/
394
395 TFolder* AliConfig::BuildEventFolder(const char* name,const char* title)
396 {
397 /*
398  creates the folder structure for one event
399  TopFolder_
400          | \
401          |  Tasks
402          |_
403          | \
404          |  Constants
405          |_
406          | \
407          |  Event_
408          |      | \
409          |      |  Modules(detector objects)
410          |      |_
411          |      | \              
412          |      |  Header
413          |      |_
414          |      | \              
415          |      |  Data_
416          |      |     | \ 
417          |      |     |  TPC_
418          |      |     |    | \
419          |      |     |    |  Hits(object;e.g. tree)
420          |      |     |    |_  
421          |      |     |    | \ 
422          |      |     |    |  SDigits(object)
423          |      |     |    |_
424          |      |     |    | \ 
425          |      |     |    |  Digits(object)
426          |      |     |    |_
427          |      |     |    | \ 
428          |      |     |    |  RecPoints(object)
429          |      |     |    |_
430          |      |     |      \ 
431          |      |     |       Tracks(object)
432          |      |     |_ 
433          |      |       \
434          |      |        ITS_
435          |      |          | \
436          |      |          |  Hits(object;e.g. tree)
437          |      |          |_  
438          |      |          | \ 
439          |      |          |  SDigits(object)
440          |      |          |_
441          |      |          | \ 
442          |      |          |  Digits(object)
443          |      |          |_
444          |      |          | \ 
445          |      |          |  RecPoints(object)
446          |      |          |_
447          |      |            \ 
448          |      |             Tracks(object)
449          |      |_         
450          |        \       
451          |         Configuration
452          |               
453          |_
454            \
455             Event2_  (to be merged with event)
456                 |  \
457                 |   Modules(detector objects)
458                 |_
459                 | \              
460                 |  Header
461                 |_
462                 | \              
463                 |  Data_
464                 |     | \ 
465                 |     |  TPC_
466                 |     |    | \
467                 |     |    |  Hits(object;e.g. tree)
468                 |     |    |_  
469                 |     |    | \ 
470                 |     |    |  SDigits(object)
471                 |     |    |_
472                 |     |    | \ 
473                 |     |    |  Digits(object)
474                 |     |    |_
475                 |     |    | \ 
476                 |     |    |  RecPoints(object)
477                 |     |    |_
478                 |     |      \ 
479                 |     |       Tracks(object)
480                 |     |_ 
481                 |       \
482                 |        ITS_
483                 |          | \
484                 |          |  Hits(object;e.g. tree)
485                 |          |_  
486                 |          | \ 
487                 |          |  SDigits(object)
488                 |          |_
489                 |          | \ 
490                 |          |  Digits(object)
491                 |          |_
492                 |          | \ 
493                 |          |  RecPoints(object)
494                 |          |_
495                 |            \ 
496                 |             Tracks(object)
497                 |_         
498                   \       
499                    Configuration
500                          
501 */
502   TFolder* eventfolder = fTopFolder->AddFolder(name,title); 
503    
504   //modules
505   eventfolder->AddFolder(fgkModuleFolderName, "Detector objects");
506   //event data
507   eventfolder->AddFolder(fgkDataFolderName, "Detector data");
508   
509     //Conditions
510   TFolder *conditions = eventfolder->AddFolder(fgkConditionsFolderName, "Run conditions");
511   conditions->AddFolder(fgkCalibrationFolderName,"Detector calibration data");
512   conditions->AddFolder(fgkAligmentFolderName,"Detector aligment");
513   conditions->AddFolder(fgkQAFolderName,"Quality Asurance Output"); //Folder with output of the QA task(s)
514   //Configuration
515   TFolder *configuration = eventfolder->AddFolder(fgkConfigurationFolderName, "Run configuration");
516   configuration->AddFolder(fgkFieldFolderName, "Magnetic field maps");
517   configuration->AddFolder(fgkGeneratorsFolderName,"list of generator objects");
518   //PH configuration->AddFolder(fgkVirtualMCFolderName,"the Virtual MC");
519
520   eventfolder->AddFolder(fgkHeaderFolderName,"MonteCarlo event header");
521
522   eventfolder->SetOwner();
523
524   return eventfolder;
525 }
526
527 /*****************************************************************************/
528
529 TString AliConfig::GetQATaskName() const
530  {
531  //returns task name
532   return fDetectorTask[kDetTaskQA];
533  }
534 /*****************************************************************************/
535  
536 TString AliConfig::GetDigitizerTaskName() const
537  {
538  //returns task name
539   return fDetectorTask[kDetTaskDigitizer];
540  }
541 /*****************************************************************************/
542  
543 TString AliConfig::GetSDigitizerTaskName() const
544  {
545  //returns task name
546   return fDetectorTask[kDetTaskSDigitizer];
547  }
548 /*****************************************************************************/
549
550 TString AliConfig::GetReconstructionerTaskName() const
551  {
552  //returns task name
553   return fDetectorTask[kDetTaskRecontructioner];
554  }
555 /*****************************************************************************/
556
557 TString AliConfig::GetTrackerTaskName() const
558  {
559  //returns task name
560   return fDetectorTask[kDetTaskTracker];
561  }
562 /*****************************************************************************/
563
564 TString AliConfig::GetPIDTaskName() const
565  {
566  //returns task name
567   return fDetectorTask[kDetTaskPID];
568  }
569 /*****************************************************************************/
570
571 const TString& AliConfig::GetQAFolderName() const
572 {
573 //returns pathname of folder with QA output relative to Top Alice Folder
574   return fDetectorFolder[kDetFolderQA];
575 }
576 /*****************************************************************************/
577
578 const TString& AliConfig::GetDataFolderName() const
579 {
580 //returns name of data folder path relative to event folder
581  return fgkDataFolderName;
582 }
583 /*****************************************************************************/
584
585 Int_t AliConfig::AddSubFolder(TFolder* topfolder, const char* infoler, 
586                      const char* newfoldname, const char* newfoldtitle)
587 {
588 //helper method
589 //in topfolder looks for folder named 'infolder'
590 //and if it exist it creates inside a new folder named 'newfoldname' and titled 'newfoldtitle'
591
592  if (topfolder == 0x0)//check if exists top folder
593   {
594    AliError("Parameter TFolder* points to NULL.");
595    return 1;
596   }
597  
598  TObject *obj;
599  TFolder* folder;
600  
601  folder = dynamic_cast<TFolder*>(topfolder->FindObject(infoler));
602  if (folder == 0x0) //check if we got inolder
603   {
604    AliError(Form("Can not find folder %s in folder %s.",infoler,topfolder->GetName()));
605    return 1;
606   }
607  obj = folder->FindObject(newfoldname); //see if such a subfolder already exists
608  if (obj == 0x0) //nope
609   {
610    TFolder *newfolder = folder->AddFolder(newfoldname,newfoldtitle);//add the desired subfolder
611    if (newfolder == 0x0) //check if we managed
612     {
613      AliError(Form("Can not create folder %s in folder %s",newfoldname,infoler));
614      return 2;
615     }
616    else return 0;//success
617   }
618  //such an object already exists
619  TFolder* fol = dynamic_cast<TFolder*>(obj);
620  if (fol == 0x0)
621    {
622      AliError(Form("Object named %s already exists in folder %s AND IT IS NOT A FOLDER",newfoldname,infoler));
623      return 3;
624    }
625  AliWarning(Form("Folder named %s already exists in folder %s",newfoldname,infoler));
626  return 0;
627 }