In AliMUONClusterInfo:
authorivana <ivana@f7af4fe6-9843-0410-8265-dc069ae4e863>
Thu, 23 Apr 2009 12:51:25 +0000 (12:51 +0000)
committerivana <ivana@f7af4fe6-9843-0410-8265-dc069ae4e863>
Thu, 23 Apr 2009 12:51:25 +0000 (12:51 +0000)
- Added new data members and methods
- Added the possibility get info from clusters not attached to a track (recPoints)
- Updated macro MUONClusterInfo.C
(Philippe P., Javier)

MUON/AliMUONClusterInfo.cxx
MUON/AliMUONClusterInfo.h
MUON/AliMUONPadInfo.cxx
MUON/AliMUONPadInfo.h
MUON/MUONClusterInfo.C

index 1129809..08f0759 100644 (file)
@@ -36,6 +36,7 @@ ClassImp(AliMUONClusterInfo)
 //_____________________________________________________________________________
 AliMUONClusterInfo::AliMUONClusterInfo()
 : TObject(),
+  fRunId(0),
   fEventId(0),
   fZ(0.),
   fClusterId(0),
@@ -55,6 +56,8 @@ AliMUONClusterInfo::AliMUONClusterInfo()
   fTrackYErr(0.),
   fTrackChi2(0.),
   fTrackCharge(0),
