]> git.uio.no Git - u/mrichter/AliRoot.git/blob - STEER/AliReconstruction.cxx
Adding list of detectors in DAQ and reco to the ESD. See bug #65738.
[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 //                                                                           //
109 ///////////////////////////////////////////////////////////////////////////////
110
111 #include <TArrayD.h>
112 #include <TArrayF.h>
113 #include <TArrayS.h>
114 #include <TChain.h>
115 #include <TFile.h>
116 #include <TGeoGlobalMagField.h>
117 #include <TGeoManager.h>
118 #include <TList.h>
119 #include <TLorentzVector.h>
120 #include <TMap.h>
121 #include <TObjArray.h>
122 #include <TPRegexp.h>
123 #include <TParameter.h>
124 #include <TPluginManager.h>
125 #include <TProof.h>
126 #include <TProofOutputFile.h>
127 #include <TROOT.h>
128 #include <TSystem.h>
129 #include <THashTable.h>
130 #include <TGrid.h>
131 #include <TMessage.h>
132 #include <TUrl.h>
133
134 #include "AliAlignObj.h"
135 #include "AliCDBEntry.h"
136 #include "AliCDBManager.h"
137 #include "AliCDBStorage.h"
138 #include "AliCTPRawStream.h"
139 #include "AliCascadeVertexer.h"
140 #include "AliCentralTrigger.h"
141 #include "AliCodeTimer.h"
142 #include "AliDAQ.h"
143 #include "AliDetectorRecoParam.h"
144 #include "AliESDCaloCells.h"
145 #include "AliESDCaloCluster.h"
146 #include "AliESDEvent.h"
147 #include "AliESDMuonTrack.h"
148 #include "AliESDPmdTrack.h"
149 #include "AliESDTagCreator.h"
150 #include "AliESDVertex.h"
151 #include "AliESDcascade.h"
152 #include "AliESDfriend.h"
153 #include "AliESDkink.h"
154 #include "AliESDpid.h"
155 #include "AliESDtrack.h"
156 #include "AliESDtrack.h"
157 #include "AliEventInfo.h"
158 #include "AliGRPObject.h"
159 #include "AliGRPRecoParam.h"
160 #include "AliGenEventHeader.h"
161 #include "AliGeomManager.h"
162 #include "AliGlobalQADataMaker.h" 
163 #include "AliHeader.h"
164 #include "AliLog.h"
165 #include "AliMagF.h"
166 #include "AliMultiplicity.h"
167 #include "AliPID.h"
168 #include "AliPlaneEff.h"
169 #include "AliQAv1.h"
170 #include "AliQADataMakerRec.h" 
171 #include "AliQAManager.h"
172 #include "AliRawVEvent.h"
173 #include "AliRawEventHeaderBase.h"
174 #include "AliRawHLTManager.h"
175 #include "AliRawReaderDate.h"
176 #include "AliRawReaderFile.h"
177 #include "AliRawReaderRoot.h"
178 #include "AliReconstruction.h"
179 #include "AliReconstructor.h"
180 #include "AliRun.h"
181 #include "AliRunInfo.h"
182 #include "AliRunLoader.h"
183 #include "AliSysInfo.h" // memory snapshots
184 #include "AliTrackPointArray.h"
185 #include "AliTracker.h"
186 #include "AliTriggerClass.h"
187 #include "AliTriggerCluster.h"
188 #include "AliTriggerIR.h"
189 #include "AliTriggerConfiguration.h"
190 #include "AliV0vertexer.h"
191 #include "AliVertexer.h"
192 #include "AliVertexerTracks.h"
193 #include "AliTriggerRunScalers.h"
194 #include "AliCTPTimeParams.h" 
195 #include "AliESDHLTDecision.h"
196 #include "AliTriggerInput.h"
197 ClassImp(AliReconstruction)
198
199 //_____________________________________________________________________________
200 const char* AliReconstruction::fgkDetectorName[AliReconstruction::kNDetectors] = {"ITS", "TPC", "TRD", "TOF", "PHOS", "HMPID", "EMCAL", "MUON", "FMD", "ZDC", "PMD", "T0", "VZERO", "ACORDE", "HLT"};
201
202 //_____________________________________________________________________________
203 AliReconstruction::AliReconstruction(const char* gAliceFilename) :
204   TSelector(),
205   fRunVertexFinder(kTRUE),
206   fRunVertexFinderTracks(kTRUE),
207   fRunHLTTracking(kFALSE),
208   fRunMuonTracking(kFALSE),
209   fRunV0Finder(kTRUE),
210   fRunCascadeFinder(kTRUE),
211   fStopOnError(kTRUE),
212   fWriteAlignmentData(kFALSE),
213   fWriteESDfriend(kFALSE),
214   fFillTriggerESD(kTRUE),
215
216   fCleanESD(kTRUE),
217   fV0DCAmax(3.),
218   fV0CsPmin(0.),
219   fDmax(50.),
220   fZmax(50.),
221
222   fRunLocalReconstruction("ALL"),
223   fRunTracking("ALL"),
224   fFillESD("ALL"),
225   fLoadCDB(""),
226   fUseTrackingErrorsForAlignment(""),
227   fGAliceFileName(gAliceFilename),
228   fRawInput(""),
229   fESDOutput(""),
230   fProofOutputFileName(""),
231   fProofOutputLocation(""),
232   fProofOutputDataset(kFALSE),
233   fProofOutputArchive(""),
234   fEquipIdMap(""),
235   fFirstEvent(0),
236   fLastEvent(-1),
237   fNumberOfEventsPerFile((UInt_t)-1),
238   fOptions(),
239   fLoadAlignFromCDB(kTRUE),
240   fLoadAlignData("ALL"),
241   fUseHLTData(),
242   fRunInfo(NULL),
243   fEventInfo(),
244   fRunScalers(NULL),
245   fCTPTimeParams(NULL),  
246
247   fRunLoader(NULL),
248   fRawReader(NULL),
249   fParentRawReader(NULL),
250
251   fRecoParam(),
252
253   fSPDTrackleter(NULL),
254
255   fDiamondProfileSPD(NULL),
256   fDiamondProfile(NULL),
257   fDiamondProfileTPC(NULL),
258   fListOfCosmicTriggers(NULL),
259   
260   fGRPData(NULL),
261
262   fAlignObjArray(NULL),
263   fCDBUri(),
264   fQARefUri(),
265   fSpecCDBUri(), 
266   fInitCDBCalled(kFALSE),
267   fSetRunNumberFromDataCalled(kFALSE),
268   fQADetectors("ALL"), 
269   fQATasks("ALL"), 
270   fRunQA(kTRUE),  
271   fRunGlobalQA(kTRUE),
272   fSameQACycle(kFALSE),
273   fInitQACalled(kFALSE), 
274   fWriteQAExpertData(kTRUE), 
275   fRunPlaneEff(kFALSE),
276
277   fesd(NULL),
278   fhltesd(NULL),
279   fesdf(NULL),
280   ffile(NULL),
281   ffileF(NULL),
282   ftree(NULL),
283   ftreeF(NULL),
284   fhlttree(NULL),
285   ftVertexer(NULL),
286   fIsNewRunLoader(kFALSE),
287   fRunAliEVE(kFALSE),
288   fChain(NULL)
289 {
290 // create reconstruction object with default parameters
291   gGeoManager = NULL;
292   
293   for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
294     fReconstructor[iDet] = NULL;
295     fLoader[iDet] = NULL;
296     fTracker[iDet] = NULL;
297   }
298   for (Int_t iDet = 0; iDet < AliQAv1::kNDET; iDet++) {
299     fQACycles[iDet] = 999999 ;
300     fQAWriteExpert[iDet] = kFALSE ; 
301   }
302     
303   AliPID pid;
304 }
305
306 //_____________________________________________________________________________
307 AliReconstruction::AliReconstruction(const AliReconstruction& rec) :
308   TSelector(),
309   fRunVertexFinder(rec.fRunVertexFinder),
310   fRunVertexFinderTracks(rec.fRunVertexFinderTracks),
311   fRunHLTTracking(rec.fRunHLTTracking),
312   fRunMuonTracking(rec.fRunMuonTracking),
313   fRunV0Finder(rec.fRunV0Finder),
314   fRunCascadeFinder(rec.fRunCascadeFinder),
315   fStopOnError(rec.fStopOnError),
316   fWriteAlignmentData(rec.fWriteAlignmentData),
317   fWriteESDfriend(rec.fWriteESDfriend),
318   fFillTriggerESD(rec.fFillTriggerESD),
319
320   fCleanESD(rec.fCleanESD),
321   fV0DCAmax(rec.fV0DCAmax),
322   fV0CsPmin(rec.fV0CsPmin),
323   fDmax(rec.fDmax),
324   fZmax(rec.fZmax),
325
326   fRunLocalReconstruction(rec.fRunLocalReconstruction),
327   fRunTracking(rec.fRunTracking),
328   fFillESD(rec.fFillESD),
329   fLoadCDB(rec.fLoadCDB),
330   fUseTrackingErrorsForAlignment(rec.fUseTrackingErrorsForAlignment),
331   fGAliceFileName(rec.fGAliceFileName),
332   fRawInput(rec.fRawInput),
333   fESDOutput(rec.fESDOutput),
334   fProofOutputFileName(rec.fProofOutputFileName),
335   fProofOutputLocation(rec.fProofOutputLocation),
336   fProofOutputDataset(rec.fProofOutputDataset),
337   fProofOutputArchive(rec.fProofOutputArchive),
338   fEquipIdMap(rec.fEquipIdMap),
339   fFirstEvent(rec.fFirstEvent),
340   fLastEvent(rec.fLastEvent),
341   fNumberOfEventsPerFile(rec.fNumberOfEventsPerFile),
342   fOptions(),
343   fLoadAlignFromCDB(rec.fLoadAlignFromCDB),
344   fLoadAlignData(rec.fLoadAlignData),
345   fUseHLTData(rec.fUseHLTData),
346   fRunInfo(NULL),
347   fEventInfo(),
348   fRunScalers(NULL),
349   fCTPTimeParams(NULL),
350
351   fRunLoader(NULL),
352   fRawReader(NULL),
353   fParentRawReader(NULL),
354
355   fRecoParam(rec.fRecoParam),
356
357   fSPDTrackleter(NULL),
358
359   fDiamondProfileSPD(rec.fDiamondProfileSPD),
360   fDiamondProfile(rec.fDiamondProfile),
361   fDiamondProfileTPC(rec.fDiamondProfileTPC),
362   fListOfCosmicTriggers(NULL),
363   
364   fGRPData(NULL),
365
366   fAlignObjArray(rec.fAlignObjArray),
367   fCDBUri(rec.fCDBUri),
368   fQARefUri(rec.fQARefUri),
369   fSpecCDBUri(), 
370   fInitCDBCalled(rec.fInitCDBCalled),
371   fSetRunNumberFromDataCalled(rec.fSetRunNumberFromDataCalled),
372   fQADetectors(rec.fQADetectors), 
373   fQATasks(rec.fQATasks), 
374   fRunQA(rec.fRunQA),  
375   fRunGlobalQA(rec.fRunGlobalQA),
376   fSameQACycle(rec.fSameQACycle),
377   fInitQACalled(rec.fInitQACalled),
378   fWriteQAExpertData(rec.fWriteQAExpertData), 
379   fRunPlaneEff(rec.fRunPlaneEff),
380
381   fesd(NULL),
382   fhltesd(NULL),
383   fesdf(NULL),
384   ffile(NULL),
385   ffileF(NULL),
386   ftree(NULL),
387   ftreeF(NULL),
388   fhlttree(NULL),
389   ftVertexer(NULL),
390   fIsNewRunLoader(rec.fIsNewRunLoader),
391   fRunAliEVE(kFALSE),
392   fChain(NULL)
393 {
394 // copy constructor
395
396   for (Int_t i = 0; i < rec.fOptions.GetEntriesFast(); i++) {
397     if (rec.fOptions[i]) fOptions.Add(rec.fOptions[i]->Clone());
398   }
399   for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
400     fReconstructor[iDet] = NULL;
401     fLoader[iDet] = NULL;
402     fTracker[iDet] = NULL;
403   }  
404   
405   for (Int_t iDet = 0; iDet < AliQAv1::kNDET; iDet++) {
406     fQACycles[iDet] = rec.fQACycles[iDet];
407     fQAWriteExpert[iDet] = rec.fQAWriteExpert[iDet] ; 
408   }
409
410   for (Int_t i = 0; i < rec.fSpecCDBUri.GetEntriesFast(); i++) {
411     if (rec.fSpecCDBUri[i]) fSpecCDBUri.Add(rec.fSpecCDBUri[i]->Clone());
412   }
413 }
414
415 //_____________________________________________________________________________
416 AliReconstruction& AliReconstruction::operator = (const AliReconstruction& rec)
417 {
418 // assignment operator
419 // Used in PROOF mode
420 // Be very careful while modifing it!
421 // Simple rules to follow:
422 // for persistent data members - use their assignment operators
423 // for non-persistent ones - do nothing or take the default values from constructor
424 // TSelector members should not be touched
425   if(&rec == this) return *this;
426
427   fRunVertexFinder       = rec.fRunVertexFinder;
428   fRunVertexFinderTracks = rec.fRunVertexFinderTracks;
429   fRunHLTTracking        = rec.fRunHLTTracking;
430   fRunMuonTracking       = rec.fRunMuonTracking;
431   fRunV0Finder           = rec.fRunV0Finder;
432   fRunCascadeFinder      = rec.fRunCascadeFinder;
433   fStopOnError           = rec.fStopOnError;
434   fWriteAlignmentData    = rec.fWriteAlignmentData;
435   fWriteESDfriend        = rec.fWriteESDfriend;
436   fFillTriggerESD        = rec.fFillTriggerESD;
437
438   fCleanESD  = rec.fCleanESD;
439   fV0DCAmax  = rec.fV0DCAmax;
440   fV0CsPmin  = rec.fV0CsPmin;
441   fDmax      = rec.fDmax;
442   fZmax      = rec.fZmax;
443
444   fRunLocalReconstruction        = rec.fRunLocalReconstruction;
445   fRunTracking                   = rec.fRunTracking;
446   fFillESD                       = rec.fFillESD;
447   fLoadCDB                       = rec.fLoadCDB;
448   fUseTrackingErrorsForAlignment = rec.fUseTrackingErrorsForAlignment;
449   fGAliceFileName                = rec.fGAliceFileName;
450   fRawInput                      = rec.fRawInput;
451   fESDOutput                     = rec.fESDOutput;
452   fProofOutputFileName           = rec.fProofOutputFileName;
453   fProofOutputLocation           = rec.fProofOutputLocation;
454   fProofOutputDataset            = rec.fProofOutputDataset;
455   fProofOutputArchive            = rec.fProofOutputArchive;
456   fEquipIdMap                    = rec.fEquipIdMap;
457   fFirstEvent                    = rec.fFirstEvent;
458   fLastEvent                     = rec.fLastEvent;
459   fNumberOfEventsPerFile         = rec.fNumberOfEventsPerFile;
460
461   for (Int_t i = 0; i < rec.fOptions.GetEntriesFast(); i++) {
462     if (rec.fOptions[i]) fOptions.Add(rec.fOptions[i]->Clone());
463   }
464
465   fLoadAlignFromCDB              = rec.fLoadAlignFromCDB;
466   fLoadAlignData                 = rec.fLoadAlignData;
467   fUseHLTData                    = rec.fUseHLTData;
468
469   delete fRunInfo; fRunInfo = NULL;
470   if (rec.fRunInfo) fRunInfo = new AliRunInfo(*rec.fRunInfo);
471
472   fEventInfo                     = rec.fEventInfo;
473
474   delete fRunScalers; fRunScalers = NULL;
475   if (rec.fRunScalers) fRunScalers = new AliTriggerRunScalers(*rec.fRunScalers); 
476
477   delete fCTPTimeParams; fCTPTimeParams = NULL;
478   if (rec.fCTPTimeParams) fCTPTimeParams = new AliCTPTimeParams(*rec.fCTPTimeParams);
479
480   fRunLoader       = NULL;
481   fRawReader       = NULL;
482   fParentRawReader = NULL;
483
484   fRecoParam = rec.fRecoParam;
485
486   for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
487     delete fReconstructor[iDet]; fReconstructor[iDet] = NULL;
488     delete fLoader[iDet]; fLoader[iDet] = NULL;
489     delete fTracker[iDet]; fTracker[iDet] = NULL;
490   }
491   
492   for (Int_t iDet = 0; iDet < AliQAv1::kNDET; iDet++) {
493     fQACycles[iDet] = rec.fQACycles[iDet];
494     fQAWriteExpert[iDet] = rec.fQAWriteExpert[iDet] ;
495   } 
496
497   delete fSPDTrackleter; fSPDTrackleter = NULL;
498     
499   delete fDiamondProfileSPD; fDiamondProfileSPD = NULL;
500   if (rec.fDiamondProfileSPD) fDiamondProfileSPD = new AliESDVertex(*rec.fDiamondProfileSPD);
501   delete fDiamondProfile; fDiamondProfile = NULL;
502   if (rec.fDiamondProfile) fDiamondProfile = new AliESDVertex(*rec.fDiamondProfile);
503   delete fDiamondProfileTPC; fDiamondProfileTPC = NULL;
504   if (rec.fDiamondProfileTPC) fDiamondProfileTPC = new AliESDVertex(*rec.fDiamondProfileTPC);
505
506   delete fListOfCosmicTriggers; fListOfCosmicTriggers = NULL;
507   if (rec.fListOfCosmicTriggers) fListOfCosmicTriggers = (THashTable*)((rec.fListOfCosmicTriggers)->Clone());
508
509   delete fGRPData; fGRPData = NULL;
510   //  if (rec.fGRPData) fGRPData = (TMap*)((rec.fGRPData)->Clone());
511   if (rec.fGRPData) fGRPData = (AliGRPObject*)((rec.fGRPData)->Clone());
512
513   delete fAlignObjArray; fAlignObjArray = NULL;
514
515   fCDBUri        = "";
516   fQARefUri      = rec.fQARefUri;
517   fSpecCDBUri.Delete();
518   fInitCDBCalled               = rec.fInitCDBCalled;
519   fSetRunNumberFromDataCalled  = rec.fSetRunNumberFromDataCalled;
520   fQADetectors                 = rec.fQADetectors;
521   fQATasks                     = rec.fQATasks; 
522   fRunQA                       = rec.fRunQA;  
523   fRunGlobalQA                 = rec.fRunGlobalQA;
524   fSameQACycle                 = rec.fSameQACycle;
525   fInitQACalled                = rec.fInitQACalled;
526   fWriteQAExpertData           = rec.fWriteQAExpertData;
527   fRunPlaneEff                 = rec.fRunPlaneEff;
528
529   fesd     = NULL;
530   fhltesd  = NULL;
531   fesdf    = NULL;
532   ffile    = NULL;
533   ffileF   = NULL;
534   ftree    = NULL;
535   ftreeF   = NULL;
536   fhlttree = NULL;
537   ftVertexer = NULL;
538   fIsNewRunLoader = rec.fIsNewRunLoader;
539   fRunAliEVE = kFALSE;
540   fChain = NULL;
541
542   return *this;
543 }
544
545 //_____________________________________________________________________________
546 AliReconstruction::~AliReconstruction()
547 {
548 // clean up
549
550   CleanUp();
551   if (fListOfCosmicTriggers) {
552     fListOfCosmicTriggers->Delete();
553     delete fListOfCosmicTriggers;
554   }
555   delete fGRPData;
556   delete fRunScalers;
557   delete fCTPTimeParams;
558   fOptions.Delete();
559   if (fAlignObjArray) {
560     fAlignObjArray->Delete();
561     delete fAlignObjArray;
562   }
563   fSpecCDBUri.Delete();
564
565   AliCodeTimer::Instance()->Print();
566 }
567
568 //_____________________________________________________________________________
569 void AliReconstruction::InitQA()
570 {
571   //Initialize the QA and start of cycle 
572   AliCodeTimerAuto("",0);
573   
574   if (fInitQACalled) return;
575   fInitQACalled = kTRUE;
576   
577   AliQAManager * qam = AliQAManager::QAManager(AliQAv1::kRECMODE) ; 
578   if (fWriteQAExpertData)
579     qam->SetWriteExpert() ; 
580  
581   if (qam->IsDefaultStorageSet()) {
582     AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
583     AliWarning("Default QA reference storage has been already set !");
584     AliWarning(Form("Ignoring the default storage declared in AliReconstruction: %s",fQARefUri.Data()));
585     AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
586     fQARefUri = qam->GetDefaultStorage()->GetURI();
587   } else {
588     if (fQARefUri.Length() > 0) {
589         AliDebug(2,"!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
590         AliDebug(2, Form("Default QA reference storage is set to: %s", fQARefUri.Data()));
591         AliDebug(2, "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
592       } else {
593         fQARefUri="local://$ALICE_ROOT/QAref";
594         AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
595         AliWarning("Default QA refeference storage not yet set !!!!");
596         AliWarning(Form("Setting it now to: %s", fQARefUri.Data()));
597         AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
598                 
599       }
600     qam->SetDefaultStorage(fQARefUri);
601   }
602   
603   if (fRunQA) {
604   qam->SetActiveDetectors(fQADetectors) ; 
605   for (Int_t det = 0 ; det < AliQAv1::kNDET ; det++) {
606     qam->SetCycleLength(AliQAv1::DETECTORINDEX_t(det), fQACycles[det]) ;  
607     qam->SetWriteExpert(AliQAv1::DETECTORINDEX_t(det)) ;
608   }
609   if (!fRawReader && !fInput && IsInTasks(AliQAv1::kRAWS))
610     fQATasks.ReplaceAll(Form("%d",AliQAv1::kRAWS), "") ;
611   qam->SetTasks(fQATasks) ; 
612   qam->InitQADataMaker(AliCDBManager::Instance()->GetRun()) ; 
613   }
614   if (fRunGlobalQA) {
615     Bool_t sameCycle = kFALSE ;
616     AliQADataMaker *qadm = qam->GetQADataMaker(AliQAv1::kGLOBAL);
617     AliInfo(Form("Initializing the global QA data maker"));
618     if (IsInTasks(AliQAv1::kRECPOINTS)) {
619       qadm->StartOfCycle(AliQAv1::kRECPOINTS, AliCDBManager::Instance()->GetRun(), sameCycle) ; 
620       TObjArray **arr=qadm->Init(AliQAv1::kRECPOINTS);
621       AliTracker::SetResidualsArray(arr);
622       sameCycle = kTRUE ; 
623     }
624     if (IsInTasks(AliQAv1::kESDS)) {
625       qadm->StartOfCycle(AliQAv1::kESDS, AliCDBManager::Instance()->GetRun(), sameCycle) ; 
626       qadm->Init(AliQAv1::kESDS);
627     }
628   }
629     AliSysInfo::AddStamp("InitQA") ; 
630 }
631
632 //_____________________________________________________________________________
633 void AliReconstruction::MergeQA(const char *fileName)
634 {
635   //Initialize the QA and start of cycle 
636   AliCodeTimerAuto("",0) ;
637   AliQAManager::QAManager()->Merge(AliCDBManager::Instance()->GetRun(),fileName) ; 
638   AliSysInfo::AddStamp("MergeQA") ; 
639 }
640   
641 //_____________________________________________________________________________
642 void AliReconstruction::InitCDB()
643 {
644 // activate a default CDB storage
645 // First check if we have any CDB storage set, because it is used 
646 // to retrieve the calibration and alignment constants
647   AliCodeTimerAuto("",0);
648
649   if (fInitCDBCalled) return;
650   fInitCDBCalled = kTRUE;
651
652   AliCDBManager* man = AliCDBManager::Instance();
653   if (man->IsDefaultStorageSet())
654   {
655     AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
656     AliWarning("Default CDB storage has been already set !");
657     AliWarning(Form("Ignoring the default storage declared in AliReconstruction: %s",fCDBUri.Data()));
658     AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
659     fCDBUri = man->GetDefaultStorage()->GetURI();
660   }
661   else {
662     if (fCDBUri.Length() > 0) 
663     {
664         AliDebug(2,"!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
665         AliDebug(2, Form("Default CDB storage is set to: %s", fCDBUri.Data()));
666         AliDebug(2, "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
667         man->SetDefaultStorage(fCDBUri);
668     } 
669     else if (!man->GetRaw()){
670         fCDBUri="local://$ALICE_ROOT/OCDB";
671         AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
672         AliWarning("Default CDB storage not yet set !!!!");
673         AliWarning(Form("Setting it now to: %s", fCDBUri.Data()));
674         AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
675         man->SetDefaultStorage(fCDBUri);
676     }
677     else {    
678         AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
679         AliWarning("Default storage will be set after setting the Run Number!!!");
680         AliWarning("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");                    
681     }
682   }
683
684   // Now activate the detector specific CDB storage locations
685   for (Int_t i = 0; i < fSpecCDBUri.GetEntriesFast(); i++) {
686     TObject* obj = fSpecCDBUri[i];
687     if (!obj) continue;
688     AliDebug(2, "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
689     AliDebug(2, Form("Specific CDB storage for %s is set to: %s",obj->GetName(),obj->GetTitle()));
690     AliDebug(2, "!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!");
691     man->SetSpecificStorage(obj->GetName(), obj->GetTitle());
692   }
693   AliSysInfo::AddStamp("InitCDB");
694 }
695
696 //_____________________________________________________________________________
697 void AliReconstruction::SetDefaultStorage(const char* uri) {
698 // Store the desired default CDB storage location
699 // Activate it later within the Run() method
700
701   fCDBUri = uri;
702
703 }
704
705 //_____________________________________________________________________________
706 void AliReconstruction::SetQARefDefaultStorage(const char* uri) {
707   // Store the desired default CDB storage location
708   // Activate it later within the Run() method
709   
710   fQARefUri = uri;
711   AliQAv1::SetQARefStorage(fQARefUri.Data()) ;
712   
713 }
714 //_____________________________________________________________________________
715 void AliReconstruction::SetSpecificStorage(const char* calibType, const char* uri) {
716 // Store a detector-specific CDB storage location
717 // Activate it later within the Run() method
718
719   AliCDBPath aPath(calibType);
720   if(!aPath.IsValid()){
721         // if calibType is not wildcard but it is a valid detector, add "/*" to make it a valid path
722         for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
723                 if(!strcmp(calibType, fgkDetectorName[iDet])) {
724                         aPath.SetPath(Form("%s/*", calibType));
725                         AliInfo(Form("Path for specific storage set to %s", aPath.GetPath().Data()));
726                         break;
727                 }
728         }
729         if(!aPath.IsValid()){
730                 AliError(Form("Not a valid path or detector: %s", calibType));
731                 return;
732         }
733   }
734
735 //  // check that calibType refers to a "valid" detector name
736 //  Bool_t isDetector = kFALSE;
737 //  for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
738 //    TString detName = fgkDetectorName[iDet];
739 //    if(aPath.GetLevel0() == detName) {
740 //      isDetector = kTRUE;
741 //      break;
742 //    }
743 //  }
744 //
745 //  if(!isDetector) {
746 //      AliError(Form("Not a valid detector: %s", aPath.GetLevel0().Data()));
747 //      return;
748 //  }
749
750   TObject* obj = fSpecCDBUri.FindObject(aPath.GetPath().Data());
751   if (obj) fSpecCDBUri.Remove(obj);
752   fSpecCDBUri.Add(new TNamed(aPath.GetPath().Data(), uri));
753
754 }
755
756 //_____________________________________________________________________________
757 Bool_t AliReconstruction::SetRunNumberFromData()
758 {
759   // The method is called in Run() in order
760   // to set a correct run number.
761   // In case of raw data reconstruction the
762   // run number is taken from the raw data header
763
764   if (fSetRunNumberFromDataCalled) return kTRUE;
765   fSetRunNumberFromDataCalled = kTRUE;
766   
767   AliCDBManager* man = AliCDBManager::Instance();
768  
769   if(fRawReader) {
770     if(fRawReader->NextEvent()) {
771       if(man->GetRun() > 0) {
772         AliWarning("Run number is taken from raw-event header! Ignoring settings in AliCDBManager!");
773       } 
774       man->SetRun(fRawReader->GetRunNumber());
775       fRawReader->RewindEvents();
776     }
777     else {
778       if(man->GetRun() > 0) {
779         AliWarning("No raw-data events are found ! Using settings in AliCDBManager !");
780       }
781       else {
782         AliWarning("Neither raw events nor settings in AliCDBManager are found !");
783         return kFALSE;
784       }
785     }
786   }
787   else {
788     AliRunLoader *rl = AliRunLoader::Open(fGAliceFileName.Data());
789     if (!rl) {
790       AliError(Form("No run loader found in file %s", fGAliceFileName.Data()));
791       return kFALSE;
792     }
793     else {
794       rl->LoadHeader();
795       // read run number from gAlice
796       if(rl->GetHeader()) {
797         man->SetRun(rl->GetHeader()->GetRun());
798         rl->UnloadHeader();
799         delete rl;
800       }
801       else {
802         AliError("Neither run-loader header nor RawReader objects are found !");
803         delete rl;
804         return kFALSE;
805       }
806     }
807   }
808
809   man->Print();  
810   
811   return kTRUE;
812 }
813
814 //_____________________________________________________________________________
815 void AliReconstruction::SetCDBLock() {
816   // Set CDB lock: from now on it is forbidden to reset the run number
817   // or the default storage or to activate any further storage!
818   
819   AliCDBManager::Instance()->SetLock(1);
820 }
821
822 //_____________________________________________________________________________
823 Bool_t AliReconstruction::MisalignGeometry(const TString& detectors)
824 {
825   // Read the alignment objects from CDB.
826   // Each detector is supposed to have the
827   // alignment objects in DET/Align/Data CDB path.
828   // All the detector objects are then collected,
829   // sorted by geometry level (starting from ALIC) and
830   // then applied to the TGeo geometry.
831   // Finally an overlaps check is performed.
832
833   // Load alignment data from CDB and fill fAlignObjArray 
834   if(fLoadAlignFromCDB){
835         
836     TString detStr = detectors;
837     TString loadAlObjsListOfDets = "";
838     
839     for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
840       if(!IsSelected(fgkDetectorName[iDet], detStr)) continue;
841       if(!strcmp(fgkDetectorName[iDet],"HLT")) continue;
842       
843       if(AliGeomManager::GetNalignable(fgkDetectorName[iDet]) != 0)
844       {
845         loadAlObjsListOfDets += fgkDetectorName[iDet];
846         loadAlObjsListOfDets += " ";
847       }
848     } // end loop over detectors
849     
850     if(AliGeomManager::GetNalignable("GRP") != 0)
851       loadAlObjsListOfDets.Prepend("GRP "); //add alignment objects for non-sensitive modules
852     AliGeomManager::ApplyAlignObjsFromCDB(loadAlObjsListOfDets.Data());
853     AliCDBManager::Instance()->UnloadFromCache("*/Align/*");
854   }else{
855     // Check if the array with alignment objects was
856     // provided by the user. If yes, apply the objects
857     // to the present TGeo geometry
858     if (fAlignObjArray) {
859       if (gGeoManager && gGeoManager->IsClosed()) {
860         if (AliGeomManager::ApplyAlignObjsToGeom(*fAlignObjArray) == kFALSE) {
861           AliError("The misalignment of one or more volumes failed!"
862                    "Compare the list of simulated detectors and the list of detector alignment data!");
863           return kFALSE;
864         }
865       }
866       else {
867         AliError("Can't apply the misalignment! gGeoManager doesn't exist or it is still opened!");
868         return kFALSE;
869       }
870     }
871   }
872   
873   if (fAlignObjArray) {
874     fAlignObjArray->Delete();
875     delete fAlignObjArray; fAlignObjArray=NULL;
876   }
877
878   return kTRUE;
879 }
880
881 //_____________________________________________________________________________
882 void AliReconstruction::SetGAliceFile(const char* fileName)
883 {
884 // set the name of the galice file
885
886   fGAliceFileName = fileName;
887 }
888
889 //_____________________________________________________________________________
890 void AliReconstruction::SetInput(const char* input) 
891 {
892   // In case the input string starts with 'mem://', we run in an online mode
893   // and AliRawReaderDateOnline object is created. In all other cases a raw-data
894   // file is assumed. One can give as an input:
895   // mem://: - events taken from DAQ monitoring libs online
896   //  or
897   // mem://<filename> - emulation of the above mode (via DATE monitoring libs)
898   if (input) fRawInput = input;
899 }
900
901 //_____________________________________________________________________________
902 void AliReconstruction::SetOutput(const char* output) 
903 {
904   // Set the output ESD filename
905   // 'output' is a normalt ROOT url
906   // The method is used in case of raw-data reco with PROOF
907   if (output) fESDOutput = output;
908 }
909
910 //_____________________________________________________________________________
911 void AliReconstruction::SetOption(const char* detector, const char* option)
912 {
913 // set options for the reconstruction of a detector
914
915   TObject* obj = fOptions.FindObject(detector);
916   if (obj) fOptions.Remove(obj);
917   fOptions.Add(new TNamed(detector, option));
918 }
919
920 //_____________________________________________________________________________
921 void AliReconstruction::SetRecoParam(const char* detector, AliDetectorRecoParam *par)
922 {
923   // Set custom reconstruction parameters for a given detector
924   // Single set of parameters for all the events
925
926   // First check if the reco-params are global
927   if(!strcmp(detector, "GRP")) {
928     par->SetAsDefault();
929     fRecoParam.AddDetRecoParam(kNDetectors,par);
930     return;
931   }
932
933   for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
934     if(!strcmp(detector, fgkDetectorName[iDet])) {
935       par->SetAsDefault();
936       fRecoParam.AddDetRecoParam(iDet,par);
937       break;
938     }
939   }
940
941 }
942
943 //_____________________________________________________________________________
944 Bool_t AliReconstruction::InitGRP() {
945   //------------------------------------
946   // Initialization of the GRP entry 
947   //------------------------------------
948   AliCDBEntry* entry = AliCDBManager::Instance()->Get("GRP/GRP/Data");
949
950   if (entry) {
951
952     TMap* m = dynamic_cast<TMap*>(entry->GetObject());  // old GRP entry
953
954     if (m) {
955        AliInfo("Found a TMap in GRP/GRP/Data, converting it into an AliGRPObject");
956        m->Print();
957        fGRPData = new AliGRPObject();
958        fGRPData->ReadValuesFromMap(m);
959     }
960
961     else {
962        AliInfo("Found an AliGRPObject in GRP/GRP/Data, reading it");
963        fGRPData = dynamic_cast<AliGRPObject*>(entry->GetObject());  // new GRP entry
964        entry->SetOwner(0);
965     }
966
967     //    FIX ME: The unloading of GRP entry is temporarily disabled
968     //    because ZDC and VZERO are using it in order to initialize
969     //    their reconstructor objects. In the future one has to think
970     //    of propagating AliRunInfo to the reconstructors.
971     //    AliCDBManager::Instance()->UnloadFromCache("GRP/GRP/Data");
972   }
973
974   if (!fGRPData) {
975      AliError("No GRP entry found in OCDB!");
976      return kFALSE;
977   }
978
979   TString lhcState = fGRPData->GetLHCState();
980   if (lhcState==AliGRPObject::GetInvalidString()) {
981     AliError("GRP/GRP/Data entry:  missing value for the LHC state ! Using UNKNOWN");
982     lhcState = "UNKNOWN";
983   }
984
985   TString beamType = fGRPData->GetBeamType();
986   if (beamType==AliGRPObject::GetInvalidString()) {
987     AliError("GRP/GRP/Data entry:  missing value for the beam type ! Using UNKNOWN");
988     beamType = "UNKNOWN";
989   }
990
991   Float_t beamEnergy = fGRPData->GetBeamEnergy();
992   if (beamEnergy==AliGRPObject::GetInvalidFloat()) {
993     AliError("GRP/GRP/Data entry:  missing value for the beam energy ! Using 0");
994     beamEnergy = 0;
995   }
996
997   TString runType = fGRPData->GetRunType();
998   if (runType==AliGRPObject::GetInvalidString()) {
999     AliError("GRP/GRP/Data entry:  missing value for the run type ! Using UNKNOWN");
1000     runType = "UNKNOWN";
1001   }
1002
1003   Int_t activeDetectors = fGRPData->GetDetectorMask();
1004   if (activeDetectors==AliGRPObject::GetInvalidUInt()) {
1005     AliError("GRP/GRP/Data entry:  missing value for the detector mask ! Using 1074790399");
1006     activeDetectors = 1074790399;
1007   }
1008
1009   fRunInfo = new AliRunInfo(lhcState, beamType, beamEnergy, runType, activeDetectors);
1010   fRunInfo->Dump();
1011
1012
1013   // Process the list of active detectors
1014   if (activeDetectors) {
1015     UInt_t detMask = activeDetectors;
1016     fRunLocalReconstruction = MatchDetectorList(fRunLocalReconstruction,detMask);
1017     fRunTracking = MatchDetectorList(fRunTracking,detMask);
1018     fFillESD = MatchDetectorList(fFillESD,detMask);
1019     fQADetectors = MatchDetectorList(fQADetectors,detMask);
1020     fLoadCDB.Form("%s %s %s %s",
1021                   fRunLocalReconstruction.Data(),
1022                   fRunTracking.Data(),
1023                   fFillESD.Data(),
1024                   fQADetectors.Data());
1025     fLoadCDB = MatchDetectorList(fLoadCDB,detMask);
1026     if (!((detMask >> AliDAQ::DetectorID("ITSSPD")) & 0x1) &&
1027         !((detMask >> AliDAQ::DetectorID("ITSSDD")) & 0x1) &&
1028         !((detMask >> AliDAQ::DetectorID("ITSSSD")) & 0x1) ) {
1029       // switch off the vertexer
1030       AliInfo("SPD,SDD,SSD is not in the list of active detectors. Vertexer switched off.");
1031       fRunVertexFinder = kFALSE;
1032     }
1033     if (!((detMask >> AliDAQ::DetectorID("TRG")) & 0x1)) {
1034       // switch off the reading of CTP raw-data payload
1035       if (fFillTriggerESD) {
1036         AliInfo("CTP is not in the list of active detectors. CTP data reading switched off.");
1037         fFillTriggerESD = kFALSE;
1038       }
1039     }
1040   }
1041
1042   AliInfo("===================================================================================");
1043   AliInfo(Form("Running local reconstruction for detectors: %s",fRunLocalReconstruction.Data()));
1044   AliInfo(Form("Running tracking for detectors: %s",fRunTracking.Data()));
1045   AliInfo(Form("Filling ESD for detectors: %s",fFillESD.Data()));
1046   AliInfo(Form("Quality assurance is active for detectors: %s",fQADetectors.Data()));
1047   AliInfo(Form("CDB and reconstruction parameters are loaded for detectors: %s",fLoadCDB.Data()));
1048   AliInfo("===================================================================================");
1049
1050   //*** Dealing with the magnetic field map
1051   if ( TGeoGlobalMagField::Instance()->IsLocked() ) {
1052     if (TGeoGlobalMagField::Instance()->GetField()->TestBit(AliMagF::kOverrideGRP)) {
1053       AliInfo("ExpertMode!!! GRP information will be ignored !");
1054       AliInfo("ExpertMode!!! Running with the externally locked B field !");
1055     }
1056     else {
1057       AliInfo("Destroying existing B field instance!");
1058       delete TGeoGlobalMagField::Instance();
1059     }    
1060   }
1061   if ( !TGeoGlobalMagField::Instance()->IsLocked() ) {
1062     // Construct the field map out of the information retrieved from GRP.
1063     Bool_t ok = kTRUE;
1064     // L3
1065     Float_t l3Current = fGRPData->GetL3Current((AliGRPObject::Stats)0);
1066     if (l3Current == AliGRPObject::GetInvalidFloat()) {
1067       AliError("GRP/GRP/Data entry:  missing value for the L3 current !");
1068       ok = kFALSE;
1069     }
1070     
1071     Char_t l3Polarity = fGRPData->GetL3Polarity();
1072     if (l3Polarity == AliGRPObject::GetInvalidChar()) {
1073       AliError("GRP/GRP/Data entry:  missing value for the L3 polarity !");
1074       ok = kFALSE;
1075     }
1076
1077     // Dipole
1078     Float_t diCurrent = fGRPData->GetDipoleCurrent((AliGRPObject::Stats)0);
1079     if (diCurrent == AliGRPObject::GetInvalidFloat()) {
1080       AliError("GRP/GRP/Data entry:  missing value for the dipole current !");
1081       ok = kFALSE;
1082     }
1083
1084     Char_t diPolarity = fGRPData->GetDipolePolarity();
1085     if (diPolarity == AliGRPObject::GetInvalidChar()) {
1086       AliError("GRP/GRP/Data entry:  missing value for the dipole polarity !");
1087       ok = kFALSE;
1088     }
1089
1090     // read special bits for the polarity convention and map type
1091     Int_t  polConvention = fGRPData->IsPolarityConventionLHC() ? AliMagF::kConvLHC : AliMagF::kConvDCS2008;
1092     Bool_t uniformB = fGRPData->IsUniformBMap();
1093
1094     if (ok) { 
1095       AliMagF* fld = AliMagF::CreateFieldMap(TMath::Abs(l3Current) * (l3Polarity ? -1:1), 
1096                                              TMath::Abs(diCurrent) * (diPolarity ? -1:1), 
1097                                              polConvention,uniformB,beamEnergy, beamType.Data());
1098       if (fld) {
1099         TGeoGlobalMagField::Instance()->SetField( fld );
1100         TGeoGlobalMagField::Instance()->Lock();
1101         AliInfo("Running with the B field constructed out of GRP !");
1102       }
1103       else AliFatal("Failed to create a B field map !");
1104     }
1105     else AliFatal("B field is neither set nor constructed from GRP ! Exitig...");
1106   }
1107   
1108   //*** Get the diamond profiles from OCDB
1109   entry = AliCDBManager::Instance()->Get("GRP/Calib/MeanVertexSPD");
1110   if (entry) {
1111     fDiamondProfileSPD = dynamic_cast<AliESDVertex*> (entry->GetObject());  
1112   } else {
1113      AliError("No SPD diamond profile found in OCDB!");
1114   }
1115
1116   entry = AliCDBManager::Instance()->Get("GRP/Calib/MeanVertex");
1117   if (entry) {
1118     fDiamondProfile = dynamic_cast<AliESDVertex*> (entry->GetObject());  
1119   } else {
1120      AliError("No diamond profile found in OCDB!");
1121   }
1122
1123   entry = AliCDBManager::Instance()->Get("GRP/Calib/MeanVertexTPC");
1124   if (entry) {
1125     fDiamondProfileTPC = dynamic_cast<AliESDVertex*> (entry->GetObject());  
1126   } else {
1127      AliError("No TPC diamond profile found in OCDB!");
1128   }
1129
1130   entry = AliCDBManager::Instance()->Get("GRP/Calib/CosmicTriggers");
1131   if (entry) {
1132     fListOfCosmicTriggers = dynamic_cast<THashTable*>(entry->GetObject());
1133     entry->SetOwner(0);
1134     AliCDBManager::Instance()->UnloadFromCache("GRP/Calib/CosmicTriggers");
1135   }
1136
1137   if (!fListOfCosmicTriggers) {
1138     AliWarning("Can not get list of cosmic triggers from OCDB! Cosmic event specie will be effectively disabled!");
1139   }
1140
1141   return kTRUE;
1142
1143
1144 //_____________________________________________________________________________
1145 Bool_t AliReconstruction::LoadCDB()
1146 {
1147   // Load CDB entries for all active detectors.
1148   // By default we load all the entries in <det>/Calib
1149   // folder.
1150
1151   AliCodeTimerAuto("",0);
1152
1153   AliCDBManager::Instance()->Get("GRP/CTP/Config");
1154
1155   TString detStr = fLoadCDB;
1156   for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
1157     if (!IsSelected(fgkDetectorName[iDet], detStr)) continue;
1158     AliCDBManager::Instance()->GetAll(Form("%s/Calib/*",fgkDetectorName[iDet]));
1159   }
1160
1161   // Temporary fix - one has to define the correct policy in order
1162   // to load the trigger OCDB entries only for the detectors that
1163   // in the trigger or that are needed in order to put correct
1164   // information in ESD
1165   AliCDBManager::Instance()->GetAll("TRIGGER/*/*");
1166
1167   return kTRUE;
1168 }
1169 //_____________________________________________________________________________
1170 Bool_t AliReconstruction::LoadTriggerScalersCDB()
1171 {
1172   // Load CTP scalers from OCDB.
1173   // The scalers are checked for consistency.
1174
1175   AliCodeTimerAuto("",0);
1176
1177   AliCDBEntry* entry = AliCDBManager::Instance()->Get("GRP/CTP/Scalers");
1178
1179   if (entry) { 
1180    
1181        AliInfo("Found an AliTriggerRunScalers in GRP/CTP/Scalers, reading it");
1182        fRunScalers = dynamic_cast<AliTriggerRunScalers*> (entry->GetObject());
1183        entry->SetOwner(0);
1184        if (fRunScalers->CorrectScalersOverflow() == 0) AliInfo("32bit Trigger counters corrected for overflow");
1185
1186   }
1187   return kTRUE;
1188 }
1189 //_____________________________________________________________________________
1190 Bool_t AliReconstruction::LoadCTPTimeParamsCDB()
1191 {
1192   // Load CTP timing information (alignment)
1193   // from OCDB.
1194
1195   AliCDBEntry* entry = AliCDBManager::Instance()->Get("GRP/CTP/CTPtiming");
1196
1197   if (entry) {
1198
1199        AliInfo("Found an AliCTPTimeParams in GRP/CTP/CTPtiming, reading it");
1200        fCTPTimeParams = dynamic_cast<AliCTPTimeParams*> (entry->GetObject());
1201        entry->SetOwner(0);
1202        return kTRUE;
1203   }
1204   
1205   return kFALSE; 
1206 }
1207 //_____________________________________________________________________________
1208 Bool_t AliReconstruction::Run(const char* input)
1209 {
1210   // Run Run Run
1211   AliCodeTimerAuto("",0);
1212
1213   InitRun(input);
1214   if (GetAbort() != TSelector::kContinue) return kFALSE;
1215
1216   TChain *chain = NULL;
1217   if (fRawReader && (chain = fRawReader->GetChain())) {
1218     Long64_t nEntries = (fLastEvent < 0) ? (TChain::kBigNumber) : (fLastEvent - fFirstEvent + 1);
1219     // Proof mode
1220     if (gProof) {
1221       // Temporary fix for long raw-data runs (until socket timeout handling in PROOF is revised)
1222       gProof->Exec("gEnv->SetValue(\"Proof.SocketActivityTimeout\",-1)", kTRUE);
1223
1224       if (gGrid)
1225         gProof->Exec("TGrid::Connect(\"alien://\")",kTRUE);
1226
1227       TMessage::EnableSchemaEvolutionForAll(kTRUE);
1228       gProof->Exec("TMessage::EnableSchemaEvolutionForAll(kTRUE)",kTRUE);
1229
1230       gProof->AddInput(this);
1231
1232       if (!ParseOutput()) return kFALSE;
1233
1234       gProof->SetParameter("PROOF_MaxSlavesPerNode", 9999);
1235       chain->SetProof();
1236       chain->Process("AliReconstruction","",nEntries,fFirstEvent);
1237     }
1238     else {
1239       chain->Process(this,"",nEntries,fFirstEvent);
1240     }
1241   }
1242   else {
1243     Begin(NULL);
1244     if (GetAbort() != TSelector::kContinue) return kFALSE;
1245     SlaveBegin(NULL);
1246     if (GetAbort() != TSelector::kContinue) return kFALSE;
1247     //******* The loop over events
1248     AliInfo("Starting looping over events");
1249     Int_t iEvent = 0;
1250     while ((iEvent < fRunLoader->GetNumberOfEvents()) ||
1251            (fRawReader && fRawReader->NextEvent())) {
1252       if (!ProcessEvent(iEvent)) {
1253         Abort("ProcessEvent",TSelector::kAbortFile);
1254         return kFALSE;
1255       }
1256       iEvent++;
1257     }
1258     SlaveTerminate();
1259     if (GetAbort() != TSelector::kContinue) return kFALSE;
1260     Terminate();
1261     if (GetAbort() != TSelector::kContinue) return kFALSE;
1262   }
1263
1264   return kTRUE;
1265 }
1266
1267 //_____________________________________________________________________________
1268 void AliReconstruction::InitRawReader(const char* input)
1269 {
1270   // Init raw-reader and
1271   // set the input in case of raw data
1272
1273   AliCodeTimerAuto("",0);
1274
1275   if (input) fRawInput = input;
1276   fRawReader = AliRawReader::Create(fRawInput.Data());
1277   if (!fRawReader) {
1278     if (fRawInput.IsNull()) {
1279       AliInfo("Reconstruction will run over digits");
1280     }
1281     else {
1282       AliFatal("Can not create raw-data reader ! Exiting..."); 
1283     }
1284   }
1285
1286   if (!fEquipIdMap.IsNull() && fRawReader)
1287     fRawReader->LoadEquipmentIdsMap(fEquipIdMap);
1288
1289   if (!fUseHLTData.IsNull()) {
1290     // create the RawReaderHLT which performs redirection of HLT input data for
1291     // the specified detectors
1292     AliRawReader* pRawReader=AliRawHLTManager::CreateRawReaderHLT(fRawReader, fUseHLTData.Data());
1293     if (pRawReader) {
1294       fParentRawReader=fRawReader;
1295       fRawReader=pRawReader;
1296     } else {
1297       AliError(Form("can not create Raw Reader for HLT input %s", fUseHLTData.Data()));
1298     }
1299   }
1300   AliSysInfo::AddStamp("CreateRawReader");
1301 }
1302
1303 //_____________________________________________________________________________
1304 void AliReconstruction::InitRun(const char* input)
1305 {
1306   // Initialization of raw-reader,
1307   // run number, CDB etc.
1308   AliCodeTimerAuto("",0);
1309   AliSysInfo::AddStamp("Start");
1310
1311   // Initialize raw-reader if any
1312   InitRawReader(input);
1313
1314   // Initialize the CDB storage
1315   InitCDB();
1316
1317   // Set run number in CDBManager (if it is not already set by the user)
1318   if (!SetRunNumberFromData()) {
1319     Abort("SetRunNumberFromData", TSelector::kAbortProcess);
1320     return;
1321   }
1322
1323   // Set CDB lock: from now on it is forbidden to reset the run number
1324   // or the default storage or to activate any further storage!
1325   SetCDBLock();
1326   
1327 }
1328
1329 //_____________________________________________________________________________
1330 void AliReconstruction::Begin(TTree *)
1331 {
1332   // Initialize AlReconstruction before
1333   // going into the event loop
1334   // Should follow the TSelector convention
1335   // i.e. initialize only the object on the client side
1336   AliCodeTimerAuto("",0);
1337
1338   AliReconstruction *reco = NULL;
1339   if (fInput) {
1340     if ((reco = (AliReconstruction*)fInput->FindObject("AliReconstruction"))) {
1341       *this = *reco;
1342     }
1343     AliSysInfo::AddStamp("ReadInputInBegin");
1344   }
1345
1346   // Import ideal TGeo geometry and apply misalignment
1347   if (!gGeoManager) {
1348     TString geom(gSystem->DirName(fGAliceFileName));
1349     geom += "/geometry.root";
1350     AliGeomManager::LoadGeometry(geom.Data());
1351     if (!gGeoManager) {
1352       Abort("LoadGeometry", TSelector::kAbortProcess);
1353       return;
1354     }
1355     AliSysInfo::AddStamp("LoadGeom");
1356     TString detsToCheck=fRunLocalReconstruction;
1357     if(!AliGeomManager::CheckSymNamesLUT(detsToCheck.Data())) {
1358       Abort("CheckSymNamesLUT", TSelector::kAbortProcess);
1359       return;
1360     }
1361     AliSysInfo::AddStamp("CheckGeom");
1362   }
1363
1364   if (!MisalignGeometry(fLoadAlignData)) {
1365     Abort("MisalignGeometry", TSelector::kAbortProcess);
1366     return;
1367   }
1368   AliCDBManager::Instance()->UnloadFromCache("GRP/Geometry/Data");
1369   AliSysInfo::AddStamp("MisalignGeom");
1370
1371   if (!InitGRP()) {
1372     Abort("InitGRP", TSelector::kAbortProcess);
1373     return;
1374   }
1375   AliSysInfo::AddStamp("InitGRP");
1376
1377   if (!LoadCDB()) {
1378     Abort("LoadCDB", TSelector::kAbortProcess);
1379     return;
1380   }
1381   AliSysInfo::AddStamp("LoadCDB");
1382
1383   if (!LoadTriggerScalersCDB()) {
1384     Abort("LoadTriggerScalersCDB", TSelector::kAbortProcess);
1385     return;
1386   }
1387   AliSysInfo::AddStamp("LoadTriggerScalersCDB");
1388
1389   if (!LoadCTPTimeParamsCDB()) {
1390     Abort("LoadCTPTimeParamsCDB", TSelector::kAbortProcess);
1391     return;
1392   }
1393   AliSysInfo::AddStamp("LoadCTPTimeParamsCDB");
1394
1395   // Read the reconstruction parameters from OCDB
1396   if (!InitRecoParams()) {
1397     AliWarning("Not all detectors have correct RecoParam objects initialized");
1398   }
1399   AliSysInfo::AddStamp("InitRecoParams");
1400
1401   if (fInput && gProof) {
1402     if (reco) *reco = *this;
1403
1404     gGeoManager->SetName("Geometry");
1405     gProof->AddInputData(gGeoManager,kTRUE);
1406     gGeoManager = NULL;
1407     gProof->AddInputData(const_cast<TMap*>(AliCDBManager::Instance()->GetEntryCache()),kTRUE);
1408     fInput->Add(new TParameter<Int_t>("RunNumber",AliCDBManager::Instance()->GetRun()));
1409     AliMagF *magFieldMap = (AliMagF*)TGeoGlobalMagField::Instance()->GetField();
1410     magFieldMap->SetName("MagneticFieldMap");
1411     gProof->AddInputData(magFieldMap,kTRUE);
1412   }
1413
1414 }
1415
1416 //_____________________________________________________________________________
1417 void AliReconstruction::SlaveBegin(TTree*)
1418 {
1419   // Initialization related to run-loader,
1420   // vertexer, trackers, recontructors
1421   // In proof mode it is executed on the slave
1422   AliCodeTimerAuto("",0);
1423
1424   TProofOutputFile *outProofFile = NULL;
1425   if (fInput) {
1426     if (AliDebugLevel() > 0) fInput->Print();
1427     if (AliDebugLevel() > 10) fInput->Dump();
1428     if (AliReconstruction *reco = (AliReconstruction*)fInput->FindObject("AliReconstruction")) {
1429       *this = *reco;
1430     }
1431     if (TGeoManager *tgeo = (TGeoManager*)fInput->FindObject("Geometry")) {
1432       gGeoManager = tgeo;
1433       AliGeomManager::SetGeometry(tgeo);
1434     }
1435     if (TMap *entryCache = (TMap*)fInput->FindObject("CDBEntryCache")) {
1436       Int_t runNumber = -1;
1437       if (TProof::GetParameter(fInput,"RunNumber",runNumber) == 0) {
1438         AliCDBManager *man = AliCDBManager::Instance(entryCache,runNumber);
1439         man->SetCacheFlag(kTRUE);
1440         man->SetLock(kTRUE);
1441         man->Print();
1442       }
1443     }
1444     if (AliMagF *map = (AliMagF*)fInput->FindObject("MagneticFieldMap")) {
1445       AliMagF *newMap = new AliMagF(*map);
1446       if (!newMap->LoadParameterization()) {
1447         Abort("AliMagF::LoadParameterization", TSelector::kAbortProcess);
1448         return;
1449       }
1450       TGeoGlobalMagField::Instance()->SetField(newMap);
1451       TGeoGlobalMagField::Instance()->Lock();
1452     }
1453     if (TNamed *outputFileName = (TNamed*)fInput->FindObject("PROOF_OUTPUTFILE"))
1454       fProofOutputFileName = outputFileName->GetTitle();
1455     if (TNamed *outputLocation = (TNamed*)fInput->FindObject("PROOF_OUTPUTFILE_LOCATION"))
1456       fProofOutputLocation = outputLocation->GetTitle();
1457     if (fInput->FindObject("PROOF_OUTPUTFILE_DATASET"))
1458       fProofOutputDataset = kTRUE;
1459     if (TNamed *archiveList = (TNamed*)fInput->FindObject("PROOF_OUTPUTFILE_ARCHIVE"))
1460       fProofOutputArchive = archiveList->GetTitle();
1461     if (!fProofOutputFileName.IsNull() &&
1462         !fProofOutputLocation.IsNull() &&
1463         fProofOutputArchive.IsNull()) {
1464       if (!fProofOutputDataset) {
1465         outProofFile = new TProofOutputFile(fProofOutputFileName.Data(),"M");
1466         outProofFile->SetOutputFileName(Form("%s%s",fProofOutputLocation.Data(),fProofOutputFileName.Data()));
1467       }
1468       else {
1469         outProofFile = new TProofOutputFile(fProofOutputFileName.Data(),"DROV",fProofOutputLocation.Data());
1470       }
1471       if (AliDebugLevel() > 0) outProofFile->Dump();
1472       fOutput->Add(outProofFile);
1473     }
1474     AliSysInfo::AddStamp("ReadInputInSlaveBegin");
1475   }
1476
1477   // get the run loader
1478   if (!InitRunLoader()) {
1479     Abort("InitRunLoader", TSelector::kAbortProcess);
1480     return;
1481   }
1482   AliSysInfo::AddStamp("LoadLoader");
1483  
1484   ftVertexer = new AliVertexerTracks(AliTracker::GetBz());
1485
1486   // get trackers
1487   if (!fRunTracking.IsNull() && !CreateTrackers(fRunTracking)) {
1488     Abort("CreateTrackers", TSelector::kAbortProcess);
1489     return;
1490   }      
1491   AliSysInfo::AddStamp("CreateTrackers");
1492
1493   // create the ESD output file and tree
1494   if (!outProofFile) {
1495     ffile = TFile::Open("AliESDs.root", "RECREATE");
1496     ffile->SetCompressionLevel(2);
1497     if (!ffile->IsOpen()) {
1498       Abort("OpenESDFile", TSelector::kAbortProcess);
1499       return;
1500     }
1501   }
1502   else {
1503     AliInfo(Form("Opening output PROOF file: %s/%s",
1504                  outProofFile->GetDir(), outProofFile->GetFileName()));
1505     if (!(ffile = outProofFile->OpenFile("RECREATE"))) {
1506       Abort(Form("Problems opening output PROOF file: %s/%s",
1507                  outProofFile->GetDir(), outProofFile->GetFileName()),
1508             TSelector::kAbortProcess);
1509       return;
1510     }
1511   }
1512
1513   ftree = new TTree("esdTree", "Tree with ESD objects");
1514   fesd = new AliESDEvent();
1515   fesd->CreateStdContent();
1516   // add a so far non-std object to the ESD, this will
1517   // become part of the std content
1518   fesd->AddObject(new AliESDHLTDecision);
1519
1520   fesd->WriteToTree(ftree);
1521   if (fWriteESDfriend) {
1522     ffileF = TFile::Open("AliESDfriends.root", "RECREATE");
1523     ftreeF = new TTree("esdFriendTree", "Tree with ESD Friend objects");
1524     fesdf  = new AliESDfriend();
1525     ftreeF->Branch("ESDfriend.","AliESDfriend", &fesdf);
1526     fesd->AddObject(fesdf);
1527     ffile->cd();
1528   }
1529   ftree->GetUserInfo()->Add(fesd);
1530
1531   fhlttree = new TTree("HLTesdTree", "Tree with HLT ESD objects");
1532   fhltesd = new AliESDEvent();
1533   fhltesd->CreateStdContent();
1534   // read the ESD template from CDB
1535   // HLT is allowed to put non-std content to its ESD, the non-std
1536   // objects need to be created before invocation of WriteToTree in
1537   // order to create all branches. Initialization is done from an
1538   // ESD layout template in CDB
1539   AliCDBManager* man = AliCDBManager::Instance();
1540   AliCDBPath hltESDConfigPath("HLT/ConfigHLT/esdLayout");
1541   AliCDBEntry* hltESDConfig=NULL;
1542   if (man->GetId(hltESDConfigPath)!=NULL &&
1543       (hltESDConfig=man->Get(hltESDConfigPath))!=NULL) {
1544     AliESDEvent* pESDLayout=dynamic_cast<AliESDEvent*>(hltESDConfig->GetObject());
1545     if (pESDLayout) {
1546       // init all internal variables from the list of objects
1547       pESDLayout->GetStdContent();
1548
1549       // copy content and create non-std objects
1550       *fhltesd=*pESDLayout;
1551       fhltesd->Reset();
1552     } else {
1553       AliError(Form("error setting hltEsd layout from %s: invalid object type",
1554                     hltESDConfigPath.GetPath().Data()));
1555     }
1556   }
1557
1558   fhltesd->WriteToTree(fhlttree);
1559   fhlttree->GetUserInfo()->Add(fhltesd);
1560
1561   ProcInfo_t procInfo;
1562   gSystem->GetProcInfo(&procInfo);
1563   AliInfo(Form("Current memory usage %d %d", procInfo.fMemResident, procInfo.fMemVirtual));
1564   
1565   //QA
1566   //Initialize the QA and start of cycle 
1567   if (fRunQA || fRunGlobalQA) 
1568     InitQA() ; 
1569
1570   //Initialize the Plane Efficiency framework
1571   if (fRunPlaneEff && !InitPlaneEff()) {
1572     Abort("InitPlaneEff", TSelector::kAbortProcess);
1573     return;
1574   }
1575
1576   if (strcmp(gProgName,"alieve") == 0)
1577     fRunAliEVE = InitAliEVE();
1578
1579   return;
1580 }
1581
1582 //_____________________________________________________________________________
1583 Bool_t AliReconstruction::Process(Long64_t entry)
1584 {
1585   // run the reconstruction over a single entry
1586   // from the chain with raw data
1587   AliCodeTimerAuto("",0);
1588
1589   TTree *currTree = fChain->GetTree();
1590   AliRawVEvent *event = NULL;
1591   currTree->SetBranchAddress("rawevent",&event);
1592   currTree->GetEntry(entry);
1593   fRawReader = new AliRawReaderRoot(event);
1594   fStatus = ProcessEvent(fRunLoader->GetNumberOfEvents());  
1595   delete fRawReader;
1596   fRawReader = NULL;
1597   delete event;
1598
1599   return fStatus;
1600 }
1601
1602 //_____________________________________________________________________________
1603 void AliReconstruction::Init(TTree *tree)
1604 {
1605   // Implementation of TSelector::Init()
1606   // method
1607   if (tree == 0) {
1608     AliError("The input tree is not found!");
1609     return;
1610   }
1611   fChain = tree;
1612 }
1613
1614 //_____________________________________________________________________________
1615 Bool_t AliReconstruction::ProcessEvent(Int_t iEvent)
1616 {
1617   // run the reconstruction over a single event
1618   // The event loop is steered in Run method
1619
1620
1621   static Long_t oldMres=0;
1622   static Long_t oldMvir=0;
1623   static Float_t oldCPU=0;
1624   static Long_t aveDMres=0;
1625   static Long_t aveDMvir=0;
1626   static Float_t aveDCPU=0;
1627
1628   AliCodeTimerAuto("",0);
1629
1630   AliESDpid pid;
1631
1632   if (iEvent >= fRunLoader->GetNumberOfEvents()) {
1633     fRunLoader->SetEventNumber(iEvent);
1634     fRunLoader->GetHeader()->Reset(fRawReader->GetRunNumber(), 
1635                                    iEvent, iEvent);
1636     fRunLoader->TreeE()->Fill();
1637     if (fRawReader && fRawReader->UseAutoSaveESD())
1638       fRunLoader->TreeE()->AutoSave("SaveSelf");
1639   }
1640
1641   if ((iEvent < fFirstEvent) || ((fLastEvent >= 0) && (iEvent > fLastEvent))) {
1642     return kTRUE;
1643   }
1644
1645
1646   fRunLoader->GetEvent(iEvent);
1647
1648   // Fill Event-info object
1649   GetEventInfo();
1650   fRecoParam.SetEventSpecie(fRunInfo,fEventInfo,fListOfCosmicTriggers);
1651   
1652   ProcInfo_t procInfo;
1653   if(iEvent==fFirstEvent) {
1654     gSystem->GetProcInfo(&procInfo);
1655     oldMres=procInfo.fMemResident;
1656     oldMvir=procInfo.fMemVirtual;
1657     oldCPU=procInfo.fCpuUser+procInfo.fCpuSys;
1658   }
1659   AliInfo(Form("================================= Processing event %d of type %-10s ==================================", iEvent,fRecoParam.PrintEventSpecie()));
1660
1661   // Set the reco-params
1662   {
1663     TString detStr = fLoadCDB;
1664     for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
1665       if (!IsSelected(fgkDetectorName[iDet], detStr)) continue;
1666       AliReconstructor *reconstructor = GetReconstructor(iDet);
1667       if (reconstructor && fRecoParam.GetDetRecoParamArray(iDet)) {
1668         const AliDetectorRecoParam *par = fRecoParam.GetDetRecoParam(iDet);
1669         reconstructor->SetRecoParam(par);
1670         reconstructor->GetPidSettings(&pid);
1671         reconstructor->SetEventInfo(&fEventInfo);
1672         if (fRunQA) {
1673           AliQAManager::QAManager()->SetRecoParam(iDet, par) ; 
1674           if (par) AliQAManager::QAManager()->SetEventSpecie(AliRecoParam::Convert(par->GetEventSpecie())) ;
1675         }
1676       }
1677     }
1678     if (fRunQA) {
1679       const AliDetectorRecoParam *grppar = fRecoParam.GetDetRecoParam(kNDetectors);
1680       AliQAManager::QAManager()->SetRecoParam(AliQAv1::kGLOBAL, grppar) ; 
1681       AliQAManager::QAManager()->SetEventSpecie(AliRecoParam::Convert(grppar->GetEventSpecie())) ;
1682     }
1683   }
1684
1685     // QA on single raw 
1686   if (fRunQA && IsInTasks(AliQAv1::kRAWS)) {
1687     AliQAManager::QAManager()->SetEventSpecie(fRecoParam.GetEventSpecie()) ;
1688     AliQAManager::QAManager()->RunOneEvent(fRawReader) ;  
1689   }
1690     // local single event reconstruction
1691     if (!fRunLocalReconstruction.IsNull()) {
1692       TString detectors=fRunLocalReconstruction;
1693       // run HLT event reconstruction first
1694       // ;-( IsSelected changes the string
1695       if (IsSelected("HLT", detectors) &&
1696           !RunLocalEventReconstruction("HLT")) {
1697         if (fStopOnError) {CleanUp(); return kFALSE;}
1698       }
1699       detectors=fRunLocalReconstruction;
1700       detectors.ReplaceAll("HLT", "");
1701       if (!RunLocalEventReconstruction(detectors)) {
1702         if (fStopOnError) {
1703           CleanUp(); 
1704           return kFALSE;
1705         }
1706       }
1707     }
1708
1709   
1710     // fill Event header information from the RawEventHeader
1711     if (fRawReader){FillRawEventHeaderESD(fesd);}
1712     if (fRawReader){FillRawEventHeaderESD(fhltesd);}
1713
1714     fesd->SetRunNumber(fRunLoader->GetHeader()->GetRun());
1715     fhltesd->SetRunNumber(fRunLoader->GetHeader()->GetRun());
1716     
1717     ((AliESDRun*)fesd->GetESDRun())->SetDetectorsInDAQ(fRunInfo->GetDetectorMask());
1718     ((AliESDRun*)fhltesd->GetESDRun())->SetDetectorsInDAQ(fRunInfo->GetDetectorMask());
1719     ((AliESDRun*)fesd->GetESDRun())->SetDetectorsInReco(AliDAQ::DetectorPatternOffline(fFillESD.Data()));
1720     ((AliESDRun*)fhltesd->GetESDRun())->SetDetectorsInReco(AliDAQ::DetectorPatternOffline(fFillESD.Data()));
1721
1722     fesd->SetEventNumberInFile(fRunLoader->GetHeader()->GetEventNrInRun());
1723     fhltesd->SetEventNumberInFile(fRunLoader->GetHeader()->GetEventNrInRun());
1724
1725     fesd->SetEventSpecie(fRecoParam.GetEventSpecie());
1726     fhltesd->SetEventSpecie(fRecoParam.GetEventSpecie());
1727     
1728     // Set magnetic field from the tracker
1729     fesd->SetMagneticField(AliTracker::GetBz());
1730     fhltesd->SetMagneticField(AliTracker::GetBz());
1731     //
1732     ((AliESDRun*)fesd->GetESDRun())->SetBeamEnergyIsSqrtSHalfGeV();
1733     ((AliESDRun*)fhltesd->GetESDRun())->SetBeamEnergyIsSqrtSHalfGeV();
1734     //
1735     AliMagF* fld = (AliMagF*)TGeoGlobalMagField::Instance()->GetField();
1736     if (fld) { // set info needed for field initialization
1737       fesd->SetCurrentL3(fld->GetCurrentSol());
1738       fesd->SetCurrentDip(fld->GetCurrentDip());
1739       fesd->SetBeamEnergy(fld->GetBeamEnergy());
1740       fesd->SetBeamType(fld->GetBeamTypeText());
1741       fesd->SetUniformBMap(fld->IsUniform());
1742       fesd->SetBInfoStored();
1743       //
1744       fhltesd->SetCurrentL3(fld->GetCurrentSol());
1745       fhltesd->SetCurrentDip(fld->GetCurrentDip());
1746       fhltesd->SetBeamEnergy(fld->GetBeamEnergy());
1747       fhltesd->SetBeamType(fld->GetBeamTypeText());
1748       fhltesd->SetUniformBMap(fld->IsUniform());
1749       fhltesd->SetBInfoStored();
1750     }
1751     //
1752     // Set most probable pt, for B=0 tracking
1753     // Get the global reco-params. They are atposition 16 inside the array of detectors in fRecoParam
1754     const AliGRPRecoParam *grpRecoParam = dynamic_cast<const AliGRPRecoParam*>(fRecoParam.GetDetRecoParam(kNDetectors));
1755     if (grpRecoParam) AliExternalTrackParam::SetMostProbablePt(grpRecoParam->GetMostProbablePt());
1756     
1757     // Fill raw-data error log into the ESD
1758     if (fRawReader) FillRawDataErrorLog(iEvent,fesd);
1759
1760     // vertex finder
1761     if (fRunVertexFinder) {
1762       if (!RunVertexFinder(fesd)) {
1763         if (fStopOnError) {CleanUp(); return kFALSE;}
1764       }
1765     }
1766
1767     // For Plane Efficiency: run the SPD trackleter
1768     if (fRunPlaneEff && fSPDTrackleter) {
1769       if (!RunSPDTrackleting(fesd)) {
1770         if (fStopOnError) {CleanUp(); return kFALSE;}
1771       }
1772     }
1773
1774     // Muon tracking
1775     if (!fRunTracking.IsNull()) {
1776       if (fRunMuonTracking) {
1777         if (!RunMuonTracking(fesd)) {
1778           if (fStopOnError) {CleanUp(); return kFALSE;}
1779         }
1780       }
1781     }
1782
1783     // barrel tracking
1784     if (!fRunTracking.IsNull()) {
1785       if (!RunTracking(fesd,pid)) {
1786         if (fStopOnError) {CleanUp(); return kFALSE;}
1787       }
1788     }
1789
1790     // fill ESD
1791     if (!fFillESD.IsNull()) {
1792       TString detectors=fFillESD;
1793       // run HLT first and on hltesd
1794       // ;-( IsSelected changes the string
1795       if (IsSelected("HLT", detectors) &&
1796           !FillESD(fhltesd, "HLT")) {
1797         if (fStopOnError) {CleanUp(); return kFALSE;}
1798       }
1799       detectors=fFillESD;
1800       // Temporary fix to avoid problems with HLT that overwrites the offline ESDs
1801       if (detectors.Contains("ALL")) {
1802         detectors="";
1803         for (Int_t idet=0; idet<kNDetectors; ++idet){
1804           detectors += fgkDetectorName[idet];
1805           detectors += " ";
1806         }
1807       }
1808       detectors.ReplaceAll("HLT", "");
1809       if (!FillESD(fesd, detectors)) {
1810         if (fStopOnError) {CleanUp(); return kFALSE;}
1811       }
1812     }
1813  
1814     // combined PID
1815     pid.MakePID(fesd);
1816
1817     if (fFillTriggerESD) {
1818       if (!FillTriggerESD(fesd)) {
1819         if (fStopOnError) {CleanUp(); return kFALSE;}
1820       }
1821     }
1822     // Always fill scalers
1823     if (!FillTriggerScalers(fesd)) {
1824        if (fStopOnError) {CleanUp(); return kFALSE;}
1825     }
1826     
1827
1828     ffile->cd();
1829
1830     //
1831     // Propagate track to the beam pipe  (if not already done by ITS)
1832     //
1833     const Int_t ntracks = fesd->GetNumberOfTracks();
1834     const Double_t kRadius  = 2.8; //something less than the beam pipe radius
1835
1836     TObjArray trkArray;
1837     UShort_t *selectedIdx=new UShort_t[ntracks];
1838
1839     for (Int_t itrack=0; itrack<ntracks; itrack++){
1840       const Double_t kMaxStep = 1;   //max step over the material
1841       Bool_t ok;
1842
1843       AliESDtrack *track = fesd->GetTrack(itrack);
1844       if (!track) continue;
1845
1846       AliExternalTrackParam *tpcTrack =
1847            (AliExternalTrackParam *)track->GetTPCInnerParam();
1848       ok = kFALSE;
1849       if (tpcTrack)
1850         ok = AliTracker::
1851           PropagateTrackToBxByBz(tpcTrack,kRadius,track->GetMass(),kMaxStep,kFALSE);
1852
1853       if (ok) {
1854         Int_t n=trkArray.GetEntriesFast();
1855         selectedIdx[n]=track->GetID();
1856         trkArray.AddLast(tpcTrack);
1857       }
1858
1859       //Tracks refitted by ITS should already be at the SPD vertex
1860       if (track->IsOn(AliESDtrack::kITSrefit)) continue;
1861
1862       AliTracker::
1863          PropagateTrackToBxByBz(track,kRadius,track->GetMass(),kMaxStep,kFALSE);
1864       Double_t x[3]; track->GetXYZ(x);
1865       Double_t b[3]; AliTracker::GetBxByBz(x,b);
1866       track->RelateToVertexBxByBz(fesd->GetPrimaryVertexSPD(), b, kVeryBig);
1867
1868     }
1869
1870     //
1871     // Improve the reconstructed primary vertex position using the tracks
1872     //
1873     Bool_t runVertexFinderTracks = fRunVertexFinderTracks;
1874     if(fesd->GetPrimaryVertexSPD()) {
1875       TString vtitle = fesd->GetPrimaryVertexSPD()->GetTitle();
1876       if(vtitle.Contains("cosmics")) {
1877         runVertexFinderTracks=kFALSE;
1878       }
1879     }
1880
1881     if (runVertexFinderTracks) {
1882        // TPC + ITS primary vertex
1883        ftVertexer->SetITSMode();
1884        ftVertexer->SetConstraintOff();
1885        // get cuts for vertexer from AliGRPRecoParam
1886        if (grpRecoParam) {
1887          Int_t nCutsVertexer = grpRecoParam->GetVertexerTracksNCuts();
1888          Double_t *cutsVertexer = new Double_t[nCutsVertexer];
1889          grpRecoParam->GetVertexerTracksCutsITS(cutsVertexer);
1890          ftVertexer->SetCuts(cutsVertexer);
1891          delete [] cutsVertexer; cutsVertexer = NULL; 
1892          if(fDiamondProfile && grpRecoParam->GetVertexerTracksConstraintITS()) { 
1893            if(fDiamondProfile->GetXRes()<kRadius) ftVertexer->SetVtxStart(fDiamondProfile); // apply constraint only if sigmax is smaller than the beam pipe radius 
1894          } 
1895        }
1896        AliESDVertex *pvtx=ftVertexer->FindPrimaryVertex(fesd);
1897        if (pvtx) {
1898           if (pvtx->GetStatus()) {
1899              fesd->SetPrimaryVertexTracks(pvtx);
1900              for (Int_t i=0; i<ntracks; i++) {
1901                  AliESDtrack *t = fesd->GetTrack(i);
1902                  Double_t x[3]; t->GetXYZ(x);
1903                  Double_t b[3]; AliTracker::GetBxByBz(x,b);
1904                  t->RelateToVertexBxByBz(pvtx, b, kVeryBig);
1905              } 
1906           }
1907           delete pvtx; pvtx=NULL;
1908        }
1909
1910        // TPC-only primary vertex
1911        ftVertexer->SetTPCMode();
1912        ftVertexer->SetConstraintOff();
1913        // get cuts for vertexer from AliGRPRecoParam
1914        if (grpRecoParam) {
1915          Int_t nCutsVertexer = grpRecoParam->GetVertexerTracksNCuts();
1916          Double_t *cutsVertexer = new Double_t[nCutsVertexer];
1917          grpRecoParam->GetVertexerTracksCutsTPC(cutsVertexer);
1918          ftVertexer->SetCuts(cutsVertexer);
1919          delete [] cutsVertexer; cutsVertexer = NULL; 
1920          if(fDiamondProfileTPC && grpRecoParam->GetVertexerTracksConstraintTPC()) { 
1921            if(fDiamondProfileTPC->GetXRes()<kRadius) ftVertexer->SetVtxStart(fDiamondProfileTPC); // apply constraint only if sigmax is smaller than the beam pipe radius 
1922          } 
1923        }
1924        pvtx=ftVertexer->FindPrimaryVertex(&trkArray,selectedIdx);
1925        if (pvtx) {
1926           if (pvtx->GetStatus()) {
1927              fesd->SetPrimaryVertexTPC(pvtx);
1928              for (Int_t i=0; i<ntracks; i++) {
1929                  AliESDtrack *t = fesd->GetTrack(i);
1930                  Double_t x[3]; t->GetXYZ(x);
1931                  Double_t b[3]; AliTracker::GetBxByBz(x,b);
1932                  t->RelateToVertexTPCBxByBz(pvtx, b, kVeryBig);
1933              } 
1934           }
1935           delete pvtx; pvtx=NULL;
1936        }
1937
1938     }
1939     delete[] selectedIdx;
1940
1941     if(fDiamondProfile) fesd->SetDiamond(fDiamondProfile);
1942     
1943
1944     if (fRunV0Finder) {
1945        // V0 finding
1946        AliV0vertexer vtxer;
1947        vtxer.Tracks2V0vertices(fesd);
1948
1949        if (fRunCascadeFinder) {
1950           // Cascade finding
1951           AliCascadeVertexer cvtxer;
1952           cvtxer.V0sTracks2CascadeVertices(fesd);
1953        }
1954     }
1955  
1956     // write ESD
1957     if (fCleanESD) CleanESD(fesd);
1958
1959   if (fRunQA && IsInTasks(AliQAv1::kESDS)) {
1960     AliQAManager::QAManager()->SetEventSpecie(fRecoParam.GetEventSpecie()) ;
1961     AliQAManager::QAManager()->RunOneEvent(fesd, fhltesd) ; 
1962   }
1963   if (fRunGlobalQA) {
1964     AliQADataMaker *qadm = AliQAManager::QAManager()->GetQADataMaker(AliQAv1::kGLOBAL);
1965       qadm->SetEventSpecie(fRecoParam.GetEventSpecie()) ;
1966     if (qadm && IsInTasks(AliQAv1::kESDS))
1967       qadm->Exec(AliQAv1::kESDS, fesd);
1968   }
1969
1970   // copy HLT decision from HLTesd to esd
1971   // the most relevant information is stored in a reduced container in the esd,
1972   // while the full information can be found in the HLTesd
1973   TObject* pHLTSrc=fhltesd->FindListObject(AliESDHLTDecision::Name());
1974   TObject* pHLTTgt=fesd->FindListObject(AliESDHLTDecision::Name());
1975   if (pHLTSrc && pHLTTgt) {
1976     pHLTSrc->Copy(*pHLTTgt);
1977   }
1978
1979     if (fWriteESDfriend) 
1980       fesd->GetESDfriend(fesdf);
1981
1982     ftree->Fill();
1983     if (fWriteESDfriend) ftreeF->Fill();
1984
1985     // Auto-save the ESD tree in case of prompt reco @P2
1986     if (fRawReader && fRawReader->UseAutoSaveESD()) {
1987       ftree->AutoSave("SaveSelf");
1988       if (fWriteESDfriend) ftreeF->AutoSave("SaveSelf");
1989       TFile *friendfile = (TFile *)(gROOT->GetListOfFiles()->FindObject("AliESDfriends.root"));
1990       if (friendfile) friendfile->Save();
1991     }
1992
1993     // write HLT ESD
1994     fhlttree->Fill();
1995
1996     // call AliEVE
1997     if (fRunAliEVE) RunAliEVE();
1998
1999     fesd->Reset();
2000     fhltesd->Reset();
2001     if (fWriteESDfriend) {
2002       fesdf->~AliESDfriend();
2003       new (fesdf) AliESDfriend(); // Reset...
2004     }
2005  
2006     gSystem->GetProcInfo(&procInfo);
2007     Long_t dMres=(procInfo.fMemResident-oldMres)/1024;
2008     Long_t dMvir=(procInfo.fMemVirtual-oldMvir)/1024;
2009     Float_t dCPU=procInfo.fCpuUser+procInfo.fCpuSys-oldCPU;
2010     aveDMres+=(dMres-aveDMres)/(iEvent-fFirstEvent+1);
2011     aveDMvir+=(dMvir-aveDMvir)/(iEvent-fFirstEvent+1);
2012     aveDCPU+=(dCPU-aveDCPU)/(iEvent-fFirstEvent+1);
2013     AliInfo(Form("======================= End Event %d: Res %d(%3d <%3d>) Vir %d(%3d <%3d>) CPU %5.2f <%5.2f> ===================",
2014                  iEvent, procInfo.fMemResident/1024, dMres, aveDMres, procInfo.fMemVirtual/1024, dMvir, aveDMvir, dCPU, aveDCPU));
2015     oldMres=procInfo.fMemResident;
2016     oldMvir=procInfo.fMemVirtual;
2017     oldCPU=procInfo.fCpuUser+procInfo.fCpuSys;
2018   
2019     fEventInfo.Reset();
2020     for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
2021       if (fReconstructor[iDet]) {
2022         fReconstructor[iDet]->SetRecoParam(NULL);
2023         fReconstructor[iDet]->SetEventInfo(NULL);
2024       }
2025       if (fTracker[iDet]) fTracker[iDet]->SetEventInfo(NULL);
2026     }
2027         
2028   if (fRunQA || fRunGlobalQA) 
2029     AliQAManager::QAManager()->Increment() ; 
2030   
2031     return kTRUE;
2032 }
2033
2034 //_____________________________________________________________________________
2035 void AliReconstruction::SlaveTerminate()
2036 {
2037   // Finalize the run on the slave side
2038   // Called after the exit
2039   // from the event loop
2040   AliCodeTimerAuto("",0);
2041
2042   if (fIsNewRunLoader) { // galice.root didn't exist
2043     fRunLoader->WriteHeader("OVERWRITE");
2044     fRunLoader->CdGAFile();
2045     fRunLoader->Write(0, TObject::kOverwrite);
2046   }
2047
2048   const TMap *cdbMap = AliCDBManager::Instance()->GetStorageMap();       
2049   const TList *cdbList = AliCDBManager::Instance()->GetRetrievedIds();   
2050                  
2051    TMap *cdbMapCopy = new TMap(cdbMap->GetEntries());    
2052    cdbMapCopy->SetOwner(1);      
2053    cdbMapCopy->SetName("cdbMap");        
2054    TIter iter(cdbMap->GetTable());       
2055          
2056    TPair* pair = 0;      
2057    while((pair = dynamic_cast<TPair*> (iter.Next()))){   
2058          TObjString* keyStr = dynamic_cast<TObjString*> (pair->Key());   
2059          TObjString* valStr = dynamic_cast<TObjString*> (pair->Value());         
2060          cdbMapCopy->Add(new TObjString(keyStr->GetName()), new TObjString(valStr->GetName()));  
2061    }     
2062          
2063    TList *cdbListCopy = new TList();     
2064    cdbListCopy->SetOwner(1);     
2065    cdbListCopy->SetName("cdbList");      
2066          
2067    TIter iter2(cdbList);         
2068          
2069         AliCDBId* id=0;
2070         while((id = dynamic_cast<AliCDBId*> (iter2.Next()))){    
2071          cdbListCopy->Add(new TObjString(id->ToString().Data()));        
2072    }     
2073          
2074    ftree->GetUserInfo()->Add(cdbMapCopy);        
2075    ftree->GetUserInfo()->Add(cdbListCopy);
2076
2077
2078   ffile->cd();
2079
2080   // we want to have only one tree version number
2081   ftree->Write(ftree->GetName(),TObject::kOverwrite);
2082   fhlttree->Write(fhlttree->GetName(),TObject::kOverwrite);
2083
2084   if (fWriteESDfriend) {
2085     ffileF->cd();
2086     ftreeF->Write(ftreeF->GetName(),TObject::kOverwrite);
2087   }
2088
2089 // Finish with Plane Efficiency evaluation: before of CleanUp !!!
2090   if (fRunPlaneEff && !FinishPlaneEff()) {
2091    AliWarning("Finish PlaneEff evaluation failed");
2092   }
2093
2094   // End of cycle for the in-loop  
2095
2096   if (fRunQA || fRunGlobalQA) {
2097     AliQAManager::QAManager()->EndOfCycle() ;
2098     if (fInput &&
2099         !fProofOutputLocation.IsNull() &&
2100         fProofOutputArchive.IsNull() &&
2101         !fProofOutputDataset) {
2102       TString qaOutputFile(Form("%sMerged.%s.Data.root",
2103                                 fProofOutputLocation.Data(),
2104                                 AliQAv1::GetQADataFileName()));
2105       TProofOutputFile *qaProofFile = new TProofOutputFile(Form("Merged.%s.Data.root",
2106                                                                 AliQAv1::GetQADataFileName()));
2107       qaProofFile->SetOutputFileName(qaOutputFile.Data());
2108       if (AliDebugLevel() > 0) qaProofFile->Dump();
2109       fOutput->Add(qaProofFile);
2110       MergeQA(qaProofFile->GetFileName());
2111     }
2112     else {
2113       MergeQA();
2114     }
2115   }
2116
2117   gROOT->cd();
2118   CleanUp();
2119
2120   if (fInput) {
2121     if (!fProofOutputFileName.IsNull() &&
2122         !fProofOutputLocation.IsNull() &&
2123         fProofOutputDataset &&
2124         !fProofOutputArchive.IsNull()) {
2125       TProofOutputFile *zipProofFile = new TProofOutputFile(fProofOutputFileName.Data(),
2126                                                             "DROV",
2127                                                             fProofOutputLocation.Data());
2128       if (AliDebugLevel() > 0) zipProofFile->Dump();
2129       fOutput->Add(zipProofFile);
2130       TString fileList(fProofOutputArchive.Data());
2131       fileList.ReplaceAll(","," ");
2132       TString command;
2133 #if ROOT_SVN_REVISION >= 30174
2134       command.Form("zip -n root %s/%s %s",zipProofFile->GetDir(kTRUE),zipProofFile->GetFileName(),fileList.Data());
2135 #else
2136       command.Form("zip -n root %s/%s %s",zipProofFile->GetDir(),zipProofFile->GetFileName(),fileList.Data());
2137 #endif
2138       AliInfo(Form("Executing: %s",command.Data()));
2139       gSystem->Exec(command.Data());
2140     }
2141   }
2142 }
2143     
2144 //_____________________________________________________________________________
2145 void AliReconstruction::Terminate()
2146 {
2147   // Create tags for the events in the ESD tree (the ESD tree is always present)
2148   // In case of empty events the tags will contain dummy values
2149   AliCodeTimerAuto("",0);
2150
2151   // Do not call the ESD tag creator in case of PROOF-based reconstruction
2152   if (!fInput) {
2153     AliESDTagCreator *esdtagCreator = new AliESDTagCreator();
2154     esdtagCreator->CreateESDTags(fFirstEvent,fLastEvent,fGRPData, AliQAv1::Instance()->GetQA(), AliQAv1::Instance()->GetEventSpecies(), AliQAv1::kNDET, AliRecoParam::kNSpecies);
2155     delete esdtagCreator;
2156   }
2157
2158   // Cleanup of CDB manager: cache and active storages!
2159   AliCDBManager::Instance()->ClearCache();
2160 }
2161
2162 //_____________________________________________________________________________
2163 Bool_t AliReconstruction::RunLocalEventReconstruction(const TString& detectors)
2164 {
2165 // run the local reconstruction
2166
2167   static Int_t eventNr=0;
2168   AliCodeTimerAuto("",0)
2169
2170   TString detStr = detectors;
2171   for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
2172     if (!IsSelected(fgkDetectorName[iDet], detStr)) continue;
2173     AliReconstructor* reconstructor = GetReconstructor(iDet);
2174     if (!reconstructor) continue;
2175     AliLoader* loader = fLoader[iDet];
2176     // Matthias April 2008: temporary fix to run HLT reconstruction
2177     // although the HLT loader is missing
2178     if (strcmp(fgkDetectorName[iDet], "HLT")==0) {
2179       if (fRawReader) {
2180         reconstructor->Reconstruct(fRawReader, NULL);
2181       } else {
2182         TTree* dummy=NULL;
2183         reconstructor->Reconstruct(dummy, NULL);
2184       }
2185       continue;
2186     }
2187     if (!loader) {
2188       AliWarning(Form("No loader is defined for %s!",fgkDetectorName[iDet]));
2189       continue;
2190     }
2191     // conversion of digits
2192     if (fRawReader && reconstructor->HasDigitConversion()) {
2193       AliInfo(Form("converting raw data digits into root objects for %s", 
2194                    fgkDetectorName[iDet]));
2195 //      AliCodeTimerAuto(Form("converting raw data digits into root objects for %s", 
2196 //                            fgkDetectorName[iDet]),0);
2197       loader->LoadDigits("update");
2198       loader->CleanDigits();
2199       loader->MakeDigitsContainer();
2200       TTree* digitsTree = loader->TreeD();
2201       reconstructor->ConvertDigits(fRawReader, digitsTree);
2202       loader->WriteDigits("OVERWRITE");
2203       loader->UnloadDigits();
2204     }
2205     // local reconstruction
2206     AliInfo(Form("running reconstruction for %s", fgkDetectorName[iDet]));
2207     //AliCodeTimerAuto(Form("running reconstruction for %s", fgkDetectorName[iDet]),0);
2208     loader->LoadRecPoints("update");
2209     loader->CleanRecPoints();
2210     loader->MakeRecPointsContainer();
2211     TTree* clustersTree = loader->TreeR();
2212     if (fRawReader && !reconstructor->HasDigitConversion()) {
2213       reconstructor->Reconstruct(fRawReader, clustersTree);
2214     } else {
2215       loader->LoadDigits("read");
2216       TTree* digitsTree = loader->TreeD();
2217       if (!digitsTree) {
2218         AliError(Form("Can't get the %s digits tree", fgkDetectorName[iDet]));
2219         if (fStopOnError) 
2220           return kFALSE;
2221       } else {
2222         reconstructor->Reconstruct(digitsTree, clustersTree);
2223         if (fRunQA && IsInTasks(AliQAv1::kDIGITSR)) {
2224           AliQAManager::QAManager()->SetEventSpecie(fRecoParam.GetEventSpecie()) ;
2225           AliQAManager::QAManager()->RunOneEventInOneDetector(iDet, digitsTree) ; 
2226         }
2227       }
2228       loader->UnloadDigits();
2229     }
2230                 if (fRunQA && IsInTasks(AliQAv1::kRECPOINTS)) {
2231       AliQAManager::QAManager()->SetEventSpecie(fRecoParam.GetEventSpecie()) ;
2232                         AliQAManager::QAManager()->RunOneEventInOneDetector(iDet, clustersTree) ; 
2233     }
2234     loader->WriteRecPoints("OVERWRITE");
2235     loader->UnloadRecPoints();
2236     AliSysInfo::AddStamp(Form("LRec%s_%d",fgkDetectorName[iDet],eventNr), iDet,1,eventNr);
2237   }
2238   IsSelected("CTP", detStr);
2239   if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
2240     AliError(Form("the following detectors were not found: %s",
2241                   detStr.Data()));
2242     if (fStopOnError) 
2243       return kFALSE;
2244   }
2245   eventNr++;
2246   return kTRUE;
2247 }
2248 //_____________________________________________________________________________
2249 Bool_t AliReconstruction::RunSPDTrackleting(AliESDEvent*& esd)
2250 {
2251 // run the SPD trackleting (for SPD efficiency purpouses)
2252
2253   AliCodeTimerAuto("",0)
2254
2255   Double_t vtxPos[3] = {0, 0, 0};
2256   Double_t vtxErr[3] = {0.0, 0.0, 0.0};
2257 /*
2258   TArrayF mcVertex(3);
2259   // if(MC)
2260   if (fRunLoader->GetHeader() && fRunLoader->GetHeader()->GenEventHeader()) {
2261     fRunLoader->GetHeader()->GenEventHeader()->PrimaryVertex(mcVertex);
2262     for (Int_t i = 0; i < 3; i++) vtxPos[i] = mcVertex[i];
2263   }
2264 */
2265   const AliESDVertex *vertex = esd->GetVertex();
2266   if(!vertex){
2267     AliWarning("Vertex not found");
2268     return kFALSE;
2269   }
2270   vertex->GetXYZ(vtxPos);
2271   vertex->GetSigmaXYZ(vtxErr);
2272   if (fSPDTrackleter) {
2273     AliInfo("running the SPD Trackleter for Plane Efficiency Evaluation");
2274
2275     // load clusters
2276     fLoader[0]->LoadRecPoints("read");
2277     TTree* tree = fLoader[0]->TreeR();
2278     if (!tree) {
2279       AliError("Can't get the ITS cluster tree");
2280       return kFALSE;
2281     }
2282     fSPDTrackleter->LoadClusters(tree);
2283     fSPDTrackleter->SetVertex(vtxPos, vtxErr);
2284     // run trackleting
2285     if (fSPDTrackleter->Clusters2Tracks(esd) != 0) {
2286       AliWarning("AliITSTrackleterSPDEff Clusters2Tracks failed");
2287      // fLoader[0]->UnloadRecPoints();
2288       return kFALSE;
2289     }
2290 //fSPDTrackleter->UnloadRecPoints();
2291   } else {
2292     AliWarning("SPDTrackleter not available");
2293     return kFALSE;
2294   }
2295   return kTRUE;
2296 }
2297
2298 //_____________________________________________________________________________
2299 Bool_t AliReconstruction::RunVertexFinder(AliESDEvent*& esd)
2300 {
2301 // run the barrel tracking
2302
2303   AliCodeTimerAuto("",0)
2304
2305   AliVertexer *vertexer = CreateVertexer();
2306   if (!vertexer) return kFALSE;
2307
2308   AliInfo("running the ITS vertex finder");
2309   AliESDVertex* vertex = NULL;
2310   if (fLoader[0]) {
2311     fLoader[0]->LoadRecPoints();
2312     TTree* cltree = fLoader[0]->TreeR();
2313     if (cltree) {
2314       if(fDiamondProfileSPD) vertexer->SetVtxStart(fDiamondProfileSPD);
2315       vertex = vertexer->FindVertexForCurrentEvent(cltree);
2316     }
2317     else {
2318       AliError("Can't get the ITS cluster tree");
2319     }
2320     fLoader[0]->UnloadRecPoints();
2321   }
2322   else {
2323     AliError("Can't get the ITS loader");
2324   }
2325   if(!vertex){
2326     AliWarning("Vertex not found");
2327     vertex = new AliESDVertex();
2328     vertex->SetName("default");
2329   }
2330   else {
2331     vertex->SetName("reconstructed");
2332   }
2333
2334   Double_t vtxPos[3];
2335   Double_t vtxErr[3];
2336   vertex->GetXYZ(vtxPos);
2337   vertex->GetSigmaXYZ(vtxErr);
2338
2339   esd->SetPrimaryVertexSPD(vertex);
2340   AliESDVertex *vpileup = NULL;
2341   Int_t novertices = 0;
2342   vpileup = vertexer->GetAllVertices(novertices);
2343   if(novertices>1){
2344     for (Int_t kk=1; kk<novertices; kk++)esd->AddPileupVertexSPD(&vpileup[kk]);
2345   }
2346   // if SPD multiplicity has been determined, it is stored in the ESD
2347   AliMultiplicity *mult = vertexer->GetMultiplicity();
2348   if(mult)esd->SetMultiplicity(mult);
2349
2350   for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
2351     if (fTracker[iDet]) fTracker[iDet]->SetVertex(vtxPos, vtxErr);
2352   }  
2353   delete vertex;
2354
2355   delete vertexer;
2356
2357   return kTRUE;
2358 }
2359
2360 //_____________________________________________________________________________
2361 Bool_t AliReconstruction::RunHLTTracking(AliESDEvent*& esd)
2362 {
2363 // run the HLT barrel tracking
2364
2365   AliCodeTimerAuto("",0)
2366
2367   if (!fRunLoader) {
2368     AliError("Missing runLoader!");
2369     return kFALSE;
2370   }
2371
2372   AliInfo("running HLT tracking");
2373
2374   // Get a pointer to the HLT reconstructor
2375   AliReconstructor *reconstructor = GetReconstructor(kNDetectors-1);
2376   if (!reconstructor) return kFALSE;
2377
2378   // TPC + ITS
2379   for (Int_t iDet = 1; iDet >= 0; iDet--) {
2380     TString detName = fgkDetectorName[iDet];
2381     AliDebug(1, Form("%s HLT tracking", detName.Data()));
2382     reconstructor->SetOption(detName.Data());
2383     AliTracker *tracker = reconstructor->CreateTracker();
2384     if (!tracker) {
2385       AliWarning(Form("couldn't create a HLT tracker for %s", detName.Data()));
2386       if (fStopOnError) return kFALSE;
2387       continue;
2388     }
2389     Double_t vtxPos[3];
2390     Double_t vtxErr[3]={0.005,0.005,0.010};
2391     const AliESDVertex *vertex = esd->GetVertex();
2392     vertex->GetXYZ(vtxPos);
2393     tracker->SetVertex(vtxPos,vtxErr);
2394     if(iDet != 1) {
2395       fLoader[iDet]->LoadRecPoints("read");
2396       TTree* tree = fLoader[iDet]->TreeR();
2397       if (!tree) {
2398         AliError(Form("Can't get the %s cluster tree", detName.Data()));
2399         return kFALSE;
2400       }
2401       tracker->LoadClusters(tree);
2402     }
2403     if (tracker->Clusters2Tracks(esd) != 0) {
2404       AliError(Form("HLT %s Clusters2Tracks failed", fgkDetectorName[iDet]));
2405       return kFALSE;
2406     }
2407     if(iDet != 1) {
2408       tracker->UnloadClusters();
2409     }
2410     delete tracker;
2411   }
2412
2413   return kTRUE;
2414 }
2415
2416 //_____________________________________________________________________________
2417 Bool_t AliReconstruction::RunMuonTracking(AliESDEvent*& esd)
2418 {
2419 // run the muon spectrometer tracking
2420
2421   AliCodeTimerAuto("",0)
2422
2423   if (!fRunLoader) {
2424     AliError("Missing runLoader!");
2425     return kFALSE;
2426   }
2427   Int_t iDet = 7; // for MUON
2428
2429   AliInfo("is running...");
2430
2431   // Get a pointer to the MUON reconstructor
2432   AliReconstructor *reconstructor = GetReconstructor(iDet);
2433   if (!reconstructor) return kFALSE;
2434
2435   
2436   TString detName = fgkDetectorName[iDet];
2437   AliDebug(1, Form("%s tracking", detName.Data()));
2438   AliTracker *tracker =  reconstructor->CreateTracker();
2439   if (!tracker) {
2440     AliWarning(Form("couldn't create a tracker for %s", detName.Data()));
2441     return kFALSE;
2442   }
2443      
2444   // read RecPoints
2445   fLoader[iDet]->LoadRecPoints("read");  
2446
2447   tracker->LoadClusters(fLoader[iDet]->TreeR());
2448   
2449   Int_t rv = tracker->Clusters2Tracks(esd);
2450   
2451   fLoader[iDet]->UnloadRecPoints();
2452
2453   tracker->UnloadClusters();
2454   
2455   delete tracker;
2456   
2457   if ( rv )
2458   {
2459     AliError(Form("%s Clusters2Tracks failed", fgkDetectorName[iDet]));
2460     return kFALSE;
2461   }
2462   
2463   return kTRUE;
2464 }
2465
2466
2467 //_____________________________________________________________________________
2468 Bool_t AliReconstruction::RunTracking(AliESDEvent*& esd,AliESDpid &PID)
2469 {
2470 // run the barrel tracking
2471   static Int_t eventNr=0;
2472   AliCodeTimerAuto("",0)
2473
2474   AliInfo("running tracking");
2475
2476   // Set the event info which is used
2477   // by the trackers in order to obtain
2478   // information about read-out detectors,
2479   // trigger etc.
2480   AliDebug(1, "Setting event info");
2481   for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
2482     if (!fTracker[iDet]) continue;
2483     fTracker[iDet]->SetEventInfo(&fEventInfo);
2484   }
2485
2486   //Fill the ESD with the T0 info (will be used by the TOF) 
2487   if (fReconstructor[11] && fLoader[11]) {
2488     fLoader[11]->LoadRecPoints("READ");
2489     TTree *treeR = fLoader[11]->TreeR();
2490     if (treeR) {
2491       GetReconstructor(11)->FillESD((TTree *)NULL,treeR,esd);
2492     }
2493   }
2494
2495   // pass 1: TPC + ITS inwards
2496   for (Int_t iDet = 1; iDet >= 0; iDet--) {
2497     if (!fTracker[iDet]) continue;
2498     AliDebug(1, Form("%s tracking", fgkDetectorName[iDet]));
2499
2500     // load clusters
2501     fLoader[iDet]->LoadRecPoints("read");
2502     AliSysInfo::AddStamp(Form("RLoadCluster%s_%d",fgkDetectorName[iDet],eventNr),iDet,1, eventNr);
2503     TTree* tree = fLoader[iDet]->TreeR();
2504     if (!tree) {
2505       AliError(Form("Can't get the %s cluster tree", fgkDetectorName[iDet]));
2506       return kFALSE;
2507     }
2508     fTracker[iDet]->LoadClusters(tree);
2509     AliSysInfo::AddStamp(Form("TLoadCluster%s_%d",fgkDetectorName[iDet],eventNr), iDet,2, eventNr);
2510     // run tracking
2511     if (fTracker[iDet]->Clusters2Tracks(esd) != 0) {
2512       AliError(Form("%s Clusters2Tracks failed", fgkDetectorName[iDet]));
2513       return kFALSE;
2514     }
2515     // preliminary PID in TPC needed by the ITS tracker
2516     if (iDet == 1) {
2517       GetReconstructor(1)->FillESD((TTree*)NULL, (TTree*)NULL, esd);
2518       PID.MakePID(esd,kTRUE);
2519     } 
2520     AliSysInfo::AddStamp(Form("Tracking0%s_%d",fgkDetectorName[iDet],eventNr), iDet,3,eventNr);
2521   }
2522
2523   // pass 2: ALL backwards
2524
2525   for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
2526     if (!fTracker[iDet]) continue;
2527     AliDebug(1, Form("%s back propagation", fgkDetectorName[iDet]));
2528
2529     // load clusters
2530     if (iDet > 1) {     // all except ITS, TPC
2531       TTree* tree = NULL;
2532       fLoader[iDet]->LoadRecPoints("read");
2533       AliSysInfo::AddStamp(Form("RLoadCluster0%s_%d",fgkDetectorName[iDet],eventNr), iDet,1, eventNr);
2534       tree = fLoader[iDet]->TreeR();
2535       if (!tree) {
2536         AliError(Form("Can't get the %s cluster tree", fgkDetectorName[iDet]));
2537         return kFALSE;
2538       }
2539       fTracker[iDet]->LoadClusters(tree); 
2540       AliSysInfo::AddStamp(Form("TLoadCluster0%s_%d",fgkDetectorName[iDet],eventNr), iDet,2, eventNr);
2541     }
2542
2543     // run tracking
2544     if (iDet>1) // start filling residuals for the "outer" detectors
2545       if (fRunGlobalQA) {
2546         AliTracker::SetFillResiduals(fRecoParam.GetEventSpecie(), kTRUE);     
2547         TObjArray ** arr = AliTracker::GetResidualsArray() ; 
2548         if (arr) {
2549           AliRecoParam::EventSpecie_t es=fRecoParam.GetEventSpecie();
2550           TObjArray * elem = arr[AliRecoParam::AConvert(es)];
2551           if ( elem && (! elem->At(0)) ) {
2552             AliQADataMaker *qadm = AliQAManager::QAManager()->GetQADataMaker(AliQAv1::kGLOBAL);
2553             if (qadm) qadm->InitRecPointsForTracker() ; 
2554           }
2555         }
2556       }
2557     if (fTracker[iDet]->PropagateBack(esd) != 0) {
2558       AliError(Form("%s backward propagation failed", fgkDetectorName[iDet]));
2559       //      return kFALSE;
2560     }
2561
2562     // unload clusters
2563     if (iDet > 3) {     // all except ITS, TPC, TRD and TOF
2564       fTracker[iDet]->UnloadClusters();
2565       fLoader[iDet]->UnloadRecPoints();
2566     }
2567     // updated PID in TPC needed by the ITS tracker -MI
2568     if (iDet == 1) {
2569       //GetReconstructor(1)->FillESD((TTree*)NULL, (TTree*)NULL, esd);
2570       //AliESDpid::MakePID(esd);
2571       PID.MakePID(esd,kTRUE);
2572     }
2573     AliSysInfo::AddStamp(Form("Tracking1%s_%d",fgkDetectorName[iDet],eventNr), iDet,3, eventNr);
2574   }
2575   //stop filling residuals for the "outer" detectors
2576   if (fRunGlobalQA) AliTracker::SetFillResiduals(fRecoParam.GetEventSpecie(), kFALSE);     
2577
2578   // pass 3: TRD + TPC + ITS refit inwards
2579
2580   for (Int_t iDet = 2; iDet >= 0; iDet--) {
2581     if (!fTracker[iDet]) continue;
2582     AliDebug(1, Form("%s inward refit", fgkDetectorName[iDet]));
2583
2584     // run tracking
2585     if (iDet<2) // start filling residuals for TPC and ITS
2586       if (fRunGlobalQA) {
2587         AliTracker::SetFillResiduals(fRecoParam.GetEventSpecie(), kTRUE);     
2588         TObjArray ** arr = AliTracker::GetResidualsArray() ; 
2589         if (arr) {
2590           AliRecoParam::EventSpecie_t es=fRecoParam.GetEventSpecie();
2591           TObjArray * elem = arr[AliRecoParam::AConvert(es)];
2592           if ( elem && (! elem->At(0)) ) {
2593             AliQADataMaker *qadm = AliQAManager::QAManager()->GetQADataMaker(AliQAv1::kGLOBAL);
2594             if (qadm) qadm->InitRecPointsForTracker() ; 
2595           }
2596         }
2597       }
2598     
2599     if (fTracker[iDet]->RefitInward(esd) != 0) {
2600       AliError(Form("%s inward refit failed", fgkDetectorName[iDet]));
2601       //      return kFALSE;
2602     }
2603     // run postprocessing
2604     if (fTracker[iDet]->PostProcess(esd) != 0) {
2605       AliError(Form("%s postprocessing failed", fgkDetectorName[iDet]));
2606       //      return kFALSE;
2607     }
2608     AliSysInfo::AddStamp(Form("Tracking2%s_%d",fgkDetectorName[iDet],eventNr), iDet,3, eventNr);
2609   }
2610
2611   // write space-points to the ESD in case alignment data output
2612   // is switched on
2613   if (fWriteAlignmentData)
2614     WriteAlignmentData(esd);
2615
2616   for (Int_t iDet = 3; iDet >= 0; iDet--) {
2617     if (!fTracker[iDet]) continue;
2618     // unload clusters
2619     fTracker[iDet]->UnloadClusters();
2620     AliSysInfo::AddStamp(Form("TUnloadCluster%s_%d",fgkDetectorName[iDet],eventNr), iDet,4, eventNr);
2621     fLoader[iDet]->UnloadRecPoints();
2622     AliSysInfo::AddStamp(Form("RUnloadCluster%s_%d",fgkDetectorName[iDet],eventNr), iDet,5, eventNr);
2623   }
2624   // stop filling residuals for TPC and ITS
2625   if (fRunGlobalQA) AliTracker::SetFillResiduals(fRecoParam.GetEventSpecie(), kFALSE);     
2626
2627   eventNr++;
2628   return kTRUE;
2629 }
2630
2631 //_____________________________________________________________________________
2632 Bool_t AliReconstruction::CleanESD(AliESDEvent *esd){
2633   //
2634   // Remove the data which are not needed for the physics analysis.
2635   //
2636
2637   Int_t nTracks=esd->GetNumberOfTracks();
2638   Int_t nV0s=esd->GetNumberOfV0s();
2639   AliInfo
2640   (Form("Number of ESD tracks and V0s before cleaning: %d %d",nTracks,nV0s));
2641
2642   Float_t cleanPars[]={fV0DCAmax,fV0CsPmin,fDmax,fZmax};
2643   Bool_t rc=esd->Clean(cleanPars);
2644
2645   nTracks=esd->GetNumberOfTracks();
2646   nV0s=esd->GetNumberOfV0s();
2647   AliInfo
2648   (Form("Number of ESD tracks and V0s after cleaning %d %d",nTracks,nV0s));
2649
2650   return rc;
2651 }
2652
2653 //_____________________________________________________________________________
2654 Bool_t AliReconstruction::FillESD(AliESDEvent*& esd, const TString& detectors)
2655 {
2656 // fill the event summary data
2657
2658   AliCodeTimerAuto("",0)
2659     static Int_t eventNr=0; 
2660   TString detStr = detectors;
2661   
2662   AliSysInfo::AddStamp(Form("FillESDb%d",eventNr), -19,-19, eventNr);
2663   for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
2664   if (!IsSelected(fgkDetectorName[iDet], detStr)) continue;
2665     AliReconstructor* reconstructor = GetReconstructor(iDet);
2666     if (!reconstructor) continue;
2667     AliDebug(1, Form("filling ESD for %s", fgkDetectorName[iDet]));
2668     TTree* clustersTree = NULL;
2669     if (fLoader[iDet]) {
2670       fLoader[iDet]->LoadRecPoints("read");
2671       clustersTree = fLoader[iDet]->TreeR();
2672       if (!clustersTree) {
2673         AliError(Form("Can't get the %s clusters tree", 
2674                       fgkDetectorName[iDet]));
2675         if (fStopOnError) return kFALSE;
2676       }
2677     }
2678     if (fRawReader && !reconstructor->HasDigitConversion()) {
2679       reconstructor->FillESD(fRawReader, clustersTree, esd);
2680     } else {
2681       TTree* digitsTree = NULL;
2682       if (fLoader[iDet]) {
2683         fLoader[iDet]->LoadDigits("read");
2684         digitsTree = fLoader[iDet]->TreeD();
2685         if (!digitsTree) {
2686           AliError(Form("Can't get the %s digits tree", 
2687                         fgkDetectorName[iDet]));
2688           if (fStopOnError) return kFALSE;
2689         }
2690       }
2691       reconstructor->FillESD(digitsTree, clustersTree, esd);
2692       if (fLoader[iDet]) fLoader[iDet]->UnloadDigits();
2693     }
2694     if (fLoader[iDet]) {
2695       fLoader[iDet]->UnloadRecPoints();
2696     }
2697   }
2698   
2699   IsSelected("CTP", detStr);
2700   if ((detStr.CompareTo("ALL") != 0) && !detStr.IsNull()) {
2701     AliError(Form("the following detectors were not found: %s", 
2702                   detStr.Data()));
2703     if (fStopOnError) return kFALSE;
2704   }
2705   AliSysInfo::AddStamp(Form("FillESDe%d",eventNr), -20,-20, eventNr);
2706   eventNr++;
2707   return kTRUE;
2708 }
2709
2710 //_____________________________________________________________________________
2711 Bool_t AliReconstruction::FillTriggerESD(AliESDEvent*& esd)
2712 {
2713   // Reads the trigger decision which is
2714   // stored in Trigger.root file and fills
2715   // the corresponding esd entries
2716
2717   AliCodeTimerAuto("",0)
2718   
2719   AliInfo("Filling trigger information into the ESD");
2720
2721   if (fRawReader) {
2722     AliCTPRawStream input(fRawReader);
2723     if (!input.Next()) {
2724       AliWarning("No valid CTP (trigger) DDL raw data is found ! The trigger info is taken from the event header!");
2725     }
2726     else {
2727       if (esd->GetTriggerMask() != input.GetClassMask())
2728         AliError(Form("Invalid trigger pattern found in CTP raw-data: %llx %llx",
2729                       input.GetClassMask(),esd->GetTriggerMask()));
2730       if (esd->GetOrbitNumber() != input.GetOrbitID())
2731         AliError(Form("Invalid orbit id found in CTP raw-data: %x %x",
2732                       input.GetOrbitID(),esd->GetOrbitNumber()));
2733       if (esd->GetBunchCrossNumber() != input.GetBCID())
2734         AliError(Form("Invalid bunch-crossing id found in CTP raw-data: %x %x",
2735                       input.GetBCID(),esd->GetBunchCrossNumber()));
2736       AliESDHeader* esdheader = esd->GetHeader();
2737       esdheader->SetL0TriggerInputs(input.GetL0Inputs());
2738       esdheader->SetL1TriggerInputs(input.GetL1Inputs());
2739       esdheader->SetL2TriggerInputs(input.GetL2Inputs());
2740       // IR
2741       UInt_t orbit=input.GetOrbitID();
2742        for(Int_t i=0 ; i<input.GetNIRs() ; i++ )
2743           if(TMath::Abs(Int_t(orbit-(input.GetIR(i))->GetOrbit()))<=1){
2744              esdheader->AddTriggerIR(input.GetIR(i));
2745           }
2746     }
2747   }
2748   return kTRUE;
2749 }
2750 //_____________________________________________________________________________
2751 Bool_t AliReconstruction::FillTriggerScalers(AliESDEvent*& esd)
2752 {
2753   //Scalers
2754   //fRunScalers->Print();
2755   if(fRunScalers && fRunScalers->CheckRunScalers()){
2756      AliTimeStamp* timestamp = new AliTimeStamp(esd->GetOrbitNumber(), esd->GetPeriodNumber(), esd->GetBunchCrossNumber());
2757      //AliTimeStamp* timestamp = new AliTimeStamp(10308000, 0, (ULong64_t)486238);
2758      AliESDHeader* esdheader = fesd->GetHeader();
2759      for(Int_t i=0;i<50;i++){
2760           if((1ull<<i) & esd->GetTriggerMask()){
2761           AliTriggerScalersESD* scalesd = fRunScalers->GetScalersForEventClass( timestamp, i+1);
2762           if(scalesd)esdheader->SetTriggerScalersRecord(scalesd);
2763         }
2764      }
2765   }
2766   return kTRUE;
2767 }
2768 //_____________________________________________________________________________
2769 Bool_t AliReconstruction::FillRawEventHeaderESD(AliESDEvent*& esd)
2770 {
2771   // 
2772   // Filling information from RawReader Header
2773   // 
2774
2775   if (!fRawReader) return kFALSE;
2776
2777   AliInfo("Filling information from RawReader Header");
2778
2779   esd->SetBunchCrossNumber(fRawReader->GetBCID());
2780   esd->SetOrbitNumber(fRawReader->GetOrbitID());
2781   esd->SetPeriodNumber(fRawReader->GetPeriod());
2782
2783   esd->SetTimeStamp(fRawReader->GetTimestamp());  
2784   esd->SetEventType(fRawReader->GetType());
2785
2786   return kTRUE;
2787 }
2788
2789
2790 //_____________________________________________________________________________
2791 Bool_t AliReconstruction::IsSelected(TString detName, TString& detectors) const
2792 {
2793 // check whether detName is contained in detectors
2794 // if yes, it is removed from detectors
2795
2796   // check if all detectors are selected
2797   if ((detectors.CompareTo("ALL") == 0) ||
2798       detectors.BeginsWith("ALL ") ||
2799       detectors.EndsWith(" ALL") ||
2800       detectors.Contains(" ALL ")) {
2801     detectors = "ALL";
2802     return kTRUE;
2803   }
2804
2805   // search for the given detector
2806   Bool_t result = kFALSE;
2807   if ((detectors.CompareTo(detName) == 0) ||
2808       detectors.BeginsWith(detName+" ") ||
2809       detectors.EndsWith(" "+detName) ||
2810       detectors.Contains(" "+detName+" ")) {
2811     detectors.ReplaceAll(detName, "");
2812     result = kTRUE;
2813   }
2814
2815   // clean up the detectors string
2816   while (detectors.Contains("  ")) detectors.ReplaceAll("  ", " ");
2817   while (detectors.BeginsWith(" ")) detectors.Remove(0, 1);
2818   while (detectors.EndsWith(" ")) detectors.Remove(detectors.Length()-1, 1);
2819
2820   return result;
2821 }
2822
2823 //_____________________________________________________________________________
2824 Bool_t AliReconstruction::InitRunLoader()
2825 {
2826 // get or create the run loader
2827
2828   if (gAlice) delete gAlice;
2829   gAlice = NULL;
2830
2831   TFile *gafile = TFile::Open(fGAliceFileName.Data());
2832   //  if (!gSystem->AccessPathName(fGAliceFileName.Data())) { // galice.root exists
2833   if (gafile) { // galice.root exists
2834     gafile->Close();
2835     delete gafile;
2836
2837     // load all base libraries to get the loader classes
2838     TString libs = gSystem->GetLibraries();
2839     for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
2840       TString detName = fgkDetectorName[iDet];
2841       if (detName == "HLT") continue;
2842       if (libs.Contains("lib" + detName + "base.so")) continue;
2843       gSystem->Load("lib" + detName + "base.so");
2844     }
2845     fRunLoader = AliRunLoader::Open(fGAliceFileName.Data());
2846     if (!fRunLoader) {
2847       AliError(Form("no run loader found in file %s", fGAliceFileName.Data()));
2848       CleanUp();
2849       return kFALSE;
2850     }
2851
2852     fRunLoader->CdGAFile();
2853     fRunLoader->LoadgAlice();
2854
2855     //PH This is a temporary fix to give access to the kinematics
2856     //PH that is needed for the labels of ITS clusters
2857     fRunLoader->LoadHeader();
2858     fRunLoader->LoadKinematics();
2859
2860   } else {               // galice.root does not exist
2861     if (!fRawReader) {
2862       AliError(Form("the file %s does not exist", fGAliceFileName.Data()));
2863     }
2864     fRunLoader = AliRunLoader::Open(fGAliceFileName.Data(),
2865                                     AliConfig::GetDefaultEventFolderName(),
2866                                     "recreate");
2867     if (!fRunLoader) {
2868       AliError(Form("could not create run loader in file %s", 
2869                     fGAliceFileName.Data()));
2870       CleanUp();
2871       return kFALSE;
2872     }
2873     fIsNewRunLoader = kTRUE;
2874     fRunLoader->MakeTree("E");
2875
2876     if (fNumberOfEventsPerFile > 0)
2877       fRunLoader->SetNumberOfEventsPerFile(fNumberOfEventsPerFile);
2878     else
2879       fRunLoader->SetNumberOfEventsPerFile((UInt_t)-1);
2880   }
2881
2882   return kTRUE;
2883 }
2884
2885 //_____________________________________________________________________________
2886 AliReconstructor* AliReconstruction::GetReconstructor(Int_t iDet)
2887 {
2888 // get the reconstructor object and the loader for a detector
2889
2890   if (fReconstructor[iDet]) {
2891     if (fRecoParam.GetDetRecoParamArray(iDet) && !AliReconstructor::GetRecoParam(iDet)) {
2892       const AliDetectorRecoParam *par = fRecoParam.GetDetRecoParam(iDet);
2893       fReconstructor[iDet]->SetRecoParam(par);
2894       fReconstructor[iDet]->SetRunInfo(fRunInfo);
2895     }
2896     return fReconstructor[iDet];
2897   }
2898
2899   // load the reconstructor object
2900   TPluginManager* pluginManager = gROOT->GetPluginManager();
2901   TString detName = fgkDetectorName[iDet];
2902   TString recName = "Ali" + detName + "Reconstructor";
2903
2904   if (!fIsNewRunLoader && !fRunLoader->GetLoader(detName+"Loader") && (detName != "HLT")) return NULL;
2905
2906   AliReconstructor* reconstructor = NULL;
2907   // first check if a plugin is defined for the reconstructor
2908   TPluginHandler* pluginHandler = 
2909     pluginManager->FindHandler("AliReconstructor", detName);
2910   // if not, add a plugin for it
2911   if (!pluginHandler) {
2912     AliDebug(1, Form("defining plugin for %s", recName.Data()));
2913     TString libs = gSystem->GetLibraries();
2914     if (libs.Contains("lib" + detName + "base.so") ||
2915         (gSystem->Load("lib" + detName + "base.so") >= 0)) {
2916       pluginManager->AddHandler("AliReconstructor", detName, 
2917                                 recName, detName + "rec", recName + "()");
2918     } else {
2919       pluginManager->AddHandler("AliReconstructor", detName, 
2920                                 recName, detName, recName + "()");
2921     }
2922     pluginHandler = pluginManager->FindHandler("AliReconstructor", detName);
2923   }
2924   if (pluginHandler && (pluginHandler->LoadPlugin() == 0)) {
2925     reconstructor = (AliReconstructor*) pluginHandler->ExecPlugin(0);
2926   }
2927   if (reconstructor) {
2928     TObject* obj = fOptions.FindObject(detName.Data());
2929     if (obj) reconstructor->SetOption(obj->GetTitle());
2930     reconstructor->SetRunInfo(fRunInfo);
2931     reconstructor->Init();
2932     fReconstructor[iDet] = reconstructor;
2933   }
2934
2935   // get or create the loader
2936   if (detName != "HLT") {
2937     fLoader[iDet] = fRunLoader->GetLoader(detName + "Loader");
2938     if (!fLoader[iDet]) {
2939       AliConfig::Instance()
2940         ->CreateDetectorFolders(fRunLoader->GetEventFolder(), 
2941                                 detName, detName);
2942       // first check if a plugin is defined for the loader
2943       pluginHandler = 
2944         pluginManager->FindHandler("AliLoader", detName);
2945       // if not, add a plugin for it
2946       if (!pluginHandler) {
2947         TString loaderName = "Ali" + detName + "Loader";
2948         AliDebug(1, Form("defining plugin for %s", loaderName.Data()));
2949         pluginManager->AddHandler("AliLoader", detName, 
2950                                   loaderName, detName + "base", 
2951                                   loaderName + "(const char*, TFolder*)");
2952         pluginHandler = pluginManager->FindHandler("AliLoader", detName);
2953       }
2954       if (pluginHandler && (pluginHandler->LoadPlugin() == 0)) {
2955         fLoader[iDet] = 
2956           (AliLoader*) pluginHandler->ExecPlugin(2, detName.Data(), 
2957                                                  fRunLoader->GetEventFolder());
2958       }
2959       if (!fLoader[iDet]) {   // use default loader
2960         fLoader[iDet] = new AliLoader(detName, fRunLoader->GetEventFolder());
2961       }
2962       if (!fLoader[iDet]) {
2963         AliWarning(Form("couldn't get loader for %s", detName.Data()));
2964         if (fStopOnError) return NULL;
2965       } else {
2966         fRunLoader->AddLoader(fLoader[iDet]);
2967         fRunLoader->CdGAFile();
2968         if (gFile && !gFile->IsWritable()) gFile->ReOpen("UPDATE");
2969         fRunLoader->Write(0, TObject::kOverwrite);
2970       }
2971     }
2972   }
2973       
2974   if (fRecoParam.GetDetRecoParamArray(iDet) && !AliReconstructor::GetRecoParam(iDet)) {
2975     const AliDetectorRecoParam *par = fRecoParam.GetDetRecoParam(iDet);
2976     reconstructor->SetRecoParam(par);
2977     reconstructor->SetRunInfo(fRunInfo);
2978   }
2979   return reconstructor;
2980 }
2981
2982 //_____________________________________________________________________________
2983 AliVertexer* AliReconstruction::CreateVertexer()
2984 {
2985 // create the vertexer
2986 // Please note that the caller is the owner of the
2987 // vertexer
2988
2989   AliVertexer* vertexer = NULL;
2990   AliReconstructor* itsReconstructor = GetReconstructor(0);
2991   if (itsReconstructor && ((fRunLocalReconstruction.Contains("ITS")) || fRunTracking.Contains("ITS"))) {
2992     vertexer = itsReconstructor->CreateVertexer();
2993   }
2994   if (!vertexer) {
2995     AliWarning("couldn't create a vertexer for ITS");
2996   }
2997
2998   return vertexer;
2999 }
3000
3001 //_____________________________________________________________________________
3002 Bool_t AliReconstruction::CreateTrackers(const TString& detectors)
3003 {
3004 // create the trackers
3005         AliInfo("Creating trackers");
3006
3007   TString detStr = detectors;
3008   for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
3009     if (!IsSelected(fgkDetectorName[iDet], detStr)) continue;
3010     AliReconstructor* reconstructor = GetReconstructor(iDet);
3011     if (!reconstructor) continue;
3012     TString detName = fgkDetectorName[iDet];
3013     if (detName == "HLT") {
3014       fRunHLTTracking = kTRUE;
3015       continue;
3016     }
3017     if (detName == "MUON") {
3018       fRunMuonTracking = kTRUE;
3019       continue;
3020     }
3021
3022
3023     fTracker[iDet] = reconstructor->CreateTracker();
3024     if (!fTracker[iDet] && (iDet < 7)) {
3025       AliWarning(Form("couldn't create a tracker for %s", detName.Data()));
3026       if (fStopOnError) return kFALSE;
3027     }
3028     AliSysInfo::AddStamp(Form("LTracker%s",fgkDetectorName[iDet]), iDet,0);
3029   }
3030
3031   return kTRUE;
3032 }
3033
3034 //_____________________________________________________________________________
3035 void AliReconstruction::CleanUp()
3036 {
3037 // delete trackers and the run loader and close and delete the file
3038
3039   for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
3040     delete fReconstructor[iDet];
3041     fReconstructor[iDet] = NULL;
3042     fLoader[iDet] = NULL;
3043     delete fTracker[iDet];
3044     fTracker[iDet] = NULL;
3045   }
3046   delete fRunInfo;
3047   fRunInfo = NULL;
3048
3049   delete fSPDTrackleter;
3050   fSPDTrackleter = NULL;
3051
3052   delete ftVertexer;
3053   ftVertexer = NULL;
3054   
3055   delete fRunLoader;
3056   fRunLoader = NULL;
3057   delete fRawReader;
3058   fRawReader = NULL;
3059   delete fParentRawReader;
3060   fParentRawReader=NULL;
3061
3062   if (ffile) {
3063     ffile->Close();
3064     delete ffile;
3065     ffile = NULL;
3066   }
3067
3068   if (AliQAManager::QAManager())
3069     AliQAManager::QAManager()->ShowQA() ; 
3070   AliQAManager::Destroy() ; 
3071   
3072 }
3073
3074 void AliReconstruction::WriteAlignmentData(AliESDEvent* esd)
3075 {
3076   // Write space-points which are then used in the alignment procedures
3077   // For the moment only ITS, TPC, TRD and TOF
3078
3079   Int_t ntracks = esd->GetNumberOfTracks();
3080   for (Int_t itrack = 0; itrack < ntracks; itrack++)
3081     {
3082       AliESDtrack *track = esd->GetTrack(itrack);
3083       Int_t nsp = 0;
3084       Int_t idx[200];
3085       for (Int_t i=0; i<200; ++i) idx[i] = -1; //PH avoid uninitialized values
3086       for (Int_t iDet = 5; iDet >= 0; iDet--) {// TOF, TRD, TPC, ITS clusters
3087           nsp += (iDet==GetDetIndex("TRD")) ? track->GetTRDntracklets():track->GetNcls(iDet);
3088
3089           if (iDet==GetDetIndex("ITS")) { // ITS "extra" clusters
3090              track->GetClusters(iDet,idx);
3091              for (Int_t i=6; i<12; i++) if(idx[i] >= 0) nsp++;
3092           }  
3093       }
3094
3095       if (nsp) {
3096         AliTrackPointArray *sp = new AliTrackPointArray(nsp);
3097         track->SetTrackPointArray(sp);
3098         Int_t isptrack = 0;
3099         for (Int_t iDet = 5; iDet >= 0; iDet--) {
3100           AliTracker *tracker = fTracker[iDet];
3101           if (!tracker) continue;
3102           Int_t nspdet = (iDet==GetDetIndex("TRD")) ? track->GetTRDtracklets(idx):track->GetClusters(iDet,idx);
3103
3104           if (iDet==GetDetIndex("ITS")) // ITS "extra" clusters             
3105              for (Int_t i=6; i<12; i++) if(idx[i] >= 0) nspdet++;
3106
3107           if (nspdet <= 0) continue;
3108           AliTrackPoint p;
3109           Int_t isp = 0;
3110           Int_t isp2 = 0;
3111           while (isp2 < nspdet) {
3112             Bool_t isvalid=kTRUE;
3113
3114             Int_t index=idx[isp++];
3115             if (index < 0) continue;
3116
3117             TString dets = fgkDetectorName[iDet];
3118             if ((fUseTrackingErrorsForAlignment.CompareTo(dets) == 0) ||
3119             fUseTrackingErrorsForAlignment.BeginsWith(dets+" ") ||
3120             fUseTrackingErrorsForAlignment.EndsWith(" "+dets) ||
3121             fUseTrackingErrorsForAlignment.Contains(" "+dets+" ")) {
3122               isvalid = tracker->GetTrackPointTrackingError(index,p,track);
3123             } else {
3124               isvalid = tracker->GetTrackPoint(index,p); 
3125             } 
3126             isp2++;
3127             if (!isvalid) continue;
3128             if (iDet==GetDetIndex("ITS") && (isp-1)>=6) p.SetExtra();
3129             sp->AddPoint(isptrack,&p); isptrack++;
3130           }
3131         }       
3132       }
3133     }
3134 }
3135
3136 //_____________________________________________________________________________
3137 void AliReconstruction::FillRawDataErrorLog(Int_t iEvent, AliESDEvent* esd)
3138 {
3139   // The method reads the raw-data error log
3140   // accumulated within the rawReader.
3141   // It extracts the raw-data errors related to
3142   // the current event and stores them into
3143   // a TClonesArray inside the esd object.
3144
3145   if (!fRawReader) return;
3146
3147   for(Int_t i = 0; i < fRawReader->GetNumberOfErrorLogs(); i++) {
3148
3149     AliRawDataErrorLog *log = fRawReader->GetErrorLog(i);
3150     if (!log) continue;
3151     if (iEvent != log->GetEventNumber()) continue;
3152
3153     esd->AddRawDataErrorLog(log);
3154   }
3155
3156 }
3157
3158 //_____________________________________________________________________________
3159 // void AliReconstruction::CheckQA()
3160 // {
3161 // check the QA of SIM for this run and remove the detectors 
3162 // with status Fatal
3163   
3164 //      TString newRunLocalReconstruction ; 
3165 //      TString newRunTracking ;
3166 //      TString newFillESD ;
3167 //       
3168 //      for (Int_t iDet = 0; iDet < AliQAv1::kNDET; iDet++) {
3169 //              TString detName(AliQAv1::GetDetName(iDet)) ;
3170 //              AliQAv1 * qa = AliQAv1::Instance(AliQAv1::DETECTORINDEX_t(iDet)) ;       
3171 //      if ( qa->IsSet(AliQAv1::DETECTORINDEX_t(iDet), AliQAv1::kSIM, specie, AliQAv1::kFATAL)) {
3172 //        AliInfo(Form("QA status for %s %s in Hits and/or SDIGITS  and/or Digits was Fatal; No reconstruction performed", 
3173 //                   detName.Data(), AliRecoParam::GetEventSpecieName(es))) ;
3174 //                      } else {
3175 //                      if ( fRunLocalReconstruction.Contains(AliQAv1::GetDetName(iDet)) || 
3176 //                                      fRunLocalReconstruction.Contains("ALL") )  {
3177 //                              newRunLocalReconstruction += detName ; 
3178 //                              newRunLocalReconstruction += " " ;                      
3179 //                      }
3180 //                      if ( fRunTracking.Contains(AliQAv1::GetDetName(iDet)) || 
3181 //                                      fRunTracking.Contains("ALL") )  {
3182 //                              newRunTracking += detName ; 
3183 //                              newRunTracking += " " ;                         
3184 //                      }
3185 //                      if ( fFillESD.Contains(AliQAv1::GetDetName(iDet)) || 
3186 //                                      fFillESD.Contains("ALL") )  {
3187 //                              newFillESD += detName ; 
3188 //                              newFillESD += " " ;                     
3189 //                      }
3190 //              }
3191 //      }
3192 //      fRunLocalReconstruction = newRunLocalReconstruction ; 
3193 //      fRunTracking            = newRunTracking ; 
3194 //      fFillESD                = newFillESD ; 
3195 // }
3196
3197 //_____________________________________________________________________________
3198 Int_t AliReconstruction::GetDetIndex(const char* detector)
3199 {
3200   // return the detector index corresponding to detector
3201   Int_t index = -1 ; 
3202   for (index = 0; index < kNDetectors ; index++) {
3203     if ( strcmp(detector, fgkDetectorName[index]) == 0 )
3204         break ; 
3205   }     
3206   return index ; 
3207 }
3208 //_____________________________________________________________________________
3209 Bool_t AliReconstruction::FinishPlaneEff() {
3210  //
3211  // Here execute all the necessary operationis, at the end of the tracking phase,
3212  // in case that evaluation of PlaneEfficiencies was required for some detector.
3213  // E.g., write into a DataBase file the PlaneEfficiency which have been evaluated.
3214  //
3215  // This Preliminary version works only FOR ITS !!!!!
3216  // other detectors (TOF,TRD, etc. have to develop their specific codes)
3217  //
3218  //  Input: none
3219  //  Return: kTRUE if all operations have been done properly, kFALSE otherwise
3220  //
3221  Bool_t ret=kFALSE;
3222  TString detStr = fLoadCDB;
3223  //for (Int_t iDet = 0; iDet < fgkNDetectors; iDet++) {
3224  for (Int_t iDet = 0; iDet < 1; iDet++) { // for the time being only ITS
3225    if (!IsSelected(fgkDetectorName[iDet], detStr)) continue;
3226    if(fTracker[iDet] && fTracker[iDet]->GetPlaneEff()) {
3227       AliPlaneEff *planeeff=fTracker[iDet]->GetPlaneEff();
3228       TString name=planeeff->GetName();
3229       name+=".root";
3230       TFile* pefile = TFile::Open(name, "RECREATE");
3231       ret=(Bool_t)planeeff->Write();
3232       pefile->Close();
3233       if(planeeff->GetCreateHistos()) {
3234         TString hname=planeeff->GetName();
3235         hname+="Histo.root";
3236         ret*=planeeff->WriteHistosToFile(hname,"RECREATE");
3237       }
3238    }
3239    if(fSPDTrackleter) {
3240      AliPlaneEff *planeeff=fSPDTrackleter->GetPlaneEff();
3241       TString name="AliITSPlaneEffSPDtracklet.root";
3242       TFile* pefile = TFile::Open(name, "RECREATE");
3243       ret=(Bool_t)planeeff->Write();
3244       pefile->Close();
3245       AliESDEvent *dummy=NULL;
3246       ret=(Bool_t)fSPDTrackleter->PostProcess(dummy); // take care of writing other files
3247    }
3248  }
3249  return ret;
3250 }
3251 //_____________________________________________________________________________
3252 Bool_t AliReconstruction::InitPlaneEff() {
3253 //
3254  // Here execute all the necessary operations, before of the tracking phase,
3255  // for the evaluation of PlaneEfficiencies, in case required for some detectors.
3256  // E.g., read from a DataBase file a first evaluation of the PlaneEfficiency
3257  // which should be updated/recalculated.
3258  //
3259  // This Preliminary version will work only FOR ITS !!!!!
3260  // other detectors (TOF,TRD, etc. have to develop their specific codes)
3261  //
3262  //  Input: none
3263  //  Return: kTRUE if all operations have been done properly, kFALSE otherwise
3264  //
3265
3266   fSPDTrackleter = NULL;
3267   TString detStr = fLoadCDB;
3268   if (IsSelected(fgkDetectorName[0], detStr)) {
3269     AliReconstructor* itsReconstructor = GetReconstructor(0);
3270     if (itsReconstructor) {
3271       fSPDTrackleter = itsReconstructor->CreateTrackleter(); // this is NULL unless required in RecoParam
3272     }
3273     if (fSPDTrackleter) {
3274       AliInfo("Trackleter for SPD has been created");
3275     }
3276   }
3277  return kTRUE;
3278 }
3279
3280 //_____________________________________________________________________________
3281 Bool_t AliReconstruction::InitAliEVE()
3282 {
3283   // This method should be called only in case 
3284   // AliReconstruction is run
3285   // within the alieve environment.
3286   // It will initialize AliEVE in a way
3287   // so that it can visualize event processed
3288   // by AliReconstruction.
3289   // The return flag shows whenever the
3290   // AliEVE initialization was successful or not.
3291
3292   TString macroStr;
3293   macroStr.Form("%s/EVE/macros/alieve_online.C",gSystem->ExpandPathName("$ALICE_ROOT"));
3294   AliInfo(Form("Loading AliEVE macro: %s",macroStr.Data()));
3295   if (gROOT->LoadMacro(macroStr.Data()) != 0) return kFALSE;
3296
3297   gROOT->ProcessLine("if (!AliEveEventManager::GetMaster()){new AliEveEventManager();AliEveEventManager::GetMaster()->AddNewEventCommand(\"alieve_online_on_new_event()\");gEve->AddEvent(AliEveEventManager::GetMaster());};");
3298   gROOT->ProcessLine("alieve_online_init()");
3299
3300   return kTRUE;
3301 }
3302   
3303 //_____________________________________________________________________________
3304 void AliReconstruction::RunAliEVE()
3305 {
3306   // Runs AliEVE visualisation of
3307   // the current event.
3308   // Should be executed only after
3309   // successful initialization of AliEVE.
3310
3311   AliInfo("Running AliEVE...");
3312   gROOT->ProcessLine(Form("AliEveEventManager::GetMaster()->SetEvent((AliRunLoader*)0x%lx,(AliRawReader*)0x%lx,(AliESDEvent*)0x%lx,(AliESDfriend*)0x%lx);",fRunLoader,fRawReader,fesd,fesdf));
3313   gSystem->Run();
3314 }
3315
3316 //_____________________________________________________________________________
3317 Bool_t AliReconstruction::SetRunQA(TString detAndAction) 
3318 {
3319         // Allows to run QA for a selected set of detectors
3320         // and a selected set of tasks among RAWS, DIGITSR, RECPOINTS and ESDS
3321         // all selected detectors run the same selected tasks
3322         
3323         if (!detAndAction.Contains(":")) {
3324                 AliError( Form("%s is a wrong syntax, use \"DetectorList:ActionList\" \n", detAndAction.Data()) ) ;
3325                 fRunQA = kFALSE ;
3326                 return kFALSE ;                 
3327         }
3328         Int_t colon = detAndAction.Index(":") ; 
3329         fQADetectors = detAndAction(0, colon) ; 
3330         fQATasks   = detAndAction(colon+1, detAndAction.Sizeof() ) ; 
3331         if (fQATasks.Contains("ALL") ) {
3332                 fQATasks = Form("%d %d %d %d", AliQAv1::kRAWS, AliQAv1::kDIGITSR, AliQAv1::kRECPOINTS, AliQAv1::kESDS) ; 
3333         } else {
3334                 fQATasks.ToUpper() ; 
3335                 TString tempo("") ; 
3336                 if ( fQATasks.Contains("RAW") ) 
3337                         tempo = Form("%d ", AliQAv1::kRAWS) ; 
3338                 if ( fQATasks.Contains("DIGIT") ) 
3339                         tempo += Form("%d ", AliQAv1::kDIGITSR) ; 
3340                 if ( fQATasks.Contains("RECPOINT") ) 
3341                         tempo += Form("%d ", AliQAv1::kRECPOINTS) ; 
3342                 if ( fQATasks.Contains("ESD") ) 
3343                         tempo += Form("%d ", AliQAv1::kESDS) ; 
3344                 fQATasks = tempo ; 
3345                 if (fQATasks.IsNull()) {
3346                         AliInfo("No QA requested\n")  ;
3347                         fRunQA = kFALSE ;
3348                         return kTRUE ; 
3349                 }
3350         }       
3351         TString tempo(fQATasks) ; 
3352         tempo.ReplaceAll(Form("%d", AliQAv1::kRAWS), AliQAv1::GetTaskName(AliQAv1::kRAWS))      ;
3353         tempo.ReplaceAll(Form("%d", AliQAv1::kDIGITSR), AliQAv1::GetTaskName(AliQAv1::kDIGITSR)) ;      
3354         tempo.ReplaceAll(Form("%d", AliQAv1::kRECPOINTS), AliQAv1::GetTaskName(AliQAv1::kRECPOINTS)) ;  
3355         tempo.ReplaceAll(Form("%d", AliQAv1::kESDS), AliQAv1::GetTaskName(AliQAv1::kESDS)) ;    
3356         AliInfo( Form("QA will be done on \"%s\" for \"%s\"\n", fQADetectors.Data(), tempo.Data()) ) ;  
3357         fRunQA = kTRUE ;
3358         return kTRUE; 
3359
3360
3361 //_____________________________________________________________________________
3362 Bool_t AliReconstruction::InitRecoParams() 
3363 {
3364   // The method accesses OCDB and retrieves all
3365   // the available reco-param objects from there.
3366
3367   Bool_t isOK = kTRUE;
3368
3369   if (fRecoParam.GetDetRecoParamArray(kNDetectors)) {
3370     AliInfo("Using custom GRP reconstruction parameters");
3371   }
3372   else {
3373     AliInfo("Loading GRP reconstruction parameter objects");
3374
3375     AliCDBPath path("GRP","Calib","RecoParam");
3376     AliCDBEntry *entry=AliCDBManager::Instance()->Get(path.GetPath());
3377     if(!entry){ 
3378       AliWarning("Couldn't find GRP RecoParam entry in OCDB");
3379       isOK = kFALSE;
3380     }
3381     else {
3382       TObject *recoParamObj = entry->GetObject();
3383       if (dynamic_cast<TObjArray*>(recoParamObj)) {
3384         // GRP has a normal TobjArray of AliDetectorRecoParam objects
3385         // Registering them in AliRecoParam
3386         fRecoParam.AddDetRecoParamArray(kNDetectors,dynamic_cast<TObjArray*>(recoParamObj));
3387       }
3388       else if (dynamic_cast<AliDetectorRecoParam*>(recoParamObj)) {
3389         // GRP has only onse set of reco parameters
3390         // Registering it in AliRecoParam
3391         AliInfo("Single set of GRP reconstruction parameters found");
3392         dynamic_cast<AliDetectorRecoParam*>(recoParamObj)->SetAsDefault();
3393         fRecoParam.AddDetRecoParam(kNDetectors,dynamic_cast<AliDetectorRecoParam*>(recoParamObj));
3394       }
3395       else {
3396         AliError("No valid GRP RecoParam object found in the OCDB");
3397         isOK = kFALSE;
3398       }
3399       entry->SetOwner(0);
3400     }
3401   }
3402
3403   TString detStr = fLoadCDB;
3404   for (Int_t iDet = 0; iDet < kNDetectors; iDet++) {
3405
3406     if (!IsSelected(fgkDetectorName[iDet], detStr)) continue;
3407
3408     if (fRecoParam.GetDetRecoParamArray(iDet)) {
3409       AliInfo(Form("Using custom reconstruction parameters for detector %s",fgkDetectorName[iDet]));
3410       continue;
3411     }
3412
3413     AliInfo(Form("Loading reconstruction parameter objects for detector %s",fgkDetectorName[iDet]));
3414   
3415     AliCDBPath path(fgkDetectorName[iDet],"Calib","RecoParam");
3416     AliCDBEntry *entry=AliCDBManager::Instance()->Get(path.GetPath());
3417     if(!entry){ 
3418       AliWarning(Form("Couldn't find RecoParam entry in OCDB for detector %s",fgkDetectorName[iDet]));
3419       isOK = kFALSE;
3420     }
3421     else {
3422       TObject *recoParamObj = entry->GetObject();
3423       if (dynamic_cast<TObjArray*>(recoParamObj)) {
3424         // The detector has a normal TobjArray of AliDetectorRecoParam objects
3425         // Registering them in AliRecoParam
3426         fRecoParam.AddDetRecoParamArray(iDet,dynamic_cast<TObjArray*>(recoParamObj));
3427       }
3428       else if (dynamic_cast<AliDetectorRecoParam*>(recoParamObj)) {
3429         // The detector has only onse set of reco parameters
3430         // Registering it in AliRecoParam
3431         AliInfo(Form("Single set of reconstruction parameters found for detector %s",fgkDetectorName[iDet]));
3432         dynamic_cast<AliDetectorRecoParam*>(recoParamObj)->SetAsDefault();
3433         fRecoParam.AddDetRecoParam(iDet,dynamic_cast<AliDetectorRecoParam*>(recoParamObj));
3434       }
3435       else {
3436         AliError(Form("No valid RecoParam object found in the OCDB for detector %s",fgkDetectorName[iDet]));
3437         isOK = kFALSE;
3438       }
3439       entry->SetOwner(0);
3440       //      FIX ME: We have to disable the unloading of reco-param CDB
3441       //      entries because QA framework is using them. Has to be fix in
3442       //      a way that the QA takes the objects already constructed in
3443       //      this method.
3444       //      AliCDBManager::Instance()->UnloadFromCache(path.GetPath());
3445     }
3446   }
3447
3448   if (AliDebugLevel() > 0) fRecoParam.Print();
3449
3450   return isOK;
3451 }
3452
3453 //_____________________________________________________________________________
3454 Bool_t AliReconstruction::GetEventInfo() 
3455 {
3456   // Fill the event info object
3457   // ...
3458   AliCodeTimerAuto("",0)
3459
3460   AliCentralTrigger *aCTP = NULL;
3461   if (fRawReader) {
3462     fEventInfo.SetEventType(fRawReader->GetType());
3463
3464     ULong64_t mask = fRawReader->GetClassMask();
3465     fEventInfo.SetTriggerMask(mask);
3466     UInt_t clmask = fRawReader->GetDetectorPattern()[0];
3467     fEventInfo.SetTriggerCluster(AliDAQ::ListOfTriggeredDetectors(clmask));
3468
3469     aCTP = new AliCentralTrigger();
3470     TString configstr("");
3471     if (!aCTP->LoadConfiguration(configstr)) { // Load CTP config from OCDB
3472       AliError("No trigger configuration found in OCDB! The trigger configuration information will not be used!");
3473       delete aCTP;
3474       return kFALSE;
3475     }
3476     aCTP->SetClassMask(mask);
3477     aCTP->SetClusterMask(clmask);
3478   }
3479   else {
3480     fEventInfo.SetEventType(AliRawEventHeaderBase::kPhysicsEvent);
3481
3482     if (fRunLoader && (!fRunLoader->LoadTrigger())) {
3483       aCTP = fRunLoader->GetTrigger();
3484       fEventInfo.SetTriggerMask(aCTP->GetClassMask());
3485       // get inputs from actp - just get
3486       AliESDHeader* esdheader = fesd->GetHeader();
3487       esdheader->SetL0TriggerInputs(aCTP->GetL0TriggerInputs());
3488       esdheader->SetL1TriggerInputs(aCTP->GetL1TriggerInputs());
3489       esdheader->SetL2TriggerInputs(aCTP->GetL2TriggerInputs());
3490       fEventInfo.SetTriggerCluster(AliDAQ::ListOfTriggeredDetectors(aCTP->GetClusterMask()));
3491     }
3492     else {
3493       AliWarning("No trigger can be loaded! The trigger information will not be used!");
3494       return kFALSE;
3495     }
3496   }
3497
3498   AliTriggerConfiguration *config = aCTP->GetConfiguration();
3499   if (!config) {
3500     AliError("No trigger configuration has been found! The trigger configuration information will not be used!");
3501     if (fRawReader) delete aCTP;
3502     return kFALSE;
3503   }
3504
3505   UChar_t clustmask = 0;
3506   TString trclasses;
3507   ULong64_t trmask = fEventInfo.GetTriggerMask();
3508   const TObjArray& classesArray = config->GetClasses();
3509   Int_t nclasses = classesArray.GetEntriesFast();
3510   for( Int_t iclass=0; iclass < nclasses; iclass++ ) {
3511     AliTriggerClass* trclass = (AliTriggerClass*)classesArray.At(iclass);
3512     if (trclass && trclass->GetMask()>0) {
3513       Int_t trindex = TMath::Nint(TMath::Log2(trclass->GetMask()));
3514       fesd->SetTriggerClass(trclass->GetName(),trindex);
3515       if (fRawReader) fRawReader->LoadTriggerClass(trclass->GetName(),trindex);
3516       if (trmask & (1ull << trindex)) {
3517         trclasses += " ";
3518         trclasses += trclass->GetName();
3519         trclasses += " ";
3520         clustmask |= trclass->GetCluster()->GetClusterMask();
3521       }
3522     }
3523   }
3524   fEventInfo.SetTriggerClasses(trclasses);
3525
3526   // Write names of active trigger inputs in ESD Header
3527   const TObjArray& inputsArray = config->GetInputs(); 
3528   Int_t ninputs = inputsArray.GetEntriesFast();
3529   for( Int_t iinput=0; iinput < ninputs; iinput++ ) {
3530     AliTriggerInput* trginput = (AliTriggerInput*)inputsArray.At(iinput);
3531     if (trginput && trginput->GetMask()>0) {
3532       Int_t inputIndex = (Int_t)TMath::Nint(TMath::Log2(trginput->GetMask()));
3533       AliESDHeader* headeresd = fesd->GetHeader();
3534       Int_t trglevel = (Int_t)trginput->GetLevel();
3535       if (trglevel == 0) headeresd->SetActiveTriggerInputs(trginput->GetInputName(), inputIndex);
3536       if (trglevel == 1) headeresd->SetActiveTriggerInputs(trginput->GetInputName(), inputIndex+24);
3537       if (trglevel == 2) headeresd->SetActiveTriggerInputs(trginput->GetInputName(), inputIndex+48);
3538     }
3539   }
3540
3541   // Set the information in ESD
3542   fesd->SetTriggerMask(trmask);
3543   fesd->SetTriggerCluster(clustmask);
3544
3545   if (!aCTP->CheckTriggeredDetectors()) {
3546     if (fRawReader) delete aCTP;
3547     return kFALSE;
3548   }    
3549
3550   if (fRawReader) delete aCTP;
3551
3552   // We have to fill also the HLT decision here!!
3553   // ...
3554
3555   return kTRUE;
3556 }
3557
3558 const char *AliReconstruction::MatchDetectorList(const char *detectorList, UInt_t detectorMask)
3559 {
3560   // Match the detector list found in the rec.C or the default 'ALL'
3561   // to the list found in the GRP (stored there by the shuttle PP which
3562   // gets the information from ECS)
3563   static TString resultList;
3564   TString detList = detectorList;
3565
3566   resultList = "";
3567
3568   for(Int_t iDet = 0; iDet < (AliDAQ::kNDetectors-1); iDet++) {
3569     if ((detectorMask >> iDet) & 0x1) {
3570       TString det = AliDAQ::OfflineModuleName(iDet);
3571       if ((detList.CompareTo("ALL") == 0) ||
3572           ((detList.BeginsWith("ALL ") ||
3573             detList.EndsWith(" ALL") ||
3574             detList.Contains(" ALL ")) &&
3575            !(detList.BeginsWith("-"+det+" ") ||
3576              detList.EndsWith(" -"+det) ||
3577              detList.Contains(" -"+det+" "))) ||
3578           (detList.CompareTo(det) == 0) ||
3579           detList.BeginsWith(det+" ") ||
3580           detList.EndsWith(" "+det) ||
3581           detList.Contains( " "+det+" " )) {
3582         if (!resultList.EndsWith(det + " ")) {
3583           resultList += det;
3584           resultList += " ";
3585         }
3586       }        
3587     }
3588   }
3589
3590   // HLT
3591   if ((detectorMask >> AliDAQ::kHLTId) & 0x1) {
3592     TString hltDet = AliDAQ::OfflineModuleName(AliDAQ::kNDetectors-1);
3593     if ((detList.CompareTo("ALL") == 0) ||
3594         ((detList.BeginsWith("ALL ") ||
3595           detList.EndsWith(" ALL") ||
3596           detList.Contains(" ALL ")) &&
3597          !(detList.BeginsWith("-"+hltDet+" ") ||
3598            detList.EndsWith(" -"+hltDet) ||
3599            detList.Contains(" -"+hltDet+" "))) ||
3600         (detList.CompareTo(hltDet) == 0) ||
3601         detList.BeginsWith(hltDet+" ") ||
3602         detList.EndsWith(" "+hltDet) ||
3603         detList.Contains( " "+hltDet+" " )) {
3604       resultList += hltDet;
3605     }
3606   }
3607
3608   return resultList.Data();
3609
3610 }
3611
3612 //______________________________________________________________________________
3613 void AliReconstruction::Abort(const char *method, EAbort what)
3614 {
3615   // Abort processing. If what = kAbortProcess, the Process() loop will be
3616   // aborted. If what = kAbortFile, the current file in a chain will be
3617   // aborted and the processing will continue with the next file, if there
3618   // is no next file then Process() will be aborted. Abort() can also  be
3619   // called from Begin(), SlaveBegin(), Init() and Notify(). After abort
3620   // the SlaveTerminate() and Terminate() are always called. The abort flag
3621   // can be checked in these methods using GetAbort().
3622   //
3623   // The method is overwritten in AliReconstruction for better handling of
3624   // reco specific errors 
3625
3626   if (!fStopOnError) return;
3627
3628   CleanUp();
3629
3630   TString whyMess = method;
3631   whyMess += " failed! Aborting...";
3632
3633   AliError(whyMess.Data());
3634
3635   fAbort = what;
3636   TString mess = "Abort";
3637   if (fAbort == kAbortProcess)
3638     mess = "AbortProcess";
3639   else if (fAbort == kAbortFile)
3640     mess = "AbortFile";
3641
3642   Info(mess, whyMess.Data());
3643 }
3644
3645 //______________________________________________________________________________
3646 Bool_t AliReconstruction::ProcessEvent(void* event)
3647 {
3648   // Method that is used in case the event loop
3649   // is steered from outside, for example by AMORE
3650   // 'event' is a pointer to the DATE event in the memory
3651
3652   if (fRawReader) delete fRawReader;
3653   fRawReader = new AliRawReaderDate(event);
3654   fStatus = ProcessEvent(fRunLoader->GetNumberOfEvents());  
3655   delete fRawReader;
3656   fRawReader = NULL;
3657
3658   return fStatus;
3659 }
3660
3661 //______________________________________________________________________________
3662 Bool_t AliReconstruction::ParseOutput()
3663 {
3664   // The method parses the output file
3665   // location string in order to steer
3666   // properly the selector
3667
3668   TPMERegexp re1("(\\w+\\.zip#\\w+\\.root):([,*\\w+\\.root,*]+)@dataset://(\\w++)");
3669   TPMERegexp re2("(\\w+\\.root)?@?dataset://(\\w++)");
3670
3671   if (re1.Match(fESDOutput) == 4) {
3672     // root archive with output files stored and regustered
3673     // in proof dataset
3674     gProof->AddInput(new TNamed("PROOF_OUTPUTFILE",re1[1].Data()));
3675     gProof->AddInput(new TNamed("PROOF_OUTPUTFILE_LOCATION",re1[3].Data()));
3676     gProof->AddInput(new TNamed("PROOF_OUTPUTFILE_DATASET",""));
3677     gProof->AddInput(new TNamed("PROOF_OUTPUTFILE_ARCHIVE",re1[2].Data()));
3678     AliInfo(Form("%s files will be stored within %s in dataset %s",
3679                  re1[2].Data(),
3680                  re1[1].Data(),
3681                  re1[3].Data()));
3682   }
3683   else if (re2.Match(fESDOutput) == 3) {
3684     // output file stored and registered
3685     // in proof dataset
3686     gProof->AddInput(new TNamed("PROOF_OUTPUTFILE",(re2[1].IsNull()) ? "AliESDs.root" : re2[1].Data()));
3687     gProof->AddInput(new TNamed("PROOF_OUTPUTFILE_LOCATION",re2[2].Data()));
3688     gProof->AddInput(new TNamed("PROOF_OUTPUTFILE_DATASET",""));
3689     AliInfo(Form("%s will be stored in dataset %s",
3690                  (re2[1].IsNull()) ? "AliESDs.root" : re2[1].Data(),
3691                  re2[2].Data()));
3692   }
3693   else {
3694     if (fESDOutput.IsNull()) {
3695       // Output location not given.
3696       // Assuming xrootd has been already started and
3697       // the output file has to be sent back
3698       // to the client machine
3699       TString esdUrl(Form("root://%s/%s/",
3700                           TUrl(gSystem->HostName()).GetHostFQDN(),
3701                           gSystem->pwd()));
3702       gProof->AddInput(new TNamed("PROOF_OUTPUTFILE","AliESDs.root"));
3703       gProof->AddInput(new TNamed("PROOF_OUTPUTFILE_LOCATION",esdUrl.Data()));
3704       AliInfo(Form("AliESDs.root will be stored in %s",
3705                    esdUrl.Data()));
3706     }
3707     else {
3708       // User specified an output location.
3709       // Ones has just to parse it here
3710       TUrl outputUrl(fESDOutput.Data());
3711       TString outputFile(gSystem->BaseName(outputUrl.GetFile()));
3712       gProof->AddInput(new TNamed("PROOF_OUTPUTFILE",outputFile.IsNull() ? "AliESDs.root" : outputFile.Data()));
3713       TString outputLocation(outputUrl.GetUrl());
3714       outputLocation.ReplaceAll(outputFile.Data(),"");
3715       gProof->AddInput(new TNamed("PROOF_OUTPUTFILE_LOCATION",outputLocation.Data()));
3716       AliInfo(Form("%s will be stored in %s",
3717                    outputFile.IsNull() ? "AliESDs.root" : outputFile.Data(),
3718                    outputLocation.Data()));
3719     }
3720   }
3721
3722   return kTRUE;
3723 }