]> git.uio.no Git - u/mrichter/AliRoot.git/blob - STEER/AliSimulation.cxx
Temporary fix (till next root version) by A.Gheata. Rebuilding of voxelization after...
[u/mrichter/AliRoot.git] / STEER / AliSimulation.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 ///////////////////////////////////////////////////////////////////////////////
19 //                                                                           //
20 // class for running generation, simulation and digitization                 //
21 //                                                                           //
22 // Hits, sdigits and digits are created for all detectors by typing:         //
23 //                                                                           //
24 //   AliSimulation sim;                                                      //
25 //   sim.Run();                                                              //
26 //                                                                           //
27 // The Run method returns kTRUE in case of successful execution.             //
28 // The number of events can be given as argument to the Run method or it     //
29 // can be set by                                                             //
30 //                                                                           //
31 //   sim.SetNumberOfEvents(n);                                               //
32 //                                                                           //
33 // The name of the configuration file can be passed as argument to the       //
34 // AliSimulation constructor or can be specified by                          //
35 //                                                                           //
36 //   sim.SetConfigFile("...");                                               //
37 //                                                                           //
38 // The generation of particles and the simulation of detector hits can be    //
39 // switched on or off by                                                     //
40 //                                                                           //
41 //   sim.SetRunGeneration(kTRUE);   // generation of primary particles       //
42 //   sim.SetRunSimulation(kFALSE);  // but no tracking                       //
43 //                                                                           //
44 // For which detectors sdigits and digits will be created, can be steered    //
45 // by                                                                        //
46 //                                                                           //
47 //   sim.SetMakeSDigits("ALL");     // make sdigits for all detectors        //
48 //   sim.SetMakeDigits("ITS TPC");  // make digits only for ITS and TPC      //
49 //                                                                           //
50 // The argument is a (case sensitive) string with the names of the           //
51 // detectors separated by a space. An empty string ("") can be used to       //
52 // disable the creation of sdigits or digits. The special string "ALL"       //
53 // selects all available detectors. This is the default.                     //
54 //                                                                           //
55 // The creation of digits from hits instead of from sdigits can be selected  //
56 // by                                                                        //
57 //                                                                           //
58 //   sim.SetMakeDigitsFromHits("TRD");                                       //
59 //                                                                           //
60 // The argument is again a string with the selected detectors. Be aware that //
61 // this feature is not available for all detectors and that merging is not   //
62 // possible, when digits are created directly from hits.                     //
63 //                                                                           //
64 // Background events can be merged by calling                                //
65 //                                                                           //
66 //   sim.MergeWith("background/galice.root", 2);                             //
67 //                                                                           //
68 // The first argument is the file name of the background galice file. The    //
69 // second argument is the number of signal events per background event.      //
70 // By default this number is calculated from the number of available         //
71 // background events. MergeWith can be called several times to merge more    //
72 // than two event streams. It is assumed that the sdigits were already       //
73 // produced for the background events.                                       //
74 //                                                                           //
75 // The output of raw data can be switched on by calling                      //
76 //                                                                           //
77 //   sim.SetWriteRawData("MUON");   // write raw data for MUON               //
78 //                                                                           //
79 // The default output format of the raw data are DDL files. They are         //
80 // converted to a DATE file, if a file name is given as second argument.     //
81 // For this conversion the program "dateStream" is required. If the file     //
82 // name has the extension ".root", the DATE file is converted to a root      //
83 // file. The program "alimdc" is used for this purpose. For the conversion   //
84 // to DATE and root format the two conversion programs have to be installed. //
85 // Only the raw data in the final format is kept if the third argument is    //
86 // kTRUE.                                                                    //
87 //                                                                           //
88 // The methods RunSimulation, RunSDigitization, RunDigitization,             //
89 // RunHitsDigitization and WriteRawData can be used to run only parts of     //
90 // the full simulation chain. The creation of raw data DDL files and their   //
91 // conversion to the DATE or root format can be run directly by calling      //
92 // the methods WriteRawFiles, ConvertRawFilesToDate and ConvertDateToRoot.   //
93 //                                                                           //
94 // The default number of events per file, which is usually set in the        //
95 // config file, can be changed for individual detectors and data types       //
96 // by calling                                                                //
97 //                                                                           //
98 //   sim.SetEventsPerFile("PHOS", "Reconstructed Points", 3);                //
99 //                                                                           //
100 // The first argument is the detector, the second one the data type and the  //
101 // last one the number of events per file. Valid data types are "Hits",      //
102 // "Summable Digits", "Digits", "Reconstructed Points" and "Tracks".         //
103 // The number of events per file has to be set before the simulation of      //
104 // hits. Otherwise it has no effect.                                         //
105 //                                                                           //
106 ///////////////////////////////////////////////////////////////////////////////
107
108 #include <TGeoManager.h>
109 #include <TObjString.h>
110 #include <TStopwatch.h>
111 #include <TSystem.h>
112 #include <TFile.h>
113
114 #include "AliCDBStorage.h"
115 #include "AliCDBEntry.h"
116 #include "AliCDBManager.h"
117 #include "AliAlignObj.h"
118 #include "AliCentralTrigger.h"
119 #include "AliDAQConfig.h"
120 #include "AliDigitizer.h"
121 #include "AliGenerator.h"
122 #include "AliLog.h"
123 #include "AliModule.h"
124 #include "AliRun.h"
125 #include "AliRunDigitizer.h"
126 #include "AliRunLoader.h"
127 #include "AliSimulation.h"
128 #include "AliVertexGenFile.h"
129 #include "AliCentralTrigger.h"
130
131 ClassImp(AliSimulation)
132
133
134 //_____________________________________________________________________________
135 AliSimulation::AliSimulation(const char* configFileName, const char* cdbUri,
136                              const char* name, const char* title) :
137   TNamed(name, title),
138
139   fRunGeneration(kTRUE),
140   fRunSimulation(kTRUE),
141   fLoadAlignFromCDB(kTRUE),
142   fLoadAlignData("ALL"),
143   fMakeSDigits("ALL"),
144   fMakeDigits("ALL"),
145   fMakeTrigger(""),
146   fMakeDigitsFromHits(""),
147   fWriteRawData(""),
148   fRawDataFileName(""),
149   fDeleteIntermediateFiles(kFALSE),
150   fStopOnError(kFALSE),
151
152   fNEvents(1),
153   fConfigFileName(configFileName),
154   fGAliceFileName("galice.root"),
155   fEventsPerFile(),
156   fBkgrdFileNames(NULL),
157   fAlignObjArray(NULL),
158   fUseBkgrdVertex(kTRUE),
159   fRegionOfInterest(kFALSE),
160   fCDBUri(cdbUri)
161 {
162 // create simulation object with default parameters
163
164   SetGAliceFile("galice.root");
165 }
166
167 //_____________________________________________________________________________
168 AliSimulation::AliSimulation(const AliSimulation& sim) :
169   TNamed(sim),
170
171   fRunGeneration(sim.fRunGeneration),
172   fRunSimulation(sim.fRunSimulation),
173   fLoadAlignFromCDB(sim.fLoadAlignFromCDB),
174   fLoadAlignData(sim.fLoadAlignData),
175   fMakeSDigits(sim.fMakeSDigits),
176   fMakeDigits(sim.fMakeDigits),
177   fMakeTrigger(sim.fMakeTrigger),
178   fMakeDigitsFromHits(sim.fMakeDigitsFromHits),
179   fWriteRawData(sim.fWriteRawData),
180   fRawDataFileName(""),
181   fDeleteIntermediateFiles(kFALSE),
182   fStopOnError(sim.fStopOnError),
183
184   fNEvents(sim.fNEvents),
185   fConfigFileName(sim.fConfigFileName),
186   fGAliceFileName(sim.fGAliceFileName),
187   fEventsPerFile(),
188   fBkgrdFileNames(NULL),
189   fAlignObjArray(NULL),
190   fUseBkgrdVertex(sim.fUseBkgrdVertex),
191   fRegionOfInterest(sim.fRegionOfInterest),
192   fCDBUri(sim.fCDBUri)
193 {
194 // copy constructor
195
196   for (Int_t i = 0; i < sim.fEventsPerFile.GetEntriesFast(); i++) {
197     if (!sim.fEventsPerFile[i]) continue;
198     fEventsPerFile.Add(sim.fEventsPerFile[i]->Clone());
199   }
200
201   fBkgrdFileNames = new TObjArray;
202   for (Int_t i = 0; i < sim.fBkgrdFileNames->GetEntriesFast(); i++) {
203     if (!sim.fBkgrdFileNames->At(i)) continue;
204     fBkgrdFileNames->Add(sim.fBkgrdFileNames->At(i)->Clone());
205   }
206 }
207
208 //_____________________________________________________________________________
209 AliSimulation& AliSimulation::operator = (const AliSimulation& sim)
210 {
211 // assignment operator
212
213   this->~AliSimulation();
214   new(this) AliSimulation(sim);
215   return *this;
216 }
217
218 //_____________________________________________________________________________
219 AliSimulation::~AliSimulation()
220 {
221 // clean up
222
223   fEventsPerFile.Delete();
224 //  if(fAlignObjArray) fAlignObjArray->Delete(); // fAlignObjArray->RemoveAll() ???
225 //  delete fAlignObjArray; fAlignObjArray=0;
226
227   if (fBkgrdFileNames) {
228     fBkgrdFileNames->Delete();
229     delete fBkgrdFileNames;
230   }
231 }
232
233
234 //_____________________________________________________________________________
235 void AliSimulation::SetNumberOfEvents(Int_t nEvents)
236 {
237 // set the number of events for one run
238
239   fNEvents = nEvents;
240 }
241
242 //_____________________________________________________________________________
243 void AliSimulation::InitCDBStorage(const char* uri)
244 {
245 // activate a default CDB storage
246 // First check if we have any CDB storage set, because it is used 
247 // to retrieve the calibration and alignment constants
248
249   AliCDBManager* man = AliCDBManager::Instance();
250   if (!man->IsDefaultStorageSet())
251   {
252     AliWarningClass("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
253     AliWarningClass("Default CDB storage not yet set");
254     AliWarningClass(Form("Using default storage declared in AliSimulation: %s",uri));
255     AliWarningClass("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
256     SetDefaultStorage(uri);
257   }  
258   
259 }
260
261 //_____________________________________________________________________________
262 void AliSimulation::SetDefaultStorage(const char* uri) {
263 // activate a default CDB storage 
264
265    AliCDBManager::Instance()->SetDefaultStorage(uri);
266
267 }
268
269 //_____________________________________________________________________________
270 void AliSimulation::SetSpecificStorage(const char* detName, const char* uri) {
271 // activate a detector-specific CDB storage 
272
273    AliCDBManager::Instance()->SetSpecificStorage(detName, uri);
274
275 }
276
277 //_____________________________________________________________________________
278 void AliSimulation::SetConfigFile(const char* fileName)
279 {
280 // set the name of the config file
281
282   fConfigFileName = fileName;
283 }
284
285 //_____________________________________________________________________________
286 void AliSimulation::SetGAliceFile(const char* fileName)
287 {
288 // set the name of the galice file
289 // the path is converted to an absolute one if it is relative
290
291   fGAliceFileName = fileName;
292   if (!gSystem->IsAbsoluteFileName(fGAliceFileName)) {
293     char* absFileName = gSystem->ConcatFileName(gSystem->WorkingDirectory(),
294                                                 fGAliceFileName);
295     fGAliceFileName = absFileName;
296     delete[] absFileName;
297   }
298
299   AliDebug(2, Form("galice file name set to %s", fileName));
300 }
301
302 //_____________________________________________________________________________
303 void AliSimulation::SetEventsPerFile(const char* detector, const char* type, 
304                                      Int_t nEvents)
305 {
306 // set the number of events per file for the given detector and data type
307 // ("Hits", "Summable Digits", "Digits", "Reconstructed Points" or "Tracks")
308
309   TNamed* obj = new TNamed(detector, type);
310   obj->SetUniqueID(nEvents);
311   fEventsPerFile.Add(obj);
312 }
313
314 //_____________________________________________________________________________
315 Bool_t AliSimulation::ApplyAlignObjsToGeom(const char* fileName, const char* clArrayName)
316 {
317   // read collection of alignment objects (AliAlignObj derived) saved
318   // in the TClonesArray ClArrayName in the file fileName and apply
319   // them to the TGeo geometry passed as argument
320   //
321
322   TFile* inFile = TFile::Open(fileName,"READ");
323   if (!inFile || !inFile->IsOpen()) {
324     AliErrorClass(Form("Could not open file %s !",fileName));
325     return kFALSE;
326   }
327
328   TClonesArray* alObjArray = ((TClonesArray*) inFile->Get(clArrayName));
329   inFile->Close();
330   if (!alObjArray) {
331     AliErrorClass(Form("Could not get array (%s) from file (%s) !",clArrayName,fileName));
332     return kFALSE;
333   }
334
335   return gAlice->ApplyAlignObjsToGeom(alObjArray);
336
337 }
338
339 //_____________________________________________________________________________
340 Bool_t AliSimulation::ApplyAlignObjsToGeom(AliCDBParam* param, AliCDBId& Id)
341 {
342   // read collection of alignment objects (AliAlignObj derived) saved
343   // in the TClonesArray ClArrayName in the AliCDBEntry identified by
344   // param (to get the AliCDBStorage) and Id; apply the alignment objects
345   // to the TGeo geometry passed as argument
346   //
347
348   AliCDBStorage* storage = AliCDBManager::Instance()->GetStorage(param);
349   AliCDBEntry* entry = storage->Get(Id);
350   TClonesArray* AlObjArray = ((TClonesArray*) entry->GetObject());
351
352   return gAlice->ApplyAlignObjsToGeom(AlObjArray);
353
354 }
355
356 //_____________________________________________________________________________
357 Bool_t AliSimulation::ApplyAlignObjsToGeom(const char* uri, const char* path, Int_t runnum, Int_t version, Int_t sversion)
358 {
359   // read collection of alignment objects (AliAlignObj derived) saved
360   // in the TClonesArray ClArrayName in the AliCDBEntry identified by
361   // param (to get the AliCDBStorage) and Id; apply the alignment objects
362   // to the TGeo geometry passed as argument
363   //
364
365   AliCDBParam* param = AliCDBManager::Instance()->CreateParameter(uri);
366   AliCDBId id(path, runnum, runnum, version, sversion);
367
368   return ApplyAlignObjsToGeom(param, id);
369
370 }
371
372 //_____________________________________________________________________________
373 Bool_t AliSimulation::ApplyAlignObjsToGeom(const char* detName, Int_t runnum, Int_t version, Int_t sversion)
374 {
375   // read collection of alignment objects (AliAlignObj derived) saved
376   // in the TClonesArray ClArrayName in the AliCDBEntry identified by
377   // param (to get the AliCDBStorage) and Id; apply the alignment objects
378   // to the TGeo geometry passed as argument
379   //
380
381   InitCDBStorage("local://$ALICE_ROOT");
382   AliCDBPath path(detName,"Align","Data");
383   AliCDBEntry* entry = AliCDBManager::Instance()->Get(path.GetPath(),runnum,version,sversion);
384
385   if(!entry) return kFALSE;
386   TClonesArray* AlObjArray = ((TClonesArray*) entry->GetObject());
387
388   return gAlice->ApplyAlignObjsToGeom(AlObjArray);
389 }
390
391
392 //_____________________________________________________________________________
393 void AliSimulation::SetAlignObjArray(const char* detectors)
394 {
395   // Fills array of detectors' alignable objects from CDB
396   // detectors can be "ALL" or "ITS TPC ..."
397   
398   AliRunLoader* runLoader = LoadRun();
399   if (!runLoader) return;
400
401   InitCDBStorage(fCDBUri);
402
403   if(!fAlignObjArray) fAlignObjArray = new TObjArray();
404   fAlignObjArray->SetOwner(0); // AliCDBEntry is owner of the align objects!
405   fAlignObjArray->Clear(); 
406
407   TString detStr = detectors;
408   TObjArray* detArray = runLoader->GetAliRun()->Detectors();
409   TString dataNotLoaded="";
410   TString dataLoaded="";
411
412   for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
413     AliModule* det = (AliModule*) detArray->At(iDet);
414     if (!det || !det->IsActive()) continue;
415     if (IsSelected(det->GetName(), detStr)) {
416     
417         if(!SetAlignObjArraySingleDet(det->GetName())){
418                 dataNotLoaded += det->GetName();
419                 dataNotLoaded += " ";
420                         } else {
421                                 dataLoaded += det->GetName();
422                                 dataLoaded += " ";
423                         }
424         }
425   } // end loop over all detectors
426
427   if ((detStr.CompareTo("ALL") == 0)) detStr = "";
428   dataNotLoaded += detStr;
429   AliInfo(Form("Alignment data loaded for: %s",
430                 dataLoaded.Data()));
431   AliInfo(Form("Didn't/couldn't load alignment data for: %s",
432                 dataNotLoaded.Data()));
433
434   AliDebug(2, Form("fAlignObjArray entries: %d",fAlignObjArray->GetEntries() ));
435   delete detArray;
436
437 }
438
439 //_____________________________________________________________________________
440 Bool_t AliSimulation::SetAlignObjArraySingleDet(const char* detName)
441 {
442   // Fills array of single detector's alignable objects from CDB
443   
444   AliDebug(2, Form("Loading alignment data for detector: %s",detName));
445   
446   AliCDBEntry *entry;
447         
448   AliCDBPath path(detName,"Align","Data");
449         
450   entry=AliCDBManager::Instance()->Get(path.GetPath());
451   if(!entry){ 
452         AliDebug(2,Form("Couldn't load alignment data for detector %s",detName));
453         return kFALSE;
454   }
455   entry->SetOwner(1);
456   TClonesArray *alignArray = (TClonesArray*) entry->GetObject();        
457   alignArray->SetOwner(0);
458   AliDebug(2,Form("Found %d alignment objects for %s",
459                         alignArray->GetEntries(),detName));
460
461   AliAlignObj *alignObj=0;
462   TIter iter(alignArray);
463         
464   // loop over align objects in detector
465   while( ( alignObj=(AliAlignObj *) iter.Next() ) ){
466         fAlignObjArray->Add(alignObj);
467   }
468   // delete entry --- Don't delete, it is cached!
469         
470   AliDebug(2, Form("fAlignObjArray entries: %d",fAlignObjArray->GetEntries() ));
471   return kTRUE;
472
473 }
474
475 //_____________________________________________________________________________
476 void AliSimulation::MergeWith(const char* fileName, Int_t nSignalPerBkgrd)
477 {
478 // add a file with background events for merging
479
480   TObjString* fileNameStr = new TObjString(fileName);
481   fileNameStr->SetUniqueID(nSignalPerBkgrd);
482   if (!fBkgrdFileNames) fBkgrdFileNames = new TObjArray;
483   fBkgrdFileNames->Add(fileNameStr);
484 }
485
486
487 //_____________________________________________________________________________
488 Bool_t AliSimulation::Run(Int_t nEvents)
489 {
490 // run the generation, simulation and digitization
491
492   InitCDBStorage(fCDBUri);
493
494   if (nEvents > 0) fNEvents = nEvents;
495
496   // generation and simulation -> hits
497   if (fRunGeneration) {
498     if (!RunSimulation()) if (fStopOnError) return kFALSE;
499   }
500
501   // hits -> summable digits
502   if (!fMakeSDigits.IsNull()) {
503     if (!RunSDigitization(fMakeSDigits)) if (fStopOnError) return kFALSE;
504   }
505
506   // summable digits -> digits
507   if (!fMakeDigits.IsNull()) {
508     if (!RunDigitization(fMakeDigits, fMakeDigitsFromHits)) {
509       if (fStopOnError) return kFALSE;
510     }
511   }
512
513   // hits -> digits
514   if (!fMakeDigitsFromHits.IsNull()) {
515     if (fBkgrdFileNames && (fBkgrdFileNames->GetEntriesFast() > 0)) {
516       AliWarning(Form("Merging and direct creation of digits from hits " 
517                  "was selected for some detectors. "
518                  "No merging will be done for the following detectors: %s",
519                  fMakeDigitsFromHits.Data()));
520     }
521     if (!RunHitsDigitization(fMakeDigitsFromHits)) {
522       if (fStopOnError) return kFALSE;
523     }
524   }
525
526   // digits -> trigger
527   if (!fMakeTrigger.IsNull()) {
528     if (!RunTrigger(fMakeTrigger)) {
529       if (fStopOnError) return kFALSE;
530     }
531   }
532
533   // digits -> raw data
534   if (!fWriteRawData.IsNull()) {
535     if (!WriteRawData(fWriteRawData, fRawDataFileName, 
536                       fDeleteIntermediateFiles)) {
537       if (fStopOnError) return kFALSE;
538     }
539   }
540
541   return kTRUE;
542 }
543
544 //_____________________________________________________________________________
545 Bool_t AliSimulation::RunTrigger(const char* descriptors)
546 {
547   // run the trigger
548
549    TStopwatch stopwatch;
550    stopwatch.Start();
551
552    AliRunLoader* runLoader = LoadRun("READ");
553    if (!runLoader) return kFALSE;
554    TString des = descriptors;
555
556    runLoader->MakeTree( "CT" );
557    AliCentralTrigger* aCTP = runLoader->GetTrigger();
558   // Load Descriptors
559    aCTP->LoadDescriptor( des );
560
561   // digits -> trigger
562    if( !aCTP->RunTrigger( runLoader ) ) {
563       if (fStopOnError) {
564     //  delete aCTP;
565          return kFALSE;
566       }
567    }
568
569    AliInfo(Form("Execution time: R:%.2fs C:%.2fs",
570            stopwatch.RealTime(),stopwatch.CpuTime()));
571
572    delete runLoader;
573
574    return kTRUE;
575 }
576
577
578
579 //_____________________________________________________________________________
580 Bool_t AliSimulation::RunSimulation(Int_t nEvents)
581 {
582 // run the generation and simulation
583
584   TStopwatch stopwatch;
585   stopwatch.Start();
586
587   if (!gAlice) {
588     AliError("no gAlice object. Restart aliroot and try again.");
589     return kFALSE;
590   }
591   if (gAlice->Modules()->GetEntries() > 0) {
592     AliError("gAlice was already run. Restart aliroot and try again.");
593     return kFALSE;
594   }
595
596   AliInfo(Form("initializing gAlice with config file %s",
597           fConfigFileName.Data()));
598   StdoutToAliInfo(StderrToAliError(
599     gAlice->Init(fConfigFileName.Data());
600   ););
601
602   // Set run number in CDBManager (here????)
603   AliCDBManager::Instance()->SetRun(gAlice->GetRunNumber());
604   AliInfo(Form("Run number: %d",AliCDBManager::Instance()->GetRun()));
605
606   AliRunLoader* runLoader = gAlice->GetRunLoader();
607   if (!runLoader) {
608              AliError(Form("gAlice has no run loader object. "
609                              "Check your config file: %s", fConfigFileName.Data()));
610              return kFALSE;
611   }
612   SetGAliceFile(runLoader->GetFileName());
613  
614   // Export ideal geometry 
615   if (gGeoManager) gGeoManager->Export("geometry.root");
616
617   // Load alignment data from CDB and fill fAlignObjArray 
618   if(fLoadAlignFromCDB){
619         if(!fAlignObjArray) fAlignObjArray = new TObjArray();
620         
621         //fAlignObjArray->RemoveAll(); 
622         fAlignObjArray->Clear();        
623         fAlignObjArray->SetOwner(0);
624  
625         TString detStr = fLoadAlignData;
626         TString dataNotLoaded="";
627         TString dataLoaded="";
628   
629         TObjArray* detArray = runLoader->GetAliRun()->Detectors();
630         for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
631                 AliModule* det = (AliModule*) detArray->At(iDet);
632                 if (!det || !det->IsActive()) continue;
633                 if (IsSelected(det->GetName(), detStr)) {
634                         if(!SetAlignObjArraySingleDet(det->GetName())){
635                                 dataNotLoaded += det->GetName();
636                                 dataNotLoaded += " ";
637                         } else {
638                                 dataLoaded += det->GetName();
639                                 dataLoaded += " ";
640                         }
641                 }
642         } // end loop over detectors
643   
644         if ((detStr.CompareTo("ALL") == 0)) detStr = "";
645         dataNotLoaded += detStr;
646         AliInfo(Form("Alignment data loaded for: %s",
647                           dataLoaded.Data()));
648         AliInfo(Form("Didn't/couldn't load alignment data for: %s",
649                           dataNotLoaded.Data()));
650   } // fLoadAlignFromCDB flag
651  
652   // Check if the array with alignment objects was
653   // provided by the user. If yes, apply the objects
654   // to the present TGeo geometry
655   if (fAlignObjArray) {
656     if (gGeoManager && gGeoManager->IsClosed()) {
657       if (gAlice->ApplyAlignObjsToGeom(fAlignObjArray) == kFALSE) {
658         AliError("The application of misalignment failed! Restart aliroot and try again. ");
659         return kFALSE;
660       }
661     }
662     else {
663       AliError("Can't apply the misalignment! gGeoManager doesn't exist or it is still opened!");
664       return kFALSE;
665     }
666   }
667
668   // Export (mis)aligned geometry 
669   if (gGeoManager) gGeoManager->Export("misaligned_geometry.root");
670
671   // Temporary fix by A.Gheata
672   // Could be removed with the next Root version (>5.11)
673   if (gGeoManager) {
674     TIter next(gGeoManager->GetListOfVolumes());
675     TGeoVolume *vol;
676     while ((vol = (TGeoVolume *)next())) {
677       if (vol->GetVoxels()) {
678         if (vol->GetVoxels()->NeedRebuild()) {
679           vol->GetVoxels()->Voxelize();
680           vol->FindOverlaps();
681         }
682       }
683     }
684   }
685
686 //   AliRunLoader* runLoader = gAlice->GetRunLoader();
687 //   if (!runLoader) {
688 //     AliError(Form("gAlice has no run loader object. "
689 //                   "Check your config file: %s", fConfigFileName.Data()));
690 //     return kFALSE;
691 //   }
692 //   SetGAliceFile(runLoader->GetFileName());
693
694   if (!gAlice->Generator()) {
695     AliError(Form("gAlice has no generator object. "
696                   "Check your config file: %s", fConfigFileName.Data()));
697     return kFALSE;
698   }
699   if (nEvents <= 0) nEvents = fNEvents;
700
701   // get vertex from background file in case of merging
702   if (fUseBkgrdVertex &&
703       fBkgrdFileNames && (fBkgrdFileNames->GetEntriesFast() > 0)) {
704     Int_t signalPerBkgrd = GetNSignalPerBkgrd(nEvents);
705     const char* fileName = ((TObjString*)
706                             (fBkgrdFileNames->At(0)))->GetName();
707     AliInfo(Form("The vertex will be taken from the background "
708                  "file %s with nSignalPerBackground = %d", 
709                  fileName, signalPerBkgrd));
710     AliVertexGenFile* vtxGen = new AliVertexGenFile(fileName, signalPerBkgrd);
711     gAlice->Generator()->SetVertexGenerator(vtxGen);
712   }
713
714   if (!fRunSimulation) {
715     gAlice->Generator()->SetTrackingFlag(0);
716   }
717
718   // set the number of events per file for given detectors and data types
719   for (Int_t i = 0; i < fEventsPerFile.GetEntriesFast(); i++) {
720     if (!fEventsPerFile[i]) continue;
721     const char* detName = fEventsPerFile[i]->GetName();
722     const char* typeName = fEventsPerFile[i]->GetTitle();
723     TString loaderName(detName);
724     loaderName += "Loader";
725     AliLoader* loader = runLoader->GetLoader(loaderName);
726     if (!loader) {
727       AliError(Form("RunSimulation", "no loader for %s found\n"
728                     "Number of events per file not set for %s %s", 
729                     detName, typeName, detName));
730       continue;
731     }
732     AliDataLoader* dataLoader = 
733       loader->GetDataLoader(typeName);
734     if (!dataLoader) {
735       AliError(Form("no data loader for %s found\n"
736                     "Number of events per file not set for %s %s", 
737                     typeName, detName, typeName));
738       continue;
739     }
740     dataLoader->SetNumberOfEventsPerFile(fEventsPerFile[i]->GetUniqueID());
741     AliDebug(1, Form("number of events per file set to %d for %s %s",
742                      fEventsPerFile[i]->GetUniqueID(), detName, typeName));
743   }
744
745   AliInfo("running gAlice");
746   StdoutToAliInfo(StderrToAliError(
747     gAlice->Run(nEvents);
748   ););
749
750   delete runLoader;
751
752   AliInfo(Form("Execution time: R:%.2fs C:%.2fs",
753                stopwatch.RealTime(),stopwatch.CpuTime()));
754
755   return kTRUE;
756 }
757
758 //_____________________________________________________________________________
759 Bool_t AliSimulation::RunSDigitization(const char* detectors)
760 {
761 // run the digitization and produce summable digits
762
763   TStopwatch stopwatch;
764   stopwatch.Start();
765
766   AliRunLoader* runLoader = LoadRun();
767   if (!runLoader) return kFALSE;
768
769   TString detStr = detectors;
770   TObjArray* detArray = runLoader->GetAliRun()->Detectors();
771   for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
772     AliModule* det = (AliModule*) detArray->At(iDet);
773     if (!det || !det->IsActive()) continue;
774     if (IsSelected(det->GetName(), detStr)) {
775       AliInfo(Form("creating summable digits for %s", det->GetName()));
776       TStopwatch stopwatchDet;
777       stopwatchDet.Start();
778       det->Hits2SDigits();
779       AliInfo(Form("Execution time for %s: R:%.2fs C:%.2fs",
780            det->GetName(),stopwatchDet.RealTime(),stopwatchDet.CpuTime()));
781     }
782   }
783
784   if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
785     AliError(Form("the following detectors were not found: %s",
786                   detStr.Data()));
787     if (fStopOnError) return kFALSE;
788   }
789
790   delete runLoader;
791
792   AliInfo(Form("Execution time: R:%.2fs C:%.2fs",
793            stopwatch.RealTime(),stopwatch.CpuTime()));
794
795   return kTRUE;
796 }
797
798
799 //_____________________________________________________________________________
800 Bool_t AliSimulation::RunDigitization(const char* detectors, 
801                                       const char* excludeDetectors)
802 {
803 // run the digitization and produce digits from sdigits
804
805   TStopwatch stopwatch;
806   stopwatch.Start();
807
808   while (AliRunLoader::GetRunLoader()) delete AliRunLoader::GetRunLoader();
809   if (gAlice) delete gAlice;
810   gAlice = NULL;
811
812   Int_t nStreams = 1;
813   if (fBkgrdFileNames) nStreams = fBkgrdFileNames->GetEntriesFast() + 1;
814   Int_t signalPerBkgrd = GetNSignalPerBkgrd();
815   AliRunDigitizer* manager = new AliRunDigitizer(nStreams, signalPerBkgrd);
816   manager->SetInputStream(0, fGAliceFileName.Data());
817   for (Int_t iStream = 1; iStream < nStreams; iStream++) {
818     const char* fileName = ((TObjString*)
819                             (fBkgrdFileNames->At(iStream-1)))->GetName();
820     manager->SetInputStream(iStream, fileName);
821   }
822
823   TString detStr = detectors;
824   TString detExcl = excludeDetectors;
825   manager->GetInputStream(0)->ImportgAlice();
826   AliRunLoader* runLoader = 
827     AliRunLoader::GetRunLoader(manager->GetInputStream(0)->GetFolderName());
828   TObjArray* detArray = runLoader->GetAliRun()->Detectors();
829   for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
830     AliModule* det = (AliModule*) detArray->At(iDet);
831     if (!det || !det->IsActive()) continue;
832     if (IsSelected(det->GetName(), detStr) && 
833         !IsSelected(det->GetName(), detExcl)) {
834       AliDigitizer* digitizer = det->CreateDigitizer(manager);
835       if (!digitizer) {
836         AliError(Form("no digitizer for %s", det->GetName()));
837         if (fStopOnError) return kFALSE;
838       } else {
839         digitizer->SetRegionOfInterest(fRegionOfInterest);
840       }
841     }
842   }
843
844   if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
845     AliError(Form("the following detectors were not found: %s", 
846                   detStr.Data()));
847     if (fStopOnError) return kFALSE;
848   }
849
850   if (!manager->GetListOfTasks()->IsEmpty()) {
851     AliInfo("executing digitization");
852     manager->Exec("");
853   }
854
855   delete manager;
856
857   AliInfo(Form("Execution time: R:%.2fs C:%.2fs",
858                stopwatch.RealTime(),stopwatch.CpuTime()));
859   
860   return kTRUE;
861 }
862
863 //_____________________________________________________________________________
864 Bool_t AliSimulation::RunHitsDigitization(const char* detectors)
865 {
866 // run the digitization and produce digits from hits
867
868   TStopwatch stopwatch;
869   stopwatch.Start();
870
871   AliRunLoader* runLoader = LoadRun("READ");
872   if (!runLoader) return kFALSE;
873
874   TString detStr = detectors;
875   TObjArray* detArray = runLoader->GetAliRun()->Detectors();
876   for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
877     AliModule* det = (AliModule*) detArray->At(iDet);
878     if (!det || !det->IsActive()) continue;
879     if (IsSelected(det->GetName(), detStr)) {
880       AliInfo(Form("creating digits from hits for %s", det->GetName()));
881       det->Hits2Digits();
882     }
883   }
884
885   if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
886     AliError(Form("the following detectors were not found: %s", 
887                   detStr.Data()));
888     if (fStopOnError) return kFALSE;
889   }
890
891   delete runLoader;
892   //PH Temporary fix to avoid interference with the PHOS loder/getter
893   //PH The problem has to be solved in more general way 09/06/05
894
895   AliInfo(Form("Execution time: R:%.2fs C:%.2fs",
896                stopwatch.RealTime(),stopwatch.CpuTime()));
897
898   return kTRUE;
899 }
900
901 //_____________________________________________________________________________
902 Bool_t AliSimulation::WriteRawData(const char* detectors, 
903                                    const char* fileName,
904                                    Bool_t deleteIntermediateFiles)
905 {
906 // convert the digits to raw data
907 // First DDL raw data files for the given detectors are created.
908 // If a file name is given, the DDL files are then converted to a DATE file.
909 // If deleteIntermediateFiles is true, the DDL raw files are deleted 
910 // afterwards.
911 // If the file name has the extension ".root", the DATE file is converted
912 // to a root file.
913 // If deleteIntermediateFiles is true, the DATE file is deleted afterwards.
914
915   TStopwatch stopwatch;
916   stopwatch.Start();
917
918   if (!WriteRawFiles(detectors)) {
919     if (fStopOnError) return kFALSE;
920   }
921
922   TString dateFileName(fileName);
923   if (!dateFileName.IsNull()) {
924     Bool_t rootOutput = dateFileName.EndsWith(".root");
925     if (rootOutput) dateFileName += ".date";
926     if (!ConvertRawFilesToDate(dateFileName)) {
927       if (fStopOnError) return kFALSE;
928     }
929     if (deleteIntermediateFiles) {
930       AliRunLoader* runLoader = LoadRun("READ");
931       if (runLoader) for (Int_t iEvent = 0; 
932                           iEvent < runLoader->GetNumberOfEvents(); iEvent++) {
933         char command[256];
934         sprintf(command, "rm -r raw%d", iEvent);
935         gSystem->Exec(command);
936       }
937     }
938
939     if (rootOutput) {
940       if (!ConvertDateToRoot(dateFileName, fileName)) {
941         if (fStopOnError) return kFALSE;
942       }
943       if (deleteIntermediateFiles) {
944         gSystem->Unlink(dateFileName);
945       }
946     }
947   }
948
949   AliInfo(Form("Execution time: R:%.2fs C:%.2fs",
950                stopwatch.RealTime(),stopwatch.CpuTime()));
951
952   return kTRUE;
953 }
954
955 //_____________________________________________________________________________
956 Bool_t AliSimulation::WriteRawFiles(const char* detectors)
957 {
958 // convert the digits to raw data DDL files
959
960   AliRunLoader* runLoader = LoadRun("READ");
961   if (!runLoader) return kFALSE;
962
963   // write raw data to DDL files
964   for (Int_t iEvent = 0; iEvent < runLoader->GetNumberOfEvents(); iEvent++) {
965     AliInfo(Form("processing event %d", iEvent));
966     runLoader->GetEvent(iEvent);
967     TString baseDir = gSystem->WorkingDirectory();
968     char dirName[256];
969     sprintf(dirName, "raw%d", iEvent);
970     gSystem->MakeDirectory(dirName);
971     if (!gSystem->ChangeDirectory(dirName)) {
972       AliError(Form("couldn't change to directory %s", dirName));
973       if (fStopOnError) return kFALSE; else continue;
974     }
975
976     TString detStr = detectors;
977     TObjArray* detArray = runLoader->GetAliRun()->Detectors();
978     for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
979       AliModule* det = (AliModule*) detArray->At(iDet);
980       if (!det || !det->IsActive()) continue;
981       if (IsSelected(det->GetName(), detStr)) {
982         AliInfo(Form("creating raw data from digits for %s", det->GetName()));
983         det->Digits2Raw();
984       }
985     }
986
987     gSystem->ChangeDirectory(baseDir);
988     if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
989       AliError(Form("the following detectors were not found: %s", 
990                     detStr.Data()));
991       if (fStopOnError) return kFALSE;
992     }
993   }
994
995   delete runLoader;
996   return kTRUE;
997 }
998
999 //_____________________________________________________________________________
1000 Bool_t AliSimulation::ConvertRawFilesToDate(const char* dateFileName)
1001 {
1002 // convert raw data DDL files to a DATE file with the program "dateStream"
1003
1004   char* path = gSystem->Which(gSystem->Getenv("PATH"), "dateStream");
1005   if (!path) {
1006     AliError("the program dateStream was not found");
1007     if (fStopOnError) return kFALSE;
1008   } else {
1009     delete[] path;
1010   }
1011
1012   AliRunLoader* runLoader = LoadRun("READ");
1013   if (!runLoader) return kFALSE;
1014
1015   AliInfo(Form("converting raw data DDL files to DATE file %s", dateFileName));
1016   char command[256];
1017   sprintf(command, "dateStream -o %s -# %d -C", 
1018           dateFileName, runLoader->GetNumberOfEvents());
1019   FILE* pipe = gSystem->OpenPipe(command, "w");
1020
1021   for (Int_t iEvent = 0; iEvent < runLoader->GetNumberOfEvents(); iEvent++) {
1022     fprintf(pipe, "GDC\n");
1023     Float_t ldc = 0;
1024     Int_t prevLDC = -1;
1025
1026     // loop over detectors and DDLs
1027     for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
1028       for (Int_t iDDL = 0; iDDL < kDetectorDDLs[iDet]; iDDL++) {
1029
1030         Int_t ddlID = 0x100*iDet + iDDL;
1031         Int_t ldcID = Int_t(ldc + 0.0001);
1032         ldc += kDetectorLDCs[iDet] / kDetectorDDLs[iDet];
1033
1034         char rawFileName[256];
1035         sprintf(rawFileName, "raw%d/%s_%d.ddl", 
1036                 iEvent, kDetectors[iDet], ddlID);
1037
1038         // check existence and size of raw data file
1039         FILE* file = fopen(rawFileName, "rb");
1040         if (!file) continue;
1041         fseek(file, 0, SEEK_END);
1042         unsigned long size = ftell(file);
1043         fclose(file);
1044         if (!size) continue;
1045
1046         if (ldcID != prevLDC) {
1047           fprintf(pipe, " LDC Id %d\n", ldcID);
1048           prevLDC = ldcID;
1049         }
1050         fprintf(pipe, "  Equipment Id %d Payload %s\n", ddlID, rawFileName);
1051       }
1052     }
1053   }
1054
1055   Int_t result = gSystem->ClosePipe(pipe);
1056
1057   delete runLoader;
1058   return (result == 0);
1059 }
1060
1061 //_____________________________________________________________________________
1062 Bool_t AliSimulation::ConvertDateToRoot(const char* dateFileName,
1063                                         const char* rootFileName)
1064 {
1065 // convert a DATE file to a root file with the program "alimdc"
1066
1067   // ALIMDC setup
1068   const Int_t kDBSize = 1000000000;
1069   const Int_t kTagDBSize = 1000000000;
1070   const Bool_t kFilter = kFALSE;
1071   const Int_t kCompression = 1;
1072
1073   char* path = gSystem->Which(gSystem->Getenv("PATH"), "alimdc");
1074   if (!path) {
1075     AliError("the program alimdc was not found");
1076     if (fStopOnError) return kFALSE;
1077   } else {
1078     delete[] path;
1079   }
1080
1081   AliInfo(Form("converting DATE file %s to root file %s", 
1082                dateFileName, rootFileName));
1083
1084   const char* rawDBFS[2] = { "/tmp/mdc1", "/tmp/mdc2" };
1085   const char* tagDBFS    = "/tmp/mdc1/tags";
1086   const char* runDBFS    = "/tmp/mdc1/meta";
1087
1088   // User defined file system locations
1089   if (gSystem->Getenv("ALIMDC_RAWDB1")) 
1090     rawDBFS[0] = gSystem->Getenv("ALIMDC_RAWDB1");
1091   if (gSystem->Getenv("ALIMDC_RAWDB2")) 
1092     rawDBFS[1] = gSystem->Getenv("ALIMDC_RAWDB2");
1093   if (gSystem->Getenv("ALIMDC_TAGDB")) 
1094     tagDBFS = gSystem->Getenv("ALIMDC_TAGDB");
1095   if (gSystem->Getenv("ALIMDC_RUNDB")) 
1096     runDBFS = gSystem->Getenv("ALIMDC_RUNDB");
1097
1098   gSystem->Exec(Form("rm -rf %s",rawDBFS[0]));
1099   gSystem->Exec(Form("rm -rf %s",rawDBFS[1]));
1100   gSystem->Exec(Form("rm -rf %s",tagDBFS));
1101   gSystem->Exec(Form("rm -rf %s",runDBFS));
1102
1103   gSystem->Exec(Form("mkdir %s",rawDBFS[0]));
1104   gSystem->Exec(Form("mkdir %s",rawDBFS[1]));
1105   gSystem->Exec(Form("mkdir %s",tagDBFS));
1106   gSystem->Exec(Form("mkdir %s",runDBFS));
1107
1108   Int_t result = gSystem->Exec(Form("alimdc %d %d %d %d %s", 
1109                                     kDBSize, kTagDBSize, kFilter, kCompression, dateFileName));
1110   gSystem->Exec(Form("mv %s/*.root %s", rawDBFS[0], rootFileName));
1111
1112   gSystem->Exec(Form("rm -rf %s",rawDBFS[0]));
1113   gSystem->Exec(Form("rm -rf %s",rawDBFS[1]));
1114   gSystem->Exec(Form("rm -rf %s",tagDBFS));
1115   gSystem->Exec(Form("rm -rf %s",runDBFS));
1116
1117   return (result == 0);
1118 }
1119
1120
1121 //_____________________________________________________________________________
1122 AliRunLoader* AliSimulation::LoadRun(const char* mode) const
1123 {
1124 // delete existing run loaders, open a new one and load gAlice
1125
1126   while (AliRunLoader::GetRunLoader()) delete AliRunLoader::GetRunLoader();
1127   AliRunLoader* runLoader = 
1128     AliRunLoader::Open(fGAliceFileName.Data(), 
1129                        AliConfig::GetDefaultEventFolderName(), mode);
1130   if (!runLoader) {
1131     AliError(Form("no run loader found in file %s", fGAliceFileName.Data()));
1132     return NULL;
1133   }
1134   runLoader->LoadgAlice();
1135   gAlice = runLoader->GetAliRun();
1136   if (!gAlice) {
1137     AliError(Form("no gAlice object found in file %s", 
1138                   fGAliceFileName.Data()));
1139     return NULL;
1140   }
1141   return runLoader;
1142 }
1143
1144 //_____________________________________________________________________________
1145 Int_t AliSimulation::GetNSignalPerBkgrd(Int_t nEvents) const
1146 {
1147 // get or calculate the number of signal events per background event
1148
1149   if (!fBkgrdFileNames) return 1;
1150   Int_t nBkgrdFiles = fBkgrdFileNames->GetEntriesFast();
1151   if (nBkgrdFiles == 0) return 1;
1152
1153   // get the number of signal events
1154   if (nEvents <= 0) {
1155     AliRunLoader* runLoader = 
1156       AliRunLoader::Open(fGAliceFileName.Data(), "SIGNAL");
1157     if (!runLoader) return 1;
1158     nEvents = runLoader->GetNumberOfEvents();
1159     delete runLoader;
1160   }
1161
1162   Int_t result = 0;
1163   for (Int_t iBkgrdFile = 0; iBkgrdFile < nBkgrdFiles; iBkgrdFile++) {
1164     // get the number of background events
1165     const char* fileName = ((TObjString*)
1166                             (fBkgrdFileNames->At(iBkgrdFile)))->GetName();
1167     AliRunLoader* runLoader = 
1168       AliRunLoader::Open(fileName, "BKGRD");
1169     if (!runLoader) continue;
1170     Int_t nBkgrdEvents = runLoader->GetNumberOfEvents();
1171     delete runLoader;
1172
1173     // get or calculate the number of signal per background events
1174     Int_t nSignalPerBkgrd = fBkgrdFileNames->At(iBkgrdFile)->GetUniqueID();
1175     if (nSignalPerBkgrd <= 0) {
1176       nSignalPerBkgrd = (nEvents-1) / nBkgrdEvents + 1;
1177     } else if (result && (result != nSignalPerBkgrd)) {
1178       AliInfo(Form("the number of signal events per background event "
1179                    "will be changed from %d to %d for stream %d", 
1180                    nSignalPerBkgrd, result, iBkgrdFile+1));
1181       nSignalPerBkgrd = result;
1182     }
1183
1184     if (!result) result = nSignalPerBkgrd;
1185     if (nSignalPerBkgrd * nBkgrdEvents < nEvents) {
1186       AliWarning(Form("not enough background events (%d) for %d signal events "
1187                       "using %d signal per background events for stream %d",
1188                       nBkgrdEvents, nEvents, nSignalPerBkgrd, iBkgrdFile+1));
1189     }
1190   }
1191
1192   return result;
1193 }
1194
1195 //_____________________________________________________________________________
1196 Bool_t AliSimulation::IsSelected(TString detName, TString& detectors) const
1197 {
1198 // check whether detName is contained in detectors
1199 // if yes, it is removed from detectors
1200
1201   // check if all detectors are selected
1202   if ((detectors.CompareTo("ALL") == 0) ||
1203       detectors.BeginsWith("ALL ") ||
1204       detectors.EndsWith(" ALL") ||
1205       detectors.Contains(" ALL ")) {
1206     detectors = "ALL";
1207     return kTRUE;
1208   }
1209
1210   // search for the given detector
1211   Bool_t result = kFALSE;
1212   if ((detectors.CompareTo(detName) == 0) ||
1213       detectors.BeginsWith(detName+" ") ||
1214       detectors.EndsWith(" "+detName) ||
1215       detectors.Contains(" "+detName+" ")) {
1216     detectors.ReplaceAll(detName, "");
1217     result = kTRUE;
1218   }
1219
1220   // clean up the detectors string
1221   while (detectors.Contains("  ")) detectors.ReplaceAll("  ", " ");
1222   while (detectors.BeginsWith(" ")) detectors.Remove(0, 1);
1223   while (detectors.EndsWith(" ")) detectors.Remove(detectors.Length()-1, 1);
1224
1225   return result;
1226 }