fixing the error message
[u/mrichter/AliRoot.git] / T0 / AliT0QAChecker.cxx
CommitLineData
c03351ac 1/**************************************************************************
2 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
3 * *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
6 * *
7 * Permission to use, copy, modify and distribute this software and its *
8 * documentation strictly for non-commercial purposes is hereby granted *
9 * without fee, provided that the above copyright notice appears in all *
10 * copies and that both the copyright notice and this permission notice *
11 * appear in the supporting documentation. The authors make no claims *
12 * about the suitability of this software for any purpose. It is *
13 * provided "as is" without express or implied warranty. *
14 **************************************************************************/
c03351ac 15//...
16// Checks the quality assurance.
17// By comparing with reference data
18// Skeleton for T0
f6c2d5e2 19//---------------------------------------------
20//checkig without reference data:
21//for RAW QA all histograms should have approximatly the same
22//number of entries as RefPoint
23//for Rec Points checks
24// - amplitude measured by 2 methos
25// - online and offline T0 measurements
26// for ESD quality of reconstruction ( and measurements):
27// RMS of vertex and T0 less than 75ps
28//
29// Alla.Maevskaya@cern.ch
c03351ac 30//...
31
32// --- ROOT system ---
b09247a2 33#include <Riostream.h>
c03351ac 34#include <TClass.h>
35#include <TH1F.h>
be3ada9f 36#include <TF1.h>
37#include <TFitResultPtr.h>
0d849919 38#include <TH2.h>
c03351ac 39#include <TIterator.h>
40#include <TKey.h>
41#include <TFile.h>
446d6ec4 42#include <TMath.h>
0d849919 43#include <TString.h>
be3ada9f 44#include <TPaveText.h>
c03351ac 45
46// --- Standard library ---
47
48// --- AliRoot header files ---
49#include "AliLog.h"
4e25ac79 50#include "AliQAv1.h"
c03351ac 51#include "AliQAChecker.h"
394c1a6d 52#include "AliCDBEntry.h"
53#include "AliQAManager.h"
c03351ac 54#include "AliT0QAChecker.h"
55
56ClassImp(AliT0QAChecker)
be3ada9f 57//____________________________________________________________________________
58AliT0QAChecker::AliT0QAChecker() :
59AliQACheckerBase("T0","T0 Quality Assurance Checker")
60
61{
62 // Standard constructor
63
64}
65
66//____________________________________________________________________________
49e33ff1 67AliT0QAChecker::AliT0QAChecker(const AliT0QAChecker& qac):
68 AliQACheckerBase(qac.GetName(), qac.GetTitle())
69{
70 // copy constructor
71 AliError("Copy should not be used with this class\n");
72}
73//____________________________________________________________________________
74AliT0QAChecker& AliT0QAChecker::operator=(const AliT0QAChecker& qac){
75 // assignment operator
76 this->~AliT0QAChecker();
77 new(this)AliT0QAChecker(qac);
78 return *this;
79}
80
81
82//____________________________________________________________________________
be3ada9f 83AliT0QAChecker::~AliT0QAChecker(){
84 // destructor
85
86}
c03351ac 87
4e67e173 88//__________________________________________________________________
a42ceb0e 89void AliT0QAChecker::Check(Double_t * test, AliQAv1::ALITASK_t index, TObjArray ** list, const AliDetectorRecoParam * /*recoParam*/)
3685c21c 90{
91
92 // Super-basic check on the QA histograms on the input list:
93 // look whether they are empty!
a42ceb0e 94
be3ada9f 95 char * detOCDBDir = Form("T0/%s/%s", AliQAv1::GetRefOCDBDirName(), AliQAv1::GetRefDataDirName()) ;
8825d145 96
394c1a6d 97 AliCDBEntry *QARefRec = AliQAManager::QAManager()->Get(detOCDBDir);
98 // QARefRec->Dump();
99 if( !QARefRec){
100 AliInfo("QA reference data NOT retrieved for Reconstruction check. No T0 reference distribution");
101 }
c724dd64 102
49e33ff1 103
104 for(Int_t specie = 0 ; specie < AliRecoParam::kNSpecies ; specie++){
105 test[specie] = 1.0; //FK// initiate qa flag for the whole set of histograms as good
106 }
107
108
109 for(Int_t specie = 0 ; specie < AliRecoParam::kNSpecies ; specie++) {
110 if(!(AliQAv1::Instance()->IsEventSpecieSet(specie) && list[specie]) || list[specie]->GetEntries() == 0) {
92664bc8 111 continue;
57acd2d2 112 }
49e33ff1 113 if(index == AliQAv1::kRAW){
114
115 if(AliRecoParam::ConvertIndex(specie) == AliRecoParam::kCalib){// if (index == AliQAv1::kRAW )
116 //check laser data efficiencies
117 Double_t qaFlag = CheckLaser(list[specie]);
118 if(qaFlag < test[specie]) test[specie] = qaFlag;
119 }
120
121 if(AliRecoParam::ConvertIndex(specie) == AliRecoParam::kCalib ||
122 AliRecoParam::ConvertIndex(specie) == AliRecoParam::kDefault){
123
124 //check BCID
125 Double_t qaFlag = CheckBCID(list[specie]);
126 if(qaFlag < test[specie]) test[specie] = qaFlag;
127 }
128
129 if(AliRecoParam::ConvertIndex(specie) == AliRecoParam::kDefault){
130 //check physics
131 Double_t qaFlag = CheckRaw(list[specie]);
132 if(qaFlag < test[specie]) test[specie] = qaFlag;
92664bc8 133 }
49e33ff1 134 }
135
136 if(index == AliQAv1::kESD && AliRecoParam::Convert(specie) != AliRecoParam::kCalib){
92664bc8 137 test[specie] = CheckESD(list[specie]);
49e33ff1 138 }
be3ada9f 139 }
140}
394c1a6d 141
be3ada9f 142//--------------------------------------------------------------------------
49e33ff1 143Double_t AliT0QAChecker::CheckLaser(TObjArray *listrec) const {
be3ada9f 144
49e33ff1 145 TH1 *hdata;
146 TH1 *fhRawEff[10];
147 Int_t nEffHistos=0;
148
149 //thresholds for warning and error on efficiencies
150 Float_t thrWarning = 0.5; //FK// warning level
151 Float_t thrError = 0.2; //FK// error level
152
153 const int kNumberOfHistos = 3;
154 Int_t consecutiveHistoNumber[kNumberOfHistos] = { 207, 208, 209}; //Checked histos fhCDFeff, hEffLED, hEffQTC
155 Int_t qualityFlag[kNumberOfHistos]; //quality flag for a given histogram
156
157 for(Int_t ir=0; ir<kNumberOfHistos; ir++){
158 qualityFlag[ir] = kT0Info; //init quality flag for a given histogram
159
160 hdata = (TH1*) listrec->UncheckedAt(consecutiveHistoNumber[ir]);
161 if(hdata){
162 fhRawEff[nEffHistos] = hdata;
163 nEffHistos++;
164 }
165 }
166
167 TLine linelowyellow(0, thrWarning, 24, thrWarning);
168 linelowyellow.SetLineColor(5);
169 linelowyellow.SetLineStyle(3);
170 linelowyellow.SetLineWidth(4);
171 TLine linelowred(0, thrError, 24, thrError);
172 linelowred.SetLineColor(2);
173 linelowred.SetLineStyle(3);
174 linelowred.SetLineWidth(4);
175
176 Bool_t bEffHistosNotEmpty = kFALSE; //check if all histograms have some counts
177
178 for(Int_t ih = 0; ih < nEffHistos; ih++){
179
180 EraseOldMessages((TH1*) fhRawEff[ih]);// clean objects added at previous checks
be3ada9f 181
49e33ff1 182 fhRawEff[ih]->SetLineWidth(2);
183 fhRawEff[ih]->SetMaximum(2.);
184 fhRawEff[ih]->SetMinimum(0.);
185 fhRawEff[ih]->GetListOfFunctions()->Add((TLine*)linelowyellow.Clone());
186 fhRawEff[ih]->GetListOfFunctions()->Add((TLine*)linelowred.Clone());
394c1a6d 187
49e33ff1 188 if(fhRawEff[ih]->Integral()>0) bEffHistosNotEmpty = kTRUE; //this histo does have some counts in it
189
190 Int_t nbins= fhRawEff[ih]->GetNbinsX();
191 for(Int_t ib=1; ib<=nbins; ib++){ //loop over bins and check if the efficiency is above level
192
193 Float_t chcont = fhRawEff[ih]->GetBinContent(ib);
194 if(chcont < thrWarning && qualityFlag[ih] > kT0Error ) qualityFlag[ih] = kT0Warning;//Warning level
195 if(chcont < thrError) qualityFlag[ih] = kT0Error;//Error level
be3ada9f 196 }
49e33ff1 197
198 if(qualityFlag[ih] == kT0Info ){
199 AliDebug(AliQAv1::GetQADebugLevel(), Form("T0 efficiency %s is good", fhRawEff[ih]->GetName() ));
200 }else if(qualityFlag[ih] == kT0Warning){
201 AliDebug(AliQAv1::GetQADebugLevel(), Form("T0 efficiency %s is not so good", fhRawEff[ih]->GetName() ));
202 }else if(qualityFlag[ih] == kT0Error){
203 AliDebug(AliQAv1::GetQADebugLevel(), Form("T0 efficiency %s is not good", fhRawEff[ih]->GetName() ));
204 }
205 }
206
207 //executive summary
208 int lowestQualityFlag = (int) kT0Info;
209 for(Int_t ih = 0; ih < nEffHistos; ih++){
210
211 if(!bEffHistosNotEmpty){ //all laser efficiency plots are empty
212 TPaveText text(0.20,0.50,0.99,0.99,"NDC");
213 text.AddText(Form("1) T0 is in BEAMTUNIG: empty plots are ok"));
214 text.AddText(Form("2) T0 is in READY: check calibriation trigger"));
215 text.AddText(Form("if also physics data are empty report"));
216 text.AddText(Form("readout problem to the T0 on-call expert"));
217 fhRawEff[ih]->GetListOfFunctions()->Add((TPaveText*)text.Clone());
218 }
219
220 if( qualityFlag[ih] <lowestQualityFlag ) lowestQualityFlag = qualityFlag[ih];
221 }
222
223 return ConvertQualityFlagToDouble(lowestQualityFlag);
224}
225//--------------------------------------------------------------------------
226Double_t AliT0QAChecker::CheckBCID(TObjArray *listrec) const {
227
228 Int_t qualityFlagBCID = kT0Info; //init quality flag for a given histogram;
229
230 TH2F *hBCID = (TH2F*) listrec->UncheckedAt(224); //BCID versus TRM BCID
231
be3ada9f 232
49e33ff1 233 // clean objects added at previous checks
234 EraseOldMessages((TH1*)hBCID);
235
236 if(hBCID->Integral()>0){
237 //BCID does have some counts in it
238
239 Int_t nbinsX = hBCID->GetNbinsX();
240 Int_t nbinsY = hBCID->GetNbinsY();
241 double entriesOnDiagonal = 0; //count diagonal and off diagonal entries
242 double entriesOffDiagonal = 0;
243
244 for(Int_t ix=1; ix<=nbinsX; ix++){
245 for(Int_t iy=1; iy<=nbinsY; iy++){
246 if(TMath::Abs(ix-iy)<6) entriesOnDiagonal += hBCID->GetBinContent(ix,iy); //On Diagonal
247 else entriesOffDiagonal += hBCID->GetBinContent(ix,iy); //Off Diagonal
57acd2d2 248 }
49e33ff1 249 }
250 if(entriesOnDiagonal<1 || entriesOffDiagonal>0){
251 qualityFlagBCID = kT0Error; //no entries on diagonal
252 AliDebug(AliQAv1::GetQADebugLevel(), Form("T0 %s is not diagonal", hBCID->GetName() ));
253
254 TPaveText text(0.20,0.50,0.99,0.99,"NDC");
255 text.AddText(Form("Check if entries are on a diagonal."));
256 text.AddText(Form("Report readout problem to the T0 on-call expert"));
257 hBCID->GetListOfFunctions()->Add((TPaveText*)text.Clone());
258 }
259 }else{ //BCID empty
260
261 qualityFlagBCID = kT0Error;
262 AliDebug(AliQAv1::GetQADebugLevel(), Form("T0 : %s has NO entries", hBCID->GetName() ));
263
264 TPaveText text(0.20,0.50,0.99,0.99,"NDC");
265 text.AddText(Form("NO ENTRIES!!!"));
266 text.AddText(Form("If T0 is READY report"));
267 text.AddText(Form("readout problem to the T0 on-call expert"));
268 hBCID->GetListOfFunctions()->Add((TPaveText*)text.Clone());
269 }
270
271 //executive summary
272 int lowestQualityFlag = (int) qualityFlagBCID;
273
274 return ConvertQualityFlagToDouble(lowestQualityFlag);
be3ada9f 275
3685c21c 276}
5ed41460 277
49e33ff1 278//--------------------------------------------------------------------------
279Double_t AliT0QAChecker::CheckRaw(TObjArray *listrec) const {
280
281
282 Int_t qualityFlagTrigger = kT0Info; //init quality flag for a given histogram;
283
284 TH1F *hTrigger = (TH1F*) listrec->UncheckedAt(169);//hRawTrigger
285
286
287 // clean objects added at previous checks
288 EraseOldMessages((TH1*) hTrigger);
289
290 if(hTrigger->Integral()>0){
291 //trigger plot does have some counts in it
292 //are Mean, ORA and ORC not empty?
293 if( hTrigger->GetBinContent(1)<0.001 || hTrigger->GetBinContent(3)<0.001 || hTrigger->GetBinContent(4)<0.001){
294 qualityFlagTrigger = kT0Error; //no entries on diagonal
295 AliDebug(AliQAv1::GetQADebugLevel(), Form("T0: too little ORA and ORC in %s", hTrigger->GetName() ));
296
297 TPaveText text(0.20,0.50,0.99,0.99,"NDC");
298 text.AddText(Form("Check ORA and ORC"));
299 text.AddText(Form("Report problem to the T0 on-call expert"));
300 hTrigger->GetListOfFunctions()->Add((TPaveText*)text.Clone());
301 }
302 }else{ //Trigger histo empty
303
304 qualityFlagTrigger = kT0Error;
305 AliDebug(AliQAv1::GetQADebugLevel(), Form("T0 histogram %s has NO entries", hTrigger->GetName() ));
306
307 TPaveText text(0.20,0.50,0.99,0.99,"NDC");
308 text.AddText(Form("NO ENTRIES!!!"));
309 text.AddText(Form("If T0 is READY report"));
310 text.AddText(Form("readout problem to the T0 on-call expert"));
311 hTrigger->GetListOfFunctions()->Add((TPaveText*)text.Clone());
312 }
313
314 //executive summary
315 int lowestQualityFlag = (int) qualityFlagTrigger;
316
317
318 return ConvertQualityFlagToDouble(lowestQualityFlag);
319
320}
be3ada9f 321
394c1a6d 322//--------------------------------------------------------------------------
be3ada9f 323Double_t AliT0QAChecker::CheckESD(TObjArray *listrec ) const
394c1a6d 324{
394c1a6d 325 Float_t checkr = 0;
be3ada9f 326 TH1 *fhESD;
327
328 fhESD = (TH1*) listrec->UncheckedAt(2);
329 if(fhESD){
330 AliDebug(AliQAv1::GetQADebugLevel(), Form("count %s ", fhESD->GetName()) );
331 TF1 *f1 = new TF1("f1","gaus",-1,1);
332 fhESD->Fit("f1","R","Q", -1,1);
333 Double_t par[3];
334 f1->GetParameters(&par[0]);
335
105ff51c 336 TPaveText text(0.30,0.50,0.99,0.99,"NDC");
be3ada9f 337
105ff51c 338 text.AddText(Form("T0 RUN %d ",AliCDBManager::Instance()->GetRun()));
be3ada9f 339
db33b25a 340 AliDebug(AliQAv1::GetQADebugLevel(), Form("numentries %d mean %f #sigma %f", (int)fhESD->GetEntries(),par[1], par[2]));
be3ada9f 341
342
343 if (par[2] > 0.07 && par[2] < 1.) {
344 checkr=0.5;
105ff51c 345 text.AddText(Form("not good resolution :\n %f ns\n", par[2] ));
346 text.SetFillColor(5);
be3ada9f 347 printf("T0 detector resolution is not good enouph: %f ns\n",par[2] );
348 }
349 if(TMath::Abs(par[1])>0.05) {
350 checkr = 0.5;
105ff51c 351 text.AddText(Form(" Check clock shift on %f ns", par[1]));
352 text.SetFillColor(5);
be3ada9f 353 }
354 if (par[2] > 1. || TMath::Abs(par[1])>0.1) {
355 checkr = 0.25;
105ff51c 356 text.AddText(Form(" Bad resolution:\n mean %f ns sigma %f ns", par[1], par[2]));
357 text.SetFillColor(2);
358 { // RS Clean previous additions
359 TList* lstF = fhESD->GetListOfFunctions();
360 if (lstF) {
361 TObject *stats = lstF->FindObject("stats");
362 lstF->Remove(stats);
363 TObject *obj;
364 while ((obj = lstF->First())) {
365 while(lstF->Remove(obj)) { }
366 delete obj;
367 }
368 if (stats) lstF->Add(stats);
369 }
370 }
371 fhESD->GetListOfFunctions()->Add((TPaveText*)text.Clone());
372 AliDebug(AliQAv1::GetQADebugLevel(),
373 Form("Please, check calibration: shift= %f resolution %f test=%f\n",
374 par[1], par[2], checkr) ) ;
be3ada9f 375 }
394c1a6d 376 }
be3ada9f 377 else
378 {
379 AliDebug(AliQAv1::GetQADebugLevel(),
380 Form("No ESD QA histogram found, nothing to check"));
381 checkr=0;
382 }
383
332b9234 384
394c1a6d 385 return checkr;
386}
49e33ff1 387
388
389//--------------------------------------------------------------------------
390void AliT0QAChecker::EraseOldMessages(TH1* h) const
391{
392 //erase the old captions
393 TList* lstF = h->GetListOfFunctions();
394 if(lstF){
395 TObject *stats = lstF->FindObject("stats");
396 lstF->Remove(stats);
397 TObject *obj;
398 while ((obj = lstF->First())) {
399 while(lstF->Remove(obj)) { }
400 delete obj;
401 }
402 if (stats) lstF->Add(stats);
403 }
404}
405//--------------------------------------------------------------------------
406Double_t AliT0QAChecker::ConvertQualityFlagToDouble(int qualityFlag) const
407{
408 //covert quality flag to double
409 Double_t checkr=1.0;
410
411 switch ( qualityFlag ){
412 case kT0Info:
413 checkr = 1.0; break;
414 case kT0Warning:
415 checkr = 0.75; break;
416 case kT0Error:
417 checkr = 0.25; break;
418 case kT0Fatal:
419 checkr = -1.0; break;
420 default:
421 AliError("Invalid ecc value. FIXME !");
422 checkr = 0.25; break;
423 };
424
425 return checkr;
426}