1 /**************************************************************************
2 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
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 **************************************************************************/
17 ///////////////////////////////////////////////////////////////////////////////
19 // TRD tender: reapply pid on the fly //
21 ///////////////////////////////////////////////////////////////////////////////
25 #include <TObjString.h>
29 #include <AliCDBEntry.h>
31 #include <AliCDBManager.h>
32 #include <AliTRDCalDet.h>
38 #include <AliVEvent.h>
39 #include <AliESDEvent.h>
40 #include <AliESDpid.h>
41 #include <AliESDtrack.h>
42 #include <AliESDInputHandler.h>
43 #include <AliAnalysisManager.h>
44 #include <AliTRDPIDReference.h>
45 #include <AliTRDPIDResponse.h>
46 #include <AliTender.h>
48 #include "AliTRDTenderSupply.h"
50 ClassImp(AliTRDTenderSupply)
52 //_____________________________________________________
53 AliTRDTenderSupply::AliTRDTenderSupply() :
57 fChamberGainOld(NULL),
58 fChamberGainNew(NULL),
59 fChamberVdriftOld(NULL),
60 fChamberVdriftNew(NULL),
63 fNormalizationFactor(1.),
66 fGainCorrection(kTRUE),
67 fLoadReferencesFromCDB(kFALSE),
68 fHasReferences(kFALSE)
75 //_____________________________________________________
76 AliTRDTenderSupply::AliTRDTenderSupply(const char *name, const AliTender *tender) :
77 AliTenderSupply(name,tender),
80 fChamberGainOld(NULL),
81 fChamberGainNew(NULL),
82 fChamberVdriftOld(NULL),
83 fChamberVdriftNew(NULL),
86 fNormalizationFactor(1.),
89 fGainCorrection(kTRUE),
90 fLoadReferencesFromCDB(kFALSE),
91 fHasReferences(kFALSE)
96 memset(fBadChamberID, 0, sizeof(Int_t) * kNChambers);
99 //_____________________________________________________
100 AliTRDTenderSupply::~AliTRDTenderSupply()
107 //_____________________________________________________
108 void AliTRDTenderSupply::Init()
111 // Initialise TRD tender
114 AliAnalysisManager *mgr=AliAnalysisManager::GetAnalysisManager();
116 // 1DLQ PID implemented in the AliESD object
117 fESDpid=fTender->GetESDhandler()->GetESDpid();
119 fESDpid=new AliESDpid;
120 fTender->GetESDhandler()->SetESDpid(fESDpid);
123 if(!fLoadReferencesFromCDB) LoadReferences();
124 fESDpid->GetTRDResponse().SetGainNormalisationFactor(fNormalizationFactor);
126 // Set Normalisation Factors
127 if(mgr->GetMCtruthEventHandler()){
129 //fESDpid->GetTRDResponse().SetGainNormalisationFactor(1.);
130 SwitchOffGainCorrection();
134 //if(fPIDmethod == kNNpid) fPidRecal->SetGainScaleFactor(1.14);
135 //fESDpid->GetTRDResponse().SetGainNormalisationFactor(1.14);
136 SwitchOnGainCorrection();
140 //_____________________________________________________
141 void AliTRDTenderSupply::ProcessEvent()
144 // Reapply pid information
146 if (fTender->RunChanged()){
147 AliDebug(0, Form("AliTPCTenderSupply::ProcessEvent - Run Changed (%d)\n",fTender->GetRun()));
148 if (fGainCorrection) SetChamberGain();
149 if(!fHasReferences) LoadReferences();
152 fESD = fTender->GetEvent();
154 Int_t ntracks=fESD->GetNumberOfTracks();
157 // recalculate PID probabilities
159 for(Int_t itrack = 0; itrack < ntracks; itrack++){
160 AliESDtrack *track=fESD->GetTrack(itrack);
161 // Recalculate likelihoods
162 if(!(track->GetStatus() & AliESDtrack::kTRDout)) continue;
163 if(fGainCorrection) ApplyGainCorrection(track);
168 fESDpid->MakeTRDPID(fESD->GetTrack(itrack));
171 AliError("PID Method not implemented (yet)");
176 //_____________________________________________________
177 void AliTRDTenderSupply::LoadReferences(){
179 // Load Reference from the OCDB/OADB into the PID Response
181 if(fLoadReferencesFromCDB){
182 AliDebug(1, "Loading Reference Distributions from the OCDB");
183 AliCDBEntry *en = fTender->GetCDBManager()->Get("TRD/Calib/PIDLQ1D");
185 AliError("References for 1D Likelihood Method not in OCDB");
189 TObjArray *arr = dynamic_cast<TObjArray *>(en->GetObject());
190 if(!arr) AliError("List with the references not found");
192 // Get new references
195 AliTRDPIDReference *ref = NULL;
197 if(!TString(o->IsA()->GetName()).CompareTo("AliTRDPIDReference")){
198 ref = dynamic_cast<AliTRDPIDReference *>(o);
203 fESDpid->GetTRDResponse().Load(ref);
204 fHasReferences = kTRUE;
205 AliInfo("Reference distributions loaded into the PID Response");
207 AliError("References not found");
210 // Backward compatibility mode
211 AliInfo("Loading Reference Distributions from ROOT file");
212 if(fRefFilename.Length() != 0){
213 fESDpid->GetTRDResponse().Load(fRefFilename.Data());
214 fHasReferences = kTRUE;
216 AliError("No file defined");
221 //_____________________________________________________
222 void AliTRDTenderSupply::SetChamberGain(){
224 // Load Chamber Gain factors into the Tender supply
227 //find previous entry from the UserInfo
228 TTree *tree=((TChain*)fTender->GetInputData(0))->GetTree();
230 AliError("Tree not found in ESDhandler");
234 TList *userInfo=(TList*)tree->GetUserInfo();
236 AliError("No UserInfo found in tree");
240 TList *cdbList=(TList*)userInfo->FindObject("cdbList");
242 AliError("No cdbList found in UserInfo");
243 if (AliLog::GetGlobalLogLevel()>=AliLog::kError) userInfo->Print();
247 TIter nextCDB(cdbList);
249 while ( (os=(TObjString*)nextCDB()) ){
250 if(os->GetString().Contains("TRD/Calib/ChamberGainFactor")){
251 // Get Old gain calibration
252 AliCDBId *id=AliCDBId::MakeFromString(os->GetString());
254 AliCDBEntry *entry=fTender->GetCDBManager()->Get(id->GetPath(), id->GetFirstRun(), id->GetVersion());
256 AliError("No previous gain calibration entry found");
260 fChamberGainOld = dynamic_cast<AliTRDCalDet *>(entry->GetObject());
262 AliDebug(1, Form("Used old Gain entry: %s\n",entry->GetId().ToString().Data()));
263 } else if(os->GetString().Contains("TRD/Calib/ChamberVdrift")){
264 // Get Old drift velocity calibration
265 AliCDBId *id=AliCDBId::MakeFromString(os->GetString());
267 AliCDBEntry *entry=fTender->GetCDBManager()->Get(id->GetPath(), id->GetFirstRun(), id->GetVersion());
269 AliError("No previous drift velocity calibration entry found");
273 fChamberVdriftOld = dynamic_cast<AliTRDCalDet *>(entry->GetObject());
275 AliDebug(1, Form("Used old Drift velocity entry: %s\n",entry->GetId().ToString().Data()));
280 // Get Latest Gain Calib Object
281 AliCDBEntry *entryNew=fTender->GetCDBManager()->Get("TRD/Calib/ChamberGainFactor",fTender->GetRun());
283 AliDebug(1, Form("Used new Gain entry: %s\n",entryNew->GetId().ToString().Data()));
284 fChamberGainNew = dynamic_cast<AliTRDCalDet *>(entryNew->GetObject());
286 AliError("No new gain calibration entry found");
288 // Also get the latest Drift Velocity calibration object
289 entryNew=fTender->GetCDBManager()->Get("TRD/Calib/ChamberVdrift",fTender->GetRun());
291 AliDebug(1, Form("Used new Drift velocity entry: %s\n",entryNew->GetId().ToString().Data()));
292 fChamberVdriftNew = dynamic_cast<AliTRDCalDet *>(entryNew->GetObject());
294 AliError("No new drift velocity calibration entry found");
296 if(!fChamberGainNew || !fChamberVdriftNew) AliError("No recent calibration found");
299 //_____________________________________________________
300 void AliTRDTenderSupply::ApplyGainCorrection(AliESDtrack * track){
302 // Apply new gain factors to the track
304 if(!fChamberGainNew || !fChamberGainOld){
305 AliError("Cannot apply gain correction.");
309 if(!(track->GetStatus() & AliESDtrack::kTRDout)) return;
310 Double_t p = track->GetOuterParam() ? track->GetOuterParam()->P() : track->P();
311 if(p < fPthreshold) return; // Apply low momentum cutoff
313 Bool_t applyCorrectionVdrift = kFALSE;
314 if(fChamberVdriftOld && fChamberVdriftNew) applyCorrectionVdrift = kTRUE;
316 Int_t chamberID[kNPlanes];
317 for(Int_t il = 0; il < kNPlanes; il++) chamberID[il] = -1;
318 if(!GetTRDchamberID(track, chamberID)) return;
319 Int_t nTrackletsPID = 0, nTracklets = track->GetTRDntracklets();
320 for(Int_t iplane = 0; iplane < kNPlanes; iplane++){
321 if(chamberID[iplane] < 0) continue;
323 // Mask out bad chambers
324 Bool_t isMasked = kFALSE;
325 for(UInt_t icam = 0; icam < fNBadChambers; icam++)
326 if(fBadChamberID[icam] == chamberID[iplane]){
331 for(Int_t islice = 0; islice < track->GetNumberOfTRDslices(); islice++){
332 track->SetTRDslice(0, iplane, islice);
337 // Take old and new gain factor and make ratio
338 Double_t facOld = fChamberGainOld->GetValue(chamberID[iplane]);
339 Double_t facNew = fChamberGainNew->GetValue(chamberID[iplane]);
340 Double_t correction = facNew/facOld;
341 if(applyCorrectionVdrift){
342 // apply also correction for drift velocity calibration
343 Double_t vDriftOld = fChamberVdriftOld->GetValue(chamberID[iplane]);
344 Double_t vDriftNew = fChamberVdriftNew->GetValue(chamberID[iplane]);
345 correction *= vDriftNew/vDriftOld;
347 AliDebug(2, Form("Applying correction factor %f\n", correction));
349 for(Int_t islice = 0; islice < track->GetNumberOfTRDslices(); islice++){
350 Double_t qslice = track->GetTRDslice(iplane, islice);
351 if(qslice <= 0.) continue;
352 track->SetTRDslice(qslice / correction, iplane, islice);
355 if(nSlices) nTrackletsPID++;
357 // Use nTrackletsPID to indicate the number of tracklets from good
358 // chambers so they are used for the PID
359 track->SetTRDntracklets(nTrackletsPID | (nTracklets << 3));
362 //_____________________________________________________
363 Bool_t AliTRDTenderSupply::GetTRDchamberID(AliESDtrack * const track, Int_t *detectors) {
365 // Calculate TRD chamber ID
367 Double_t xLayer[kNPlanes] = {300.2, 312.8, 325.4, 338., 350.6, 363.2};
368 Double_t etamin[kNStacks] = {0.536, 0.157, -0.145, -0.527,-0.851};
369 Double_t etamax[kNStacks] = {0.851, 0.527, 0.145, -0.157,-0.536};
370 for(Int_t ily = 0; ily < kNPlanes; ily++) detectors[ily] = -1;
372 const AliExternalTrackParam *trueparam = NULL;
373 if(track->GetTPCInnerParam()) trueparam = track->GetTPCInnerParam();
374 else if(track->GetOuterParam()) trueparam = track->GetOuterParam();
375 else if(track->GetInnerParam()) trueparam = track->GetInnerParam();
377 AliDebug(2, "No Track Params");
381 AliExternalTrackParam workparam(*trueparam); // Do calculation on working Copy
384 for(Int_t ily = 0; ily < kNPlanes; ily++){
385 if(!workparam.PropagateTo(xLayer[ily], fESD->GetMagneticField())) {
386 AliDebug(2, "Propagation failed");
389 workparam.GetXYZ(pos);
390 Double_t trackAlpha = TMath::ATan2(pos[1], pos[0]);
391 if(trackAlpha < 0) trackAlpha = 2 * TMath::Pi() + trackAlpha;
392 Double_t secAlpha = 2 * TMath::Pi() / 18.;
394 Int_t sector = static_cast<Int_t>(trackAlpha/secAlpha);
395 Double_t etaTrack = track->Eta();
397 for(Int_t istack = 0; istack < 5; istack++){
398 if(etaTrack >= etamin[istack] && etaTrack <= etamax[istack]){
404 AliDebug(2, "Dead Area");
408 detectors[ily] = sector * kNStacks * kNPlanes + stack * kNPlanes + ily;
411 return nDet ? kTRUE : kFALSE;