]> git.uio.no Git - u/mrichter/AliRoot.git/blob - TOF/AliTOFtracker.cxx
Fix for DA's
[u/mrichter/AliRoot.git] / TOF / AliTOFtracker.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 //--------------------------------------------------------------------//
17 //                                                                    //
18 // AliTOFtracker Class                                                //
19 // Task: Perform association of the ESD tracks to TOF Clusters        //
20 // and Update ESD track with associated TOF Cluster parameters        //
21 //                                                                    //
22 // -- Authors : S. Arcelli, C. Zampolli (Bologna University and INFN) //
23 // -- Contacts: Annalisa.De.Caro@cern.ch                              //
24 // --         : Chiara.Zampolli@bo.infn.it                            //
25 // --         : Silvia.Arcelli@bo.infn.it                             //
26 //                                                                    //
27 //--------------------------------------------------------------------//
28
29 #include <Rtypes.h>
30 #include <TROOT.h>
31
32 #include <TSeqCollection.h>
33 #include <TClonesArray.h>
34 #include <TObjArray.h>
35 #include <TGeoManager.h>
36 #include <TTree.h>
37 #include <TFile.h>
38 #include <TH2F.h>
39
40 #include "AliGeomManager.h"
41 #include "AliESDtrack.h"
42 #include "AliESDEvent.h"
43 #include "AliESDpid.h"
44 #include "AliLog.h"
45 #include "AliTrackPointArray.h"
46 #include "AliCDBManager.h"
47
48 //#include "AliTOFpidESD.h"
49 #include "AliTOFRecoParam.h"
50 #include "AliTOFReconstructor.h"
51 #include "AliTOFcluster.h"
52 #include "AliTOFGeometry.h"
53 #include "AliTOFtracker.h"
54 #include "AliTOFtrack.h"
55
56 extern TGeoManager *gGeoManager;
57 extern TROOT *gROOT;
58
59
60 ClassImp(AliTOFtracker)
61
62 //_____________________________________________________________________________
63 AliTOFtracker::AliTOFtracker():
64   fkRecoParam(0x0),
65   fGeom(0x0),
66   fN(0),
67   fNseeds(0),
68   fNseedsTOF(0),
69   fngoodmatch(0),
70   fnbadmatch(0),
71   fnunmatch(0),
72   fnmatch(0),
73   fTracks(new TClonesArray("AliTOFtrack")),
74   fSeeds(new TObjArray(100)),
75   fTOFtrackPoints(new TObjArray(10)),
76   fHDigClusMap(0x0),
77   fHDigNClus(0x0),
78   fHDigClusTime(0x0),
79   fHDigClusToT(0x0),
80   fHRecNClus(0x0),
81   fHRecDist(0x0),
82   fHRecSigYVsP(0x0),
83   fHRecSigZVsP(0x0),
84   fHRecSigYVsPWin(0x0),
85   fHRecSigZVsPWin(0x0),
86   fCalTree(0x0),
87   fIch(-1),
88   fToT(-1.),
89   fTime(-1.),
90   fExpTimePi(-1.),
91   fExpTimeKa(-1.),
92   fExpTimePr(-1.)
93 {
94   //AliTOFtracker main Ctor
95
96   for (Int_t ii=0; ii<kMaxCluster; ii++) fClusters[ii]=0x0;
97
98   // Getting the geometry
99   fGeom = new AliTOFGeometry();
100
101   InitCheckHists();
102
103 }
104 //_____________________________________________________________________________
105 AliTOFtracker::~AliTOFtracker() {
106   //
107   // Dtor
108   //
109
110   SaveCheckHists();
111
112   if(!(AliCDBManager::Instance()->GetCacheFlag())){
113     delete fkRecoParam;
114   }
115   delete fGeom; 
116   delete fHDigClusMap;
117   delete fHDigNClus;
118   delete fHDigClusTime;
119   delete fHDigClusToT;
120   delete fHRecNClus;
121   delete fHRecDist;
122   delete fHRecSigYVsP;
123   delete fHRecSigZVsP;
124   delete fHRecSigYVsPWin;
125   delete fHRecSigZVsPWin;
126   delete fCalTree;
127   if (fTracks){
128     fTracks->Delete();
129     delete fTracks;
130     fTracks=0x0;
131   }
132   if (fSeeds){
133     fSeeds->Delete();
134     delete fSeeds;
135     fSeeds=0x0;
136   }
137   if (fTOFtrackPoints){
138     fTOFtrackPoints->Delete();
139     delete fTOFtrackPoints;
140     fTOFtrackPoints=0x0;
141   }
142
143   for (Int_t ii=0; ii<kMaxCluster; ii++)
144     if (fClusters[ii]) fClusters[ii]->Delete();
145
146 }
147 //_____________________________________________________________________________
148 void AliTOFtracker::GetPidSettings(AliESDpid *esdPID) {
149   // 
150   // Sets TOF resolution from RecoParams
151   //
152   if (fkRecoParam)
153     esdPID->GetTOFResponse().SetTimeResolution(fkRecoParam->GetTimeResolution());
154   else
155     AliWarning("fkRecoParam not yet set; cannot set PID settings");
156
157 //_____________________________________________________________________________
158 Int_t AliTOFtracker::PropagateBack(AliESDEvent * const event) {
159   //
160   // Gets seeds from ESD event and Match with TOF Clusters
161   //
162
163   // initialize RecoParam for current event
164   AliDebug(1,"Initializing params for TOF");
165
166   fkRecoParam = AliTOFReconstructor::GetRecoParam();  // instantiate reco param from STEER...
167
168   if (fkRecoParam == 0x0) { 
169     AliFatal("No Reco Param found for TOF!!!");
170   }
171   //fkRecoParam->Dump();
172   //if(fkRecoParam->GetApplyPbPbCuts())fkRecoParam=fkRecoParam->GetPbPbparam();
173   //fkRecoParam->PrintParameters();
174
175   //Initialise some counters
176
177   fNseeds=0;
178   fNseedsTOF=0;
179   fngoodmatch=0;
180   fnbadmatch=0;
181   fnunmatch=0;
182   fnmatch=0;
183
184   Int_t ntrk=event->GetNumberOfTracks();
185   fNseeds = ntrk;
186
187
188   //Load ESD tracks into a local Array of ESD Seeds
189   for (Int_t i=0; i<fNseeds; i++)
190     fSeeds->AddLast(event->GetTrack(i));
191
192   //Prepare ESD tracks candidates for TOF Matching
193   CollectESD();
194
195   //First Step with Strict Matching Criterion
196   MatchTracks(kFALSE);
197
198   //Second Step with Looser Matching Criterion
199   MatchTracks(kTRUE);
200
201   AliInfo(Form("Number of matched tracks = %d (good = %d, bad = %d)",fnmatch,fngoodmatch,fnbadmatch));
202
203   //Update the matched ESD tracks
204
205   for (Int_t i=0; i<ntrk; i++) {
206     AliESDtrack *t=event->GetTrack(i);
207     AliESDtrack *seed =(AliESDtrack*)fSeeds->At(i);
208
209     if ( (seed->GetStatus()&AliESDtrack::kTOFin)!=0 ) {
210       t->SetStatus(AliESDtrack::kTOFin);
211       //if(seed->GetTOFsignal()>0){
212       if ( (seed->GetStatus()&AliESDtrack::kTOFout)!=0 ) {
213         t->SetStatus(AliESDtrack::kTOFout);
214         t->SetTOFsignal(seed->GetTOFsignal());
215         t->SetTOFcluster(seed->GetTOFcluster());
216         t->SetTOFsignalToT(seed->GetTOFsignalToT());
217         t->SetTOFsignalRaw(seed->GetTOFsignalRaw());
218         t->SetTOFsignalDz(seed->GetTOFsignalDz());
219         t->SetTOFsignalDx(seed->GetTOFsignalDx());
220         t->SetTOFDeltaBC(seed->GetTOFDeltaBC());
221         t->SetTOFL0L1(seed->GetTOFL0L1());
222         t->SetTOFCalChannel(seed->GetTOFCalChannel());
223         Int_t tlab[3]; seed->GetTOFLabel(tlab);    
224         t->SetTOFLabel(tlab);
225
226         Double_t alphaA = (Double_t)t->GetAlpha();
227         Double_t xA = (Double_t)t->GetX();
228         Double_t yA = (Double_t)t->GetY();
229         Double_t zA = (Double_t)t->GetZ();
230         Double_t p1A = (Double_t)t->GetSnp();
231         Double_t p2A = (Double_t)t->GetTgl();
232         Double_t p3A = (Double_t)t->GetSigned1Pt();
233         const Double_t *covA = (Double_t*)t->GetCovariance();
234
235         // Make attention, please:
236         //      AliESDtrack::fTOFInfo array does not be stored in the AliESDs.root file
237         //      it is there only for a check during the reconstruction step.
238         Float_t info[10]; seed->GetTOFInfo(info);
239         t->SetTOFInfo(info);
240         AliDebug(3,Form(" distance=%f; residual in the pad reference frame: dX=%f, dZ=%f", info[0],info[1],info[2]));
241
242         // Check done:
243         //       by calling the AliESDtrack::UpdateTrackParams,
244         //       the current track parameters are changed
245         //       and it could cause refit problems.
246         //       We need to update only the following track parameters:
247         //            the track length and expected times.
248         //       Removed AliESDtrack::UpdateTrackParams call
249         //       Called AliESDtrack::SetIntegratedTimes(...) and
250         //       AliESDtrack::SetIntegratedLength() routines.
251         /*
252           AliTOFtrack *track = new AliTOFtrack(*seed);
253           t->UpdateTrackParams(track,AliESDtrack::kTOFout); // to be checked - AdC
254           delete track;
255           Double_t time[10]; t->GetIntegratedTimes(time);
256         */
257
258         Double_t time[10]; seed->GetIntegratedTimes(time);
259         t->SetIntegratedTimes(time);
260
261         Double_t length =  seed->GetIntegratedLength();
262         t->SetIntegratedLength(length);
263
264         Double_t alphaB = (Double_t)t->GetAlpha();
265         Double_t xB = (Double_t)t->GetX();
266         Double_t yB = (Double_t)t->GetY();
267         Double_t zB = (Double_t)t->GetZ();
268         Double_t p1B = (Double_t)t->GetSnp();
269         Double_t p2B = (Double_t)t->GetTgl();
270         Double_t p3B = (Double_t)t->GetSigned1Pt();
271         const Double_t *covB = (Double_t*)t->GetCovariance();
272         AliDebug(2,"Track params -now(before)-:");
273         AliDebug(2,Form("    X: %f(%f), Y: %f(%f), Z: %f(%f) --- alpha: %f(%f)",
274                         xB,xA,
275                         yB,yA,
276                         zB,zA,
277                         alphaB,alphaA));
278         AliDebug(2,Form("    p1: %f(%f), p2: %f(%f), p3: %f(%f)",
279                         p1B,p1A,
280                         p2B,p2A,
281                         p3B,p3A));
282         AliDebug(2,Form("    cov1: %f(%f), cov2: %f(%f), cov3: %f(%f)"
283                         " cov4: %f(%f), cov5: %f(%f), cov6: %f(%f)"
284                         " cov7: %f(%f), cov8: %f(%f), cov9: %f(%f)"
285                         " cov10: %f(%f), cov11: %f(%f), cov12: %f(%f)"
286                         " cov13: %f(%f), cov14: %f(%f), cov15: %f(%f)",
287                         covB[0],covA[0],
288                         covB[1],covA[1],
289                         covB[2],covA[2],
290                         covB[3],covA[3],
291                         covB[4],covA[4],
292                         covB[5],covA[5],
293                         covB[6],covA[6],
294                         covB[7],covA[7],
295                         covB[8],covA[8],
296                         covB[9],covA[9],
297                         covB[10],covA[10],
298                         covB[11],covA[11],
299                         covB[12],covA[12],
300                         covB[13],covA[13],
301                         covB[14],covA[14]
302                         ));
303         AliDebug(3,Form(" TOF params: %6d  %f %f %f %f %f %6d %3d %f  %f %f %f %f %f",
304                         i,
305                         t->GetTOFsignalRaw(),
306                         t->GetTOFsignal(),
307                         t->GetTOFsignalToT(),
308                         t->GetTOFsignalDz(),
309                         t->GetTOFsignalDx(),
310                         t->GetTOFCalChannel(),
311                         t->GetTOFcluster(),
312                         t->GetIntegratedLength(),
313                         time[0], time[1], time[2], time[3], time[4]
314                         )
315                  );
316       }
317     }
318   }
319
320   //Make TOF PID
321   // Now done in AliESDpid
322   // fPid->MakePID(event,timeZero);
323
324   fSeeds->Clear();
325   //fTracks->Delete();
326   fTracks->Clear();
327   return 0;
328   
329 }
330 //_________________________________________________________________________
331 void AliTOFtracker::CollectESD() {
332    //prepare the set of ESD tracks to be matched to clusters in TOF
333
334   Int_t seedsTOF1=0;
335   Int_t seedsTOF3=0;
336   Int_t seedsTOF2=0;
337  
338   TClonesArray &aTOFTrack = *fTracks;
339   for (Int_t i=0; i<fNseeds; i++) {
340
341     AliESDtrack *t =(AliESDtrack*)fSeeds->At(i);
342     if ((t->GetStatus()&AliESDtrack::kTPCout)==0)continue;
343
344     AliTOFtrack *track = new AliTOFtrack(*t); // New
345     Float_t x = (Float_t)track->GetX(); //New
346
347     // TRD 'good' tracks
348     if ( ( (t->GetStatus()&AliESDtrack::kTRDout)!=0 ) ) {
349
350       AliDebug(1,Form(" Before propagation till inner TOF radius, ESDtrackLength=%f, TOFtrackLength=%f",t->GetIntegratedLength(),track->GetIntegratedLength()));
351
352       // TRD 'good' tracks, already propagated at 371 cm
353       if( x >= AliTOFGeometry::Rmin() ) {
354
355         if  ( track->PropagateToInnerTOF() ) {
356
357           AliDebug(1,Form(" TRD propagated track till rho = %fcm."
358                           " And then the track has been propagated till rho = %fcm.",
359                           x, (Float_t)track->GetX()));
360
361           track->SetSeedIndex(i);
362           t->UpdateTrackParams(track,AliESDtrack::kTOFin);
363           new(aTOFTrack[fNseedsTOF]) AliTOFtrack(*track);
364           fNseedsTOF++;
365           seedsTOF1++;
366
367           AliDebug(1,Form(" After propagation till inner TOF radius, ESDtrackLength=%f, TOFtrackLength=%f",t->GetIntegratedLength(),track->GetIntegratedLength()));
368         }
369         delete track;
370
371       }
372       else { // TRD 'good' tracks, propagated rho<371cm
373
374         if  ( track->PropagateToInnerTOF() ) {
375
376           AliDebug(1,Form(" TRD propagated track till rho = %fcm."
377                           " And then the track has been propagated till rho = %fcm.",
378                           x, (Float_t)track->GetX()));
379
380           track->SetSeedIndex(i);
381           t->UpdateTrackParams(track,AliESDtrack::kTOFin);
382           new(aTOFTrack[fNseedsTOF]) AliTOFtrack(*track);
383           fNseedsTOF++;
384           seedsTOF3++;
385
386           AliDebug(1,Form(" After propagation till inner TOF radius, ESDtrackLength=%f, TOFtrackLength=%f",t->GetIntegratedLength(),track->GetIntegratedLength()));
387         }
388         delete track;
389
390       }
391       //delete track;
392     }
393
394     else { // Propagate the rest of TPCbp
395
396       AliDebug(1,Form(" Before propagation till inner TOF radius, ESDtrackLength=%f, TOFtrackLength=%f",t->GetIntegratedLength(),track->GetIntegratedLength()));
397
398       if ( track->PropagateToInnerTOF() ) { 
399
400         AliDebug(1,Form(" TPC propagated track till rho = %fcm."
401                         " And then the track has been propagated till rho = %fcm.",
402                         x, (Float_t)track->GetX()));
403
404         track->SetSeedIndex(i);
405         t->UpdateTrackParams(track,AliESDtrack::kTOFin);
406         new(aTOFTrack[fNseedsTOF]) AliTOFtrack(*track);
407         fNseedsTOF++;
408         seedsTOF2++;
409
410         AliDebug(1,Form(" After propagation till inner TOF radius, ESDtrackLength=%f, TOFtrackLength=%f",t->GetIntegratedLength(),track->GetIntegratedLength()));
411       }
412       delete track;
413     }
414   }
415
416   AliInfo(Form("Number of TOF seeds = %d (kTRDout371 = %d, kTRDoutLess371 = %d, !kTRDout = %d)",fNseedsTOF,seedsTOF1,seedsTOF3,seedsTOF2));
417
418   // Sort according uncertainties on track position 
419   fTracks->Sort();
420
421 }
422
423 //_________________________________________________________________________
424 void AliTOFtracker::MatchTracks( Bool_t mLastStep){
425
426   // Parameters used/regulating the reconstruction
427
428   //static Float_t corrLen=0.;//0.75;
429   static Float_t detDepth=18.;
430   static Float_t padDepth=0.5;
431
432   const Float_t kSpeedOfLight= 2.99792458e-2; // speed of light [cm/ps]
433   const Float_t kTimeOffset = 0.; // time offset for tracking algorithm [ps]
434
435   Float_t dY=AliTOFGeometry::XPad(); 
436   Float_t dZ=AliTOFGeometry::ZPad(); 
437
438   Float_t sensRadius = fkRecoParam->GetSensRadius();
439   Float_t stepSize   = fkRecoParam->GetStepSize();
440   Float_t scaleFact  = fkRecoParam->GetWindowScaleFact();
441   Float_t dyMax=fkRecoParam->GetWindowSizeMaxY(); 
442   Float_t dzMax=fkRecoParam->GetWindowSizeMaxZ();
443   Float_t dCut=fkRecoParam->GetDistanceCut();
444   if (dCut==3. && fNseedsTOF<=10) {
445     dCut=10.;
446     AliInfo(Form("Matching window=%f, since low multiplicity event (fNseedsTOF=%d)",
447                  dCut, fNseedsTOF));
448   }
449   Double_t maxChi2=fkRecoParam->GetMaxChi2TRD();
450   Bool_t timeWalkCorr    = fkRecoParam->GetTimeWalkCorr();
451   if(!mLastStep){
452     AliDebug(1,"++++++++++++++TOF Reconstruction Parameters:++++++++++++ \n");
453     AliDebug(1,Form("TOF sens radius: %f",sensRadius));
454     AliDebug(1,Form("TOF step size: %f",stepSize));
455     AliDebug(1,Form("TOF Window scale factor: %f",scaleFact));
456     AliDebug(1,Form("TOF Window max dy: %f",dyMax));
457     AliDebug(1,Form("TOF Window max dz: %f",dzMax));
458     AliDebug(1,Form("TOF distance Cut: %f",dCut));
459     AliDebug(1,Form("TOF Max Chi2: %f",maxChi2));
460     AliDebug(1,Form("Time Walk Correction? : %d",timeWalkCorr));   
461   }
462
463   //Match ESD tracks to clusters in TOF
464
465   // Get the number of propagation steps
466   Int_t nSteps=(Int_t)(detDepth/stepSize);
467   AliDebug(1,Form(" Number of steps to be done %d",nSteps));
468
469   //PH Arrays (moved outside of the loop)
470   Float_t * trackPos[4];
471   for (Int_t ii=0; ii<4; ii++) trackPos[ii] = new Float_t[nSteps];
472   Int_t * clind = new Int_t[fN];
473   
474   // Some init
475   const Int_t kNclusterMax = 1000; // related to fN value
476   TGeoHMatrix global[kNclusterMax];
477
478   //The matching loop
479   for (Int_t iseed=0; iseed<fNseedsTOF; iseed++) {
480
481     fTOFtrackPoints->Delete();
482
483     for (Int_t ii=0; ii<kNclusterMax; ii++)
484       global[ii] = 0x0;
485     AliTOFtrack *track =(AliTOFtrack*)fTracks->UncheckedAt(iseed);
486     AliESDtrack *t =(AliESDtrack*)fSeeds->At(track->GetSeedIndex());
487     //if ( t->GetTOFsignal()>0. ) continue;
488     if ( (t->GetStatus()&AliESDtrack::kTOFout)!=0 ) continue;
489     AliTOFtrack *trackTOFin = new AliTOFtrack(*track);
490
491     // Determine a window around the track
492     Double_t x,par[5]; 
493     trackTOFin->GetExternalParameters(x,par);
494     Double_t cov[15]; 
495     trackTOFin->GetExternalCovariance(cov);
496
497     if (cov[0]<0. || cov[2]<0.) {
498       AliWarning(Form("Very strange track (%d)! At least one of its covariance matrix diagonal elements is negative!",iseed));
499       //delete trackTOFin;
500       //continue;
501     }
502
503     Double_t dphi=
504       scaleFact*
505       ((5*TMath::Sqrt(TMath::Abs(cov[0])) + 0.5*dY + 2.5*TMath::Abs(par[2]))/sensRadius); 
506     Double_t dz=
507        scaleFact*
508        (5*TMath::Sqrt(TMath::Abs(cov[2])) + 0.5*dZ + 2.5*TMath::Abs(par[3]));
509
510     Double_t phi=TMath::ATan2(par[0],x) + trackTOFin->GetAlpha();
511     if (phi<-TMath::Pi())phi+=2*TMath::Pi();
512     if (phi>=TMath::Pi())phi-=2*TMath::Pi();
513     Double_t z=par[1];   
514
515     //upper limit on window's size.
516     if (dz> dzMax) dz=dzMax;
517     if (dphi*sensRadius> dyMax) dphi=dyMax/sensRadius;
518
519
520     // find the clusters in the window of the track
521     Int_t nc=0;
522     for (Int_t k=FindClusterIndex(z-dz); k<fN; k++) {
523
524       if (nc>=kNclusterMax) {
525         AliWarning("No more matchable clusters can be stored! Please, increase the corresponding vectors size.");
526         break;
527       }
528
529       AliTOFcluster *c=fClusters[k];
530       if (c->GetZ() > z+dz) break;
531       if (c->IsUsed()) continue;
532       if (!c->GetStatus()) {
533         AliDebug(1,"Cluster in channel declared bad!");
534         continue; // skip bad channels as declared in OCDB
535       }
536
537       Double_t dph=TMath::Abs(c->GetPhi()-phi);
538       if (dph>TMath::Pi()) dph-=2.*TMath::Pi();
539       if (TMath::Abs(dph)>dphi) continue;
540
541       Double_t yc=(c->GetPhi() - trackTOFin->GetAlpha())*c->GetR();
542       Double_t p[2]={yc, c->GetZ()};
543       Double_t cov2[3]= {dY*dY/12., 0., dZ*dZ/12.};
544       if (trackTOFin->AliExternalTrackParam::GetPredictedChi2(p,cov2) > maxChi2)continue;
545
546       clind[nc] = k;      
547       Char_t path[200];
548       Int_t ind[5];
549       ind[0]=c->GetDetInd(0);
550       ind[1]=c->GetDetInd(1);
551       ind[2]=c->GetDetInd(2);
552       ind[3]=c->GetDetInd(3);
553       ind[4]=c->GetDetInd(4);
554       fGeom->GetVolumePath(ind,path);
555       gGeoManager->cd(path);
556       global[nc] = *gGeoManager->GetCurrentMatrix();
557       nc++;
558     }
559
560     AliDebug(1,Form(" Number of matchable TOF clusters for the track number %d: %d",iseed,nc));
561
562     if (nc == 0 ) {
563       fnunmatch++;
564       delete trackTOFin;
565       continue;
566     }
567
568     //start fine propagation 
569
570     Int_t nStepsDone = 0;
571     for( Int_t istep=0; istep<nSteps; istep++){ 
572
573       // First of all, propagate the track...
574       Float_t xs = AliTOFGeometry::RinTOF()+istep*stepSize;
575       if(!trackTOFin->PropagateTo(xs)) {
576         break;
577       }
578
579       //  ...and then, if necessary, rotate the track
580       Double_t ymax = xs*TMath::Tan(0.5*AliTOFGeometry::GetAlpha());
581       Double_t ysect = trackTOFin->GetY();
582       if (ysect > ymax) {
583         if (!trackTOFin->Rotate(AliTOFGeometry::GetAlpha())) {
584           break;
585         }
586       } else if (ysect <-ymax) {
587         if (!trackTOFin->Rotate(-AliTOFGeometry::GetAlpha())) {
588           break;
589         }
590       }
591
592       nStepsDone++;
593       AliDebug(2,Form(" current step %d (%d) - nStepsDone=%d",istep,nSteps,nStepsDone));
594
595       // store the running point (Globalrf) - fine propagation     
596
597       Double_t r[3];
598       trackTOFin->GetXYZ(r);
599       trackPos[0][nStepsDone-1]= (Float_t) r[0];
600       trackPos[1][nStepsDone-1]= (Float_t) r[1];
601       trackPos[2][nStepsDone-1]= (Float_t) r[2];   
602       trackPos[3][nStepsDone-1]= trackTOFin->GetIntegratedLength();
603     }
604
605
606 #if 0
607     /*****************/
608     /**** OLD CODE ***/
609     /*****************/
610
611     Int_t nfound = 0;
612     Bool_t accept = kFALSE;
613     Bool_t isInside = kFALSE;
614     for (Int_t istep=0; istep<nStepsDone; istep++) {
615
616       Float_t ctrackPos[3];     
617       ctrackPos[0] = trackPos[0][istep];
618       ctrackPos[1] = trackPos[1][istep];
619       ctrackPos[2] = trackPos[2][istep];
620
621       //now see whether the track matches any of the TOF clusters            
622
623       Float_t dist3d[3];
624       accept = kFALSE;
625       for (Int_t i=0; i<nc; i++) {
626         isInside = fGeom->IsInsideThePad((TGeoHMatrix*)(&global[i]),ctrackPos,dist3d);
627
628         if ( mLastStep ) {
629           Float_t yLoc = dist3d[1];
630           Float_t rLoc = TMath::Sqrt(dist3d[0]*dist3d[0]+dist3d[2]*dist3d[2]);
631           accept = (TMath::Abs(yLoc)<padDepth*0.5 && rLoc<dCut);
632           AliDebug(2," I am in the case mLastStep==kTRUE ");
633         }
634         else {
635           accept = isInside;
636         }
637         if (accept) {
638
639           fTOFtrackPoints->AddLast(new AliTOFtrackPoint(clind[i],
640                                                         TMath::Sqrt(dist3d[0]*dist3d[0] + dist3d[1]*dist3d[1] + dist3d[2]*dist3d[2]),
641                                                         dist3d[2],dist3d[0],dist3d[1],
642                                                         AliTOFGeometry::RinTOF()+istep*stepSize,trackPos[3][istep]));
643
644           AliDebug(2,Form(" dist3dLoc[0] = %f, dist3dLoc[1] = %f, dist3dLoc[2] = %f ",dist3d[0],dist3d[1],dist3d[2]));
645           nfound++;
646           if(accept &&!mLastStep)break;
647         }//end if accept
648
649       } //end for on the clusters
650       if(accept &&!mLastStep)break;
651     } //end for on the steps     
652
653     /*****************/
654     /**** OLD CODE ***/
655     /*****************/
656 #endif
657
658     AliDebug(1,Form(" Number of steps done for the track number %d: %d",iseed,nStepsDone));
659
660     if ( nStepsDone == 0 ) {
661       fnunmatch++;
662       delete trackTOFin;
663       continue;
664     }
665
666     /*****************/
667     /**** NEW CODE ***/
668     /*****************/
669
670     Int_t nfound = 0;
671     Bool_t accept = kFALSE;
672     Bool_t isInside = kFALSE;
673     for (Int_t istep=0; istep<nStepsDone; istep++) {
674
675       Bool_t gotInsideCluster = kFALSE;
676       Int_t trackInsideCluster = -1;
677
678       Float_t ctrackPos[3];     
679       ctrackPos[0] = trackPos[0][istep];
680       ctrackPos[1] = trackPos[1][istep];
681       ctrackPos[2] = trackPos[2][istep];
682
683       //now see whether the track matches any of the TOF clusters            
684
685       Float_t dist3d[3]={0.,0.,0.};
686       accept = kFALSE;
687       for (Int_t i=0; i<nc; i++) {
688
689         // ***** NEW *****
690         /* check whether track was inside another cluster
691          * and in case inhibit this cluster.
692          * this will allow to only go on and add track points for
693          * that cluster where the track got inside first */
694         if (gotInsideCluster && trackInsideCluster != i) {
695           AliDebug(2,Form(" A - istep=%d ~ %d %d ~ nfound=%d",istep,trackInsideCluster,i,nfound));
696           continue;
697         }
698         AliDebug(2,Form(" B - istep=%d ~ %d %d ~ nfound=%d",istep,trackInsideCluster,i,nfound));
699
700         /* check whether track is inside this cluster */
701         for (Int_t hh=0; hh<3; hh++) dist3d[hh]=0.;
702         isInside = fGeom->IsInsideThePad((TGeoHMatrix*)(&global[i]),ctrackPos,dist3d);
703
704         // ***** NEW *****
705         /* if track is inside this cluster set flags which will then
706          * inhibit to add track points for the other clusters */
707         if (isInside) {
708           gotInsideCluster = kTRUE;
709           trackInsideCluster = i;
710         }
711
712         if ( mLastStep ) {
713           Float_t yLoc = dist3d[1];
714           Float_t rLoc = TMath::Sqrt(dist3d[0]*dist3d[0]+dist3d[2]*dist3d[2]);
715           accept = (TMath::Abs(yLoc)<padDepth*0.5 && rLoc<dCut);
716           AliDebug(2," I am in the case mLastStep==kTRUE ");
717         }
718
719         //***** NEW *****
720         /* add point everytime that:
721          * - the track is inside the cluster
722          * - the track got inside the cluster, even when it eventually exited the cluster
723          * - the tracks is within dCut from the cluster
724          */
725         if (accept || isInside || gotInsideCluster) {
726
727           fTOFtrackPoints->AddLast(new AliTOFtrackPoint(clind[i],
728                                                         TMath::Sqrt(dist3d[0]*dist3d[0] + dist3d[1]*dist3d[1] + dist3d[2]*dist3d[2]),
729                                                         dist3d[2],dist3d[0],dist3d[1],
730                                                         AliTOFGeometry::RinTOF()+istep*stepSize,trackPos[3][istep]));
731
732           AliDebug(2,Form(" dist3dLoc[0] = %f, dist3dLoc[1] = %f, dist3dLoc[2] = %f ",dist3d[0],dist3d[1],dist3d[2]));
733           nfound++;
734
735           AliDebug(2,Form(" C - istep=%d ~ %d %d ~ nfound=%d",istep,trackInsideCluster,i,nfound));
736         
737           // ***** NEW *****
738           /* do not break loop in any case
739            * if the track got inside a cluster all other clusters
740            * are inhibited */
741           //      if(accept &&!mLastStep)break;
742           
743         }//end if accept
744         
745       } //end for on the clusters
746       
747       // ***** NEW *****
748       /* do not break loop in any case
749       * if the track got inside a cluster all other clusters
750       * are inhibited but we want to go on adding track points */
751       //      if(accept &&!mLastStep)break;
752       
753     } //end for on the steps     
754
755
756     AliDebug(1,Form(" Number of track points for the track number %d: %d",iseed,nfound));
757
758     if (nfound == 0 ) {
759       fnunmatch++;
760       delete trackTOFin;
761       continue;
762     }
763     
764     // now choose the cluster to be matched with the track.
765
766     Int_t idclus=-1;
767     Float_t  recL = 0.;
768     Float_t  xpos=0.;
769     Float_t  mindist=1000.;
770     Float_t  mindistZ=0.;
771     Float_t  mindistY=0.;
772     Float_t  mindistX=stepSize;
773     for (Int_t iclus= 0; iclus<nfound;iclus++) {
774       AliTOFtrackPoint *matchableTOFcluster = (AliTOFtrackPoint*)fTOFtrackPoints->At(iclus);
775       //if ( matchableTOFcluster->Distance()<mindist ) {
776       if ( TMath::Abs(matchableTOFcluster->DistanceX())<TMath::Abs(mindistX) &&
777            TMath::Abs(matchableTOFcluster->DistanceX())<=stepSize ) {
778         mindist = matchableTOFcluster->Distance();
779         mindistZ = matchableTOFcluster->DistanceZ(); // Z distance in the
780                                                      // RF of the hit pad
781                                                      // closest to the
782                                                      // reconstructed
783                                                      // track
784         mindistY = matchableTOFcluster->DistanceY(); // Y distance in the
785                                                      // RF of the hit pad
786                                                      // closest to the
787                                                      // reconstructed
788                                                      // track
789         mindistX = matchableTOFcluster->DistanceX(); // X distance in the
790                                                      // RF of the hit pad
791                                                      // closest to the
792                                                      // reconstructed
793                                                      // track
794         xpos = matchableTOFcluster->PropRadius();
795         idclus = matchableTOFcluster->Index();
796         recL = matchableTOFcluster->Length();// + corrLen*0.5;
797
798         AliDebug(1,Form(" %d(%d) --- %f (%f, %f, %f), step=%f -- idclus=%d --- seed=%d, trackId=%d, trackLab=%d", iclus,nfound,
799                         mindist,mindistX,mindistY,mindistZ,stepSize,idclus,iseed,track->GetSeedIndex(),track->GetLabel()));
800
801       }
802     } // loop on found TOF track points
803
804     if (TMath::Abs(mindistX)>stepSize && idclus!=-1) {
805       AliInfo(Form("--------Not matched --- but idclus=%d, trackId=%d, trackLab=%d",
806                    idclus,track->GetSeedIndex(),track->GetLabel()));
807       idclus=-1;
808     }
809
810     if (idclus==-1) {
811       AliDebug(1,Form("Reconstructed track %d doesn't match any TOF cluster", iseed));
812       fnunmatch++;
813       delete trackTOFin;
814       continue;
815     }
816
817     AliDebug(1,"--------Matched");
818
819     fnmatch++;
820
821     AliTOFcluster *c=fClusters[idclus];
822
823     AliDebug(2, Form("%7d     %7d     %10d     %10d  %10d  %10d      %7d",
824                      iseed,
825                      fnmatch-1,
826                      TMath::Abs(trackTOFin->GetLabel()),
827                      c->GetLabel(0), c->GetLabel(1), c->GetLabel(2),
828                      idclus)); // AdC
829
830     c->Use(); 
831
832     // Track length correction for matching Step 2 
833     /*
834     if (mLastStep) {
835       Float_t rc = TMath::Sqrt(c->GetR()*c->GetR() + c->GetZ()*c->GetZ());
836       Float_t rt = TMath::Sqrt(trackPos[0][70]*trackPos[0][70]
837                                +trackPos[1][70]*trackPos[1][70]
838                                +trackPos[2][70]*trackPos[2][70]);
839       Float_t dlt=rc-rt;
840       recL=trackPos[3][70]+dlt;
841     }
842     */
843     if (
844         (c->GetLabel(0)==TMath::Abs(trackTOFin->GetLabel()))
845         ||
846         (c->GetLabel(1)==TMath::Abs(trackTOFin->GetLabel()))
847         ||
848         (c->GetLabel(2)==TMath::Abs(trackTOFin->GetLabel()))
849         ) {
850       fngoodmatch++;
851
852        AliDebug(2,Form(" track label good %5d",trackTOFin->GetLabel()));
853
854     }
855     else {
856       fnbadmatch++;
857
858       AliDebug(2,Form(" track label  bad %5d",trackTOFin->GetLabel()));
859
860     }
861
862     delete trackTOFin;
863
864     //  Store quantities to be used in the TOF Calibration
865     Float_t tToT=AliTOFGeometry::ToTBinWidth()*c->GetToT()*1E-3; // in ns
866     t->SetTOFsignalToT(tToT);
867     Float_t rawTime=AliTOFGeometry::TdcBinWidth()*c->GetTDCRAW()+kTimeOffset; // RAW time,in ps
868     t->SetTOFsignalRaw(rawTime);
869     t->SetTOFsignalDz(mindistZ);
870     t->SetTOFsignalDx(mindistY);
871     t->SetTOFDeltaBC(c->GetDeltaBC());
872     t->SetTOFL0L1(c->GetL0L1Latency());
873
874     Float_t info[10] = {mindist,mindistY,mindistZ,
875                         0.,0.,0.,0.,0.,0.,0.};
876     t->SetTOFInfo(info);
877     AliDebug(2,Form(" distance=%f; residual in the pad reference frame: dX=%f, dZ=%f", info[0],info[1],info[2]));
878
879
880     Int_t ind[5];
881     ind[0]=c->GetDetInd(0);
882     ind[1]=c->GetDetInd(1);
883     ind[2]=c->GetDetInd(2);
884     ind[3]=c->GetDetInd(3);
885     ind[4]=c->GetDetInd(4);
886     Int_t calindex = AliTOFGeometry::GetIndex(ind);
887     t->SetTOFCalChannel(calindex);
888
889     // keep track of the track labels in the matched cluster
890     Int_t tlab[3];
891     tlab[0]=c->GetLabel(0);
892     tlab[1]=c->GetLabel(1);
893     tlab[2]=c->GetLabel(2);
894     AliDebug(2,Form(" tdc time of the matched track %6d = ",c->GetTDC()));    
895     Double_t tof=AliTOFGeometry::TdcBinWidth()*c->GetTDC()+kTimeOffset; // in ps
896     AliDebug(2,Form(" tof time of the matched track: %f = ",tof));    
897     Double_t tofcorr=tof;
898     if(timeWalkCorr)tofcorr=CorrectTimeWalk(mindistZ,tof);
899     AliDebug(2,Form(" tof time of the matched track, after TW corr: %f = ",tofcorr));    
900     //Set TOF time signal and pointer to the matched cluster
901     t->SetTOFsignal(tofcorr);
902     t->SetTOFcluster(idclus); // pointing to the recPoints tree
903
904     AliDebug(2,Form(" Setting TOF raw time: %f, z distance: %f  corrected time: %f ",rawTime,mindistZ,tofcorr));
905
906     //Tracking info
907     Double_t time[AliPID::kSPECIES]; t->GetIntegratedTimes(time); // in ps
908     Double_t mom=t->GetP();
909     AliDebug(2,Form(" Momentum for track %d -> %f", iseed,mom));
910     for (Int_t j=0;j<AliPID::kSPECIES;j++) {
911       Double_t mass=AliPID::ParticleMass(j);
912       time[j]+=(recL-trackPos[3][0])/kSpeedOfLight*TMath::Sqrt(mom*mom+mass*mass)/mom;
913     }
914
915     AliTOFtrack *trackTOFout = new AliTOFtrack(*t); 
916     trackTOFout->PropagateTo(xpos);
917
918     // If necessary, rotate the track
919     Double_t yATxposMax=xpos*TMath::Tan(0.5*AliTOFGeometry::GetAlpha());
920     Double_t yATxpos=trackTOFout->GetY();
921     if (yATxpos > yATxposMax) {
922       trackTOFout->Rotate(AliTOFGeometry::GetAlpha());
923     } else if (yATxpos < -yATxposMax) {
924       trackTOFout->Rotate(-AliTOFGeometry::GetAlpha());
925     }
926
927     // Fill the track residual histograms.
928     FillResiduals(trackTOFout,c,kFALSE);
929
930     t->UpdateTrackParams(trackTOFout,AliESDtrack::kTOFout);
931     t->SetIntegratedLength(recL);
932     t->SetIntegratedTimes(time);
933     t->SetTOFLabel(tlab);
934
935  
936     // Fill Reco-QA histos for Reconstruction
937     fHRecNClus->Fill(nc);
938     fHRecDist->Fill(mindist);
939     if (cov[0]>=0.)
940       fHRecSigYVsP->Fill(mom,TMath::Sqrt(cov[0]));
941     else
942       fHRecSigYVsP->Fill(mom,-TMath::Sqrt(-cov[0]));
943     if (cov[2]>=0.)
944       fHRecSigZVsP->Fill(mom,TMath::Sqrt(cov[2]));
945     else
946       fHRecSigZVsP->Fill(mom,-TMath::Sqrt(-cov[2]));
947     fHRecSigYVsPWin->Fill(mom,dphi*sensRadius);
948     fHRecSigZVsPWin->Fill(mom,dz);
949
950     // Fill Tree for on-the-fly offline Calibration
951
952     if ( !((t->GetStatus() & AliESDtrack::kTIME)==0 ) ) {
953       fIch=calindex;
954       fToT=tToT;
955       fTime=rawTime;
956       fExpTimePi=time[2];
957       fExpTimeKa=time[3];
958       fExpTimePr=time[4];
959       fCalTree->Fill();
960     }
961     delete trackTOFout;
962   }
963
964   for (Int_t ii=0; ii<4; ii++) delete [] trackPos[ii];
965   delete [] clind;
966  
967 }
968 //_________________________________________________________________________
969 Int_t AliTOFtracker::LoadClusters(TTree *cTree) {
970   //--------------------------------------------------------------------
971   //This function loads the TOF clusters
972   //--------------------------------------------------------------------
973
974   Int_t npadX = AliTOFGeometry::NpadX();
975   Int_t npadZ = AliTOFGeometry::NpadZ();
976   Int_t nStripA = AliTOFGeometry::NStripA();
977   Int_t nStripB = AliTOFGeometry::NStripB();
978   Int_t nStripC = AliTOFGeometry::NStripC();
979
980   TBranch *branch=cTree->GetBranch("TOF");
981   if (!branch) { 
982     AliError("can't get the branch with the TOF clusters !");
983     return 1;
984   }
985
986   static TClonesArray dummy("AliTOFcluster",10000);
987   dummy.Clear();
988   TClonesArray *clusters=&dummy;
989   branch->SetAddress(&clusters);
990
991   cTree->GetEvent(0);
992   Int_t nc=clusters->GetEntriesFast();
993   fHDigNClus->Fill(nc);
994
995   AliInfo(Form("Number of clusters: %d",nc));
996
997   for (Int_t i=0; i<nc; i++) {
998     AliTOFcluster *c=(AliTOFcluster*)clusters->UncheckedAt(i);
999 //PH    fClusters[i]=new AliTOFcluster(*c); fN++;
1000     fClusters[i]=c; fN++;
1001
1002   // Fill Digits QA histos
1003  
1004     Int_t isector = c->GetDetInd(0);
1005     Int_t iplate = c->GetDetInd(1);
1006     Int_t istrip = c->GetDetInd(2);
1007     Int_t ipadX = c->GetDetInd(4);
1008     Int_t ipadZ = c->GetDetInd(3);
1009
1010     Float_t time =(AliTOFGeometry::TdcBinWidth()*c->GetTDC())*1E-3; // in ns
1011     Float_t tot = (AliTOFGeometry::TdcBinWidth()*c->GetToT())*1E-3;//in ns
1012  
1013     Int_t stripOffset = 0;
1014     switch (iplate) {
1015     case 0:
1016       stripOffset = 0;
1017       break;
1018     case 1:
1019       stripOffset = nStripC;
1020       break;
1021     case 2:
1022       stripOffset = nStripC+nStripB;
1023       break;
1024     case 3:
1025       stripOffset = nStripC+nStripB+nStripA;
1026       break;
1027     case 4:
1028       stripOffset = nStripC+nStripB+nStripA+nStripB;
1029       break;
1030     default:
1031       AliError(Form("Wrong plate number in TOF (%d) !",iplate));
1032       break;
1033     };
1034     Int_t zindex=npadZ*(istrip+stripOffset)+(ipadZ+1);
1035     Int_t phiindex=npadX*isector+ipadX+1;
1036     fHDigClusMap->Fill(zindex,phiindex);
1037     fHDigClusTime->Fill(time);
1038     fHDigClusToT->Fill(tot);
1039
1040   }
1041
1042
1043   return 0;
1044 }
1045 //_________________________________________________________________________
1046 void AliTOFtracker::UnloadClusters() {
1047   //--------------------------------------------------------------------
1048   //This function unloads TOF clusters
1049   //--------------------------------------------------------------------
1050   for (Int_t i=0; i<fN; i++) {
1051 //PH    delete fClusters[i];
1052     fClusters[i] = 0x0;
1053   }
1054   fN=0;
1055 }
1056
1057 //_________________________________________________________________________
1058 Int_t AliTOFtracker::FindClusterIndex(Double_t z) const {
1059   //--------------------------------------------------------------------
1060   // This function returns the index of the nearest cluster 
1061   //--------------------------------------------------------------------
1062   if (fN==0) return 0;
1063   if (z <= fClusters[0]->GetZ()) return 0;
1064   if (z > fClusters[fN-1]->GetZ()) return fN;
1065   Int_t b=0, e=fN-1, m=(b+e)/2;
1066   for (; b<e; m=(b+e)/2) {
1067     if (z > fClusters[m]->GetZ()) b=m+1;
1068     else e=m; 
1069   }
1070   return m;
1071 }
1072
1073 //_________________________________________________________________________
1074 Bool_t AliTOFtracker::GetTrackPoint(Int_t index, AliTrackPoint& p) const
1075 {
1076   // Get track space point with index i
1077   // Coordinates are in the global system
1078   AliTOFcluster *cl = fClusters[index];
1079   Float_t xyz[3];
1080   xyz[0] = cl->GetR()*TMath::Cos(cl->GetPhi());
1081   xyz[1] = cl->GetR()*TMath::Sin(cl->GetPhi());
1082   xyz[2] = cl->GetZ();
1083   Float_t phiangle = (Int_t(cl->GetPhi()*TMath::RadToDeg()/20.)+0.5)*20.*TMath::DegToRad();
1084   Float_t sinphi = TMath::Sin(phiangle), cosphi = TMath::Cos(phiangle);
1085   Float_t tiltangle = AliTOFGeometry::GetAngles(cl->GetDetInd(1),cl->GetDetInd(2))*TMath::DegToRad();
1086   Float_t sinth = TMath::Sin(tiltangle), costh = TMath::Cos(tiltangle);
1087   Float_t sigmay2 = AliTOFGeometry::XPad()*AliTOFGeometry::XPad()/12.;
1088   Float_t sigmaz2 = AliTOFGeometry::ZPad()*AliTOFGeometry::ZPad()/12.;
1089   Float_t cov[6];
1090   cov[0] = sinphi*sinphi*sigmay2 + cosphi*cosphi*sinth*sinth*sigmaz2;
1091   cov[1] = -sinphi*cosphi*sigmay2 + sinphi*cosphi*sinth*sinth*sigmaz2;
1092   cov[2] = -cosphi*sinth*costh*sigmaz2;
1093   cov[3] = cosphi*cosphi*sigmay2 + sinphi*sinphi*sinth*sinth*sigmaz2;
1094   cov[4] = -sinphi*sinth*costh*sigmaz2;
1095   cov[5] = costh*costh*sigmaz2;
1096   p.SetXYZ(xyz[0],xyz[1],xyz[2],cov);
1097
1098   // Detector numbering scheme
1099   Int_t nSector = AliTOFGeometry::NSectors();
1100   Int_t nPlate  = AliTOFGeometry::NPlates();
1101   Int_t nStripA = AliTOFGeometry::NStripA();
1102   Int_t nStripB = AliTOFGeometry::NStripB();
1103   Int_t nStripC = AliTOFGeometry::NStripC();
1104
1105   Int_t isector = cl->GetDetInd(0);
1106   if (isector >= nSector)
1107     AliError(Form("Wrong sector number in TOF (%d) !",isector));
1108   Int_t iplate = cl->GetDetInd(1);
1109   if (iplate >= nPlate)
1110     AliError(Form("Wrong plate number in TOF (%d) !",iplate));
1111   Int_t istrip = cl->GetDetInd(2);
1112
1113   Int_t stripOffset = 0;
1114   switch (iplate) {
1115   case 0:
1116     stripOffset = 0;
1117     break;
1118   case 1:
1119     stripOffset = nStripC;
1120     break;
1121   case 2:
1122     stripOffset = nStripC+nStripB;
1123     break;
1124   case 3:
1125     stripOffset = nStripC+nStripB+nStripA;
1126     break;
1127   case 4:
1128     stripOffset = nStripC+nStripB+nStripA+nStripB;
1129     break;
1130   default:
1131     AliError(Form("Wrong plate number in TOF (%d) !",iplate));
1132     break;
1133   };
1134
1135   Int_t idet = (2*(nStripC+nStripB)+nStripA)*isector +
1136                stripOffset +
1137                istrip;
1138   UShort_t volid = AliGeomManager::LayerToVolUID(AliGeomManager::kTOF,idet);
1139   p.SetVolumeID((UShort_t)volid);
1140   return kTRUE;
1141 }
1142 //_________________________________________________________________________
1143 void AliTOFtracker::InitCheckHists() {
1144
1145   //Init histos for Digits/Reco QA and Calibration
1146
1147
1148   TDirectory *dir = gDirectory;
1149   TFile *logFileTOF = 0;
1150
1151   TSeqCollection *list = gROOT->GetListOfFiles();
1152   int n = list->GetEntries();
1153   Bool_t isThere=kFALSE;
1154   for(int i=0; i<n; i++) {
1155     logFileTOF = (TFile*)list->At(i);
1156     if (strstr(logFileTOF->GetName(), "TOFQA.root")){
1157       isThere=kTRUE;
1158       break;
1159     } 
1160   }
1161
1162   if(!isThere)logFileTOF = new TFile( "TOFQA.root","RECREATE");
1163   logFileTOF->cd(); 
1164
1165   fCalTree = new TTree("CalTree", "Tree for TOF calibration");
1166   fCalTree->Branch("TOFchannelindex",&fIch,"iTOFch/I");
1167   fCalTree->Branch("ToT",&fToT,"TOFToT/F");
1168   fCalTree->Branch("TOFtime",&fTime,"TOFtime/F");
1169   fCalTree->Branch("PionExpTime",&fExpTimePi,"PiExpTime/F");
1170   fCalTree->Branch("KaonExpTime",&fExpTimeKa,"KaExpTime/F");
1171   fCalTree->Branch("ProtonExpTime",&fExpTimePr,"PrExpTime/F");
1172
1173   //Digits "QA" 
1174   fHDigClusMap = new TH2F("TOFDig_ClusMap", "",182,0.5,182.5,864, 0.5,864.5);  
1175   fHDigNClus = new TH1F("TOFDig_NClus", "",200,0.5,200.5);  
1176   fHDigClusTime = new TH1F("TOFDig_ClusTime", "",2000,0.,200.);  
1177   fHDigClusToT = new TH1F("TOFDig_ClusToT", "",500,0.,100);  
1178
1179   //Reco "QA"
1180   fHRecNClus =new TH1F("TOFRec_NClusW", "",50,0.5,50.5);
1181   fHRecDist=new TH1F("TOFRec_Dist", "",50,0.5,10.5);
1182   fHRecSigYVsP=new TH2F("TOFDig_SigYVsP", "",40,0.,4.,100, 0.,5.);
1183   fHRecSigZVsP=new TH2F("TOFDig_SigZVsP", "",40,0.,4.,100, 0.,5.);
1184   fHRecSigYVsPWin=new TH2F("TOFDig_SigYVsPWin", "",40,0.,4.,100, 0.,50.);
1185   fHRecSigZVsPWin=new TH2F("TOFDig_SigZVsPWin", "",40,0.,4.,100, 0.,50.);
1186
1187   dir->cd();
1188
1189 }
1190
1191 //_________________________________________________________________________
1192 void AliTOFtracker::SaveCheckHists() {
1193
1194   //write histos for Digits/Reco QA and Calibration
1195
1196   TDirectory *dir = gDirectory;
1197   TFile *logFileTOF = 0;
1198
1199   TSeqCollection *list = gROOT->GetListOfFiles();
1200   int n = list->GetEntries();
1201   Bool_t isThere=kFALSE;
1202   for(int i=0; i<n; i++) {
1203     logFileTOF = (TFile*)list->At(i);
1204     if (strstr(logFileTOF->GetName(), "TOFQA.root")){
1205       isThere=kTRUE;
1206       break;
1207     } 
1208   }
1209    
1210   if(!isThere) {
1211           AliError(Form("File TOFQA.root not found!! not wring histograms...."));
1212           return;
1213   }
1214   logFileTOF->cd(); 
1215   fHDigClusMap->Write(fHDigClusMap->GetName(), TObject::kOverwrite);
1216   fHDigNClus->Write(fHDigNClus->GetName(), TObject::kOverwrite);
1217   fHDigClusTime->Write(fHDigClusTime->GetName(), TObject::kOverwrite);
1218   fHDigClusToT->Write(fHDigClusToT->GetName(), TObject::kOverwrite);
1219   fHRecNClus->Write(fHRecNClus->GetName(), TObject::kOverwrite);
1220   fHRecDist->Write(fHRecDist->GetName(), TObject::kOverwrite);
1221   fHRecSigYVsP->Write(fHRecSigYVsP->GetName(), TObject::kOverwrite);
1222   fHRecSigZVsP->Write(fHRecSigZVsP->GetName(), TObject::kOverwrite);
1223   fHRecSigYVsPWin->Write(fHRecSigYVsPWin->GetName(), TObject::kOverwrite);
1224   fHRecSigZVsPWin->Write(fHRecSigZVsPWin->GetName(), TObject::kOverwrite);
1225   fCalTree->Write(fCalTree->GetName(),TObject::kOverwrite);
1226   logFileTOF->Flush();  
1227
1228   dir->cd();
1229   }
1230 //_________________________________________________________________________
1231 Float_t AliTOFtracker::CorrectTimeWalk( Float_t dist, Float_t tof) const {
1232
1233   //dummy, for the moment
1234   Float_t tofcorr=0.;
1235   if(dist<AliTOFGeometry::ZPad()*0.5){
1236     tofcorr=tof;
1237     //place here the actual correction
1238   }else{
1239     tofcorr=tof; 
1240   } 
1241   return tofcorr;
1242 }
1243 //_________________________________________________________________________
1244
1245 void AliTOFtracker::FillClusterArray(TObjArray* arr) const
1246 {
1247   //
1248   // Returns the TOF cluster array
1249   //
1250
1251   if (fN==0)
1252     arr = 0x0;
1253   else
1254     for (Int_t i=0; i<fN; ++i) arr->Add(fClusters[i]);
1255
1256 }
1257 //_________________________________________________________________________
1258