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