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