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 AliDebug(2,"!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
276 AliDebug(2, Form("Default CDB storage is set to: %s",fCDBUri.Data()));
277 AliDebug(2, "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
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 AliDebug(2, "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
286 AliDebug(2, Form("Specific CDB storage for %s is set to: %s",obj->GetName(),obj->GetTitle()));
287 AliDebug(2, "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
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* calibType, const char* uri) {
304 // Store a detector-specific CDB storage location
305 // Activate it later within the Run() method
307 AliCDBPath aPath(calibType);
308 if(!aPath.IsValid()){
309 AliError(Form("Not a valid path: %s", calibType));
313 TObject* obj = fSpecCDBUri.FindObject(calibType);
314 if (obj) fSpecCDBUri.Remove(obj);
315 fSpecCDBUri.Add(new TNamed(calibType, uri));
319 //_____________________________________________________________________________
320 void AliSimulation::SetConfigFile(const char* fileName)
322 // set the name of the config file
324 fConfigFileName = fileName;
327 //_____________________________________________________________________________
328 void AliSimulation::SetGAliceFile(const char* fileName)
330 // set the name of the galice file
331 // the path is converted to an absolute one if it is relative
333 fGAliceFileName = fileName;
334 if (!gSystem->IsAbsoluteFileName(fGAliceFileName)) {
335 char* absFileName = gSystem->ConcatFileName(gSystem->WorkingDirectory(),
337 fGAliceFileName = absFileName;
338 delete[] absFileName;
341 AliDebug(2, Form("galice file name set to %s", fileName));
344 //_____________________________________________________________________________
345 void AliSimulation::SetEventsPerFile(const char* detector, const char* type,
348 // set the number of events per file for the given detector and data type
349 // ("Hits", "Summable Digits", "Digits", "Reconstructed Points" or "Tracks")
351 TNamed* obj = new TNamed(detector, type);
352 obj->SetUniqueID(nEvents);
353 fEventsPerFile.Add(obj);
356 //_____________________________________________________________________________
357 Bool_t AliSimulation::ApplyAlignObjsToGeom(TObjArray* alObjArray)
359 // Read collection of alignment objects (AliAlignObj derived) saved
360 // in the TClonesArray ClArrayName and apply them to the geometry
361 // manager singleton.
364 Int_t nvols = alObjArray->GetEntriesFast();
368 for(Int_t j=0; j<nvols; j++)
370 AliAlignObj* alobj = (AliAlignObj*) alObjArray->UncheckedAt(j);
371 if (alobj->ApplyToGeometry() == kFALSE) flag = kFALSE;
374 if (AliDebugLevelClass() >= 1) {
375 gGeoManager->GetTopNode()->CheckOverlaps(1);
376 TObjArray* ovexlist = gGeoManager->GetListOfOverlaps();
377 if(ovexlist->GetEntriesFast()){
378 AliError("The application of alignment objects to the geometry caused huge overlaps/extrusions!");
386 //_____________________________________________________________________________
387 Bool_t AliSimulation::ApplyAlignObjsToGeom(const char* fileName, const char* clArrayName)
389 // read collection of alignment objects (AliAlignObj derived) saved
390 // in the TClonesArray ClArrayName in the file fileName and apply
391 // them to the TGeo geometry passed as argument
394 TFile* inFile = TFile::Open(fileName,"READ");
395 if (!inFile || !inFile->IsOpen()) {
396 AliErrorClass(Form("Could not open file %s !",fileName));
400 TClonesArray* alObjArray = ((TClonesArray*) inFile->Get(clArrayName));
403 AliErrorClass(Form("Could not get array (%s) from file (%s) !",clArrayName,fileName));
407 return ApplyAlignObjsToGeom(alObjArray);
411 //_____________________________________________________________________________
412 Bool_t AliSimulation::ApplyAlignObjsToGeom(AliCDBParam* param, AliCDBId& Id)
414 // read collection of alignment objects (AliAlignObj derived) saved
415 // in the TClonesArray ClArrayName in the AliCDBEntry identified by
416 // param (to get the AliCDBStorage) and Id; apply the alignment objects
417 // to the TGeo geometry passed as argument
420 AliCDBStorage* storage = AliCDBManager::Instance()->GetStorage(param);
421 AliCDBEntry* entry = storage->Get(Id);
422 TClonesArray* AlObjArray = ((TClonesArray*) entry->GetObject());
424 return ApplyAlignObjsToGeom(AlObjArray);
428 //_____________________________________________________________________________
429 Bool_t AliSimulation::ApplyAlignObjsToGeom(const char* uri, const char* path, Int_t runnum, Int_t version, Int_t sversion)
431 // read collection of alignment objects (AliAlignObj derived) saved
432 // in the TClonesArray ClArrayName in the AliCDBEntry identified by
433 // param (to get the AliCDBStorage) and Id; apply the alignment objects
434 // to the TGeo geometry passed as argument
437 AliCDBParam* param = AliCDBManager::Instance()->CreateParameter(uri);
438 AliCDBId id(path, runnum, runnum, version, sversion);
440 return ApplyAlignObjsToGeom(param, id);
444 //_____________________________________________________________________________
445 Bool_t AliSimulation::ApplyAlignObjsToGeom(const char* detName, Int_t runnum, Int_t version, Int_t sversion)
447 // read collection of alignment objects (AliAlignObj derived) saved
448 // in the TClonesArray ClArrayName in the AliCDBEntry identified by
449 // param (to get the AliCDBStorage) and Id; apply the alignment objects
450 // to the TGeo geometry passed as argument
453 AliCDBPath path(detName,"Align","Data");
454 AliCDBEntry* entry = AliCDBManager::Instance()->Get(path.GetPath(),runnum,version,sversion);
456 if(!entry) return kFALSE;
457 TClonesArray* AlObjArray = ((TClonesArray*) entry->GetObject());
459 return ApplyAlignObjsToGeom(AlObjArray);
462 //_____________________________________________________________________________
463 Bool_t AliSimulation::SetAlignObjArraySingleDet(const char* detName)
465 // Fills array of single detector's alignable objects from CDB
467 AliDebug(2, Form("Loading alignment data for detector: %s",detName));
471 AliCDBPath path(detName,"Align","Data");
473 entry=AliCDBManager::Instance()->Get(path.GetPath());
475 AliDebug(2,Form("Couldn't load alignment data for detector %s",detName));
479 TClonesArray *alignArray = (TClonesArray*) entry->GetObject();
480 alignArray->SetOwner(0);
481 AliDebug(2,Form("Found %d alignment objects for %s",
482 alignArray->GetEntries(),detName));
484 AliAlignObj *alignObj=0;
485 TIter iter(alignArray);
487 // loop over align objects in detector
488 while( ( alignObj=(AliAlignObj *) iter.Next() ) ){
489 fAlignObjArray->Add(alignObj);
491 // delete entry --- Don't delete, it is cached!
493 AliDebug(2, Form("fAlignObjArray entries: %d",fAlignObjArray->GetEntries() ));
498 //_____________________________________________________________________________
499 Bool_t AliSimulation::MisalignGeometry(AliRunLoader *runLoader)
501 // Read the alignment objects from CDB.
502 // Each detector is supposed to have the
503 // alignment objects in DET/Align/Data CDB path.
504 // All the detector objects are then collected,
505 // sorted by geometry level (starting from ALIC) and
506 // then applied to the TGeo geometry.
507 // Finally an overlaps check is performed.
509 Bool_t delRunLoader = kFALSE;
511 runLoader = LoadRun("READ");
512 if (!runLoader) return kFALSE;
513 delRunLoader = kTRUE;
516 // Load alignment data from CDB and fill fAlignObjArray
517 if(fLoadAlignFromCDB){
518 if(!fAlignObjArray) fAlignObjArray = new TObjArray();
520 //fAlignObjArray->RemoveAll();
521 fAlignObjArray->Clear();
522 fAlignObjArray->SetOwner(0);
524 TString detStr = fLoadAlignData;
525 TString dataNotLoaded="";
526 TString dataLoaded="";
528 TObjArray* detArray = runLoader->GetAliRun()->Detectors();
529 for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
530 AliModule* det = (AliModule*) detArray->At(iDet);
531 if (!det || !det->IsActive()) continue;
532 if (IsSelected(det->GetName(), detStr)) {
533 if(!SetAlignObjArraySingleDet(det->GetName())){
534 dataNotLoaded += det->GetName();
535 dataNotLoaded += " ";
537 dataLoaded += det->GetName();
541 } // end loop over detectors
543 if ((detStr.CompareTo("ALL") == 0)) detStr = "";
544 dataNotLoaded += detStr;
545 if(!dataLoaded.IsNull()) AliInfo(Form("Alignment data loaded for: %s",
547 if(!dataNotLoaded.IsNull()) AliInfo(Form("Didn't/couldn't load alignment data for: %s",
548 dataNotLoaded.Data()));
549 } // fLoadAlignFromCDB flag
551 // Check if the array with alignment objects was
552 // provided by the user. If yes, apply the objects
553 // to the present TGeo geometry
554 if (fAlignObjArray) {
555 if (gGeoManager && gGeoManager->IsClosed()) {
556 if (ApplyAlignObjsToGeom(fAlignObjArray) == kFALSE) {
557 AliError("The misalignment of one or more volumes failed!"
558 "Compare the list of simulated detectors and the list of detector alignment data!");
559 if (delRunLoader) delete runLoader;
564 AliError("Can't apply the misalignment! gGeoManager doesn't exist or it is still opened!");
565 if (delRunLoader) delete runLoader;
571 // Update the internal geometry of modules (ITS needs it)
572 TString detStr = fLoadAlignData;
573 TObjArray* detArray = runLoader->GetAliRun()->Detectors();
574 for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
576 AliModule* det = (AliModule*) detArray->At(iDet);
577 if (!det || !det->IsActive()) continue;
578 if (IsSelected(det->GetName(), detStr)) {
579 det->UpdateInternalGeometry();
581 } // end loop over detectors
584 if (delRunLoader) delete runLoader;
586 // Update the TGeoPhysicalNodes
587 gGeoManager->RefreshPhysicalNodes();
593 //_____________________________________________________________________________
594 Bool_t AliSimulation::SetRunNumber()
596 // Set the CDB manager run number
597 // The run number is retrieved from gAlice
599 if(AliCDBManager::Instance()->GetRun() < 0) {
600 AliRunLoader* runLoader = LoadRun("READ");
601 if (!runLoader) return kFALSE;
603 AliCDBManager::Instance()->SetRun(runLoader->GetAliRun()->GetRunNumber());
604 AliInfo(Form("Run number: %d",AliCDBManager::Instance()->GetRun()));
611 //_____________________________________________________________________________
612 void AliSimulation::MergeWith(const char* fileName, Int_t nSignalPerBkgrd)
614 // add a file with background events for merging
616 TObjString* fileNameStr = new TObjString(fileName);
617 fileNameStr->SetUniqueID(nSignalPerBkgrd);
618 if (!fBkgrdFileNames) fBkgrdFileNames = new TObjArray;
619 fBkgrdFileNames->Add(fileNameStr);
622 void AliSimulation::EmbedInto(const char* fileName, Int_t nSignalPerBkgrd)
624 // add a file with background events for embeddin
625 MergeWith(fileName, nSignalPerBkgrd);
626 fEmbeddingFlag = kTRUE;
629 //_____________________________________________________________________________
630 Bool_t AliSimulation::Run(Int_t nEvents)
632 // run the generation, simulation and digitization
636 if (nEvents > 0) fNEvents = nEvents;
638 // generation and simulation -> hits
639 if (fRunGeneration) {
640 if (!RunSimulation()) if (fStopOnError) return kFALSE;
643 // Set run number in CDBManager (if it is not already set in RunSimulation)
644 if (!SetRunNumber()) if (fStopOnError) return kFALSE;
646 // Load and misalign the geometry
648 TGeoManager::Import("geometry.root");
649 if (!gGeoManager) if (fStopOnError) return kFALSE;
650 if (!MisalignGeometry()) if (fStopOnError) return kFALSE;
653 // hits -> summable digits
654 if (!fMakeSDigits.IsNull()) {
655 if (!RunSDigitization(fMakeSDigits)) if (fStopOnError) return kFALSE;
658 // summable digits -> digits
659 if (!fMakeDigits.IsNull()) {
660 if (!RunDigitization(fMakeDigits, fMakeDigitsFromHits)) {
661 if (fStopOnError) return kFALSE;
666 if (!fMakeDigitsFromHits.IsNull()) {
667 if (fBkgrdFileNames && (fBkgrdFileNames->GetEntriesFast() > 0)) {
668 AliWarning(Form("Merging and direct creation of digits from hits "
669 "was selected for some detectors. "
670 "No merging will be done for the following detectors: %s",
671 fMakeDigitsFromHits.Data()));
673 if (!RunHitsDigitization(fMakeDigitsFromHits)) {
674 if (fStopOnError) return kFALSE;
679 if (!RunTrigger(fMakeTrigger)) {
680 if (fStopOnError) return kFALSE;
683 // digits -> raw data
684 if (!fWriteRawData.IsNull()) {
685 if (!WriteRawData(fWriteRawData, fRawDataFileName,
686 fDeleteIntermediateFiles)) {
687 if (fStopOnError) return kFALSE;
694 //_____________________________________________________________________________
695 Bool_t AliSimulation::RunTrigger(const char* descriptors)
699 TStopwatch stopwatch;
702 AliRunLoader* runLoader = LoadRun("READ");
703 if (!runLoader) return kFALSE;
704 TString des = descriptors;
707 if (gAlice->GetTriggerDescriptor() != "") {
708 des = gAlice->GetTriggerDescriptor();
711 AliWarning("No trigger descriptor is specified. Skipping the trigger simulation...");
716 runLoader->MakeTree( "GG" );
717 AliCentralTrigger* aCTP = runLoader->GetTrigger();
719 aCTP->LoadDescriptor( des );
722 if( !aCTP->RunTrigger( runLoader ) ) {
729 AliInfo(Form("Execution time: R:%.2fs C:%.2fs",
730 stopwatch.RealTime(),stopwatch.CpuTime()));
737 //_____________________________________________________________________________
738 Bool_t AliSimulation::WriteTriggerRawData()
740 // Writes the CTP (trigger) DDL raw data
741 // Details of the format are given in the
742 // trigger TDR - pages 134 and 135.
743 AliCTPRawData writer;
749 //_____________________________________________________________________________
750 Bool_t AliSimulation::RunSimulation(Int_t nEvents)
752 // run the generation and simulation
754 TStopwatch stopwatch;
758 AliError("no gAlice object. Restart aliroot and try again.");
761 if (gAlice->Modules()->GetEntries() > 0) {
762 AliError("gAlice was already run. Restart aliroot and try again.");
766 AliInfo(Form("initializing gAlice with config file %s",
767 fConfigFileName.Data()));
768 StdoutToAliInfo(StderrToAliError(
769 gAlice->Init(fConfigFileName.Data());
772 // Get the trigger descriptor string
773 // Either from AliSimulation or from
775 if (fMakeTrigger.IsNull()) {
776 if (gAlice->GetTriggerDescriptor() != "")
777 fMakeTrigger = gAlice->GetTriggerDescriptor();
780 gAlice->SetTriggerDescriptor(fMakeTrigger.Data());
782 // Set run number in CDBManager
783 AliCDBManager::Instance()->SetRun(gAlice->GetRunNumber());
784 AliInfo(Form("Run number: %d",AliCDBManager::Instance()->GetRun()));
786 AliRunLoader* runLoader = gAlice->GetRunLoader();
788 AliError(Form("gAlice has no run loader object. "
789 "Check your config file: %s", fConfigFileName.Data()));
792 SetGAliceFile(runLoader->GetFileName());
794 // Export ideal geometry
795 if (gGeoManager) gGeoManager->Export("geometry.root");
798 // if (!MisalignGeometry(runLoader)) {
802 MisalignGeometry(runLoader);
804 // Export (mis)aligned geometry
805 if (gGeoManager) gGeoManager->Export("misaligned_geometry.root");
807 // AliRunLoader* runLoader = gAlice->GetRunLoader();
809 // AliError(Form("gAlice has no run loader object. "
810 // "Check your config file: %s", fConfigFileName.Data()));
813 // SetGAliceFile(runLoader->GetFileName());
815 if (!gAlice->Generator()) {
816 AliError(Form("gAlice has no generator object. "
817 "Check your config file: %s", fConfigFileName.Data()));
820 if (nEvents <= 0) nEvents = fNEvents;
822 // get vertex from background file in case of merging
823 if (fUseBkgrdVertex &&
824 fBkgrdFileNames && (fBkgrdFileNames->GetEntriesFast() > 0)) {
825 Int_t signalPerBkgrd = GetNSignalPerBkgrd(nEvents);
826 const char* fileName = ((TObjString*)
827 (fBkgrdFileNames->At(0)))->GetName();
828 AliInfo(Form("The vertex will be taken from the background "
829 "file %s with nSignalPerBackground = %d",
830 fileName, signalPerBkgrd));
831 AliVertexGenFile* vtxGen = new AliVertexGenFile(fileName, signalPerBkgrd);
832 gAlice->Generator()->SetVertexGenerator(vtxGen);
835 if (!fRunSimulation) {
836 gAlice->Generator()->SetTrackingFlag(0);
839 // set the number of events per file for given detectors and data types
840 for (Int_t i = 0; i < fEventsPerFile.GetEntriesFast(); i++) {
841 if (!fEventsPerFile[i]) continue;
842 const char* detName = fEventsPerFile[i]->GetName();
843 const char* typeName = fEventsPerFile[i]->GetTitle();
844 TString loaderName(detName);
845 loaderName += "Loader";
846 AliLoader* loader = runLoader->GetLoader(loaderName);
848 AliError(Form("RunSimulation", "no loader for %s found\n"
849 "Number of events per file not set for %s %s",
850 detName, typeName, detName));
853 AliDataLoader* dataLoader =
854 loader->GetDataLoader(typeName);
856 AliError(Form("no data loader for %s found\n"
857 "Number of events per file not set for %s %s",
858 typeName, detName, typeName));
861 dataLoader->SetNumberOfEventsPerFile(fEventsPerFile[i]->GetUniqueID());
862 AliDebug(1, Form("number of events per file set to %d for %s %s",
863 fEventsPerFile[i]->GetUniqueID(), detName, typeName));
866 AliInfo("running gAlice");
867 StdoutToAliInfo(StderrToAliError(
868 gAlice->Run(nEvents);
873 AliInfo(Form("Execution time: R:%.2fs C:%.2fs",
874 stopwatch.RealTime(),stopwatch.CpuTime()));
879 //_____________________________________________________________________________
880 Bool_t AliSimulation::RunSDigitization(const char* detectors)
882 // run the digitization and produce summable digits
884 TStopwatch stopwatch;
887 AliRunLoader* runLoader = LoadRun();
888 if (!runLoader) return kFALSE;
890 TString detStr = detectors;
891 TObjArray* detArray = runLoader->GetAliRun()->Detectors();
892 for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
893 AliModule* det = (AliModule*) detArray->At(iDet);
894 if (!det || !det->IsActive()) continue;
895 if (IsSelected(det->GetName(), detStr)) {
896 AliInfo(Form("creating summable digits for %s", det->GetName()));
897 TStopwatch stopwatchDet;
898 stopwatchDet.Start();
900 AliInfo(Form("Execution time for %s: R:%.2fs C:%.2fs",
901 det->GetName(),stopwatchDet.RealTime(),stopwatchDet.CpuTime()));
905 if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
906 AliError(Form("the following detectors were not found: %s",
908 if (fStopOnError) return kFALSE;
913 AliInfo(Form("Execution time: R:%.2fs C:%.2fs",
914 stopwatch.RealTime(),stopwatch.CpuTime()));
920 //_____________________________________________________________________________
921 Bool_t AliSimulation::RunDigitization(const char* detectors,
922 const char* excludeDetectors)
924 // run the digitization and produce digits from sdigits
926 TStopwatch stopwatch;
929 while (AliRunLoader::GetRunLoader()) delete AliRunLoader::GetRunLoader();
930 if (gAlice) delete gAlice;
934 if (fBkgrdFileNames) nStreams = fBkgrdFileNames->GetEntriesFast() + 1;
935 Int_t signalPerBkgrd = GetNSignalPerBkgrd();
936 AliRunDigitizer* manager = new AliRunDigitizer(nStreams, signalPerBkgrd);
937 // manager->SetEmbeddingFlag(fEmbeddingFlag);
938 manager->SetInputStream(0, fGAliceFileName.Data());
939 for (Int_t iStream = 1; iStream < nStreams; iStream++) {
940 const char* fileName = ((TObjString*)
941 (fBkgrdFileNames->At(iStream-1)))->GetName();
942 manager->SetInputStream(iStream, fileName);
945 TString detStr = detectors;
946 TString detExcl = excludeDetectors;
947 manager->GetInputStream(0)->ImportgAlice();
948 AliRunLoader* runLoader =
949 AliRunLoader::GetRunLoader(manager->GetInputStream(0)->GetFolderName());
950 TObjArray* detArray = runLoader->GetAliRun()->Detectors();
951 for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
952 AliModule* det = (AliModule*) detArray->At(iDet);
953 if (!det || !det->IsActive()) continue;
954 if (IsSelected(det->GetName(), detStr) &&
955 !IsSelected(det->GetName(), detExcl)) {
956 AliDigitizer* digitizer = det->CreateDigitizer(manager);
959 AliError(Form("no digitizer for %s", det->GetName()));
960 if (fStopOnError) return kFALSE;
962 digitizer->SetRegionOfInterest(fRegionOfInterest);
967 if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
968 AliError(Form("the following detectors were not found: %s",
970 if (fStopOnError) return kFALSE;
973 if (!manager->GetListOfTasks()->IsEmpty()) {
974 AliInfo("executing digitization");
980 AliInfo(Form("Execution time: R:%.2fs C:%.2fs",
981 stopwatch.RealTime(),stopwatch.CpuTime()));
986 //_____________________________________________________________________________
987 Bool_t AliSimulation::RunHitsDigitization(const char* detectors)
989 // run the digitization and produce digits from hits
991 TStopwatch stopwatch;
994 AliRunLoader* runLoader = LoadRun("READ");
995 if (!runLoader) return kFALSE;
997 TString detStr = detectors;
998 TObjArray* detArray = runLoader->GetAliRun()->Detectors();
999 for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
1000 AliModule* det = (AliModule*) detArray->At(iDet);
1001 if (!det || !det->IsActive()) continue;
1002 if (IsSelected(det->GetName(), detStr)) {
1003 AliInfo(Form("creating digits from hits for %s", det->GetName()));
1008 if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
1009 AliError(Form("the following detectors were not found: %s",
1011 if (fStopOnError) return kFALSE;
1015 //PH Temporary fix to avoid interference with the PHOS loder/getter
1016 //PH The problem has to be solved in more general way 09/06/05
1018 AliInfo(Form("Execution time: R:%.2fs C:%.2fs",
1019 stopwatch.RealTime(),stopwatch.CpuTime()));
1024 //_____________________________________________________________________________
1025 Bool_t AliSimulation::WriteRawData(const char* detectors,
1026 const char* fileName,
1027 Bool_t deleteIntermediateFiles)
1029 // convert the digits to raw data
1030 // First DDL raw data files for the given detectors are created.
1031 // If a file name is given, the DDL files are then converted to a DATE file.
1032 // If deleteIntermediateFiles is true, the DDL raw files are deleted
1034 // If the file name has the extension ".root", the DATE file is converted
1036 // If deleteIntermediateFiles is true, the DATE file is deleted afterwards.
1038 TStopwatch stopwatch;
1041 if (!WriteRawFiles(detectors)) {
1042 if (fStopOnError) return kFALSE;
1045 TString dateFileName(fileName);
1046 if (!dateFileName.IsNull()) {
1047 Bool_t rootOutput = dateFileName.EndsWith(".root");
1048 if (rootOutput) dateFileName += ".date";
1049 if (!ConvertRawFilesToDate(dateFileName)) {
1050 if (fStopOnError) return kFALSE;
1052 if (deleteIntermediateFiles) {
1053 AliRunLoader* runLoader = LoadRun("READ");
1054 if (runLoader) for (Int_t iEvent = 0;
1055 iEvent < runLoader->GetNumberOfEvents(); iEvent++) {
1057 sprintf(command, "rm -r raw%d", iEvent);
1058 gSystem->Exec(command);
1063 if (!ConvertDateToRoot(dateFileName, fileName)) {
1064 if (fStopOnError) return kFALSE;
1066 if (deleteIntermediateFiles) {
1067 gSystem->Unlink(dateFileName);
1072 AliInfo(Form("Execution time: R:%.2fs C:%.2fs",
1073 stopwatch.RealTime(),stopwatch.CpuTime()));
1078 //_____________________________________________________________________________
1079 Bool_t AliSimulation::WriteRawFiles(const char* detectors)
1081 // convert the digits to raw data DDL files
1083 AliRunLoader* runLoader = LoadRun("READ");
1084 if (!runLoader) return kFALSE;
1086 // write raw data to DDL files
1087 for (Int_t iEvent = 0; iEvent < runLoader->GetNumberOfEvents(); iEvent++) {
1088 AliInfo(Form("processing event %d", iEvent));
1089 runLoader->GetEvent(iEvent);
1090 TString baseDir = gSystem->WorkingDirectory();
1092 sprintf(dirName, "raw%d", iEvent);
1093 gSystem->MakeDirectory(dirName);
1094 if (!gSystem->ChangeDirectory(dirName)) {
1095 AliError(Form("couldn't change to directory %s", dirName));
1096 if (fStopOnError) return kFALSE; else continue;
1099 TString detStr = detectors;
1100 TObjArray* detArray = runLoader->GetAliRun()->Detectors();
1101 for (Int_t iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
1102 AliModule* det = (AliModule*) detArray->At(iDet);
1103 if (!det || !det->IsActive()) continue;
1104 if (IsSelected(det->GetName(), detStr)) {
1105 AliInfo(Form("creating raw data from digits for %s", det->GetName()));
1110 if (!WriteTriggerRawData())
1111 if (fStopOnError) return kFALSE;
1113 gSystem->ChangeDirectory(baseDir);
1114 if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
1115 AliError(Form("the following detectors were not found: %s",
1117 if (fStopOnError) return kFALSE;
1125 //_____________________________________________________________________________
1126 Bool_t AliSimulation::ConvertRawFilesToDate(const char* dateFileName)
1128 // convert raw data DDL files to a DATE file with the program "dateStream"
1130 char* path = gSystem->Which(gSystem->Getenv("PATH"), "dateStream");
1132 AliError("the program dateStream was not found");
1133 if (fStopOnError) return kFALSE;
1138 AliRunLoader* runLoader = LoadRun("READ");
1139 if (!runLoader) return kFALSE;
1141 AliInfo(Form("converting raw data DDL files to DATE file %s", dateFileName));
1143 // Note the option -s. It is used in order to avoid
1144 // the generation of SOR/EOR events.
1145 sprintf(command, "dateStream -s -D -o %s -# %d -C",
1146 dateFileName, runLoader->GetNumberOfEvents());
1147 FILE* pipe = gSystem->OpenPipe(command, "w");
1149 for (Int_t iEvent = 0; iEvent < runLoader->GetNumberOfEvents(); iEvent++) {
1150 fprintf(pipe, "GDC\n");
1154 // loop over detectors and DDLs
1155 for (Int_t iDet = 0; iDet < AliDAQ::kNDetectors; iDet++) {
1156 for (Int_t iDDL = 0; iDDL < AliDAQ::NumberOfDdls(iDet); iDDL++) {
1158 Int_t ddlID = AliDAQ::DdlID(iDet,iDDL);
1159 Int_t ldcID = Int_t(ldc + 0.0001);
1160 ldc += AliDAQ::NumberOfLdcs(iDet) / AliDAQ::NumberOfDdls(iDet);
1162 char rawFileName[256];
1163 sprintf(rawFileName, "raw%d/%s",
1164 iEvent, AliDAQ::DdlFileName(iDet,iDDL));
1166 // check existence and size of raw data file
1167 FILE* file = fopen(rawFileName, "rb");
1168 if (!file) continue;
1169 fseek(file, 0, SEEK_END);
1170 unsigned long size = ftell(file);
1172 if (!size) continue;
1174 if (ldcID != prevLDC) {
1175 fprintf(pipe, " LDC Id %d\n", ldcID);
1178 fprintf(pipe, " Equipment Id %d Payload %s\n", ddlID, rawFileName);
1183 Int_t result = gSystem->ClosePipe(pipe);
1186 return (result == 0);
1189 //_____________________________________________________________________________
1190 Bool_t AliSimulation::ConvertDateToRoot(const char* dateFileName,
1191 const char* rootFileName)
1193 // convert a DATE file to a root file with the program "alimdc"
1196 const Int_t kDBSize = 2000000000;
1197 const Int_t kTagDBSize = 1000000000;
1198 const Bool_t kFilter = kFALSE;
1199 const Int_t kCompression = 0;
1201 char* path = gSystem->Which(gSystem->Getenv("PATH"), "alimdc");
1203 AliError("the program alimdc was not found");
1204 if (fStopOnError) return kFALSE;
1209 AliInfo(Form("converting DATE file %s to root file %s",
1210 dateFileName, rootFileName));
1212 const char* rawDBFS[2] = { "/tmp/mdc1", "/tmp/mdc2" };
1213 const char* tagDBFS = "/tmp/mdc1/tags";
1215 // User defined file system locations
1216 if (gSystem->Getenv("ALIMDC_RAWDB1"))
1217 rawDBFS[0] = gSystem->Getenv("ALIMDC_RAWDB1");
1218 if (gSystem->Getenv("ALIMDC_RAWDB2"))
1219 rawDBFS[1] = gSystem->Getenv("ALIMDC_RAWDB2");
1220 if (gSystem->Getenv("ALIMDC_TAGDB"))
1221 tagDBFS = gSystem->Getenv("ALIMDC_TAGDB");
1223 gSystem->Exec(Form("rm -rf %s",rawDBFS[0]));
1224 gSystem->Exec(Form("rm -rf %s",rawDBFS[1]));
1225 gSystem->Exec(Form("rm -rf %s",tagDBFS));
1227 gSystem->Exec(Form("mkdir %s",rawDBFS[0]));
1228 gSystem->Exec(Form("mkdir %s",rawDBFS[1]));
1229 gSystem->Exec(Form("mkdir %s",tagDBFS));
1231 Int_t result = gSystem->Exec(Form("alimdc %d %d %d %d %s",
1232 kDBSize, kTagDBSize, kFilter, kCompression, dateFileName));
1233 gSystem->Exec(Form("mv %s/*.root %s", rawDBFS[0], rootFileName));
1235 gSystem->Exec(Form("rm -rf %s",rawDBFS[0]));
1236 gSystem->Exec(Form("rm -rf %s",rawDBFS[1]));
1237 gSystem->Exec(Form("rm -rf %s",tagDBFS));
1239 return (result == 0);
1243 //_____________________________________________________________________________
1244 AliRunLoader* AliSimulation::LoadRun(const char* mode) const
1246 // delete existing run loaders, open a new one and load gAlice
1248 while (AliRunLoader::GetRunLoader()) delete AliRunLoader::GetRunLoader();
1249 AliRunLoader* runLoader =
1250 AliRunLoader::Open(fGAliceFileName.Data(),
1251 AliConfig::GetDefaultEventFolderName(), mode);
1253 AliError(Form("no run loader found in file %s", fGAliceFileName.Data()));
1256 runLoader->LoadgAlice();
1257 gAlice = runLoader->GetAliRun();
1259 AliError(Form("no gAlice object found in file %s",
1260 fGAliceFileName.Data()));
1266 //_____________________________________________________________________________
1267 Int_t AliSimulation::GetNSignalPerBkgrd(Int_t nEvents) const
1269 // get or calculate the number of signal events per background event
1271 if (!fBkgrdFileNames) return 1;
1272 Int_t nBkgrdFiles = fBkgrdFileNames->GetEntriesFast();
1273 if (nBkgrdFiles == 0) return 1;
1275 // get the number of signal events
1277 AliRunLoader* runLoader =
1278 AliRunLoader::Open(fGAliceFileName.Data(), "SIGNAL");
1279 if (!runLoader) return 1;
1281 nEvents = runLoader->GetNumberOfEvents();
1286 for (Int_t iBkgrdFile = 0; iBkgrdFile < nBkgrdFiles; iBkgrdFile++) {
1287 // get the number of background events
1288 const char* fileName = ((TObjString*)
1289 (fBkgrdFileNames->At(iBkgrdFile)))->GetName();
1290 AliRunLoader* runLoader =
1291 AliRunLoader::Open(fileName, "BKGRD");
1292 if (!runLoader) continue;
1293 Int_t nBkgrdEvents = runLoader->GetNumberOfEvents();
1296 // get or calculate the number of signal per background events
1297 Int_t nSignalPerBkgrd = fBkgrdFileNames->At(iBkgrdFile)->GetUniqueID();
1298 if (nSignalPerBkgrd <= 0) {
1299 nSignalPerBkgrd = (nEvents-1) / nBkgrdEvents + 1;
1300 } else if (result && (result != nSignalPerBkgrd)) {
1301 AliInfo(Form("the number of signal events per background event "
1302 "will be changed from %d to %d for stream %d",
1303 nSignalPerBkgrd, result, iBkgrdFile+1));
1304 nSignalPerBkgrd = result;
1307 if (!result) result = nSignalPerBkgrd;
1308 if (nSignalPerBkgrd * nBkgrdEvents < nEvents) {
1309 AliWarning(Form("not enough background events (%d) for %d signal events "
1310 "using %d signal per background events for stream %d",
1311 nBkgrdEvents, nEvents, nSignalPerBkgrd, iBkgrdFile+1));
1318 //_____________________________________________________________________________
1319 Bool_t AliSimulation::IsSelected(TString detName, TString& detectors) const
1321 // check whether detName is contained in detectors
1322 // if yes, it is removed from detectors
1324 // check if all detectors are selected
1325 if ((detectors.CompareTo("ALL") == 0) ||
1326 detectors.BeginsWith("ALL ") ||
1327 detectors.EndsWith(" ALL") ||
1328 detectors.Contains(" ALL ")) {
1333 // search for the given detector
1334 Bool_t result = kFALSE;
1335 if ((detectors.CompareTo(detName) == 0) ||
1336 detectors.BeginsWith(detName+" ") ||
1337 detectors.EndsWith(" "+detName) ||
1338 detectors.Contains(" "+detName+" ")) {
1339 detectors.ReplaceAll(detName, "");
1343 // clean up the detectors string
1344 while (detectors.Contains(" ")) detectors.ReplaceAll(" ", " ");
1345 while (detectors.BeginsWith(" ")) detectors.Remove(0, 1);
1346 while (detectors.EndsWith(" ")) detectors.Remove(detectors.Length()-1, 1);
1351 Bool_t AliSimulation::ConvertRaw2SDigits(const char* rawDirectory, const char* esdFileName)
1354 // Steering routine to convert raw data in directory rawDirectory/ to fake SDigits.
1355 // These can be used for embedding of MC tracks into RAW data using the standard
1356 // merging procedure.
1358 // If an ESD file is given the reconstructed vertex is taken from it and stored in the event header.
1361 AliError("no gAlice object. Restart aliroot and try again.");
1364 if (gAlice->Modules()->GetEntries() > 0) {
1365 AliError("gAlice was already run. Restart aliroot and try again.");
1369 AliInfo(Form("initializing gAlice with config file %s",fConfigFileName.Data()));
1370 StdoutToAliInfo(StderrToAliError(gAlice->Init(fConfigFileName.Data());););
1374 AliCDBManager* man = AliCDBManager::Instance();
1375 man->SetRun(0); // Should this come from rawdata header ?
1379 // Get the runloader
1380 AliRunLoader* runLoader = gAlice->GetRunLoader();
1382 // Open esd file if available
1383 TFile* esdFile = TFile::Open(esdFileName);
1384 Bool_t esdOK = (esdFile != 0);
1385 AliESD* esd = new AliESD;
1388 treeESD = (TTree*) esdFile->Get("esdTree");
1390 AliWarning("No ESD tree found");
1393 treeESD->SetBranchAddress("ESD", &esd);
1397 // Create the RawReader
1398 AliRawReaderFile* rawReader = new AliRawReaderFile(rawDirectory);
1400 // Get list of detectors
1401 TObjArray* detArray = runLoader->GetAliRun()->Detectors();
1404 AliHeader* header = runLoader->GetHeader();
1409 if (!(rawReader->NextEvent())) break;
1412 for (iDet = 0; iDet < detArray->GetEntriesFast(); iDet++) {
1413 AliModule* det = (AliModule*) detArray->At(iDet);
1414 AliInfo(Form("Calling Raw2SDigits for %s\n", det->GetName()));
1415 det->Raw2SDigits(rawReader);
1420 // If ESD information available obtain reconstructed vertex and store in header.
1422 treeESD->GetEvent(nev);
1423 const AliESDVertex* esdVertex = esd->GetPrimaryVertex();
1424 Double_t position[3];
1425 esdVertex->GetXYZ(position);
1426 AliGenEventHeader* mcHeader = new AliGenEventHeader("ESD");
1429 for (Int_t i = 0; i < 3; i++) mcV[i] = position[i];
1430 mcHeader->SetPrimaryVertex(mcV);
1431 header->Reset(0,nev);
1432 header->SetGenEventHeader(mcHeader);
1433 printf("***** Saved vertex %f %f %f \n", position[0], position[1], position[2]);
1438 runLoader->TreeE()->Fill();
1439 runLoader->SetNextEvent();
1445 runLoader->CdGAFile();
1446 runLoader->WriteHeader("OVERWRITE");
1447 runLoader->WriteRunLoader();