Fixes for coverity.
[u/mrichter/AliRoot.git] / STEER / 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: AliSimulation.cxx 64623 2013-10-21 13:38:58Z rgrosso $ */
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 <TFile.h>
109 #include <TGeoGlobalMagField.h>
110 #include <TGeoManager.h>
111 #include <TObjString.h>
112 #include <TROOT.h>
113 #include <TSystem.h>
114 #include <TVirtualMC.h>
115 #include <TVirtualMCApplication.h>
116 #include <TDatime.h>
117 #include <TInterpreter.h>
118
119 #include "AliAlignObj.h"
120 #include "AliCDBEntry.h"
121 #include "AliCDBManager.h"
122 #include "AliGRPManager.h"
123 #include "AliCDBStorage.h"
124 #include "AliCTPRawData.h"
125 #include "AliCentralTrigger.h"
126 #include "AliCentralTrigger.h"
127 #include "AliCodeTimer.h"
128 #include "AliDAQ.h"
129 #include "AliDigitizer.h"
130 #include "AliESDEvent.h"
131 #include "AliGRPObject.h"
132 #include "AliGenEventHeader.h"
133 #include "AliGenerator.h"
134 #include "AliGeomManager.h"
135 #include "AliHLTSimulation.h"
136 #include "AliHeader.h"
137 #include "AliLego.h"
138 #include "AliLegoGenerator.h"
139 #include "AliLog.h"
140 #include "AliMC.h"
141 #include "AliMagF.h"
142 #include "AliModule.h"
143 #include "AliPDG.h"
144 #include "AliRawReaderDate.h"
145 #include "AliRawReaderFile.h"
146 #include "AliRawReaderRoot.h"
147 #include "AliRun.h"
148 #include "AliDigitizationInput.h"
149 #include "AliRunLoader.h"
150 #include "AliStack.h"
151 #include "AliSimulation.h"
152 #include "AliSysInfo.h"
153 #include "AliVertexGenFile.h"
154
155 using std::ofstream;
156 ClassImp(AliSimulation)
157
158 AliSimulation *AliSimulation::fgInstance = 0;
159  const char* AliSimulation::fgkDetectorName[AliSimulation::fgkNDetectors] = {"ITS", "TPC", "TRD", 
160  "TOF", "PHOS", "HMPID", "EMCAL", "MUON", "FMD", "ZDC", "PMD", "T0", "VZERO", "ACORDE","AD",
161  "FIT","MFT","HLT"};
162
163 //_____________________________________________________________________________
164 AliSimulation::AliSimulation(const char* configFileName,
165                              const char* name, const char* title) :
166   TNamed(name, title),
167
168   fRunGeneratorOnly(kFALSE),
169   fRunGeneration(kTRUE),
170   fRunSimulation(kTRUE),
171   fLoadAlignFromCDB(kTRUE),
172   fLoadAlObjsListOfDets("ALL"),
173   fMakeSDigits("ALL"),
174   fMakeDigits("ALL"),
175   fTriggerConfig(""),
176   fMakeDigitsFromHits(""),
177   fWriteRawData(""),
178   fRawDataFileName(""),
179   fDeleteIntermediateFiles(kFALSE),
180   fWriteSelRawData(kFALSE),
181   fStopOnError(kFALSE),
182   fUseMonitoring(kFALSE),
183   fNEvents(1),
184   fConfigFileName(configFileName),
185   fGAliceFileName("galice.root"),
186   fEventsPerFile(),
187   fBkgrdFileNames(NULL),
188   fAlignObjArray(NULL),
189   fUseBkgrdVertex(kTRUE),
190   fRegionOfInterest(kFALSE),
191   fCDBUri(""),
192   fQARefUri(""), 
193   fSpecCDBUri(),
194   fRun(-1),
195   fSeed(0),
196   fInitCDBCalled(kFALSE),
197   fInitRunNumberCalled(kFALSE),
198   fSetRunNumberFromDataCalled(kFALSE),
199   fEmbeddingFlag(kFALSE),
200   fLego(NULL),
201   fKey(0),
202   fUseVertexFromCDB(0),
203   fUseMagFieldFromGRP(0),
204   fGRPWriteLocation(Form("local://%s", gSystem->pwd())),
205   fUseTimeStampFromCDB(0),
206   fTimeStart(0),
207   fTimeEnd(0),
208   fQADetectors("ALL"),                  
209   fQATasks("ALL"),      
210   fRunQA(kTRUE), 
211   fEventSpecie(AliRecoParam::kDefault),
212   fWriteQAExpertData(kTRUE), 
213   fGeometryFile(),
214   fRunHLT("default"),
215   fpHLT(NULL),
216   fWriteGRPEntry(kTRUE)
217 {
218 // create simulation object with default parameters
219   fgInstance = this;
220   SetGAliceFile("galice.root");
221   
222 // for QA
223         AliQAManager * qam = AliQAManager::QAManager(AliQAv1::kSIMMODE) ; 
224         qam->SetActiveDetectors(fQADetectors) ; 
225         fQATasks = Form("%d %d %d", AliQAv1::kHITS, AliQAv1::kSDIGITS, AliQAv1::kDIGITS) ; 
226         qam->SetTasks(fQATasks) ;       
227 }
228
229 //_____________________________________________________________________________
230 AliSimulation::~AliSimulation()
231 {
232 // clean up
233
234   fEventsPerFile.Delete();
235 //  if(fAlignObjArray) fAlignObjArray->Delete(); // fAlignObjArray->RemoveAll() ???
236 //  delete fAlignObjArray; fAlignObjArray=0;
237
238   if (fBkgrdFileNames) {
239     fBkgrdFileNames->Delete();
240     delete fBkgrdFileNames;
241   }
242
243   fSpecCDBUri.Delete();
244   if (fgInstance==this) fgInstance = 0;
245
246   AliQAManager::QAManager()->ShowQA() ; 
247   AliQAManager::Destroy() ;     
248   AliCodeTimer::Instance()->Print();
249 }
250
251
252 //_____________________________________________________________________________
253 void AliSimulation::SetNumberOfEvents(Int_t nEvents)
254 {
255 // set the number of events for one run
256
257   fNEvents = nEvents;
258 }
259
260 //_____________________________________________________________________________
261 void AliSimulation::InitQA()
262 {
263   // activate a default CDB storage
264   // First check if we have any CDB storage set, because it is used 
265   // to retrieve the calibration and alignment constants
266   
267   if (fInitCDBCalled) return;
268   fInitCDBCalled = kTRUE;
269
270   AliQAManager * qam = AliQAManager::QAManager(AliQAv1::kSIMMODE) ; 
271   qam->SetActiveDetectors(fQADetectors) ; 
272   fQATasks = Form("%d %d %d", AliQAv1::kHITS, AliQAv1::kSDIGITS, AliQAv1::kDIGITS) ; 
273   qam->SetTasks(fQATasks) ;
274         if (fWriteQAExpertData)
275     qam->SetWriteExpert() ; 
276   
277   if (qam->IsDefaultStorageSet()) {
278     AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
279     AliWarning("Default QA reference storage has been already set !");
280     AliWarning(Form("Ignoring the default storage declared in AliSimulation: %s",fQARefUri.Data()));
281     AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
282     fQARefUri = qam->GetDefaultStorage()->GetURI();
283   } else {
284       if (fQARefUri.Length() > 0) {
285         AliDebug(2,"!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
286         AliDebug(2, Form("Default QA reference storage is set to: %s", fQARefUri.Data()));
287         AliDebug(2, "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
288       } else {
289         fQARefUri="local://$ALICE_ROOT/QARef";
290         AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
291         AliWarning("Default QA reference storage not yet set !!!!");
292         AliWarning(Form("Setting it now to: %s", fQARefUri.Data()));
293         AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
294       }
295     qam->SetDefaultStorage(fQARefUri);
296   }
297 }
298
299 //_____________________________________________________________________________
300 void AliSimulation::InitCDB()
301 {
302 // activate a default CDB storage
303 // First check if we have any CDB storage set, because it is used 
304 // to retrieve the calibration and alignment constants
305
306   if (fInitCDBCalled) return;
307   fInitCDBCalled = kTRUE;
308
309   AliCDBManager* man = AliCDBManager::Instance();
310   if (man->IsDefaultStorageSet())
311   {
312     AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
313     AliWarning("Default CDB storage has been already set !");
314     AliWarning(Form("Ignoring the default storage declared in AliSimulation: %s",fCDBUri.Data()));
315     AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
316     fCDBUri = man->GetDefaultStorage()->GetURI();
317   }
318   else {
319     if (fCDBUri.Length() > 0) 
320     {
321         AliDebug(2,"!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
322         AliDebug(2, Form("Default CDB storage is set to: %s", fCDBUri.Data()));
323         AliDebug(2, "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
324     } else {
325         fCDBUri="local://$ALICE_ROOT/OCDB";
326         AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
327         AliWarning("Default CDB storage not yet set !!!!");
328         AliWarning(Form("Setting it now to: %s", fCDBUri.Data()));
329         AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
330                 
331     }
332     man->SetDefaultStorage(fCDBUri);
333   }
334
335   // Now activate the detector specific CDB storage locations
336   for (Int_t i = 0; i < fSpecCDBUri.GetEntriesFast(); i++) {
337     TObject* obj = fSpecCDBUri[i];
338     if (!obj) continue;
339     AliDebug(2, "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
340     AliDebug(2, Form("Specific CDB storage for %s is set to: %s",obj->GetName(),obj->GetTitle()));
341     AliDebug(2, "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
342     man->SetSpecificStorage(obj->GetName(), obj->GetTitle());
343   }
344       
345 }
346
347 //_____________________________________________________________________________
348 void AliSimulation::InitRunNumber(){
349 // check run number. If not set, set it to 0 !!!!
350   
351   if (fInitRunNumberCalled) return;
352   fInitRunNumberCalled = kTRUE;
353   
354   AliCDBManager* man = AliCDBManager::Instance();
355   if (man->GetRun() >= 0)
356   {
357         AliFatal(Form("Run number cannot be set in AliCDBManager before start of simulation: "
358                         "Use external variable DC_RUN or AliSimulation::SetRun()!"));
359   }
360     
361   if(fRun >= 0) {
362         AliDebug(2, Form("Setting CDB run number to: %d",fRun));
363   } else {
364         fRun=0;
365         AliWarning(Form("Run number not yet set !!!! Setting it now to: %d",
366                         fRun));
367   }
368   man->SetRun(fRun);
369
370   man->Print();
371
372 }
373
374 //_____________________________________________________________________________
375 void AliSimulation::SetCDBLock() {
376   // Set CDB lock: from now on it is forbidden to reset the run number
377   // or the default storage or to activate any further storage!
378   
379   ULong64_t key = AliCDBManager::Instance()->SetLock(1);
380   if (key) fKey = key;
381 }
382
383 //_____________________________________________________________________________
384 void AliSimulation::SetDefaultStorage(const char* uri) {
385   // Store the desired default CDB storage location
386   // Activate it later within the Run() method
387   
388   fCDBUri = uri;
389   
390 }
391
392 //_____________________________________________________________________________
393 void AliSimulation::SetQARefDefaultStorage(const char* uri) {
394   // Store the desired default CDB storage location
395   // Activate it later within the Run() method
396   
397   fQARefUri = uri;
398   AliQAv1::SetQARefStorage(fQARefUri.Data()) ;
399 }
400
401 //_____________________________________________________________________________
402 void AliSimulation::SetSpecificStorage(const char* calibType, const char* uri) {
403 // Store a detector-specific CDB storage location
404 // Activate it later within the Run() method
405
406   AliCDBPath aPath(calibType);
407   if(!aPath.IsValid()){
408         AliError(Form("Not a valid path: %s", calibType));
409         return;
410   }
411
412   TObject* obj = fSpecCDBUri.FindObject(calibType);
413   if (obj) fSpecCDBUri.Remove(obj);
414   fSpecCDBUri.Add(new TNamed(calibType, uri));
415
416 }
417
418 //_____________________________________________________________________________
419 void AliSimulation::SetRunNumber(Int_t run)
420 {
421 // sets run number
422 // Activate it later within the Run() method
423
424         fRun = run;
425 }
426
427 //_____________________________________________________________________________
428 void AliSimulation::SetSeed(Int_t seed)
429 {
430 // sets seed number
431 // Activate it later within the Run() method
432
433         fSeed = seed;
434 }
435
436 //_____________________________________________________________________________
437 Bool_t AliSimulation::SetRunNumberFromData()
438 {
439   // Set the CDB manager run number
440   // The run number is retrieved from gAlice
441
442     if (fSetRunNumberFromDataCalled) return kTRUE;
443     fSetRunNumberFromDataCalled = kTRUE;    
444   
445     AliCDBManager* man = AliCDBManager::Instance();
446     Int_t runData = -1, runCDB = -1;
447   
448     AliRunLoader* runLoader = LoadRun("READ");
449     if (!runLoader) return kFALSE;
450     else {
451         runData = runLoader->GetHeader()->GetRun();
452         delete runLoader;
453     }
454   
455     runCDB = man->GetRun();
456     if(runCDB >= 0) {
457         if (runCDB != runData) {
458                 AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
459                 AliWarning(Form("A run number was previously set in AliCDBManager: %d !", runCDB));
460                 AliWarning(Form("It will be replaced with the run number got from run header: %d !", runData));
461                 AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");    
462         }
463         
464     }
465       
466     man->SetRun(runData);
467     fRun = runData;
468     
469     if(man->GetRun() < 0) {
470         AliError("Run number not properly initalized!");
471         return kFALSE;
472     }
473   
474     man->Print();
475     
476     return kTRUE;
477 }
478
479 //_____________________________________________________________________________
480 void AliSimulation::SetConfigFile(const char* fileName)
481 {
482 // set the name of the config file
483
484   fConfigFileName = fileName;
485 }
486
487 //_____________________________________________________________________________
488 void AliSimulation::SetGAliceFile(const char* fileName)
489 {
490 // set the name of the galice file
491 // the path is converted to an absolute one if it is relative
492
493   fGAliceFileName = fileName;
494   if (!gSystem->IsAbsoluteFileName(fGAliceFileName)) {
495     char* absFileName = gSystem->ConcatFileName(gSystem->WorkingDirectory(),
496                                                 fGAliceFileName);
497     fGAliceFileName = absFileName;
498     delete[] absFileName;
499   }
500
501   AliDebug(2, Form("galice file name set to %s", fileName));
502 }
503
504 //_____________________________________________________________________________
505 void AliSimulation::SetEventsPerFile(const char* detector, const char* type, 
506                                      Int_t nEvents)
507 {
508 // set the number of events per file for the given detector and data type
509 // ("Hits", "Summable Digits", "Digits", "Reconstructed Points" or "Tracks")
510
511   TNamed* obj = new TNamed(detector, type);
512   obj->SetUniqueID(nEvents);
513   fEventsPerFile.Add(obj);
514 }
515
516 //_____________________________________________________________________________
517 Bool_t AliSimulation::MisalignGeometry(AliRunLoader *runLoader)
518 {
519   // Read the alignment objects from CDB.
520   // Each detector is supposed to have the
521   // alignment objects in DET/Align/Data CDB path.
522   // All the detector objects are then collected,
523   // sorted by geometry level (starting from ALIC) and
524   // then applied to the TGeo geometry.
525   // Finally an overlaps check is performed.
526
527   if (!AliGeomManager::GetGeometry() || !AliGeomManager::GetGeometry()->IsClosed()) {
528     AliError("Can't apply the misalignment! Geometry is not loaded or it is still opened!");
529     return kFALSE;
530   }  
531   
532   // initialize CDB storage, run number, set CDB lock
533   InitCDB();
534 //  if (!SetRunNumberFromData()) if (fStopOnError) return kFALSE;
535   SetCDBLock();
536     
537   Bool_t delRunLoader = kFALSE;
538   if (!runLoader) {
539     runLoader = LoadRun("READ");
540     if (!runLoader) return kFALSE;
541     delRunLoader = kTRUE;
542   }
543   
544   // Export ideal geometry 
545   if(!IsGeometryFromFile()) AliGeomManager::GetGeometry()->Export("geometry.root");
546
547   // Load alignment data from CDB and apply to geometry through AliGeomManager
548   if(fLoadAlignFromCDB){
549     
550     TString detStr = fLoadAlObjsListOfDets;
551     TString loadAlObjsListOfDets = "";
552     
553     TObjArray* detArray = runLoader->GetAliRun()->Detectors();
554     for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
555       AliModule* det = (AliModule*) detArray->At(iDet);
556       if (!det || !det->IsActive()) continue;
557       if (IsSelected(det->GetName(), detStr)) {
558         //add det to list of dets to be aligned from CDB
559         loadAlObjsListOfDets += det->GetName();
560         loadAlObjsListOfDets += " ";
561       }
562     } // end loop over detectors
563     loadAlObjsListOfDets.Prepend("GRP "); //add alignment objects for non-sensitive modules
564     AliGeomManager::ApplyAlignObjsFromCDB(loadAlObjsListOfDets.Data());
565   }else{
566     // Check if the array with alignment objects was
567     // provided by the user. If yes, apply the objects
568     // to the present TGeo geometry
569     if (fAlignObjArray) {
570       if (AliGeomManager::ApplyAlignObjsToGeom(*fAlignObjArray) == kFALSE) {
571         AliError("The misalignment of one or more volumes failed!"
572                  "Compare the list of simulated detectors and the list of detector alignment data!");
573         if (delRunLoader) delete runLoader;
574         return kFALSE;
575       }
576     }
577   }
578
579   // Update the internal geometry of modules (ITS needs it)
580   TString detStr = fLoadAlObjsListOfDets;
581   TObjArray* detArray = runLoader->GetAliRun()->Detectors();
582   for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
583
584     AliModule* det = (AliModule*) detArray->At(iDet);
585     if (!det || !det->IsActive()) continue;
586     if (IsSelected(det->GetName(), detStr)) {
587       det->UpdateInternalGeometry();
588     }
589   } // end loop over detectors
590
591
592   if (delRunLoader) delete runLoader;
593
594   return kTRUE;
595 }
596
597 //_____________________________________________________________________________
598 void AliSimulation::MergeWith(const char* fileName, Int_t nSignalPerBkgrd)
599 {
600 // add a file with background events for merging
601
602   TObjString* fileNameStr = new TObjString(fileName);
603   fileNameStr->SetUniqueID(nSignalPerBkgrd);
604   if (!fBkgrdFileNames) fBkgrdFileNames = new TObjArray;
605   fBkgrdFileNames->Add(fileNameStr);
606 }
607
608 void AliSimulation::EmbedInto(const char* fileName, Int_t nSignalPerBkgrd)
609 {
610 // add a file with background events for embeddin
611   MergeWith(fileName, nSignalPerBkgrd);
612   fEmbeddingFlag = kTRUE;
613 }
614
615 //_____________________________________________________________________________
616 Bool_t AliSimulation::Run(Int_t nEvents)
617 {
618 // run the generation, simulation and digitization
619
620  
621   AliCodeTimerAuto("",0)
622   AliSysInfo::AddStamp("Start_Run");
623   
624   // Load run number and seed from environmental vars
625   ProcessEnvironmentVars();
626   AliSysInfo::AddStamp("ProcessEnvironmentVars");
627
628   gRandom->SetSeed(fSeed);
629    
630   if (nEvents > 0) fNEvents = nEvents;
631
632   // Run generator-only code on demand
633   if (fRunGeneratorOnly)
634   {
635     if(!RunGeneratorOnly())
636     {
637       if (fStopOnError) return kFALSE;
638     }
639     else
640       return kTRUE;
641   }
642
643   // create and setup the HLT instance
644   if (!fRunHLT.IsNull() && !CreateHLT()) {
645     if (fStopOnError) return kFALSE;
646     // disable HLT
647     fRunHLT="";
648   }
649   
650   // generation and simulation -> hits
651   if (fRunGeneration) {
652     if (!RunSimulation()) if (fStopOnError) return kFALSE;
653   }
654   AliSysInfo::AddStamp("RunSimulation");
655            
656   // initialize CDB storage from external environment
657   // (either CDB manager or AliSimulation setters),
658   // if not already done in RunSimulation()
659   InitCDB();
660   AliSysInfo::AddStamp("InitCDB");
661   
662   // Set run number in CDBManager from data 
663   // From this point on the run number must be always loaded from data!
664   if (!SetRunNumberFromData()) if (fStopOnError) return kFALSE;
665   
666   // Set CDB lock: from now on it is forbidden to reset the run number
667   // or the default storage or to activate any further storage!
668   SetCDBLock();
669
670   // If RunSimulation was not called, load the geometry and misalign it
671   if (!AliGeomManager::GetGeometry()) {
672     // Initialize the geometry manager
673     AliGeomManager::LoadGeometry("geometry.root");
674     AliSysInfo::AddStamp("GetGeometry");
675 //    // Check that the consistency of symbolic names for the activated subdetectors
676 //    // in the geometry loaded by AliGeomManager
677 //    AliRunLoader* runLoader = LoadRun("READ");
678 //    if (!runLoader) return kFALSE;
679 //
680 //    TString detsToBeChecked = "";
681 //    TObjArray* detArray = runLoader->GetAliRun()->Detectors();
682 //    for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
683 //      AliModule* det = (AliModule*) detArray->At(iDet);
684 //      if (!det || !det->IsActive()) continue;
685 //      detsToBeChecked += det->GetName();
686 //      detsToBeChecked += " ";
687 //    } // end loop over detectors
688 //    if(!AliGeomManager::CheckSymNamesLUT(detsToBeChecked.Data()))
689     if(!AliGeomManager::CheckSymNamesLUT("ALL"))
690         AliFatalClass("Current loaded geometry differs in the definition of symbolic names!");
691         
692     if (!AliGeomManager::GetGeometry()) if (fStopOnError) return kFALSE;
693     // Misalign geometry
694     if(!MisalignGeometry()) if (fStopOnError) return kFALSE;
695   }
696   AliSysInfo::AddStamp("MissalignGeometry");
697
698
699   // hits -> summable digits
700   AliSysInfo::AddStamp("Start_sdigitization");
701   if (!fMakeSDigits.IsNull()) {
702     if (!RunSDigitization(fMakeSDigits)) if (fStopOnError) return kFALSE;
703  
704   }
705   AliSysInfo::AddStamp("Stop_sdigitization");
706   
707   AliSysInfo::AddStamp("Start_digitization");  
708   // summable digits -> digits  
709   if (!fMakeDigits.IsNull()) {
710     if (!RunDigitization(fMakeDigits, fMakeDigitsFromHits)) {
711       if (fStopOnError) return kFALSE;
712     }
713    }
714   AliSysInfo::AddStamp("Stop_digitization");
715
716   
717   
718   // hits -> digits
719   if (!fMakeDigitsFromHits.IsNull()) {
720     if (fBkgrdFileNames && (fBkgrdFileNames->GetEntriesFast() > 0)) {
721       AliWarning(Form("Merging and direct creation of digits from hits " 
722                  "was selected for some detectors. "
723                  "No merging will be done for the following detectors: %s",
724                  fMakeDigitsFromHits.Data()));
725     }
726     if (!RunHitsDigitization(fMakeDigitsFromHits)) {
727       if (fStopOnError) return kFALSE;
728     }
729   }
730
731   AliSysInfo::AddStamp("Hits2Digits");
732   
733   
734   // digits -> trigger
735   if (!fTriggerConfig.IsNull() && !RunTrigger(fTriggerConfig,fMakeDigits)) {
736     if (fStopOnError) return kFALSE;
737   }
738
739   AliSysInfo::AddStamp("RunTrigger");
740   
741   
742   // digits -> raw data
743   if (!fWriteRawData.IsNull()) {
744     if (!WriteRawData(fWriteRawData, fRawDataFileName, 
745                       fDeleteIntermediateFiles,fWriteSelRawData)) {
746       if (fStopOnError) return kFALSE;
747     }
748   }
749
750   AliSysInfo::AddStamp("WriteRaw");
751   
752   // run HLT simulation on simulated digit data if raw data is not
753   // simulated, otherwise its called as part of WriteRawData
754   if (!fRunHLT.IsNull() && fWriteRawData.IsNull()) {
755     if (!RunHLT()) {
756       if (fStopOnError) return kFALSE;
757     }
758   }
759
760   AliSysInfo::AddStamp("RunHLT");
761   
762   //QA
763   if (fRunQA) {
764       Bool_t rv = RunQA() ; 
765       if (!rv)
766           if (fStopOnError) 
767               return kFALSE ;
768   }
769
770   AliSysInfo::AddStamp("RunQA");
771   //
772   StoreUsedCDBMaps();
773   //  
774   TString snapshotFileOut("");
775   if(TString(gSystem->Getenv("OCDB_SNAPSHOT_CREATE")) == TString("kTRUE")){ 
776       AliInfo(" ******** Creating the snapshot! *********");
777       TString snapshotFile(gSystem->Getenv("OCDB_SNAPSHOT_FILENAME")); 
778       if(!(snapshotFile.IsNull() || snapshotFile.IsWhitespace())) 
779           snapshotFileOut = snapshotFile;
780       else 
781           snapshotFileOut="OCDB.root"; 
782       AliCDBManager::Instance()->DumpToSnapshotFile(snapshotFileOut.Data(),kFALSE); 
783   }
784
785   // Cleanup of CDB manager: cache and active storages!
786   AliCDBManager::Instance()->ClearCache();
787
788   return kTRUE;
789 }
790
791 //_______________________________________________________________________
792 Bool_t AliSimulation::RunLego(const char *setup, Int_t nc1, Float_t c1min,
793                      Float_t c1max,Int_t nc2,Float_t c2min,Float_t c2max,
794                      Float_t rmin,Float_t rmax,Float_t zmax, AliLegoGenerator* gener, Int_t nev)
795 {
796   //
797   // Generates lego plots of:
798   //    - radiation length map phi vs theta
799   //    - radiation length map phi vs eta
800   //    - interaction length map
801   //    - g/cm2 length map
802   //
803   //  ntheta    bins in theta, eta
804   //  themin    minimum angle in theta (degrees)
805   //  themax    maximum angle in theta (degrees)
806   //  nphi      bins in phi
807   //  phimin    minimum angle in phi (degrees)
808   //  phimax    maximum angle in phi (degrees)
809   //  rmin      minimum radius
810   //  rmax      maximum radius
811   //  
812   //
813   //  The number of events generated = ntheta*nphi
814   //  run input parameters in macro setup (default="Config.C")
815   //
816   //  Use macro "lego.C" to visualize the 3 lego plots in spherical coordinates
817   //Begin_Html
818   /*
819     <img src="picts/AliRunLego1.gif">
820   */
821   //End_Html
822   //Begin_Html
823   /*
824     <img src="picts/AliRunLego2.gif">
825   */
826   //End_Html
827   //Begin_Html
828   /*
829     <img src="picts/AliRunLego3.gif">
830   */
831   //End_Html
832   //
833
834 // run the generation and simulation
835
836   AliCodeTimerAuto("",0)
837
838   // initialize CDB storage and run number from external environment
839   // (either CDB manager or AliSimulation setters)
840   InitCDB();
841   InitRunNumber();
842   SetCDBLock();
843   
844   if (!gAlice) {
845     AliError("no gAlice object. Restart aliroot and try again.");
846     return kFALSE;
847   }
848   if (gAlice->Modules()->GetEntries() > 0) {
849     AliError("gAlice was already run. Restart aliroot and try again.");
850     return kFALSE;
851   }
852
853   AliInfo(Form("initializing gAlice with config file %s",
854           fConfigFileName.Data()));
855
856   // Number of events 
857     if (nev == -1) nev  = nc1 * nc2;
858     
859   // check if initialisation has been done
860   // If runloader has been initialized, set the number of events per file to nc1 * nc2
861     
862   // Set new generator
863   if (!gener) gener  = new AliLegoGenerator();
864   //
865   // Configure Generator
866
867   gener->SetRadiusRange(rmin, rmax);
868   gener->SetZMax(zmax);
869   gener->SetCoor1Range(nc1, c1min, c1max);
870   gener->SetCoor2Range(nc2, c2min, c2max);
871   
872   
873   //Create Lego object  
874   fLego = new AliLego("lego",gener);
875
876   //__________________________________________________________________________
877
878   gAlice->Announce();
879
880   gROOT->LoadMacro(setup);
881   gInterpreter->ProcessLine(gAlice->GetConfigFunction());
882
883   if(AliCDBManager::Instance()->GetRun() >= 0) { 
884     SetRunNumber(AliCDBManager::Instance()->GetRun());
885   } else {
886     AliWarning("Run number not initialized!!");
887   }
888
889   AliRunLoader::Instance()->CdGAFile();
890   
891   AliPDG::AddParticlesToPdgDataBase();  
892   
893   TVirtualMC::GetMC()->SetMagField(TGeoGlobalMagField::Instance()->GetField());
894
895   gAlice->GetMCApp()->Init();
896   
897   
898   //Must be here because some MCs (G4) adds detectors here and not in Config.C
899   gAlice->InitLoaders();
900   AliRunLoader::Instance()->MakeTree("E");
901   
902   //
903   // Save stuff at the beginning of the file to avoid file corruption
904   AliRunLoader::Instance()->CdGAFile();
905   gAlice->Write();
906
907   //Save current generator
908   AliGenerator *gen=gAlice->GetMCApp()->Generator();
909   gAlice->GetMCApp()->ResetGenerator(gener);
910   //Prepare MC for Lego Run
911   TVirtualMC::GetMC()->InitLego();
912   
913   //Run Lego Object
914   
915   
916   AliRunLoader::Instance()->SetNumberOfEventsPerFile(nev);
917   TVirtualMC::GetMC()->ProcessRun(nev);
918   
919   // End of this run, close files
920   FinishRun();
921   // Restore current generator
922   gAlice->GetMCApp()->ResetGenerator(gen);
923   // Delete Lego Object
924   delete fLego;
925
926   return kTRUE;
927 }
928
929 //_____________________________________________________________________________
930 Bool_t AliSimulation::RunTrigger(const char* config, const char* detectors)
931 {
932   // run the trigger
933
934   AliCodeTimerAuto("",0)
935
936   // initialize CDB storage from external environment
937   // (either CDB manager or AliSimulation setters),
938   // if not already done in RunSimulation()
939   InitCDB();
940   
941   // Set run number in CDBManager from data 
942   // From this point on the run number must be always loaded from data!
943   if (!SetRunNumberFromData()) if (fStopOnError) return kFALSE;
944   
945   // Set CDB lock: from now on it is forbidden to reset the run number
946   // or the default storage or to activate any further storage!
947   SetCDBLock();
948    
949    AliRunLoader* runLoader = LoadRun("READ");
950    if (!runLoader) return kFALSE;
951    TString trconfiguration = config;
952
953    if (trconfiguration.IsNull()) {
954      if(!fTriggerConfig.IsNull()) {
955        trconfiguration = fTriggerConfig;
956      }
957      else
958        AliWarning("No trigger descriptor is specified. Loading the one that is in the CDB.");
959    }
960
961    runLoader->MakeTree( "GG" );
962    AliCentralTrigger* aCTP = runLoader->GetTrigger();
963    // Load Configuration
964    if (!aCTP->LoadConfiguration( trconfiguration ))
965      return kFALSE;
966
967    // digits -> trigger
968    if( !aCTP->RunTrigger( runLoader , detectors ) ) {
969       if (fStopOnError) {
970         //  delete aCTP;
971         return kFALSE;
972       }
973    }
974
975    delete runLoader;
976
977    return kTRUE;
978 }
979
980 //_____________________________________________________________________________
981 Bool_t AliSimulation::WriteTriggerRawData()
982 {
983   // Writes the CTP (trigger) DDL raw data
984   // Details of the format are given in the
985   // trigger TDR - pages 134 and 135.
986   AliCTPRawData writer;
987   //writer.RawData();
988   writer.RawDataRun2();
989
990   return kTRUE;
991 }
992
993 //_____________________________________________________________________________
994 Bool_t AliSimulation::RunSimulation(Int_t nEvents)
995 {
996 // run the generation and simulation
997
998   AliCodeTimerAuto("",0)
999
1000   // initialize CDB storage and run number from external environment
1001   // (either CDB manager or AliSimulation setters)
1002   AliSysInfo::AddStamp("RunSimulation_Begin");
1003   InitCDB();
1004   AliSysInfo::AddStamp("RunSimulation_InitCDB");
1005   InitRunNumber();
1006
1007   SetCDBLock();
1008   AliSysInfo::AddStamp("RunSimulation_SetCDBLock");
1009   
1010   if (!gAlice) {
1011     AliError("no gAlice object. Restart aliroot and try again.");
1012     return kFALSE;
1013   }
1014   if (gAlice->Modules()->GetEntries() > 0) {
1015     AliError("gAlice was already run. Restart aliroot and try again.");
1016     return kFALSE;
1017   }
1018   
1019   // Setup monitoring if requested
1020   gAlice->GetMCApp()->SetUseMonitoring(fUseMonitoring);
1021
1022   AliInfo(Form("initializing gAlice with config file %s",
1023           fConfigFileName.Data()));
1024
1025   //
1026   // Initialize ALICE Simulation run
1027   //
1028   gAlice->Announce();
1029
1030   //
1031   // If requested set the mag. field from the GRP entry.
1032   // After this the field is loccked and cannot be changed by Config.C
1033   if (fUseMagFieldFromGRP) {
1034       AliGRPManager grpM;
1035       grpM.ReadGRPEntry();
1036       grpM.SetMagField();
1037       AliInfo("Field is locked now. It cannot be changed in Config.C");
1038   }
1039 //
1040 // Execute Config.C
1041   TInterpreter::EErrorCode interpreterError=TInterpreter::kNoError;
1042   gROOT->LoadMacro(fConfigFileName.Data());
1043   Long_t interpreterResult=gInterpreter->ProcessLine(gAlice->GetConfigFunction(), &interpreterError);
1044   if (interpreterResult!=0 || interpreterError!=TInterpreter::kNoError) {
1045     AliFatal(Form("execution of config file \"%s\" failed with error %d", fConfigFileName.Data(), (int)interpreterError));
1046   }
1047   AliSysInfo::AddStamp("RunSimulation_Config");
1048
1049 //
1050 // If requested obtain the vertex position and vertex sigma_z from the CDB
1051 // This overwrites the settings from the Config.C  
1052   if (fUseVertexFromCDB) {
1053       Double_t vtxPos[3] = {0., 0., 0.}; 
1054       Double_t vtxSig[3] = {0., 0., 0.};
1055       AliCDBEntry* entry = AliCDBManager::Instance()->Get("GRP/Calib/MeanVertex");
1056       if (entry) {
1057           AliESDVertex* vertex = dynamic_cast<AliESDVertex*> (entry->GetObject());
1058           if (vertex) {
1059               if(vertex->GetXRes()>2.8) { // > pipe radius --> it's a dummy object, don't use it 
1060                   entry = AliCDBManager::Instance()->Get("GRP/Calib/MeanVertexSPD");
1061                   if (entry) vertex = dynamic_cast<AliESDVertex*> (entry->GetObject());
1062               }
1063           }
1064           if (vertex) {
1065               vertex->GetXYZ(vtxPos);
1066               vertex->GetSigmaXYZ(vtxSig);
1067               AliInfo("Overwriting Config.C vertex settings !");
1068               AliInfo(Form("Vertex position from OCDB entry: x = %13.3f, y = %13.3f, z = %13.3f (sigma = %13.3f)\n",
1069                            vtxPos[0], vtxPos[1], vtxPos[2], vtxSig[2]));
1070               
1071               AliGenerator *gen = gAlice->GetMCApp()->Generator();
1072               gen->SetOrigin(vtxPos[0], vtxPos[1], vtxPos[2]);   // vertex position
1073               gen->SetSigmaZ(vtxSig[2]);
1074           }
1075       }
1076   }
1077
1078   // If requested we take the SOR and EOR time-stamps from the GRP and use them
1079   // in order to generate the event time-stamps
1080   if (fUseTimeStampFromCDB) {
1081     AliGRPManager grpM;
1082     grpM.ReadGRPEntry();
1083     const AliGRPObject *grpObj = grpM.GetGRPData();
1084     if (!grpObj || (grpObj->GetTimeEnd() <= grpObj->GetTimeStart())) {
1085       AliError("Missing GRP or bad SOR/EOR time-stamps! Switching off the time-stamp generation from GRP!");
1086       fTimeStart = fTimeEnd = 0;
1087       fUseTimeStampFromCDB = kFALSE;
1088     }
1089     else {
1090       fTimeStart = grpObj->GetTimeStart();
1091       fTimeEnd = grpObj->GetTimeEnd();
1092     }
1093   }
1094   
1095   if(AliCDBManager::Instance()->GetRun() >= 0) { 
1096     AliRunLoader::Instance()->SetRunNumber(AliCDBManager::Instance()->GetRun());
1097     AliRunLoader::Instance()->SetNumberOfEventsPerRun(fNEvents);
1098   } else {
1099         AliWarning("Run number not initialized!!");
1100   }
1101   
1102    AliRunLoader::Instance()->CdGAFile();
1103    
1104
1105    AliPDG::AddParticlesToPdgDataBase();  
1106
1107    TVirtualMC::GetMC()->SetMagField(TGeoGlobalMagField::Instance()->GetField());
1108    AliSysInfo::AddStamp("RunSimulation_GetField");
1109    gAlice->GetMCApp()->Init();
1110    AliSysInfo::AddStamp("RunSimulation_InitMCApp");
1111
1112    //Must be here because some MCs (G4) adds detectors here and not in Config.C
1113    gAlice->InitLoaders();
1114    AliRunLoader::Instance()->MakeTree("E");
1115    AliRunLoader::Instance()->LoadKinematics("RECREATE");
1116    AliRunLoader::Instance()->LoadTrackRefs("RECREATE");
1117    AliRunLoader::Instance()->LoadHits("all","RECREATE");
1118    //
1119    // Save stuff at the beginning of the file to avoid file corruption
1120    AliRunLoader::Instance()->CdGAFile();
1121    gAlice->Write();
1122    gAlice->SetEventNrInRun(-1); //important - we start Begin event from increasing current number in run
1123    AliSysInfo::AddStamp("RunSimulation_InitLoaders");
1124   //___________________________________________________________________________________________
1125   
1126   AliSysInfo::AddStamp("RunSimulation_TriggerDescriptor");
1127
1128   // Set run number in CDBManager
1129   AliInfo(Form("Run number: %d",AliCDBManager::Instance()->GetRun()));
1130
1131   AliRunLoader* runLoader = AliRunLoader::Instance();
1132   if (!runLoader) {
1133              AliError(Form("gAlice has no run loader object. "
1134                              "Check your config file: %s", fConfigFileName.Data()));
1135              return kFALSE;
1136   }
1137   SetGAliceFile(runLoader->GetFileName());
1138       
1139   // Misalign geometry
1140 #if ROOT_VERSION_CODE < 331527
1141   AliGeomManager::SetGeometry(gGeoManager);
1142   
1143   // Check that the consistency of symbolic names for the activated subdetectors
1144   // in the geometry loaded by AliGeomManager
1145   TString detsToBeChecked = "";
1146   TObjArray* detArray = runLoader->GetAliRun()->Detectors();
1147   for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
1148     AliModule* det = (AliModule*) detArray->At(iDet);
1149     if (!det || !det->IsActive()) continue;
1150     detsToBeChecked += det->GetName();
1151     detsToBeChecked += " ";
1152   } // end loop over detectors
1153   if(!AliGeomManager::CheckSymNamesLUT(detsToBeChecked.Data()))
1154     AliFatalClass("Current loaded geometry differs in the definition of symbolic names!");
1155   MisalignGeometry(runLoader);
1156   AliSysInfo::AddStamp("RunSimulation_MisalignGeometry");
1157 #endif
1158
1159 //   AliRunLoader* runLoader = AliRunLoader::Instance();
1160 //   if (!runLoader) {
1161 //     AliError(Form("gAlice has no run loader object. "
1162 //                   "Check your config file: %s", fConfigFileName.Data()));
1163 //     return kFALSE;
1164 //   }
1165 //   SetGAliceFile(runLoader->GetFileName());
1166
1167   if (!gAlice->GetMCApp()->Generator()) {
1168     AliError(Form("gAlice has no generator object. "
1169                   "Check your config file: %s", fConfigFileName.Data()));
1170     return kFALSE;
1171   }
1172
1173   // Write GRP entry corresponding to the setting found in Cofig.C
1174   if (fWriteGRPEntry)
1175     WriteGRPEntry();
1176   AliSysInfo::AddStamp("RunSimulation_WriteGRP");
1177
1178   if (nEvents <= 0) nEvents = fNEvents;
1179
1180   // get vertex from background file in case of merging
1181   if (fUseBkgrdVertex &&
1182       fBkgrdFileNames && (fBkgrdFileNames->GetEntriesFast() > 0)) {
1183     Int_t signalPerBkgrd = GetNSignalPerBkgrd(nEvents);
1184     const char* fileName = ((TObjString*)
1185                             (fBkgrdFileNames->At(0)))->GetName();
1186     AliInfo(Form("The vertex will be taken from the background "
1187                  "file %s with nSignalPerBackground = %d", 
1188                  fileName, signalPerBkgrd));
1189     AliVertexGenFile* vtxGen = new AliVertexGenFile(fileName, signalPerBkgrd);
1190     gAlice->GetMCApp()->Generator()->SetVertexGenerator(vtxGen);
1191   }
1192
1193   if (!fRunSimulation) {
1194     gAlice->GetMCApp()->Generator()->SetTrackingFlag(0);
1195   }
1196
1197   // set the number of events per file for given detectors and data types
1198   for (Int_t i = 0; i < fEventsPerFile.GetEntriesFast(); i++) {
1199     if (!fEventsPerFile[i]) continue;
1200     const char* detName = fEventsPerFile[i]->GetName();
1201     const char* typeName = fEventsPerFile[i]->GetTitle();
1202     TString loaderName(detName);
1203     loaderName += "Loader";
1204     AliLoader* loader = runLoader->GetLoader(loaderName);
1205     if (!loader) {
1206       AliError(Form("RunSimulation no loader for %s found\n Number of events per file not set for %s %s", 
1207                     detName, typeName, detName));
1208       continue;
1209     }
1210     AliDataLoader* dataLoader = 
1211       loader->GetDataLoader(typeName);
1212     if (!dataLoader) {
1213       AliError(Form("no data loader for %s found\n"
1214                     "Number of events per file not set for %s %s", 
1215                     typeName, detName, typeName));
1216       continue;
1217     }
1218     dataLoader->SetNumberOfEventsPerFile(fEventsPerFile[i]->GetUniqueID());
1219     AliDebug(1, Form("number of events per file set to %d for %s %s",
1220                      fEventsPerFile[i]->GetUniqueID(), detName, typeName));
1221   }
1222
1223   AliInfo("running gAlice");
1224   AliSysInfo::AddStamp("Start_ProcessRun");
1225
1226   // Create the Root Tree with one branch per detector
1227   //Hits moved to begin event -> now we are crating separate tree for each event
1228   TVirtualMC::GetMC()->ProcessRun(nEvents);
1229
1230   // End of this run, close files
1231   if(nEvents>0) FinishRun();
1232
1233   AliSysInfo::AddStamp("Stop_ProcessRun");
1234   delete runLoader;
1235
1236   return kTRUE;
1237 }
1238
1239 //_____________________________________________________________________________
1240 Bool_t AliSimulation::RunGeneratorOnly()
1241 {
1242   // Execute Config.C
1243   TInterpreter::EErrorCode interpreterError=TInterpreter::kNoError;
1244   gROOT->LoadMacro(fConfigFileName.Data());
1245   Long_t interpreterResult=gInterpreter->ProcessLine(gAlice->GetConfigFunction(), &interpreterError);
1246   if (interpreterResult!=0 || interpreterError!=TInterpreter::kNoError) {
1247     AliFatal(Form("execution of config file \"%s\" failed with error %d", fConfigFileName.Data(), (int)interpreterError));
1248   }
1249
1250   // Setup the runloader and generator, check if everything is OK
1251   AliRunLoader* runLoader = AliRunLoader::Instance();
1252   AliGenerator* generator = gAlice->GetMCApp()->Generator();
1253   if (!runLoader) {
1254     AliError(Form("gAlice has no run loader object. "
1255                   "Check your config file: %s", fConfigFileName.Data()));
1256     return kFALSE;
1257   }
1258   if (!generator) {
1259     AliError(Form("gAlice has no generator object. "
1260                   "Check your config file: %s", fConfigFileName.Data()));
1261     return kFALSE;
1262   }
1263
1264   runLoader->LoadKinematics("RECREATE");
1265   runLoader->MakeTree("E");
1266
1267   // Create stack and header
1268   runLoader->MakeStack();
1269   AliStack*  stack      = runLoader->Stack();
1270   AliHeader* header     = runLoader->GetHeader();
1271
1272   // Intialize generator
1273   generator->Init();
1274   generator->SetStack(stack);
1275
1276   // Run main generator loop
1277
1278   for (Int_t iev=0; iev<fNEvents; iev++)
1279   {
1280     // Initialize event
1281     header->Reset(0,iev);
1282     runLoader->SetEventNumber(iev);
1283     stack->Reset();
1284     runLoader->MakeTree("K");
1285
1286     // Generate event
1287     generator->Generate();
1288
1289     // Finish event
1290     header->SetNprimary(stack->GetNprimary());
1291     header->SetNtrack(stack->GetNtrack());
1292     stack->FinishEvent();
1293     header->SetStack(stack);
1294     runLoader->TreeE()->Fill();
1295     runLoader->WriteKinematics("OVERWRITE");
1296   }
1297
1298   // Finalize
1299   generator->FinishRun();
1300   // Write file
1301   runLoader->WriteHeader("OVERWRITE");
1302   generator->Write();
1303   runLoader->Write();
1304
1305   return kTRUE;
1306 }
1307
1308 //_____________________________________________________________________________
1309 Bool_t AliSimulation::RunSDigitization(const char* detectors)
1310 {
1311 // run the digitization and produce summable digits
1312   static Int_t eventNr=0;
1313   AliCodeTimerAuto("",0) ;
1314
1315   // initialize CDB storage, run number, set CDB lock
1316   InitCDB();
1317   if (!SetRunNumberFromData()) if (fStopOnError) return kFALSE;
1318   SetCDBLock();
1319   
1320   AliRunLoader* runLoader = LoadRun();
1321   if (!runLoader) return kFALSE;
1322
1323   TString detStr = detectors;
1324   TObjArray* detArray = runLoader->GetAliRun()->Detectors();
1325   for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
1326     AliModule* det = (AliModule*) detArray->At(iDet);
1327     if (!det || !det->IsActive()) continue;
1328     if (IsSelected(det->GetName(), detStr)) {
1329       AliInfo(Form("creating summable digits for %s", det->GetName()));
1330       AliCodeTimerStart(Form("creating summable digits for %s", det->GetName()));
1331       det->Hits2SDigits();
1332       AliCodeTimerStop(Form("creating summable digits for %s", det->GetName()));
1333       AliSysInfo::AddStamp(Form("Digit_%s_%d",det->GetName(),eventNr), 0,1, eventNr);
1334     }
1335   }
1336
1337   if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
1338     AliError(Form("the following detectors were not found: %s",
1339                   detStr.Data()));
1340     if (fStopOnError) return kFALSE;
1341   }
1342   eventNr++;
1343   delete runLoader;
1344
1345   return kTRUE;
1346 }
1347
1348
1349 //_____________________________________________________________________________
1350 Bool_t AliSimulation::RunDigitization(const char* detectors, 
1351                                       const char* excludeDetectors)
1352 {
1353 // run the digitization and produce digits from sdigits
1354
1355   AliCodeTimerAuto("",0)
1356
1357   // initialize CDB storage, run number, set CDB lock
1358   InitCDB();
1359   if (!SetRunNumberFromData()) if (fStopOnError) return kFALSE;
1360   SetCDBLock();
1361   
1362   delete AliRunLoader::Instance();
1363   delete gAlice;
1364   gAlice = NULL;
1365
1366   Int_t nStreams = 1;
1367   if (fBkgrdFileNames) nStreams = fBkgrdFileNames->GetEntriesFast() + 1;
1368   Int_t signalPerBkgrd = GetNSignalPerBkgrd();
1369   AliDigitizationInput digInp(nStreams, signalPerBkgrd);
1370   // digInp.SetEmbeddingFlag(fEmbeddingFlag);
1371   digInp.SetRegionOfInterest(fRegionOfInterest);
1372   digInp.SetInputStream(0, fGAliceFileName.Data());
1373   for (Int_t iStream = 1; iStream < nStreams; iStream++) {
1374     const char* fileName = ((TObjString*)(fBkgrdFileNames->At(iStream-1)))->GetName();
1375     digInp.SetInputStream(iStream, fileName);
1376   }
1377   TObjArray detArr;
1378   detArr.SetOwner(kTRUE);
1379   TString detStr = detectors;
1380   TString detExcl = excludeDetectors;
1381   if (!static_cast<AliStream*>(digInp.GetInputStream(0))->ImportgAlice()) {
1382     AliError("Error occured while getting gAlice from Input 0");
1383     return kFALSE;
1384   }
1385   AliRunLoader* runLoader = AliRunLoader::GetRunLoader(digInp.GetInputStream(0)->GetFolderName());
1386   TObjArray* detArray = runLoader->GetAliRun()->Detectors();
1387   for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
1388     AliModule* det = (AliModule*) detArray->At(iDet);
1389     if (!det || !det->IsActive()) continue;
1390     if (!IsSelected(det->GetName(), detStr) || IsSelected(det->GetName(), detExcl)) continue;
1391     AliDigitizer* digitizer = det->CreateDigitizer(&digInp);
1392     if (!digitizer || !digitizer->Init()) {
1393       AliError(Form("no digitizer for %s", det->GetName()));
1394       if (fStopOnError) return kFALSE;
1395       else continue;
1396     }
1397     detArr.AddLast(digitizer);    
1398     AliInfo(Form("Created digitizer from SDigits -> Digits for %s", det->GetName()));    
1399   }
1400   //
1401   if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
1402     AliError(Form("the following detectors were not found: %s", detStr.Data()));
1403     if (fStopOnError) return kFALSE;
1404   }
1405   //
1406   Int_t ndigs = detArr.GetEntriesFast();
1407   Int_t eventsCreated = 0;
1408   AliRunLoader* outRl =  digInp.GetOutRunLoader();
1409   while ((eventsCreated++ < fNEvents) || (fNEvents < 0)) {
1410     if (!digInp.ConnectInputTrees()) break;
1411     digInp.InitEvent(); //this must be after call of Connect Input tress.
1412     if (outRl) outRl->SetEventNumber(eventsCreated-1);
1413     static_cast<AliStream*>(digInp.GetInputStream(0))->ImportgAlice(); // use gAlice of the first input stream
1414     for (int id=0;id<ndigs;id++) ((AliDigitizer*)detArr[id])->Digitize("");
1415     digInp.FinishEvent();
1416   };
1417   digInp.FinishGlobal();
1418   //
1419   return kTRUE;
1420 }
1421
1422 //_____________________________________________________________________________
1423 Bool_t AliSimulation::RunHitsDigitization(const char* detectors)
1424 {
1425 // run the digitization and produce digits from hits
1426
1427   AliCodeTimerAuto("",0)
1428
1429   // initialize CDB storage, run number, set CDB lock
1430   InitCDB();
1431   if (!SetRunNumberFromData()) if (fStopOnError) return kFALSE;
1432   SetCDBLock();
1433   
1434   AliRunLoader* runLoader = LoadRun("READ");
1435   if (!runLoader) return kFALSE;
1436
1437   TString detStr = detectors;
1438   TObjArray* detArray = runLoader->GetAliRun()->Detectors();
1439   for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
1440     AliModule* det = (AliModule*) detArray->At(iDet);
1441     if (!det || !det->IsActive()) continue;
1442     if (IsSelected(det->GetName(), detStr)) {
1443       AliInfo(Form("creating digits from hits for %s", det->GetName()));
1444       det->Hits2Digits();
1445     }
1446   }
1447
1448   if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
1449     AliError(Form("the following detectors were not found: %s", 
1450                   detStr.Data()));
1451     if (fStopOnError) return kFALSE;
1452   }
1453
1454   return kTRUE;
1455 }
1456
1457 //_____________________________________________________________________________
1458 Bool_t AliSimulation::WriteRawData(const char* detectors, 
1459                                    const char* fileName,
1460                                    Bool_t deleteIntermediateFiles,
1461                                    Bool_t selrawdata)
1462 {
1463 // convert the digits to raw data
1464 // First DDL raw data files for the given detectors are created.
1465 // If a file name is given, the DDL files are then converted to a DATE file.
1466 // If deleteIntermediateFiles is true, the DDL raw files are deleted 
1467 // afterwards.
1468 // If the file name has the extension ".root", the DATE file is converted
1469 // to a root file.
1470 // If deleteIntermediateFiles is true, the DATE file is deleted afterwards.
1471 // 'selrawdata' flag can be used to enable writing of detectors raw data
1472 // accoring to the trigger cluster.
1473
1474   AliCodeTimerAuto("",0)
1475   AliSysInfo::AddStamp("WriteRawData_Start");
1476   
1477   TString detStr = detectors;
1478   if (!WriteRawFiles(detStr.Data())) {
1479     if (fStopOnError) return kFALSE;
1480   }
1481   AliSysInfo::AddStamp("WriteRawFiles");
1482
1483   // run HLT simulation on simulated DDL raw files
1484   // and produce HLT ddl raw files to be included in date/root file
1485   // bugfix 2009-06-26: the decision whether to write HLT raw data
1486   // is taken in RunHLT. Here HLT always needs to be run in order to
1487   // create HLT digits, unless its switched off. This is due to the
1488   // special placement of the HLT between the generation of DDL files
1489   // and conversion to DATE/Root file.
1490   detStr.ReplaceAll("HLT", "");
1491   if (!fRunHLT.IsNull()) {
1492     if (!RunHLT()) {
1493       if (fStopOnError) return kFALSE;
1494     }
1495   }
1496   AliSysInfo::AddStamp("WriteRawData_RunHLT");
1497
1498   TString dateFileName(fileName);
1499   if (!dateFileName.IsNull()) {
1500     Bool_t rootOutput = dateFileName.EndsWith(".root");
1501     if (rootOutput) dateFileName += ".date";
1502     TString selDateFileName;
1503     if (selrawdata) {
1504       selDateFileName = "selected.";
1505       selDateFileName+= dateFileName;
1506     }
1507     if (!ConvertRawFilesToDate(dateFileName,selDateFileName)) {
1508       if (fStopOnError) return kFALSE;
1509     }
1510     AliSysInfo::AddStamp("ConvertRawFilesToDate");
1511     if (deleteIntermediateFiles) {
1512       AliRunLoader* runLoader = LoadRun("READ");
1513       if (runLoader) for (Int_t iEvent = 0; 
1514                           iEvent < runLoader->GetNumberOfEvents(); iEvent++) {
1515         char command[256];
1516         snprintf(command, 256, "rm -r raw%d", iEvent);
1517         gSystem->Exec(command);
1518       }
1519       delete runLoader;
1520     }
1521
1522     if (rootOutput) {
1523       if (!ConvertDateToRoot(dateFileName, fileName)) {
1524         if (fStopOnError) return kFALSE;
1525       }
1526       AliSysInfo::AddStamp("ConvertDateToRoot");
1527       if (deleteIntermediateFiles) {
1528         gSystem->Unlink(dateFileName);
1529       }
1530       if (selrawdata) {
1531         TString selFileName = "selected.";
1532         selFileName        += fileName;
1533         if (!ConvertDateToRoot(selDateFileName, selFileName)) {
1534           if (fStopOnError) return kFALSE;
1535         }
1536         if (deleteIntermediateFiles) {
1537           gSystem->Unlink(selDateFileName);
1538         }
1539       }
1540     }
1541   }
1542
1543   return kTRUE;
1544 }
1545
1546 //_____________________________________________________________________________
1547 Bool_t AliSimulation::WriteRawFiles(const char* detectors)
1548 {
1549 // convert the digits to raw data DDL files
1550
1551   AliCodeTimerAuto("",0)
1552   
1553   AliRunLoader* runLoader = LoadRun("READ");
1554   if (!runLoader) return kFALSE;
1555
1556   // write raw data to DDL files
1557   for (Int_t iEvent = 0; iEvent < runLoader->GetNumberOfEvents(); iEvent++) {
1558     AliInfo(Form("processing event %d", iEvent));
1559     runLoader->GetEvent(iEvent);
1560     TString baseDir = gSystem->WorkingDirectory();
1561     char dirName[256];
1562     snprintf(dirName, 256, "raw%d", iEvent);
1563     gSystem->MakeDirectory(dirName);
1564     if (!gSystem->ChangeDirectory(dirName)) {
1565       AliError(Form("couldn't change to directory %s", dirName));
1566       if (fStopOnError) return kFALSE; else continue;
1567     }
1568
1569     ofstream runNbFile(Form("run%u",runLoader->GetHeader()->GetRun()));
1570     runNbFile.close();
1571
1572     TString detStr = detectors;
1573     if (IsSelected("HLT", detStr)) {
1574       // Do nothing. "HLT" will be removed from detStr and HLT raw
1575       // data files are generated in RunHLT.
1576     }
1577
1578     TObjArray* detArray = runLoader->GetAliRun()->Detectors();
1579     for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
1580       AliModule* det = (AliModule*) detArray->At(iDet);
1581       if (!det || !det->IsActive()) continue;
1582       if (IsSelected(det->GetName(), detStr)) {
1583         AliInfo(Form("creating raw data from digits for %s", det->GetName()));
1584         det->Digits2Raw();
1585       }
1586     }
1587
1588     if (!WriteTriggerRawData())
1589       if (fStopOnError) return kFALSE;
1590
1591     gSystem->ChangeDirectory(baseDir);
1592     if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
1593       AliError(Form("the following detectors were not found: %s", 
1594                     detStr.Data()));
1595       if (fStopOnError) return kFALSE;
1596     }
1597   }
1598
1599   delete runLoader;
1600   
1601   return kTRUE;
1602 }
1603
1604 //_____________________________________________________________________________
1605 Bool_t AliSimulation::ConvertRawFilesToDate(const char* dateFileName,
1606                                             const char* selDateFileName)
1607 {
1608 // convert raw data DDL files to a DATE file with the program "dateStream"
1609 // The second argument is not empty when the user decides to write
1610 // the detectors raw data according to the trigger cluster.
1611
1612   AliCodeTimerAuto("",0)
1613   
1614   char* path = gSystem->Which(gSystem->Getenv("PATH"), "dateStream");
1615   if (!path) {
1616     AliError("the program dateStream was not found");
1617     if (fStopOnError) return kFALSE;
1618   } else {
1619     delete[] path;
1620   }
1621
1622   AliRunLoader* runLoader = LoadRun("READ");
1623   if (!runLoader) return kFALSE;
1624
1625   AliInfo(Form("converting raw data DDL files to DATE file %s", dateFileName));
1626   Bool_t selrawdata = kFALSE;
1627   if (strcmp(selDateFileName,"") != 0) selrawdata = kTRUE;
1628
1629   char command[256];
1630   // Note the option -s. It is used in order to avoid
1631   // the generation of SOR/EOR events.
1632   snprintf(command, 256, "dateStream -c -s -D -o %s -# %d -C -run %d", 
1633           dateFileName, runLoader->GetNumberOfEvents(),runLoader->GetHeader()->GetRun());
1634   FILE* pipe = gSystem->OpenPipe(command, "w");
1635
1636   if (!pipe) {
1637     AliError(Form("Cannot execute command: %s",command));
1638     return kFALSE;
1639   }
1640
1641   Int_t selEvents = 0;
1642   for (Int_t iEvent = 0; iEvent < runLoader->GetNumberOfEvents(); iEvent++) {
1643
1644     UInt_t detectorPattern = 0;
1645     runLoader->GetEvent(iEvent);
1646     if (!runLoader->LoadTrigger()) {
1647       AliCentralTrigger *aCTP = runLoader->GetTrigger();
1648       detectorPattern = aCTP->GetClusterMask();
1649       // Check if the event was triggered by CTP
1650       if (selrawdata) {
1651         if (aCTP->GetClassMask()) selEvents++;
1652       }
1653     }
1654     else {
1655       AliWarning("No trigger can be loaded! Some fields in the event header will be empty !");
1656       if (selrawdata) {
1657         AliWarning("No trigger can be loaded! Writing of selected raw data is abandoned !");
1658         selrawdata = kFALSE;
1659       }
1660     }
1661
1662     fprintf(pipe, "GDC DetectorPattern %u Timestamp %ld\n", detectorPattern, runLoader->GetHeader()->GetTimeStamp());
1663     Float_t ldc = 0;
1664     Int_t prevLDC = -1;
1665
1666     // loop over detectors and DDLs
1667     for (Int_t iDet = 0; iDet < AliDAQ::kNDetectors; iDet++) {
1668       for (Int_t iDDL = 0; iDDL < AliDAQ::NumberOfDdls(iDet); iDDL++) {
1669
1670         Int_t ddlID = AliDAQ::DdlID(iDet,iDDL);
1671         Int_t ldcID = Int_t(ldc + 0.0001);
1672         ldc += AliDAQ::NumberOfLdcs(iDet) / AliDAQ::NumberOfDdls(iDet);
1673
1674         char rawFileName[256];
1675         snprintf(rawFileName, 256, "raw%d/%s", 
1676                 iEvent, AliDAQ::DdlFileName(iDet,iDDL));
1677
1678         // check existence and size of raw data file
1679         FILE* file = fopen(rawFileName, "rb");
1680         if (!file) continue;
1681         fseek(file, 0, SEEK_END);
1682         unsigned long size = ftell(file);
1683         fclose(file);
1684         if (!size) continue;
1685
1686         if (ldcID != prevLDC) {
1687           fprintf(pipe, " LDC Id %d\n", ldcID);
1688           prevLDC = ldcID;
1689         }
1690         fprintf(pipe, "  Equipment Id %d Payload %s\n", ddlID, rawFileName);
1691       }
1692     }
1693   }
1694
1695   Int_t result = gSystem->ClosePipe(pipe);
1696
1697   if (!(selrawdata && selEvents > 0)) {
1698     delete runLoader;
1699     return (result == 0);
1700   }
1701
1702   AliInfo(Form("converting selected by trigger cluster raw data DDL files to DATE file %s", selDateFileName));
1703   
1704   snprintf(command, 256, "dateStream -c -s -D -o %s -# %d -C -run %d", 
1705           selDateFileName,selEvents,runLoader->GetHeader()->GetRun());
1706   FILE* pipe2 = gSystem->OpenPipe(command, "w");
1707
1708   for (Int_t iEvent = 0; iEvent < runLoader->GetNumberOfEvents(); iEvent++) {
1709
1710     // Get the trigger decision and cluster
1711     UInt_t detectorPattern = 0;
1712     TString detClust;
1713     runLoader->GetEvent(iEvent);
1714     if (!runLoader->LoadTrigger()) {
1715       AliCentralTrigger *aCTP = runLoader->GetTrigger();
1716       if (aCTP->GetClassMask() == 0) continue;
1717       detectorPattern = aCTP->GetClusterMask();
1718       detClust = AliDAQ::ListOfTriggeredDetectors(detectorPattern);
1719       AliInfo(Form("List of detectors to be read out: %s",detClust.Data()));
1720     }
1721
1722     fprintf(pipe2, "GDC DetectorPattern %u Timestamp %ld\n", detectorPattern, runLoader->GetHeader()->GetTimeStamp());
1723     Float_t ldc = 0;
1724     Int_t prevLDC = -1;
1725
1726     // loop over detectors and DDLs
1727     for (Int_t iDet = 0; iDet < AliDAQ::kNDetectors; iDet++) {
1728       // Write only raw data from detectors that
1729       // are contained in the trigger cluster(s)
1730       if (!IsSelected(AliDAQ::DetectorName(iDet),detClust)) continue;
1731
1732       for (Int_t iDDL = 0; iDDL < AliDAQ::NumberOfDdls(iDet); iDDL++) {
1733
1734         Int_t ddlID = AliDAQ::DdlID(iDet,iDDL);
1735         Int_t ldcID = Int_t(ldc + 0.0001);
1736         ldc += AliDAQ::NumberOfLdcs(iDet) / AliDAQ::NumberOfDdls(iDet);
1737
1738         char rawFileName[256];
1739         snprintf(rawFileName, 256, "raw%d/%s", 
1740                 iEvent, AliDAQ::DdlFileName(iDet,iDDL));
1741
1742         // check existence and size of raw data file
1743         FILE* file = fopen(rawFileName, "rb");
1744         if (!file) continue;
1745         fseek(file, 0, SEEK_END);
1746         unsigned long size = ftell(file);
1747         fclose(file);
1748         if (!size) continue;
1749
1750         if (ldcID != prevLDC) {
1751           fprintf(pipe2, " LDC Id %d\n", ldcID);
1752           prevLDC = ldcID;
1753         }
1754         fprintf(pipe2, "  Equipment Id %d Payload %s\n", ddlID, rawFileName);
1755       }
1756     }
1757   }
1758
1759   Int_t result2 = gSystem->ClosePipe(pipe2);
1760
1761   delete runLoader;
1762   return ((result == 0) && (result2 == 0));
1763 }
1764
1765 //_____________________________________________________________________________
1766 Bool_t AliSimulation::ConvertDateToRoot(const char* dateFileName,
1767                                         const char* rootFileName)
1768 {
1769 // convert a DATE file to a root file with the program "alimdc"
1770
1771   // ALIMDC setup
1772   const Int_t kDBSize = 2000000000;
1773   const Int_t kTagDBSize = 1000000000;
1774   const Bool_t kFilter = kFALSE;
1775   const Int_t kCompression = 1;
1776
1777   char* path = gSystem->Which(gSystem->Getenv("PATH"), "alimdc");
1778   if (!path) {
1779     AliError("the program alimdc was not found");
1780     if (fStopOnError) return kFALSE;
1781   } else {
1782     delete[] path;
1783   }
1784
1785   AliInfo(Form("converting DATE file %s to root file %s", 
1786                dateFileName, rootFileName));
1787
1788   const char* rawDBFS[2] = { "/tmp/mdc1", "/tmp/mdc2" };
1789   const char* tagDBFS    = "/tmp/mdc1/tags";
1790
1791   // User defined file system locations
1792   if (gSystem->Getenv("ALIMDC_RAWDB1")) 
1793     rawDBFS[0] = gSystem->Getenv("ALIMDC_RAWDB1");
1794   if (gSystem->Getenv("ALIMDC_RAWDB2")) 
1795     rawDBFS[1] = gSystem->Getenv("ALIMDC_RAWDB2");
1796   if (gSystem->Getenv("ALIMDC_TAGDB")) 
1797     tagDBFS = gSystem->Getenv("ALIMDC_TAGDB");
1798
1799   gSystem->Exec(Form("rm -rf %s",rawDBFS[0]));
1800   gSystem->Exec(Form("rm -rf %s",rawDBFS[1]));
1801   gSystem->Exec(Form("rm -rf %s",tagDBFS));
1802
1803   gSystem->Exec(Form("mkdir %s",rawDBFS[0]));
1804   gSystem->Exec(Form("mkdir %s",rawDBFS[1]));
1805   gSystem->Exec(Form("mkdir %s",tagDBFS));
1806
1807   Int_t result = gSystem->Exec(Form("alimdc %d %d %d %d %s", 
1808                                     kDBSize, kTagDBSize, kFilter, kCompression, dateFileName));
1809   gSystem->Exec(Form("mv %s/*.root %s", rawDBFS[0], rootFileName));
1810
1811   gSystem->Exec(Form("rm -rf %s",rawDBFS[0]));
1812   gSystem->Exec(Form("rm -rf %s",rawDBFS[1]));
1813   gSystem->Exec(Form("rm -rf %s",tagDBFS));
1814
1815   return (result == 0);
1816 }
1817
1818
1819 //_____________________________________________________________________________
1820 AliRunLoader* AliSimulation::LoadRun(const char* mode) const
1821 {
1822 // delete existing run loaders, open a new one and load gAlice
1823
1824   delete AliRunLoader::Instance();
1825   AliRunLoader* runLoader = 
1826     AliRunLoader::Open(fGAliceFileName.Data(), 
1827                        AliConfig::GetDefaultEventFolderName(), mode);
1828   if (!runLoader) {
1829     AliError(Form("no run loader found in file %s", fGAliceFileName.Data()));
1830     return NULL;
1831   }
1832   runLoader->LoadgAlice();
1833   runLoader->LoadHeader();
1834   gAlice = runLoader->GetAliRun();
1835   if (!gAlice) {
1836     AliError(Form("no gAlice object found in file %s", 
1837                   fGAliceFileName.Data()));
1838     return NULL;
1839   }
1840   return runLoader;
1841 }
1842
1843 //_____________________________________________________________________________
1844 Int_t AliSimulation::GetNSignalPerBkgrd(Int_t nEvents) const
1845 {
1846 // get or calculate the number of signal events per background event
1847
1848   if (!fBkgrdFileNames) return 1;
1849   Int_t nBkgrdFiles = fBkgrdFileNames->GetEntriesFast();
1850   if (nBkgrdFiles == 0) return 1;
1851
1852   // get the number of signal events
1853   if (nEvents <= 0) {
1854     AliRunLoader* runLoader = 
1855         AliRunLoader::Open(fGAliceFileName.Data(), "SIGNAL");
1856     if (!runLoader) return 1;
1857     
1858     nEvents = runLoader->GetNumberOfEvents();
1859     delete runLoader;
1860   }
1861
1862   Int_t result = 0;
1863   for (Int_t iBkgrdFile = 0; iBkgrdFile < nBkgrdFiles; iBkgrdFile++) {
1864     // get the number of background events
1865     const char* fileName = ((TObjString*)
1866                             (fBkgrdFileNames->At(iBkgrdFile)))->GetName();
1867     AliRunLoader* runLoader =
1868       AliRunLoader::Open(fileName, "BKGRD");
1869     if (!runLoader) continue;
1870     Int_t nBkgrdEvents = runLoader->GetNumberOfEvents();
1871     delete runLoader;
1872   
1873     // get or calculate the number of signal per background events
1874     Int_t nSignalPerBkgrd = fBkgrdFileNames->At(iBkgrdFile)->GetUniqueID();
1875     if (nSignalPerBkgrd <= 0) {
1876       nSignalPerBkgrd = (nEvents-1) / nBkgrdEvents + 1;
1877     } else if (result && (result != nSignalPerBkgrd)) {
1878       AliInfo(Form("the number of signal events per background event "
1879                    "will be changed from %d to %d for stream %d", 
1880                    nSignalPerBkgrd, result, iBkgrdFile+1));
1881       nSignalPerBkgrd = result;
1882     }
1883
1884     if (!result) result = nSignalPerBkgrd;
1885     if (nSignalPerBkgrd * nBkgrdEvents < nEvents) {
1886       AliWarning(Form("not enough background events (%d) for %d signal events "
1887                       "using %d signal per background events for stream %d",
1888                       nBkgrdEvents, nEvents, nSignalPerBkgrd, iBkgrdFile+1));
1889     }
1890   }
1891
1892   return result;
1893 }
1894
1895 //_____________________________________________________________________________
1896 Bool_t AliSimulation::IsSelected(TString detName, TString& detectors) const
1897 {
1898 // check whether detName is contained in detectors
1899 // if yes, it is removed from detectors
1900
1901   // check if all detectors are selected
1902   if ((detectors.CompareTo("ALL") == 0) ||
1903       detectors.BeginsWith("ALL ") ||
1904       detectors.EndsWith(" ALL") ||
1905       detectors.Contains(" ALL ")) {
1906     detectors = "ALL";
1907     return kTRUE;
1908   }
1909
1910   // search for the given detector
1911   Bool_t result = kFALSE;
1912   if ((detectors.CompareTo(detName) == 0) ||
1913       detectors.BeginsWith(detName+" ") ||
1914       detectors.EndsWith(" "+detName) ||
1915       detectors.Contains(" "+detName+" ")) {
1916     detectors.ReplaceAll(detName, "");
1917     result = kTRUE;
1918   }
1919
1920   // clean up the detectors string
1921   while (detectors.Contains("  ")) detectors.ReplaceAll("  ", " ");
1922   while (detectors.BeginsWith(" ")) detectors.Remove(0, 1);
1923   while (detectors.EndsWith(" ")) detectors.Remove(detectors.Length()-1, 1);
1924
1925   return result;
1926 }
1927
1928 //_____________________________________________________________________________
1929 Int_t AliSimulation::ConvertRaw2SDigits(const char* rawDirectory, const char* esdFileName, Int_t N, Int_t nSkip)
1930 {
1931 //
1932 // Steering routine  to convert raw data in directory rawDirectory/ to fake SDigits. 
1933 // These can be used for embedding of MC tracks into RAW data using the standard 
1934 // merging procedure.
1935 //
1936 // If an ESD file is given the reconstructed vertex is taken from it and stored in the event header.
1937 //
1938   if (!gAlice) {
1939     AliError("no gAlice object. Restart aliroot and try again.");
1940     return kFALSE;
1941   }
1942   if (gAlice->Modules()->GetEntries() > 0) {
1943     AliError("gAlice was already run. Restart aliroot and try again.");
1944     return kFALSE;
1945   }
1946   
1947   AliInfo(Form("initializing gAlice with config file %s",fConfigFileName.Data()));
1948   
1949   gAlice->Announce();
1950   
1951   gROOT->LoadMacro(fConfigFileName.Data());
1952   gInterpreter->ProcessLine(gAlice->GetConfigFunction());
1953   
1954   if(AliCDBManager::Instance()->GetRun() >= 0) { 
1955         SetRunNumber(AliCDBManager::Instance()->GetRun());
1956   } else {
1957         AliWarning("Run number not initialized!!");
1958   }
1959   
1960    AliRunLoader::Instance()->CdGAFile();
1961     
1962    AliPDG::AddParticlesToPdgDataBase();  
1963
1964    TVirtualMC::GetMC()->SetMagField(TGeoGlobalMagField::Instance()->GetField());
1965    
1966    gAlice->GetMCApp()->Init();
1967
1968    //Must be here because some MCs (G4) adds detectors here and not in Config.C
1969    gAlice->InitLoaders();
1970    AliRunLoader::Instance()->MakeTree("E");
1971    AliRunLoader::Instance()->LoadKinematics("RECREATE");
1972    AliRunLoader::Instance()->LoadTrackRefs("RECREATE");
1973    AliRunLoader::Instance()->LoadHits("all","RECREATE");
1974
1975    //
1976    // Save stuff at the beginning of the file to avoid file corruption
1977    AliRunLoader::Instance()->CdGAFile();
1978    gAlice->Write();
1979 //
1980 //  Initialize CDB     
1981     InitCDB();
1982     //AliCDBManager* man = AliCDBManager::Instance();
1983     //man->SetRun(0); // Should this come from rawdata header ?
1984     
1985     Int_t iDet;
1986     //
1987     // Get the runloader
1988     AliRunLoader* runLoader = AliRunLoader::Instance();
1989     //
1990     // Open esd file if available
1991     TFile* esdFile = 0;
1992     TTree* treeESD = 0;
1993     AliESDEvent* esd = 0;
1994     if (esdFileName && (strlen(esdFileName)>0)) {
1995       esdFile = TFile::Open(esdFileName);
1996       if (esdFile) {
1997         esd = new AliESDEvent();
1998         esdFile->GetObject("esdTree", treeESD);
1999                   if (treeESD) {
2000                           esd->ReadFromTree(treeESD);
2001                           if (nSkip>0) {
2002                                   AliInfo(Form("Asking to skip first %d ESDs events",nSkip));
2003                           } else {
2004                                   nSkip=0;
2005                           }
2006                   }
2007       }
2008     }
2009
2010     //
2011     // Create the RawReader
2012     TString fileName(rawDirectory);
2013     AliRawReader* rawReader = AliRawReader::Create(fileName.Data());
2014     if (!rawReader) return (kFALSE);
2015     
2016 //     if (!fEquipIdMap.IsNull() && fRawReader)
2017 //       fRawReader->LoadEquipmentIdsMap(fEquipIdMap);
2018     //
2019     // Get list of detectors
2020     TObjArray* detArray = runLoader->GetAliRun()->Detectors();
2021     //
2022     // Get Header
2023     AliHeader* header = runLoader->GetHeader();
2024     // Event loop
2025     Int_t nev = 0;
2026     while(kTRUE) {
2027         if (!(rawReader->NextEvent())) break;
2028         runLoader->SetEventNumber(nev);
2029         runLoader->GetHeader()->Reset(rawReader->GetRunNumber(), 
2030                                       nev, nev);
2031         runLoader->GetEvent(nev);
2032         AliInfo(Form("We are at event %d",nev));
2033         //
2034         // Detector loop
2035         TString detStr = fMakeSDigits;
2036         for (iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
2037             AliModule* det = (AliModule*) detArray->At(iDet);
2038             if (!det || !det->IsActive()) continue;
2039             if (IsSelected(det->GetName(), detStr)) {
2040               AliInfo(Form("Calling Raw2SDigits for %s", det->GetName()));
2041               det->Raw2SDigits(rawReader);
2042               rawReader->Reset();
2043             }
2044         } // detectors
2045         
2046
2047         //
2048         //  If ESD information available obtain reconstructed vertex and store in header.
2049         if (treeESD) {
2050                 AliInfo(Form("Selected event %d correspond to event %d in raw and to %d in esd",nev,rawReader->GetEventIndex(),nSkip+rawReader->GetEventIndex()));
2051             treeESD->GetEvent(nSkip+rawReader->GetEventIndex());
2052             const AliESDVertex* esdVertex = esd->GetPrimaryVertex();
2053             Double_t position[3];
2054             esdVertex->GetXYZ(position);
2055             AliGenEventHeader* mcHeader = new  AliGenEventHeader("ESD");
2056             TArrayF mcV;
2057             mcV.Set(3);
2058             for (Int_t i = 0; i < 3; i++) mcV[i] = position[i];
2059             mcHeader->SetPrimaryVertex(mcV);
2060             header->Reset(0,nev);
2061             header->SetGenEventHeader(mcHeader);
2062             AliInfo(Form("***** Saved vertex %f %f %f \n", position[0], position[1], position[2]));
2063         }
2064 //
2065 //      Finish the event
2066         runLoader->TreeE()->Fill();
2067         AliInfo(Form("Finished event %d",nev));
2068         nev++;
2069         if (N>0&&nev>=N)
2070           break;
2071     } // events
2072  
2073     delete rawReader;
2074 //
2075 //  Finish the run 
2076     runLoader->CdGAFile();
2077     runLoader->WriteHeader("OVERWRITE");
2078     runLoader->WriteRunLoader();
2079
2080     return nev;
2081 }
2082
2083 //_____________________________________________________________________________
2084 void AliSimulation::FinishRun()
2085 {
2086   //
2087   // Called at the end of the run.
2088   //
2089
2090   if(IsLegoRun()) 
2091    {
2092     AliDebug(1, "Finish Lego");
2093     AliRunLoader::Instance()->CdGAFile();
2094     fLego->FinishRun();
2095    }
2096   
2097   // Clean detector information
2098   TIter next(gAlice->Modules());
2099   AliModule *detector;
2100   while((detector = dynamic_cast<AliModule*>(next()))) {
2101     AliDebug(2, Form("%s->FinishRun()", detector->GetName()));
2102     detector->FinishRun();
2103   }
2104   
2105   AliDebug(1, "AliRunLoader::Instance()->WriteHeader(OVERWRITE)");
2106   AliRunLoader::Instance()->WriteHeader("OVERWRITE");
2107
2108   // Write AliRun info and all detectors parameters
2109   AliRunLoader::Instance()->CdGAFile();
2110   gAlice->Write(0,TObject::kOverwrite);//write AliRun
2111   AliRunLoader::Instance()->Write(0,TObject::kOverwrite);//write RunLoader itself
2112   //
2113   if(gAlice->GetMCApp()) gAlice->GetMCApp()->FinishRun();  
2114   AliRunLoader::Instance()->Synchronize();
2115 }
2116
2117 //_____________________________________________________________________________
2118 Int_t AliSimulation::GetDetIndex(const char* detector)
2119 {
2120   // return the detector index corresponding to detector
2121   Int_t index = -1 ; 
2122   for (index = 0; index < fgkNDetectors ; index++) {
2123     if ( strcmp(detector, fgkDetectorName[index]) == 0 )
2124           break ; 
2125   }     
2126   return index ; 
2127 }
2128
2129 //_____________________________________________________________________________
2130 Bool_t AliSimulation::CreateHLT()
2131 {
2132   // Init the HLT simulation.
2133   // The function  loads the library and creates the instance of AliHLTSimulation.
2134   // the main reason for the decoupled creation is to set the transient OCDB
2135   // objects before the OCDB is locked
2136
2137   // load the library dynamically
2138   gSystem->Load(ALIHLTSIMULATION_LIBRARY);
2139
2140   // check for the library version
2141   AliHLTSimulationGetLibraryVersion_t fctVersion=(AliHLTSimulationGetLibraryVersion_t)(gSystem->DynFindSymbol(ALIHLTSIMULATION_LIBRARY, ALIHLTSIMULATION_GET_LIBRARY_VERSION));
2142   if (!fctVersion) {
2143     AliError(Form("can not load library %s", ALIHLTSIMULATION_LIBRARY));
2144     return kFALSE;
2145   }
2146   if (fctVersion()!= ALIHLTSIMULATION_LIBRARY_VERSION) {
2147     AliWarning(Form("%s version does not match: compiled for version %d, loaded %d", ALIHLTSIMULATION_LIBRARY, ALIHLTSIMULATION_LIBRARY_VERSION, fctVersion()));
2148   }
2149
2150   // print compile info
2151   typedef void (*CompileInfo)( const char*& date, const char*& time);
2152   CompileInfo fctInfo=(CompileInfo)gSystem->DynFindSymbol(ALIHLTSIMULATION_LIBRARY, "CompileInfo");
2153   if (fctInfo) {
2154     const char* date="";
2155     const char* time="";
2156     (*fctInfo)(date, time);
2157     if (!date) date="unknown";
2158     if (!time) time="unknown";
2159     AliInfo(Form("%s build on %s (%s)", ALIHLTSIMULATION_LIBRARY, date, time));
2160   } else {
2161     AliInfo(Form("no build info available for %s", ALIHLTSIMULATION_LIBRARY));
2162   }
2163
2164   // create instance of the HLT simulation
2165   AliHLTSimulationCreateInstance_t fctCreate=(AliHLTSimulationCreateInstance_t)(gSystem->DynFindSymbol(ALIHLTSIMULATION_LIBRARY, ALIHLTSIMULATION_CREATE_INSTANCE));
2166   if (fctCreate==NULL || (fpHLT=(fctCreate()))==NULL) {
2167     AliError(Form("can not create instance of HLT simulation (creator %p)", fctCreate));
2168     return kFALSE;    
2169   }
2170
2171   TString specObjects;
2172   for (Int_t i = 0; i < fSpecCDBUri.GetEntriesFast(); i++) {
2173     if (specObjects.Length()>0) specObjects+=" ";
2174     specObjects+=fSpecCDBUri[i]->GetName();
2175   }
2176
2177   AliHLTSimulationSetup_t fctSetup=(AliHLTSimulationSetup_t)(gSystem->DynFindSymbol(ALIHLTSIMULATION_LIBRARY, ALIHLTSIMULATION_SETUP));
2178   if (fctSetup==NULL || fctSetup(fpHLT, this, specObjects.Data())<0) {
2179     AliWarning(Form("failed to setup HLT simulation (function %p)", fctSetup));
2180   }
2181
2182   return kTRUE;
2183 }
2184
2185 //_____________________________________________________________________________
2186 Bool_t AliSimulation::RunHLT()
2187 {
2188   // Run the HLT simulation
2189   // HLT simulation is implemented in HLT/sim/AliHLTSimulation
2190   // Disabled if fRunHLT is empty, default vaule is "default".
2191   // AliSimulation::SetRunHLT can be used to set the options for HLT simulation
2192   // The default simulation depends on the HLT component libraries and their
2193   // corresponding agents which define components and chains to run. See
2194   // http://web.ift.uib.no/~kjeks/doc/alice-hlt-current/
2195   // http://web.ift.uib.no/~kjeks/doc/alice-hlt-current/classAliHLTModuleAgent.html
2196   //
2197   // The libraries to be loaded can be specified as an option.
2198   // <pre>
2199   // AliSimulation sim;
2200   // sim.SetRunHLT("libAliHLTSample.so");
2201   // </pre>
2202   // will only load <tt>libAliHLTSample.so</tt>
2203
2204   // Other available options:
2205   // \li loglevel=<i>level</i> <br>
2206   //     logging level for this processing
2207   // \li alilog=off
2208   //     disable redirection of log messages to AliLog class
2209   // \li config=<i>macro</i>
2210   //     configuration macro
2211   // \li chains=<i>configuration</i>
2212   //     comma separated list of configurations to be run during simulation
2213   // \li rawfile=<i>file</i>
2214   //     source for the RawReader to be created, the default is <i>./</i> if
2215   //     raw data is simulated
2216
2217   int iResult=0;
2218
2219   if (!fpHLT && !CreateHLT()) {
2220     return kFALSE;
2221   }
2222   AliHLTSimulation* pHLT=fpHLT;
2223
2224   AliRunLoader* pRunLoader = LoadRun("READ");
2225   if (!pRunLoader) return kFALSE;
2226
2227   // initialize CDB storage, run number, set CDB lock
2228   // thats for the case of running HLT simulation without all the other steps
2229   // multiple calls are handled by the function, so we can just call
2230   InitCDB();
2231   if (!SetRunNumberFromData()) if (fStopOnError) return kFALSE;
2232   SetCDBLock();
2233   
2234   // init the HLT simulation
2235   TString options;
2236   if (fRunHLT.CompareTo("default")!=0) options=fRunHLT;
2237   TString detStr = fWriteRawData;
2238   if (!IsSelected("HLT", detStr)) {
2239     options+=" writerawfiles=";
2240   } else {
2241     options+=" writerawfiles=HLT";
2242   }
2243
2244   if (!detStr.IsNull() && !options.Contains("rawfile=")) {
2245     // as a matter of fact, HLT will run reconstruction and needs the RawReader
2246     // in order to get detector data. By default, RawReaderFile is used to read
2247     // the already simulated ddl files. Date and Root files from the raw data
2248     // are generated after the HLT simulation.
2249     options+=" rawfile=./";
2250   }
2251
2252   AliHLTSimulationInit_t fctInit=(AliHLTSimulationInit_t)(gSystem->DynFindSymbol(ALIHLTSIMULATION_LIBRARY, ALIHLTSIMULATION_INIT));
2253   if (fctInit==NULL || (iResult=(fctInit(pHLT, pRunLoader, options.Data())))<0) {
2254     AliError(Form("can not init HLT simulation: error %d (init %p)", iResult, fctInit));
2255   } else {
2256     // run the HLT simulation
2257     AliHLTSimulationRun_t fctRun=(AliHLTSimulationRun_t)(gSystem->DynFindSymbol(ALIHLTSIMULATION_LIBRARY, ALIHLTSIMULATION_RUN));
2258     if (fctRun==NULL || (iResult=(fctRun(pHLT, pRunLoader)))<0) {
2259       AliError(Form("can not run HLT simulation: error %d (run %p)", iResult, fctRun));
2260     }
2261   }
2262
2263   // delete the instance
2264   AliHLTSimulationDeleteInstance_t fctDelete=(AliHLTSimulationDeleteInstance_t)(gSystem->DynFindSymbol(ALIHLTSIMULATION_LIBRARY, ALIHLTSIMULATION_DELETE_INSTANCE));
2265   if (fctDelete==NULL || fctDelete(pHLT)<0) {
2266     AliError(Form("can not delete instance of HLT simulation (creator %p)", fctDelete));
2267   }
2268   pHLT=NULL;
2269
2270   return iResult>=0?kTRUE:kFALSE;
2271 }
2272
2273 //_____________________________________________________________________________
2274 Bool_t AliSimulation::RunQA()
2275 {
2276         // run the QA on summable hits, digits or digits
2277         
2278     //if(!gAlice) return kFALSE;
2279         AliQAManager::QAManager()->SetRunLoader(AliRunLoader::Instance()) ;
2280
2281         TString detectorsw("") ;  
2282         Bool_t rv = kTRUE ; 
2283   AliQAManager::QAManager()->SetEventSpecie(fEventSpecie) ;
2284         detectorsw = AliQAManager::QAManager()->Run(fQADetectors.Data()) ; 
2285         if ( detectorsw.IsNull() ) 
2286                 rv = kFALSE ; 
2287         return rv ; 
2288 }
2289
2290 //_____________________________________________________________________________
2291 Bool_t AliSimulation::SetRunQA(TString detAndAction) 
2292 {
2293         // Allows to run QA for a selected set of detectors
2294         // and a selected set of tasks among HITS, SDIGITS and DIGITS
2295         // all selected detectors run the same selected tasks
2296         
2297         if (!detAndAction.Contains(":")) {
2298                 AliError( Form("%s is a wrong syntax, use \"DetectorList:ActionList\" \n", detAndAction.Data()) ) ;
2299                 fRunQA = kFALSE ;
2300                 return kFALSE ;                 
2301         }
2302         Int_t colon = detAndAction.Index(":") ; 
2303         fQADetectors = detAndAction(0, colon) ; 
2304         if (fQADetectors.Contains("ALL") ){
2305     TString tmp = Form("%s %s", fMakeDigits.Data(), fMakeDigitsFromHits.Data()) ; 
2306     Int_t minus = fQADetectors.Last('-') ; 
2307     TString toKeep = Form("%s %s", fMakeDigits.Data(), fMakeDigitsFromHits.Data()) ; 
2308     TString toRemove("") ;
2309     while (minus >= 0) {
2310       toRemove = fQADetectors(minus+1, fQADetectors.Length()) ; 
2311       toRemove = toRemove.Strip() ; 
2312       toKeep.ReplaceAll(toRemove, "") ; 
2313       fQADetectors.ReplaceAll(Form("-%s", toRemove.Data()), "") ; 
2314       minus = fQADetectors.Last('-') ; 
2315     }
2316     fQADetectors = toKeep ; 
2317   }
2318   fQATasks   = detAndAction(colon+1, detAndAction.Sizeof() ) ; 
2319         if (fQATasks.Contains("ALL") ) {
2320                 fQATasks = Form("%d %d %d", AliQAv1::kHITS, AliQAv1::kSDIGITS, AliQAv1::kDIGITS) ; 
2321         } else {
2322                 fQATasks.ToUpper() ; 
2323                 TString tempo("") ; 
2324                 if ( fQATasks.Contains("HIT") ) 
2325                         tempo = Form("%d ", AliQAv1::kHITS) ; 
2326                 if ( fQATasks.Contains("SDIGIT") ) 
2327                         tempo += Form("%d ", AliQAv1::kSDIGITS) ; 
2328                 if ( fQATasks.Contains("DIGIT") ) 
2329                         tempo += Form("%d ", AliQAv1::kDIGITS) ; 
2330                 fQATasks = tempo ; 
2331                 if (fQATasks.IsNull()) {
2332                         AliInfo("No QA requested\n")  ;
2333                         fRunQA = kFALSE ;
2334                         return kTRUE ; 
2335                 }
2336         }       
2337         TString tempo(fQATasks) ; 
2338     tempo.ReplaceAll(Form("%d", AliQAv1::kHITS), AliQAv1::GetTaskName(AliQAv1::kHITS))  ;
2339     tempo.ReplaceAll(Form("%d", AliQAv1::kSDIGITS), AliQAv1::GetTaskName(AliQAv1::kSDIGITS)) ;  
2340     tempo.ReplaceAll(Form("%d", AliQAv1::kDIGITS), AliQAv1::GetTaskName(AliQAv1::kDIGITS)) ;    
2341         AliInfo( Form("QA will be done on \"%s\" for \"%s\"\n", fQADetectors.Data(), tempo.Data()) ) ;  
2342         fRunQA = kTRUE ;
2343         AliQAManager::QAManager()->SetActiveDetectors(fQADetectors) ; 
2344         AliQAManager::QAManager()->SetTasks(fQATasks) ; 
2345   for (Int_t det = 0 ; det < AliQAv1::kNDET ; det++) 
2346     AliQAManager::QAManager()->SetWriteExpert(AliQAv1::DETECTORINDEX_t(det)) ;
2347   
2348         return kTRUE; 
2349
2350
2351 //_____________________________________________________________________________
2352 void AliSimulation::ProcessEnvironmentVars()
2353 {
2354 // Extract run number and random generator seed from env variables
2355
2356     AliInfo("Processing environment variables");
2357     
2358     // Random Number seed
2359     
2360     // first check that seed is not already set
2361     if (fSeed == 0) {
2362         if (gSystem->Getenv("CONFIG_SEED")) {
2363                 fSeed = atoi(gSystem->Getenv("CONFIG_SEED"));
2364         }
2365     } else {
2366         if (gSystem->Getenv("CONFIG_SEED")) {
2367                 AliInfo(Form("Seed for random number generation already set (%d)"
2368                              ": CONFIG_SEED variable ignored!", fSeed));
2369         }
2370     }
2371    
2372     AliInfo(Form("Seed for random number generation = %d ", fSeed)); 
2373
2374     // Run Number
2375     
2376     // first check that run number is not already set
2377     if(fRun < 0) {    
2378         if (gSystem->Getenv("DC_RUN")) {
2379                 fRun = atoi(gSystem->Getenv("DC_RUN"));
2380         }
2381     } else {
2382         if (gSystem->Getenv("DC_RUN")) {
2383                 AliInfo(Form("Run number already set (%d): DC_RUN variable ignored!", fRun));
2384         }
2385     }
2386     
2387     AliInfo(Form("Run number = %d", fRun)); 
2388 }
2389
2390 //---------------------------------------------------------------------
2391 void AliSimulation::WriteGRPEntry()
2392 {
2393   // Get the necessary information from galice (generator, trigger etc) and
2394   // write a GRP entry corresponding to the settings in the Config.C used
2395   // note that Hall probes and Cavern and Surface Atmos pressures are not simulated.
2396
2397
2398   AliInfo("Writing global run parameters entry into the OCDB");
2399
2400   AliGRPObject* grpObj = new AliGRPObject();
2401
2402   grpObj->SetRunType("PHYSICS");
2403   grpObj->SetTimeStart(fTimeStart);
2404   grpObj->SetTimeEnd(fTimeEnd); 
2405   grpObj->SetBeamEnergyIsSqrtSHalfGeV(); // new format of GRP: store sqrt(s)/2 in GeV
2406
2407   const AliGenerator *gen = gAlice->GetMCApp()->Generator();
2408   Int_t a = 0;
2409   Int_t z = 0;
2410
2411   if (gen) {
2412     TString projectile;
2413     gen->GetProjectile(projectile,a,z);
2414     TString target;
2415     gen->GetTarget(target,a,z);
2416     TString beamType = projectile + "-" + target;
2417     beamType.ReplaceAll(" ","");
2418     if (!beamType.CompareTo("-")) {
2419       grpObj->SetBeamType("UNKNOWN");
2420       grpObj->SetBeamEnergy(gen->GetEnergyCMS()/2);
2421     }
2422     else {
2423       grpObj->SetBeamType(beamType);
2424       if (z != 0) {
2425           grpObj->SetBeamEnergy(gen->GetEnergyCMS()/2 * a / z);
2426       } else {
2427           grpObj->SetBeamEnergy(gen->GetEnergyCMS()/2 );
2428       }
2429       // Heavy ion run, the event specie is set to kHighMult
2430       fEventSpecie = AliRecoParam::kHighMult;
2431       if ((strcmp(beamType,"p-p") == 0) ||
2432           (strcmp(beamType,"p-")  == 0) ||
2433           (strcmp(beamType,"-p")  == 0) ||
2434           (strcmp(beamType,"P-P") == 0) ||
2435           (strcmp(beamType,"P-")  == 0) ||
2436           (strcmp(beamType,"-P")  == 0)) {
2437         // Proton run, the event specie is set to kLowMult
2438         fEventSpecie = AliRecoParam::kLowMult;
2439       } 
2440     }
2441   } else {
2442     AliWarning("Unknown beam type and energy! Setting energy to 0");
2443     grpObj->SetBeamEnergy(0);
2444     grpObj->SetBeamType("UNKNOWN");
2445   }
2446
2447   UInt_t detectorPattern  = 0;
2448   Int_t nDets = 0;
2449   TObjArray *detArray = gAlice->Detectors();
2450   for (Int_t iDet = 0; iDet < AliDAQ::kNDetectors-1; iDet++) {
2451     if (detArray->FindObject(AliDAQ::OfflineModuleName(iDet))) {
2452       AliDebug(1, Form("Detector #%d found: %s", iDet, AliDAQ::OfflineModuleName(iDet)));
2453       detectorPattern |= (1 << iDet);
2454       nDets++;
2455     }
2456   }
2457   // CTP
2458   if (!fTriggerConfig.IsNull())
2459     detectorPattern |= (1 << AliDAQ::DetectorID("TRG"));
2460
2461   // HLT
2462   if (!fRunHLT.IsNull())
2463     detectorPattern |= (1 << AliDAQ::kHLTId);
2464
2465   grpObj->SetNumberOfDetectors((Char_t)nDets);
2466   grpObj->SetDetectorMask((Int_t)detectorPattern);
2467   grpObj->SetLHCPeriod("LHC08c");
2468   grpObj->SetLHCState("STABLE_BEAMS");
2469   //
2470   AliMagF *field = (AliMagF*)TGeoGlobalMagField::Instance()->GetField();
2471   Float_t solenoidField = field ? TMath::Abs(field->SolenoidField()) : 0;
2472
2473   Float_t factorSol     = field ? field->GetFactorSol() : 0;
2474   Float_t currentSol    = TMath::Abs(factorSol)>1E-6 ? 
2475     TMath::Nint(TMath::Abs(solenoidField/factorSol))/5.*30000.*TMath::Abs(factorSol) : 0;
2476   //
2477   Float_t factorDip     = field ? field->GetFactorDip() : 0;
2478   Float_t currentDip    = 6000.*TMath::Abs(factorDip);
2479   //
2480   grpObj->SetL3Current(currentSol,(AliGRPObject::Stats)0);
2481   grpObj->SetDipoleCurrent(currentDip,(AliGRPObject::Stats)0);  
2482   grpObj->SetL3Polarity(factorSol>0 ? 0:1);  
2483   grpObj->SetDipolePolarity(factorDip>0 ? 0:1);
2484   if (field) grpObj->SetUniformBMap(field->IsUniform()); // for special MC with k5kGUniform map
2485   grpObj->SetPolarityConventionLHC();                    // LHC convention +/+ current -> -/- field main components
2486   //
2487   grpObj->SetCavernTemperature(0,(AliGRPObject::Stats)0);
2488   
2489   //grpMap->Add(new TObjString("fCavernPressure"),new TObjString("0")); ---> not inserted in simulation with the new object, since it is now an AliDCSSensor
2490
2491   // Now store the entry in OCDB
2492   AliCDBManager* man = AliCDBManager::Instance();
2493   
2494   man->SetLock(0, fKey);
2495   
2496   AliCDBStorage* sto = man->GetStorage(fGRPWriteLocation.Data());
2497   
2498
2499   AliCDBId id("GRP/GRP/Data", man->GetRun(), man->GetRun(), 1, 1);
2500   AliCDBMetaData *metadata= new AliCDBMetaData();
2501
2502   metadata->SetResponsible("alice-off@cern.ch");
2503   metadata->SetComment("Automatically produced GRP entry for Monte Carlo");
2504  
2505   sto->Put(grpObj,id,metadata);
2506   man->SetLock(1, fKey);
2507 }
2508
2509 //_____________________________________________________________________________
2510 time_t AliSimulation::GenerateTimeStamp() const
2511 {
2512   // Generate event time-stamp according to
2513   // SOR/EOR time from GRP
2514   if (fUseTimeStampFromCDB)
2515     return fTimeStart + gRandom->Integer(fTimeEnd-fTimeStart);
2516   else
2517     return 0;
2518 }
2519
2520 //_____________________________________________________________________________
2521 void AliSimulation::StoreUsedCDBMaps() const
2522 {
2523   // write in galice.root maps with used CDB paths
2524   //
2525   //
2526   AliRunLoader* runLoader = LoadRun();
2527   if (!runLoader) {
2528     AliError("Failed to open gAlice.root in write mode");
2529     return;
2530   }
2531   //
2532   const TMap *cdbMap = AliCDBManager::Instance()->GetStorageMap();       
2533   const TList *cdbList = AliCDBManager::Instance()->GetRetrievedIds();   
2534   //
2535   TMap *cdbMapCopy = new TMap(cdbMap->GetEntries());     
2536   cdbMapCopy->SetOwner(1);       
2537   //  cdbMapCopy->SetName("cdbMap");     
2538   TIter iter(cdbMap->GetTable());        
2539   //     
2540   TPair* pair = 0;       
2541   while((pair = dynamic_cast<TPair*> (iter.Next()))){    
2542     TObjString* keyStr = dynamic_cast<TObjString*> (pair->Key());        
2543     TObjString* valStr = dynamic_cast<TObjString*> (pair->Value());
2544     if (keyStr && valStr)
2545       cdbMapCopy->Add(new TObjString(keyStr->GetName()), new TObjString(valStr->GetName()));     
2546   }      
2547   //     
2548   TList *cdbListCopy = new TList();      
2549   cdbListCopy->SetOwner(1);      
2550   //  cdbListCopy->SetName("cdbList");   
2551   //
2552   TIter iter2(cdbList);  
2553   
2554   AliCDBId* id=0;
2555   while((id = dynamic_cast<AliCDBId*> (iter2.Next()))){  
2556     cdbListCopy->Add(new TObjString(id->ToString().Data()));     
2557   }      
2558   //
2559   AliRunLoader::Instance()->CdGAFile();
2560   gDirectory->WriteObject(cdbMapCopy,"cdbMap","kSingleKey");
2561   gDirectory->WriteObject(cdbListCopy,"cdbList","kSingleKey");  
2562   delete runLoader;
2563   //
2564   AliInfo(Form("Stored used OCDB entries as TMap %s and TList %s in %s",
2565                cdbMapCopy->GetName(),
2566                cdbListCopy->GetName(),
2567                fGAliceFileName.Data()));
2568   //
2569 }