X-Git-Url: http://git.uio.no/git/?a=blobdiff_plain;f=MUON%2FAliMUONTracker.cxx;h=7af60833eb67139b9c945eb0d677f6878d274cdb;hb=716ccba730076136b23f8c72e8be85ee1f3766e5;hp=6f192fb6680c5c64f55b691c1b53a49729ec95c5;hpb=196471e99c253cf039813065e4a8221982fe54d0;p=u%2Fmrichter%2FAliRoot.git diff --git a/MUON/AliMUONTracker.cxx b/MUON/AliMUONTracker.cxx index 6f192fb6680..7af60833eb6 100644 --- a/MUON/AliMUONTracker.cxx +++ b/MUON/AliMUONTracker.cxx @@ -13,78 +13,409 @@ * provided "as is" without express or implied warranty. * **************************************************************************/ +/* $Id$ */ + +//----------------------------------------------------------------------------- +/// \class AliMUONTracker +/// +/// Steering class for use in global tracking framework; +/// reconstruct tracks from recpoints +/// +/// Actual tracking is performed by some AliMUONVTrackReconstructor children +/// Tracking modes (ORIGINAL, KALMAN) and associated options and parameters can be changed +/// through the AliMUONRecoParam object set in the reconstruction macro or read from the CDB +/// (see methods in AliMUONRecoParam.h file for details) +/// +/// \author Christian Finck and Laurent Aphecetche, SUBATECH Nantes +//----------------------------------------------------------------------------- #include "AliMUONTracker.h" -#include "AliMUONTrackReconstructorK.h" + +#include "AliCodeTimer.h" +#include "AliESDEvent.h" +#include "AliESDMuonTrack.h" +#include "AliESDVertex.h" +#include "AliLog.h" +#include "AliMUONClusterStoreV2.h" +#include "AliMUONESDInterface.h" +#include "AliMUONLegacyClusterServer.h" +#include "AliMUONRecoParam.h" +#include "AliMUONReconstructor.h" +#include "AliMUONTrack.h" +#include "AliMUONTrackExtrap.h" +#include "AliMUONTrackHitPattern.h" +#include "AliMUONTrackParam.h" #include "AliMUONTrackReconstructor.h" -#include "AliMUONData.h" +#include "AliMUONTrackReconstructorK.h" +#include "AliMUONTrackStoreV1.h" +#include "AliMUONTriggerTrackStoreV1.h" +#include "AliMUONTriggerTrack.h" +#include "AliMUONLocalTrigger.h" +#include "AliMUONVClusterServer.h" +#include "AliMUONVDigitStore.h" +#include "AliMUONVTriggerStore.h" +#include "AliMUONTriggerUtilities.h" +#include +#include +#include #include "AliLog.h" +/// \cond CLASSIMP +ClassImp(AliMUONTracker) +/// \endcond + + //_____________________________________________________________________________ -AliMUONTracker::AliMUONTracker() - : AliTracker(), - fTriggerCircuit(0x0), - fMUONData(0x0), - fTrackReco(0x0) +AliMUONTracker::AliMUONTracker(const AliMUONRecoParam* recoParam, + AliMUONVClusterServer* clusterServer, + AliMUONVDigitStore& digitStore, + const AliMUONGeometryTransformer* transformer, + const AliMUONTriggerCircuit* triggerCircuit, + const AliMUONTriggerUtilities* triggerUtilities) +: AliTracker(), +fkTransformer(transformer), // not owner +fkTriggerCircuit(triggerCircuit), // not owner +fTrackHitPatternMaker(0x0), +fTrackReco(0x0), +fClusterStore(0x0), +fTriggerStore(0x0), +fClusterServer(clusterServer), +fIsOwnerOfClusterServer(kFALSE), +fkDigitStore(digitStore), // not owner +fInputClusterStore(0x0), +fTriggerTrackStore(0x0), +fkRecoParam(recoParam), +fInternalTrackStore(0x0) { /// constructor - + + if (fkTransformer) + fTrackHitPatternMaker = new AliMUONTrackHitPattern(recoParam,*fkTransformer,fkDigitStore,triggerUtilities); + + if (!fClusterServer) + { + AliDebug(1,"No cluster server given. Will use AliMUONLegacyClusterServer"); + fIsOwnerOfClusterServer = kTRUE; + } + else + { + TIter next(fkDigitStore.CreateIterator()); + fClusterServer->UseDigits(next,&digitStore); + + SetupClusterServer(*fClusterServer); + } } + //_____________________________________________________________________________ AliMUONTracker::~AliMUONTracker() { - /// dtr + /// dtor + delete fTrackReco; + delete fTrackHitPatternMaker; + delete fClusterStore; + delete fTriggerStore; + if ( fIsOwnerOfClusterServer ) delete fClusterServer; + delete fInputClusterStore; + delete fTriggerTrackStore; + delete fInternalTrackStore; } //_____________________________________________________________________________ -void AliMUONTracker::SetOption(Option_t* option) +AliMUONVClusterStore* +AliMUONTracker::ClusterStore() const { - /// set reconstructor class + /// Return (and create if necessary) the cluster container + if (!fClusterStore) + { + fClusterStore = new AliMUONClusterStoreV2; + } + return fClusterStore; +} - if (!fMUONData) - AliError("MUONData not defined"); +//_____________________________________________________________________________ +AliMUONVTriggerTrackStore* +AliMUONTracker::TriggerTrackStore() const +{ + /// Return (and create if necessary) the trigger track container + if (!fTriggerTrackStore) + { + fTriggerTrackStore = new AliMUONTriggerTrackStoreV1; + } + return fTriggerTrackStore; +} - if (!fTriggerCircuit) - AliError("TriggerCircuit not defined"); +//_____________________________________________________________________________ +Int_t AliMUONTracker::LoadClusters(TTree* clustersTree) +{ + /// Load triggerStore from clustersTree - if (strstr(option,"Original")) - fTrackReco = new AliMUONTrackReconstructor(fMUONData); - else if (strstr(option,"Combi")) - fTrackReco = new AliMUONTrackReconstructorK(fMUONData,"Combi"); - else - fTrackReco = new AliMUONTrackReconstructorK(fMUONData,"Kalman"); + if ( ! clustersTree ) { + AliFatal("No clustersTree"); + return 1; + } - fTrackReco->SetTriggerCircuit(fTriggerCircuit); + if ( !fTriggerStore ) + { + fTriggerStore = AliMUONVTriggerStore::Create(*clustersTree); + } + + if (!fTriggerStore) + { + AliError("Could not get triggerStore"); + return 2; + } + + if (!fInputClusterStore) + { + fInputClusterStore = AliMUONVClusterStore::Create(*clustersTree); + if (!fInputClusterStore) + { + AliError("Could not get clusterStore"); + return 3; + } + AliDebug(1,Form("Created %s from cluster tree",fInputClusterStore->ClassName())); + } + + if ( !fClusterServer && fIsOwnerOfClusterServer ) + { + if ( !fClusterServer ) + { + fClusterServer = new AliMUONLegacyClusterServer(*fkTransformer,fInputClusterStore, + GetRecoParam()->BypassSt4(), + GetRecoParam()->BypassSt5()); + SetupClusterServer(*fClusterServer); + } + } + + fInputClusterStore->Clear(); + fInputClusterStore->Connect(*clustersTree,kFALSE); + fTriggerStore->Clear(); + fTriggerStore->Connect(*clustersTree,kFALSE); + + clustersTree->GetEvent(0); + + return 0; } //_____________________________________________________________________________ -Int_t AliMUONTracker::Clusters2Tracks(AliESD* /*esd*/) +Int_t AliMUONTracker::Clusters2Tracks(AliESDEvent* esd) { + /// Performs the tracking and store the resulting tracks in the ESD + /// + /// note that we're dealing with two cluster stores here : fInputClusterStore + /// and ClusterStore(). + /// The first one is read from the TreeR and may be used by the cluster server + /// (that's the case for the legacy cluster server) to fill the other one. + /// The second one is more dynamic and might be created on the fly by the cluster + /// server (used by the combined tracking, in which case the first one is not used + /// at all). + + AliCodeTimerAuto("",0) + + if (!fTrackReco) + { + fTrackReco = CreateTrackReconstructor(GetRecoParam(),fClusterServer); + fInternalTrackStore = new AliMUONTrackStoreV1; + } + + // if the required tracking mode does not exist + if (!fTrackReco) return 1; + + if ( ! ClusterStore() ) + { + AliError("ClusterStore is NULL"); + return 2; + } + + if (!fTriggerStore) { + AliError("TriggerStore is NULL"); + return 3; + } + + // Make trigger tracks + if ( fkTriggerCircuit ) + { + TriggerTrackStore()->Clear(); + fTrackReco->EventReconstructTrigger(*fkTriggerCircuit,*fTriggerStore,*(TriggerTrackStore())); + } + + if ( TriggerTrackStore()->GetSize() > GetRecoParam()->GetMaxTriggerTracks() ) + { + // cut to reject shower events + + AliCodeTimerAuto("MUON Shower events",1); - /// clusters2Tracks method - /// in general tracking framework - - // open TClonesArray for reading - fMUONData->SetTreeAddress("TC,RC"); - - // open for writing - // trigger branch - fMUONData->MakeBranch("RL"); //trigger track - fMUONData->SetTreeAddress("RL"); - fTrackReco->EventReconstructTrigger(); - fMUONData->Fill("RL"); - - // tracking branch - fMUONData->MakeBranch("RT"); //track - fMUONData->SetTreeAddress("RT"); - fTrackReco->EventReconstruct(); - fMUONData->Fill("RT"); - - fMUONData->ResetRecTracks(); - fMUONData->ResetRecTriggerTracks(); - - - return kTRUE; + AliWarning(Form("Probably got a shower event (%d trigger tracks). Will not reconstruct tracks.", + TriggerTrackStore()->GetSize())); + + return 0; + } + + fTrackReco->EventReconstruct(*(ClusterStore()),*fInternalTrackStore); + + // Match tracker/trigger tracks + if ( fTrackHitPatternMaker ) + { + fTrackReco->ValidateTracksWithTrigger(*fInternalTrackStore,*(TriggerTrackStore()),*fTriggerStore,*fTrackHitPatternMaker); + } + + // Fill ESD + FillESD(*fInternalTrackStore,esd); + + fInternalTrackStore->Clear(); + ClusterStore()->Clear(); + + return 0; } + +//_____________________________________________________________________________ +void AliMUONTracker::FillESD(const AliMUONVTrackStore& trackStore, AliESDEvent* esd) const +{ + /// Fill the ESD from the trackStore + AliDebug(1,""); + AliCodeTimerAuto("",0) + + // get ITS vertex + Double_t vertex[3] = {0., 0., 0.}; + const AliESDVertex* esdVert = esd->GetVertex(); + if (esdVert->GetNContributors() > 0 || !strcmp(esdVert->GetTitle(),"vertexer: smearMC")) { + esdVert->GetXYZ(vertex); + AliDebug(1,Form("found vertex (%e,%e,%e)",vertex[0],vertex[1],vertex[2])); + } + + // fill ESD event including all info in ESD cluster if required and only for the given fraction of events + AliMUONTrack* track; + AliMUONLocalTrigger* locTrg; + TIter next(trackStore.CreateIterator()); + if (GetRecoParam()->SaveFullClusterInESD() && + gRandom->Uniform(100.) <= GetRecoParam()->GetPercentOfFullClusterInESD()) { + + while ( ( track = static_cast(next()) ) ) { + + if (track->GetMatchTrigger() > 0) { + locTrg = static_cast(fTriggerStore->FindLocal(track->LoCircuit())); + AliMUONESDInterface::MUONToESD(*track, *esd, vertex, &fkDigitStore, locTrg); + } else AliMUONESDInterface::MUONToESD(*track, *esd, vertex, &fkDigitStore); + + } + + } else { + + while ( ( track = static_cast(next()) ) ) { + + if (track->GetMatchTrigger() > 0) { + locTrg = static_cast(fTriggerStore->FindLocal(track->LoCircuit())); + AliMUONESDInterface::MUONToESD(*track, *esd, vertex, 0x0, locTrg); + } else AliMUONESDInterface::MUONToESD(*track, *esd, vertex); + + } + + } + + // fill the local trigger decisions not matched with tracks (associate them to "ghost" tracks) + UInt_t ghostId = 0xFFFFFFFF - 1; + Bool_t matched = kFALSE; + AliMUONTriggerTrack *triggerTrack; + TIter itTriggerTrack(fTriggerTrackStore->CreateIterator()); + while ( ( triggerTrack = static_cast(itTriggerTrack()) ) ) { + + locTrg = static_cast(fTriggerStore->FindLocal(triggerTrack->GetLoTrgNum())); + + // check if this local trigger has already been matched + TIter itTrack(trackStore.CreateIterator()); + while ( ( track = static_cast(itTrack()) ) ) { + matched = (track->LoCircuit() == locTrg->LoCircuit()); + if (matched) break; + } + if (matched) continue; + + AliMUONESDInterface::MUONToESD(*locTrg, *esd, ghostId, triggerTrack); + + ghostId -= 1; + } + +} + +//_____________________________________________________________________________ +AliMUONVTrackReconstructor* AliMUONTracker::CreateTrackReconstructor(const AliMUONRecoParam* recoParam, AliMUONVClusterServer* clusterServer) +{ + /// Create track reconstructor, depending on tracking mode set in RecoParam + + AliMUONVTrackReconstructor* trackReco(0x0); + + TString opt(recoParam->GetTrackingMode()); + opt.ToUpper(); + + if (strstr(opt,"ORIGINAL")) + { + trackReco = new AliMUONTrackReconstructor(recoParam,clusterServer); + } + else if (strstr(opt,"KALMAN")) + { + trackReco = new AliMUONTrackReconstructorK(recoParam,clusterServer); + } + else + { + AliErrorClass(Form("tracking mode \"%s\" does not exist",opt.Data())); + return 0x0; + } + + AliDebugClass(1,Form("Will use %s for tracking",trackReco->ClassName())); + + return trackReco; +} + +//_____________________________________________________________________________ +void AliMUONTracker::UnloadClusters() +{ + /// Clear internal clusterStore + + fInputClusterStore->Clear(); +} + + +//_____________________________________________________________________________ +void +AliMUONTracker::SetupClusterServer(AliMUONVClusterServer& clusterServer) +{ + /// Setup the cluster server + + if ( GetRecoParam()->BypassSt4() || + GetRecoParam()->BypassSt5() ) + { + Bool_t ok = clusterServer.UseTriggerTrackStore(TriggerTrackStore()); + + TString msg1; + TString msg2; + + if ( GetRecoParam()->BypassSt45() ) + { + msg1 = "STATIONS 4 AND 5"; + msg2 = "THOSE TWO STATIONS"; + } + else if ( GetRecoParam()->BypassSt4() ) + { + msg1 = "STATION 4"; + msg2 = "THAT STATION"; + } + else if ( GetRecoParam()->BypassSt5() ) + { + msg1 = "STATION 5"; + msg2 = "THAT STATION"; + } + + if ( ok ) + { + AliWarning(Form("WILL USE TRIGGER TRACKS TO GENERATE CLUSTERS IN %s, " + "THUS BYPASSING REAL CLUSTERS IN %s!!!",msg1.Data(),msg2.Data())); + } + else + { + AliWarning("BYPASSING OF ST4 AND/OR 5 REQUESTED, BUT CLUSTERSERVER DOES NOT SEEM TO SUPPORT IT !!!"); + } + } +} + +