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