+  fTrackNHits(0),
+  fTrackChamberHitMap(0),
   fNPads(0),
   fPads(new TClonesArray("AliMUONPadInfo",10))
 {
@@ -64,6 +67,7 @@ AliMUONClusterInfo::AliMUONClusterInfo()
 //_____________________________________________________________________________
 AliMUONClusterInfo::AliMUONClusterInfo (const AliMUONClusterInfo& clusterInfo)
 : TObject(clusterInfo),
+  fRunId(clusterInfo.fRunId),
   fEventId(clusterInfo.fEventId),
   fZ(clusterInfo.fZ),
   fClusterId(clusterInfo.fClusterId),
@@ -83,6 +87,8 @@ AliMUONClusterInfo::AliMUONClusterInfo (const AliMUONClusterInfo& clusterInfo)
   fTrackYErr(clusterInfo.fTrackYErr),
   fTrackChi2(clusterInfo.fTrackChi2),
   fTrackCharge(clusterInfo.fTrackCharge),
+  fTrackNHits(clusterInfo.fTrackNHits),
+  fTrackChamberHitMap(clusterInfo.fTrackChamberHitMap),
   fNPads(clusterInfo.fNPads),
   fPads(new TClonesArray("AliMUONPadInfo",clusterInfo.fNPads))
 {
@@ -102,6 +108,7 @@ AliMUONClusterInfo& AliMUONClusterInfo::operator=(const AliMUONClusterInfo& clus
   
   TObject::operator=(clusterInfo); // don't forget to invoke the base class' assignment operator
   
+  fRunId = clusterInfo.fRunId;
   fEventId = clusterInfo.fEventId;
   fZ = clusterInfo.fZ;
   fClusterId = clusterInfo.fClusterId;
@@ -121,6 +128,8 @@ AliMUONClusterInfo& AliMUONClusterInfo::operator=(const AliMUONClusterInfo& clus
   fTrackYErr = clusterInfo.fTrackYErr;
   fTrackChi2 = clusterInfo.fTrackChi2;
   fTrackCharge = clusterInfo.fTrackCharge;
+  fTrackNHits = clusterInfo.fTrackNHits;
+  fTrackChamberHitMap = clusterInfo.fTrackChamberHitMap;
   fNPads = clusterInfo.fNPads;
   
   fPads->Clear("C");
@@ -186,3 +195,100 @@ void AliMUONClusterInfo::Print(Option_t* option) const
   
 }
 
+Double_t AliMUONClusterInfo::GetClusterCharge(Int_t iPlaneType) const
+{
+  Double_t lClusterChargeC = 0.;
+  if (!fPads) {
+    lClusterChargeC = GetClusterCharge()/2.;
+  }
+  else {
+    AliMUONPadInfo *pad = (AliMUONPadInfo*) fPads->First();
+    while (pad) {
+      if (pad->GetPadPlaneType()==iPlaneType) lClusterChargeC += pad->GetPadCharge();
+      pad = (AliMUONPadInfo*) fPads->After(pad);
+    }    
+  }
+  return lClusterChargeC;
+}
+
+Int_t AliMUONClusterInfo::GetNPads(Int_t iPlaneType) const
+{
+  Int_t iNPads = 0;
+
+  if (!fPads) {
+    iNPads = GetNPads();
+  }
+  else {
+    AliMUONPadInfo *pad = (AliMUONPadInfo*) fPads->First();
+    while (pad) {
+      if (pad->GetPadPlaneType()==iPlaneType) {
+       iNPads++;
+      }
+      pad = (AliMUONPadInfo*) fPads->After(pad);
+    }   
+  }
+  return iNPads;
+}
+
+Int_t AliMUONClusterInfo::GetNPadsX(Int_t iPlaneType) const
+{
+  Int_t iNPadsX = 0;
+  Double_t lPadXMin = 10000.;
+  Double_t lPadXMax = -10000.;
+  Int_t nChangedMin = 0;
+  Int_t nChangedMax = 0;
+
+  if (!fPads) {
+    iNPadsX = GetNPads();
+  }
+  else {
+    AliMUONPadInfo *pad = (AliMUONPadInfo*) fPads->First();
+    while (pad) {
+      if (pad->GetPadPlaneType()==iPlaneType) {
+       if (pad->GetPadX()<lPadXMin){
+         lPadXMin = pad->GetPadX();
+         nChangedMin++;
+       }
+       if (pad->GetPadX()>lPadXMax){
+         lPadXMax = pad->GetPadX();
+         nChangedMax++;
+       }  
+      }    
+      pad = (AliMUONPadInfo*) fPads->After(pad);
+    }    
+    iNPadsX = TMath::Max(nChangedMin+nChangedMax-1,0);
+  }
+  return iNPadsX;
+}
+
+Int_t AliMUONClusterInfo::GetNPadsY(Int_t iPlaneType) const
+{
+  Int_t iNPadsY = 0;
+  Double_t lPadYMin = 10000.;
+  Double_t lPadYMax = -10000.;
+  Int_t nChangedMin = 0;
+  Int_t nChangedMax = 0;
+
+  if (!fPads) {
+    iNPadsY = GetNPads();
+  }
+  else {
+    AliMUONPadInfo *pad = (AliMUONPadInfo*) fPads->First();
+    while (pad) {
+      if (pad->GetPadPlaneType()==iPlaneType) {
+       if (pad->GetPadY()<lPadYMin){
+         lPadYMin = pad->GetPadY();
+         nChangedMin++;
+       }
+       if (pad->GetPadY()>lPadYMax){
+         lPadYMax = pad->GetPadY();
+         nChangedMax++;
+       }  
+      }    
+      pad = (AliMUONPadInfo*) fPads->After(pad);
+    }    
+    iNPadsY = TMath::Max(nChangedMin+nChangedMax-1,0);
+  }
+  return iNPadsY;
+}
+
index a4e30a9..8c84f15 100644 (file)
@@ -29,10 +29,16 @@ public:
   
   
   // ------ general info ------
+  /// set run number
+  void     SetRunId(Int_t runId) {fRunId = runId;}
+  /// return run ID
+  Int_t    GetRunId() const {return fRunId;}
+
   /// set event number
   void     SetEventId(Int_t eventId) {fEventId = eventId;}
   /// return event ID
   Int_t    GetEventId() const {return fEventId;}
+
   
   /// Set cluster/track Z-position (cm)
   void     SetZ(Double_t z) {fZ = z;}
@@ -75,6 +81,12 @@ public:
   void     SetClusterCharge(Double_t charge) {fClusterCharge = charge;}
   /// Return the total cluster charge
   Double_t GetClusterCharge() const {return fClusterCharge;}
+  /// Return the cluster charge for cathode iC
+  Double_t GetClusterCharge(Int_t iC) const ;
+  /// Return the bending cluster charge
+  Double_t GetClusterChargeB() const {return GetClusterCharge(0);}
+  /// Return the non bending cluster charge
+  Double_t GetClusterChargeNB() const {return GetClusterCharge(1);}
   
   
   // ------ track info ------
@@ -116,11 +128,40 @@ public:
   void     SetTrackCharge(Short_t charge) {fTrackCharge = charge;}
   /// Return the muon charge
   Short_t  GetTrackCharge() const {return fTrackCharge;}
-  
+
+  /// Get the total number of hits associated to the track leaving this cluster
+  UChar_t  GetTrackNHits(void) const {return fTrackNHits;}
+  /// Set the total number of hits associated to the track leaving this cluster
+    void     SetTrackNHits(UInt_t NHits) {fTrackNHits = NHits;}
+
+  /// Get the map of hit chambers
+  UInt_t   GetTrackChamberHitMap() const {return fTrackChamberHitMap;}
+  /// Set the map of hit chambers
+  void     SetTrackChamberHitMap(UInt_t trackChamberHitMap) {fTrackChamberHitMap = trackChamberHitMap;}
+  /// Is chamber hit by track
+  Bool_t   IsChamberHit(Int_t chamber) const {return (Bool_t) ((fTrackChamberHitMap & BIT(chamber)) != 0);}
   
   // ------ pad info ------
   /// return the number of pads attached to the cluster
   Int_t    GetNPads() const {return fPads->GetEntriesFast();}
+  /// return the number of pads attached to the cluster in cathode iC
+  Int_t    GetNPads(Int_t iC) const ;
+  /// return the number of bending pads attached to the cluster
+  Int_t    GetNPadsB() const {return GetNPads(0);}
+  /// return the number of non bending pads attached to the cluster
+  Int_t    GetNPadsNB() const {return GetNPads(1);}
+  /// return the number of pads attached to the cluster
+  Int_t    GetNPadsX(Int_t iC) const ;
+  /// return the number of pads attached to the cluster
+  Int_t    GetNPadsXB() const {return GetNPadsX(0);}
+  /// return the number of pads attached to the cluster
+  Int_t    GetNPadsXNB() const {return GetNPadsX(1);}
+  /// return the number of pads attached to the cluster
+  Int_t    GetNPadsY(Int_t iC) const ;
+  /// return the number of pads attached to the cluster
+  Int_t    GetNPadsYB() const {return GetNPadsY(0);}
+  /// return the number of pads attached to the cluster
+  Int_t    GetNPadsYNB() const {return GetNPadsY(1);}
   /// return the array of pads attached to the cluster
   TClonesArray& GetPads() const {return *fPads;}
   /// attach a pad to the cluster
@@ -130,6 +171,7 @@ public:
 protected:
   
   // general info
+  Int_t      fRunId;    ///< run number
   Int_t      fEventId;    ///< event number
   Double32_t fZ;          ///< track/cluster Z position
   
@@ -153,11 +195,13 @@ protected:
   Double32_t fTrackYErr;   ///< track Y resolution
   Double32_t fTrackChi2;   ///< track normalized chi2
   Short_t    fTrackCharge; ///< track charge  
-  
+  UChar_t    fTrackNHits;   ///< track number of hits
+  UInt_t     fTrackChamberHitMap; ///< Map of clusters in tracking chambers
+
   Int_t         fNPads; ///< nPads  
   TClonesArray* fPads;  ///< Array of pads attached to the cluster
     
-  ClassDef(AliMUONClusterInfo, 2)
+  ClassDef(AliMUONClusterInfo, 3)
 };
 
 #endif
index 2396287..d28b327 100644 (file)
@@ -38,6 +38,7 @@ ClassImp(AliMUONPadInfo)
 AliMUONPadInfo::AliMUONPadInfo()
 : TObject(),
   fPadId(0),
+  fPadPlaneType(0),
   fPadX(0.),
   fPadY(0.),
   fPadDimX(0.),
@@ -60,6 +61,7 @@ AliMUONPadInfo::AliMUONPadInfo()
 AliMUONPadInfo::AliMUONPadInfo (const AliMUONPadInfo& padInfo)
 : TObject(padInfo),
   fPadId(padInfo.fPadId),
+  fPadPlaneType(padInfo.fPadPlaneType),
   fPadX(padInfo.fPadX),
   fPadY(padInfo.fPadY),
   fPadDimX(padInfo.fPadDimX),
@@ -87,6 +89,7 @@ AliMUONPadInfo& AliMUONPadInfo::operator=(const AliMUONPadInfo& padInfo)
   TObject::operator=(padInfo); // don't forget to invoke the base class' assignment operator
   
   fPadId = padInfo.fPadId;
+  fPadPlaneType = padInfo.fPadPlaneType;
   fPadX = padInfo.fPadX;
   fPadY = padInfo.fPadY;
   fPadDimX = padInfo.fPadDimX;
index 8a62a58..5d970bc 100644 (file)
@@ -40,6 +40,10 @@ public:
   Int_t    GetManuChannel() const {return (fPadId & 0x3F000000) >> 24;}
   /// Return the cathode number, part of the uniqueID
   Int_t    GetCathode() const     {return (fPadId & 0x40000000) >> 30;}
+  /// Return the plane type 0=Bending 1=NonBending
+  Int_t    GetPadPlaneType() const     {return fPadPlaneType;}
+  /// Set the plane type 0=Bending 1=NonBending
+  void     SetPadPlaneType(Int_t planeType) {fPadPlaneType = planeType;}
   
   /// Set pad coordinates (cm)
   void     SetPadXY(Double_t x, Double_t y) {fPadX = x; fPadY = y;}
@@ -99,6 +103,7 @@ protected:
     
   // pad info
   UInt_t     fPadId;         ///< pad ID
+  Int_t      fPadPlaneType;   ///< pad plane tye (0=Bending; 1=NonBending)
   Double32_t fPadX;          ///< pad X position
   Double32_t fPadY;          ///< pad Y position
   Double32_t fPadDimX;       ///< pad X dimension
@@ -116,7 +121,7 @@ protected:
   Int_t      fGainThres;     ///< threshold of quadratic behaviour of gain
   Int_t      fGainQual;      ///< quality of gain parameters
   
-  ClassDef(AliMUONPadInfo, 1)
+  ClassDef(AliMUONPadInfo, 2)
 };
 
 #endif
index 67009ae..2f49635 100644 (file)
@@ -1,17 +1,17 @@
 /**************************************************************************
-* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
-*                                                                        *
-* Author: The ALICE Off-line Project.                                    *
-* Contributors are mentioned in the code where appropriate.              *
-*                                                                        *
-* Permission to use, copy, modify and distribute this software and its   *
-* documentation strictly for non-commercial purposes is hereby granted   *
-* without fee, provided that the above copyright notice appears in all   *
-* copies and that both the copyright notice and this permission notice   *
-* appear in the supporting documentation. The authors make no claims     *
-* about the suitability of this software for any purpose. It is          *
-* provided "as is" without express or implied warranty.                  *
-**************************************************************************/
+ * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
+ *                                                                        *
+ * Author: The ALICE Off-line Project.                                    *
+ * Contributors are mentioned in the code where appropriate.              *
+ *                                                                        *
+ * Permission to use, copy, modify and distribute this software and its   *
+ * documentation strictly for non-commercial purposes is hereby granted   *
+ * without fee, provided that the above copyright notice appears in all   *
+ * copies and that both the copyright notice and this permission notice   *
+ * appear in the supporting documentation. The authors make no claims     *
+ * about the suitability of this software for any purpose. It is          *
+ * provided "as is" without express or implied warranty.                  *
+ **************************************************************************/
 
 /* $Id$ */
 
 #include <TTree.h>
 #include <TString.h>
 #include <Riostream.h>
-#include <TGeoManager.h>
 #include <TRandom.h>
 #include <TROOT.h>
+#include <TMath.h>
 
 // STEER includes
 #include "AliMagF.h"
 #include "AliTracker.h"
 #include "AliESDEvent.h"
-#include "AliESDMuonTrack.h"
 #include "AliRecoParam.h"
 #include "AliCDBManager.h"
-#include "AliGeomManager.h"
+#include "AliRunLoader.h"
+#include "AliLoader.h"
 
 // MUON includes
+#include "AliMpConstants.h"
 #include "AliMpCDB.h"
 #include "AliMpSegmentation.h"
 #include "AliMpVSegmentation.h"
@@ -55,6 +56,7 @@
 #include "AliMUONVDigit.h"
 #include "AliMUONVDigitStore.h"
 #include "AliMUONVCluster.h"
+#include "AliMUONVClusterStore.h"
 #include "AliMUONTrack.h"
 #include "AliMUONTrackParam.h"
 #endif
@@ -63,29 +65,61 @@ const Int_t printLevel = 1;
 
 void Prepare();
 TTree* GetESDTree(TFile *esdFile);
+UInt_t buildClusterMap(AliMUONTrack &track);
 
 //-----------------------------------------------------------------------
-void MUONClusterInfo(Int_t nevents = -1, const char* esdFileName = "AliESDs.root", const char* outFileName = "clusterInfo.root")
+void MUONClusterInfo(Int_t nevents = -1, const char* esdFileName = "AliESDs.root",
+                    const char* inFileName = "galice.root", const char* outFileName = "clusterInfo.root")
 {
-  /// load ESD event in the ESDInterface to recover MUON objects;
-  /// track parameters at each cluster are recomputed by the interface using Kalman filter + Smoother
-  /// (It can be changed by resetting the tracker in the interface with a new recoParam object);
-  /// fill AliMUONESDClusterInfo object with ESD cluster + corresponding track parameters;
-  /// write results in a new root file.
+  /// 1) if (esdFileName != "")
+  /// loop over ESD event and fill AliMUONClusterInfo object with cluster + corresponding track parameters;
+  /// 2) if (inFileName != "")
+  /// loop over RecPoints and fill AliMUONClusterInfo object with cluster not attached to a track;
+  /// 3) write results in a new root file.
+  ///
+  /// ******************************************* WARNING ******************************************* ///
+  /// track parameters at each cluster are recomputed by the interface using Kalman filter + Smoother ///
+  /// (It can be changed by resetting the tracker in the interface with a new recoParam object)       ///
+  /// and the magnetic field set in the function prepare()                                            ///
+  /// ******************************************* WARNING ******************************************* ///
+  
+  Bool_t useESD = (strcmp(esdFileName,""));
+  Bool_t useRecPoints = (strcmp(inFileName,""));
+  if (!useESD && !useRecPoints) {
+    Error("MUONClusterInfo","you must provide ESD and/or galice root file(s)");
+    return;
+  }
   
   AliMUONClusterInfo* clusterInfo = new AliMUONClusterInfo();
   AliMUONPadInfo padInfo;
   AliMUONCalibrationData* calibData = 0x0;
   AliMUONESDInterface esdInterface;
+  AliMUONVClusterStore* clusterStore = 0x0;
+  AliMUONVDigitStore* digitStore = 0x0;
   
   // prepare the refitting during ESD->MUON conversion
   Prepare();
   
   // open the ESD file and tree and connect the ESD event
-  TFile* esdFile = TFile::Open(esdFileName);
-  TTree* esdTree = GetESDTree(esdFile);
-  AliESDEvent* esd = new AliESDEvent();
-  esd->ReadFromTree(esdTree);
+  TFile* esdFile = 0x0;
+  TTree* esdTree = 0x0;
+  AliESDEvent* esd = 0x0;
+  if (useESD) {
+    esdFile = TFile::Open(esdFileName);
+    esdTree = GetESDTree(esdFile);
+    esd = new AliESDEvent();
+    esd->ReadFromTree(esdTree);
+  }
+  
+  // get the cluster from RecPoints
+  AliRunLoader * rl = 0x0;
+  AliLoader* MUONLoader = 0x0;
+  if (useRecPoints) {
+    rl = AliRunLoader::Open(inFileName,"MUONLoader");
+    MUONLoader = rl->GetDetectorLoader("MUON");
+    MUONLoader->LoadRecPoints("READ");   
+    MUONLoader->LoadDigits("READ");
+  }
   
   // prepare the output tree
   gROOT->cd();
@@ -98,46 +132,161 @@ void MUONClusterInfo(Int_t nevents = -1, const char* esdFileName = "AliESDs.root
   // timer start...
   TStopwatch timer;
   
-  // Loop over ESD events
-  if (nevents > 0) nevents = TMath::Min(nevents,(Int_t)esdTree->GetEntries());
-  else nevents = (Int_t)esdTree->GetEntries();
+  // Loop over events
+  if (useESD) {
+    if (nevents > 0) nevents = TMath::Min(nevents,(Int_t)esdTree->GetEntries());
+    else nevents = (Int_t)esdTree->GetEntries();
+  } else {
+    if (nevents > 0) nevents = TMath::Min(nevents,(Int_t)rl->GetNumberOfEvents());
+    else nevents = (Int_t)rl->GetNumberOfEvents();
+  }
   for (Int_t iEvent = 0; iEvent < nevents; iEvent++) {
     
     //----------------------------------------------//
     // -------------- process event --------------- //
     //----------------------------------------------//
     // get the ESD of current event
-    esdTree->GetEvent(iEvent);
-    if (!esd) {
-      Error("CheckESD", "no ESD object found for event %d", iEvent);
-      return;
+    if (useESD) {
+      esdTree->GetEvent(iEvent);
+      if (!esd) {
+        Error("MUONClusterInfo", "no ESD object found for event %d", iEvent);
+        return;
+      }
+      // load the current esd event
+      esdInterface.LoadEvent(*esd);
+      // get digit store
+      if (!useRecPoints) digitStore = esdInterface.GetDigits();
     }
-    if (esd->GetNumberOfMuonTracks() < 1) continue;
     
-    // prepare access to calibration data
-    if (!calibData) calibData = new AliMUONCalibrationData(esd->GetESDRun()->GetRunNumber());
-    
-    // load the current event
-    esdInterface.LoadEvent(*esd);
+    if (useRecPoints) {
+      if (!(rl->GetEvent(iEvent) == 0)) {
+        Error("MUONClusterInfo", "unable to load event %d", iEvent);
+       return;
+      }
+      // get the clusters of current event
+      TTree* treeR = MUONLoader->TreeR();
+      clusterStore = AliMUONVClusterStore::Create(*treeR);
+      if ( clusterStore != 0x0 ) {
+       clusterStore->Clear();
+       clusterStore->Connect(*treeR);
+       treeR->GetEvent(0);
+      }
+      // get the digits of current event
+      TTree* treeD = MUONLoader->TreeD();
+      digitStore = AliMUONVDigitStore::Create(*treeD);
+      if ( digitStore != 0x0 ) {
+       digitStore->Clear();
+       digitStore->Connect(*treeD);
+       treeD->GetEvent(0);
+      }
+    }
     
-    // get digit store
-    AliMUONVDigitStore* digitStore = esdInterface.GetDigits();
+    // prepare access to calibration data
+    if (useESD && !calibData) calibData = new AliMUONCalibrationData(esd->GetESDRun()->GetRunNumber());
+    else if (!calibData) calibData = new AliMUONCalibrationData(rl->GetRunNumber());
     
     //----------------------------------------------//
     // ------------- fill cluster info ------------ //
     //----------------------------------------------//
-    // loop over the refitted tracks
-    TIter nextTrack(esdInterface.CreateTrackIterator());
-    AliMUONTrack* track;
-    while ((track = static_cast<AliMUONTrack*>(nextTrack()))) {
+    // --- loop over the refitted tracks ---
+    if (useESD) {
+      
+      TIter nextTrack(esdInterface.CreateTrackIterator());
+      AliMUONTrack* track;
+      while ((track = static_cast<AliMUONTrack*>(nextTrack()))) {
+       
+       UInt_t muonClusterMap = buildClusterMap(*track);
+       
+       // loop over clusters
+       AliMUONTrackParam* trackParam = static_cast<AliMUONTrackParam*>(track->GetTrackParamAtCluster()->First());
+       while (trackParam) {
+         clusterInfo->Clear("C");
+         
+         // fill cluster info
+         AliMUONVCluster* cluster = trackParam->GetClusterPtr();
+         clusterInfo->SetRunId(esd->GetRunNumber());
+         clusterInfo->SetEventId(iEvent);
+         clusterInfo->SetZ(cluster->GetZ());
+         clusterInfo->SetClusterId(cluster->GetUniqueID());
+         clusterInfo->SetClusterXY(cluster->GetX(), cluster->GetY());
+         clusterInfo->SetClusterXYErr(cluster->GetErrX(), cluster->GetErrY());
+         clusterInfo->SetClusterChi2(cluster->GetChi2());
+         clusterInfo->SetClusterCharge(cluster->GetCharge());
+         
+         // fill track info
+         clusterInfo->SetTrackId(track->GetUniqueID());
+         clusterInfo->SetTrackXY(trackParam->GetNonBendingCoor(), trackParam->GetBendingCoor());
+         clusterInfo->SetTrackThetaXY(TMath::ATan(trackParam->GetNonBendingSlope()), TMath::ATan(trackParam->GetBendingSlope()));
+         clusterInfo->SetTrackP(trackParam->P());
+         const TMatrixD paramCov = trackParam->GetCovariances();
+         clusterInfo->SetTrackXYErr(TMath::Sqrt(paramCov(0,0)), TMath::Sqrt(paramCov(2,2)));
+         clusterInfo->SetTrackChi2(track->GetNormalizedChi2());
+         clusterInfo->SetTrackCharge((Short_t)trackParam->GetCharge());
+         clusterInfo->SetTrackNHits(track->GetNClusters());
+         clusterInfo->SetTrackChamberHitMap(muonClusterMap);
+         
+         // fill pad info if available   
+         for (Int_t i=0; i<cluster->GetNDigits(); i++) {
+           AliMUONVDigit* digit = digitStore->FindObject(cluster->GetDigitId(i));
+           if (!digit) continue;
+           
+           // pad location
+           const AliMpVSegmentation* seg = AliMpSegmentation::Instance()->
+           GetMpSegmentation(digit->DetElemId(),AliMp::GetCathodType(digit->Cathode()));
+           AliMpPad pad = seg->PadByIndices(digit->PadX(), digit->PadY());
+           
+           // calibration parameters
+           AliMUONVCalibParam* ped = calibData->Pedestals(digit->DetElemId(), digit->ManuId());
+           AliMUONVCalibParam* gain = calibData->Gains(digit->DetElemId(), digit->ManuId());
+           Int_t manuChannel = digit->ManuChannel();
+           Int_t planeType = 0;
+           if ( digit->ManuId() & AliMpConstants::ManuMask(AliMp::kNonBendingPlane)) {
+             planeType = 1;
+           }
+           
+           // fill pad info
+           padInfo.SetPadId(digit->GetUniqueID());
+           padInfo.SetPadPlaneType(planeType);
+           padInfo.SetPadXY(pad.GetPositionX(), pad.GetPositionY());
+           padInfo.SetPadDimXY(pad.GetDimensionX(), pad.GetDimensionY());
+           padInfo.SetPadCharge((Double_t)digit->Charge());
+           padInfo.SetPadADC(digit->ADC());
+           padInfo.SetSaturated(digit->IsSaturated());
+           padInfo.SetCalibrated(digit->IsCalibrated());
+           padInfo.SetPedestal(ped->ValueAsFloatFast(manuChannel,0), ped->ValueAsFloatFast(manuChannel,1));
+           padInfo.SetGain(gain->ValueAsFloatFast(manuChannel,0), gain->ValueAsFloatFast(manuChannel,1),
+                           gain->ValueAsFloatFast(manuChannel,2), gain->ValueAsFloatFast(manuChannel,3));
+           
+           clusterInfo->AddPad(padInfo);
+         }
+         
+         // remove clusters attached to a track
+         if (useRecPoints) {
+           AliMUONVCluster* cl = clusterStore->FindObject(cluster->GetUniqueID());
+           if (cl) clusterStore->Remove(*cl);
+         }
+         
+         // fill cluster info tree
+         clusterInfoTree->Fill();
+         
+         trackParam = static_cast<AliMUONTrackParam*>(track->GetTrackParamAtCluster()->After(trackParam));
+       }
+       
+      }
+      
+    }
+    
+    // --- loop over clusters not attached to a track ---
+    if (useRecPoints) {
       
-      // loop over clusters
-      AliMUONTrackParam* trackParam = static_cast<AliMUONTrackParam*>(track->GetTrackParamAtCluster()->First());
-      while (trackParam) {
+      TIter nextCluster(clusterStore->CreateIterator());
+      AliMUONVCluster *cluster;
+      while ( ( cluster = static_cast<AliMUONVCluster*>(nextCluster()) ) ) {
+       
        clusterInfo->Clear("C");
        
        // fill cluster info
-       AliMUONVCluster* cluster = trackParam->GetClusterPtr();
+       clusterInfo->SetRunId(rl->GetRunNumber());
        clusterInfo->SetEventId(iEvent);
        clusterInfo->SetZ(cluster->GetZ());
        clusterInfo->SetClusterId(cluster->GetUniqueID());
@@ -146,16 +295,17 @@ void MUONClusterInfo(Int_t nevents = -1, const char* esdFileName = "AliESDs.root
        clusterInfo->SetClusterChi2(cluster->GetChi2());
        clusterInfo->SetClusterCharge(cluster->GetCharge());
        
-       // fill track info
-       clusterInfo->SetTrackId(track->GetUniqueID());
-       clusterInfo->SetTrackXY(trackParam->GetNonBendingCoor(), trackParam->GetBendingCoor());
-       clusterInfo->SetTrackThetaXY(TMath::ATan(trackParam->GetBendingSlope()), TMath::ATan(trackParam->GetNonBendingSlope()));
-       clusterInfo->SetTrackP(trackParam->P());
-       const TMatrixD paramCov = trackParam->GetCovariances();
-       clusterInfo->SetTrackXYErr(TMath::Sqrt(paramCov(0,0)), TMath::Sqrt(paramCov(2,2)));
-       clusterInfo->SetTrackChi2(track->GetNormalizedChi2());
-       clusterInfo->SetTrackCharge((Short_t)trackParam->GetCharge());
-
+       // fill dummy track info
+       clusterInfo->SetTrackId(0);
+       clusterInfo->SetTrackXY(0.,0.);
+       clusterInfo->SetTrackThetaXY(0.,0.);
+       clusterInfo->SetTrackP(0.);
+       clusterInfo->SetTrackXYErr(0.,0.);
+       clusterInfo->SetTrackChi2(0.);
+       clusterInfo->SetTrackCharge(0);
+       clusterInfo->SetTrackNHits(0);
+       clusterInfo->SetTrackChamberHitMap(0);
+       
        // fill pad info if available     
        for (Int_t i=0; i<cluster->GetNDigits(); i++) {
          AliMUONVDigit* digit = digitStore->FindObject(cluster->GetDigitId(i));
@@ -163,16 +313,21 @@ void MUONClusterInfo(Int_t nevents = -1, const char* esdFileName = "AliESDs.root
          
          // pad location
          const AliMpVSegmentation* seg = AliMpSegmentation::Instance()->
-           GetMpSegmentation(digit->DetElemId(),AliMp::GetCathodType(digit->Cathode()));
+         GetMpSegmentation(digit->DetElemId(),AliMp::GetCathodType(digit->Cathode()));
          AliMpPad pad = seg->PadByIndices(digit->PadX(), digit->PadY());
          
          // calibration parameters
          AliMUONVCalibParam* ped = calibData->Pedestals(digit->DetElemId(), digit->ManuId());
          AliMUONVCalibParam* gain = calibData->Gains(digit->DetElemId(), digit->ManuId());
          Int_t manuChannel = digit->ManuChannel();
+         Int_t planeType = 0;
+         if ( digit->ManuId() & AliMpConstants::ManuMask(AliMp::kNonBendingPlane)) {
+           planeType = 1;
+         }
          
          // fill pad info
          padInfo.SetPadId(digit->GetUniqueID());
+         padInfo.SetPadPlaneType(planeType);
          padInfo.SetPadXY(pad.GetPositionX(), pad.GetPositionY());
          padInfo.SetPadDimXY(pad.GetDimensionX(), pad.GetDimensionY());
          padInfo.SetPadCharge((Double_t)digit->Charge());
@@ -189,9 +344,11 @@ void MUONClusterInfo(Int_t nevents = -1, const char* esdFileName = "AliESDs.root
        // fill cluster info tree
        clusterInfoTree->Fill();
        
-       trackParam = static_cast<AliMUONTrackParam*>(track->GetTrackParamAtCluster()->After(trackParam));
       }
       
+      delete digitStore;
+      delete clusterStore;
+      
     }
     
   }
@@ -212,30 +369,25 @@ void MUONClusterInfo(Int_t nevents = -1, const char* esdFileName = "AliESDs.root
   delete calibData;
   printf("Deleting clusterInfo\n");
   delete clusterInfo;
-  printf("Closing esdFile\n");
-  esdFile->Close();
-  printf("Deleting esd\n");
-  delete esd;
-  //  delete padInfo;
+  if (useRecPoints) {
+    MUONLoader->UnloadDigits();
+    MUONLoader->UnloadRecPoints();
+    delete rl;
+  }
+  if (useESD) {
+    esdFile->Close();
+    delete esd;
+  }
   cout<<endl<<"time to fill cluster/track info: R:"<<timer.RealTime()<<" C:"<<timer.CpuTime()<<endl<<endl;
 }
 
 //-----------------------------------------------------------------------
 void Prepare()
 {
-  /// Set the geometry, the magnetic field, the mapping and the reconstruction parameters
+  /// Set the magnetic field, the mapping and the reconstruction parameters
   
   gRandom->SetSeed(0);
   
-  // Import TGeo geometry (needed for track extrapolation)
-  if (!gGeoManager) {
-    AliGeomManager::LoadGeometry("geometry.root");
-    if (!gGeoManager) {
-      Error("MUONRefit", "getting geometry from file %s failed", "generated/galice.root");
-      return;
-    }
-  }
-  
   // set mag field
   if (!TGeoGlobalMagField::Instance()->GetField()) {
     printf("Loading field map...\n");
@@ -248,14 +400,14 @@ void Prepare()
   man->SetDefaultStorage("local://$ALICE_ROOT/OCDB");
   man->SetRun(0);
   if ( ! AliMpCDB::LoadDDLStore() ) {
-    Error("MUONRefit","Could not access mapping from OCDB !");
+    Error("Prepare","Could not access mapping from OCDB !");
     exit(-1);
   }
   
   // Reset the reconstruction parameters for track refitting if needed
   // (by default will use Kalman filter + Smoother)
-//  AliMUONRecoParam *muonRecoParam = AliMUONRecoParam::GetLowFluxParam();
-//  AliMUONESDInterface::ResetTracker(muonRecoParam);
+  //  AliMUONRecoParam *muonRecoParam = AliMUONRecoParam::GetLowFluxParam();
+  //  AliMUONESDInterface::ResetTracker(muonRecoParam);
   
 }
 
@@ -280,3 +432,23 @@ TTree* GetESDTree(TFile *esdFile)
   
 }
 
+      
+//-----------------------------------------------------------------------
+UInt_t buildClusterMap(AliMUONTrack &track)
+{
+  /// Build the map of clusters in tracking chambers
+  
+  UInt_t muonClusterMap = 0;
+  
+  AliMUONTrackParam* trackParam = static_cast<AliMUONTrackParam*>(track.GetTrackParamAtCluster()->First());
+  while (trackParam) {
+    
+    muonClusterMap |= BIT(trackParam->GetClusterPtr()->GetChamberId());
+    
+    trackParam = static_cast<AliMUONTrackParam*>(track.GetTrackParamAtCluster()->After(trackParam));
+  }
+  
+  return muonClusterMap;
+  
+}
+