1 /**************************************************************************
2 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
7 * Permission to use, copy, modify and distribute this software and its *
8 * documentation strictly for non-commercial purposes is hereby granted *
9 * without fee, provided that the above copyright notice appears in all *
10 * copies and that both the copyright notice and this permission notice *
11 * appear in the supporting documentation. The authors make no claims *
12 * about the suitability of this software for any purpose. It is *
13 * provided "as is" without express or implied warranty. *
14 **************************************************************************/
18 ///////////////////////////////////////////////////////////////////////////////
20 // class for running generation, simulation and digitization //
22 // Hits, sdigits and digits are created for all detectors by typing: //
24 // AliSimulation sim; //
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 //
31 // sim.SetNumberOfEvents(n); //
33 // The name of the configuration file can be passed as argument to the //
34 // AliSimulation constructor or can be specified by //
36 // sim.SetConfigFile("..."); //
38 // The generation of particles and the simulation of detector hits can be //
39 // switched on or off by //
41 // sim.SetRunGeneration(kTRUE); // generation of primary particles //
42 // sim.SetRunSimulation(kFALSE); // but no tracking //
44 // For which detectors sdigits and digits will be created, can be steered //
47 // sim.SetMakeSDigits("ALL"); // make sdigits for all detectors //
48 // sim.SetMakeDigits("ITS TPC"); // make digits only for ITS and TPC //
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. //
55 // The creation of digits from hits instead of from sdigits can be selected //
58 // sim.SetMakeDigitsFromHits("TRD"); //
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. //
64 // Background events can be merged by calling //
66 // sim.MergeWith("background/galice.root", 2); //
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. //
75 // The output of raw data can be switched on by calling //
77 // sim.SetWriteRawData("MUON"); // write raw data for MUON //
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 //
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. //
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 //
98 // sim.SetEventsPerFile("PHOS", "Reconstructed Points", 3); //
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. //
106 ///////////////////////////////////////////////////////////////////////////////
108 #include <TGeoManager.h>
109 #include <TObjString.h>
110 #include <TStopwatch.h>
114 #include "AliCDBStorage.h"
115 #include "AliCDBEntry.h"
116 #include "AliCDBManager.h"
117 #include "AliAlignObj.h"
118 #include "AliCentralTrigger.h"
120 #include "AliDigitizer.h"
121 #include "AliGenerator.h"
123 #include "AliModule.h"
125 #include "AliRunDigitizer.h"
126 #include "AliRunLoader.h"
127 #include "AliSimulation.h"
128 #include "AliVertexGenFile.h"
129 #include "AliCentralTrigger.h"
130 #include "AliCTPRawData.h"
131 #include "AliRawReaderFile.h"
133 #include "AliHeader.h"
134 #include "AliGenEventHeader.h"
136 ClassImp(AliSimulation)
139 //_____________________________________________________________________________
140 AliSimulation::AliSimulation(const char* configFileName, const char* cdbUri,
141 const char* name, const char* title) :
144 fRunGeneration(kTRUE),
145 fRunSimulation(kTRUE),
146 fLoadAlignFromCDB(kTRUE),
147 fLoadAlignData("ALL"),
151 fMakeDigitsFromHits(""),
153 fRawDataFileName(""),
154 fDeleteIntermediateFiles(kFALSE),
155 fStopOnError(kFALSE),
158 fConfigFileName(configFileName),
159 fGAliceFileName("galice.root"),
161 fBkgrdFileNames(NULL),
162 fAlignObjArray(NULL),
163 fUseBkgrdVertex(kTRUE),
164 fRegionOfInterest(kFALSE),
167 fEmbeddingFlag(kFALSE)
169 // create simulation object with default parameters
171 SetGAliceFile("galice.root");
174 //_____________________________________________________________________________
175 AliSimulation::AliSimulation(const AliSimulation& sim) :
178 fRunGeneration(sim.fRunGeneration),
179 fRunSimulation(sim.fRunSimulation),
180 fLoadAlignFromCDB(sim.fLoadAlignFromCDB),
181 fLoadAlignData(sim.fLoadAlignData),
182 fMakeSDigits(sim.fMakeSDigits),
183 fMakeDigits(sim.fMakeDigits),
184 fMakeTrigger(sim.fMakeTrigger),
185 fMakeDigitsFromHits(sim.fMakeDigitsFromHits),
186 fWriteRawData(sim.fWriteRawData),
187 fRawDataFileName(""),
188 fDeleteIntermediateFiles(kFALSE),
189 fStopOnError(sim.fStopOnError),
191 fNEvents(sim.fNEvents),
192 fConfigFileName(sim.fConfigFileName),
193 fGAliceFileName(sim.fGAliceFileName),
195 fBkgrdFileNames(NULL),
196 fAlignObjArray(NULL),
197 fUseBkgrdVertex(sim.fUseBkgrdVertex),
198 fRegionOfInterest(sim.fRegionOfInterest),
199 fCDBUri(sim.fCDBUri),
201 fEmbeddingFlag(sim.fEmbeddingFlag)
205 for (Int_t i = 0; i < sim.fEventsPerFile.GetEntriesFast(); i++) {
206 if (!sim.fEventsPerFile[i]) continue;
207 fEventsPerFile.Add(sim.fEventsPerFile[i]->Clone());
210 fBkgrdFileNames = new TObjArray;
211 for (Int_t i = 0; i < sim.fBkgrdFileNames->GetEntriesFast(); i++) {
212 if (!sim.fBkgrdFileNames->At(i)) continue;
213 fBkgrdFileNames->Add(sim.fBkgrdFileNames->At(i)->Clone());
216 for (Int_t i = 0; i < sim.fSpecCDBUri.GetEntriesFast(); i++) {
217 if (sim.fSpecCDBUri[i]) fSpecCDBUri.Add(sim.fSpecCDBUri[i]->Clone());
222 //_____________________________________________________________________________
223 AliSimulation& AliSimulation::operator = (const AliSimulation& sim)
225 // assignment operator
227 this->~AliSimulation();
228 new(this) AliSimulation(sim);
232 //_____________________________________________________________________________
233 AliSimulation::~AliSimulation()
237 fEventsPerFile.Delete();
238 // if(fAlignObjArray) fAlignObjArray->Delete(); // fAlignObjArray->RemoveAll() ???
239 // delete fAlignObjArray; fAlignObjArray=0;
241 if (fBkgrdFileNames) {
242 fBkgrdFileNames->Delete();
243 delete fBkgrdFileNames;
246 fSpecCDBUri.Delete();
250 //_____________________________________________________________________________
251 void AliSimulation::SetNumberOfEvents(Int_t nEvents)
253 // set the number of events for one run
258 //_____________________________________________________________________________
259 void AliSimulation::InitCDBStorage()
261 // activate a default CDB storage
262 // First check if we have any CDB storage set, because it is used
263 // to retrieve the calibration and alignment constants
265 AliCDBManager* man = AliCDBManager::Instance();
266 if (man->IsDefaultStorageSet())
268 AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
269 AliWarning("Default CDB storage has been already set !");
270 AliWarning(Form("Ignoring the default storage declared in AliReconstruction: %s",fCDBUri.Data()));
271 AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
275 AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
276 AliWarning(Form("Default CDB storage is set to: %s",fCDBUri.Data()));
277 AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
278 man->SetDefaultStorage(fCDBUri);
281 // Now activate the detector specific CDB storage locations
282 for (Int_t i = 0; i < fSpecCDBUri.GetEntriesFast(); i++) {
283 TObject* obj = fSpecCDBUri[i];
285 AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
286 AliWarning(Form("Specific CDB storage for %s is set to: %s",obj->GetName(),obj->GetTitle()));
287 AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
288 man->SetSpecificStorage(obj->GetName(),obj->GetTitle());
293 //_____________________________________________________________________________
294 void AliSimulation::SetDefaultStorage(const char* uri) {
295 // Store the desired default CDB storage location
296 // Activate it later within the Run() method
302 //_____________________________________________________________________________
303 void AliSimulation::SetSpecificStorage(const char* detName, const char* uri) {
304 // Store a detector-specific CDB storage location
305 // Activate it later within the Run() method
307 TObject* obj = fSpecCDBUri.FindObject(detName);
308 if (obj) fSpecCDBUri.Remove(obj);
309 fSpecCDBUri.Add(new TNamed(detName, uri));
313 //_____________________________________________________________________________
314 void AliSimulation::SetConfigFile(const char* fileName)
316 // set the name of the config file
318 fConfigFileName = fileName;
321 //_____________________________________________________________________________
322 void AliSimulation::SetGAliceFile(const char* fileName)
324 // set the name of the galice file
325 // the path is converted to an absolute one if it is relative
327 fGAliceFileName = fileName;
328 if (!gSystem->IsAbsoluteFileName(fGAliceFileName)) {
329 char* absFileName = gSystem->ConcatFileName(gSystem->WorkingDirectory(),
331 fGAliceFileName = absFileName;
332 delete[] absFileName;
335 AliDebug(2, Form("galice file name set to %s", fileName));
338 //_____________________________________________________________________________
339 void AliSimulation::SetEventsPerFile(const char* detector, const char* type,
342 // set the number of events per file for the given detector and data type
343 // ("Hits", "Summable Digits", "Digits", "Reconstructed Points" or "Tracks")
345 TNamed* obj = new TNamed(detector, type);
346 obj->SetUniqueID(nEvents);
347 fEventsPerFile.Add(obj);
350 //_____________________________________________________________________________
351 Bool_t AliSimulation::ApplyAlignObjsToGeom(TObjArray* alObjArray)
353 // Read collection of alignment objects (AliAlignObj derived) saved
354 // in the TClonesArray ClArrayName and apply them to the geometry
355 // manager singleton.
358 Int_t nvols = alObjArray->GetEntriesFast();
362 for(Int_t j=0; j<nvols; j++)
364 AliAlignObj* alobj = (AliAlignObj*) alObjArray->UncheckedAt(j);
365 if (alobj->ApplyToGeometry() == kFALSE) flag = kFALSE;
368 if (AliDebugLevelClass() >= 1) {
369 gGeoManager->GetTopNode()->CheckOverlaps(20);
370 TObjArray* ovexlist = gGeoManager->GetListOfOverlaps();
371 if(ovexlist->GetEntriesFast()){
372 AliError("The application of alignment objects to the geometry caused huge overlaps/extrusions!");
380 //_____________________________________________________________________________
381 Bool_t AliSimulation::ApplyAlignObjsToGeom(const char* fileName, const char* clArrayName)
383 // read collection of alignment objects (AliAlignObj derived) saved
384 // in the TClonesArray ClArrayName in the file fileName and apply
385 // them to the TGeo geometry passed as argument
388 TFile* inFile = TFile::Open(fileName,"READ");
389 if (!inFile || !inFile->IsOpen()) {
390 AliErrorClass(Form("Could not open file %s !",fileName));
394 TClonesArray* alObjArray = ((TClonesArray*) inFile->Get(clArrayName));
397 AliErrorClass(Form("Could not get array (%s) from file (%s) !",clArrayName,fileName));
401 return ApplyAlignObjsToGeom(alObjArray);
405 //_____________________________________________________________________________
406 Bool_t AliSimulation::ApplyAlignObjsToGeom(AliCDBParam* param, AliCDBId& Id)
408 // read collection of alignment objects (AliAlignObj derived) saved
409 // in the TClonesArray ClArrayName in the AliCDBEntry identified by
410 // param (to get the AliCDBStorage) and Id; apply the alignment objects
411 // to the TGeo geometry passed as argument
414 AliCDBStorage* storage = AliCDBManager::Instance()->GetStorage(param);
415 AliCDBEntry* entry = storage->Get(Id);
416 TClonesArray* AlObjArray = ((TClonesArray*) entry->GetObject());
418 return ApplyAlignObjsToGeom(AlObjArray);
422 //_____________________________________________________________________________
423 Bool_t AliSimulation::ApplyAlignObjsToGeom(const char* uri, const char* path, Int_t runnum, Int_t version, Int_t sversion)
425 // read collection of alignment objects (AliAlignObj derived) saved
426 // in the TClonesArray ClArrayName in the AliCDBEntry identified by
427 // param (to get the AliCDBStorage) and Id; apply the alignment objects
428 // to the TGeo geometry passed as argument
431 AliCDBParam* param = AliCDBManager::Instance()->CreateParameter(uri);
432 AliCDBId id(path, runnum, runnum, version, sversion);
434 return ApplyAlignObjsToGeom(param, id);
438 //_____________________________________________________________________________
439 Bool_t AliSimulation::ApplyAlignObjsToGeom(const char* detName, Int_t runnum, Int_t version, Int_t sversion)
441 // read collection of alignment objects (AliAlignObj derived) saved
442 // in the TClonesArray ClArrayName in the AliCDBEntry identified by
443 // param (to get the AliCDBStorage) and Id; apply the alignment objects
444 // to the TGeo geometry passed as argument
447 AliCDBPath path(detName,"Align","Data");
448 AliCDBEntry* entry = AliCDBManager::Instance()->Get(path.GetPath(),runnum,version,sversion);
450 if(!entry) return kFALSE;
451 TClonesArray* AlObjArray = ((TClonesArray*) entry->GetObject());
453 return ApplyAlignObjsToGeom(AlObjArray);
456 //_____________________________________________________________________________
457 Bool_t AliSimulation::SetAlignObjArraySingleDet(const char* detName)
459 // Fills array of single detector's alignable objects from CDB
461 AliDebug(2, Form("Loading alignment data for detector: %s",detName));
465 AliCDBPath path(detName,"Align","Data");
467 entry=AliCDBManager::Instance()->Get(path.GetPath());
469 AliDebug(2,Form("Couldn't load alignment data for detector %s",detName));
473 TClonesArray *alignArray = (TClonesArray*) entry->GetObject();
474 alignArray->SetOwner(0);
475 AliDebug(2,Form("Found %d alignment objects for %s",
476 alignArray->GetEntries(),detName));
478 AliAlignObj *alignObj=0;
479 TIter iter(alignArray);
481 // loop over align objects in detector
482 while( ( alignObj=(AliAlignObj *) iter.Next() ) ){
483 fAlignObjArray->Add(alignObj);
485 // delete entry --- Don't delete, it is cached!
487 AliDebug(2, Form("fAlignObjArray entries: %d",fAlignObjArray->GetEntries() ));
492 //_____________________________________________________________________________
493 Bool_t AliSimulation::MisalignGeometry(AliRunLoader *runLoader)
495 // Read the alignment objects from CDB.
496 // Each detector is supposed to have the
497 // alignment objects in DET/Align/Data CDB path.
498 // All the detector objects are then collected,
499 // sorted by geometry level (starting from ALIC) and
500 // then applied to the TGeo geometry.
501 // Finally an overlaps check is performed.
503 Bool_t delRunLoader = kFALSE;
505 runLoader = LoadRun("READ");
506 if (!runLoader) return kFALSE;
507 delRunLoader = kTRUE;
510 // Load alignment data from CDB and fill fAlignObjArray
511 if(fLoadAlignFromCDB){
512 if(!fAlignObjArray) fAlignObjArray = new TObjArray();
514 //fAlignObjArray->RemoveAll();
515 fAlignObjArray->Clear();
516 fAlignObjArray->SetOwner(0);
518 TString detStr = fLoadAlignData;
519 TString dataNotLoaded="";
520 TString dataLoaded="";
522 TObjArray* detArray = runLoader->GetAliRun()->Detectors();
523 for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
524 AliModule* det = (AliModule*) detArray->At(iDet);
526 if (IsSelected(det->GetName(), detStr)) {
527 if(!SetAlignObjArraySingleDet(det->GetName())){
528 dataNotLoaded += det->GetName();
529 dataNotLoaded += " ";
531 dataLoaded += det->GetName();
535 } // end loop over detectors
537 if ((detStr.CompareTo("ALL") == 0)) detStr = "";
538 dataNotLoaded += detStr;
539 AliInfo(Form("Alignment data loaded for: %s",
541 AliInfo(Form("Didn't/couldn't load alignment data for: %s",
542 dataNotLoaded.Data()));
543 } // fLoadAlignFromCDB flag
545 // Check if the array with alignment objects was
546 // provided by the user. If yes, apply the objects
547 // to the present TGeo geometry
548 if (fAlignObjArray) {
549 if (gGeoManager && gGeoManager->IsClosed()) {
550 if (ApplyAlignObjsToGeom(fAlignObjArray) == kFALSE) {
551 AliError("The misalignment of one or more volumes failed!"
552 "Compare the list of simulated detectors and the list of detector alignment data!");
553 if (delRunLoader) delete runLoader;
558 AliError("Can't apply the misalignment! gGeoManager doesn't exist or it is still opened!");
559 if (delRunLoader) delete runLoader;
565 // Update the internal geometry of modules (ITS needs it)
566 TString detStr = fLoadAlignData;
567 TObjArray* detArray = runLoader->GetAliRun()->Detectors();
568 for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
570 AliModule* det = (AliModule*) detArray->At(iDet);
571 if (!det || !det->IsActive()) continue;
572 if (IsSelected(det->GetName(), detStr)) {
573 det->UpdateInternalGeometry();
575 } // end loop over detectors
578 if (delRunLoader) delete runLoader;
584 //_____________________________________________________________________________
585 Bool_t AliSimulation::SetRunNumber()
587 // Set the CDB manager run number
588 // The run number is retrieved from gAlice
590 if(AliCDBManager::Instance()->GetRun() < 0) {
591 AliRunLoader* runLoader = LoadRun("READ");
592 if (!runLoader) return kFALSE;
594 AliCDBManager::Instance()->SetRun(runLoader->GetAliRun()->GetRunNumber());
595 AliInfo(Form("Run number: %d",AliCDBManager::Instance()->GetRun()));
602 //_____________________________________________________________________________
603 void AliSimulation::MergeWith(const char* fileName, Int_t nSignalPerBkgrd)
605 // add a file with background events for merging
607 TObjString* fileNameStr = new TObjString(fileName);
608 fileNameStr->SetUniqueID(nSignalPerBkgrd);
609 if (!fBkgrdFileNames) fBkgrdFileNames = new TObjArray;
610 fBkgrdFileNames->Add(fileNameStr);
613 void AliSimulation::EmbedInto(const char* fileName, Int_t nSignalPerBkgrd)
615 // add a file with background events for embeddin
616 MergeWith(fileName, nSignalPerBkgrd);
617 fEmbeddingFlag = kTRUE;
620 //_____________________________________________________________________________
621 Bool_t AliSimulation::Run(Int_t nEvents)
623 // run the generation, simulation and digitization
627 if (nEvents > 0) fNEvents = nEvents;
629 // generation and simulation -> hits
630 if (fRunGeneration) {
631 if (!RunSimulation()) if (fStopOnError) return kFALSE;
634 // Set run number in CDBManager (if it is not already set in RunSimulation)
635 if (!SetRunNumber()) if (fStopOnError) return kFALSE;
637 // Load and misalign the geometry
639 TGeoManager::Import("geometry.root");
640 if (!gGeoManager) if (fStopOnError) return kFALSE;
641 if (!MisalignGeometry()) if (fStopOnError) return kFALSE;
644 // hits -> summable digits
645 if (!fMakeSDigits.IsNull()) {
646 if (!RunSDigitization(fMakeSDigits)) if (fStopOnError) return kFALSE;
649 // summable digits -> digits
650 if (!fMakeDigits.IsNull()) {
651 if (!RunDigitization(fMakeDigits, fMakeDigitsFromHits)) {
652 if (fStopOnError) return kFALSE;
657 if (!fMakeDigitsFromHits.IsNull()) {
658 if (fBkgrdFileNames && (fBkgrdFileNames->GetEntriesFast() > 0)) {
659 AliWarning(Form("Merging and direct creation of digits from hits "
660 "was selected for some detectors. "
661 "No merging will be done for the following detectors: %s",
662 fMakeDigitsFromHits.Data()));
664 if (!RunHitsDigitization(fMakeDigitsFromHits)) {
665 if (fStopOnError) return kFALSE;
670 if (!RunTrigger(fMakeTrigger)) {
671 if (fStopOnError) return kFALSE;
674 // digits -> raw data
675 if (!fWriteRawData.IsNull()) {
676 if (!WriteRawData(fWriteRawData, fRawDataFileName,
677 fDeleteIntermediateFiles)) {
678 if (fStopOnError) return kFALSE;
685 //_____________________________________________________________________________
686 Bool_t AliSimulation::RunTrigger(const char* descriptors)
690 TStopwatch stopwatch;
693 AliRunLoader* runLoader = LoadRun("READ");
694 if (!runLoader) return kFALSE;
695 TString des = descriptors;
698 if (gAlice->GetTriggerDescriptor() != "") {
699 des = gAlice->GetTriggerDescriptor();
702 AliWarning("No trigger descriptor is specified. Skipping the trigger simulation...");
707 runLoader->MakeTree( "CT" );
708 AliCentralTrigger* aCTP = runLoader->GetTrigger();
710 aCTP->LoadDescriptor( des );
713 if( !aCTP->RunTrigger( runLoader ) ) {
720 AliInfo(Form("Execution time: R:%.2fs C:%.2fs",
721 stopwatch.RealTime(),stopwatch.CpuTime()));
728 //_____________________________________________________________________________
729 Bool_t AliSimulation::WriteTriggerRawData()
731 // Writes the CTP (trigger) DDL raw data
732 // Details of the format are given in the
733 // trigger TDR - pages 134 and 135.
734 AliCTPRawData writer;
740 //_____________________________________________________________________________
741 Bool_t AliSimulation::RunSimulation(Int_t nEvents)
743 // run the generation and simulation
745 TStopwatch stopwatch;
749 AliError("no gAlice object. Restart aliroot and try again.");
752 if (gAlice->Modules()->GetEntries() > 0) {
753 AliError("gAlice was already run. Restart aliroot and try again.");
757 AliInfo(Form("initializing gAlice with config file %s",
758 fConfigFileName.Data()));
759 StdoutToAliInfo(StderrToAliError(
760 gAlice->Init(fConfigFileName.Data());
763 // Get the trigger descriptor string
764 // Either from AliSimulation or from
766 if (fMakeTrigger.IsNull()) {
767 if (gAlice->GetTriggerDescriptor() != "")
768 fMakeTrigger = gAlice->GetTriggerDescriptor();
771 gAlice->SetTriggerDescriptor(fMakeTrigger.Data());
773 // Set run number in CDBManager
774 AliCDBManager::Instance()->SetRun(gAlice->GetRunNumber());
775 AliInfo(Form("Run number: %d",AliCDBManager::Instance()->GetRun()));
777 AliRunLoader* runLoader = gAlice->GetRunLoader();
779 AliError(Form("gAlice has no run loader object. "
780 "Check your config file: %s", fConfigFileName.Data()));
783 SetGAliceFile(runLoader->GetFileName());
785 // Export ideal geometry
786 if (gGeoManager) gGeoManager->Export("geometry.root");
789 // if (!MisalignGeometry(runLoader)) {
793 MisalignGeometry(runLoader);
795 // Export (mis)aligned geometry
796 if (gGeoManager) gGeoManager->Export("misaligned_geometry.root");
798 // AliRunLoader* runLoader = gAlice->GetRunLoader();
800 // AliError(Form("gAlice has no run loader object. "
801 // "Check your config file: %s", fConfigFileName.Data()));
804 // SetGAliceFile(runLoader->GetFileName());
806 if (!gAlice->Generator()) {
807 AliError(Form("gAlice has no generator object. "
808 "Check your config file: %s", fConfigFileName.Data()));
811 if (nEvents <= 0) nEvents = fNEvents;
813 // get vertex from background file in case of merging
814 if (fUseBkgrdVertex &&
815 fBkgrdFileNames && (fBkgrdFileNames->GetEntriesFast() > 0)) {
816 Int_t signalPerBkgrd = GetNSignalPerBkgrd(nEvents);
817 const char* fileName = ((TObjString*)
818 (fBkgrdFileNames->At(0)))->GetName();
819 AliInfo(Form("The vertex will be taken from the background "
820 "file %s with nSignalPerBackground = %d",
821 fileName, signalPerBkgrd));
822 AliVertexGenFile* vtxGen = new AliVertexGenFile(fileName, signalPerBkgrd);
823 gAlice->Generator()->SetVertexGenerator(vtxGen);
826 if (!fRunSimulation) {
827 gAlice->Generator()->SetTrackingFlag(0);
830 // set the number of events per file for given detectors and data types
831 for (Int_t i = 0; i < fEventsPerFile.GetEntriesFast(); i++) {
832 if (!fEventsPerFile[i]) continue;
833 const char* detName = fEventsPerFile[i]->GetName();
834 const char* typeName = fEventsPerFile[i]->GetTitle();
835 TString loaderName(detName);
836 loaderName += "Loader";
837 AliLoader* loader = runLoader->GetLoader(loaderName);
839 AliError(Form("RunSimulation", "no loader for %s found\n"
840 "Number of events per file not set for %s %s",
841 detName, typeName, detName));
844 AliDataLoader* dataLoader =
845 loader->GetDataLoader(typeName);
847 AliError(Form("no data loader for %s found\n"
848 "Number of events per file not set for %s %s",
849 typeName, detName, typeName));
852 dataLoader->SetNumberOfEventsPerFile(fEventsPerFile[i]->GetUniqueID());
853 AliDebug(1, Form("number of events per file set to %d for %s %s",
854 fEventsPerFile[i]->GetUniqueID(), detName, typeName));
857 AliInfo("running gAlice");
858 StdoutToAliInfo(StderrToAliError(
859 gAlice->Run(nEvents);
864 AliInfo(Form("Execution time: R:%.2fs C:%.2fs",
865 stopwatch.RealTime(),stopwatch.CpuTime()));
870 //_____________________________________________________________________________
871 Bool_t AliSimulation::RunSDigitization(const char* detectors)
873 // run the digitization and produce summable digits
875 TStopwatch stopwatch;
878 AliRunLoader* runLoader = LoadRun();
879 if (!runLoader) return kFALSE;
881 TString detStr = detectors;
882 TObjArray* detArray = runLoader->GetAliRun()->Detectors();
883 for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
884 AliModule* det = (AliModule*) detArray->At(iDet);
885 if (!det || !det->IsActive()) continue;
886 if (IsSelected(det->GetName(), detStr)) {
887 AliInfo(Form("creating summable digits for %s", det->GetName()));
888 TStopwatch stopwatchDet;
889 stopwatchDet.Start();
891 AliInfo(Form("Execution time for %s: R:%.2fs C:%.2fs",
892 det->GetName(),stopwatchDet.RealTime(),stopwatchDet.CpuTime()));
896 if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
897 AliError(Form("the following detectors were not found: %s",
899 if (fStopOnError) return kFALSE;
904 AliInfo(Form("Execution time: R:%.2fs C:%.2fs",
905 stopwatch.RealTime(),stopwatch.CpuTime()));
911 //_____________________________________________________________________________
912 Bool_t AliSimulation::RunDigitization(const char* detectors,
913 const char* excludeDetectors)
915 // run the digitization and produce digits from sdigits
917 TStopwatch stopwatch;
920 while (AliRunLoader::GetRunLoader()) delete AliRunLoader::GetRunLoader();
921 if (gAlice) delete gAlice;
925 if (fBkgrdFileNames) nStreams = fBkgrdFileNames->GetEntriesFast() + 1;
926 Int_t signalPerBkgrd = GetNSignalPerBkgrd();
927 AliRunDigitizer* manager = new AliRunDigitizer(nStreams, signalPerBkgrd);
928 // manager->SetEmbeddingFlag(fEmbeddingFlag);
929 manager->SetInputStream(0, fGAliceFileName.Data());
930 for (Int_t iStream = 1; iStream < nStreams; iStream++) {
931 const char* fileName = ((TObjString*)
932 (fBkgrdFileNames->At(iStream-1)))->GetName();
933 manager->SetInputStream(iStream, fileName);
936 TString detStr = detectors;
937 TString detExcl = excludeDetectors;
938 manager->GetInputStream(0)->ImportgAlice();
939 AliRunLoader* runLoader =
940 AliRunLoader::GetRunLoader(manager->GetInputStream(0)->GetFolderName());
941 TObjArray* detArray = runLoader->GetAliRun()->Detectors();
942 for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
943 AliModule* det = (AliModule*) detArray->At(iDet);
944 if (!det || !det->IsActive()) continue;
945 if (IsSelected(det->GetName(), detStr) &&
946 !IsSelected(det->GetName(), detExcl)) {
947 AliDigitizer* digitizer = det->CreateDigitizer(manager);
950 AliError(Form("no digitizer for %s", det->GetName()));
951 if (fStopOnError) return kFALSE;
953 digitizer->SetRegionOfInterest(fRegionOfInterest);
958 if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
959 AliError(Form("the following detectors were not found: %s",
961 if (fStopOnError) return kFALSE;
964 if (!manager->GetListOfTasks()->IsEmpty()) {
965 AliInfo("executing digitization");
971 AliInfo(Form("Execution time: R:%.2fs C:%.2fs",
972 stopwatch.RealTime(),stopwatch.CpuTime()));
977 //_____________________________________________________________________________
978 Bool_t AliSimulation::RunHitsDigitization(const char* detectors)
980 // run the digitization and produce digits from hits
982 TStopwatch stopwatch;
985 AliRunLoader* runLoader = LoadRun("READ");
986 if (!runLoader) return kFALSE;
988 TString detStr = detectors;
989 TObjArray* detArray = runLoader->GetAliRun()->Detectors();
990 for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
991 AliModule* det = (AliModule*) detArray->At(iDet);
992 if (!det || !det->IsActive()) continue;
993 if (IsSelected(det->GetName(), detStr)) {
994 AliInfo(Form("creating digits from hits for %s", det->GetName()));
999 if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
1000 AliError(Form("the following detectors were not found: %s",
1002 if (fStopOnError) return kFALSE;
1006 //PH Temporary fix to avoid interference with the PHOS loder/getter
1007 //PH The problem has to be solved in more general way 09/06/05
1009 AliInfo(Form("Execution time: R:%.2fs C:%.2fs",
1010 stopwatch.RealTime(),stopwatch.CpuTime()));
1015 //_____________________________________________________________________________
1016 Bool_t AliSimulation::WriteRawData(const char* detectors,
1017 const char* fileName,
1018 Bool_t deleteIntermediateFiles)
1020 // convert the digits to raw data
1021 // First DDL raw data files for the given detectors are created.
1022 // If a file name is given, the DDL files are then converted to a DATE file.
1023 // If deleteIntermediateFiles is true, the DDL raw files are deleted
1025 // If the file name has the extension ".root", the DATE file is converted
1027 // If deleteIntermediateFiles is true, the DATE file is deleted afterwards.
1029 TStopwatch stopwatch;
1032 if (!WriteRawFiles(detectors)) {
1033 if (fStopOnError) return kFALSE;
1036 TString dateFileName(fileName);
1037 if (!dateFileName.IsNull()) {
1038 Bool_t rootOutput = dateFileName.EndsWith(".root");
1039 if (rootOutput) dateFileName += ".date";
1040 if (!ConvertRawFilesToDate(dateFileName)) {
1041 if (fStopOnError) return kFALSE;
1043 if (deleteIntermediateFiles) {
1044 AliRunLoader* runLoader = LoadRun("READ");
1045 if (runLoader) for (Int_t iEvent = 0;
1046 iEvent < runLoader->GetNumberOfEvents(); iEvent++) {
1048 sprintf(command, "rm -r raw%d", iEvent);
1049 gSystem->Exec(command);
1054 if (!ConvertDateToRoot(dateFileName, fileName)) {
1055 if (fStopOnError) return kFALSE;
1057 if (deleteIntermediateFiles) {
1058 gSystem->Unlink(dateFileName);
1063 AliInfo(Form("Execution time: R:%.2fs C:%.2fs",
1064 stopwatch.RealTime(),stopwatch.CpuTime()));
1069 //_____________________________________________________________________________
1070 Bool_t AliSimulation::WriteRawFiles(const char* detectors)
1072 // convert the digits to raw data DDL files
1074 AliRunLoader* runLoader = LoadRun("READ");
1075 if (!runLoader) return kFALSE;
1077 // write raw data to DDL files
1078 for (Int_t iEvent = 0; iEvent < runLoader->GetNumberOfEvents(); iEvent++) {
1079 AliInfo(Form("processing event %d", iEvent));
1080 runLoader->GetEvent(iEvent);
1081 TString baseDir = gSystem->WorkingDirectory();
1083 sprintf(dirName, "raw%d", iEvent);
1084 gSystem->MakeDirectory(dirName);
1085 if (!gSystem->ChangeDirectory(dirName)) {
1086 AliError(Form("couldn't change to directory %s", dirName));
1087 if (fStopOnError) return kFALSE; else continue;
1090 TString detStr = detectors;
1091 TObjArray* detArray = runLoader->GetAliRun()->Detectors();
1092 for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
1093 AliModule* det = (AliModule*) detArray->At(iDet);
1094 if (!det || !det->IsActive()) continue;
1095 if (IsSelected(det->GetName(), detStr)) {
1096 AliInfo(Form("creating raw data from digits for %s", det->GetName()));
1101 if (!WriteTriggerRawData())
1102 if (fStopOnError) return kFALSE;
1104 gSystem->ChangeDirectory(baseDir);
1105 if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
1106 AliError(Form("the following detectors were not found: %s",
1108 if (fStopOnError) return kFALSE;
1116 //_____________________________________________________________________________
1117 Bool_t AliSimulation::ConvertRawFilesToDate(const char* dateFileName)
1119 // convert raw data DDL files to a DATE file with the program "dateStream"
1121 char* path = gSystem->Which(gSystem->Getenv("PATH"), "dateStream");
1123 AliError("the program dateStream was not found");
1124 if (fStopOnError) return kFALSE;
1129 AliRunLoader* runLoader = LoadRun("READ");
1130 if (!runLoader) return kFALSE;
1132 AliInfo(Form("converting raw data DDL files to DATE file %s", dateFileName));
1134 sprintf(command, "dateStream -D -o %s -# %d -C",
1135 dateFileName, runLoader->GetNumberOfEvents());
1136 FILE* pipe = gSystem->OpenPipe(command, "w");
1138 for (Int_t iEvent = 0; iEvent < runLoader->GetNumberOfEvents(); iEvent++) {
1139 fprintf(pipe, "GDC\n");
1143 // loop over detectors and DDLs
1144 for (Int_t iDet = 0; iDet < AliDAQ::kNDetectors; iDet++) {
1145 for (Int_t iDDL = 0; iDDL < AliDAQ::NumberOfDdls(iDet); iDDL++) {
1147 Int_t ddlID = AliDAQ::DdlID(iDet,iDDL);
1148 Int_t ldcID = Int_t(ldc + 0.0001);
1149 ldc += AliDAQ::NumberOfLdcs(iDet) / AliDAQ::NumberOfDdls(iDet);
1151 char rawFileName[256];
1152 sprintf(rawFileName, "raw%d/%s",
1153 iEvent, AliDAQ::DdlFileName(iDet,iDDL));
1155 // check existence and size of raw data file
1156 FILE* file = fopen(rawFileName, "rb");
1157 if (!file) continue;
1158 fseek(file, 0, SEEK_END);
1159 unsigned long size = ftell(file);
1161 if (!size) continue;
1163 if (ldcID != prevLDC) {
1164 fprintf(pipe, " LDC Id %d\n", ldcID);
1167 fprintf(pipe, " Equipment Id %d Payload %s\n", ddlID, rawFileName);
1172 Int_t result = gSystem->ClosePipe(pipe);
1175 return (result == 0);
1178 //_____________________________________________________________________________
1179 Bool_t AliSimulation::ConvertDateToRoot(const char* dateFileName,
1180 const char* rootFileName)
1182 // convert a DATE file to a root file with the program "alimdc"
1185 const Int_t kDBSize = 1000000000;
1186 const Int_t kTagDBSize = 1000000000;
1187 const Bool_t kFilter = kFALSE;
1188 const Int_t kCompression = 1;
1190 char* path = gSystem->Which(gSystem->Getenv("PATH"), "alimdc");
1192 AliError("the program alimdc was not found");
1193 if (fStopOnError) return kFALSE;
1198 AliInfo(Form("converting DATE file %s to root file %s",
1199 dateFileName, rootFileName));
1201 const char* rawDBFS[2] = { "/tmp/mdc1", "/tmp/mdc2" };
1202 const char* tagDBFS = "/tmp/mdc1/tags";
1203 const char* runDBFS = "/tmp/mdc1/meta";
1205 // User defined file system locations
1206 if (gSystem->Getenv("ALIMDC_RAWDB1"))
1207 rawDBFS[0] = gSystem->Getenv("ALIMDC_RAWDB1");
1208 if (gSystem->Getenv("ALIMDC_RAWDB2"))
1209 rawDBFS[1] = gSystem->Getenv("ALIMDC_RAWDB2");
1210 if (gSystem->Getenv("ALIMDC_TAGDB"))
1211 tagDBFS = gSystem->Getenv("ALIMDC_TAGDB");
1212 if (gSystem->Getenv("ALIMDC_RUNDB"))
1213 runDBFS = gSystem->Getenv("ALIMDC_RUNDB");
1215 gSystem->Exec(Form("rm -rf %s",rawDBFS[0]));
1216 gSystem->Exec(Form("rm -rf %s",rawDBFS[1]));
1217 gSystem->Exec(Form("rm -rf %s",tagDBFS));
1218 gSystem->Exec(Form("rm -rf %s",runDBFS));
1220 gSystem->Exec(Form("mkdir %s",rawDBFS[0]));
1221 gSystem->Exec(Form("mkdir %s",rawDBFS[1]));
1222 gSystem->Exec(Form("mkdir %s",tagDBFS));
1223 gSystem->Exec(Form("mkdir %s",runDBFS));
1225 Int_t result = gSystem->Exec(Form("alimdc %d %d %d %d %s",
1226 kDBSize, kTagDBSize, kFilter, kCompression, dateFileName));
1227 gSystem->Exec(Form("mv %s/*.root %s", rawDBFS[0], rootFileName));
1229 gSystem->Exec(Form("rm -rf %s",rawDBFS[0]));
1230 gSystem->Exec(Form("rm -rf %s",rawDBFS[1]));
1231 gSystem->Exec(Form("rm -rf %s",tagDBFS));
1232 gSystem->Exec(Form("rm -rf %s",runDBFS));
1234 return (result == 0);
1238 //_____________________________________________________________________________
1239 AliRunLoader* AliSimulation::LoadRun(const char* mode) const
1241 // delete existing run loaders, open a new one and load gAlice
1243 while (AliRunLoader::GetRunLoader()) delete AliRunLoader::GetRunLoader();
1244 AliRunLoader* runLoader =
1245 AliRunLoader::Open(fGAliceFileName.Data(),
1246 AliConfig::GetDefaultEventFolderName(), mode);
1248 AliError(Form("no run loader found in file %s", fGAliceFileName.Data()));
1251 runLoader->LoadgAlice();
1252 gAlice = runLoader->GetAliRun();
1254 AliError(Form("no gAlice object found in file %s",
1255 fGAliceFileName.Data()));
1261 //_____________________________________________________________________________
1262 Int_t AliSimulation::GetNSignalPerBkgrd(Int_t nEvents) const
1264 // get or calculate the number of signal events per background event
1266 if (!fBkgrdFileNames) return 1;
1267 Int_t nBkgrdFiles = fBkgrdFileNames->GetEntriesFast();
1268 if (nBkgrdFiles == 0) return 1;
1270 // get the number of signal events
1272 AliRunLoader* runLoader =
1273 AliRunLoader::Open(fGAliceFileName.Data(), "SIGNAL");
1274 if (!runLoader) return 1;
1276 nEvents = runLoader->GetNumberOfEvents();
1281 for (Int_t iBkgrdFile = 0; iBkgrdFile < nBkgrdFiles; iBkgrdFile++) {
1282 // get the number of background events
1283 const char* fileName = ((TObjString*)
1284 (fBkgrdFileNames->At(iBkgrdFile)))->GetName();
1285 AliRunLoader* runLoader =
1286 AliRunLoader::Open(fileName, "BKGRD");
1287 if (!runLoader) continue;
1288 Int_t nBkgrdEvents = runLoader->GetNumberOfEvents();
1291 // get or calculate the number of signal per background events
1292 Int_t nSignalPerBkgrd = fBkgrdFileNames->At(iBkgrdFile)->GetUniqueID();
1293 if (nSignalPerBkgrd <= 0) {
1294 nSignalPerBkgrd = (nEvents-1) / nBkgrdEvents + 1;
1295 } else if (result && (result != nSignalPerBkgrd)) {
1296 AliInfo(Form("the number of signal events per background event "
1297 "will be changed from %d to %d for stream %d",
1298 nSignalPerBkgrd, result, iBkgrdFile+1));
1299 nSignalPerBkgrd = result;
1302 if (!result) result = nSignalPerBkgrd;
1303 if (nSignalPerBkgrd * nBkgrdEvents < nEvents) {
1304 AliWarning(Form("not enough background events (%d) for %d signal events "
1305 "using %d signal per background events for stream %d",
1306 nBkgrdEvents, nEvents, nSignalPerBkgrd, iBkgrdFile+1));
1313 //_____________________________________________________________________________
1314 Bool_t AliSimulation::IsSelected(TString detName, TString& detectors) const
1316 // check whether detName is contained in detectors
1317 // if yes, it is removed from detectors
1319 // check if all detectors are selected
1320 if ((detectors.CompareTo("ALL") == 0) ||
1321 detectors.BeginsWith("ALL ") ||
1322 detectors.EndsWith(" ALL") ||
1323 detectors.Contains(" ALL ")) {
1328 // search for the given detector
1329 Bool_t result = kFALSE;
1330 if ((detectors.CompareTo(detName) == 0) ||
1331 detectors.BeginsWith(detName+" ") ||
1332 detectors.EndsWith(" "+detName) ||
1333 detectors.Contains(" "+detName+" ")) {
1334 detectors.ReplaceAll(detName, "");
1338 // clean up the detectors string
1339 while (detectors.Contains(" ")) detectors.ReplaceAll(" ", " ");
1340 while (detectors.BeginsWith(" ")) detectors.Remove(0, 1);
1341 while (detectors.EndsWith(" ")) detectors.Remove(detectors.Length()-1, 1);
1346 Bool_t AliSimulation::ConvertRaw2SDigits(const char* rawDirectory, const char* esdFileName)
1349 // Steering routine to convert raw data in directory rawDirectory/ to fake SDigits.
1350 // These can be used for embedding of MC tracks into RAW data using the standard
1351 // merging procedure.
1353 // If an ESD file is given the reconstructed vertex is taken from it and stored in the event header.
1356 AliError("no gAlice object. Restart aliroot and try again.");
1359 if (gAlice->Modules()->GetEntries() > 0) {
1360 AliError("gAlice was already run. Restart aliroot and try again.");
1364 AliInfo(Form("initializing gAlice with config file %s",fConfigFileName.Data()));
1365 StdoutToAliInfo(StderrToAliError(gAlice->Init(fConfigFileName.Data());););
1369 AliCDBManager* man = AliCDBManager::Instance();
1370 man->SetRun(0); // Should this come from rawdata header ?
1374 // Get the runloader
1375 AliRunLoader* runLoader = gAlice->GetRunLoader();
1377 // Open esd file if available
1378 TFile* esdFile = TFile::Open(esdFileName);
1379 Bool_t esdOK = (esdFile != 0);
1380 AliESD* esd = new AliESD;
1383 treeESD = (TTree*) esdFile->Get("esdTree");
1385 AliWarning("No ESD tree found");
1388 treeESD->SetBranchAddress("ESD", &esd);
1392 // Create the RawReader
1393 AliRawReaderFile* rawReader = new AliRawReaderFile(rawDirectory);
1395 // Get list of detectors
1396 TObjArray* detArray = runLoader->GetAliRun()->Detectors();
1399 AliHeader* header = runLoader->GetHeader();
1404 if (!(rawReader->NextEvent())) break;
1407 for (iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
1408 AliModule* det = (AliModule*) detArray->At(iDet);
1409 AliInfo(Form("Calling Raw2SDigits for %s\n", det->GetName()));
1410 det->Raw2SDigits(rawReader);
1415 // If ESD information available obtain reconstructed vertex and store in header.
1417 treeESD->GetEvent(nev);
1418 const AliESDVertex* esdVertex = esd->GetPrimaryVertex();
1419 Double_t position[3];
1420 esdVertex->GetXYZ(position);
1421 AliGenEventHeader* mcHeader = new AliGenEventHeader("ESD");
1424 for (Int_t i = 0; i < 3; i++) mcV[i] = position[i];
1425 mcHeader->SetPrimaryVertex(mcV);
1426 header->Reset(0,nev);
1427 header->SetGenEventHeader(mcHeader);
1428 printf("***** Saved vertex %f %f %f \n", position[0], position[1], position[2]);
1433 runLoader->TreeE()->Fill();
1434 runLoader->SetNextEvent();
1440 runLoader->CdGAFile();
1441 runLoader->WriteHeader("OVERWRITE");
1442 runLoader->WriteRunLoader();