1 /* $Id: AliTriggerAnalysis.cxx 35782 2009-10-22 11:54:31Z jgrosseo $ */
3 /**************************************************************************
4 * Copyright(c) 1998-2009, ALICE Experiment at CERN, All rights reserved. *
6 * Author: The ALICE Off-line Project. *
7 * Contributors are mentioned in the code where appropriate. *
9 * Permission to use, copy, modify and distribute this software and its *
10 * documentation strictly for non-commercial purposes is hereby granted *
11 * without fee, provided that the above copyright notice appears in all *
12 * copies and that both the copyright notice and this permission notice *
13 * appear in the supporting documentation. The authors make no claims *
14 * about the suitability of this software for any purpose. It is *
15 * provided "as is" without express or implied warranty. *
16 **************************************************************************/
18 //-------------------------------------------------------------------------
19 // Implementation of Class AliTriggerAnalysis
20 // This class provides function to check if events have been triggered based on the data in the ESD
21 // The trigger bits, trigger class inputs and only the data (offline trigger) can be used
22 // Origin: Jan Fiete Grosse-Oetringhaus, CERN
23 //-------------------------------------------------------------------------
25 #include <Riostream.h>
29 #include <TIterator.h>
30 #include "TParameter.h"
34 #include <AliTriggerAnalysis.h>
37 #include <AliAnalysisManager.h>
39 #include <AliESDEvent.h>
41 #include <AliMultiplicity.h>
42 #include <AliESDVZERO.h>
43 #include <AliESDZDC.h>
44 #include <AliESDFMD.h>
45 #include <AliESDVertex.h>
46 #include <AliESDtrackCuts.h>
48 ClassImp(AliTriggerAnalysis)
50 AliTriggerAnalysis::AliTriggerAnalysis() :
58 fZDCCutRefSum(-568.5),
59 fZDCCutRefDelta(-2.1),
60 fZDCCutSigmaSum(3.25),
61 fZDCCutSigmaDelta(2.25),
62 fZDCCutRefSumCorr(-65.5),
63 fZDCCutRefDeltaCorr(-2.1),
64 fZDCCutSigmaSumCorr(6.0),
65 fZDCCutSigmaDeltaCorr(1.2),
66 fZDCCutZNATimeCorr(2.0),
67 fZDCCutZNCTimeCorr(5.0),
95 AliTriggerAnalysis::~AliTriggerAnalysis()
105 if (fHistFiredBitsSPD)
107 delete fHistFiredBitsSPD;
108 fHistFiredBitsSPD = 0;
111 if (fHistSPDClsVsTrk)
113 delete fHistSPDClsVsTrk;
114 fHistSPDClsVsTrk = 0;
144 if (fHistTimeCorrZDC)
146 delete fHistTimeCorrZDC;
147 fHistTimeCorrZDC = 0;
164 delete fHistFMDSingle;
182 fTriggerClasses->DeleteAll();
183 delete fTriggerClasses;
188 delete fEsdTrackCuts;
193 void AliTriggerAnalysis::EnableHistograms()
195 // creates the monitoring histograms
197 // do not add this hists to the directory
198 Bool_t oldStatus = TH1::AddDirectoryStatus();
199 TH1::AddDirectory(kFALSE);
201 fHistBitsSPD = new TH2F("fHistBitsSPD", "SPD GFO;number of fired chips (offline);number of fired chips (hardware)", 1202, -1.5, 1200.5, 1202, -1.5, 1200.5);
202 fHistFiredBitsSPD = new TH1F("fHistFiredBitsSPD", "SPD GFO Hardware;chip number;events", 1200, -0.5, 1199.5);
203 fHistSPDClsVsTrk = new TH2F("fHistSPDClsVsTrk", "SPD Clusters vs Tracklets", 300, -0.5, 2999.5, 1000, -0.5, 9999.5);
204 fHistV0A = new TH1F("fHistV0A", "V0A;leading time (ns);events", 400, -100, 100);
205 fHistV0C = new TH1F("fHistV0C", "V0C;leading time (ns);events", 400, -100, 100);
206 fHistZDC = new TH1F("fHistZDC", "ZDC;trigger bits;events", 8, -1.5, 6.5);
207 fHistTDCZDC = new TH1F("fHistTDCZDC", "ZDC;TDC bits;events", 32, -0.5, 32-0.5);
208 fHistTimeZDC = new TH2F("fHistTimeZDC", "ZDC;TDC timing A+C vs C-A; events", 120,-30,30,120,-600,-540);
209 fHistTimeCorrZDC = new TH2F("fHistTimeCorrZDC", "ZDC;Corrected TDC timing A+C vs C-A; events", 120,-30,30,260,-100,30);
212 fHistFMDA = new TH1F("fHistFMDA", "FMDA;combinations above threshold;events", 102, -1.5, 100.5);
213 fHistFMDC = new TH1F("fHistFMDC", "FMDC;combinations above threshold;events", 102, -1.5, 100.5);
214 fHistFMDSingle = new TH1F("fHistFMDSingle", "FMD single;multiplicity value;counts", 1000, 0, 10);
215 fHistFMDSum = new TH1F("fHistFMDSum", "FMD sum;multiplicity value;counts", 1000, 0, 10);
216 fHistT0 = new TH1F("fHistT0", "T0;time (ns);events", 100, -25, 25);
218 fTriggerClasses = new TMap;
219 fTriggerClasses->SetOwner();
221 TH1::AddDirectory(oldStatus);
224 //____________________________________________________________________
225 const char* AliTriggerAnalysis::GetTriggerName(Trigger trigger)
227 // returns the name of the requested trigger
228 // the returned string will only be valid until the next call to this function [not thread-safe]
232 UInt_t triggerNoFlags = (UInt_t) trigger % (UInt_t) kStartOfFlags;
234 switch (triggerNoFlags)
236 case kAcceptAll : str = "ACCEPT ALL (bypass!)"; break;
237 case kMB1 : str = "MB1"; break;
238 case kMB2 : str = "MB2"; break;
239 case kMB3 : str = "MB3"; break;
240 case kSPDGFO : str = "SPD GFO"; break;
241 case kSPDGFOBits : str = "SPD GFO Bits"; break;
242 case kSPDGFOL0 : str = "SPD GFO L0 (first layer)"; break;
243 case kSPDGFOL1 : str = "SPD GFO L1 (second layer)"; break;
244 case kSPDClsVsTrkBG : str = "Cluster vs Tracklets"; break;
245 case kV0A : str = "V0 A BB"; break;
246 case kV0C : str = "V0 C BB"; break;
247 case kV0OR : str = "V0 OR BB"; break;
248 case kV0AND : str = "V0 AND BB"; break;
249 case kV0ABG : str = "V0 A BG"; break;
250 case kV0CBG : str = "V0 C BG"; break;
251 case kZDC : str = "ZDC"; break;
252 case kZDCA : str = "ZDC A"; break;
253 case kZDCC : str = "ZDC C"; break;
254 case kZNA : str = "ZN A"; break;
255 case kZNC : str = "ZN C"; break;
256 case kZNABG : str = "ZN A BG"; break;
257 case kZNCBG : str = "ZN C BG"; break;
258 case kFMDA : str = "FMD A"; break;
259 case kFMDC : str = "FMD C"; break;
260 case kFPANY : str = "SPD GFO | V0 | ZDC | FMD"; break;
261 case kNSD1 : str = "NSD1"; break;
262 case kMB1Prime: str = "MB1prime"; break;
263 case kZDCTDCA : str = "ZDC TDC A"; break;
264 case kZDCTDCC : str = "ZDC TDC C"; break;
265 case kZDCTime : str = "ZDC Time Cut"; break;
266 case kCentral : str = "V0 Central"; break;
267 case kSemiCentral : str = "V0 Semi-central"; break;
268 case kEMCAL : str = "EMCAL"; break;
269 default: str = ""; break;
272 if (trigger & kOfflineFlag)
275 if (trigger & kOneParticle)
276 str += " OneParticle";
278 if (trigger & kOneTrack)
284 Bool_t AliTriggerAnalysis::IsTriggerFired(const AliESDEvent* aEsd, Trigger trigger)
286 // checks if an event has been triggered
288 if (trigger & kOfflineFlag)
289 return IsOfflineTriggerFired(aEsd, trigger);
291 return IsTriggerBitFired(aEsd, trigger);
294 Bool_t AliTriggerAnalysis::IsTriggerBitFired(const AliESDEvent* aEsd, Trigger trigger) const
296 // checks if an event is fired using the trigger bits
298 return IsTriggerBitFired(aEsd->GetTriggerMask(), trigger);
301 Bool_t AliTriggerAnalysis::IsTriggerBitFired(ULong64_t triggerMask, Trigger trigger) const
303 // checks if an event is fired using the trigger bits
305 // this function needs the branch TriggerMask in the ESD
307 // definitions from p-p.cfg
308 ULong64_t spdFO = (1 << 14);
309 ULong64_t v0left = (1 << 10);
310 ULong64_t v0right = (1 << 11);
321 if (triggerMask & spdFO || ((triggerMask & v0left) || (triggerMask & v0right)))
327 if (triggerMask & spdFO && ((triggerMask & v0left) || (triggerMask & v0right)))
333 if (triggerMask & spdFO && (triggerMask & v0left) && (triggerMask & v0right))
339 if (triggerMask & spdFO)
344 Printf("IsEventTriggered: ERROR: Trigger type %d not implemented in this method", (Int_t) trigger);
351 Bool_t AliTriggerAnalysis::IsTriggerBitFired(const AliESDEvent* aEsd, ULong64_t tclass) const
353 // Checks if corresponding bit in mask is on
355 ULong64_t trigmask = aEsd->GetTriggerMask();
356 return (trigmask & (1ull << (tclass-1)));
359 Int_t AliTriggerAnalysis::EvaluateTrigger(const AliESDEvent* aEsd, Trigger trigger)
361 // evaluates a given trigger "offline"
362 // trigger combinations are not supported, for that see IsOfflineTriggerFired
364 UInt_t triggerNoFlags = (UInt_t) trigger % (UInt_t) kStartOfFlags;
365 Bool_t offline = kFALSE;
366 if (trigger & kOfflineFlag)
370 switch (triggerNoFlags)
374 decision = SPDFiredChips(aEsd, (offline) ? 0 : 1);
379 decision = SPDFiredChips(aEsd, (offline) ? 0 : 1, kFALSE, 1);
384 decision = SPDFiredChips(aEsd, (offline) ? 0 : 1, kFALSE, 2);
390 AliFatal(Form("Online trigger not available for trigger %d", triggerNoFlags));
391 decision = IsSPDClusterVsTrackletBG(aEsd);
396 if (V0Trigger(aEsd, kASide, !offline) == kV0BB)
402 if (V0Trigger(aEsd, kCSide, !offline) == kV0BB)
408 if (V0Trigger(aEsd, kASide, !offline) == kV0BG)
414 if (V0Trigger(aEsd, kCSide, !offline) == kV0BG)
420 if (T0Trigger(aEsd, !offline) == kT0BB)
427 AliFatal(Form("Online trigger not available for trigger %d", triggerNoFlags));
428 if (T0Trigger(aEsd, !offline) == kT0DecBG)
435 AliFatal(Form("Online trigger not available for trigger %d", triggerNoFlags));
436 if (T0Trigger(aEsd, !offline) == kT0DecPileup)
443 AliFatal(Form("Online trigger not available for trigger %d", triggerNoFlags));
444 if (ZDCTrigger(aEsd, kASide))
451 AliFatal(Form("Online trigger not available for trigger %d", triggerNoFlags));
452 if (ZDCTrigger(aEsd, kCSide))
459 AliFatal(Form("Online trigger not available for trigger %d", triggerNoFlags));
460 if (ZDCTDCTrigger(aEsd, kASide))
467 AliFatal(Form("Online trigger not available for trigger %d", triggerNoFlags));
468 if (ZDCTDCTrigger(aEsd, kCSide))
475 AliFatal(Form("Online trigger not available for trigger %d", triggerNoFlags));
476 if (ZDCTimeTrigger(aEsd))
483 AliFatal(Form("Online trigger not available for trigger %d", triggerNoFlags));
484 if (ZDCTDCTrigger(aEsd,kASide,kTRUE,kFALSE,kFALSE))
491 AliFatal(Form("Online trigger not available for trigger %d", triggerNoFlags));
492 if (ZDCTDCTrigger(aEsd,kCSide,kTRUE,kFALSE,kFALSE))
499 AliFatal(Form("Online trigger not available for trigger %d", triggerNoFlags));
500 if (ZDCTimeBGTrigger(aEsd,kASide))
507 AliFatal(Form("Online trigger not available for trigger %d", triggerNoFlags));
508 if (ZDCTimeBGTrigger(aEsd,kCSide))
515 AliFatal(Form("Online trigger not available for trigger %d", triggerNoFlags));
516 if (FMDTrigger(aEsd, kASide))
523 AliFatal(Form("Online trigger not available for trigger %d", triggerNoFlags));
524 if (FMDTrigger(aEsd, kCSide))
531 AliFatal(Form("Offline trigger not available for trigger %d", triggerNoFlags));
532 if (IsL0InputFired(aEsd, 2))
539 AliFatal(Form("Offline trigger not available for trigger %d", triggerNoFlags));
540 if (IsL0InputFired(aEsd, 3))
544 case kTPCLaserWarmUp:
547 AliFatal(Form("Online trigger not available for trigger %d", triggerNoFlags));
548 return IsLaserWarmUpTPCEvent(aEsd);
553 AliFatal(Form("Offline trigger not available for trigger %d - use centrality selection", triggerNoFlags));
554 if (aEsd->GetVZEROData()) {
555 if (aEsd->GetVZEROData()->TestBit(AliESDVZERO::kTriggerChargeBitsFilled)) {
556 if (aEsd->GetVZEROData()->GetTriggerBits() & (1<<AliESDVZERO::kCTA2andCTC2))
560 AliWarning("V0 centrality trigger bits were not filled!");
567 AliFatal(Form("Offline trigger not available for trigger %d - use centrality selection", triggerNoFlags));
568 if (aEsd->GetVZEROData()) {
569 if (aEsd->GetVZEROData()->TestBit(AliESDVZERO::kTriggerChargeBitsFilled)) {
570 if (aEsd->GetVZEROData()->GetTriggerBits() & (1<<AliESDVZERO::kCTA1andCTC1))
574 AliWarning("V0 centrality trigger bits were not filled!");
581 AliFatal(Form("Online trigger not available for trigger %d", triggerNoFlags));
582 if (EMCALCellsTrigger(aEsd))
588 AliFatal(Form("Trigger type %d not implemented", triggerNoFlags));
595 Bool_t AliTriggerAnalysis::IsLaserWarmUpTPCEvent(const AliESDEvent* esd)
598 // This function flags noisy TPC events which can happen during laser warm-up.
601 Int_t trackCounter = 0;
602 for (Int_t i=0; i<esd->GetNumberOfTracks(); ++i)
604 AliESDtrack *track = esd->GetTrack(i);
608 if (track->GetTPCNcls() < 30) continue;
609 if (TMath::Abs(track->Eta()) > 0.005) continue;
610 if (track->Pt() < 4) continue;
611 if (track->GetKinkIndex(0) > 0) continue;
613 UInt_t status = track->GetStatus();
614 if ((status&AliESDtrack::kITSrefit)==AliESDtrack::kITSrefit) continue; // explicitly ask for tracks without ITS refit
615 if ((status&AliESDtrack::kTPCrefit)!=AliESDtrack::kTPCrefit) continue;
617 if (track->GetTPCsignal() > 10) continue; // explicitly ask for tracks without dE/dx
621 if (trackCounter > 15)
626 Bool_t AliTriggerAnalysis::IsOfflineTriggerFired(const AliESDEvent* aEsd, Trigger trigger)
628 // checks if an event has been triggered "offline"
630 UInt_t triggerNoFlags = (UInt_t) trigger % (UInt_t) kStartOfFlags;
632 Bool_t decision = kFALSE;
633 switch (triggerNoFlags)
642 if (SPDGFOTrigger(aEsd, 0) || V0Trigger(aEsd, kASide, kFALSE) == kV0BB || V0Trigger(aEsd, kCSide, kFALSE) == kV0BB)
648 if (SPDGFOTrigger(aEsd, 0) && (V0Trigger(aEsd, kASide, kFALSE) == kV0BB || V0Trigger(aEsd, kCSide, kFALSE) == kV0BB))
654 if (SPDGFOTrigger(aEsd, 0) && V0Trigger(aEsd, kASide, kFALSE) == kV0BB && V0Trigger(aEsd, kCSide, kFALSE) == kV0BB)
660 if (SPDGFOTrigger(aEsd, 0))
666 if (SPDGFOTrigger(aEsd, 1))
672 if (V0Trigger(aEsd, kASide, kFALSE) == kV0BB)
678 if (V0Trigger(aEsd, kCSide, kFALSE) == kV0BB)
684 if (V0Trigger(aEsd, kASide, kFALSE) == kV0BB || V0Trigger(aEsd, kCSide, kFALSE) == kV0BB)
690 if (V0Trigger(aEsd, kASide, kFALSE) == kV0BB && V0Trigger(aEsd, kCSide, kFALSE) == kV0BB)
696 if (V0Trigger(aEsd, kASide, kFALSE) == kV0BG)
702 if (V0Trigger(aEsd, kCSide, kFALSE) == kV0BG)
708 if (ZDCTrigger(aEsd, kASide) || ZDCTrigger(aEsd, kCentralBarrel) || ZDCTrigger(aEsd, kCSide))
714 if (ZDCTrigger(aEsd, kASide))
720 if (ZDCTrigger(aEsd, kCSide))
726 if (ZDCTDCTrigger(aEsd,kASide,kTRUE,kFALSE,kFALSE))
732 if (ZDCTDCTrigger(aEsd,kCSide,kTRUE,kFALSE,kFALSE))
738 if (ZDCTimeBGTrigger(aEsd,kASide))
744 if (ZDCTimeBGTrigger(aEsd,kCSide))
750 if (FMDTrigger(aEsd, kASide))
756 if (FMDTrigger(aEsd, kCSide))
762 if (SPDGFOTrigger(aEsd, 0) || V0Trigger(aEsd, kASide, kFALSE) == kV0BB || V0Trigger(aEsd, kCSide, kFALSE) == kV0BB || ZDCTrigger(aEsd, kASide) || ZDCTrigger(aEsd, kCentralBarrel) || ZDCTrigger(aEsd, kCSide) || FMDTrigger(aEsd, kASide) || FMDTrigger(aEsd, kCSide))
768 if (SPDFiredChips(aEsd, 0) >= 5 || (V0Trigger(aEsd, kASide, kFALSE) == kV0BB && V0Trigger(aEsd, kCSide, kFALSE) == kV0BB))
775 if (SPDGFOTrigger(aEsd, 0))
777 if (V0Trigger(aEsd, kASide, kFALSE) == kV0BB)
779 if (V0Trigger(aEsd, kCSide, kFALSE) == kV0BB)
789 if (EMCALCellsTrigger(aEsd))
795 AliFatal(Form("Trigger type %d not implemented", triggerNoFlags));
799 // hadron-level requirement
800 if (decision && (trigger & kOneParticle))
804 const AliESDVertex* vertex = aEsd->GetPrimaryVertexSPD();
805 const AliMultiplicity* mult = aEsd->GetMultiplicity();
807 if (mult && vertex && vertex->GetNContributors() > 0 && (!vertex->IsFromVertexerZ() || vertex->GetDispersion() < 0.02) && TMath::Abs(vertex->GetZv()) < 5.5)
809 for (Int_t i=0; i<mult->GetNumberOfTracklets(); ++i)
811 if (TMath::Abs(mult->GetEta(i)) < 1)
820 // hadron level definition for TPC tracks
822 if (decision && (trigger & kOneTrack))
825 const AliESDVertex* vertex =0x0;
826 vertex = aEsd->GetPrimaryVertexTracks();
827 if (!vertex || vertex->GetNContributors() <= 0)
829 vertex = aEsd->GetPrimaryVertexSPD();
831 Float_t ptmin, ptmax;
832 fEsdTrackCuts->GetPtRange(ptmin,ptmax);
833 AliDebug(3, Form("ptmin = %f, ptmax = %f\n",ptmin, ptmax));
835 if (vertex && vertex->GetNContributors() > 0 && (!vertex->IsFromVertexerZ() || vertex->GetDispersion() < 0.02) && TMath::Abs(vertex->GetZv()) < 10.) {
836 AliDebug(3,Form("Check on the vertex passed\n"));
837 for (Int_t i=0; i<aEsd->GetNumberOfTracks(); ++i){
838 if (fTPCOnly == kFALSE){
839 if (fEsdTrackCuts->AcceptTrack(aEsd->GetTrack(i))){
840 AliDebug(2, Form("pt of track = %f --> check passed\n",aEsd->GetTrack(i)->Pt()));
847 AliESDtrack *tpcTrack = fEsdTrackCuts->GetTPCOnlyTrack((AliESDEvent*)aEsd, i);
849 AliDebug(3,Form("track %d is NOT a TPC track",i));
853 AliDebug(3,Form("track %d IS a TPC track",i));
854 if (!(fEsdTrackCuts->AcceptTrack(tpcTrack))) {
855 AliDebug(2, Form("TPC track %d NOT ACCEPTED, pt = %f, eta = %f",i,tpcTrack->Pt(), tpcTrack->Eta()));
856 delete tpcTrack; tpcTrack = 0x0;
858 } // end if the TPC track is not accepted
860 AliDebug(2, Form("TPC track %d ACCEPTED, pt = %f, eta = %f",i,tpcTrack->Pt(), tpcTrack->Eta()));
862 delete tpcTrack; tpcTrack = 0x0;
864 } // end if the TPC track is accepted
865 } // end if it is a TPC track
866 } // end if you are looking at TPC only tracks
867 } // end loop on tracks
868 } // end check on vertex
870 AliDebug(4,Form("Check on the vertex not passed\n"));
871 for (Int_t i=0; i<aEsd->GetNumberOfTracks(); ++i){
872 if (fEsdTrackCuts->AcceptTrack(aEsd->GetTrack(i))){
873 AliDebug(4,Form("pt of track = %f --> check would be passed if the vertex was ok\n",aEsd->GetTrack(i)->Pt()));
878 if (!decision) AliDebug(3,("Check for kOneTrack NOT passed\n"));
884 Bool_t AliTriggerAnalysis::IsTriggerClassFired(const AliESDEvent* aEsd, const Char_t* tclass) const
886 // tclass is logical function of inputs, e.g. 01 && 02 || 03 && 11 && 21
887 // = L0 inp 1 && L0 inp 2 || L0 inp 3 && L1 inp 1 && L2 inp 1
888 // NO brackets in logical function !
889 // Spaces between operators and inputs.
890 // Not all logical functions are available in CTP=
891 // =any function of first 4 inputs; 'AND' of other inputs, check not done
892 // This method will be replaced/complemened by similar one
893 // which works withh class and inputs names as in CTP cfg file
895 TString TClass(tclass);
896 TObjArray* tcltokens = TClass.Tokenize(" ");
897 Char_t level=((TObjString*)tcltokens->At(0))->String()[0];
898 UInt_t input=atoi((((TObjString*)tcltokens->At(0))->String()).Remove(0));
899 Bool_t tcl = IsInputFired(aEsd,level,input);
901 for (Int_t i=1;i<tcltokens->GetEntriesFast();i=i+2) {
902 level=((TObjString*)tcltokens->At(i+1))->String()[0];
903 input=atoi((((TObjString*)tcltokens->At(i+1))->String()).Remove(0));
904 Bool_t inpnext = IsInputFired(aEsd,level,input);
905 Char_t op =((TObjString*)tcltokens->At(i))->String()[0];
906 if (op == '&') tcl=tcl && inpnext;
907 else if (op == '|') tcl =tcl || inpnext;
909 AliError(Form("Syntax error in %s", tclass));
912 // tcltokens->Delete();
918 // tcltokens->Delete();
922 Bool_t AliTriggerAnalysis::IsInputFired(const AliESDEvent* aEsd, Char_t level, UInt_t input) const
924 // Checks trigger input of any level
928 case '0': return IsL0InputFired(aEsd,input);
929 case '1': return IsL1InputFired(aEsd,input);
930 case '2': return IsL2InputFired(aEsd,input);
932 AliError(Form("Wrong level %i",level));
937 Bool_t AliTriggerAnalysis::IsL0InputFired(const AliESDEvent* aEsd, UInt_t input) const
939 // Checks if corresponding bit in mask is on
941 UInt_t inpmask = aEsd->GetHeader()->GetL0TriggerInputs();
942 return (inpmask & (1<<(input-1)));
945 Bool_t AliTriggerAnalysis::IsL1InputFired(const AliESDEvent* aEsd, UInt_t input) const
947 // Checks if corresponding bit in mask is on
949 UInt_t inpmask = aEsd->GetHeader()->GetL1TriggerInputs();
950 return (inpmask & (1<<(input-1)));
953 Bool_t AliTriggerAnalysis::IsL2InputFired(const AliESDEvent* aEsd, UInt_t input) const
955 // Checks if corresponding bit in mask is on
957 UInt_t inpmask = aEsd->GetHeader()->GetL2TriggerInputs();
958 return (inpmask & (1<<(input-1)));
961 void AliTriggerAnalysis::FillHistograms(const AliESDEvent* aEsd)
963 // fills the histograms with the info from the ESD
965 fHistBitsSPD->Fill(SPDFiredChips(aEsd, 0), SPDFiredChips(aEsd, 1, kTRUE));
967 V0Trigger(aEsd, kASide, kFALSE, kTRUE);
968 V0Trigger(aEsd, kCSide, kFALSE, kTRUE);
969 T0Trigger(aEsd, kFALSE, kTRUE);
970 ZDCTDCTrigger(aEsd,kASide,kFALSE,kFALSE,kTRUE);
971 ZDCTimeTrigger(aEsd,kTRUE);
972 IsSPDClusterVsTrackletBG(aEsd, kTRUE);
974 AliESDZDC* zdcData = aEsd->GetESDZDC();
977 UInt_t quality = zdcData->GetESDQuality();
979 // from Nora's presentation, general first physics meeting 16.10.09
980 static UInt_t zpc = 0x20;
981 static UInt_t znc = 0x10;
982 static UInt_t zem1 = 0x08;
983 static UInt_t zem2 = 0x04;
984 static UInt_t zpa = 0x02;
985 static UInt_t zna = 0x01;
987 fHistZDC->Fill(1, (quality & zna) ? 1 : 0);
988 fHistZDC->Fill(2, (quality & zpa) ? 1 : 0);
989 fHistZDC->Fill(3, (quality & zem2) ? 1 : 0);
990 fHistZDC->Fill(4, (quality & zem1) ? 1 : 0);
991 fHistZDC->Fill(5, (quality & znc) ? 1 : 0);
992 fHistZDC->Fill(6, (quality & zpc) ? 1 : 0);
997 AliError("AliESDZDC not available");
1001 fHistFMDA->Fill(FMDHitCombinations(aEsd, kASide, kTRUE));
1002 fHistFMDC->Fill(FMDHitCombinations(aEsd, kCSide, kTRUE));
1006 void AliTriggerAnalysis::FillTriggerClasses(const AliESDEvent* aEsd)
1008 // fills trigger classes map
1010 TParameter<Long64_t>* count = dynamic_cast<TParameter<Long64_t>*> (fTriggerClasses->GetValue(aEsd->GetFiredTriggerClasses().Data()));
1013 count = new TParameter<Long64_t>(aEsd->GetFiredTriggerClasses(), 0);
1014 fTriggerClasses->Add(new TObjString(aEsd->GetFiredTriggerClasses().Data()), count);
1016 count->SetVal(count->GetVal() + 1);
1019 Int_t AliTriggerAnalysis::SSDClusters(const AliESDEvent* aEsd)
1021 // returns the number of clusters in the SSD
1022 const AliMultiplicity* mult = aEsd->GetMultiplicity();
1023 Int_t clusters = mult->GetNumberOfITSClusters(4)+mult->GetNumberOfITSClusters(5);
1028 Int_t AliTriggerAnalysis::SPDFiredChips(const AliESDEvent* aEsd, Int_t origin, Bool_t fillHists, Int_t layer)
1030 // returns the number of fired chips in the SPD
1032 // origin = 0 --> aEsd->GetMultiplicity()->GetNumberOfFiredChips() (filled from clusters)
1033 // origin = 1 --> aEsd->GetMultiplicity()->TestFastOrFiredChips() (from hardware bits)
1034 // layer = 0 --> both layers
1035 // layer = 1 --> inner
1036 // layer = 2 --> outer
1038 const AliMultiplicity* mult = aEsd->GetMultiplicity();
1041 AliError("AliMultiplicity not available");
1047 return mult->GetNumberOfFiredChips(0) + mult->GetNumberOfFiredChips(1);
1049 return mult->GetNumberOfFiredChips(layer-1);
1055 Int_t firstChip = 0;
1056 Int_t lastChip = 1200;
1062 for (Int_t i=firstChip; i<lastChip; i++)
1064 if (mult->TestFastOrFiredChips(i) == kTRUE)
1066 // efficiency simulation (if enabled)
1067 if (fSPDGFOEfficiency)
1069 if (gRandom->Uniform() > fSPDGFOEfficiency->GetBinContent(i+1))
1075 fHistFiredBitsSPD->Fill(i);
1084 Bool_t AliTriggerAnalysis::SPDGFOTrigger(const AliESDEvent* aEsd, Int_t origin)
1086 // Returns if the SPD gave a global Fast OR trigger
1088 Int_t firedChips = SPDFiredChips(aEsd, origin);
1090 if (firedChips >= fSPDGFOThreshold)
1095 Bool_t AliTriggerAnalysis::IsSPDClusterVsTrackletBG(const AliESDEvent* aEsd, Bool_t fillHists){
1096 //rejects BG based on the cluster vs tracklet correlation
1097 // returns true if the event is BG
1098 const AliMultiplicity* mult = aEsd->GetMultiplicity();
1100 AliFatal("No multiplicity object"); // TODO: Should this be fatal?
1102 Int_t ntracklet = mult->GetNumberOfTracklets();
1104 Int_t spdClusters = 0;
1105 for(Int_t ilayer = 0; ilayer < 2; ilayer++){
1106 spdClusters += mult->GetNumberOfITSClusters(ilayer);
1110 fHistSPDClsVsTrk->Fill(ntracklet,spdClusters);
1113 Bool_t isCvsTOk = kFALSE;
1114 Float_t limit = Float_t(fASPDCvsTCut) + Float_t(ntracklet) * fBSPDCvsTCut;
1115 if (spdClusters > limit) isCvsTOk = kTRUE;
1116 else isCvsTOk = kFALSE ;
1123 AliTriggerAnalysis::V0Decision AliTriggerAnalysis::V0Trigger(const AliESDEvent* aEsd, AliceSide side, Bool_t online, Bool_t fillHists)
1125 // Returns the V0 trigger decision in V0A | V0C
1127 // Returns kV0Fake if the calculated average time is in a window where neither BB nor BG is expected.
1128 // The rate of such triggers can be used to estimate the background. Note that the rate has to be
1129 // rescaled with the size of the windows (numerical values see below in the code)
1131 // argument 'online' is used as a switch between online and offline trigger algorithms
1133 // Based on an algorithm by Cvetan Cheshkov
1135 AliESDVZERO* esdV0 = aEsd->GetVZEROData();
1138 AliError("AliESDVZERO not available");
1141 AliDebug(2,Form("In V0Trigger: %f %f",esdV0->GetV0ATime(),esdV0->GetV0CTime()));
1151 else if (side == kCSide)
1159 if (esdV0->TestBit(AliESDVZERO::kDecisionFilled)) {
1161 if (esdV0->TestBit(AliESDVZERO::kOnlineBitsFilled)) {
1162 for (Int_t i = begin; i < end; ++i) {
1163 if (esdV0->GetBBFlag(i)) return kV0BB;
1165 for (Int_t i = begin; i < end; ++i) {
1166 if (esdV0->GetBGFlag(i)) return kV0BG;
1171 AliWarning("V0 online trigger analysis is not yet available!");
1178 if (side == kASide && fHistV0A)
1179 fHistV0A->Fill(esdV0->GetV0ATime());
1180 if (side == kCSide && fHistV0C)
1181 fHistV0C->Fill(esdV0->GetV0CTime());
1184 if (side == kASide) return (V0Decision)esdV0->GetV0ADecision();
1185 else if (side == kCSide) return (V0Decision)esdV0->GetV0CDecision();
1186 else return kV0Invalid;
1195 if (aEsd->GetRunNumber() <= 104803) runRange = 0;
1196 else if (aEsd->GetRunNumber() <= 104876) runRange = 1;
1199 Float_t factors[3][64] = {
1200 // runs: 104792-104803
1201 {4.6,5.9,6.3,6.0,4.7,5.9,4.9,5.4,4.8,4.1,4.9,4.6,4.5,5.5,5.1,5.8,4.3,4.0,4.0,3.3,3.1,2.9,3.0,5.6,3.3,4.9,3.9,5.3,4.1,4.4,3.9,5.5,5.7,9.5,5.1,5.3,6.6,7.1,8.9,4.4,4.1,5.9,9.0,4.5,4.1,6.0,4.7,7.1,4.2,4.7,3.9,6.3,5.9,4.8,4.7,4.5,4.7,5.4,5.8,5.0,5.1,5.9,5.3,3.6},
1202 // runs: 104841-104876
1203 {4.6,4.8,4.9,4.8,4.3,4.9,4.4,4.5,4.6,5.0,4.7,4.6,4.7,4.6,4.6,5.5,4.7,4.5,4.7,5.0,6.5,7.6,5.3,4.9,5.5,4.8,4.6,4.9,4.5,4.5,4.6,4.9,5.7,9.8,4.9,5.2,7.1,7.1,8.1,4.4,4.0,6.0,8.3,4.6,4.2,5.6,4.6,6.4,4.4,4.7,4.5,6.5,6.0,4.7,4.5,4.4,4.8,5.5,5.9,5.3,5.0,5.7,5.1,3.6},
1205 {4.7,5.2,4.8,5.0,4.4,5.0,4.4,4.6,4.6,4.5,4.4,4.6,4.5,4.6,4.8,5.5,4.8,4.5,4.4,4.3,5.4,7.7,5.6,5.0,5.4,4.3,4.5,4.8,4.5,4.5,4.6,5.3,5.7,9.6,4.9,5.4,6.1,7.2,8.6,4.4,4.0,5.4,8.8,4.4,4.2,5.8,4.7,6.7,4.3,4.7,4.0,6.1,6.0,4.9,4.8,4.6,4.7,5.2,5.7,5.0,5.0,5.8,5.3,3.6}
1207 Float_t dA = 77.4 - 11.0;
1208 Float_t dC = 77.4 - 2.9;
1209 // Time misalignment
1210 Float_t timeShift[64] = {0.477957 , 0.0889999 , 0.757669 , 0.205439 , 0.239666 , -0.183705 , 0.442873 , -0.281366 , 0.260976 , 0.788995 , 0.974758 , 0.548532 , 0.495023 , 0.868472 , 0.661167 , 0.358307 , 0.221243 , 0.530179 , 1.26696 , 1.33082 , 1.27086 , 1.77133 , 1.10253 , 0.634806 , 2.14838 , 1.50212 , 1.59253 , 1.66122 , 1.16957 , 1.52056 , 1.47791 , 1.81905 , -1.94123 , -1.29124 , -2.16045 , -1.78939 , -3.11111 , -1.87178 , -1.57671 , -1.70311 , -1.81208 , -1.94475 , -2.53058 , -1.7042 , -2.08109 , -1.84416 , -0.61073 , -1.77145 , 0.16999 , -0.0585339 , 0.00401133 , 0.397726 , 0.851111 , 0.264187 , 0.59573 , -0.158263 , 0.584362 , 1.20835 , 0.927573 , 1.13895 , 0.64648 , 2.18747 , 1.68909 , 0.451194};
1211 Float_t dA2 = 2.8, dC2 = 3.3;
1214 for (Int_t i = begin; i < end; ++i) {
1215 Float_t tempAdc = esdV0->GetAdc(i)/factors[runRange][i];
1216 Float_t tempTime = (i >= 32) ? esdV0->GetTime(i)+dA+timeShift[i]+dA2 : esdV0->GetTime(i)+dC+timeShift[i]+dC2;
1217 if (esdV0->GetTime(i) >= 1e-6 &&
1218 tempTime > fV0HwWinLow && tempTime < fV0HwWinHigh &&
1219 tempAdc > fV0HwAdcThr)
1225 for (Int_t i = begin; i < end; ++i) {
1226 Float_t tempAdc = esdV0->GetAdc(i)/factors[runRange][i];
1227 Float_t tempTime = (i >= 32) ? esdV0->GetTime(i)+dA : esdV0->GetTime(i)+dC;
1228 Float_t tempRawTime = (i >= 32) ? esdV0->GetTime(i)+dA+timeShift[i]+dA2 : esdV0->GetTime(i)+dC+timeShift[i]+dC2;
1229 if (esdV0->GetTime(i) >= 1e-6 &&
1230 tempRawTime < 125.0 &&
1231 tempAdc > fV0AdcThr) {
1240 for (Int_t i = begin; i < end; ++i) {
1241 if (esdV0->GetTime(i) >= 1e-6 &&
1242 esdV0->GetTime(i) > fV0HwWinLow && esdV0->GetTime(i) < fV0HwWinHigh &&
1243 esdV0->GetAdc(i) > fV0HwAdcThr)
1249 for (Int_t i = begin; i < end; ++i) {
1250 if (esdV0->GetTime(i) > 1e-6 && esdV0->GetAdc(i) > fV0AdcThr) {
1251 Float_t correctedTime = V0CorrectLeadingTime(i, esdV0->GetTime(i), esdV0->GetAdc(i),aEsd->GetRunNumber());
1252 Float_t timeWeight = V0LeadingTimeWeight(esdV0->GetAdc(i));
1253 time += correctedTime*timeWeight;
1255 weight += timeWeight;
1263 time += fV0TimeOffset;
1267 if (side == kASide && fHistV0A)
1268 fHistV0A->Fill(time);
1269 if (side == kCSide && fHistV0C)
1270 fHistV0C->Fill(time);
1275 if (time > 68 && time < 100)
1277 if (time > 54 && time < 57.5)
1279 if (time > 57.5 && time < 68)
1285 if (time > 75.5 && time < 100)
1287 if (time > 69.5 && time < 73)
1289 if (time > 55 && time < 69.5)
1296 Float_t AliTriggerAnalysis::V0CorrectLeadingTime(Int_t i, Float_t time, Float_t adc, Int_t runNumber) const
1298 // Correct for slewing and align the channels
1300 // Authors: Cvetan Cheshkov / Raphael Tieulent
1302 if (time == 0) return 0;
1305 Float_t timeShift[64] = {0.477957 , 0.0889999 , 0.757669 , 0.205439 , 0.239666 , -0.183705 , 0.442873 , -0.281366 , 0.260976 , 0.788995 , 0.974758 , 0.548532 , 0.495023 , 0.868472 , 0.661167 , 0.358307 , 0.221243 , 0.530179 , 1.26696 , 1.33082 , 1.27086 , 1.77133 , 1.10253 , 0.634806 , 2.14838 , 1.50212 , 1.59253 , 1.66122 , 1.16957 , 1.52056 , 1.47791 , 1.81905 , -1.94123 , -1.29124 , -2.16045 , -1.78939 , -3.11111 , -1.87178 , -1.57671 , -1.70311 , -1.81208 , -1.94475 , -2.53058 , -1.7042 , -2.08109 , -1.84416 , -0.61073 , -1.77145 , 0.16999 , -0.0585339 , 0.00401133 , 0.397726 , 0.851111 , 0.264187 , 0.59573 , -0.158263 , 0.584362 , 1.20835 , 0.927573 , 1.13895 , 0.64648 , 2.18747 , 1.68909 , 0.451194};
1307 if(runNumber < 106031)
1308 time -= timeShift[i];
1310 // Slewing correction
1311 if (adc == 0) return time;
1313 Float_t p1 = 1.57345e1;
1314 Float_t p2 =-4.25603e-1;
1316 if(runNumber >= 106031) adc *= (2.5/4.0);
1317 return (time - p1*TMath::Power(adc,p2));
1320 Float_t AliTriggerAnalysis::V0LeadingTimeWeight(Float_t adc) const
1322 if (adc < 1e-6) return 0;
1324 Float_t p1 = 40.211;
1325 Float_t p2 =-4.25603e-1;
1326 Float_t p3 = 0.5646;
1328 return 1./(p1*p1*TMath::Power(adc,2.*(p2-1.))+p3*p3);
1332 Bool_t AliTriggerAnalysis::ZDCTDCTrigger(const AliESDEvent* aEsd, AliceSide side, Bool_t useZN, Bool_t useZP, Bool_t fillHists) const
1334 // Returns if ZDC triggered, based on TDC information
1336 AliESDZDC *esdZDC = aEsd->GetESDZDC();
1338 Bool_t zdcNA = kFALSE;
1339 Bool_t zdcNC = kFALSE;
1340 Bool_t zdcPA = kFALSE;
1341 Bool_t zdcPC = kFALSE;
1344 // If it's MC, we use the energy
1345 Double_t minEnergy = 0;
1346 Double_t zNCEnergy = esdZDC->GetZDCN1Energy();
1347 Double_t zPCEnergy = esdZDC->GetZDCP1Energy();
1348 Double_t zNAEnergy = esdZDC->GetZDCN2Energy();
1349 Double_t zPAEnergy = esdZDC->GetZDCP2Energy();
1350 zdcNA = (zNAEnergy>minEnergy);
1351 zdcNC = (zNCEnergy>minEnergy);
1352 zdcPA = (zPAEnergy>minEnergy);
1353 zdcPC = (zPCEnergy>minEnergy);
1358 Bool_t tdc[32] = {kFALSE};
1359 for(Int_t itdc=0; itdc<32; itdc++){
1360 for(Int_t i=0; i<4; i++){
1361 if (esdZDC->GetZDCTDCData(itdc, i) != 0){
1365 if(fillHists && tdc[itdc]) {
1366 fHistTDCZDC->Fill(itdc);
1375 if (side == kASide) return ((useZP&&zdcPA) || (useZN&&zdcNA));
1376 if (side == kCSide) return ((useZP&&zdcPC) || (useZN&&zdcNC));
1380 Bool_t AliTriggerAnalysis::ZDCTimeTrigger(const AliESDEvent *aEsd, Bool_t fillHists) const
1382 // This method implements a selection
1383 // based on the timing in both sides of zdcN
1384 // It can be used in order to eliminate
1385 // parasitic collisions
1386 Bool_t zdcAccept = kFALSE;
1387 AliESDZDC *esdZDC = aEsd->GetESDZDC();
1390 UInt_t esdFlag = esdZDC->GetESDQuality();
1392 Bool_t znaFired=kFALSE, zpaFired=kFALSE;
1393 Bool_t zem1Fired=kFALSE, zem2Fired=kFALSE;
1394 Bool_t zncFired=kFALSE, zpcFired=kFALSE;
1396 // **** Trigger patterns
1397 if((esdFlag & 0x00000001) == 0x00000001) znaFired=kTRUE;
1398 if((esdFlag & 0x00000002) == 0x00000002) zpaFired=kTRUE;
1399 if((esdFlag & 0x00000004) == 0x00000004) zem1Fired=kTRUE;
1400 if((esdFlag & 0x00000008) == 0x00000008) zem2Fired=kTRUE;
1401 if((esdFlag & 0x00000010) == 0x00000010) zncFired=kTRUE;
1402 if((esdFlag & 0x00000020) == 0x00000020) zpcFired=kTRUE;
1403 zdcAccept = (znaFired | zncFired);
1406 for(Int_t i = 0; i < 4; ++i) {
1407 if (esdZDC->GetZDCTDCData(10,i) != 0) {
1408 Float_t tdcC = 0.025*(esdZDC->GetZDCTDCData(10,i)-esdZDC->GetZDCTDCData(14,i));
1409 Float_t tdcCcorr = esdZDC->GetZDCTDCCorrected(10,i);
1410 for(Int_t j = 0; j < 4; ++j) {
1411 if (esdZDC->GetZDCTDCData(12,j) != 0) {
1412 Float_t tdcA = 0.025*(esdZDC->GetZDCTDCData(12,j)-esdZDC->GetZDCTDCData(14,j));
1414 Float_t tdcAcorr = esdZDC->GetZDCTDCCorrected(12,j);
1416 fHistTimeZDC->Fill(tdcC-tdcA,tdcC+tdcA);
1417 fHistTimeCorrZDC->Fill(tdcCcorr-tdcAcorr,tdcCcorr+tdcAcorr);
1419 if (esdZDC->TestBit(AliESDZDC::kCorrectedTDCFilled)) {
1420 if (((tdcCcorr-tdcAcorr-fZDCCutRefDeltaCorr)*(tdcCcorr-tdcAcorr-fZDCCutRefDeltaCorr)/(fZDCCutSigmaDeltaCorr*fZDCCutSigmaDeltaCorr) +
1421 (tdcCcorr+tdcAcorr-fZDCCutRefSumCorr)*(tdcCcorr+tdcAcorr-fZDCCutRefSumCorr)/(fZDCCutSigmaSumCorr*fZDCCutSigmaSumCorr))< 1.0)
1425 if (((tdcC-tdcA-fZDCCutRefDelta)*(tdcC-tdcA-fZDCCutRefDelta)/(fZDCCutSigmaDelta*fZDCCutSigmaDelta) +
1426 (tdcC+tdcA-fZDCCutRefSum)*(tdcC+tdcA-fZDCCutRefSum)/(fZDCCutSigmaSum*fZDCCutSigmaSum))< 1.0)
1437 Bool_t AliTriggerAnalysis::ZDCTimeBGTrigger(const AliESDEvent *aEsd, AliceSide side) const
1439 // This method implements a selection
1440 // based on the timing in of zdcN
1441 // It can be used in order to flag background
1442 // ** So far only implemented for the 2012 pA run **
1444 if(fMC) return kFALSE;
1446 AliESDZDC *zdcData = aEsd->GetESDZDC();
1447 Bool_t zna = kFALSE;
1448 Bool_t znc = kFALSE;
1450 Float_t tdcC=999, tdcCcorr=999, tdcA=999, tdcAcorr=999;
1451 for(Int_t i = 0; i < 4; ++i) {
1452 if (zdcData->GetZDCTDCData(10,i) != 0) {
1454 tdcC = 0.025*(zdcData->GetZDCTDCData(10,i)-zdcData->GetZDCTDCData(14,i));
1455 tdcCcorr = zdcData->GetZDCTDCCorrected(10,i);
1458 for(Int_t j = 0; j < 4; ++j) {
1459 if (zdcData->GetZDCTDCData(12,j) != 0) {
1461 tdcA = 0.025*(zdcData->GetZDCTDCData(12,j)-zdcData->GetZDCTDCData(14,j));
1462 tdcAcorr = zdcData->GetZDCTDCCorrected(12,j);
1466 const Int_t runNumber = aEsd->GetRunNumber();
1467 if(runNumber<188124 || (runNumber>188374 && runNumber<194713)){ // FIXME: end of pA-run is not known
1468 AliDebug(3,Form(" ZN BG time cut not implemented for run %d",runNumber));
1472 Bool_t znabg = (zna && (TMath::Abs(tdcAcorr)>fZDCCutZNATimeCorr));
1473 Bool_t zncbg = (znc && (TMath::Abs(tdcCcorr)>fZDCCutZNCTimeCorr));
1475 // Printf("Checking ZN background (time) for run %d, A = %d, time=%2.2f, C = %d, time=%2.2f",runNumber,(Int_t)zna,tdcAcorr,(Int_t)znc,tdcCcorr);
1476 // Printf("Checking ZN background (time) for run %d, A-BG = %d, C-BG = %d",runNumber,(Int_t)znabg,(Int_t)zncbg);
1478 if (side == kASide) return znabg;
1479 if (side == kCSide) return zncbg;
1483 Bool_t AliTriggerAnalysis::ZDCTrigger(const AliESDEvent* aEsd, AliceSide side) const
1485 // Returns if ZDC triggered
1487 AliESDZDC* zdcData = aEsd->GetESDZDC();
1490 AliError("AliESDZDC not available");
1494 UInt_t quality = zdcData->GetESDQuality();
1496 // from Nora's presentation, general first physics meeting 16.10.09
1497 static UInt_t zpc = 0x20;
1498 static UInt_t znc = 0x10;
1499 static UInt_t zem1 = 0x08;
1500 static UInt_t zem2 = 0x04;
1501 static UInt_t zpa = 0x02;
1502 static UInt_t zna = 0x01;
1504 if (side == kASide && ((quality & zpa) || (quality & zna)))
1506 if (side == kCentralBarrel && ((quality & zem1) || (quality & zem2)))
1508 if (side == kCSide && ((quality & zpc) || (quality & znc)))
1514 Int_t AliTriggerAnalysis::FMDHitCombinations(const AliESDEvent* aEsd, AliceSide side, Bool_t fillHists)
1516 // returns number of hit combinations agove threshold
1518 // Authors: FMD team, Hans Dalsgaard (code merged from FMD/AliFMDOfflineTrigger)
1523 // Workaround for AliESDEvent::GetFMDData is not const!
1524 const AliESDFMD* fmdData = (const_cast<AliESDEvent*>(aEsd))->GetFMDData();
1527 AliError("AliESDFMD not available");
1531 Int_t detFrom = (side == kASide) ? 1 : 3;
1532 Int_t detTo = (side == kASide) ? 2 : 3;
1535 Float_t totalMult = 0;
1536 for (UShort_t det=detFrom;det<=detTo;det++) {
1537 Int_t nRings = (det == 1 ? 1 : 2);
1538 for (UShort_t ir = 0; ir < nRings; ir++) {
1539 Char_t ring = (ir == 0 ? 'I' : 'O');
1540 UShort_t nsec = (ir == 0 ? 20 : 40);
1541 UShort_t nstr = (ir == 0 ? 512 : 256);
1542 for (UShort_t sec =0; sec < nsec; sec++) {
1543 for (UShort_t strip = 0; strip < nstr; strip++) {
1544 Float_t mult = fmdData->Multiplicity(det,ring,sec,strip);
1545 if (mult == AliESDFMD::kInvalidMult) continue;
1548 fHistFMDSingle->Fill(mult);
1550 if (mult > fFMDLowCut)
1551 totalMult = totalMult + mult;
1554 if (totalMult > fFMDHitCut)
1558 fHistFMDSum->Fill(totalMult);
1570 Bool_t AliTriggerAnalysis::FMDTrigger(const AliESDEvent* aEsd, AliceSide side)
1572 // Returns if the FMD triggered
1574 // Authors: FMD team, Hans Dalsgaard (code merged from FMD/AliFMDOfflineTrigger)
1576 Int_t triggers = FMDHitCombinations(aEsd, side, kFALSE);
1584 Long64_t AliTriggerAnalysis::Merge(TCollection* list)
1586 // Merge a list of AliMultiplicityCorrection objects with this (needed for
1588 // Returns the number of merged objects (including this).
1593 if (list->IsEmpty())
1596 TIterator* iter = list->MakeIterator();
1599 // collections of all histograms
1600 const Int_t nHists = 14;
1601 TList collections[nHists];
1604 while ((obj = iter->Next())) {
1606 AliTriggerAnalysis* entry = dynamic_cast<AliTriggerAnalysis*> (obj);
1611 collections[n++].Add(entry->fHistV0A);
1612 collections[n++].Add(entry->fHistV0C);
1613 collections[n++].Add(entry->fHistZDC);
1614 collections[n++].Add(entry->fHistTDCZDC);
1615 collections[n++].Add(entry->fHistTimeZDC);
1616 collections[n++].Add(entry->fHistTimeCorrZDC);
1617 collections[n++].Add(entry->fHistFMDA);
1618 collections[n++].Add(entry->fHistFMDC);
1619 collections[n++].Add(entry->fHistFMDSingle);
1620 collections[n++].Add(entry->fHistFMDSum);
1621 collections[n++].Add(entry->fHistBitsSPD);
1622 collections[n++].Add(entry->fHistFiredBitsSPD);
1623 collections[n++].Add(entry->fHistSPDClsVsTrk);
1624 collections[n++].Add(entry->fHistT0);
1626 // merge fTriggerClasses
1627 TIterator* iter2 = entry->fTriggerClasses->MakeIterator();
1628 TObjString* obj2 = 0;
1629 while ((obj2 = dynamic_cast<TObjString*> (iter2->Next())))
1631 TParameter<Long64_t>* param2 = static_cast<TParameter<Long64_t>*> (entry->fTriggerClasses->GetValue(obj2));
1633 TParameter<Long64_t>* param1 = dynamic_cast<TParameter<Long64_t>*> (fTriggerClasses->GetValue(obj2));
1636 param1->SetVal(param1->GetVal() + param2->GetVal());
1640 param1 = dynamic_cast<TParameter<Long64_t>*> (param2->Clone());
1641 fTriggerClasses->Add(new TObjString(obj2->String()), param1);
1651 fHistV0A->Merge(&collections[n++]);
1652 fHistV0C->Merge(&collections[n++]);
1653 fHistZDC->Merge(&collections[n++]);
1654 fHistTDCZDC->Merge(&collections[n++]);
1656 fHistTimeZDC->Merge(&collections[n++]);
1659 if (fHistTimeCorrZDC)
1660 fHistTimeCorrZDC->Merge(&collections[n++]);
1663 fHistFMDA->Merge(&collections[n++]);
1664 fHistFMDC->Merge(&collections[n++]);
1665 fHistFMDSingle->Merge(&collections[n++]);
1666 fHistFMDSum->Merge(&collections[n++]);
1667 fHistBitsSPD->Merge(&collections[n++]);
1668 fHistFiredBitsSPD->Merge(&collections[n++]);
1669 fHistSPDClsVsTrk->Merge(&collections[n++]);
1670 fHistT0->Merge(&collections[n++]);
1676 void AliTriggerAnalysis::SaveHistograms() const
1678 // write histograms to current directory
1684 fHistBitsSPD->Write();
1685 fHistBitsSPD->ProjectionX();
1686 fHistBitsSPD->ProjectionY();
1688 else Printf("Cannot save fHistBitsSPD");
1689 if (fHistFiredBitsSPD) fHistFiredBitsSPD->Write();
1690 else Printf("Cannot save fHistFiredBitsSPD");
1691 if (fHistV0A) fHistV0A->Write();
1692 else Printf("Cannot save fHistV0A");
1693 if (fHistV0C) fHistV0C->Write();
1694 else Printf("Cannot save fHistV0C");
1695 if (fHistZDC) fHistZDC->Write();
1696 else Printf("Cannot save fHistZDC");
1697 if (fHistTDCZDC) fHistTDCZDC->Write();
1698 else Printf("Cannot save fHistTDCZDC");
1699 if (fHistTimeZDC) fHistTimeZDC->Write();
1700 else Printf("Cannot save fHistTimeZDC");
1701 if (fHistTimeCorrZDC) fHistTimeCorrZDC->Write();
1702 else Printf("Cannot save fHistTimeCorrZDC");
1703 if (fHistFMDA) fHistFMDA->Write();
1704 else Printf("Cannot save fHistFMDA");
1705 if (fHistFMDC) fHistFMDC->Write();
1706 else Printf("Cannot save fHistFMDC");
1707 if (fHistFMDSingle) fHistFMDSingle->Write();
1708 else Printf("Cannot save fHistFMDSingle");
1709 if (fHistFMDSum) fHistFMDSum->Write();
1710 else Printf("Cannot save fHistFMDSum");
1711 if (fSPDGFOEfficiency) fSPDGFOEfficiency->Write("fSPDGFOEfficiency");
1712 if (fHistSPDClsVsTrk) fHistSPDClsVsTrk->Write("fHistSPDClsVsTrk");
1713 if (fHistT0) fHistT0->Write("fHistT0");
1715 // else Printf("Cannot save fSPDGFOEfficiency");
1717 fTriggerClasses->Write("fTriggerClasses", TObject::kSingleKey);
1720 void AliTriggerAnalysis::PrintTriggerClasses() const
1722 // print trigger classes
1724 Printf("Trigger Classes:");
1726 Printf("Event count for trigger combinations:");
1729 singleTrigger.SetOwner();
1731 TIterator* iter = fTriggerClasses->MakeIterator();
1732 TObjString* obj = 0;
1733 while ((obj = dynamic_cast<TObjString*> (iter->Next())))
1735 TParameter<Long64_t>* param = static_cast<TParameter<Long64_t>*> (fTriggerClasses->GetValue(obj));
1737 Printf(" %s: %ld triggers", obj->String().Data(), (Long_t)param->GetVal());
1739 TObjArray* tokens = obj->String().Tokenize(" ");
1740 for (Int_t i=0; i<tokens->GetEntries(); i++)
1742 TParameter<Long64_t>* count = dynamic_cast<TParameter<Long64_t>*> (singleTrigger.GetValue(((TObjString*) tokens->At(i))->String().Data()));
1745 count = new TParameter<Long64_t>(((TObjString*) tokens->At(i))->String().Data(), 0);
1746 singleTrigger.Add(new TObjString(((TObjString*) tokens->At(i))->String().Data()), count);
1748 count->SetVal(count->GetVal() + param->GetVal());
1755 Printf("Event count for single trigger:");
1757 iter = singleTrigger.MakeIterator();
1758 while ((obj = dynamic_cast<TObjString*> (iter->Next())))
1760 TParameter<Long64_t>* param = static_cast<TParameter<Long64_t>*> (singleTrigger.GetValue(obj));
1762 Printf(" %s: %ld triggers", obj->String().Data(), (Long_t)param->GetVal());
1766 singleTrigger.DeleteAll();
1770 //----------------------------------------------------------------------------------------------------
1771 AliTriggerAnalysis::T0Decision AliTriggerAnalysis::T0Trigger(const AliESDEvent* aEsd, Bool_t online, Bool_t fillHists)
1773 // Returns the T0 TVDC trigger decision
1775 // argument 'online' is used as a switch between online and offline trigger algorithms
1776 // in online mode return 0TVX
1777 // in offline mode in addition check pile-up and background :
1778 // pile-up readed from ESD: check if TVDC (0TVX module name) has more 1 hit;
1779 // backgroud flag readed from ESD : check in given time interval OrA and OrC were correct but TVDC not
1781 // Based on an algorithm by Alla Maevskaya
1783 const AliESDTZERO* esdT0 = aEsd->GetESDTZERO();
1786 AliError("AliESDTZERO not available");
1789 //???? AliDebug(2,Form("In T0Trigger: %f %f",esdV0->GetV0ATime(),esdV0->GetV0CTime()));
1791 for (Int_t ii=0; ii<5; ii++)
1792 tvdc[ii] = esdT0->GetTVDC(ii);
1793 // Int_t trig=esdT0->GetT0Trig();
1794 // cout<<" T0 trig "<<trig<<endl;
1796 if(fillHists) fHistT0->Fill(tvdc[0]);
1799 if(aEsd->GetHeader()->GetFiredTriggerInputs().Contains("0TVX") ) return kT0BB;
1803 if (esdT0->GetPileupFlag()) return kT0DecPileup;
1804 if (esdT0->GetBackgroundFlag()) return kT0DecBG;
1805 if (tvdc[0]>-5 && tvdc[0]<5 && tvdc[0] != 0) return kT0BB;
1809 if( esdT0->GetT0zVertex()>-12.3 && esdT0->GetT0zVertex() < 10.3) return kT0BB;
1814 //----------------------------------------------------------------------------------------------------
1815 Bool_t AliTriggerAnalysis::EMCALCellsTrigger(const AliESDEvent *aEsd)
1818 // Returns the EMCAL trigger decision
1819 // so far only implemented for LHC11a data
1820 // see http://alisoft.cern.ch/viewvc/trunk/PWGGA/EMCALTasks/AliEmcalPhysicsSelection.cxx?view=markup&root=AliRoot Revision 56136
1823 Bool_t isFired = kTRUE;
1824 const Int_t runNumber = aEsd->GetRunNumber();
1827 // Load EMCAL branches from the manager
1828 AliAnalysisManager *am = AliAnalysisManager::GetAnalysisManager();
1829 am->LoadBranch("EMCALCells.");
1830 am->LoadBranch("CaloClusters");
1834 AliVCaloCells *cells = aEsd->GetEMCALCells();
1835 const Short_t nCells = cells->GetNumberOfCells();
1837 // count cells above threshold per sm
1838 Int_t nCellCount[10] = {0,0,0,0,0,0,0,0,0,0};
1839 for(Int_t iCell=0; iCell<nCells; ++iCell) {
1840 Short_t cellId = cells->GetCellNumber(iCell);
1841 Double_t cellE = cells->GetCellAmplitude(cellId);
1842 Int_t sm = cellId / (24*48);
1847 // Trigger decision for LHC11a
1848 Bool_t isLedEvent = kFALSE;
1849 if ((runNumber>=144871) && (runNumber<=146860)) {
1850 if (nCellCount[4] > 100)
1853 if ((runNumber>=146858) && (runNumber<=146860)) {
1854 if (nCellCount[3]>=35)