Fixed memory leak
[u/mrichter/AliRoot.git] / STEER / AliReconstruction.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 the reconstruction                                      //
21 //                                                                           //
22 // Clusters and tracks are created for all detectors and all events by       //
23 // typing:                                                                   //
24 //                                                                           //
25 //   AliReconstruction rec;                                                  //
26 //   rec.Run();                                                              //
27 //                                                                           //
28 // The Run method returns kTRUE in case of successful execution.             //
29 //                                                                           //
30 // If the input to the reconstruction are not simulated digits but raw data, //
31 // this can be specified by an argument of the Run method or by the method   //
32 //                                                                           //
33 //   rec.SetInput("...");                                                    //
34 //                                                                           //
35 // The input formats and the corresponding argument are:                     //
36 // - DDL raw data files: directory name, ends with "/"                       //
37 // - raw data root file: root file name, extension ".root"                   //
38 // - raw data DATE file: DATE file name, any other non-empty string          //
39 // - MC root files     : empty string, default                               //
40 //                                                                           //
41 // By default all events are reconstructed. The reconstruction can be        //
42 // limited to a range of events by giving the index of the first and the     //
43 // last event as an argument to the Run method or by calling                 //
44 //                                                                           //
45 //   rec.SetEventRange(..., ...);                                            //
46 //                                                                           //
47 // The index -1 (default) can be used for the last event to indicate no      //
48 // upper limit of the event range.                                           //
49 //                                                                           //
50 // In case of raw-data reconstruction the user can modify the default        //
51 // number of events per digits/clusters/tracks file. In case the option      //
52 // is not used the number is set 1. In case the user provides 0, than        //
53 // the number of events is equal to the number of events inside the          //
54 // raw-data file (i.e. one digits/clusters/tracks file):                     //
55 //                                                                           //
56 //   rec.SetNumberOfEventsPerFile(...);                                      //
57 //                                                                           //
58 //                                                                           //
59 // The name of the galice file can be changed from the default               //
60 // "galice.root" by passing it as argument to the AliReconstruction          //
61 // constructor or by                                                         //
62 //                                                                           //
63 //   rec.SetGAliceFile("...");                                               //
64 //                                                                           //
65 // The local reconstruction can be switched on or off for individual         //
66 // detectors by                                                              //
67 //                                                                           //
68 //   rec.SetRunLocalReconstruction("...");                                   //
69 //                                                                           //
70 // The argument is a (case sensitive) string with the names of the           //
71 // detectors separated by a space. The special string "ALL" selects all      //
72 // available detectors. This is the default.                                 //
73 //                                                                           //
74 // The reconstruction of the primary vertex position can be switched off by  //
75 //                                                                           //
76 //   rec.SetRunVertexFinder(kFALSE);                                         //
77 //                                                                           //
78 // The tracking and the creation of ESD tracks can be switched on for        //
79 // selected detectors by                                                     //
80 //                                                                           //
81 //   rec.SetRunTracking("...");                                              //
82 //                                                                           //
83 // Uniform/nonuniform field tracking switches (default: uniform field)       //
84 //                                                                           //
85 //   rec.SetUniformFieldTracking(); ( rec.SetUniformFieldTracking(kFALSE); ) //
86 //                                                                           //
87 // The filling of additional ESD information can be steered by               //
88 //                                                                           //
89 //   rec.SetFillESD("...");                                                  //
90 //                                                                           //
91 // Again, for both methods the string specifies the list of detectors.       //
92 // The default is "ALL".                                                     //
93 //                                                                           //
94 // The call of the shortcut method                                           //
95 //                                                                           //
96 //   rec.SetRunReconstruction("...");                                        //
97 //                                                                           //
98 // is equivalent to calling SetRunLocalReconstruction, SetRunTracking and    //
99 // SetFillESD with the same detector selecting string as argument.           //
100 //                                                                           //
101 // The reconstruction requires digits or raw data as input. For the creation //
102 // of digits and raw data have a look at the class AliSimulation.            //
103 //                                                                           //
104 // The input data of a detector can be replaced by the corresponding HLT     //
105 // data by calling (usual detector string)                                   //
106 // SetUseHLTData("...");                                                     //
107 //                                                                           //
108 // For debug purposes the method SetCheckPointLevel can be used. If the      //
109 // argument is greater than 0, files with ESD events will be written after   //
110 // selected steps of the reconstruction for each event:                      //
111 //   level 1: after tracking and after filling of ESD (final)                //
112 //   level 2: in addition after each tracking step                           //
113 //   level 3: in addition after the filling of ESD for each detector         //
114 // If a final check point file exists for an event, this event will be       //
115 // skipped in the reconstruction. The tracking and the filling of ESD for    //
116 // a detector will be skipped as well, if the corresponding check point      //
117 // file exists. The ESD event will then be loaded from the file instead.     //
118 //                                                                           //
119 ///////////////////////////////////////////////////////////////////////////////
120
121 #include <TArrayF.h>
122 #include <TFile.h>
123 #include <TList.h>
124 #include <TSystem.h>
125 #include <TROOT.h>
126 #include <TPluginManager.h>
127 #include <TGeoManager.h>
128 #include <TLorentzVector.h>
129 #include <TArrayS.h>
130 #include <TArrayD.h>
131 #include <TObjArray.h>
132
133 #include "AliReconstruction.h"
134 #include "AliCodeTimer.h"
135 #include "AliReconstructor.h"
136 #include "AliLog.h"
137 #include "AliRunLoader.h"
138 #include "AliRun.h"
139 #include "AliRawReaderFile.h"
140 #include "AliRawReaderDate.h"
141 #include "AliRawReaderRoot.h"
142 #include "AliRawEventHeaderBase.h"
143 #include "AliESDEvent.h"
144 #include "AliESDMuonTrack.h"
145 #include "AliESDfriend.h"
146 #include "AliESDVertex.h"
147 #include "AliESDcascade.h"
148 #include "AliESDkink.h"
149 #include "AliESDtrack.h"
150 #include "AliESDCaloCluster.h"
151 #include "AliESDCaloCells.h"
152 #include "AliMultiplicity.h"
153 #include "AliTracker.h"
154 #include "AliVertexer.h"
155 #include "AliVertexerTracks.h"
156 #include "AliV0vertexer.h"
157 #include "AliCascadeVertexer.h"
158 #include "AliHeader.h"
159 #include "AliGenEventHeader.h"
160 #include "AliPID.h"
161 #include "AliESDpid.h"
162 #include "AliESDtrack.h"
163 #include "AliESDPmdTrack.h"
164
165 #include "AliESDTagCreator.h"
166 #include "AliAODTagCreator.h"
167
168 #include "AliGeomManager.h"
169 #include "AliTrackPointArray.h"
170 #include "AliCDBManager.h"
171 #include "AliCDBStorage.h"
172 #include "AliCDBEntry.h"
173 #include "AliAlignObj.h"
174
175 #include "AliCentralTrigger.h"
176 #include "AliTriggerConfiguration.h"
177 #include "AliTriggerClass.h"
178 #include "AliCTPRawStream.h"
179
180 #include "AliQADataMakerRec.h" 
181 #include "AliGlobalQADataMaker.h" 
182 #include "AliQA.h"
183 #include "AliQADataMakerSteer.h"
184
185 #include "AliPlaneEff.h"
186
187 #include "AliSysInfo.h" // memory snapshots
188 #include "AliRawHLTManager.h"
189
190
191 ClassImp(AliReconstruction)
192
193
194 //_____________________________________________________________________________
195 const char* AliReconstruction::fgkDetectorName[AliReconstruction::fgkNDetectors] = {"ITS", "TPC", "TRD", "TOF", "PHOS", "HMPID", "EMCAL", "MUON", "FMD", "ZDC", "PMD", "T0", "VZERO", "ACORDE", "HLT"};
196
197 //_____________________________________________________________________________
198 AliReconstruction::AliReconstruction(const char* gAliceFilename,
199                                      const char* name, const char* title) :
200   TNamed(name, title),
201
202   fUniformField(kTRUE),
203   fRunVertexFinder(kTRUE),
204   fRunVertexFinderTracks(kTRUE),
205   fRunHLTTracking(kFALSE),
206   fRunMuonTracking(kFALSE),
207   fRunV0Finder(kTRUE),
208   fRunCascadeFinder(kTRUE),
209   fStopOnError(kFALSE),
210   fWriteAlignmentData(kFALSE),
211   fWriteESDfriend(kFALSE),
212   fWriteAOD(kFALSE),
213   fFillTriggerESD(kTRUE),
214
215   fCleanESD(kTRUE),
216   fV0DCAmax(3.),
217   fV0CsPmin(0.),
218   fDmax(50.),
219   fZmax(50.),
220
221   fRunLocalReconstruction("ALL"),
222   fRunTracking("ALL"),
223   fFillESD("ALL"),
224   fUseTrackingErrorsForAlignment(""),
225   fGAliceFileName(gAliceFilename),
226   fInput(""),
227   fpEvent(NULL),
228   fEquipIdMap(""),
229   fFirstEvent(0),
230   fLastEvent(-1),
231   fNumberOfEventsPerFile(1),
232   fCheckPointLevel(0),
233   fOptions(),
234   fLoadAlignFromCDB(kTRUE),
235   fLoadAlignData("ALL"),
236   fESDPar(""),
237   fUseHLTData(),
238
239   fRunLoader(NULL),
240   fRawReader(NULL),
241   fParentRawReader(NULL),
242
243   fVertexer(NULL),
244   fDiamondProfile(NULL),
245   fDiamondProfileTPC(NULL),
246   fMeanVertexConstraint(kTRUE),
247
248   fGRPList(NULL),
249
250   fAlignObjArray(NULL),
251   fCDBUri(),
252   fSpecCDBUri(), 
253   fInitCDBCalled(kFALSE),
254   fSetRunNumberFromDataCalled(kFALSE),
255   fRunQA(kTRUE),  
256   fRunGlobalQA(kTRUE),
257   fInLoopQA(kFALSE),
258
259   fRunPlaneEff(kFALSE),
260
261   fesd(NULL),
262   fhltesd(NULL),
263   fesdf(NULL),
264   ffile(NULL),
265   ftree(NULL),
266   fhlttree(NULL),
267   ffileOld(NULL),
268   ftreeOld(NULL),
269   fhlttreeOld(NULL),
270   ftVertexer(NULL),
271   fIsNewRunLoader(kFALSE)
272 {
273 // create reconstruction object with default parameters
274   
275   for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
276     fReconstructor[iDet] = NULL;
277     fLoader[iDet] = NULL;
278     fTracker[iDet] = NULL;
279     fQADataMaker[iDet] = NULL;
280         fQACycles[iDet] = 999999;       
281   }
282   fQADataMaker[fgkNDetectors]=NULL;  //Global QA
283   AliPID pid;
284 }
285
286 //_____________________________________________________________________________
287 AliReconstruction::AliReconstruction(const AliReconstruction& rec) :
288   TNamed(rec),
289
290   fUniformField(rec.fUniformField),
291   fRunVertexFinder(rec.fRunVertexFinder),
292   fRunVertexFinderTracks(rec.fRunVertexFinderTracks),
293   fRunHLTTracking(rec.fRunHLTTracking),
294   fRunMuonTracking(rec.fRunMuonTracking),
295   fRunV0Finder(rec.fRunV0Finder),
296   fRunCascadeFinder(rec.fRunCascadeFinder),
297   fStopOnError(rec.fStopOnError),
298   fWriteAlignmentData(rec.fWriteAlignmentData),
299   fWriteESDfriend(rec.fWriteESDfriend),
300   fWriteAOD(rec.fWriteAOD),
301   fFillTriggerESD(rec.fFillTriggerESD),
302
303   fCleanESD(rec.fCleanESD),
304   fV0DCAmax(rec.fV0DCAmax),
305   fV0CsPmin(rec.fV0CsPmin),
306   fDmax(rec.fDmax),
307   fZmax(rec.fZmax),
308
309   fRunLocalReconstruction(rec.fRunLocalReconstruction),
310   fRunTracking(rec.fRunTracking),
311   fFillESD(rec.fFillESD),
312   fUseTrackingErrorsForAlignment(rec.fUseTrackingErrorsForAlignment),
313   fGAliceFileName(rec.fGAliceFileName),
314   fInput(rec.fInput),
315   fpEvent(rec.fpEvent),
316   fEquipIdMap(rec.fEquipIdMap),
317   fFirstEvent(rec.fFirstEvent),
318   fLastEvent(rec.fLastEvent),
319   fNumberOfEventsPerFile(rec.fNumberOfEventsPerFile),
320   fCheckPointLevel(0),
321   fOptions(),
322   fLoadAlignFromCDB(rec.fLoadAlignFromCDB),
323   fLoadAlignData(rec.fLoadAlignData),
324   fESDPar(rec.fESDPar),
325   fUseHLTData(rec.fUseHLTData),
326
327   fRunLoader(NULL),
328   fRawReader(NULL),
329   fParentRawReader(NULL),
330
331   fVertexer(NULL),
332   fDiamondProfile(NULL),
333   fDiamondProfileTPC(NULL),
334   fMeanVertexConstraint(rec.fMeanVertexConstraint),
335
336   fGRPList(NULL),
337
338   fAlignObjArray(rec.fAlignObjArray),
339   fCDBUri(rec.fCDBUri),
340   fSpecCDBUri(), 
341   fInitCDBCalled(rec.fInitCDBCalled),
342   fSetRunNumberFromDataCalled(rec.fSetRunNumberFromDataCalled),
343   fRunQA(rec.fRunQA),  
344   fRunGlobalQA(rec.fRunGlobalQA),
345   fInLoopQA(rec.fInLoopQA),
346   fRunPlaneEff(rec.fRunPlaneEff),
347
348   fesd(NULL),
349   fhltesd(NULL),
350   fesdf(NULL),
351   ffile(NULL),
352   ftree(NULL),
353   fhlttree(NULL),
354   ffileOld(NULL),
355   ftreeOld(NULL),
356   fhlttreeOld(NULL),
357   ftVertexer(NULL),
358   fIsNewRunLoader(rec.fIsNewRunLoader)
359 {
360 // copy constructor
361
362   for (Int_t i = 0; i < rec.fOptions.GetEntriesFast(); i++) {
363     if (rec.fOptions[i]) fOptions.Add(rec.fOptions[i]->Clone());
364   }
365   for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
366     fReconstructor[iDet] = NULL;
367     fLoader[iDet] = NULL;
368     fTracker[iDet] = NULL;
369     fQADataMaker[iDet] = NULL;
370         fQACycles[iDet] = rec.fQACycles[iDet];  
371   }
372   fQADataMaker[fgkNDetectors]=NULL;  //Global QA
373   for (Int_t i = 0; i < rec.fSpecCDBUri.GetEntriesFast(); i++) {
374     if (rec.fSpecCDBUri[i]) fSpecCDBUri.Add(rec.fSpecCDBUri[i]->Clone());
375   }
376 }
377
378 //_____________________________________________________________________________
379 AliReconstruction& AliReconstruction::operator = (const AliReconstruction& rec)
380 {
381 // assignment operator
382
383   this->~AliReconstruction();
384   new(this) AliReconstruction(rec);
385   return *this;
386 }
387
388 //_____________________________________________________________________________
389 AliReconstruction::~AliReconstruction()
390 {
391 // clean up
392
393   CleanUp();
394   fOptions.Delete();
395   fSpecCDBUri.Delete();
396
397   AliCodeTimer::Instance()->Print();
398 }
399
400 //_____________________________________________________________________________
401 void AliReconstruction::InitCDB()
402 {
403 // activate a default CDB storage
404 // First check if we have any CDB storage set, because it is used 
405 // to retrieve the calibration and alignment constants
406
407   if (fInitCDBCalled) return;
408   fInitCDBCalled = kTRUE;
409
410   AliCDBManager* man = AliCDBManager::Instance();
411   if (man->IsDefaultStorageSet())
412   {
413     AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
414     AliWarning("Default CDB storage has been already set !");
415     AliWarning(Form("Ignoring the default storage declared in AliReconstruction: %s",fCDBUri.Data()));
416     AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
417     fCDBUri = man->GetDefaultStorage()->GetURI();
418   }
419   else {
420     if (fCDBUri.Length() > 0) 
421     {
422         AliDebug(2,"!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
423         AliDebug(2, Form("Default CDB storage is set to: %s", fCDBUri.Data()));
424         AliDebug(2, "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
425     } else {
426         fCDBUri="local://$ALICE_ROOT";
427         AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
428         AliWarning("Default CDB storage not yet set !!!!");
429         AliWarning(Form("Setting it now to: %s", fCDBUri.Data()));
430         AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
431                 
432     }
433     man->SetDefaultStorage(fCDBUri);
434   }
435
436   // Now activate the detector specific CDB storage locations
437   for (Int_t i = 0; i < fSpecCDBUri.GetEntriesFast(); i++) {
438     TObject* obj = fSpecCDBUri[i];
439     if (!obj) continue;
440     AliDebug(2, "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
441     AliDebug(2, Form("Specific CDB storage for %s is set to: %s",obj->GetName(),obj->GetTitle()));
442     AliDebug(2, "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
443     man->SetSpecificStorage(obj->GetName(), obj->GetTitle());
444   }
445   
446 }
447
448 //_____________________________________________________________________________
449 void AliReconstruction::SetDefaultStorage(const char* uri) {
450 // Store the desired default CDB storage location
451 // Activate it later within the Run() method
452
453   fCDBUri = uri;
454
455 }
456
457 //_____________________________________________________________________________
458 void AliReconstruction::SetSpecificStorage(const char* calibType, const char* uri) {
459 // Store a detector-specific CDB storage location
460 // Activate it later within the Run() method
461
462   AliCDBPath aPath(calibType);
463   if(!aPath.IsValid()){
464         // if calibType is not wildcard but it is a valid detector, add "/*" to make it a valid path
465         for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
466                 if(!strcmp(calibType, fgkDetectorName[iDet])) {
467                         aPath.SetPath(Form("%s/*", calibType));
468                         AliInfo(Form("Path for specific storage set to %s", aPath.GetPath().Data()));
469                         break;
470                 }
471         }
472         if(!aPath.IsValid()){
473                 AliError(Form("Not a valid path or detector: %s", calibType));
474                 return;
475         }
476   }
477
478 //  // check that calibType refers to a "valid" detector name
479 //  Bool_t isDetector = kFALSE;
480 //  for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
481 //    TString detName = fgkDetectorName[iDet];
482 //    if(aPath.GetLevel0() == detName) {
483 //      isDetector = kTRUE;
484 //      break;
485 //    }
486 //  }
487 //
488 //  if(!isDetector) {
489 //      AliError(Form("Not a valid detector: %s", aPath.GetLevel0().Data()));
490 //      return;
491 //  }
492
493   TObject* obj = fSpecCDBUri.FindObject(aPath.GetPath().Data());
494   if (obj) fSpecCDBUri.Remove(obj);
495   fSpecCDBUri.Add(new TNamed(aPath.GetPath().Data(), uri));
496
497 }
498
499 //_____________________________________________________________________________
500 Bool_t AliReconstruction::SetRunNumberFromData()
501 {
502   // The method is called in Run() in order
503   // to set a correct run number.
504   // In case of raw data reconstruction the
505   // run number is taken from the raw data header
506
507   if (fSetRunNumberFromDataCalled) return kTRUE;
508   fSetRunNumberFromDataCalled = kTRUE;
509   
510   AliCDBManager* man = AliCDBManager::Instance();
511   
512   if(man->GetRun() > 0) {
513         AliWarning("Run number is taken from raw-event header! Ignoring settings in AliCDBManager!");
514   } 
515   
516   if (!fRunLoader) {
517       AliError("No run loader is found !"); 
518       return kFALSE;
519     }
520     // read run number from gAlice
521     if(fRunLoader->GetAliRun())
522       AliCDBManager::Instance()->SetRun(fRunLoader->GetHeader()->GetRun());
523     else {
524       if(fRawReader) {
525         if(fRawReader->NextEvent()) {
526           AliCDBManager::Instance()->SetRun(fRawReader->GetRunNumber());
527           fRawReader->RewindEvents();
528         }
529         else {
530           if(man->GetRun() > 0) {
531             AliWarning("No raw events is found ! Using settings in AliCDBManager !");
532             man->Print();  
533             return kTRUE;
534           }
535           else {
536             AliWarning("Neither raw events nor settings in AliCDBManager are found !");
537             return kFALSE;
538           }
539         }
540       }
541       else {
542         AliError("Neither gAlice nor RawReader objects are found !");
543         return kFALSE;
544       }
545   }
546
547   man->Print();  
548   
549   return kTRUE;
550 }
551
552 //_____________________________________________________________________________
553 void AliReconstruction::SetCDBLock() {
554   // Set CDB lock: from now on it is forbidden to reset the run number
555   // or the default storage or to activate any further storage!
556   
557   AliCDBManager::Instance()->SetLock(1);
558 }
559
560 //_____________________________________________________________________________
561 Bool_t AliReconstruction::MisalignGeometry(const TString& detectors)
562 {
563   // Read the alignment objects from CDB.
564   // Each detector is supposed to have the
565   // alignment objects in DET/Align/Data CDB path.
566   // All the detector objects are then collected,
567   // sorted by geometry level (starting from ALIC) and
568   // then applied to the TGeo geometry.
569   // Finally an overlaps check is performed.
570
571   // Load alignment data from CDB and fill fAlignObjArray 
572   if(fLoadAlignFromCDB){
573         
574     TString detStr = detectors;
575     TString loadAlObjsListOfDets = "";
576     
577     for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
578       if (!IsSelected(fgkDetectorName[iDet], detStr)) continue;
579       loadAlObjsListOfDets += fgkDetectorName[iDet];
580       loadAlObjsListOfDets += " ";
581     } // end loop over detectors
582     loadAlObjsListOfDets.Prepend("GRP "); //add alignment objects for non-sensitive modules
583     AliGeomManager::ApplyAlignObjsFromCDB(loadAlObjsListOfDets.Data());
584   }else{
585     // Check if the array with alignment objects was
586     // provided by the user. If yes, apply the objects
587     // to the present TGeo geometry
588     if (fAlignObjArray) {
589       if (gGeoManager && gGeoManager->IsClosed()) {
590         if (AliGeomManager::ApplyAlignObjsToGeom(*fAlignObjArray) == kFALSE) {
591           AliError("The misalignment of one or more volumes failed!"
592                    "Compare the list of simulated detectors and the list of detector alignment data!");
593           return kFALSE;
594         }
595       }
596       else {
597         AliError("Can't apply the misalignment! gGeoManager doesn't exist or it is still opened!");
598         return kFALSE;
599       }
600     }
601   }
602   
603   delete fAlignObjArray; fAlignObjArray=0;
604
605   return kTRUE;
606 }
607
608 //_____________________________________________________________________________
609 void AliReconstruction::SetGAliceFile(const char* fileName)
610 {
611 // set the name of the galice file
612
613   fGAliceFileName = fileName;
614 }
615
616 //_____________________________________________________________________________
617 void AliReconstruction::SetInput(const char* input,void **pEvent) 
618 {
619   // In case event pointer is given, we run in an online mode
620   // and the first argument is ignored.
621   // In case event pointer is NULL, we run in a normal
622   // mode over a raw-data file and the first argument points
623   // to the name of that file
624   if (!pEvent) {
625     fInput = input;
626     fpEvent = NULL;
627   }
628   else {
629     fInput = "";
630     fpEvent = pEvent;
631   }
632 }
633
634 //_____________________________________________________________________________
635 void AliReconstruction::SetOption(const char* detector, const char* option)
636 {
637 // set options for the reconstruction of a detector
638
639   TObject* obj = fOptions.FindObject(detector);
640   if (obj) fOptions.Remove(obj);
641   fOptions.Add(new TNamed(detector, option));
642 }
643
644 //_____________________________________________________________________________
645 Bool_t AliReconstruction::Run(const char* input)
646 {
647   // Run Run Run
648   AliCodeTimerAuto("");
649
650   if (!InitRun(input)) return kFALSE;
651   
652   //******* The loop over events
653   Int_t iEvent = 0;
654   while ((iEvent < fRunLoader->GetNumberOfEvents()) ||
655          (fRawReader && fRawReader->NextEvent())) {
656     if (!RunEvent(iEvent)) return kFALSE;
657     iEvent++;
658   }
659
660   if (!FinishRun()) return kFALSE;
661
662   return kTRUE;
663 }
664
665 //_____________________________________________________________________________
666 Bool_t AliReconstruction::InitRun(const char* input, void **pEvent)
667 {
668   // Initialize all the stuff before
669   // going into the event loop
670   // If the second argument is given, the first one is ignored and
671   // the reconstruction works in an online mode
672   AliCodeTimerAuto("");
673
674   if (pEvent) fpEvent = pEvent;
675   if (input) fInput = input;
676
677   // set the input in case of raw data
678   if (!fInput.IsNull() || fpEvent) {
679     if (!fInput.IsNull()) {
680       AliInfo(Form("Reconstruction will run over a raw-data file: %s",fInput.Data()));
681       TString fileName(fInput);
682       if (fInput.EndsWith("/")) {
683         fRawReader = new AliRawReaderFile(fInput);
684       } else if (fInput.EndsWith(".root")) {
685         fRawReader = new AliRawReaderRoot(fInput);
686       } else {
687         fRawReader = new AliRawReaderDate(fInput);
688       }
689     }
690     else {
691       AliInfo(Form("Reconstruction will run over an event in memory at: %p",*fpEvent));
692       fRawReader = new AliRawReaderDate((void *)(*fpEvent));
693     }
694   }
695   else {
696     AliInfo("Reconstruction will run over digits");
697   }
698
699   if (!fEquipIdMap.IsNull() && fRawReader)
700     fRawReader->LoadEquipmentIdsMap(fEquipIdMap);
701
702   if (!fUseHLTData.IsNull()) {
703     // create the RawReaderHLT which performs redirection of HLT input data for
704     // the specified detectors
705     AliRawReader* pRawReader=AliRawHLTManager::CreateRawReaderHLT(fRawReader, fUseHLTData.Data());
706     if (pRawReader) {
707       fParentRawReader=fRawReader;
708       fRawReader=pRawReader;
709     } else {
710       AliError(Form("can not create Raw Reader for HLT input %s", fUseHLTData.Data()));
711     }
712   }
713
714    AliSysInfo::AddStamp("Start");
715   // get the run loader
716   if (!InitRunLoader()) return kFALSE;
717    AliSysInfo::AddStamp("LoadLoader");
718
719   // Initialize the CDB storage
720   InitCDB();
721   
722   AliSysInfo::AddStamp("LoadCDB");
723
724   // Set run number in CDBManager (if it is not already set by the user)
725   if (!SetRunNumberFromData()) if (fStopOnError) return kFALSE;
726   
727   // Set CDB lock: from now on it is forbidden to reset the run number
728   // or the default storage or to activate any further storage!
729   SetCDBLock();
730   
731   // Import ideal TGeo geometry and apply misalignment
732   if (!gGeoManager) {
733     TString geom(gSystem->DirName(fGAliceFileName));
734     geom += "/geometry.root";
735     AliGeomManager::LoadGeometry(geom.Data());
736     if (!gGeoManager) if (fStopOnError) return kFALSE;
737   }
738
739   if (!MisalignGeometry(fLoadAlignData)) if (fStopOnError) return kFALSE;
740    AliSysInfo::AddStamp("LoadGeom");
741
742   //QA
743   AliQADataMakerSteer qas ; 
744   if (fRunQA && fRawReader) { 
745     qas.Run(fRunLocalReconstruction, fRawReader) ; 
746   }
747   // checking the QA of previous steps
748   //CheckQA() ; 
749  
750   /*
751   // local reconstruction
752   if (!fRunLocalReconstruction.IsNull()) {
753     if (!RunLocalReconstruction(fRunLocalReconstruction)) {
754       if (fStopOnError) {CleanUp(); return kFALSE;}
755     }
756   }
757   */
758
759   // get vertexer
760   if (fRunVertexFinder && !CreateVertexer()) {
761     if (fStopOnError) {
762       CleanUp(); 
763       return kFALSE;
764     }
765   }
766    AliSysInfo::AddStamp("Vertexer");
767
768   // get trackers
769   if (!fRunTracking.IsNull() && !CreateTrackers(fRunTracking)) {
770     if (fStopOnError) {
771       CleanUp(); 
772       return kFALSE;
773     }      
774   }
775    AliSysInfo::AddStamp("LoadTrackers");
776
777   // get the possibly already existing ESD file and tree
778   fesd = new AliESDEvent(); fhltesd = new AliESDEvent();
779   if (!gSystem->AccessPathName("AliESDs.root")){
780     gSystem->CopyFile("AliESDs.root", "AliESDs.old.root", kTRUE);
781     ffileOld = TFile::Open("AliESDs.old.root");
782     if (ffileOld && ffileOld->IsOpen()) {
783       ftreeOld = (TTree*) ffileOld->Get("esdTree");
784       if (ftreeOld)fesd->ReadFromTree(ftreeOld);
785       fhlttreeOld = (TTree*) ffileOld->Get("HLTesdTree");
786       if (fhlttreeOld)  fhltesd->ReadFromTree(fhlttreeOld);
787     }
788   }
789
790   // create the ESD output file and tree
791   ffile = TFile::Open("AliESDs.root", "RECREATE");
792   ffile->SetCompressionLevel(2);
793   if (!ffile->IsOpen()) {
794     AliError("opening AliESDs.root failed");
795     if (fStopOnError) {CleanUp(ffile, ffileOld); return kFALSE;}    
796   }
797
798   ftree = new TTree("esdTree", "Tree with ESD objects");
799   fesd = new AliESDEvent();
800   fesd->CreateStdContent();
801   fesd->WriteToTree(ftree);
802
803   fhlttree = new TTree("HLTesdTree", "Tree with HLT ESD objects");
804   fhltesd = new AliESDEvent();
805   fhltesd->CreateStdContent();
806   fhltesd->WriteToTree(fhlttree);
807
808   /* CKB Why?
809   delete esd; delete hltesd;
810   esd = NULL; hltesd = NULL;
811   */
812   // create the branch with ESD additions
813
814
815
816   if (fWriteESDfriend) {
817     fesdf = new AliESDfriend();
818     TBranch *br=ftree->Branch("ESDfriend.","AliESDfriend", &fesdf);
819     br->SetFile("AliESDfriends.root");
820     fesd->AddObject(fesdf);
821   }
822
823   
824   // Get the GRP CDB entry
825   AliCDBEntry* entryGRP = AliCDBManager::Instance()->Get("GRP/GRP/Data");
826         
827   if(entryGRP) {
828         fGRPList = dynamic_cast<TList*> (entryGRP->GetObject());  
829   } else {
830         AliError("No GRP entry found in OCDB!");
831   }
832
833   // Get the diamond profile from OCDB
834   AliCDBEntry* entry = AliCDBManager::Instance()
835         ->Get("GRP/Calib/MeanVertex");
836         
837   if(entry) {
838         fDiamondProfile = dynamic_cast<AliESDVertex*> (entry->GetObject());  
839   } else {
840         AliError("No diamond profile found in OCDB!");
841   }
842
843   entry = 0;
844   entry = AliCDBManager::Instance()
845         ->Get("GRP/Calib/MeanVertexTPC");
846         
847   if(entry) {
848         fDiamondProfileTPC = dynamic_cast<AliESDVertex*> (entry->GetObject());  
849   } else {
850         AliError("No diamond profile found in OCDB!");
851   }
852
853   ftVertexer = new AliVertexerTracks(AliTracker::GetBz());
854   if(fDiamondProfile && fMeanVertexConstraint) ftVertexer->SetVtxStart(fDiamondProfile);
855
856   if (fRawReader) fRawReader->RewindEvents();
857
858   ProcInfo_t ProcInfo;
859   gSystem->GetProcInfo(&ProcInfo);
860   AliInfo(Form("Current memory usage %d %d", ProcInfo.fMemResident, ProcInfo.fMemVirtual));
861   
862
863   //Initialize the QA and start of cycle for out-of-cycle QA
864   if (fRunQA) {
865      TString detStr(fFillESD); 
866      for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
867         if (!IsSelected(fgkDetectorName[iDet], detStr)) continue;
868         AliQADataMakerRec *qadm = GetQADataMaker(iDet);  
869         if (!qadm) continue;
870         AliInfo(Form("Initializing the QA data maker for %s", 
871                fgkDetectorName[iDet]));
872         qadm->Init(AliQA::kRECPOINTS, AliCDBManager::Instance()->GetRun());
873         qadm->Init(AliQA::kESDS, AliCDBManager::Instance()->GetRun());
874  //       if (!fInLoopQA) {
875 //           qadm->StartOfCycle(AliQA::kRECPOINTS);
876 //           qadm->StartOfCycle(AliQA::kESDS,"same");
877 //        }
878      }
879   }
880   if (fRunGlobalQA) {
881           AliQADataMakerRec *qadm = GetQADataMaker(AliQA::kGLOBAL);
882      AliInfo(Form("Initializing the global QA data maker"));
883      TObjArray *arr=
884           qadm->Init(AliQA::kRECPOINTS, AliCDBManager::Instance()->GetRun());
885      AliTracker::SetResidualsArray(arr);
886      qadm->Init(AliQA::kESDS, AliCDBManager::Instance()->GetRun());
887      if (!fInLoopQA) {
888         qadm->StartOfCycle(AliQA::kRECPOINTS, (fRunQA && fRawReader));
889         qadm->StartOfCycle(AliQA::kESDS, "same");
890      }
891   }
892
893   //Initialize the Plane Efficiency framework
894   if (fRunPlaneEff && !InitPlaneEff()) {
895     if(fStopOnError) {CleanUp(ffile, ffileOld); return kFALSE;}
896   }
897
898   return kTRUE;
899 }
900
901 //_____________________________________________________________________________
902 Bool_t AliReconstruction::RunEvent(Int_t iEvent)
903 {
904   // run the reconstruction over a single event
905   // The event loop is steered in Run method
906
907   AliCodeTimerAuto("");
908
909   if (iEvent >= fRunLoader->GetNumberOfEvents()) {
910     fRunLoader->SetEventNumber(iEvent);
911     fRunLoader->GetHeader()->Reset(fRawReader->GetRunNumber(), 
912                                    iEvent, iEvent);
913     //??      fRunLoader->MakeTree("H");
914     fRunLoader->TreeE()->Fill();
915   }
916
917   if ((iEvent < fFirstEvent) || ((fLastEvent >= 0) && (iEvent > fLastEvent))) {
918     // copy old ESD to the new one
919     if (ftreeOld) {
920       fesd->ReadFromTree(ftreeOld);
921       ftreeOld->GetEntry(iEvent);
922       ftree->Fill();
923     }
924     if (fhlttreeOld) {
925       fesd->ReadFromTree(fhlttreeOld);
926       fhlttreeOld->GetEntry(iEvent);
927       fhlttree->Fill();
928     }
929     return kTRUE;
930   }
931
932   AliInfo(Form("processing event %d", iEvent));
933
934     //Start of cycle for the in-loop QA
935     if (fInLoopQA) {
936        if (fRunQA) {
937           TString detStr(fFillESD); 
938           for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
939              if (!IsSelected(fgkDetectorName[iDet], detStr)) continue;
940              AliQADataMakerRec *qadm = GetQADataMaker(iDet);  
941              if (!qadm) continue;
942              qadm->StartOfCycle(AliQA::kRECPOINTS, (fRunQA && fRawReader));
943              qadm->StartOfCycle(AliQA::kESDS, "same") ;         
944           }
945        }
946        if (fRunGlobalQA) {
947           AliQADataMakerRec *qadm = GetQADataMaker(AliQA::kGLOBAL);
948           qadm->StartOfCycle(AliQA::kRECPOINTS, (fRunQA && fRawReader));
949           qadm->StartOfCycle(AliQA::kESDS, "same");
950        }
951     }
952
953     fRunLoader->GetEvent(iEvent);
954
955     char aFileName[256];
956     sprintf(aFileName, "ESD_%d.%d_final.root", 
957             fRunLoader->GetHeader()->GetRun(), 
958             fRunLoader->GetHeader()->GetEventNrInRun());
959     if (!gSystem->AccessPathName(aFileName)) return kTRUE;
960
961     // local signle event reconstruction
962     if (!fRunLocalReconstruction.IsNull()) {
963       if (!RunLocalEventReconstruction(fRunLocalReconstruction)) {
964         if (fStopOnError) {CleanUp(ffile, ffileOld); return kFALSE;}
965       }
966     }
967
968     fesd->SetRunNumber(fRunLoader->GetHeader()->GetRun());
969     fhltesd->SetRunNumber(fRunLoader->GetHeader()->GetRun());
970     fesd->SetEventNumberInFile(fRunLoader->GetHeader()->GetEventNrInRun());
971     fhltesd->SetEventNumberInFile(fRunLoader->GetHeader()->GetEventNrInRun());
972     
973     // Set magnetic field from the tracker
974     fesd->SetMagneticField(AliTracker::GetBz());
975     fhltesd->SetMagneticField(AliTracker::GetBz());
976
977     
978     
979     // Fill raw-data error log into the ESD
980     if (fRawReader) FillRawDataErrorLog(iEvent,fesd);
981
982     // vertex finder
983     if (fRunVertexFinder) {
984       if (!ReadESD(fesd, "vertex")) {
985         if (!RunVertexFinder(fesd)) {
986           if (fStopOnError) {CleanUp(ffile, ffileOld); return kFALSE;}
987         }
988         if (fCheckPointLevel > 0) WriteESD(fesd, "vertex");
989       }
990     }
991
992     // HLT tracking
993     if (!fRunTracking.IsNull()) {
994       if (fRunHLTTracking) {
995         fhltesd->SetPrimaryVertexSPD(fesd->GetVertex());
996         if (!RunHLTTracking(fhltesd)) {
997           if (fStopOnError) {CleanUp(ffile, ffileOld); return kFALSE;}
998         }
999       }
1000     }
1001
1002     // Muon tracking
1003     if (!fRunTracking.IsNull()) {
1004       if (fRunMuonTracking) {
1005         if (!RunMuonTracking(fesd)) {
1006           if (fStopOnError) {CleanUp(ffile, ffileOld); return kFALSE;}
1007         }
1008       }
1009     }
1010
1011     // barrel tracking
1012     if (!fRunTracking.IsNull()) {
1013       if (!ReadESD(fesd, "tracking")) {
1014         if (!RunTracking(fesd)) {
1015           if (fStopOnError) {CleanUp(ffile, ffileOld); return kFALSE;}
1016         }
1017         if (fCheckPointLevel > 0) WriteESD(fesd, "tracking");
1018       }
1019     }
1020
1021     // fill ESD
1022     if (!fFillESD.IsNull()) {
1023       if (!FillESD(fesd, fFillESD)) {
1024         if (fStopOnError) {CleanUp(ffile, ffileOld); return kFALSE;}
1025       }
1026     }
1027   
1028     // fill Event header information from the RawEventHeader
1029     if (fRawReader){FillRawEventHeaderESD(fesd);}
1030
1031     // combined PID
1032     AliESDpid::MakePID(fesd);
1033     if (fCheckPointLevel > 1) WriteESD(fesd, "PID");
1034
1035     if (fFillTriggerESD) {
1036       if (!ReadESD(fesd, "trigger")) {
1037         if (!FillTriggerESD(fesd)) {
1038           if (fStopOnError) {CleanUp(ffile, ffileOld); return kFALSE;}
1039         }
1040         if (fCheckPointLevel > 1) WriteESD(fesd, "trigger");
1041       }
1042     }
1043
1044     ffile->cd();
1045
1046     //
1047     // Propagate track to the beam pipe  (if not laready done by ITS)
1048     //
1049     const Int_t ntracks = fesd->GetNumberOfTracks();
1050     const Double_t kBz = fesd->GetMagneticField();
1051     const Double_t kRadius  = 2.8; //something less than the beam pipe radius
1052
1053     TObjArray trkArray;
1054     UShort_t *selectedIdx=new UShort_t[ntracks];
1055
1056     for (Int_t itrack=0; itrack<ntracks; itrack++){
1057       const Double_t kMaxStep = 5;   //max step over the material
1058       Bool_t ok;
1059
1060       AliESDtrack *track = fesd->GetTrack(itrack);
1061       if (!track) continue;
1062
1063       AliExternalTrackParam *tpcTrack =
1064            (AliExternalTrackParam *)track->GetTPCInnerParam();
1065       ok = kFALSE;
1066       if (tpcTrack)
1067         ok = AliTracker::
1068           PropagateTrackTo(tpcTrack,kRadius,track->GetMass(),kMaxStep,kTRUE);
1069
1070
1071
1072       if (ok) {
1073         Int_t n=trkArray.GetEntriesFast();
1074         selectedIdx[n]=track->GetID();
1075         trkArray.AddLast(tpcTrack);
1076       }
1077
1078       if (track->GetX() < kRadius) continue;
1079
1080       ok = AliTracker::
1081            PropagateTrackTo(track,kRadius,track->GetMass(),kMaxStep,kTRUE);
1082       if (ok) {
1083          track->RelateToVertex(fesd->GetPrimaryVertexSPD(), kBz, kRadius);
1084       }
1085     }
1086
1087     //
1088     // Improve the reconstructed primary vertex position using the tracks
1089     //
1090     TObject *obj = fOptions.FindObject("ITS");
1091     if (obj) {
1092       TString optITS = obj->GetTitle();
1093       if (optITS.Contains("cosmics") || optITS.Contains("COSMICS")) 
1094         fRunVertexFinderTracks=kFALSE;
1095     }
1096     if (fRunVertexFinderTracks) {
1097        // TPC + ITS primary vertex
1098        ftVertexer->SetITSrefitRequired();
1099        if(fDiamondProfile && fMeanVertexConstraint) {
1100          ftVertexer->SetVtxStart(fDiamondProfile);
1101        } else {
1102          ftVertexer->SetConstraintOff();
1103        }
1104        AliESDVertex *pvtx=ftVertexer->FindPrimaryVertex(fesd);
1105        if (pvtx) {
1106           if (pvtx->GetStatus()) {
1107              fesd->SetPrimaryVertex(pvtx);
1108              for (Int_t i=0; i<ntracks; i++) {
1109                  AliESDtrack *t = fesd->GetTrack(i);
1110                  t->RelateToVertex(pvtx, kBz, kRadius);
1111              } 
1112           }
1113        }
1114
1115        // TPC-only primary vertex
1116        ftVertexer->SetITSrefitNotRequired();
1117        if(fDiamondProfileTPC && fMeanVertexConstraint) {
1118          ftVertexer->SetVtxStart(fDiamondProfileTPC);
1119        } else {
1120          ftVertexer->SetConstraintOff();
1121        }
1122        pvtx=ftVertexer->FindPrimaryVertex(&trkArray,selectedIdx);
1123        if (pvtx) {
1124           if (pvtx->GetStatus()) {
1125              fesd->SetPrimaryVertexTPC(pvtx);
1126              Int_t nsel=trkArray.GetEntriesFast();
1127              for (Int_t i=0; i<nsel; i++) {
1128                  AliExternalTrackParam *t = 
1129                    (AliExternalTrackParam *)trkArray.UncheckedAt(i);
1130                  t->PropagateToDCA(pvtx, kBz, kRadius);
1131              } 
1132           }
1133        }
1134
1135     }
1136     delete[] selectedIdx;
1137
1138     if(fDiamondProfile) fesd->SetDiamond(fDiamondProfile);
1139     
1140
1141     if (fRunV0Finder) {
1142        // V0 finding
1143        AliV0vertexer vtxer;
1144        vtxer.Tracks2V0vertices(fesd);
1145
1146        if (fRunCascadeFinder) {
1147           // Cascade finding
1148           AliCascadeVertexer cvtxer;
1149           cvtxer.V0sTracks2CascadeVertices(fesd);
1150        }
1151     }
1152  
1153     // write ESD
1154     if (fCleanESD) CleanESD(fesd);
1155
1156     if (fRunGlobalQA) {
1157        AliQADataMakerRec *qadm = GetQADataMaker(AliQA::kGLOBAL);
1158        if (qadm) qadm->Exec(AliQA::kESDS, fesd);
1159     }
1160
1161     if (fWriteESDfriend) {
1162       fesdf->~AliESDfriend();
1163       new (fesdf) AliESDfriend(); // Reset...
1164       fesd->GetESDfriend(fesdf);
1165     }
1166     ftree->Fill();
1167
1168     // write HLT ESD
1169     fhlttree->Fill();
1170
1171     if (fCheckPointLevel > 0)  WriteESD(fesd, "final"); 
1172     fesd->Reset();
1173     fhltesd->Reset();
1174     if (fWriteESDfriend) {
1175       fesdf->~AliESDfriend();
1176       new (fesdf) AliESDfriend(); // Reset...
1177     }
1178  
1179     ProcInfo_t ProcInfo;
1180     gSystem->GetProcInfo(&ProcInfo);
1181     AliInfo(Form("Event %d -> Current memory usage %d %d",iEvent, ProcInfo.fMemResident, ProcInfo.fMemVirtual));
1182   
1183
1184   // End of cycle for the in-loop QA
1185      if (fInLoopQA) {
1186         if (fRunQA) {
1187            RunQA(fFillESD.Data(), fesd);
1188            TString detStr(fFillESD); 
1189            for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
1190                            if (!IsSelected(fgkDetectorName[iDet], detStr)) 
1191                                    continue;
1192                            AliQADataMakerRec * qadm = GetQADataMaker(iDet);
1193                            if (!qadm) 
1194                                    continue;
1195                            qadm->EndOfCycle(AliQA::kRECPOINTS);
1196                            qadm->EndOfCycle(AliQA::kESDS);
1197                            qadm->Finish();
1198                    }
1199         }
1200         if (fRunGlobalQA) {
1201            AliQADataMakerRec *qadm = GetQADataMaker(AliQA::kGLOBAL);
1202            if (qadm) {
1203               qadm->EndOfCycle(AliQA::kRECPOINTS);
1204               qadm->EndOfCycle(AliQA::kESDS);
1205               qadm->Finish();
1206            }
1207         }
1208      }
1209
1210      return kTRUE;
1211 }
1212
1213 //_____________________________________________________________________________
1214 Bool_t AliReconstruction::AddEventAndRun()
1215 {
1216   // for online usage only
1217   // Add an event to the run-loader
1218   // and
1219   // re-creates AliRawReaderDate for this new event
1220   AliCodeTimerAuto("");
1221
1222   if (!fpEvent) {
1223     AliError("No raw-data event in memory given as an input! Do nothing!");
1224     return kFALSE;
1225   }
1226
1227   // New raw-reader. Could be redone in a better way... To do
1228   fRawReader->~AliRawReader();
1229   new (fRawReader) AliRawReaderDate((void*)(*fpEvent));
1230   if (!fRawReader->NextEvent()) return kFALSE;
1231
1232   // Expand the number of events in the run-loader
1233
1234   Int_t nEvents = fRunLoader->GetNumberOfEvents();
1235
1236   return RunEvent(nEvents);
1237 }
1238
1239 //_____________________________________________________________________________
1240 Bool_t AliReconstruction::FinishRun()
1241 {
1242   // Finalize the run
1243   // Called after the exit
1244   // from the event loop
1245   AliCodeTimerAuto("");
1246
1247   if (fIsNewRunLoader) { // galice.root didn't exist
1248     fRunLoader->WriteHeader("OVERWRITE");
1249     fRunLoader->CdGAFile();
1250     fRunLoader->Write(0, TObject::kOverwrite);
1251   }
1252
1253   ftree->GetUserInfo()->Add(fesd);
1254   fhlttree->GetUserInfo()->Add(fhltesd);
1255   
1256   const TMap *cdbMap = AliCDBManager::Instance()->GetStorageMap();       
1257   const TList *cdbList = AliCDBManager::Instance()->GetRetrievedIds();   
1258                  
1259    TMap *cdbMapCopy = new TMap(cdbMap->GetEntries());    
1260    cdbMapCopy->SetOwner(1);      
1261    cdbMapCopy->SetName("cdbMap");        
1262    TIter iter(cdbMap->GetTable());       
1263          
1264    TPair* pair = 0;      
1265    while((pair = dynamic_cast<TPair*> (iter.Next()))){   
1266          TObjString* keyStr = dynamic_cast<TObjString*> (pair->Key());   
1267          TObjString* valStr = dynamic_cast<TObjString*> (pair->Value());         
1268          cdbMapCopy->Add(new TObjString(keyStr->GetName()), new TObjString(valStr->GetName()));  
1269    }     
1270          
1271    TList *cdbListCopy = new TList();     
1272    cdbListCopy->SetOwner(1);     
1273    cdbListCopy->SetName("cdbList");      
1274          
1275    TIter iter2(cdbList);         
1276          
1277    AliCDBId* id=0;       
1278    while((id = dynamic_cast<AliCDBId*> (iter2.Next()))){         
1279          cdbListCopy->Add(new TObjString(id->ToString().Data()));        
1280    }     
1281          
1282    ftree->GetUserInfo()->Add(cdbMapCopy);        
1283    ftree->GetUserInfo()->Add(cdbListCopy);
1284
1285
1286   if(fESDPar.Contains("ESD.par")){
1287     AliInfo("Attaching ESD.par to Tree");
1288     TNamed *fn = CopyFileToTNamed(fESDPar.Data(),"ESD.par");
1289     ftree->GetUserInfo()->Add(fn);
1290   }
1291
1292
1293   ffile->cd();
1294
1295   if (fWriteESDfriend)
1296     ftree->SetBranchStatus("ESDfriend*",0);
1297   // we want to have only one tree version number
1298   ftree->Write(ftree->GetName(),TObject::kOverwrite);
1299   fhlttree->Write();
1300
1301 // Finish with Plane Efficiency evaluation: before of CleanUp !!!
1302   if (fRunPlaneEff && !FinishPlaneEff()) {
1303    AliWarning("Finish PlaneEff evaluation failed");
1304   }
1305
1306   gROOT->cd();
1307   CleanUp(ffile, ffileOld);
1308     
1309   if (fWriteAOD) {
1310     AliWarning("AOD creation not supported anymore during reconstruction. See ANALYSIS/AliAnalysisTaskESDfilter.cxx instead.");
1311   }
1312
1313   // Create tags for the events in the ESD tree (the ESD tree is always present)
1314   // In case of empty events the tags will contain dummy values
1315   AliESDTagCreator *esdtagCreator = new AliESDTagCreator();
1316   esdtagCreator->CreateESDTags(fFirstEvent,fLastEvent,fGRPList);
1317   if (fWriteAOD) {
1318     AliWarning("AOD tag creation not supported anymore during reconstruction.");
1319   }
1320
1321   //Finish QA and end of cycle for out-of-loop QA
1322   if (!fInLoopQA) {
1323      if (fRunQA) {
1324        AliQADataMakerSteer qas;
1325        qas.Run(fRunLocalReconstruction.Data(), AliQA::kRECPOINTS, (fRunQA && fRawReader));
1326        //qas.Reset() ;
1327        qas.Run(fRunTracking.Data(), AliQA::kESDS, (fRunQA && fRawReader));
1328      }
1329      if (fRunGlobalQA) {
1330         AliQADataMakerRec *qadm = GetQADataMaker(AliQA::kGLOBAL);
1331         if (qadm) {
1332            qadm->EndOfCycle(AliQA::kRECPOINTS);
1333            qadm->EndOfCycle(AliQA::kESDS);
1334            qadm->Finish();
1335         }
1336      }
1337   }
1338   
1339   // Cleanup of CDB manager: cache and active storages!
1340   AliCDBManager::Instance()->ClearCache();
1341   
1342   return kTRUE;
1343 }
1344
1345
1346 //_____________________________________________________________________________
1347 Bool_t AliReconstruction::RunLocalReconstruction(const TString& /*detectors*/)
1348 {
1349 // run the local reconstruction
1350   static Int_t eventNr=0;
1351   AliCodeTimerAuto("")
1352
1353  //  AliCDBManager* man = AliCDBManager::Instance();
1354 //   Bool_t origCache = man->GetCacheFlag();
1355
1356 //   TString detStr = detectors;
1357 //   for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
1358 //     if (!IsSelected(fgkDetectorName[iDet], detStr)) continue;
1359 //     AliReconstructor* reconstructor = GetReconstructor(iDet);
1360 //     if (!reconstructor) continue;
1361 //     if (reconstructor->HasLocalReconstruction()) continue;
1362
1363 //     AliCodeTimerStart(Form("running reconstruction for %s", fgkDetectorName[iDet]));
1364 //     AliInfo(Form("running reconstruction for %s", fgkDetectorName[iDet]));
1365     
1366 //     AliCodeTimerStart(Form("Loading calibration data from OCDB for %s", fgkDetectorName[iDet]));                          
1367 //     AliInfo(Form("Loading calibration data from OCDB for %s", fgkDetectorName[iDet]));
1368
1369 //     man->SetCacheFlag(kTRUE);
1370 //     TString calibPath = Form("%s/Calib/*", fgkDetectorName[iDet]);
1371 //     man->GetAll(calibPath); // entries are cached!
1372
1373 //     AliCodeTimerStop(Form("Loading calibration data from OCDB for %s", fgkDetectorName[iDet]));
1374      
1375 //     if (fRawReader) {
1376 //       fRawReader->RewindEvents();
1377 //       reconstructor->Reconstruct(fRunLoader, fRawReader);
1378 //     } else {
1379 //       reconstructor->Reconstruct(fRunLoader);
1380 //     }
1381      
1382 //      AliCodeTimerStop(Form("running reconstruction for %s", fgkDetectorName[iDet]));
1383     // AliSysInfo::AddStamp(Form("LRec%s_%d",fgkDetectorName[iDet],eventNr));
1384
1385 //     // unload calibration data
1386 //     man->UnloadFromCache(calibPath);
1387 //     //man->ClearCache();
1388 //   }
1389
1390 //   man->SetCacheFlag(origCache);
1391
1392 //   if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
1393 //     AliError(Form("the following detectors were not found: %s",
1394 //                   detStr.Data()));
1395 //     if (fStopOnError) return kFALSE;
1396 //   }
1397
1398           eventNr++;
1399   return kTRUE;
1400 }
1401
1402 //_____________________________________________________________________________
1403 Bool_t AliReconstruction::RunLocalEventReconstruction(const TString& detectors)
1404 {
1405 // run the local reconstruction
1406
1407   static Int_t eventNr=0;
1408   AliCodeTimerAuto("")
1409
1410   TString detStr = detectors;
1411   for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
1412     if (!IsSelected(fgkDetectorName[iDet], detStr)) continue;
1413     AliReconstructor* reconstructor = GetReconstructor(iDet);
1414     if (!reconstructor) continue;
1415     AliLoader* loader = fLoader[iDet];
1416     if (!loader) {
1417       AliWarning(Form("No loader is defined for %s!",fgkDetectorName[iDet]));
1418       continue;
1419     }
1420     // conversion of digits
1421     if (fRawReader && reconstructor->HasDigitConversion()) {
1422       AliInfo(Form("converting raw data digits into root objects for %s", 
1423                    fgkDetectorName[iDet]));
1424       AliCodeTimerAuto(Form("converting raw data digits into root objects for %s", 
1425                             fgkDetectorName[iDet]));
1426       loader->LoadDigits("update");
1427       loader->CleanDigits();
1428       loader->MakeDigitsContainer();
1429       TTree* digitsTree = loader->TreeD();
1430       reconstructor->ConvertDigits(fRawReader, digitsTree);
1431       loader->WriteDigits("OVERWRITE");
1432       loader->UnloadDigits();
1433     }
1434     // local reconstruction
1435     AliInfo(Form("running reconstruction for %s", fgkDetectorName[iDet]));
1436     AliCodeTimerAuto(Form("running reconstruction for %s", fgkDetectorName[iDet]));
1437     loader->LoadRecPoints("update");
1438     loader->CleanRecPoints();
1439     loader->MakeRecPointsContainer();
1440     TTree* clustersTree = loader->TreeR();
1441     if (fRawReader && !reconstructor->HasDigitConversion()) {
1442       reconstructor->Reconstruct(fRawReader, clustersTree);
1443     } else {
1444       loader->LoadDigits("read");
1445       TTree* digitsTree = loader->TreeD();
1446       if (!digitsTree) {
1447         AliError(Form("Can't get the %s digits tree", fgkDetectorName[iDet]));
1448         if (fStopOnError) return kFALSE;
1449       } else {
1450         reconstructor->Reconstruct(digitsTree, clustersTree);
1451       }
1452       loader->UnloadDigits();
1453     }
1454
1455     // In-loop QA for local reconstrucion 
1456     if (fRunQA && fInLoopQA) {
1457        AliQADataMakerRec * qadm = GetQADataMaker(iDet);
1458        if (qadm) {
1459           //AliCodeTimerStart
1460           //(Form("Running QA data maker for %s", fgkDetectorName[iDet]));
1461           //AliInfo
1462           //(Form("Running QA data maker for %s", fgkDetectorName[iDet]));
1463
1464           qadm->Exec(AliQA::kRECPOINTS, clustersTree) ;
1465  
1466           //AliCodeTimerStop
1467           //(Form("Running QA data maker for %s", fgkDetectorName[iDet]));
1468        }
1469     }
1470
1471     loader->WriteRecPoints("OVERWRITE");
1472     loader->UnloadRecPoints();
1473     AliSysInfo::AddStamp(Form("LRec%s_%d",fgkDetectorName[iDet],eventNr), iDet,1,eventNr);
1474   }
1475
1476   if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
1477     AliError(Form("the following detectors were not found: %s",
1478                   detStr.Data()));
1479     if (fStopOnError) return kFALSE;
1480   }
1481   eventNr++;
1482   return kTRUE;
1483 }
1484
1485 //_____________________________________________________________________________
1486 Bool_t AliReconstruction::RunVertexFinder(AliESDEvent*& esd)
1487 {
1488 // run the barrel tracking
1489
1490   AliCodeTimerAuto("")
1491
1492   AliESDVertex* vertex = NULL;
1493   Double_t vtxPos[3] = {0, 0, 0};
1494   Double_t vtxErr[3] = {0.07, 0.07, 0.1};
1495   TArrayF mcVertex(3); 
1496   if (fRunLoader->GetHeader() && fRunLoader->GetHeader()->GenEventHeader()) {
1497     fRunLoader->GetHeader()->GenEventHeader()->PrimaryVertex(mcVertex);
1498     for (Int_t i = 0; i < 3; i++) vtxPos[i] = mcVertex[i];
1499   }
1500
1501   if (fVertexer) {
1502     if(fDiamondProfile) fVertexer->SetVtxStart(fDiamondProfile);
1503     AliInfo("running the ITS vertex finder");
1504     if (fLoader[0]) fLoader[0]->LoadRecPoints();
1505     vertex = fVertexer->FindVertexForCurrentEvent(fRunLoader->GetEventNumber());
1506     if (fLoader[0]) fLoader[0]->UnloadRecPoints();
1507     if(!vertex){
1508       AliWarning("Vertex not found");
1509       vertex = new AliESDVertex();
1510       vertex->SetName("default");
1511     }
1512     else {
1513       vertex->SetName("reconstructed");
1514     }
1515
1516   } else {
1517     AliInfo("getting the primary vertex from MC");
1518     vertex = new AliESDVertex(vtxPos, vtxErr);
1519   }
1520
1521   if (vertex) {
1522     vertex->GetXYZ(vtxPos);
1523     vertex->GetSigmaXYZ(vtxErr);
1524   } else {
1525     AliWarning("no vertex reconstructed");
1526     vertex = new AliESDVertex(vtxPos, vtxErr);
1527   }
1528   esd->SetPrimaryVertexSPD(vertex);
1529   // if SPD multiplicity has been determined, it is stored in the ESD
1530   AliMultiplicity *mult = fVertexer->GetMultiplicity();
1531   if(mult)esd->SetMultiplicity(mult);
1532
1533   for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
1534     if (fTracker[iDet]) fTracker[iDet]->SetVertex(vtxPos, vtxErr);
1535   }  
1536   delete vertex;
1537
1538   return kTRUE;
1539 }
1540
1541 //_____________________________________________________________________________
1542 Bool_t AliReconstruction::RunHLTTracking(AliESDEvent*& esd)
1543 {
1544 // run the HLT barrel tracking
1545
1546   AliCodeTimerAuto("")
1547
1548   if (!fRunLoader) {
1549     AliError("Missing runLoader!");
1550     return kFALSE;
1551   }
1552
1553   AliInfo("running HLT tracking");
1554
1555   // Get a pointer to the HLT reconstructor
1556   AliReconstructor *reconstructor = GetReconstructor(fgkNDetectors-1);
1557   if (!reconstructor) return kFALSE;
1558
1559   // TPC + ITS
1560   for (Int_t iDet = 1; iDet >= 0; iDet--) {
1561     TString detName = fgkDetectorName[iDet];
1562     AliDebug(1, Form("%s HLT tracking", detName.Data()));
1563     reconstructor->SetOption(detName.Data());
1564     AliTracker *tracker = reconstructor->CreateTracker();
1565     if (!tracker) {
1566       AliWarning(Form("couldn't create a HLT tracker for %s", detName.Data()));
1567       if (fStopOnError) return kFALSE;
1568       continue;
1569     }
1570     Double_t vtxPos[3];
1571     Double_t vtxErr[3]={0.005,0.005,0.010};
1572     const AliESDVertex *vertex = esd->GetVertex();
1573     vertex->GetXYZ(vtxPos);
1574     tracker->SetVertex(vtxPos,vtxErr);
1575     if(iDet != 1) {
1576       fLoader[iDet]->LoadRecPoints("read");
1577       TTree* tree = fLoader[iDet]->TreeR();
1578       if (!tree) {
1579         AliError(Form("Can't get the %s cluster tree", detName.Data()));
1580         return kFALSE;
1581       }
1582       tracker->LoadClusters(tree);
1583     }
1584     if (tracker->Clusters2Tracks(esd) != 0) {
1585       AliError(Form("HLT %s Clusters2Tracks failed", fgkDetectorName[iDet]));
1586       return kFALSE;
1587     }
1588     if(iDet != 1) {
1589       tracker->UnloadClusters();
1590     }
1591     delete tracker;
1592   }
1593
1594   return kTRUE;
1595 }
1596
1597 //_____________________________________________________________________________
1598 Bool_t AliReconstruction::RunMuonTracking(AliESDEvent*& esd)
1599 {
1600 // run the muon spectrometer tracking
1601
1602   AliCodeTimerAuto("")
1603
1604   if (!fRunLoader) {
1605     AliError("Missing runLoader!");
1606     return kFALSE;
1607   }
1608   Int_t iDet = 7; // for MUON
1609
1610   AliInfo("is running...");
1611
1612   // Get a pointer to the MUON reconstructor
1613   AliReconstructor *reconstructor = GetReconstructor(iDet);
1614   if (!reconstructor) return kFALSE;
1615
1616   
1617   TString detName = fgkDetectorName[iDet];
1618   AliDebug(1, Form("%s tracking", detName.Data()));
1619   AliTracker *tracker =  reconstructor->CreateTracker();
1620   if (!tracker) {
1621     AliWarning(Form("couldn't create a tracker for %s", detName.Data()));
1622     return kFALSE;
1623   }
1624      
1625   // read RecPoints
1626   fLoader[iDet]->LoadRecPoints("read");  
1627
1628   tracker->LoadClusters(fLoader[iDet]->TreeR());
1629   
1630   Int_t rv = tracker->Clusters2Tracks(esd);
1631   
1632   if ( rv )
1633   {
1634     AliError(Form("%s Clusters2Tracks failed", fgkDetectorName[iDet]));
1635     return kFALSE;
1636   }
1637   
1638   fLoader[iDet]->UnloadRecPoints();
1639
1640   tracker->UnloadClusters();
1641   
1642   delete tracker;
1643   
1644   return kTRUE;
1645 }
1646
1647
1648 //_____________________________________________________________________________
1649 Bool_t AliReconstruction::RunTracking(AliESDEvent*& esd)
1650 {
1651 // run the barrel tracking
1652   static Int_t eventNr=0;
1653   AliCodeTimerAuto("")
1654
1655   AliInfo("running tracking");
1656
1657   //Fill the ESD with the T0 info (will be used by the TOF) 
1658   if (fReconstructor[11] && fLoader[11]) {
1659     fLoader[11]->LoadRecPoints("READ");
1660     TTree *treeR = fLoader[11]->TreeR();
1661     GetReconstructor(11)->FillESD((TTree *)NULL,treeR,esd);
1662   }
1663
1664   // pass 1: TPC + ITS inwards
1665   for (Int_t iDet = 1; iDet >= 0; iDet--) {
1666     if (!fTracker[iDet]) continue;
1667     AliDebug(1, Form("%s tracking", fgkDetectorName[iDet]));
1668
1669     // load clusters
1670     fLoader[iDet]->LoadRecPoints("read");
1671     AliSysInfo::AddStamp(Form("RLoadCluster%s_%d",fgkDetectorName[iDet],eventNr),iDet,1, eventNr);
1672     TTree* tree = fLoader[iDet]->TreeR();
1673     if (!tree) {
1674       AliError(Form("Can't get the %s cluster tree", fgkDetectorName[iDet]));
1675       return kFALSE;
1676     }
1677     fTracker[iDet]->LoadClusters(tree);
1678     AliSysInfo::AddStamp(Form("TLoadCluster%s_%d",fgkDetectorName[iDet],eventNr), iDet,2, eventNr);
1679     // run tracking
1680     if (fTracker[iDet]->Clusters2Tracks(esd) != 0) {
1681       AliError(Form("%s Clusters2Tracks failed", fgkDetectorName[iDet]));
1682       return kFALSE;
1683     }
1684     if (fCheckPointLevel > 1) {
1685       WriteESD(esd, Form("%s.tracking", fgkDetectorName[iDet]));
1686     }
1687     // preliminary PID in TPC needed by the ITS tracker
1688     if (iDet == 1) {
1689       GetReconstructor(1)->FillESD((TTree*)NULL, (TTree*)NULL, esd);
1690       AliESDpid::MakePID(esd);
1691     } 
1692     AliSysInfo::AddStamp(Form("Tracking0%s_%d",fgkDetectorName[iDet],eventNr), iDet,3,eventNr);
1693   }
1694
1695   // pass 2: ALL backwards
1696
1697   for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
1698     if (!fTracker[iDet]) continue;
1699     AliDebug(1, Form("%s back propagation", fgkDetectorName[iDet]));
1700
1701     // load clusters
1702     if (iDet > 1) {     // all except ITS, TPC
1703       TTree* tree = NULL;
1704       fLoader[iDet]->LoadRecPoints("read");
1705       AliSysInfo::AddStamp(Form("RLoadCluster0%s_%d",fgkDetectorName[iDet],eventNr), iDet,1, eventNr);
1706       tree = fLoader[iDet]->TreeR();
1707       if (!tree) {
1708         AliError(Form("Can't get the %s cluster tree", fgkDetectorName[iDet]));
1709         return kFALSE;
1710       }
1711       fTracker[iDet]->LoadClusters(tree); 
1712       AliSysInfo::AddStamp(Form("TLoadCluster0%s_%d",fgkDetectorName[iDet],eventNr), iDet,2, eventNr);
1713     }
1714
1715     // run tracking
1716     if (iDet>1) // start filling residuals for the "outer" detectors
1717     if (fRunGlobalQA) AliTracker::SetFillResiduals(kTRUE);     
1718
1719     if (fTracker[iDet]->PropagateBack(esd) != 0) {
1720       AliError(Form("%s backward propagation failed", fgkDetectorName[iDet]));
1721       //      return kFALSE;
1722     }
1723     if (fCheckPointLevel > 1) {
1724       WriteESD(esd, Form("%s.back", fgkDetectorName[iDet]));
1725     }
1726
1727     // unload clusters
1728     if (iDet > 2) {     // all except ITS, TPC, TRD
1729       fTracker[iDet]->UnloadClusters();
1730       fLoader[iDet]->UnloadRecPoints();
1731     }
1732     // updated PID in TPC needed by the ITS tracker -MI
1733     if (iDet == 1) {
1734       GetReconstructor(1)->FillESD((TTree*)NULL, (TTree*)NULL, esd);
1735       AliESDpid::MakePID(esd);
1736     }
1737     AliSysInfo::AddStamp(Form("Tracking1%s_%d",fgkDetectorName[iDet],eventNr), iDet,3, eventNr);
1738   }
1739   //stop filling residuals for the "outer" detectors
1740   if (fRunGlobalQA) AliTracker::SetFillResiduals(kFALSE);     
1741
1742   // write space-points to the ESD in case alignment data output
1743   // is switched on
1744   if (fWriteAlignmentData)
1745     WriteAlignmentData(esd);
1746
1747   // pass 3: TRD + TPC + ITS refit inwards
1748
1749   for (Int_t iDet = 2; iDet >= 0; iDet--) {
1750     if (!fTracker[iDet]) continue;
1751     AliDebug(1, Form("%s inward refit", fgkDetectorName[iDet]));
1752
1753     // run tracking
1754     if (iDet<2) // start filling residuals for TPC and ITS
1755     if (fRunGlobalQA) AliTracker::SetFillResiduals(kTRUE);     
1756
1757     if (fTracker[iDet]->RefitInward(esd) != 0) {
1758       AliError(Form("%s inward refit failed", fgkDetectorName[iDet]));
1759       //      return kFALSE;
1760     }
1761     // run postprocessing
1762     if (fTracker[iDet]->PostProcess(esd) != 0) {
1763       AliError(Form("%s postprocessing failed", fgkDetectorName[iDet]));
1764       //      return kFALSE;
1765     }
1766     if (fCheckPointLevel > 1) {
1767       WriteESD(esd, Form("%s.refit", fgkDetectorName[iDet]));
1768     }
1769     AliSysInfo::AddStamp(Form("Tracking2%s_%d",fgkDetectorName[iDet],eventNr), iDet,3, eventNr);
1770     // unload clusters
1771     fTracker[iDet]->UnloadClusters();
1772     AliSysInfo::AddStamp(Form("TUnloadCluster%s_%d",fgkDetectorName[iDet],eventNr), iDet,4, eventNr);
1773     fLoader[iDet]->UnloadRecPoints();
1774     AliSysInfo::AddStamp(Form("RUnloadCluster%s_%d",fgkDetectorName[iDet],eventNr), iDet,5, eventNr);
1775   }
1776   // stop filling residuals for TPC and ITS
1777   if (fRunGlobalQA) AliTracker::SetFillResiduals(kFALSE);     
1778
1779   eventNr++;
1780   return kTRUE;
1781 }
1782
1783 //_____________________________________________________________________________
1784 Bool_t AliReconstruction::CleanESD(AliESDEvent *esd){
1785   //
1786   // Remove the data which are not needed for the physics analysis.
1787   //
1788
1789   Int_t nTracks=esd->GetNumberOfTracks();
1790   Int_t nV0s=esd->GetNumberOfV0s();
1791   AliInfo
1792   (Form("Number of ESD tracks and V0s before cleaning: %d %d",nTracks,nV0s));
1793
1794   Float_t cleanPars[]={fV0DCAmax,fV0CsPmin,fDmax,fZmax};
1795   Bool_t rc=esd->Clean(cleanPars);
1796
1797   nTracks=esd->GetNumberOfTracks();
1798   nV0s=esd->GetNumberOfV0s();
1799   AliInfo
1800   (Form("Number of ESD tracks and V0s after cleaning %d %d",nTracks,nV0s));
1801
1802   return rc;
1803 }
1804
1805 //_____________________________________________________________________________
1806 Bool_t AliReconstruction::FillESD(AliESDEvent*& esd, const TString& detectors)
1807 {
1808 // fill the event summary data
1809
1810   AliCodeTimerAuto("")
1811     static Int_t eventNr=0; 
1812   TString detStr = detectors;
1813   
1814   for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
1815   if (!IsSelected(fgkDetectorName[iDet], detStr)) continue;
1816     AliReconstructor* reconstructor = GetReconstructor(iDet);
1817     if (!reconstructor) continue;
1818     if (!ReadESD(esd, fgkDetectorName[iDet])) {
1819       AliDebug(1, Form("filling ESD for %s", fgkDetectorName[iDet]));
1820       TTree* clustersTree = NULL;
1821       if (fLoader[iDet]) {
1822         fLoader[iDet]->LoadRecPoints("read");
1823         clustersTree = fLoader[iDet]->TreeR();
1824         if (!clustersTree) {
1825           AliError(Form("Can't get the %s clusters tree", 
1826                         fgkDetectorName[iDet]));
1827           if (fStopOnError) return kFALSE;
1828         }
1829       }
1830       if (fRawReader && !reconstructor->HasDigitConversion()) {
1831         reconstructor->FillESD(fRawReader, clustersTree, esd);
1832       } else {
1833         TTree* digitsTree = NULL;
1834         if (fLoader[iDet]) {
1835           fLoader[iDet]->LoadDigits("read");
1836           digitsTree = fLoader[iDet]->TreeD();
1837           if (!digitsTree) {
1838             AliError(Form("Can't get the %s digits tree", 
1839                           fgkDetectorName[iDet]));
1840             if (fStopOnError) return kFALSE;
1841           }
1842         }
1843         reconstructor->FillESD(digitsTree, clustersTree, esd);
1844         if (fLoader[iDet]) fLoader[iDet]->UnloadDigits();
1845       }
1846       if (fLoader[iDet]) {
1847         fLoader[iDet]->UnloadRecPoints();
1848       }
1849
1850       if (fCheckPointLevel > 2) WriteESD(esd, fgkDetectorName[iDet]);
1851     }
1852   }
1853
1854   if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
1855     AliError(Form("the following detectors were not found: %s", 
1856                   detStr.Data()));
1857     if (fStopOnError) return kFALSE;
1858   }
1859   AliSysInfo::AddStamp(Form("FillESD%d",eventNr), 0,1, eventNr);
1860   eventNr++;
1861   return kTRUE;
1862 }
1863
1864 //_____________________________________________________________________________
1865 Bool_t AliReconstruction::FillTriggerESD(AliESDEvent*& esd)
1866 {
1867   // Reads the trigger decision which is
1868   // stored in Trigger.root file and fills
1869   // the corresponding esd entries
1870
1871   AliCodeTimerAuto("")
1872   
1873   AliInfo("Filling trigger information into the ESD");
1874
1875   AliCentralTrigger *aCTP = NULL;
1876
1877   if (fRawReader) {
1878     AliCTPRawStream input(fRawReader);
1879     if (!input.Next()) {
1880       AliError("No valid CTP (trigger) DDL raw data is found ! The trigger information is not stored in the ESD !");
1881       return kFALSE;
1882     }
1883     esd->SetTriggerMask(input.GetClassMask());
1884     esd->SetTriggerCluster(input.GetClusterMask());
1885
1886     aCTP = new AliCentralTrigger();
1887     TString configstr("");
1888     if (!aCTP->LoadConfiguration(configstr)) { // Load CTP config from OCDB
1889       AliError("No trigger configuration found in OCDB! The trigger classes information will no be stored in ESD!");
1890       delete aCTP;
1891       return kFALSE;
1892     }
1893   }
1894   else {
1895     AliRunLoader *runloader = AliRunLoader::GetRunLoader();
1896     if (runloader) {
1897       if (!runloader->LoadTrigger()) {
1898         aCTP = runloader->GetTrigger();
1899         esd->SetTriggerMask(aCTP->GetClassMask());
1900         esd->SetTriggerCluster(aCTP->GetClusterMask());
1901       }
1902       else {
1903         AliWarning("No trigger can be loaded! The trigger information is not stored in the ESD !");
1904         return kFALSE;
1905       }
1906     }
1907     else {
1908       AliError("No run loader is available! The trigger information is not stored in the ESD !");
1909       return kFALSE;
1910     }
1911   }
1912
1913   // Now fill the trigger class names into AliESDRun object
1914   AliTriggerConfiguration *config = aCTP->GetConfiguration();
1915   if (fRawReader) delete aCTP;
1916   if (!config) {
1917     AliError("No trigger configuration has been found! The trigger classes information will no be stored in ESD!");
1918     return kFALSE;
1919   }
1920
1921   const TObjArray& classesArray = config->GetClasses();
1922   Int_t nclasses = classesArray.GetEntriesFast();
1923   for( Int_t j=0; j<nclasses; j++ ) {
1924     AliTriggerClass* trclass = (AliTriggerClass*)classesArray.At( j );
1925     Int_t trindex = (Int_t)TMath::Log2(trclass->GetMask());
1926     esd->SetTriggerClass(trclass->GetName(),trindex);
1927   }
1928
1929   return kTRUE;
1930 }
1931
1932
1933
1934
1935
1936 //_____________________________________________________________________________
1937 Bool_t AliReconstruction::FillRawEventHeaderESD(AliESDEvent*& esd)
1938 {
1939   // 
1940   // Filling information from RawReader Header
1941   // 
1942
1943   AliInfo("Filling information from RawReader Header");
1944   esd->SetBunchCrossNumber(0);
1945   esd->SetOrbitNumber(0);
1946   esd->SetPeriodNumber(0);
1947   esd->SetTimeStamp(0);
1948   esd->SetEventType(0);
1949   const AliRawEventHeaderBase * eventHeader = fRawReader->GetEventHeader();
1950   if (eventHeader){
1951
1952     const UInt_t *id = eventHeader->GetP("Id");
1953     esd->SetBunchCrossNumber((id)[1]&0x00000fff);
1954     esd->SetOrbitNumber((((id)[0]<<20)&0xf00000)|(((id)[1]>>12)&0xfffff));
1955     esd->SetPeriodNumber(((id)[0]>>4)&0x0fffffff);
1956
1957     esd->SetTimeStamp((eventHeader->Get("Timestamp")));  
1958     esd->SetEventType((eventHeader->Get("Type")));
1959   }
1960
1961   return kTRUE;
1962 }
1963
1964
1965 //_____________________________________________________________________________
1966 Bool_t AliReconstruction::IsSelected(TString detName, TString& detectors) const
1967 {
1968 // check whether detName is contained in detectors
1969 // if yes, it is removed from detectors
1970
1971   // check if all detectors are selected
1972   if ((detectors.CompareTo("ALL") == 0) ||
1973       detectors.BeginsWith("ALL ") ||
1974       detectors.EndsWith(" ALL") ||
1975       detectors.Contains(" ALL ")) {
1976     detectors = "ALL";
1977     return kTRUE;
1978   }
1979
1980   // search for the given detector
1981   Bool_t result = kFALSE;
1982   if ((detectors.CompareTo(detName) == 0) ||
1983       detectors.BeginsWith(detName+" ") ||
1984       detectors.EndsWith(" "+detName) ||
1985       detectors.Contains(" "+detName+" ")) {
1986     detectors.ReplaceAll(detName, "");
1987     result = kTRUE;
1988   }
1989
1990   // clean up the detectors string
1991   while (detectors.Contains("  ")) detectors.ReplaceAll("  ", " ");
1992   while (detectors.BeginsWith(" ")) detectors.Remove(0, 1);
1993   while (detectors.EndsWith(" ")) detectors.Remove(detectors.Length()-1, 1);
1994
1995   return result;
1996 }
1997
1998 //_____________________________________________________________________________
1999 Bool_t AliReconstruction::InitRunLoader()
2000 {
2001 // get or create the run loader
2002
2003   if (gAlice) delete gAlice;
2004   gAlice = NULL;
2005
2006   if (!gSystem->AccessPathName(fGAliceFileName.Data())) { // galice.root exists
2007     // load all base libraries to get the loader classes
2008     TString libs = gSystem->GetLibraries();
2009     for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
2010       TString detName = fgkDetectorName[iDet];
2011       if (detName == "HLT") continue;
2012       if (libs.Contains("lib" + detName + "base.so")) continue;
2013       gSystem->Load("lib" + detName + "base.so");
2014     }
2015     fRunLoader = AliRunLoader::Open(fGAliceFileName.Data());
2016     if (!fRunLoader) {
2017       AliError(Form("no run loader found in file %s", fGAliceFileName.Data()));
2018       CleanUp();
2019       return kFALSE;
2020     }
2021     fRunLoader->CdGAFile();
2022     if (gFile->GetKey(AliRunLoader::GetGAliceName())) {
2023       if (fRunLoader->LoadgAlice() == 0) {
2024         gAlice = fRunLoader->GetAliRun();
2025         AliTracker::SetFieldMap(gAlice->Field(),fUniformField);
2026       }
2027     }
2028     if (!gAlice && !fRawReader) {
2029       AliError(Form("no gAlice object found in file %s",
2030                     fGAliceFileName.Data()));
2031       CleanUp();
2032       return kFALSE;
2033     }
2034
2035     //PH This is a temporary fix to give access to the kinematics
2036     //PH that is needed for the labels of ITS clusters
2037     fRunLoader->LoadHeader();
2038     fRunLoader->LoadKinematics();
2039
2040   } else {               // galice.root does not exist
2041     if (!fRawReader) {
2042       AliError(Form("the file %s does not exist", fGAliceFileName.Data()));
2043       CleanUp();
2044       return kFALSE;
2045     }
2046     fRunLoader = AliRunLoader::Open(fGAliceFileName.Data(),
2047                                     AliConfig::GetDefaultEventFolderName(),
2048                                     "recreate");
2049     if (!fRunLoader) {
2050       AliError(Form("could not create run loader in file %s", 
2051                     fGAliceFileName.Data()));
2052       CleanUp();
2053       return kFALSE;
2054     }
2055     fIsNewRunLoader = kTRUE;
2056     fRunLoader->MakeTree("E");
2057
2058     if (fNumberOfEventsPerFile > 0)
2059       fRunLoader->SetNumberOfEventsPerFile(fNumberOfEventsPerFile);
2060     else
2061       fRunLoader->SetNumberOfEventsPerFile((UInt_t)-1);
2062   }
2063
2064   return kTRUE;
2065 }
2066
2067 //_____________________________________________________________________________
2068 AliReconstructor* AliReconstruction::GetReconstructor(Int_t iDet)
2069 {
2070 // get the reconstructor object and the loader for a detector
2071
2072   if (fReconstructor[iDet]) return fReconstructor[iDet];
2073
2074   // load the reconstructor object
2075   TPluginManager* pluginManager = gROOT->GetPluginManager();
2076   TString detName = fgkDetectorName[iDet];
2077   TString recName = "Ali" + detName + "Reconstructor";
2078   if (gAlice && !gAlice->GetDetector(detName) && (detName != "HLT")) return NULL;
2079
2080   AliReconstructor* reconstructor = NULL;
2081   // first check if a plugin is defined for the reconstructor
2082   TPluginHandler* pluginHandler = 
2083     pluginManager->FindHandler("AliReconstructor", detName);
2084   // if not, add a plugin for it
2085   if (!pluginHandler) {
2086     AliDebug(1, Form("defining plugin for %s", recName.Data()));
2087     TString libs = gSystem->GetLibraries();
2088     if (libs.Contains("lib" + detName + "base.so") ||
2089         (gSystem->Load("lib" + detName + "base.so") >= 0)) {
2090       pluginManager->AddHandler("AliReconstructor", detName, 
2091                                 recName, detName + "rec", recName + "()");
2092     } else {
2093       pluginManager->AddHandler("AliReconstructor", detName, 
2094                                 recName, detName, recName + "()");
2095     }
2096     pluginHandler = pluginManager->FindHandler("AliReconstructor", detName);
2097   }
2098   if (pluginHandler && (pluginHandler->LoadPlugin() == 0)) {
2099     reconstructor = (AliReconstructor*) pluginHandler->ExecPlugin(0);
2100   }
2101   if (reconstructor) {
2102     TObject* obj = fOptions.FindObject(detName.Data());
2103     if (obj) reconstructor->SetOption(obj->GetTitle());
2104     reconstructor->Init();
2105     fReconstructor[iDet] = reconstructor;
2106   }
2107
2108   // get or create the loader
2109   if (detName != "HLT") {
2110     fLoader[iDet] = fRunLoader->GetLoader(detName + "Loader");
2111     if (!fLoader[iDet]) {
2112       AliConfig::Instance()
2113         ->CreateDetectorFolders(fRunLoader->GetEventFolder(), 
2114                                 detName, detName);
2115       // first check if a plugin is defined for the loader
2116       pluginHandler = 
2117         pluginManager->FindHandler("AliLoader", detName);
2118       // if not, add a plugin for it
2119       if (!pluginHandler) {
2120         TString loaderName = "Ali" + detName + "Loader";
2121         AliDebug(1, Form("defining plugin for %s", loaderName.Data()));
2122         pluginManager->AddHandler("AliLoader", detName, 
2123                                   loaderName, detName + "base", 
2124                                   loaderName + "(const char*, TFolder*)");
2125         pluginHandler = pluginManager->FindHandler("AliLoader", detName);
2126       }
2127       if (pluginHandler && (pluginHandler->LoadPlugin() == 0)) {
2128         fLoader[iDet] = 
2129           (AliLoader*) pluginHandler->ExecPlugin(2, detName.Data(), 
2130                                                  fRunLoader->GetEventFolder());
2131       }
2132       if (!fLoader[iDet]) {   // use default loader
2133         fLoader[iDet] = new AliLoader(detName, fRunLoader->GetEventFolder());
2134       }
2135       if (!fLoader[iDet]) {
2136         AliWarning(Form("couldn't get loader for %s", detName.Data()));
2137         if (fStopOnError) return NULL;
2138       } else {
2139         fRunLoader->AddLoader(fLoader[iDet]);
2140         fRunLoader->CdGAFile();
2141         if (gFile && !gFile->IsWritable()) gFile->ReOpen("UPDATE");
2142         fRunLoader->Write(0, TObject::kOverwrite);
2143       }
2144     }
2145   }
2146       
2147   return reconstructor;
2148 }
2149
2150 //_____________________________________________________________________________
2151 Bool_t AliReconstruction::CreateVertexer()
2152 {
2153 // create the vertexer
2154
2155   fVertexer = NULL;
2156   AliReconstructor* itsReconstructor = GetReconstructor(0);
2157   if (itsReconstructor) {
2158     fVertexer = itsReconstructor->CreateVertexer();
2159   }
2160   if (!fVertexer) {
2161     AliWarning("couldn't create a vertexer for ITS");
2162     if (fStopOnError) return kFALSE;
2163   }
2164
2165   return kTRUE;
2166 }
2167
2168 //_____________________________________________________________________________
2169 Bool_t AliReconstruction::CreateTrackers(const TString& detectors)
2170 {
2171 // create the trackers
2172
2173   TString detStr = detectors;
2174   for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
2175     if (!IsSelected(fgkDetectorName[iDet], detStr)) continue;
2176     AliReconstructor* reconstructor = GetReconstructor(iDet);
2177     if (!reconstructor) continue;
2178     TString detName = fgkDetectorName[iDet];
2179     if (detName == "HLT") {
2180       fRunHLTTracking = kTRUE;
2181       continue;
2182     }
2183     if (detName == "MUON") {
2184       fRunMuonTracking = kTRUE;
2185       continue;
2186     }
2187
2188
2189     fTracker[iDet] = reconstructor->CreateTracker();
2190     if (!fTracker[iDet] && (iDet < 7)) {
2191       AliWarning(Form("couldn't create a tracker for %s", detName.Data()));
2192       if (fStopOnError) return kFALSE;
2193     }
2194     AliSysInfo::AddStamp(Form("LTracker%s",fgkDetectorName[iDet]), iDet,0);
2195   }
2196
2197   return kTRUE;
2198 }
2199
2200 //_____________________________________________________________________________
2201 void AliReconstruction::CleanUp(TFile* file, TFile* fileOld)
2202 {
2203 // delete trackers and the run loader and close and delete the file
2204
2205   for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
2206     delete fReconstructor[iDet];
2207     fReconstructor[iDet] = NULL;
2208     fLoader[iDet] = NULL;
2209     delete fTracker[iDet];
2210     fTracker[iDet] = NULL;
2211 //    delete fQADataMaker[iDet];
2212 //    fQADataMaker[iDet] = NULL;
2213   }
2214   delete fVertexer;
2215   fVertexer = NULL;
2216
2217   if (ftVertexer) delete ftVertexer;
2218   ftVertexer = NULL;
2219   
2220   if(!(AliCDBManager::Instance()->GetCacheFlag())) {
2221         delete fDiamondProfile;
2222         fDiamondProfile = NULL;
2223         delete fDiamondProfileTPC;
2224         fDiamondProfileTPC = NULL;
2225         delete fGRPList;
2226         fGRPList = NULL;
2227   }
2228
2229
2230   delete fRunLoader;
2231   fRunLoader = NULL;
2232   delete fRawReader;
2233   fRawReader = NULL;
2234   if (fParentRawReader) delete fParentRawReader;
2235   fParentRawReader=NULL;
2236
2237   if (file) {
2238     file->Close();
2239     delete file;
2240   }
2241
2242   if (fileOld) {
2243     fileOld->Close();
2244     delete fileOld;
2245     gSystem->Unlink("AliESDs.old.root");
2246   }
2247
2248 }
2249
2250 //_____________________________________________________________________________
2251
2252 Bool_t AliReconstruction::ReadESD(AliESDEvent*& esd, const char* recStep) const
2253 {
2254 // read the ESD event from a file
2255
2256   if (!esd) return kFALSE;
2257   char fileName[256];
2258   sprintf(fileName, "ESD_%d.%d_%s.root", 
2259           esd->GetRunNumber(), esd->GetEventNumberInFile(), recStep);
2260   if (gSystem->AccessPathName(fileName)) return kFALSE;
2261
2262   AliInfo(Form("reading ESD from file %s", fileName));
2263   AliDebug(1, Form("reading ESD from file %s", fileName));
2264   TFile* file = TFile::Open(fileName);
2265   if (!file || !file->IsOpen()) {
2266     AliError(Form("opening %s failed", fileName));
2267     delete file;
2268     return kFALSE;
2269   }
2270
2271   gROOT->cd();
2272   delete esd;
2273   esd = (AliESDEvent*) file->Get("ESD");
2274   file->Close();
2275   delete file;
2276   return kTRUE;
2277
2278 }
2279
2280
2281
2282 //_____________________________________________________________________________
2283 void AliReconstruction::WriteESD(AliESDEvent* esd, const char* recStep) const
2284 {
2285 // write the ESD event to a file
2286
2287   if (!esd) return;
2288   char fileName[256];
2289   sprintf(fileName, "ESD_%d.%d_%s.root", 
2290           esd->GetRunNumber(), esd->GetEventNumberInFile(), recStep);
2291
2292   AliDebug(1, Form("writing ESD to file %s", fileName));
2293   TFile* file = TFile::Open(fileName, "recreate");
2294   if (!file || !file->IsOpen()) {
2295     AliError(Form("opening %s failed", fileName));
2296   } else {
2297     esd->Write("ESD");
2298     file->Close();
2299   }
2300   delete file;
2301 }
2302
2303
2304 void AliReconstruction::WriteAlignmentData(AliESDEvent* esd)
2305 {
2306   // Write space-points which are then used in the alignment procedures
2307   // For the moment only ITS, TRD and TPC
2308
2309   // Load TOF clusters
2310   if (fTracker[3]){
2311     fLoader[3]->LoadRecPoints("read");
2312     TTree* tree = fLoader[3]->TreeR();
2313     if (!tree) {
2314       AliError(Form("Can't get the %s cluster tree", fgkDetectorName[3]));
2315       return;
2316     }
2317     fTracker[3]->LoadClusters(tree);
2318   }
2319   Int_t ntracks = esd->GetNumberOfTracks();
2320   for (Int_t itrack = 0; itrack < ntracks; itrack++)
2321     {
2322       AliESDtrack *track = esd->GetTrack(itrack);
2323       Int_t nsp = 0;
2324       Int_t idx[200];
2325       for (Int_t iDet = 3; iDet >= 0; iDet--)
2326         nsp += track->GetNcls(iDet);
2327       if (nsp) {
2328         AliTrackPointArray *sp = new AliTrackPointArray(nsp);
2329         track->SetTrackPointArray(sp);
2330         Int_t isptrack = 0;
2331         for (Int_t iDet = 3; iDet >= 0; iDet--) {
2332           AliTracker *tracker = fTracker[iDet];
2333           if (!tracker) continue;
2334           Int_t nspdet = track->GetNcls(iDet);
2335           if (nspdet <= 0) continue;
2336           track->GetClusters(iDet,idx);
2337           AliTrackPoint p;
2338           Int_t isp = 0;
2339           Int_t isp2 = 0;
2340           while (isp2 < nspdet) {
2341             Bool_t isvalid;
2342             TString dets = fgkDetectorName[iDet];
2343             if ((fUseTrackingErrorsForAlignment.CompareTo(dets) == 0) ||
2344             fUseTrackingErrorsForAlignment.BeginsWith(dets+" ") ||
2345             fUseTrackingErrorsForAlignment.EndsWith(" "+dets) ||
2346             fUseTrackingErrorsForAlignment.Contains(" "+dets+" ")) {
2347               isvalid = tracker->GetTrackPointTrackingError(idx[isp2],p,track);
2348             } else {
2349               isvalid = tracker->GetTrackPoint(idx[isp2],p); 
2350             } 
2351             isp2++;
2352             const Int_t kNTPCmax = 159;
2353             if (iDet==1 && isp2>kNTPCmax) break;   // to be fixed
2354             if (!isvalid) continue;
2355             sp->AddPoint(isptrack,&p); isptrack++; isp++;
2356           }
2357         }       
2358       }
2359     }
2360   if (fTracker[3]){
2361     fTracker[3]->UnloadClusters();
2362     fLoader[3]->UnloadRecPoints();
2363   }
2364 }
2365
2366 //_____________________________________________________________________________
2367 void AliReconstruction::FillRawDataErrorLog(Int_t iEvent, AliESDEvent* esd)
2368 {
2369   // The method reads the raw-data error log
2370   // accumulated within the rawReader.
2371   // It extracts the raw-data errors related to
2372   // the current event and stores them into
2373   // a TClonesArray inside the esd object.
2374
2375   if (!fRawReader) return;
2376
2377   for(Int_t i = 0; i < fRawReader->GetNumberOfErrorLogs(); i++) {
2378
2379     AliRawDataErrorLog *log = fRawReader->GetErrorLog(i);
2380     if (!log) continue;
2381     if (iEvent != log->GetEventNumber()) continue;
2382
2383     esd->AddRawDataErrorLog(log);
2384   }
2385
2386 }
2387
2388 TNamed* AliReconstruction::CopyFileToTNamed(TString fPath,TString fName){
2389   // Dump a file content into a char in TNamed
2390   ifstream in;
2391   in.open(fPath.Data(),ios::in | ios::binary|ios::ate);
2392   Int_t kBytes = (Int_t)in.tellg();
2393   printf("Size: %d \n",kBytes);
2394   TNamed *fn = 0;
2395   if(in.good()){
2396     char* memblock = new char [kBytes];
2397     in.seekg (0, ios::beg);
2398     in.read (memblock, kBytes);
2399     in.close();
2400     TString fData(memblock,kBytes);
2401     fn = new TNamed(fName,fData);
2402     printf("fData Size: %d \n",fData.Sizeof());
2403     printf("fName Size: %d \n",fName.Sizeof());
2404     printf("fn    Size: %d \n",fn->Sizeof());
2405     delete[] memblock;
2406   }
2407   else{
2408     AliInfo(Form("Could not Open %s\n",fPath.Data()));
2409   }
2410
2411   return fn;
2412 }
2413
2414 void AliReconstruction::TNamedToFile(TTree* fTree, TString fName){
2415   // This is not really needed in AliReconstruction at the moment
2416   // but can serve as a template
2417
2418   TList *fList = fTree->GetUserInfo();
2419   TNamed *fn = (TNamed*)fList->FindObject(fName.Data());
2420   printf("fn Size: %d \n",fn->Sizeof());
2421
2422   TString fTmp(fn->GetName()); // to be 100% sure in principle fName also works
2423   const char* cdata = fn->GetTitle();
2424   printf("fTmp Size %d\n",fTmp.Sizeof());
2425
2426   int size = fn->Sizeof()-fTmp.Sizeof()-sizeof(UChar_t)-sizeof(Int_t); // see dfinition of TString::SizeOf()...
2427   printf("calculated size %d\n",size);
2428   ofstream out(fName.Data(),ios::out | ios::binary);
2429   out.write(cdata,size);
2430   out.close();
2431
2432 }
2433   
2434 //_____________________________________________________________________________
2435 AliQADataMakerRec * AliReconstruction::GetQADataMaker(Int_t iDet)
2436 {
2437  // get the quality assurance data maker object and the loader for a detector
2438
2439   if (fQADataMaker[iDet]) 
2440     return fQADataMaker[iDet];
2441
2442   AliQADataMakerRec * qadm = NULL;
2443   if (iDet == fgkNDetectors) { //Global QA
2444      qadm = new AliGlobalQADataMaker();
2445      fQADataMaker[iDet] = qadm;
2446      return qadm;
2447   }
2448
2449   // load the QA data maker object
2450   TPluginManager* pluginManager = gROOT->GetPluginManager();
2451   TString detName = fgkDetectorName[iDet];
2452   TString qadmName = "Ali" + detName + "QADataMakerRec";
2453   if (gAlice && !gAlice->GetDetector(detName) && (detName != "HLT")) 
2454     return NULL;
2455
2456   // first check if a plugin is defined for the quality assurance data maker
2457   TPluginHandler* pluginHandler = pluginManager->FindHandler("AliQADataMakerRec", detName);
2458   // if not, add a plugin for it
2459   if (!pluginHandler) {
2460     AliDebug(1, Form("defining plugin for %s", qadmName.Data()));
2461     TString libs = gSystem->GetLibraries();
2462     if (libs.Contains("lib" + detName + "base.so") ||
2463         (gSystem->Load("lib" + detName + "base.so") >= 0)) {
2464       pluginManager->AddHandler("AliQADataMakerRec", detName, 
2465                                 qadmName, detName + "qadm", qadmName + "()");
2466     } else {
2467       pluginManager->AddHandler("AliQADataMakerRec", detName, 
2468                                 qadmName, detName, qadmName + "()");
2469     }
2470     pluginHandler = pluginManager->FindHandler("AliQADataMakerRec", detName);
2471   }
2472   if (pluginHandler && (pluginHandler->LoadPlugin() == 0)) {
2473     qadm = (AliQADataMakerRec *) pluginHandler->ExecPlugin(0);
2474   }
2475
2476   fQADataMaker[iDet] = qadm;
2477
2478   return qadm;
2479 }
2480
2481 //_____________________________________________________________________________
2482 Bool_t AliReconstruction::RunQA(const char* detectors, AliESDEvent *& esd)
2483 {
2484   // run the Quality Assurance data producer
2485
2486   AliCodeTimerAuto("")
2487   TString detStr = detectors;
2488   for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
2489    if (!IsSelected(fgkDetectorName[iDet], detStr)) 
2490      continue;
2491    AliQADataMakerRec * qadm = GetQADataMaker(iDet);
2492    if (!qadm) 
2493      continue;
2494    AliCodeTimerStart(Form("running quality assurance data maker for %s", fgkDetectorName[iDet]));
2495    AliInfo(Form("running quality assurance data maker for %s", fgkDetectorName[iDet]));
2496     
2497    qadm->Exec(AliQA::kESDS, esd) ; 
2498    qadm->Increment() ; 
2499
2500    AliCodeTimerStop(Form("running quality assurance data maker for %s", fgkDetectorName[iDet]));
2501  }
2502  if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
2503    AliError(Form("the following detectors were not found: %s",
2504                  detStr.Data()));
2505    if (fStopOnError) 
2506      return kFALSE;
2507  }
2508  
2509  return kTRUE;
2510   
2511 }
2512
2513 //_____________________________________________________________________________
2514 void AliReconstruction::CheckQA()
2515 {
2516 // check the QA of SIM for this run and remove the detectors 
2517 // with status Fatal
2518   
2519         TString newRunLocalReconstruction ; 
2520         TString newRunTracking ;
2521         TString newFillESD ;
2522          
2523         for (Int_t iDet = 0; iDet < AliQA::kNDET; iDet++) {
2524                 TString detName(AliQA::GetDetName(iDet)) ;
2525                 AliQA * qa = AliQA::Instance(AliQA::DETECTORINDEX_t(iDet)) ; 
2526                 if ( qa->IsSet(AliQA::DETECTORINDEX_t(iDet), AliQA::kSIM, AliQA::kFATAL)) {
2527                                 AliInfo(Form("QA status for %s in Hits and/or SDIGITS  and/or Digits was Fatal; No reconstruction performed", detName.Data())) ;
2528                 } else {
2529                         if ( fRunLocalReconstruction.Contains(AliQA::GetDetName(iDet)) || 
2530                                         fRunLocalReconstruction.Contains("ALL") )  {
2531                                 newRunLocalReconstruction += detName ; 
2532                                 newRunLocalReconstruction += " " ;                      
2533                         }
2534                         if ( fRunTracking.Contains(AliQA::GetDetName(iDet)) || 
2535                                         fRunTracking.Contains("ALL") )  {
2536                                 newRunTracking += detName ; 
2537                                 newRunTracking += " " ;                         
2538                         }
2539                         if ( fFillESD.Contains(AliQA::GetDetName(iDet)) || 
2540                                         fFillESD.Contains("ALL") )  {
2541                                 newFillESD += detName ; 
2542                                 newFillESD += " " ;                     
2543                         }
2544                 }
2545         }
2546         fRunLocalReconstruction = newRunLocalReconstruction ; 
2547         fRunTracking            = newRunTracking ; 
2548         fFillESD                = newFillESD ; 
2549 }
2550
2551 //_____________________________________________________________________________
2552 Int_t AliReconstruction::GetDetIndex(const char* detector)
2553 {
2554   // return the detector index corresponding to detector
2555   Int_t index = -1 ; 
2556   for (index = 0; index < fgkNDetectors ; index++) {
2557     if ( strcmp(detector, fgkDetectorName[index]) == 0 )
2558         break ; 
2559   }     
2560   return index ; 
2561 }
2562 //_____________________________________________________________________________
2563 Bool_t AliReconstruction::FinishPlaneEff() {
2564  //
2565  // Here execute all the necessary operationis, at the end of the tracking phase,
2566  // in case that evaluation of PlaneEfficiencies was required for some detector. 
2567  // E.g., write into a DataBase file the PlaneEfficiency which have been evaluated. 
2568  //
2569  // This Preliminary version works only FOR ITS !!!!!
2570  // other detectors (TOF,TRD, etc. have to develop their specific codes)
2571  //
2572  //  Input: none
2573  //  Return: kTRUE if all operations have been done properly, kFALSE otherwise 
2574  //
2575  Bool_t ret=kFALSE;
2576  //for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
2577  for (Int_t iDet = 0; iDet < 1; iDet++) { // for the time being only ITS  
2578    //if (!IsSelected(fgkDetectorName[iDet], detStr)) continue;
2579    if(fTracker[iDet]) {
2580       AliPlaneEff *planeeff=fTracker[iDet]->GetPlaneEff(); 
2581       ret=planeeff->WriteIntoCDB();
2582       if(planeeff->GetCreateHistos()) {
2583         TString name="PlaneEffHisto";
2584         name+=fgkDetectorName[iDet];
2585         name+=".root";
2586         ret*=planeeff->WriteHistosToFile(name,"RECREATE");
2587       }
2588    }
2589  }
2590  return ret;
2591 }
2592 //_____________________________________________________________________________
2593 Bool_t AliReconstruction::InitPlaneEff() {
2594 //
2595  // Here execute all the necessary operations, before of the tracking phase,
2596  // for the evaluation of PlaneEfficiencies, in case required for some detectors.
2597  // E.g., read from a DataBase file a first evaluation of the PlaneEfficiency 
2598  // which should be updated/recalculated.
2599  //
2600  // This Preliminary version will work only FOR ITS !!!!!
2601  // other detectors (TOF,TRD, etc. have to develop their specific codes)
2602  //
2603  //  Input: none
2604  //  Return: kTRUE if all operations have been done properly, kFALSE otherwise
2605  //
2606  AliWarning(Form("Implementation of this method not yet done !! Method return kTRUE"));
2607  return kTRUE;
2608 }