]> git.uio.no Git - u/mrichter/AliRoot.git/blob - STEER/ESD/AliESDEvent.cxx
make Whoami() compile nicely + other warning fixes
[u/mrichter/AliRoot.git] / STEER / ESD / AliESDEvent.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: AliESDEvent.cxx 64008 2013-08-28 13:09:59Z hristov $ */
17
18 //-----------------------------------------------------------------
19 //           Implementation of the AliESDEvent class
20 //   This is the class to deal with during the physics analysis of data.
21 //   It also ensures the backward compatibility with the old ESD format.
22 /*
23    AliESDEvent *ev= new AliESDEvent();
24    ev->ReadFromTree(esdTree);
25    ...
26     for (Int_t i=0; i<nev; i++) {
27       esdTree->GetEntry(i);
28       if(ev->GetAliESDOld())ev->CopyFromOldESD();
29 */
30 //   The AliESDInputHandler does this automatically for you
31 //
32 // Origin: Christian Klein-Boesing, CERN, Christian.Klein-Boesing@cern.ch
33 //-----------------------------------------------------------------
34
35 #include "TList.h"
36 #include "TRefArray.h"
37 #include <TNamed.h>
38 #include <TROOT.h>
39 #include <TInterpreter.h>
40
41 #include "AliESDEvent.h"
42 #include "AliESDfriend.h"
43 #include "AliESDVZERO.h"
44 #include "AliESDFMD.h"
45 #include "AliESD.h"
46 #include "AliESDMuonTrack.h"
47 #include "AliESDMuonCluster.h"
48 #include "AliESDMuonPad.h"
49 #include "AliESDMuonGlobalTrack.h"       // AU
50 #include "AliESDPmdTrack.h"
51 #include "AliESDTrdTrack.h"
52 #include "AliESDVertex.h"
53 #include "AliESDcascade.h"
54 #include "AliESDPmdTrack.h"
55 #include "AliESDTrdTrigger.h"
56 #include "AliESDTrdTrack.h"
57 #include "AliESDTrdTracklet.h"
58 #include "AliESDVertex.h"
59 #include "AliVertexerTracks.h"
60 #include "AliESDcascade.h"
61 #include "AliESDkink.h"
62 #include "AliESDtrack.h"
63 #include "AliESDHLTtrack.h"
64 #include "AliESDCaloCluster.h"
65 #include "AliESDCaloCells.h"
66 #include "AliESDv0.h"
67 #include "AliESDFMD.h"
68 #include "AliESDVZERO.h"
69 #include "AliMultiplicity.h"
70 #include "AliRawDataErrorLog.h"
71 #include "AliLog.h"
72 #include "AliESDACORDE.h"
73 #include "AliESDAD.h"
74 #include "AliESDHLTDecision.h"
75 #include "AliCentrality.h"
76 #include "AliESDCosmicTrack.h"
77 #include "AliTriggerConfiguration.h"
78 #include "AliTriggerClass.h"
79 #include "AliTriggerCluster.h"
80 #include "AliEventplane.h"
81
82 ClassImp(AliESDEvent)
83
84 // here we define the names, some classes are no TNamed, therefore the classnames 
85 // are the Names
86   const char* AliESDEvent::fgkESDListName[kESDListN] = {"AliESDRun",
87                                                         "AliESDHeader",
88                                                         "AliESDZDC",
89                                                         "AliESDFMD",
90                                                         "AliESDVZERO",
91                                                         "AliESDTZERO",
92                                                         "TPCVertex",
93                                                         "SPDVertex",
94                                                         "PrimaryVertex",
95                                                         "AliMultiplicity",
96                                                         "PHOSTrigger",
97                                                         "EMCALTrigger",
98                                                         "SPDPileupVertices",
99                                                         "TrkPileupVertices",
100                                                         "Tracks",
101                                                         "MuonTracks",
102                                                         "MuonClusters",
103                                                         "MuonPads",
104                                                         "MuonGlobalTracks",      // AU
105                                                         "PmdTracks",
106                                                         "AliESDTrdTrigger",
107                                                         "TrdTracks",
108                                                         "TrdTracklets",
109                                                         "V0s",
110                                                         "Cascades",
111                                                         "Kinks",
112                                                         "CaloClusters",
113                                                         "EMCALCells",
114                                                         "PHOSCells",
115                                                         "AliRawDataErrorLogs",
116                                                         "AliESDACORDE",
117                                                         "AliESDAD",
118                                                         "AliTOFHeader",
119                                                         "CosmicTracks",
120                                                         "AliESDTOFCluster",
121                                                         "AliESDTOFHit",
122                                                         "AliESDTOFMatch"};
123
124
125 //______________________________________________________________________________
126 AliESDEvent::AliESDEvent():
127   AliVEvent(),
128   fESDObjects(new TList()),
129   fESDRun(0),
130   fHeader(0),
131   fESDZDC(0),
132   fESDFMD(0),
133   fESDVZERO(0),
134   fESDTZERO(0),
135   fTPCVertex(0),
136   fSPDVertex(0),
137   fPrimaryVertex(0),
138   fSPDMult(0),
139   fPHOSTrigger(0),
140   fEMCALTrigger(0),
141   fESDACORDE(0),
142   fESDAD(0),
143   fTrdTrigger(0),
144   fSPDPileupVertices(0),
145   fTrkPileupVertices(0),
146   fTracks(0),
147   fMuonTracks(0),
148   fMuonClusters(0),
149   fMuonPads(0),
150   fMuonGlobalTracks(0),    // AU
151   fPmdTracks(0),
152   fTrdTracks(0),
153   fTrdTracklets(0),
154   fV0s(0),  
155   fCascades(0),
156   fKinks(0),
157   fCaloClusters(0),
158   fEMCALCells(0), fPHOSCells(0),
159   fCosmicTracks(0),
160   fESDTOFClusters(0),
161   fESDTOFHits(0),
162   fESDTOFMatchess(0),
163   fErrorLogs(0),
164   fOldMuonStructure(kFALSE),
165   fESDOld(0),
166   fESDFriendOld(0),
167   fConnected(kFALSE),
168   fUseOwnList(kFALSE),
169   fTracksConnected(kFALSE),
170   fTOFHeader(0),
171   fCentrality(0),
172   fEventplane(0),
173   fDetectorStatus(0xFFFFFFFF),
174   fDAQDetectorPattern(0xFFFF),
175   fDAQAttributes(0xFFFF)
176 {
177 }
178 //______________________________________________________________________________
179 AliESDEvent::AliESDEvent(const AliESDEvent& esd):
180   AliVEvent(esd),
181   fESDObjects(new TList()),
182   fESDRun(new AliESDRun(*esd.fESDRun)),
183   fHeader(new AliESDHeader(*esd.fHeader)),
184   fESDZDC(new AliESDZDC(*esd.fESDZDC)),
185   fESDFMD(new AliESDFMD(*esd.fESDFMD)),
186   fESDVZERO(new AliESDVZERO(*esd.fESDVZERO)),
187   fESDTZERO(new AliESDTZERO(*esd.fESDTZERO)),
188   fTPCVertex(new AliESDVertex(*esd.fTPCVertex)),
189   fSPDVertex(new AliESDVertex(*esd.fSPDVertex)),
190   fPrimaryVertex(new AliESDVertex(*esd.fPrimaryVertex)),
191   fSPDMult(new AliMultiplicity(*esd.fSPDMult)),
192   fPHOSTrigger(new AliESDCaloTrigger(*esd.fPHOSTrigger)),
193   fEMCALTrigger(new AliESDCaloTrigger(*esd.fEMCALTrigger)),
194   fESDACORDE(new AliESDACORDE(*esd.fESDACORDE)),
195   fESDAD(new AliESDAD(*esd.fESDAD)),
196   fTrdTrigger(new AliESDTrdTrigger(*esd.fTrdTrigger)),
197   fSPDPileupVertices(new TClonesArray(*esd.fSPDPileupVertices)),
198   fTrkPileupVertices(new TClonesArray(*esd.fTrkPileupVertices)),
199   fTracks(new TClonesArray(*esd.fTracks)),
200   fMuonTracks(new TClonesArray(*esd.fMuonTracks)),
201   fMuonClusters(new TClonesArray(*esd.fMuonClusters)),
202   fMuonPads(new TClonesArray(*esd.fMuonPads)),
203   fMuonGlobalTracks(new TClonesArray(*esd.fMuonGlobalTracks)),     // AU
204   fPmdTracks(new TClonesArray(*esd.fPmdTracks)),
205   fTrdTracks(new TClonesArray(*esd.fTrdTracks)),
206   fTrdTracklets(new TClonesArray(*esd.fTrdTracklets)),
207   fV0s(new TClonesArray(*esd.fV0s)),  
208   fCascades(new TClonesArray(*esd.fCascades)),
209   fKinks(new TClonesArray(*esd.fKinks)),
210   fCaloClusters(new TClonesArray(*esd.fCaloClusters)),
211   fEMCALCells(new AliESDCaloCells(*esd.fEMCALCells)),
212   fPHOSCells(new AliESDCaloCells(*esd.fPHOSCells)),
213   fCosmicTracks(new TClonesArray(*esd.fCosmicTracks)),
214   fESDTOFClusters(esd.fESDTOFClusters ? new TClonesArray(*esd.fESDTOFClusters) : 0),
215   fESDTOFHits(esd.fESDTOFHits ? new TClonesArray(*esd.fESDTOFHits) : 0),
216   fESDTOFMatchess(esd.fESDTOFMatchess ? new TClonesArray(*esd.fESDTOFMatchess) : 0),
217   fErrorLogs(new TClonesArray(*esd.fErrorLogs)),
218   fOldMuonStructure(esd.fOldMuonStructure),
219   fESDOld(esd.fESDOld ? new AliESD(*esd.fESDOld) : 0),
220   fESDFriendOld(esd.fESDFriendOld ? new AliESDfriend(*esd.fESDFriendOld) : 0),
221   fConnected(esd.fConnected),
222   fUseOwnList(esd.fUseOwnList),
223   fTracksConnected(kFALSE),
224   fTOFHeader(new AliTOFHeader(*esd.fTOFHeader)),
225   fCentrality(new AliCentrality(*esd.fCentrality)),
226   fEventplane(new AliEventplane(*esd.fEventplane)),
227   fDetectorStatus(esd.fDetectorStatus),
228   fDAQDetectorPattern(esd.fDAQDetectorPattern),
229   fDAQAttributes(esd.fDAQAttributes)
230 {
231   printf("copying ESD event...\n");   // AU
232   // CKB init in the constructor list and only add here ...
233   AddObject(fESDRun);
234   AddObject(fHeader);
235   AddObject(fESDZDC);
236   AddObject(fESDFMD);
237   AddObject(fESDVZERO);
238   AddObject(fESDTZERO);
239   AddObject(fTPCVertex);
240   AddObject(fSPDVertex);
241   AddObject(fPrimaryVertex);
242   AddObject(fSPDMult);
243   AddObject(fPHOSTrigger);
244   AddObject(fEMCALTrigger);
245   AddObject(fTrdTrigger);
246   AddObject(fSPDPileupVertices);
247   AddObject(fTrkPileupVertices);
248   AddObject(fTracks);
249   AddObject(fMuonTracks);
250   AddObject(fMuonGlobalTracks);    // AU
251   AddObject(fPmdTracks);
252   AddObject(fTrdTracks);
253   AddObject(fTrdTracklets);
254   AddObject(fV0s);
255   AddObject(fCascades);
256   AddObject(fKinks);
257   AddObject(fCaloClusters);
258   AddObject(fEMCALCells);
259   AddObject(fPHOSCells);
260   AddObject(fCosmicTracks);
261   AddObject(fESDTOFClusters);
262   AddObject(fESDTOFHits);
263   AddObject(fESDTOFMatchess);
264   AddObject(fErrorLogs);
265   AddObject(fESDACORDE);
266   AddObject(fESDAD);
267   AddObject(fTOFHeader);
268   AddObject(fMuonClusters);
269   AddObject(fMuonPads);
270   GetStdContent();
271   ConnectTracks();
272 }
273
274 //______________________________________________________________________________
275 AliESDEvent & AliESDEvent::operator=(const AliESDEvent& source) {
276
277   // Assignment operator
278   printf("operator = ESD\n");
279   if(&source == this) return *this;
280   AliVEvent::operator=(source);
281
282   // This assumes that the list is already created
283   // and that the virtual void Copy(Tobject&) function
284   // is correctly implemented in the derived class
285   // otherwise only TObject::Copy() will be used
286
287
288
289   if((fESDObjects->GetSize()==0)&&(source.fESDObjects->GetSize()>=kESDListN)){
290     // We cover the case that we do not yet have the 
291     // standard content but the source has it
292     CreateStdContent();
293   }
294
295   TIter next(source.GetList());
296   TObject *its = 0;
297   TString name;
298   while ((its = next())) {
299     name.Form("%s", its->GetName());
300     TObject *mine = fESDObjects->FindObject(name.Data());
301     if(!mine){
302       TClass* pClass=TClass::GetClass(its->ClassName());
303       if (!pClass) {
304         AliWarning(Form("Can not find class description for entry %s (%s)\n",
305                         its->ClassName(), name.Data()));
306         continue;
307       }
308
309       mine=(TObject*)pClass->New();
310       if(!mine){
311       // not in this: can be added to list
312         AliWarning(Form("%s:%d Could not find %s for copying \n",
313                         (char*)__FILE__,__LINE__,name.Data()));
314         continue;
315       }  
316       if(mine->InheritsFrom("TNamed")){
317         ((TNamed*)mine)->SetName(name);
318       }
319       else if(mine->InheritsFrom("TCollection")){
320         if(mine->InheritsFrom("TClonesArray")) {
321           TClonesArray* tcits = dynamic_cast<TClonesArray*>(its);
322           if (tcits)
323             dynamic_cast<TClonesArray*>(mine)->SetClass(tcits->GetClass());
324         }
325         dynamic_cast<TCollection*>(mine)->SetName(name);
326       }
327       AliDebug(1, Form("adding object %s of type %s", mine->GetName(), mine->ClassName()));
328       AddObject(mine);
329     }  
330    
331     if(!its->InheritsFrom("TCollection")){
332       // simple objects
333       its->Copy(*mine);
334     }
335     else if(its->InheritsFrom("TClonesArray")){
336       // Create or expand the tclonesarray pointers
337       // so we can directly copy to the object
338       TClonesArray *itstca = (TClonesArray*)its;
339       TClonesArray *minetca = (TClonesArray*)mine;
340
341       // this leaves the capacity of the TClonesArray the same
342       // except for a factor of 2 increase when size > capacity
343       // does not release any memory occupied by the tca
344       minetca->ExpandCreate(itstca->GetEntriesFast());
345       for(int i = 0;i < itstca->GetEntriesFast();++i){
346         // copy 
347         TObject *minetcaobj = minetca->At(i);
348         TObject *itstcaobj = itstca->At(i);
349         // no need to delete first
350         // pointers within the class should be handled by Copy()...
351         // Can there be Empty slots?
352         itstcaobj->Copy(*minetcaobj);
353       }
354     }
355     else{
356       AliWarning(Form("%s:%d cannot copy TCollection \n",
357                       (char*)__FILE__,__LINE__));
358     }
359   }
360
361   fOldMuonStructure = source.fOldMuonStructure;
362   
363   fCentrality = source.fCentrality;
364   fEventplane = source.fEventplane;
365
366   fConnected  = source.fConnected;
367   fUseOwnList = source.fUseOwnList;
368
369   fDetectorStatus = source.fDetectorStatus;
370   fDAQDetectorPattern = source.fDAQDetectorPattern;
371   fDAQAttributes = source.fDAQAttributes;
372
373   fTracksConnected = kFALSE;
374   ConnectTracks();
375   return *this;
376 }
377
378
379 //______________________________________________________________________________
380 AliESDEvent::~AliESDEvent()
381 {
382   //
383   // Standard destructor
384   //
385
386   // everthing on the list gets deleted automatically
387
388   
389   if(fESDObjects&&!fConnected)
390     {
391       delete fESDObjects;
392       fESDObjects = 0;
393     }
394   if (fCentrality) delete fCentrality;
395   if (fEventplane) delete fEventplane;
396   
397
398 }
399
400 void AliESDEvent::Copy(TObject &obj) const {
401
402   // interface to TOBject::Copy
403   // Copies the content of this into obj!
404   // bascially obj = *this
405
406   if(this==&obj)return;
407   AliESDEvent *robj = dynamic_cast<AliESDEvent*>(&obj);
408   if(!robj)return; // not an AliESEvent
409   *robj = *this;
410   return;
411 }
412
413 //______________________________________________________________________________
414 void AliESDEvent::Reset()
415 {
416
417   // Handle the cases
418   // Std content + Non std content
419
420   // Reset the standard contents
421   ResetStdContent(); 
422   fDetectorStatus = 0xFFFFFFFF;
423   fDAQDetectorPattern = 0xFFFF;
424   fDAQAttributes = 0xFFFF;
425   //  reset for the old data without AliESDEvent...
426   if(fESDOld)fESDOld->Reset();
427   if(fESDFriendOld){
428     fESDFriendOld->~AliESDfriend();
429     new (fESDFriendOld) AliESDfriend();
430   }
431   // 
432
433   if(fESDObjects->GetSize()>kESDListN){
434     // we have non std content
435     // this also covers esdfriends
436     for(int i = kESDListN;i < fESDObjects->GetSize();++i){
437       TObject *pObject = fESDObjects->At(i);
438       // TClonesArrays
439       if(pObject->InheritsFrom(TClonesArray::Class())){
440         ((TClonesArray*)pObject)->Delete();
441       }
442       else if(!pObject->InheritsFrom(TCollection::Class())){
443         TClass *pClass = TClass::GetClass(pObject->ClassName());
444         if (pClass && pClass->GetListOfMethods()->FindObject("Clear")) {
445           AliDebug(1, Form("Clear for object %s class %s", pObject->GetName(), pObject->ClassName()));
446           pObject->Clear();
447         }
448         else {
449           AliDebug(1, Form("ResetWithPlacementNew for object %s class %s", pObject->GetName(), pObject->ClassName()));
450           ResetWithPlacementNew(pObject);
451         }
452       }
453       else{
454         AliWarning(Form("No reset for %s \n",
455                         pObject->ClassName()));
456       }
457     }
458   }
459
460 }
461
462 //______________________________________________________________________________
463 Bool_t AliESDEvent::ResetWithPlacementNew(TObject *pObject){
464   //
465   // funtion to reset using the already allocated space
466   //
467   Long_t dtoronly = TObject::GetDtorOnly();
468   TClass *pClass = TClass::GetClass(pObject->ClassName()); 
469   TObject::SetDtorOnly(pObject);
470   delete pObject;
471   // Recreate with placement new
472   pClass->New(pObject);
473   // Restore the state.
474   TObject::SetDtorOnly((void*)dtoronly);
475   return kTRUE;
476 }
477
478 //______________________________________________________________________________
479 void AliESDEvent::ResetStdContent()
480 {
481   // Reset the standard contents
482   if(fESDRun) fESDRun->Reset();
483   if(fHeader) fHeader->Reset();
484   if(fCentrality) fCentrality->Reset();
485   if(fEventplane) fEventplane->Reset();
486   if(fESDZDC) fESDZDC->Reset();
487   if(fESDFMD) {
488     fESDFMD->Clear();
489   }
490   if(fESDVZERO){
491     // reset by callin d'to /c'tor keep the pointer
492     fESDVZERO->~AliESDVZERO();
493     new (fESDVZERO) AliESDVZERO();
494   }  
495   if(fESDACORDE){
496     fESDACORDE->~AliESDACORDE();
497     new (fESDACORDE) AliESDACORDE();    
498   } 
499
500   if(fESDAD){
501     fESDAD->~AliESDAD();
502     new (fESDAD) AliESDAD();    
503   } 
504
505
506   if(fESDTZERO) fESDTZERO->Reset(); 
507   // CKB no clear/reset implemented
508   if(fTPCVertex){
509     fTPCVertex->~AliESDVertex();
510     new (fTPCVertex) AliESDVertex();
511     fTPCVertex->SetName(fgkESDListName[kTPCVertex]);
512   }
513   if(fSPDVertex){
514     fSPDVertex->~AliESDVertex();
515     new (fSPDVertex) AliESDVertex();
516     fSPDVertex->SetName(fgkESDListName[kSPDVertex]);
517   }
518   if(fPrimaryVertex){
519     fPrimaryVertex->~AliESDVertex();
520     new (fPrimaryVertex) AliESDVertex();
521     fPrimaryVertex->SetName(fgkESDListName[kPrimaryVertex]);
522   }
523   if(fSPDMult){
524     fSPDMult->~AliMultiplicity();
525     new (fSPDMult) AliMultiplicity();
526   }
527   if(fTOFHeader){
528     fTOFHeader->~AliTOFHeader();
529     new (fTOFHeader) AliTOFHeader();
530     //fTOFHeader->SetName(fgkESDListName[kTOFHeader]);
531   }
532   if (fTrdTrigger) {
533     fTrdTrigger->~AliESDTrdTrigger();
534     new (fTrdTrigger) AliESDTrdTrigger();
535   }
536         
537   if(fPHOSTrigger)fPHOSTrigger->DeAllocate(); 
538   if(fEMCALTrigger)fEMCALTrigger->DeAllocate(); 
539   if(fSPDPileupVertices)fSPDPileupVertices->Delete();
540   if(fTrkPileupVertices)fTrkPileupVertices->Delete();
541   fTracksConnected = kFALSE;
542   if(fTracks)fTracks->Delete();
543   if(fMuonTracks)fMuonTracks->Clear("C");
544   if(fMuonClusters)fMuonClusters->Clear("C");
545   if(fMuonPads)fMuonPads->Clear("C");
546   if(fMuonGlobalTracks)fMuonGlobalTracks->Clear("C");     // AU
547   if(fPmdTracks)fPmdTracks->Delete();
548   if(fTrdTracks)fTrdTracks->Delete();
549   if(fTrdTracklets)fTrdTracklets->Delete();
550   if(fV0s)fV0s->Delete();
551   if(fCascades)fCascades->Delete();
552   if(fKinks)fKinks->Delete();
553   if(fCaloClusters)fCaloClusters->Delete();
554   if(fPHOSCells)fPHOSCells->DeleteContainer();
555   if(fEMCALCells)fEMCALCells->DeleteContainer();
556   if(fCosmicTracks)fCosmicTracks->Delete();
557   if(fESDTOFClusters)fESDTOFClusters->Clear();
558   if(fESDTOFHits)fESDTOFHits->Clear();
559   if(fESDTOFMatchess)fESDTOFMatchess->Clear();
560   if(fErrorLogs) fErrorLogs->Delete();
561
562   // don't reset fconnected fConnected and the list
563
564 }
565
566
567 //______________________________________________________________________________
568 Int_t AliESDEvent::AddV0(const AliESDv0 *v) {
569   //
570   // Add V0
571   //
572   TClonesArray &fv = *fV0s;
573   Int_t idx=fV0s->GetEntriesFast();
574   new(fv[idx]) AliESDv0(*v);
575   return idx;
576 }  
577
578 //______________________________________________________________________________
579 Bool_t AliESDEvent::IsDetectorInTriggerCluster(TString detector, AliTriggerConfiguration* trigConf) const {
580   // Check if a given detector was read-out in the analyzed event
581   const TObjArray& classesArray=trigConf->GetClasses();
582   ULong64_t trigMask=GetTriggerMask();
583   Int_t nclasses = classesArray.GetEntriesFast();
584   for(Int_t iclass=0; iclass < nclasses; iclass++ ) {
585     AliTriggerClass* trclass = (AliTriggerClass*)classesArray.At(iclass);
586     Int_t classMask=trclass->GetMask();
587     if(trigMask & classMask){
588       TString detList=trclass->GetCluster()->GetDetectorsInCluster();
589       if(detList.Contains(detector.Data())){
590         return kTRUE;
591       }
592     }
593   }
594   return kFALSE; 
595 }
596 //______________________________________________________________________________
597 void AliESDEvent::Print(Option_t *) const 
598 {
599   //
600   // Print header information of the event
601   //
602   printf("ESD run information\n");
603   printf("Event # in file %d Bunch crossing # %d Orbit # %d Period # %d Run # %d Trigger %lld Magnetic field %f \n",
604          GetEventNumberInFile(),
605          GetBunchCrossNumber(),
606          GetOrbitNumber(),
607          GetPeriodNumber(),
608          GetRunNumber(),
609          GetTriggerMask(),
610          GetMagneticField() );
611   if (fPrimaryVertex)
612     printf("Vertex: (%.4f +- %.4f, %.4f +- %.4f, %.4f +- %.4f) cm\n",
613            fPrimaryVertex->GetXv(), fPrimaryVertex->GetXRes(),
614            fPrimaryVertex->GetYv(), fPrimaryVertex->GetYRes(),
615            fPrimaryVertex->GetZv(), fPrimaryVertex->GetZRes());
616   printf("Mean vertex in RUN: X=%.4f Y=%.4f Z=%.4f cm\n",
617          GetDiamondX(),GetDiamondY(),GetDiamondZ());
618   if(fSPDMult)
619     printf("SPD Multiplicity. Number of tracklets %d \n",
620            fSPDMult->GetNumberOfTracklets());
621   printf("Number of pileup primary vertices reconstructed with SPD %d\n", 
622          GetNumberOfPileupVerticesSPD());
623   printf("Number of pileup primary vertices reconstructed using the tracks %d\n",
624          GetNumberOfPileupVerticesTracks());
625   printf("Number of tracks: \n");
626   printf("                 charged   %d\n", GetNumberOfTracks());
627   printf("                 muon      %d\n", GetNumberOfMuonTracks());
628   printf("                 glob muon %d\n", GetNumberOfMuonGlobalTracks());    // AU
629   printf("                 pmd       %d\n", GetNumberOfPmdTracks());
630   printf("                 trd       %d\n", GetNumberOfTrdTracks());
631   printf("                 trd trkl  %d\n", GetNumberOfTrdTracklets());
632   printf("                 v0        %d\n", GetNumberOfV0s());
633   printf("                 cascades  %d\n", GetNumberOfCascades());
634   printf("                 kinks     %d\n", GetNumberOfKinks());
635   if(fPHOSCells)printf("                 PHOSCells %d\n", fPHOSCells->GetNumberOfCells());
636   else printf("                 PHOSCells not in the Event\n");
637   if(fEMCALCells)printf("                 EMCALCells %d\n", fEMCALCells->GetNumberOfCells());
638   else printf("                 EMCALCells not in the Event\n");
639   printf("                 CaloClusters %d\n", GetNumberOfCaloClusters());
640   printf("                 FMD       %s\n", (fESDFMD ? "yes" : "no"));
641   printf("                 VZERO     %s\n", (fESDVZERO ? "yes" : "no"));
642   printf("                 muClusters %d\n", fMuonClusters ? fMuonClusters->GetEntriesFast() : 0);
643   printf("                 muPad     %d\n", fMuonPads ? fMuonPads->GetEntriesFast() : 0);
644   if (fCosmicTracks) printf("                 Cosmics   %d\n",  GetNumberOfCosmicTracks());
645         
646   TObject* pHLTDecision=GetHLTTriggerDecision();
647   printf("HLT trigger decision: %s\n", pHLTDecision?pHLTDecision->GetOption():"not available");
648   if (pHLTDecision) pHLTDecision->Print("compact");
649
650   return;
651 }
652
653 //______________________________________________________________________________
654 void AliESDEvent::SetESDfriend(const AliESDfriend *ev) const 
655 {
656 //
657 // Attaches the complementary info to the ESD
658 //
659   if (!ev) return;
660
661   // to be sure that we set the tracks also
662   // in case of old esds 
663   // if(fESDOld)CopyFromOldESD();
664
665   Int_t ntrk=ev->GetNumberOfTracks();
666  
667   for (Int_t i=0; i<ntrk; i++) {
668     const AliESDfriendTrack *f=ev->GetTrack(i);
669     if (!f) {AliFatal(Form("NULL pointer for ESD track %d",i));}
670     GetTrack(i)->SetFriendTrack(f);
671   }
672 }
673
674 //______________________________________________________________________________
675 Bool_t  AliESDEvent::RemoveKink(Int_t rm) const 
676 {
677 // ---------------------------------------------------------
678 // Remove a kink candidate and references to it from ESD,
679 // if this candidate does not come from a reconstructed decay
680 // Not yet implemented...
681 // ---------------------------------------------------------
682   Int_t last=GetNumberOfKinks()-1;
683   if ((rm<0)||(rm>last)) return kFALSE;
684
685   return kTRUE;
686 }
687
688 //______________________________________________________________________________
689 Bool_t  AliESDEvent::RemoveV0(Int_t rm) const 
690 {
691 // ---------------------------------------------------------
692 // Remove a V0 candidate and references to it from ESD,
693 // if this candidate does not come from a reconstructed decay
694 // ---------------------------------------------------------
695   Int_t last=GetNumberOfV0s()-1;
696   if ((rm<0)||(rm>last)) return kFALSE;
697
698   AliESDv0 *v0=GetV0(rm);
699   Int_t idxP=v0->GetPindex(), idxN=v0->GetNindex();
700
701   v0=GetV0(last);
702   Int_t lastIdxP=v0->GetPindex(), lastIdxN=v0->GetNindex();
703
704   Int_t used=0;
705
706   // Check if this V0 comes from a reconstructed decay
707   Int_t ncs=GetNumberOfCascades();
708   for (Int_t n=0; n<ncs; n++) {
709     AliESDcascade *cs=GetCascade(n);
710
711     Int_t csIdxP=cs->GetPindex();
712     Int_t csIdxN=cs->GetNindex();
713
714     if (idxP==csIdxP)
715        if (idxN==csIdxN) return kFALSE;
716
717     if (csIdxP==lastIdxP)
718        if (csIdxN==lastIdxN) used++;
719   }
720
721   //Replace the removed V0 with the last V0 
722   TClonesArray &a=*fV0s;
723   delete a.RemoveAt(rm);
724
725   if (rm==last) return kTRUE;
726
727   //v0 is pointing to the last V0 candidate... 
728   new (a[rm]) AliESDv0(*v0);
729   delete a.RemoveAt(last);
730
731   if (!used) return kTRUE;
732   
733
734   // Remap the indices of the daughters of reconstructed decays
735   for (Int_t n=0; n<ncs; n++) {
736     AliESDcascade *cs=GetCascade(n);
737
738
739     Int_t csIdxP=cs->GetPindex();
740     Int_t csIdxN=cs->GetNindex();
741
742     if (csIdxP==lastIdxP)
743       if (csIdxN==lastIdxN) {
744          cs->AliESDv0::SetIndex(1,idxP);
745          cs->AliESDv0::SetIndex(0,idxN);
746          used--;
747          if (!used) return kTRUE;
748       }
749   }
750
751   return kTRUE;
752 }
753
754 //______________________________________________________________________________
755 Bool_t  AliESDEvent::RemoveTrack(Int_t rm) const 
756 {
757 // ---------------------------------------------------------
758 // Remove a track and references to it from ESD,
759 // if this track does not come from a reconstructed decay
760 // ---------------------------------------------------------
761   Int_t last=GetNumberOfTracks()-1;
762   if ((rm<0)||(rm>last)) return kFALSE;
763
764   Int_t used=0;
765
766   // Check if this track comes from the reconstructed primary vertices
767   if (fTPCVertex && fTPCVertex->GetStatus()) {
768      UShort_t *primIdx=fTPCVertex->GetIndices();
769      Int_t n=fTPCVertex->GetNIndices();
770      while (n--) {
771        Int_t idx=Int_t(primIdx[n]);
772        if (rm==idx) return kFALSE;
773        if (idx==last) used++; 
774      }
775   }
776   if (fPrimaryVertex && fPrimaryVertex->GetStatus()) {
777      UShort_t *primIdx=fPrimaryVertex->GetIndices();
778      Int_t n=fPrimaryVertex->GetNIndices();
779      while (n--) {
780        Int_t idx=Int_t(primIdx[n]);
781        if (rm==idx) return kFALSE;
782        if (idx==last) used++; 
783      }
784   }
785   
786   // Check if this track comes from a reconstructed decay
787   Int_t nv0=GetNumberOfV0s();
788   for (Int_t n=0; n<nv0; n++) {
789     AliESDv0 *v0=GetV0(n);
790
791     Int_t idx=v0->GetNindex();
792     if (rm==idx) return kFALSE;
793     if (idx==last) used++;
794
795     idx=v0->GetPindex();
796     if (rm==idx) return kFALSE;
797     if (idx==last) used++;
798   }
799
800   Int_t ncs=GetNumberOfCascades();
801   for (Int_t n=0; n<ncs; n++) {
802     AliESDcascade *cs=GetCascade(n);
803
804     Int_t idx=cs->GetIndex();
805     if (rm==idx) return kFALSE;
806     if (idx==last) used++;
807
808     AliESDv0 *v0=cs;
809     idx=v0->GetNindex();
810     if (rm==idx) return kFALSE;
811     if (idx==last) used++;
812
813     idx=v0->GetPindex();
814     if (rm==idx) return kFALSE;
815     if (idx==last) used++;
816   }
817
818   Int_t nkn=GetNumberOfKinks();
819   for (Int_t n=0; n<nkn; n++) {
820     AliESDkink *kn=GetKink(n);
821
822     Int_t idx=kn->GetIndex(0);
823     if (rm==idx) return kFALSE;
824     if (idx==last) used++;
825
826     idx=kn->GetIndex(1);
827     if (rm==idx) return kFALSE;
828     if (idx==last) used++;
829   }
830
831   // Check if this track is associated with a CaloCluster
832   Int_t ncl=GetNumberOfCaloClusters();
833   for (Int_t n=0; n<ncl; n++) {
834     AliESDCaloCluster *cluster=GetCaloCluster(n);
835     TArrayI *arr=cluster->GetTracksMatched();
836     Int_t s=arr->GetSize();
837     while (s--) {
838       Int_t idx=arr->At(s);
839       if (rm==idx) return kFALSE;
840       if (idx==last) used++;     
841     }
842   }
843
844   // from here on we remove the track
845   //
846   //Replace the removed track with the last track 
847   TClonesArray &a=*fTracks;
848   AliESDtrack* trm = GetTrack(rm);
849   trm->SuppressTOFMatches(); // remove reference to this track from stored TOF clusters
850   delete a.RemoveAt(rm);
851   //
852   if (rm==last) return kTRUE;
853
854   AliESDtrack *t=GetTrack(last);
855   if (!t) {AliFatal(Form("NULL pointer for ESD track %d",last));}
856   t->SetID(rm);
857   new (a[rm]) AliESDtrack(*t);
858   delete a.RemoveAt(last);
859
860   if (!used) return kTRUE;
861   
862
863   // Remap the indices of the tracks used for the primary vertex reconstruction
864   if (fTPCVertex && fTPCVertex->GetStatus()) {
865      UShort_t *primIdx=fTPCVertex->GetIndices();
866      Int_t n=fTPCVertex->GetNIndices();
867      while (n--) {
868        Int_t idx=Int_t(primIdx[n]);
869        if (idx==last) {
870           primIdx[n]=Short_t(rm); 
871           used--;
872           if (!used) return kTRUE;
873        }
874      }
875   }  
876   if (fPrimaryVertex && fPrimaryVertex->GetStatus()) {
877      UShort_t *primIdx=fPrimaryVertex->GetIndices();
878      Int_t n=fPrimaryVertex->GetNIndices();
879      while (n--) {
880        Int_t idx=Int_t(primIdx[n]);
881        if (idx==last) {
882           primIdx[n]=Short_t(rm); 
883           used--;
884           if (!used) return kTRUE;
885        }
886      }
887   }  
888
889   // Remap the indices of the daughters of reconstructed decays
890   for (Int_t n=0; n<nv0; n++) {
891     AliESDv0 *v0=GetV0(n);
892     if (v0->GetIndex(0)==last) {
893        v0->SetIndex(0,rm);
894        used--;
895        if (!used) return kTRUE;
896     }
897     if (v0->GetIndex(1)==last) {
898        v0->SetIndex(1,rm);
899        used--;
900        if (!used) return kTRUE;
901     }
902   }
903
904   for (Int_t n=0; n<ncs; n++) {
905     AliESDcascade *cs=GetCascade(n);
906     if (cs->GetIndex()==last) {
907        cs->SetIndex(rm);
908        used--;
909        if (!used) return kTRUE;
910     }
911     AliESDv0 *v0=cs;
912     if (v0->GetIndex(0)==last) {
913        v0->SetIndex(0,rm);
914        used--;
915        if (!used) return kTRUE;
916     }
917     if (v0->GetIndex(1)==last) {
918        v0->SetIndex(1,rm);
919        used--;
920        if (!used) return kTRUE;
921     }
922   }
923
924   for (Int_t n=0; n<nkn; n++) {
925     AliESDkink *kn=GetKink(n);
926     if (kn->GetIndex(0)==last) {
927        kn->SetIndex(rm,0);
928        used--;
929        if (!used) return kTRUE;
930     }
931     if (kn->GetIndex(1)==last) {
932        kn->SetIndex(rm,1);
933        used--;
934        if (!used) return kTRUE;
935     }
936   }
937
938   // Remap the indices of the tracks accosicated with CaloClusters
939   for (Int_t n=0; n<ncl; n++) {
940     AliESDCaloCluster *cluster=GetCaloCluster(n);
941     TArrayI *arr=cluster->GetTracksMatched();
942     Int_t s=arr->GetSize();
943     while (s--) {
944       Int_t idx=arr->At(s);
945       if (idx==last) {
946          arr->AddAt(rm,s);
947          used--; 
948          if (!used) return kTRUE;
949       }
950     }
951   }
952
953   return kTRUE;
954 }
955
956 //______________________________________________________________________________
957 Bool_t AliESDEvent::Clean(Float_t *cleanPars) 
958 {
959   //
960   // Remove the data which are not needed for the physics analysis.
961   //
962   // 1) Cleaning the V0 candidates
963   //    ---------------------------
964   //    If the cosine of the V0 pointing angle "csp" and 
965   //    the DCA between the daughter tracks "dca" does not satisfy 
966   //    the conditions 
967   //
968   //     csp > cleanPars[1] + dca/cleanPars[0]*(1.- cleanPars[1])
969   //
970   //    an attempt to remove this V0 candidate from ESD is made.
971   //
972   //    The V0 candidate gets removed if it does not belong to any 
973   //    recosntructed cascade decay
974   //
975   //    12.11.2007, optimal values: cleanPars[0]=0.5, cleanPars[1]=0.999
976   //
977   // 2) Cleaning the tracks
978   //    ----------------------
979   //    If track's transverse parameter is larger than cleanPars[2]
980   //                       OR
981   //    track's longitudinal parameter is larger than cleanPars[3]
982   //    an attempt to remove this track from ESD is made.
983   //
984   //    The track gets removed if it does not come 
985   //    from a reconstructed decay
986   //
987   Bool_t rc=kFALSE;
988
989   Float_t dcaMax=cleanPars[0];
990   Float_t cspMin=cleanPars[1];
991
992   Int_t nV0s=GetNumberOfV0s();
993   for (Int_t i=nV0s-1; i>=0; i--) {
994     AliESDv0 *v0=GetV0(i);
995
996     Float_t dca=v0->GetDcaV0Daughters();
997     Float_t csp=v0->GetV0CosineOfPointingAngle();
998     Float_t cspcut=cspMin + dca/dcaMax*(1.-cspMin);
999     if (csp > cspcut) continue;
1000     if (RemoveV0(i)) rc=kTRUE;
1001   }
1002
1003
1004   Float_t dmax=cleanPars[2], zmax=cleanPars[3];
1005
1006   const AliESDVertex *vertex=GetPrimaryVertexSPD();
1007   Bool_t vtxOK=vertex->GetStatus();
1008   
1009   Int_t nTracks=GetNumberOfTracks();
1010   for (Int_t i=nTracks-1; i>=0; i--) {
1011     AliESDtrack *track=GetTrack(i);
1012     if (!track) {AliFatal(Form("NULL pointer for ESD track %d",i));}
1013     Float_t xy,z; track->GetImpactParameters(xy,z);
1014     if ((TMath::Abs(xy) > dmax) || (vtxOK && (TMath::Abs(z) > zmax))) {
1015       if (RemoveTrack(i)) rc=kTRUE;
1016     }
1017   }
1018
1019   return rc;
1020 }
1021
1022 //______________________________________________________________________________
1023 Char_t  AliESDEvent::AddPileupVertexSPD(const AliESDVertex *vtx) 
1024 {
1025     // Add a pileup primary vertex reconstructed with SPD
1026     TClonesArray &ftr = *fSPDPileupVertices;
1027     Char_t n=Char_t(ftr.GetEntriesFast());
1028     AliESDVertex *vertex = new(ftr[n]) AliESDVertex(*vtx);
1029     vertex->SetID(n);
1030     return n;
1031 }
1032
1033 //______________________________________________________________________________
1034 Char_t  AliESDEvent::AddPileupVertexTracks(const AliESDVertex *vtx) 
1035 {
1036     // Add a pileup primary vertex reconstructed with SPD
1037     TClonesArray &ftr = *fTrkPileupVertices;
1038     Char_t n=Char_t(ftr.GetEntriesFast());
1039     AliESDVertex *vertex = new(ftr[n]) AliESDVertex(*vtx);
1040     vertex->SetID(n);
1041     return n;
1042 }
1043
1044 //______________________________________________________________________________
1045 Int_t  AliESDEvent::AddTrack(const AliESDtrack *t) 
1046 {
1047     // Add track
1048     TClonesArray &ftr = *fTracks;
1049     AliESDtrack * track = new(ftr[fTracks->GetEntriesFast()])AliESDtrack(*t);
1050     track->SetID(fTracks->GetEntriesFast()-1);
1051     track->SetESDEvent(this);
1052     return  track->GetID();    
1053 }
1054
1055 //______________________________________________________________________________
1056 AliESDtrack*  AliESDEvent::NewTrack() 
1057 {
1058     // Add a new track
1059     TClonesArray &ftr = *fTracks;
1060     AliESDtrack * track = new(ftr[fTracks->GetEntriesFast()])AliESDtrack();
1061     track->SetID(fTracks->GetEntriesFast()-1);
1062     track->SetESDEvent(this);
1063     return  track;
1064 }
1065
1066 //______________________________________________________________________________
1067 Bool_t AliESDEvent::MoveMuonObjects() 
1068 {
1069   // move MUON clusters and pads to the new ESD structure in needed.
1070   // to ensure backward compatibility
1071   
1072   if (!fOldMuonStructure) return kTRUE;
1073   
1074   if (!fMuonTracks || !fMuonClusters || !fMuonPads) return kFALSE;
1075   
1076   Bool_t reset = kTRUE;
1077   Bool_t containTrackerData = kFALSE;
1078   for (Int_t i = 0; i < fMuonTracks->GetEntriesFast(); i++) {
1079     
1080     AliESDMuonTrack *track = (AliESDMuonTrack*) fMuonTracks->UncheckedAt(i);
1081     
1082     if (track->ContainTrackerData()) containTrackerData = kTRUE;
1083     else continue;
1084     
1085     if (!track->IsOldTrack()) continue;
1086     
1087     // remove objects connected to previous event if needed
1088     if (reset) {
1089       if (fMuonClusters->GetEntriesFast() > 0) fMuonClusters->Clear("C");
1090       if (fMuonPads->GetEntriesFast() > 0) fMuonPads->Clear("C");
1091       reset = kFALSE;
1092     }
1093     
1094     track->MoveClustersToESD(*this);
1095     
1096   }
1097   
1098   // remove objects connected to previous event if needed
1099   if (!containTrackerData) {
1100     if (fMuonClusters->GetEntriesFast() > 0) fMuonClusters->Clear("C");
1101     if (fMuonPads->GetEntriesFast() > 0) fMuonPads->Clear("C");
1102   }
1103   
1104   return kTRUE;
1105 }
1106
1107 //______________________________________________________________________________
1108 AliESDMuonTrack* AliESDEvent::GetMuonTrack(Int_t i)
1109 {
1110   // get the MUON track at the position i in the internal array of track
1111   if (!fMuonTracks) return 0x0;
1112   if (!MoveMuonObjects()) return 0x0;
1113   AliESDMuonTrack *track = (AliESDMuonTrack*) fMuonTracks->UncheckedAt(i);
1114   track->SetESDEvent(this);
1115   return track;
1116 }
1117
1118 //______________________________________________________________________________
1119 AliESDMuonGlobalTrack* AliESDEvent::GetMuonGlobalTrack(Int_t i)                      // AU
1120 {
1121   // get the MUON+MFT track at the position i in the internal array of track
1122   if (!fMuonGlobalTracks) return 0x0;
1123   AliESDMuonGlobalTrack *track = (AliESDMuonGlobalTrack*) fMuonGlobalTracks->UncheckedAt(i);
1124   track->SetESDEvent(this);
1125   return track;
1126 }
1127
1128 //______________________________________________________________________________
1129 void AliESDEvent::AddMuonTrack(const AliESDMuonTrack *t) 
1130 {
1131   // add a MUON track
1132   TClonesArray &fmu = *fMuonTracks;
1133   AliESDMuonTrack *track = new(fmu[fMuonTracks->GetEntriesFast()]) AliESDMuonTrack(*t);
1134   track->MoveClustersToESD(*this);
1135 }
1136
1137 //______________________________________________________________________________
1138 void AliESDEvent::AddMuonGlobalTrack(const AliESDMuonGlobalTrack *t)                             // AU
1139 {
1140   // add a MUON+MFT track
1141   TClonesArray &fmu = *fMuonGlobalTracks;
1142   new (fmu[fMuonGlobalTracks->GetEntriesFast()]) AliESDMuonGlobalTrack(*t);
1143 }
1144
1145 //______________________________________________________________________________
1146
1147 AliESDMuonTrack* AliESDEvent::NewMuonTrack() 
1148 {
1149   // create a new MUON track at the end of the internal array of track
1150   TClonesArray &fmu = *fMuonTracks;
1151   return new(fmu[fMuonTracks->GetEntriesFast()]) AliESDMuonTrack();
1152 }
1153
1154 //______________________________________________________________________________
1155 AliESDMuonGlobalTrack* AliESDEvent::NewMuonGlobalTrack()                                         // AU
1156 {
1157   // create a new MUON+MFT track at the end of the internal array of track
1158   TClonesArray &fmu = *fMuonGlobalTracks;
1159   return new(fmu[fMuonGlobalTracks->GetEntriesFast()]) AliESDMuonGlobalTrack();
1160 }
1161
1162 //______________________________________________________________________________
1163 Int_t AliESDEvent::GetNumberOfMuonClusters()
1164 {
1165   // get the number of MUON clusters
1166   if (!fMuonClusters) return 0;
1167   if (!MoveMuonObjects()) return 0;
1168   return fMuonClusters->GetEntriesFast();
1169 }
1170
1171 //______________________________________________________________________________
1172 AliESDMuonCluster* AliESDEvent::GetMuonCluster(Int_t i)
1173 {
1174   // get the MUON cluster at the position i in the internal array of cluster
1175   if (!fMuonClusters) return 0x0;
1176   if (!MoveMuonObjects()) return 0x0;
1177   return (AliESDMuonCluster*) fMuonClusters->UncheckedAt(i);
1178 }
1179
1180 //______________________________________________________________________________
1181 AliESDMuonCluster* AliESDEvent::FindMuonCluster(UInt_t clusterId)
1182 {
1183   // find the MUON cluster with this Id in the internal array of cluster
1184   if (!fMuonClusters) return 0x0;
1185   if (!MoveMuonObjects()) return 0x0;
1186   for (Int_t i = 0; i < fMuonClusters->GetEntriesFast(); i++) {
1187     AliESDMuonCluster *cluster = (AliESDMuonCluster*) fMuonClusters->UncheckedAt(i);
1188     if (cluster->GetUniqueID() == clusterId) return cluster;
1189   }
1190   return 0x0;
1191 }
1192
1193 //______________________________________________________________________________
1194 AliESDMuonCluster* AliESDEvent::NewMuonCluster() 
1195 {
1196   // create a new MUON cluster at the end of the internal array of cluster
1197   TClonesArray &fmu = *fMuonClusters;
1198   return new(fmu[fMuonClusters->GetEntriesFast()]) AliESDMuonCluster();
1199 }
1200
1201 //______________________________________________________________________________
1202 Int_t AliESDEvent::GetNumberOfMuonPads()
1203 {
1204   // get the number of MUON pads
1205   if (!fMuonPads) return 0;
1206   if (!MoveMuonObjects()) return 0;
1207   return fMuonPads->GetEntriesFast();
1208 }
1209
1210 //______________________________________________________________________________
1211 AliESDMuonPad* AliESDEvent::GetMuonPad(Int_t i)
1212 {
1213   // get the MUON pad at the position i in the internal array of pad
1214   if (!fMuonPads) return 0x0;
1215   if (!MoveMuonObjects()) return 0x0;
1216   return (AliESDMuonPad*) fMuonPads->UncheckedAt(i);
1217 }
1218
1219 //______________________________________________________________________________
1220 AliESDMuonPad* AliESDEvent::FindMuonPad(UInt_t padId)
1221 {
1222   // find the MUON pad with this Id in the internal array of pad
1223   if (!fMuonPads) return 0x0;
1224   if (!MoveMuonObjects()) return 0x0;
1225   for (Int_t i = 0; i < fMuonPads->GetEntriesFast(); i++) {
1226     AliESDMuonPad *pad = (AliESDMuonPad*) fMuonPads->UncheckedAt(i);
1227     if (pad->GetUniqueID() == padId) return pad;
1228   }
1229   return 0x0;
1230 }
1231
1232 //______________________________________________________________________________
1233 AliESDMuonPad* AliESDEvent::NewMuonPad() 
1234 {
1235   // create a new MUON pad at the end of the internal array of pad
1236   TClonesArray &fmu = *fMuonPads;
1237   return new(fmu[fMuonPads->GetEntriesFast()]) AliESDMuonPad();
1238 }
1239
1240 //______________________________________________________________________________
1241 void AliESDEvent::AddPmdTrack(const AliESDPmdTrack *t) 
1242 {
1243   TClonesArray &fpmd = *fPmdTracks;
1244   new(fpmd[fPmdTracks->GetEntriesFast()]) AliESDPmdTrack(*t);
1245 }
1246
1247 //______________________________________________________________________________
1248 void AliESDEvent::SetTrdTrigger(const AliESDTrdTrigger *t)
1249 {
1250   *fTrdTrigger = *t;
1251 }
1252
1253 //______________________________________________________________________________
1254 void AliESDEvent::AddTrdTrack(const AliESDTrdTrack *t) 
1255 {
1256   TClonesArray &ftrd = *fTrdTracks;
1257   new(ftrd[fTrdTracks->GetEntriesFast()]) AliESDTrdTrack(*t);
1258 }
1259
1260 //______________________________________________________________________________
1261 void AliESDEvent::AddTrdTracklet(const AliESDTrdTracklet *trkl)
1262 {
1263   new ((*fTrdTracklets)[fTrdTracklets->GetEntriesFast()]) AliESDTrdTracklet(*trkl);
1264 }
1265
1266 //______________________________________________________________________________
1267 void AliESDEvent::AddTrdTracklet(UInt_t trackletWord, Short_t hcid, Int_t label)
1268 {
1269   new ((*fTrdTracklets)[fTrdTracklets->GetEntriesFast()]) AliESDTrdTracklet(trackletWord, hcid, label);
1270 }
1271
1272 //______________________________________________________________________________
1273 Int_t AliESDEvent::AddKink(const AliESDkink *c) 
1274 {
1275   // Add kink
1276   TClonesArray &fk = *fKinks;
1277   AliESDkink * kink = new(fk[fKinks->GetEntriesFast()]) AliESDkink(*c);
1278   kink->SetID(fKinks->GetEntriesFast()); // CKB different from the other imps..
1279   return fKinks->GetEntriesFast()-1;
1280 }
1281
1282
1283 //______________________________________________________________________________
1284 void AliESDEvent::AddCascade(const AliESDcascade *c) 
1285 {
1286   TClonesArray &fc = *fCascades;
1287   new(fc[fCascades->GetEntriesFast()]) AliESDcascade(*c);
1288 }
1289
1290 //______________________________________________________________________________
1291 void AliESDEvent::AddCosmicTrack(const AliESDCosmicTrack *t) 
1292 {
1293   TClonesArray &ft = *fCosmicTracks;
1294   new(ft[fCosmicTracks->GetEntriesFast()]) AliESDCosmicTrack(*t);
1295
1296
1297
1298 //______________________________________________________________________________
1299 Int_t AliESDEvent::AddCaloCluster(const AliESDCaloCluster *c) 
1300 {
1301   // Add calocluster
1302   TClonesArray &fc = *fCaloClusters;
1303   AliESDCaloCluster *clus = new(fc[fCaloClusters->GetEntriesFast()]) AliESDCaloCluster(*c);
1304   clus->SetID(fCaloClusters->GetEntriesFast()-1);
1305   return fCaloClusters->GetEntriesFast()-1;
1306 }
1307
1308
1309 //______________________________________________________________________________
1310 void  AliESDEvent::AddRawDataErrorLog(const AliRawDataErrorLog *log) const {
1311   TClonesArray &errlogs = *fErrorLogs;
1312   new(errlogs[errlogs.GetEntriesFast()])  AliRawDataErrorLog(*log);
1313 }
1314
1315 //______________________________________________________________________________
1316 void AliESDEvent::SetZDCData(const AliESDZDC * obj)
1317
1318   // use already allocated space
1319   if(fESDZDC)
1320     *fESDZDC = *obj;
1321 }
1322
1323 //______________________________________________________________________________
1324 void  AliESDEvent::SetPrimaryVertexTPC(const AliESDVertex *vertex) 
1325 {
1326   // Set the TPC vertex
1327   // use already allocated space
1328   if(fTPCVertex){
1329     *fTPCVertex = *vertex;
1330     fTPCVertex->SetName(fgkESDListName[kTPCVertex]);
1331   }
1332 }
1333
1334 //______________________________________________________________________________
1335 void  AliESDEvent::SetPrimaryVertexSPD(const AliESDVertex *vertex) 
1336 {
1337   // Set the SPD vertex
1338   // use already allocated space
1339   if(fSPDVertex){
1340     *fSPDVertex = *vertex;
1341     fSPDVertex->SetName(fgkESDListName[kSPDVertex]);
1342   }
1343 }
1344
1345 //______________________________________________________________________________
1346 void  AliESDEvent::SetPrimaryVertexTracks(const AliESDVertex *vertex) 
1347 {
1348   // Set the primary vertex reconstructed using he ESD tracks.
1349   // use already allocated space
1350   if(fPrimaryVertex){
1351     *fPrimaryVertex = *vertex;
1352     fPrimaryVertex->SetName(fgkESDListName[kPrimaryVertex]);
1353   }
1354 }
1355
1356 //______________________________________________________________________________
1357 const AliESDVertex * AliESDEvent::GetPrimaryVertex() const 
1358 {
1359   //
1360   // Get the "best" available reconstructed primary vertex.
1361   //
1362   if(fPrimaryVertex){
1363     if (fPrimaryVertex->GetStatus()) return fPrimaryVertex;
1364   }
1365   if(fSPDVertex){
1366     if (fSPDVertex->GetStatus()) return fSPDVertex;
1367   }
1368   if(fTPCVertex) return fTPCVertex;
1369   
1370   AliWarning("No primary vertex available. Returning the \"default\"...");
1371   return fSPDVertex;
1372 }
1373
1374 //______________________________________________________________________________
1375 AliESDVertex * AliESDEvent::PrimaryVertexTracksUnconstrained() const 
1376 {
1377   //
1378   // Removes diamond constraint from fPrimaryVertex (reconstructed with tracks)
1379   // Returns a AliESDVertex which has to be deleted by the user
1380   //
1381   if(!fPrimaryVertex) {
1382     AliWarning("No primary vertex from tracks available.");
1383     return 0;
1384   }
1385   if(!fPrimaryVertex->GetStatus()) {
1386     AliWarning("No primary vertex from tracks available.");
1387     return 0;
1388   }
1389
1390   AliVertexerTracks vertexer(GetMagneticField());
1391   Float_t diamondxyz[3]={(Float_t)GetDiamondX(),(Float_t)GetDiamondY(),0.};
1392   Float_t diamondcovxy[3]; GetDiamondCovXY(diamondcovxy);
1393   Float_t diamondcov[6]={diamondcovxy[0],diamondcovxy[1],diamondcovxy[2],0.,0.,7.};
1394   AliESDVertex *vertex = 
1395     (AliESDVertex*)vertexer.RemoveConstraintFromVertex(fPrimaryVertex,diamondxyz,diamondcov);
1396
1397   return vertex;
1398 }
1399
1400 //______________________________________________________________________________
1401 void AliESDEvent::SetMultiplicity(const AliMultiplicity *mul) 
1402 {
1403   // Set the SPD Multiplicity
1404   if(fSPDMult){
1405     *fSPDMult = *mul;
1406   }
1407 }
1408
1409
1410 //______________________________________________________________________________
1411 void AliESDEvent::SetFMDData(AliESDFMD * obj) 
1412
1413   // use already allocated space
1414   if(fESDFMD){
1415     *fESDFMD = *obj;
1416   }
1417 }
1418
1419 //______________________________________________________________________________
1420 void AliESDEvent::SetVZEROData(const AliESDVZERO * obj)
1421
1422   // use already allocated space
1423   if(fESDVZERO)
1424     *fESDVZERO = *obj;
1425 }
1426
1427 //______________________________________________________________________________
1428 void AliESDEvent::SetTZEROData(const AliESDTZERO * obj)
1429
1430   // use already allocated space
1431   if(fESDTZERO)
1432     *fESDTZERO = *obj;
1433 }
1434
1435
1436 //______________________________________________________________________________
1437 void AliESDEvent::SetACORDEData(AliESDACORDE * obj)
1438 {
1439   if(fESDACORDE)
1440     *fESDACORDE = *obj;
1441 }
1442
1443 //______________________________________________________________________________
1444 void AliESDEvent::SetADData(AliESDAD * obj)
1445 {
1446   if(fESDAD)
1447     *fESDAD = *obj;
1448 }
1449
1450 //______________________________________________________________________________
1451 void AliESDEvent::GetESDfriend(AliESDfriend *ev) const 
1452 {
1453   //
1454   // Extracts the complementary info from the ESD
1455   //
1456   if (!ev) return;
1457
1458   Int_t ntrk=GetNumberOfTracks();
1459
1460   for (Int_t i=0; i<ntrk; i++) {
1461     AliESDtrack *t=GetTrack(i);
1462     if (!t) {AliFatal(Form("NULL pointer for ESD track %d",i));}
1463     const AliESDfriendTrack *f=t->GetFriendTrack();
1464     ev->AddTrack(f);
1465
1466     t->ReleaseESDfriendTrack();// Not to have two copies of "friendTrack"
1467
1468   }
1469
1470   AliESDfriend *fr = (AliESDfriend*)(const_cast<AliESDEvent*>(this)->FindFriend());
1471   if (fr) ev->SetVZEROfriend(fr->GetVZEROfriend());
1472 }
1473
1474 //______________________________________________________________________________
1475 void AliESDEvent::AddObject(TObject* obj) 
1476 {
1477   // Add an object to the list of object.
1478   // Please be aware that in order to increase performance you should
1479   // refrain from using TObjArrays (if possible). Use TClonesArrays, instead.
1480   fESDObjects->SetOwner(kTRUE);
1481   fESDObjects->AddLast(obj);
1482 }
1483
1484 //______________________________________________________________________________
1485 void AliESDEvent::GetStdContent() 
1486 {
1487   // set pointers for standard content
1488   // get by name much safer and not a big overhead since not called very often
1489  
1490   fESDRun = (AliESDRun*)fESDObjects->FindObject(fgkESDListName[kESDRun]);
1491   fHeader = (AliESDHeader*)fESDObjects->FindObject(fgkESDListName[kHeader]);
1492   fESDZDC = (AliESDZDC*)fESDObjects->FindObject(fgkESDListName[kESDZDC]);
1493   fESDFMD = (AliESDFMD*)fESDObjects->FindObject(fgkESDListName[kESDFMD]);
1494   fESDVZERO = (AliESDVZERO*)fESDObjects->FindObject(fgkESDListName[kESDVZERO]);
1495   fESDTZERO = (AliESDTZERO*)fESDObjects->FindObject(fgkESDListName[kESDTZERO]);
1496   fTPCVertex = (AliESDVertex*)fESDObjects->FindObject(fgkESDListName[kTPCVertex]);
1497   fSPDVertex = (AliESDVertex*)fESDObjects->FindObject(fgkESDListName[kSPDVertex]);
1498   fPrimaryVertex = (AliESDVertex*)fESDObjects->FindObject(fgkESDListName[kPrimaryVertex]);
1499   fSPDMult =       (AliMultiplicity*)fESDObjects->FindObject(fgkESDListName[kSPDMult]);
1500   fPHOSTrigger = (AliESDCaloTrigger*)fESDObjects->FindObject(fgkESDListName[kPHOSTrigger]);
1501   fEMCALTrigger = (AliESDCaloTrigger*)fESDObjects->FindObject(fgkESDListName[kEMCALTrigger]);
1502   fSPDPileupVertices = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kSPDPileupVertices]);
1503   fTrkPileupVertices = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kTrkPileupVertices]);
1504   fTracks = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kTracks]);
1505   fMuonTracks = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kMuonTracks]);
1506   fMuonClusters = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kMuonClusters]);
1507   fMuonPads = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kMuonPads]);
1508   fMuonGlobalTracks = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kMuonGlobalTracks]);         // AU
1509   fPmdTracks = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kPmdTracks]);
1510   fTrdTrigger = (AliESDTrdTrigger*)fESDObjects->FindObject(fgkESDListName[kTrdTrigger]);
1511   fTrdTracks = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kTrdTracks]);
1512   fTrdTracklets = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kTrdTracklets]);
1513   fV0s = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kV0s]);
1514   fCascades = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kCascades]);
1515   fKinks = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kKinks]);
1516   fCaloClusters = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kCaloClusters]);
1517   fEMCALCells = (AliESDCaloCells*)fESDObjects->FindObject(fgkESDListName[kEMCALCells]);
1518   fPHOSCells = (AliESDCaloCells*)fESDObjects->FindObject(fgkESDListName[kPHOSCells]);
1519   fErrorLogs = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kErrorLogs]);
1520   fESDACORDE = (AliESDACORDE*)fESDObjects->FindObject(fgkESDListName[kESDACORDE]);
1521   fESDAD = (AliESDAD*)fESDObjects->FindObject(fgkESDListName[kESDAD]);
1522   fTOFHeader = (AliTOFHeader*)fESDObjects->FindObject(fgkESDListName[kTOFHeader]);
1523   fCosmicTracks = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kCosmicTracks]);
1524   fESDTOFClusters = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kTOFclusters]);
1525   fESDTOFHits = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kTOFhit]);
1526   fESDTOFMatchess = (TClonesArray*)fESDObjects->FindObject(fgkESDListName[kTOFmatch]);
1527 }
1528
1529 //______________________________________________________________________________
1530 void AliESDEvent::SetStdNames(){
1531   // Set the names of the standard contents
1532   // 
1533   if(fESDObjects->GetEntries()>=kESDListN){
1534     for(int i = 0;i < fESDObjects->GetEntries() && i<kESDListN;i++){
1535       TObject *fObj = fESDObjects->At(i);
1536       if(fObj->InheritsFrom("TNamed")){
1537         ((TNamed*)fObj)->SetName(fgkESDListName[i]);
1538       }
1539       else if(fObj->InheritsFrom("TClonesArray")){
1540         ((TClonesArray*)fObj)->SetName(fgkESDListName[i]);
1541       }
1542     }
1543   }
1544   else{
1545      AliWarning("Std Entries missing");
1546   }
1547
1548
1549 //______________________________________________________________________________
1550 void AliESDEvent::CreateStdContent(Bool_t bUseThisList){
1551   fUseOwnList = bUseThisList;
1552   CreateStdContent();
1553 }
1554
1555 //______________________________________________________________________________
1556 void AliESDEvent::CreateStdContent() 
1557 {
1558   // create the standard AOD content and set pointers
1559
1560   // create standard objects and add them to the TList of objects
1561   AddObject(new AliESDRun());
1562   AddObject(new AliESDHeader());
1563   AddObject(new AliESDZDC());
1564   AddObject(new AliESDFMD());
1565   AddObject(new AliESDVZERO());
1566   AddObject(new AliESDTZERO());
1567   AddObject(new AliESDVertex());
1568   AddObject(new AliESDVertex());
1569   AddObject(new AliESDVertex());
1570   AddObject(new AliMultiplicity());
1571   AddObject(new AliESDCaloTrigger());
1572   AddObject(new AliESDCaloTrigger());
1573   AddObject(new TClonesArray("AliESDVertex",0));
1574   AddObject(new TClonesArray("AliESDVertex",0));
1575   AddObject(new TClonesArray("AliESDtrack",0));
1576   AddObject(new TClonesArray("AliESDMuonTrack",0));
1577   AddObject(new TClonesArray("AliESDMuonCluster",0));
1578   AddObject(new TClonesArray("AliESDMuonPad",0));
1579   AddObject(new TClonesArray("AliESDMuonGlobalTrack",0));   // AU
1580   AddObject(new TClonesArray("AliESDPmdTrack",0));
1581   AddObject(new AliESDTrdTrigger());
1582   AddObject(new TClonesArray("AliESDTrdTrack",0));
1583   AddObject(new TClonesArray("AliESDTrdTracklet",0));
1584   AddObject(new TClonesArray("AliESDv0",0));
1585   AddObject(new TClonesArray("AliESDcascade",0));
1586   AddObject(new TClonesArray("AliESDkink",0));
1587   AddObject(new TClonesArray("AliESDCaloCluster",0));
1588   AddObject(new AliESDCaloCells());
1589   AddObject(new AliESDCaloCells());
1590   AddObject(new TClonesArray("AliRawDataErrorLog",0));
1591   AddObject(new AliESDACORDE()); 
1592   AddObject(new AliESDAD()); 
1593   AddObject(new AliTOFHeader());
1594   AddObject(new TClonesArray("AliESDCosmicTrack",0));
1595   AddObject(new TClonesArray("AliESDTOFCluster",0));
1596   AddObject(new TClonesArray("AliESDTOFHit",0));
1597   AddObject(new TClonesArray("AliESDTOFMatch",0));
1598         
1599   // check the order of the indices against enum...
1600
1601   // set names
1602   SetStdNames();
1603   // read back pointers
1604   GetStdContent();
1605 }
1606
1607 //______________________________________________________________________________
1608 void AliESDEvent::CompleteStdContent() 
1609 {
1610   // Create missing standard objects and add them to the TList of objects
1611   //
1612   // Add cosmic tracks for cases where esd files were created 
1613   // before adding them to the std content
1614   if (!fESDObjects->FindObject(fgkESDListName[kCosmicTracks])) {
1615     TClonesArray* cosmics = new TClonesArray("AliESDCosmicTrack",0);
1616     fESDObjects->AddAt(cosmics, kCosmicTracks);
1617     fESDObjects->SetOwner(kTRUE);
1618   }
1619   // Add new MUON containers if missing (for backward compatibility)
1620   if (!fESDObjects->FindObject(fgkESDListName[kMuonClusters])) {
1621     TClonesArray* muonClusters = new TClonesArray("AliESDMuonCluster",0);
1622     muonClusters->SetName(fgkESDListName[kMuonClusters]);
1623     fESDObjects->AddAt(muonClusters, kMuonClusters);
1624     fESDObjects->SetOwner(kTRUE);
1625   }
1626   if (!fESDObjects->FindObject(fgkESDListName[kMuonPads])) {
1627     TClonesArray* muonPads = new TClonesArray("AliESDMuonPad",0);
1628     muonPads->SetName(fgkESDListName[kMuonPads]);
1629     fESDObjects->AddAt(muonPads, kMuonPads);
1630     fESDObjects->SetOwner(kTRUE);
1631   }
1632 }
1633
1634 //______________________________________________________________________________
1635 TObject* AliESDEvent::FindListObject(const char *name) const {
1636 //
1637 // Find object with name "name" in the list of branches
1638 //
1639   if(fESDObjects){
1640     return fESDObjects->FindObject(name);
1641   }
1642   return 0;
1643
1644
1645 //______________________________________________________________________________
1646 Int_t AliESDEvent::GetPHOSClusters(TRefArray *clusters) const
1647 {
1648   // fills the provided TRefArray with all found phos clusters
1649   
1650   clusters->Clear();
1651   
1652   AliESDCaloCluster *cl = 0;
1653   for (Int_t i = 0; i < GetNumberOfCaloClusters(); i++) {
1654     
1655     if ( (cl = GetCaloCluster(i)) ) {
1656       if (cl->IsPHOS()){
1657         clusters->Add(cl);
1658         AliDebug(1,Form("IsPHOS cluster %d Size: %d \n",i,clusters->GetEntriesFast()));
1659       }
1660     }
1661   }
1662   return clusters->GetEntriesFast();
1663 }
1664
1665 //______________________________________________________________________________
1666 Int_t AliESDEvent::GetEMCALClusters(TRefArray *clusters) const
1667 {
1668   // fills the provided TRefArray with all found emcal clusters
1669
1670   clusters->Clear();
1671
1672   AliESDCaloCluster *cl = 0;
1673   for (Int_t i = 0; i < GetNumberOfCaloClusters(); i++) {
1674
1675     if ( (cl = GetCaloCluster(i)) ) {
1676       if (cl->IsEMCAL()){
1677         clusters->Add(cl);
1678         AliDebug(1,Form("IsEMCAL cluster %d Size: %d \n",i,clusters->GetEntriesFast()));
1679       }
1680     }
1681   }
1682   return clusters->GetEntriesFast();
1683 }
1684
1685 //______________________________________________________________________________
1686 void AliESDEvent::WriteToTree(TTree* tree) const {
1687   // Book the branches as in TTree::Branch(TCollection*)
1688   // but add a "." at the end of top level branches which are
1689   // not a TClonesArray
1690
1691
1692   TString branchname;
1693   TIter next(fESDObjects);
1694   const Int_t kSplitlevel = 99; // default value in TTree::Branch()
1695   const Int_t kBufsize = 32000; // default value in TTree::Branch()
1696   TObject *obj = 0;
1697
1698   while ((obj = next())) {
1699     branchname.Form("%s", obj->GetName());
1700     if(branchname.CompareTo("AliESDfriend")==0)branchname = "ESDfriend.";
1701     if ((kSplitlevel > 1) &&  !obj->InheritsFrom(TClonesArray::Class())) {
1702       if(!branchname.EndsWith("."))branchname += ".";
1703     }
1704     if (!tree->FindBranch(branchname)) {
1705       // For the custom streamer to be called splitlevel
1706       // has to be negative, only needed for HLT
1707       Int_t splitLevel = (TString(obj->ClassName()) == "AliHLTGlobalTriggerDecision") ? -1 : kSplitlevel - 1;
1708       tree->Bronch(branchname, obj->ClassName(), fESDObjects->GetObjectRef(obj),kBufsize, splitLevel);
1709     }
1710   }
1711
1712   tree->Branch("fDetectorStatus",(void*)&fDetectorStatus,"fDetectorStatus/l");
1713   tree->Branch("fDAQDetectorPattern",(void*)&fDAQDetectorPattern,"fDAQDetectorPattern/i");
1714   tree->Branch("fDAQAttributes",(void*)&fDAQAttributes,"fDAQAttributes/i");
1715 }
1716
1717 //______________________________________________________________________________
1718 void AliESDEvent::ReadFromTree(TTree *tree, Option_t* opt){
1719 //
1720 // Connect the ESDEvent to a tree
1721 //
1722   if(!tree){
1723     AliWarning("AliESDEvent::ReadFromTree() Zero Pointer to Tree \n");
1724     return;
1725   }
1726   // load the TTree
1727   if(!tree->GetTree())tree->LoadTree(0);
1728
1729   // if we find the "ESD" branch on the tree we do have the old structure
1730   if(tree->GetBranch("ESD")) {
1731     fOldMuonStructure = kFALSE;
1732     char ** address  = (char **)(tree->GetBranch("ESD")->GetAddress());
1733     // do we have the friend branch
1734     TBranch * esdFB = tree->GetBranch("ESDfriend.");
1735     char ** addressF = 0;
1736     if(esdFB)addressF = (char **)(esdFB->GetAddress());
1737     if (!address) {
1738       AliInfo("AliESDEvent::ReadFromTree() Reading old Tree");
1739       tree->SetBranchAddress("ESD",       &fESDOld);
1740       if(esdFB){
1741         tree->SetBranchAddress("ESDfriend.",&fESDFriendOld);
1742       }
1743     } else {
1744       AliInfo("AliESDEvent::ReadFromTree() Reading old Tree");
1745       AliInfo("Branch already connected. Using existing branch address.");
1746       fESDOld       = (AliESD*)       (*address);
1747       // addressF can still be 0, since branch needs to switched on
1748       if(addressF)fESDFriendOld = (AliESDfriend*) (*addressF);
1749     }
1750                                        
1751     //  have already connected the old ESD structure... ?
1752     // reuse also the pointer of the AlliESDEvent
1753     // otherwise create new ones
1754     TList* connectedList = (TList*) (tree->GetUserInfo()->FindObject("ESDObjectsConnectedToTree"));
1755   
1756     if(connectedList){
1757       // If connected use the connected list of objects
1758       if(fESDObjects!= connectedList){
1759         // protect when called twice 
1760         fESDObjects->Delete();
1761         fESDObjects = connectedList;
1762       }
1763       GetStdContent(); 
1764
1765       
1766       // The pointer to the friend changes when called twice via InitIO
1767       // since AliESDEvent is deleted
1768       TObject* oldf = FindListObject("AliESDfriend");
1769       TObject* newf = 0;
1770       if(addressF){
1771         newf = (TObject*)*addressF;
1772       }
1773       if(newf!=0&&oldf!=newf){
1774         // remove the old reference
1775         // Should we also delete it? Or is this handled in TTree I/O
1776         // since it is created by the first SetBranchAddress
1777         fESDObjects->Remove(oldf);
1778         // add the new one 
1779         fESDObjects->Add(newf);
1780       }
1781       
1782       fConnected = true;
1783       return;
1784     }
1785     // else...    
1786     CreateStdContent(); // create for copy
1787     // if we have the esdfriend add it, so we always can access it via the userinfo
1788     if(fESDFriendOld)AddObject(fESDFriendOld);
1789     // we are not owner of the list objects 
1790     // must not delete it
1791     fESDObjects->SetOwner(kTRUE);
1792     fESDObjects->SetName("ESDObjectsConnectedToTree");
1793     tree->GetUserInfo()->Add(fESDObjects);
1794     fConnected = true;
1795     return;
1796   }
1797   
1798
1799     delete fESDOld;
1800     fESDOld = 0;
1801   // Try to find AliESDEvent
1802   AliESDEvent *esdEvent = 0;
1803   esdEvent = (AliESDEvent*)tree->GetTree()->GetUserInfo()->FindObject("AliESDEvent");
1804   if(esdEvent){   
1805       // Check if already connected to tree
1806     esdEvent->Reset();
1807     TList* connectedList = (TList*) (tree->GetUserInfo()->FindObject("ESDObjectsConnectedToTree"));
1808
1809     
1810     if (connectedList && (strcmp(opt, "reconnect"))) {
1811       // If connected use the connected list if objects
1812       fESDObjects->Delete();
1813       fESDObjects = connectedList;
1814       tree->SetBranchAddress("fDetectorStatus",&fDetectorStatus); //PH probably redundant
1815       tree->SetBranchAddress("fDAQDetectorPattern",&fDAQDetectorPattern);
1816       tree->SetBranchAddress("fDAQAttributes",&fDAQAttributes);
1817       GetStdContent(); 
1818       fOldMuonStructure = fESDObjects->TestBit(BIT(23));
1819       fConnected = true;
1820       return;
1821     }
1822
1823     // Connect to tree
1824     // prevent a memory leak when reading back the TList
1825     // if (!(strcmp(opt, "reconnect"))) fESDObjects->Delete();
1826     
1827     if(!fUseOwnList){
1828       // create a new TList from the UserInfo TList... 
1829       // copy constructor does not work...
1830       fESDObjects = (TList*)(esdEvent->GetList()->Clone());
1831       fESDObjects->SetOwner(kTRUE);
1832     }
1833     else if ( fESDObjects->GetEntries()==0){
1834       // at least create the std content if we want to read to our list
1835       CreateStdContent(); 
1836     }
1837
1838     // in principle
1839     // we only need new things in the list if we do no already have it..
1840     // TODO just add new entries
1841     CompleteStdContent();
1842
1843     if(fESDObjects->GetEntries()<kESDListN){
1844       AliWarning(Form("AliESDEvent::ReadFromTree() TList contains less than the standard contents %d < %d \n",
1845                       fESDObjects->GetEntries(),kESDListN));
1846     }
1847     // set the branch addresses
1848     fOldMuonStructure = kFALSE;
1849     TIter next(fESDObjects);
1850     TNamed *el;
1851     while((el=(TNamed*)next())){
1852       TString bname(el->GetName());
1853       if(bname.CompareTo("AliESDfriend")==0)
1854         {
1855           // AliESDfriend does not have a name ...
1856             TBranch *br = tree->GetBranch("ESDfriend.");
1857             if (br) tree->SetBranchAddress("ESDfriend.",fESDObjects->GetObjectRef(el));
1858         }
1859       else{
1860         // check if branch exists under this Name
1861         TBranch *br = tree->GetBranch(bname.Data());
1862         if(br){
1863           tree->SetBranchAddress(bname.Data(),fESDObjects->GetObjectRef(el));
1864         }
1865         else{
1866           br = tree->GetBranch(Form("%s.",bname.Data()));
1867           if(br){
1868             tree->SetBranchAddress(Form("%s.",bname.Data()),fESDObjects->GetObjectRef(el));
1869           }
1870           else{
1871             AliWarning(Form("AliESDEvent::ReadFromTree() No Branch found with Name %s or %s.",bname.Data(),bname.Data()));
1872             if (bname == fgkESDListName[kMuonClusters]) {
1873               fOldMuonStructure = kTRUE;
1874             }
1875           }
1876
1877         }
1878       }
1879     }
1880     tree->SetBranchAddress("fDetectorStatus",&fDetectorStatus);
1881     tree->SetBranchAddress("fDAQDetectorPattern",&fDAQDetectorPattern);
1882     tree->SetBranchAddress("fDAQAttributes",&fDAQAttributes);
1883
1884     GetStdContent();
1885     // when reading back we are not owner of the list 
1886     // must not delete it
1887     fESDObjects->SetOwner(kTRUE);
1888     fESDObjects->SetName("ESDObjectsConnectedToTree");
1889     fESDObjects->SetBit(BIT(23), fOldMuonStructure);
1890     // we are not owner of the list objects 
1891     // must not delete it
1892     tree->GetUserInfo()->Add(fESDObjects);
1893     tree->GetUserInfo()->SetOwner(kFALSE);
1894     fConnected = true;
1895   }// no esdEvent -->
1896   else {
1897     // we can't get the list from the user data, create standard content
1898     // and set it by hand (no ESDfriend at the moment
1899     CreateStdContent();
1900     fOldMuonStructure = kFALSE;
1901     TIter next(fESDObjects);
1902     TNamed *el;
1903     while((el=(TNamed*)next())){
1904       TString bname(el->GetName());    
1905       TBranch *br = tree->GetBranch(bname.Data());
1906       if(br){
1907         tree->SetBranchAddress(bname.Data(),fESDObjects->GetObjectRef(el));
1908       }
1909       else{
1910         br = tree->GetBranch(Form("%s.",bname.Data()));
1911         if(br){
1912           tree->SetBranchAddress(Form("%s.",bname.Data()),fESDObjects->GetObjectRef(el));
1913         }
1914         else if (bname == fgkESDListName[kMuonClusters]) {
1915           fOldMuonStructure = kTRUE;
1916         }
1917       }
1918     }
1919     tree->SetBranchAddress("fDetectorStatus",&fDetectorStatus);
1920     tree->SetBranchAddress("fDAQDetectorPattern",&fDAQDetectorPattern);
1921     tree->SetBranchAddress("fDAQAttributes",&fDAQAttributes);
1922
1923     GetStdContent();
1924     // when reading back we are not owner of the list 
1925     // must not delete it
1926     fESDObjects->SetOwner(kTRUE);
1927   }
1928 }
1929
1930 //______________________________________________________________________________
1931 void AliESDEvent::CopyFromOldESD()
1932 {
1933   // Method which copies over everthing from the old esd structure to the 
1934   // new  
1935   if(fESDOld){
1936     ResetStdContent();
1937      // Run
1938     SetRunNumber(fESDOld->GetRunNumber());
1939     SetPeriodNumber(fESDOld->GetPeriodNumber());
1940     SetMagneticField(fESDOld->GetMagneticField());
1941   
1942     // leave out diamond ...
1943     // SetDiamond(const AliESDVertex *vertex) { fESDRun->SetDiamond(vertex);}
1944
1945     // header
1946     SetTriggerMask(fESDOld->GetTriggerMask());
1947     SetOrbitNumber(fESDOld->GetOrbitNumber());
1948     SetTimeStamp(fESDOld->GetTimeStamp());
1949     SetEventType(fESDOld->GetEventType());
1950     SetEventNumberInFile(fESDOld->GetEventNumberInFile());
1951     SetBunchCrossNumber(fESDOld->GetBunchCrossNumber());
1952     SetTriggerCluster(fESDOld->GetTriggerCluster());
1953
1954     // ZDC
1955
1956     SetZDC(fESDOld->GetZDCN1Energy(),
1957            fESDOld->GetZDCP1Energy(),
1958            fESDOld->GetZDCEMEnergy(),
1959            0,
1960            fESDOld->GetZDCN2Energy(),
1961            fESDOld->GetZDCP2Energy(),
1962            fESDOld->GetZDCParticipants(),
1963            0,
1964            0,
1965            0,
1966            0,
1967            0,
1968            0);
1969
1970     // FMD
1971     
1972     if(fESDOld->GetFMDData())SetFMDData(fESDOld->GetFMDData());
1973
1974     // T0
1975
1976     SetT0zVertex(fESDOld->GetT0zVertex());
1977     SetT0(fESDOld->GetT0());
1978     //  leave amps out
1979
1980     // VZERO
1981     if (fESDOld->GetVZEROData()) SetVZEROData(fESDOld->GetVZEROData());
1982
1983     if(fESDOld->GetVertex())SetPrimaryVertexSPD(fESDOld->GetVertex());
1984
1985     if(fESDOld->GetPrimaryVertex())SetPrimaryVertexTracks(fESDOld->GetPrimaryVertex());
1986
1987     if(fESDOld->GetMultiplicity())SetMultiplicity(fESDOld->GetMultiplicity());
1988
1989     for(int i = 0;i<fESDOld->GetNumberOfTracks();i++){
1990       AddTrack(fESDOld->GetTrack(i));
1991     }
1992
1993     for(int i = 0;i<fESDOld->GetNumberOfMuonTracks();i++){
1994       AddMuonTrack(fESDOld->GetMuonTrack(i));
1995     }
1996
1997     for(int i = 0;i<fESDOld->GetNumberOfPmdTracks();i++){
1998       AddPmdTrack(fESDOld->GetPmdTrack(i));
1999     }
2000
2001     for(int i = 0;i<fESDOld->GetNumberOfTrdTracks();i++){
2002       AddTrdTrack(fESDOld->GetTrdTrack(i));
2003     }
2004
2005     for(int i = 0;i<fESDOld->GetNumberOfV0s();i++){
2006       AddV0(fESDOld->GetV0(i));
2007     }
2008
2009     for(int i = 0;i<fESDOld->GetNumberOfCascades();i++){
2010       AddCascade(fESDOld->GetCascade(i));
2011     }
2012
2013     for(int i = 0;i<fESDOld->GetNumberOfKinks();i++){
2014       AddKink(fESDOld->GetKink(i));
2015     }
2016
2017
2018     for(int i = 0;i<fESDOld->GetNumberOfCaloClusters();i++){
2019       AddCaloCluster(fESDOld->GetCaloCluster(i));
2020     }
2021           
2022   }// if fesdold
2023 }
2024
2025 //______________________________________________________________________________
2026 Bool_t AliESDEvent::IsEventSelected(const char *trigExpr) const
2027 {
2028   // Check if the event satisfies the trigger
2029   // selection expression trigExpr.
2030   // trigExpr can be any logical expression
2031   // of the trigger classes defined in AliESDRun
2032   // In case of wrong syntax return kTRUE.
2033
2034   TString expr(trigExpr);
2035   if (expr.IsNull()) return kTRUE;
2036
2037   ULong64_t mask = GetTriggerMask();
2038   for(Int_t itrig = 0; itrig < AliESDRun::kNTriggerClasses; itrig++) {
2039     if (mask & (1ull << itrig)) {
2040       expr.ReplaceAll(GetESDRun()->GetTriggerClass(itrig),"1");
2041     }
2042     else {
2043       expr.ReplaceAll(GetESDRun()->GetTriggerClass(itrig),"0");
2044     }
2045   }
2046
2047   Int_t error;
2048   if ((gROOT->ProcessLineFast(expr.Data(),&error) == 0) &&
2049       (error == TInterpreter::kNoError)) {
2050     return kFALSE;
2051   }
2052
2053   return kTRUE;
2054
2055 }
2056
2057 //______________________________________________________________________________
2058 TObject*  AliESDEvent::GetHLTTriggerDecision() const
2059 {
2060   // get the HLT trigger decission object
2061
2062   // cast away const'nes because the FindListObject method
2063   // is not const
2064   AliESDEvent* pNonConst=const_cast<AliESDEvent*>(this);
2065   return pNonConst->FindListObject("HLTGlobalTrigger");
2066 }
2067
2068 TString   AliESDEvent::GetHLTTriggerDescription() const
2069 {
2070   // get the HLT trigger decission description
2071   TString description;
2072   TObject* pDecision=GetHLTTriggerDecision();
2073   if (pDecision) {
2074     description=pDecision->GetTitle();
2075   }
2076
2077   return description;
2078 }
2079
2080 //______________________________________________________________________________
2081 Bool_t    AliESDEvent::IsHLTTriggerFired(const char* name) const
2082 {
2083   // get the HLT trigger decission description
2084   TObject* pDecision=GetHLTTriggerDecision();
2085   if (!pDecision) return kFALSE;
2086
2087   Option_t* option=pDecision->GetOption();
2088   if (option==NULL || *option!='1') return kFALSE;
2089
2090   if (name) {
2091     TString description=GetHLTTriggerDescription();
2092     Int_t index=description.Index(name);
2093     if (index<0) return kFALSE;
2094     index+=strlen(name);
2095     if (index>=description.Length()) return kFALSE;
2096     if (description[index]!=0 && description[index]!=' ') return kFALSE;
2097   }
2098   return kTRUE;
2099 }
2100
2101 //______________________________________________________________________________
2102 Bool_t  AliESDEvent::IsPileupFromSPD(Int_t minContributors, 
2103                                      Double_t minZdist, 
2104                                      Double_t nSigmaZdist, 
2105                                      Double_t nSigmaDiamXY, 
2106                                      Double_t nSigmaDiamZ) const{
2107   //
2108   // This function checks if there was a pile up
2109   // reconstructed with SPD
2110   //
2111   Int_t nc1=fSPDVertex->GetNContributors();
2112   if(nc1<1) return kFALSE;
2113   Int_t nPileVert=GetNumberOfPileupVerticesSPD();
2114   if(nPileVert==0) return kFALSE;
2115   
2116   for(Int_t i=0; i<nPileVert;i++){
2117     const AliESDVertex* pv=GetPileupVertexSPD(i);
2118     Int_t nc2=pv->GetNContributors();
2119     if(nc2>=minContributors){
2120       Double_t z1=fSPDVertex->GetZ();
2121       Double_t z2=pv->GetZ();
2122       Double_t distZ=TMath::Abs(z2-z1);
2123       Double_t distZdiam=TMath::Abs(z2-GetDiamondZ());
2124       Double_t cutZdiam=nSigmaDiamZ*TMath::Sqrt(GetSigma2DiamondZ());
2125       if(GetSigma2DiamondZ()<0.0001)cutZdiam=99999.; //protection for missing z diamond information
2126       if(distZ>minZdist && distZdiam<cutZdiam){
2127         Double_t x2=pv->GetX();
2128         Double_t y2=pv->GetY();
2129         Double_t distXdiam=TMath::Abs(x2-GetDiamondX());
2130         Double_t distYdiam=TMath::Abs(y2-GetDiamondY());
2131         Double_t cov1[6],cov2[6];       
2132         fSPDVertex->GetCovarianceMatrix(cov1);
2133         pv->GetCovarianceMatrix(cov2);
2134         Double_t errxDist=TMath::Sqrt(cov2[0]+GetSigma2DiamondX());
2135         Double_t erryDist=TMath::Sqrt(cov2[2]+GetSigma2DiamondY());
2136         Double_t errzDist=TMath::Sqrt(cov1[5]+cov2[5]);
2137         Double_t cutXdiam=nSigmaDiamXY*errxDist;
2138         if(GetSigma2DiamondX()<0.0001)cutXdiam=99999.; //protection for missing diamond information
2139         Double_t cutYdiam=nSigmaDiamXY*erryDist;
2140         if(GetSigma2DiamondY()<0.0001)cutYdiam=99999.; //protection for missing diamond information
2141         if( (distXdiam<cutXdiam) && (distYdiam<cutYdiam) && (distZ>nSigmaZdist*errzDist) ){
2142           return kTRUE;
2143         }
2144       }
2145     }
2146   }
2147   return kFALSE;
2148 }
2149
2150 //______________________________________________________________________________
2151 void AliESDEvent::EstimateMultiplicity(Int_t &tracklets, Int_t &trITSTPC, Int_t &trITSSApure, Double_t eta, Bool_t useDCAFlag,Bool_t useV0Flag) const
2152 {
2153   //
2154   // calculates 3 estimators for the multiplicity in the -eta:eta range
2155   // tracklets   : using SPD tracklets only
2156   // trITSTPC    : using TPC/ITS + complementary ITS SA tracks + tracklets from clusters not used by tracks
2157   // trITSSApure : using ITS standalone tracks + tracklets from clusters not used by tracks
2158   // if useDCAFlag is true: account for the ESDtrack flag marking the tracks with large DCA
2159   // if useV0Flag  is true: account for the ESDtrack flag marking conversion and K0's V0s
2160
2161   AliWarning("This obsolete method will be eliminated soon. Use AliESDtrackCuts::GetReferenceMultiplicity");
2162
2163   tracklets = trITSSApure = trITSTPC = 0;
2164   int ntr = fSPDMult ? fSPDMult->GetNumberOfTracklets() : 0;
2165   //
2166   // count tracklets
2167   for (int itr=ntr;itr--;) { 
2168     if (TMath::Abs(fSPDMult->GetEta(itr))>eta) continue;
2169     tracklets++;
2170     if (fSPDMult->FreeClustersTracklet(itr,0)) trITSTPC++;    // not used in ITS/TPC or ITS_SA track
2171     if (fSPDMult->FreeClustersTracklet(itr,1)) trITSSApure++; // not used in ITS_SA_Pure track
2172   }
2173   //
2174   // count real tracks
2175   ntr = GetNumberOfTracks();
2176   for (int itr=ntr;itr--;) {
2177     AliESDtrack *t = GetTrack(itr);
2178     if (!t) {AliFatal(Form("NULL pointer for ESD track %d",itr));}
2179     if (TMath::Abs(t->Eta())>eta) continue;
2180     if (!t->IsOn(AliESDtrack::kITSin)) continue;
2181     if (useDCAFlag && t->IsOn(AliESDtrack::kMultSec))  continue;
2182     if (useV0Flag  && t->IsOn(AliESDtrack::kMultInV0)) continue;    
2183     if (t->IsOn(AliESDtrack::kITSpureSA)) trITSSApure++;
2184     else                                  trITSTPC++;
2185   }
2186   //
2187 }
2188
2189 //______________________________________________________________________________
2190 Bool_t AliESDEvent::IsPileupFromSPDInMultBins() const {
2191     Int_t nTracklets=GetMultiplicity()->GetNumberOfTracklets();
2192     if(nTracklets<20) return IsPileupFromSPD(3,0.8);
2193     else if(nTracklets<50) return IsPileupFromSPD(4,0.8);
2194     else return IsPileupFromSPD(5,0.8);
2195 }
2196
2197 //______________________________________________________________________________
2198 void  AliESDEvent::SetTOFHeader(const AliTOFHeader *header)
2199 {
2200   //
2201   // Set the TOF event_time
2202   //
2203
2204   if (fTOFHeader) {
2205     *fTOFHeader=*header;
2206     //fTOFHeader->SetName(fgkESDListName[kTOFHeader]);
2207   }
2208   else {
2209     // for analysis of reconstructed events
2210     // when this information is not avaliable
2211     fTOFHeader = new AliTOFHeader(*header);
2212     //AddObject(fTOFHeader);
2213   }
2214
2215 }
2216
2217 //______________________________________________________________________________
2218 AliCentrality* AliESDEvent::GetCentrality()
2219 {
2220     if (!fCentrality) fCentrality = new AliCentrality();
2221     return  fCentrality;
2222 }
2223
2224 //______________________________________________________________________________
2225 AliEventplane* AliESDEvent::GetEventplane()
2226 {
2227     if (!fEventplane) fEventplane = new AliEventplane();
2228     return  fEventplane;
2229 }
2230
2231 //______________________________________________________________________________
2232 Float_t AliESDEvent::GetVZEROEqMultiplicity(Int_t i) const
2233 {
2234   // Get VZERO Multiplicity for channel i
2235   // Themethod uses the equalization factors
2236   // stored in the ESD-run object in order to
2237   // get equal multiplicities within a VZERO rins (1/8 of VZERO)
2238   if (!fESDVZERO || !fESDRun) return -1;
2239
2240   Int_t ring = i/8;
2241   Float_t factorSum = 0;
2242   for(Int_t j = 8*ring; j < (8*ring+8); ++j) {
2243     factorSum += fESDRun->GetVZEROEqFactors(j);
2244   }
2245   Float_t factor = fESDRun->GetVZEROEqFactors(i)*8./factorSum;
2246
2247   return (fESDVZERO->GetMultiplicity(i)/factor);
2248 }
2249
2250 //______________________________________________________________________________
2251 void AliESDEvent::SetTOFcluster(Int_t ntofclusters,AliESDTOFCluster *cluster,Int_t *mapping)
2252 {
2253   // Reset TClonesArray of TOF clusters
2254   if (!fESDTOFClusters) {
2255     AliError("fESDTOFClusters is not initialized");
2256     return;
2257   }
2258   fESDTOFClusters->Clear();
2259   
2260   Int_t goodhit[20000];
2261   if(mapping){
2262     for(Int_t i=0;i < 20000;i++){
2263       goodhit[i] = 0;
2264     }
2265   }
2266
2267   for(Int_t i=0;i < ntofclusters;i++){
2268     
2269     if(cluster[i].GetNMatchableTracks() || !mapping){
2270       if(mapping)
2271         mapping[i] = fESDTOFClusters->GetEntriesFast();
2272       
2273       // update TClonesArray
2274       TClonesArray &ftr = *fESDTOFClusters;
2275       AliESDTOFCluster *clusterTBW = new(ftr[fESDTOFClusters->GetEntriesFast()])AliESDTOFCluster(cluster[i]);
2276
2277       if(mapping){
2278         // loop over hit in the cluster
2279         for(Int_t k=0;k < clusterTBW->GetNTOFhits();k++){
2280           Int_t ipos = clusterTBW->GetHitIndex(k);
2281           goodhit[ipos] = 1; // hit should be kept
2282         }
2283       }
2284     }
2285   }
2286
2287   if(mapping){
2288     AliInfo(Form("TOF cluster before of matching = %i , after = %i\n",ntofclusters,fESDTOFClusters->GetEntriesFast()));
2289     Int_t hitnewpos[20000]={0};
2290     Int_t nhitOriginal = fESDTOFHits->GetEntries();
2291     for(Int_t i=0;i < fESDTOFHits->GetEntries();i++){
2292       if(goodhit[i]){
2293         hitnewpos[i] = i;
2294       }
2295       else{ // remove hit and decrease the hit array
2296         TClonesArray &a=*fESDTOFHits;
2297         Int_t lastpos = fESDTOFHits->GetEntries()-1;
2298
2299         if(i == lastpos)
2300           delete a.RemoveAt(i);
2301         else{
2302           Int_t nhitBefore = fESDTOFHits->GetEntries();
2303           for(Int_t k=nhitBefore-1;k>i;k--){ // find the last good track
2304             if(!goodhit[k]){ // remove track
2305               delete a.RemoveAt(k);
2306               if(k-i==1) delete a.RemoveAt(i);
2307             }
2308             else{ // replace last one to the "i"
2309               AliESDTOFHit *last = (AliESDTOFHit *) fESDTOFHits->At(k);
2310               delete a.RemoveAt(i);
2311               new (a[i]) AliESDTOFHit(*last);
2312               delete a.RemoveAt(k);
2313               hitnewpos[k] = i;
2314               k = 0;
2315             }
2316           }
2317         }
2318       }
2319     }
2320
2321     // remap cluster to hits
2322     for(Int_t i=0;i < fESDTOFClusters->GetEntries();i++){
2323       AliESDTOFCluster *cl = (AliESDTOFCluster *) fESDTOFClusters->At(i);
2324       // loop over hit in the cluster
2325       for(Int_t k=0;k < cl->GetNTOFhits();k++){
2326         cl->SetHitIndex(k,hitnewpos[cl->GetHitIndex(k)]);
2327       }
2328     }
2329     AliInfo(Form("TOF hit before of matching = %i , after = %i\n",nhitOriginal,fESDTOFHits->GetEntriesFast()));
2330   } // end mapping
2331
2332 }
2333
2334 //______________________________________________________________________________
2335 void AliESDEvent::SetTOFcluster(Int_t ntofclusters,AliESDTOFCluster *cluster[],Int_t *mapping)
2336 {    
2337   // Reset TClonesArray of TOF clusters
2338   if(fESDTOFClusters)fESDTOFClusters->Delete();
2339    
2340   Int_t goodhit[20000];
2341   if(mapping){
2342     for(Int_t i=0;i < 20000;i++){
2343       goodhit[i] = 0;
2344     }
2345   }
2346       
2347   for(Int_t i=0;i < ntofclusters;i++){
2348
2349     if(cluster[i]->GetNMatchableTracks() || !mapping){
2350       if(mapping)
2351         mapping[i] = fESDTOFClusters->GetEntriesFast();
2352         
2353       // update TClonesArray
2354       TClonesArray &ftr = *fESDTOFClusters;
2355       AliESDTOFCluster *clusterTBW = new(ftr[fESDTOFClusters->GetEntriesFast()])AliESDTOFCluster(*(cluster[i]));
2356
2357       if(mapping){
2358         // loop over hit in the cluster
2359         for(Int_t k=0;k < clusterTBW->GetNTOFhits();k++){
2360           Int_t ipos = clusterTBW->GetHitIndex(k);
2361           goodhit[ipos] = 1; // hit should be kept
2362         }
2363       }
2364     }
2365   }
2366
2367   if(mapping){
2368     AliInfo(Form("TOF cluster before of matching = %i , after = %i\n",ntofclusters,fESDTOFClusters->GetEntriesFast()));
2369     Int_t hitnewpos[20000]={0};
2370     Int_t nhitOriginal = fESDTOFHits->GetEntries();
2371     for(Int_t i=0;i < fESDTOFHits->GetEntries();i++){
2372       if(goodhit[i]){
2373         hitnewpos[i] = i;
2374       }
2375       else{ // remove hit and decrease the hit array
2376         TClonesArray &a=*fESDTOFHits;
2377         Int_t lastpos = fESDTOFHits->GetEntries()-1;
2378
2379         if(i == lastpos)
2380           delete a.RemoveAt(i);
2381         else{
2382           Int_t nhitBefore = fESDTOFHits->GetEntries();
2383           for(Int_t k=nhitBefore-1;k>i;k--){ // find the last good track
2384             if(!goodhit[k]){ // remove track
2385               delete a.RemoveAt(k);
2386               if(k-i==1) delete a.RemoveAt(i);
2387             }
2388             else{ // replace last one to the "i"
2389               AliESDTOFHit *last = (AliESDTOFHit *) fESDTOFHits->At(k);
2390               delete a.RemoveAt(i);
2391               new (a[i]) AliESDTOFHit(*last);
2392               delete a.RemoveAt(k);
2393               hitnewpos[k] = i;
2394               k = 0;
2395             }
2396           }
2397         }
2398       }
2399     }
2400
2401     // remap cluster to hits
2402     for(Int_t i=0;i < fESDTOFClusters->GetEntries();i++){
2403       AliESDTOFCluster *cl = (AliESDTOFCluster *) fESDTOFClusters->At(i);
2404       // loop over hit in the cluster
2405       for(Int_t k=0;k < cl->GetNTOFhits();k++){
2406         cl->SetHitIndex(k,hitnewpos[cl->GetHitIndex(k)]);
2407       }
2408     }
2409     AliInfo(Form("TOF hit before of matching = %i , after = %i\n",nhitOriginal,fESDTOFHits->GetEntriesFast()));
2410   } // end mapping
2411
2412 }
2413
2414 //______________________________________________________________________________
2415 void AliESDEvent::ConnectTracks() {
2416 // Connect tracks to this event
2417   if (fTracksConnected || !fTracks || !fTracks->GetEntriesFast()) return;
2418   AliESDtrack *track;
2419   TIter next(fTracks);
2420   while ((track=(AliESDtrack*)next())) track->SetESDEvent(this);
2421   //
2422   // The same for TOF clusters
2423   if (fESDTOFClusters) {
2424     AliESDTOFCluster *clus;
2425     TIter nextTOF(fESDTOFClusters);
2426     while ((clus=(AliESDTOFCluster*)nextTOF())) clus->SetEvent((AliVEvent *) this);
2427   }
2428   fTracksConnected = kTRUE;
2429   //
2430 }
2431
2432 //______________________________________________________________________________
2433 AliESDfriend* AliESDEvent::FindFriend() const 
2434
2435   return static_cast<AliESDfriend*>(FindListObject("AliESDfriend")); 
2436 }
2437
2438 AliVEvent::EDataLayoutType AliESDEvent::GetDataLayoutType() const {return AliVEvent::kESD;}
2439