33b8e338bb05a6c83d55497f30945fb6cc71281f
[u/mrichter/AliRoot.git] / STEER / AliQAChecker.cxx
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  **************************************************************************/
15
16 /* $Id: */
17
18 ///////////////////////////////////////////////////////////////////////////////
19 //                                                                           //
20 // class for running the Quality Assurance Checker
21 //                                                                           //
22 ///////////////////////////////////////////////////////////////////////////////
23
24 #include "AliCDBEntry.h"
25 #include "AliCDBManager.h"
26 #include "AliCDBStorage.h"
27 #include "AliRunInfo.h"
28 #include "AliLog.h"
29 #include "AliModule.h" 
30 #include "AliQA.h"
31 #include "AliQAChecker.h"
32 #include "AliQACheckerBase.h"
33 #include "AliCorrQAChecker.h"
34 #include "AliGlobalQAChecker.h"
35
36 #include <TKey.h>
37 #include <TObjArray.h>
38 #include <TObjString.h>
39 #include <TPluginManager.h> 
40 #include <TROOT.h>
41 #include <TStopwatch.h> 
42 #include <TString.h> 
43 #include <TSystem.h> 
44 #include <TList.h>
45 #include <TNtupleD.h>
46
47 ClassImp(AliQAChecker)
48   AliQAChecker * AliQAChecker::fgQAChecker = 0x0 ;
49
50 //_____________________________________________________________________________
51 AliQAChecker::AliQAChecker(const char* name, const char* title) :
52   TNamed(name, title),
53   fDataFile(0x0), 
54   fRunInfo(0x0), 
55   fRunInfoOwner(kFALSE), 
56   fRefFile(0x0), 
57   fFoundDetectors(".")
58 {
59   // ctor: initialise checkers and open the data file   
60   for (Int_t det = 0 ; det < AliQA::kNDET ; det++) 
61     fCheckers[det] = NULL ; 
62 }
63
64 //_____________________________________________________________________________
65 AliQAChecker::AliQAChecker(const AliQAChecker& qac) :
66   TNamed(qac),
67   fDataFile(qac.fDataFile), 
68   fRunInfo(qac.fRunInfo), 
69   fRunInfoOwner(kFALSE),   
70   fRefFile(qac.fRefFile), 
71   fFoundDetectors(qac.fFoundDetectors)
72 {
73   // copy constructor
74   
75   for (Int_t det = 0 ; det < AliQA::kNDET ; det++) 
76     fCheckers[det] = NULL ; 
77 }
78
79 //_____________________________________________________________________________
80 AliQAChecker& AliQAChecker::operator = (const AliQAChecker& qac)
81 {
82 // assignment operator
83
84   this->~AliQAChecker();
85   new(this) AliQAChecker(qac);
86   return *this;
87 }
88
89 //_____________________________________________________________________________
90 AliQAChecker::~AliQAChecker()
91 {
92 // clean up
93   if (fRunInfo)
94     delete fRunInfo ; 
95   delete [] fCheckers ; 
96   AliQA::Close() ; 
97 }
98
99 //_____________________________________________________________________________
100   AliQACheckerBase * AliQAChecker::GetDetQAChecker(Int_t det)
101 {
102         // Gets the Quality Assurance checker for the detector specified by its name
103         
104         if (fCheckers[det]) 
105     return fCheckers[det];
106
107         AliQACheckerBase * qac = NULL ;
108
109         TString detName(AliQA::GetDetName(det)) ; 
110         
111         if (det == AliQA::kGLOBAL) {
112                 qac = new AliGlobalQAChecker() ; 
113         } else if (det == AliQA::kCORR) {
114                 qac = new AliCorrQAChecker() ; 
115         } else {
116                 AliDebug(1, Form("Retrieving QA checker for %s", detName.Data())) ; 
117                 TPluginManager* pluginManager = gROOT->GetPluginManager() ;
118                 TString qacName = "Ali" + detName + "QAChecker" ;
119
120                 // first check if a plugin is defined for the quality assurance checker
121                 TPluginHandler* pluginHandler = pluginManager->FindHandler("AliQAChecker", detName.Data());
122                 // if not, add a plugin for it
123                 if (!pluginHandler) {
124                         //AliInfo(Form("defining plugin for %s", qacName.Data()));
125                         TString libs = gSystem->GetLibraries();
126                 
127                         if (libs.Contains("lib" + detName + "base.so") || (gSystem->Load("lib" + detName + "base.so") >= 0))
128                                 pluginManager->AddHandler("AliQAChecker", detName, qacName, detName + "qac", qacName + "()");
129                         else 
130                                 pluginManager->AddHandler("AliQAChecker", detName, qacName, detName, qacName + "()");
131
132                         pluginHandler = pluginManager->FindHandler("AliQAChecker", detName);    
133
134                         if (pluginHandler && (pluginHandler->LoadPlugin() == 0)) 
135                                 qac = (AliQACheckerBase *) pluginHandler->ExecPlugin(0);
136   
137                 }
138         }
139         if (qac) 
140                 fCheckers[det] = qac ;
141         
142         return qac ; 
143 }
144  
145 //_____________________________________________________________________________
146 void AliQAChecker::GetRefSubDir(const char * det, const char * task, TDirectory *& dirFile, TObjArray *& dirOCDB)     
147
148   // Opens and returns the file with the reference data 
149         
150   dirFile = NULL ; 
151   dirOCDB = NULL ; 
152   TString refStorage(AliQA::GetQARefStorage()) ; 
153   //refStorage += AliQA::GetQARefFileName() ;
154   if (refStorage.Contains(AliQA::GetLabLocalFile())) {  
155     refStorage.ReplaceAll(AliQA::GetLabLocalFile(), "") ; 
156     if ( fRefFile ) 
157       if ( fRefFile->IsOpen() ) 
158                                         fRefFile->Close() ; 
159     fRefFile = TFile::Open(refStorage.Data()) ; 
160     if (!fRefFile) { 
161       AliError(Form("Cannot find reference file %s", refStorage.Data())) ; 
162       dirFile = NULL ; 
163     }
164     dirFile = fRefFile->GetDirectory(det) ; 
165     if (!dirFile) {
166       AliWarning(Form("Directory %s not found in %d", det, refStorage.Data())) ; 
167     } else {
168                         dirFile = dirFile->GetDirectory(task) ; 
169       if (!dirFile) 
170                                 AliWarning(Form("Directory %s/%s not found in %s", det, task, refStorage.Data())) ; 
171     }  
172   } else if (refStorage.Contains(AliQA::GetLabLocalOCDB()) || refStorage.Contains(AliQA::GetLabAliEnOCDB())) {  
173     AliCDBManager* man = AliCDBManager::Instance() ;
174     if ( strcmp(AliQA::GetRefDataDirName(), "") == 0 ) { // the name of the last level of the directory is not set (RUNTYPE)
175       // Get it from RunInfo
176       if (!fRunInfo)  // not yet set, get the info from GRP
177                                 LoadRunInfoFromGRP() ; 
178       AliQA::SetQARefDataDirName(fRunInfo->GetRunType()) ;
179     }
180     if ( ! man->GetLock() ) { 
181       man->SetDefaultStorage(AliQA::GetQARefStorage()) ; 
182       man->SetSpecificStorage("*", AliQA::GetQARefStorage()) ;
183     }
184     char * detOCDBDir = Form("%s/%s/%s", det, AliQA::GetRefOCDBDirName(), AliQA::GetRefDataDirName()) ; 
185     AliInfo(Form("Reference QA data are taken from %s", detOCDBDir)) ;
186     AliCDBEntry * entry = man->Get(detOCDBDir, man->GetRun()) ;
187     if (entry) {
188       TList * listDetQAD = dynamic_cast<TList *>(entry->GetObject()) ;
189       if ( listDetQAD ) 
190                                 dirOCDB = dynamic_cast<TObjArray *>(listDetQAD->FindObject(task)) ; 
191     }
192   }
193 }
194
195 //_____________________________________________________________________________
196 AliQAChecker * AliQAChecker::Instance()
197 {
198         // returns unique instance of the checker
199   if ( ! fgQAChecker ) 
200    fgQAChecker = new AliQAChecker() ; 
201   return fgQAChecker ;  
202 }
203
204 //_____________________________________________________________________________
205 void AliQAChecker::LoadRunInfoFromGRP() 
206 {
207   AliCDBManager* man = AliCDBManager::Instance() ;
208   AliCDBEntry* entry = man->Get(AliQA::GetGRPPath().Data());
209   TMap * data = 0x0 ; 
210   if (entry) 
211     data = dynamic_cast<TMap*>(entry->GetObject());  
212   if (!data) {
213     AliFatal("No GRP entry found in OCDB!");      
214   }
215   TObjString *lhcState=  
216     dynamic_cast<TObjString*>(data->GetValue("fLHCState"));
217   if (!lhcState) {
218     AliWarning(Form("%s entry:  missing value for the LHC state ! Using UNKNOWN", AliQA::GetGRPPath().Data()));
219   }
220   TObjString *beamType=
221     dynamic_cast<TObjString*>(data->GetValue("fAliceBeamType"));
222   if (!beamType) {
223     AliWarning(Form("%s entry:  missing value for the LHC state ! Using UNKNOWN", AliQA::GetGRPPath().Data()));
224   }
225   TObjString *beamEnergyStr=
226     dynamic_cast<TObjString*>(data->GetValue("fAliceBeamEnergy"));
227   if (!beamEnergyStr) {
228     AliWarning(Form("%s entry:  missing value for the beam energy ! Using 0", AliQA::GetGRPPath().Data()));
229   }
230   TObjString *runType=
231     dynamic_cast<TObjString*>(data->GetValue("fRunType"));
232   if (!runType) {
233     AliWarning(Form("%s entry:  missing value for the run type ! Using UNKNOWN", AliQA::GetGRPPath().Data()));  }
234   TObjString *activeDetectors=
235     dynamic_cast<TObjString*>(data->GetValue("fDetectorMask"));
236   if (!activeDetectors) {
237     AliWarning(Form("%s entry:  missing value for the detector mask ! Using 1074790399", AliQA::GetGRPPath().Data()));  
238   }
239   fRunInfo = new AliRunInfo(lhcState ? lhcState->GetString().Data() : "UNKNOWN",
240                             beamType ? beamType->GetString().Data() : "UNKNOWN",
241                             beamEnergyStr ? beamEnergyStr->GetString().Atof() : 0,
242                             runType  ? runType->GetString().Data()  : "UNKNOWN",
243                             activeDetectors ? activeDetectors->GetString().Atoi() : 1074790399);
244   fRunInfoOwner = kTRUE ; 
245 }
246
247 //_____________________________________________________________________________
248 Bool_t AliQAChecker::Run(const char * fileName)
249 {
250   // run the Quality Assurance Checker for all tasks Hits, SDigits, Digits, recpoints, tracksegments, recparticles and ESDs
251   // starting from data in file
252
253   Bool_t rv = kFALSE ; 
254   
255   TStopwatch stopwatch;
256   stopwatch.Start();
257
258   //search for all detectors QA directories
259   TList * detKeyList = AliQA::GetQADataFile(fileName)->GetListOfKeys() ; 
260   TIter nextd(detKeyList) ; 
261   TKey * detKey ; 
262   while ( (detKey = dynamic_cast<TKey *>(nextd()) ) ) {
263     AliDebug(1, Form("Found %s", detKey->GetName())) ;
264     //Check which detector
265     TString detName ; 
266     TString detNameQA(detKey->GetName()) ; 
267     Int_t det ; 
268     for ( det = 0; det < AliQA::kNDET ; det++) {
269       detName = AliQA::GetDetName(det) ; 
270       if (detNameQA.Contains(detName)) {
271         fFoundDetectors+=detName ; 
272         fFoundDetectors+="." ;          
273         break ; 
274       }
275     } 
276     TDirectory * detDir = AliQA::GetQADataFile(fileName)->GetDirectory(detKey->GetName()) ; 
277     TList * taskKeyList = detDir->GetListOfKeys() ;
278     TIter nextt(taskKeyList) ; 
279     TKey * taskKey ; 
280     // now search for the tasks dir
281     while ( (taskKey = static_cast<TKey *>(nextt()) ) ) {
282       TString taskName( taskKey->GetName() ) ; 
283       AliInfo(Form("Found %s", taskName.Data())) ;
284       TDirectory * taskDir = detDir->GetDirectory(taskName.Data()) ; 
285       taskDir->cd() ; 
286       AliQACheckerBase * qac = GetDetQAChecker(det) ; 
287       if (qac)
288                 AliInfo(Form("QA checker found for %s", detName.Data())) ; 
289       if (!qac)
290                 AliFatal(Form("QA checker not found for %s", detName.Data())) ; 
291       AliQA::ALITASK_t index = AliQA::kNULLTASK ; 
292       if ( taskName == AliQA::GetTaskName(AliQA::kHITS) ) 
293                 index = AliQA::kSIM ; 
294       if ( taskName == AliQA::GetTaskName(AliQA::kSDIGITS) ) 
295                 index = AliQA::kSIM ; 
296       if ( taskName == AliQA::GetTaskName(AliQA::kDIGITS) ) 
297                 index = AliQA::kSIM ; 
298       if ( taskName == AliQA::GetTaskName(AliQA::kRECPOINTS) ) 
299                 index = AliQA::kREC ; 
300       if ( taskName == AliQA::GetTaskName(AliQA::kTRACKSEGMENTS) ) 
301                 index = AliQA::kREC ; 
302       if ( taskName == AliQA::GetTaskName(AliQA::kRECPARTICLES) ) 
303                 index = AliQA::kREC ; 
304       if ( taskName == AliQA::GetTaskName(AliQA::kESDS) ) 
305                 index = AliQA::kESD ; 
306       qac->Init(AliQA::DETECTORINDEX_t(det)) ; 
307
308           TDirectory * refDir    = NULL ; 
309           TObjArray * refOCDBDir = NULL ;       
310           GetRefSubDir(detNameQA.Data(), taskName.Data(), refDir, refOCDBDir) ;
311           if ( refDir || refOCDBDir) {
312                   qac->SetRefandData(refDir, refOCDBDir, taskDir) ;
313                   qac->Run(index) ; 
314           }
315         }
316   }
317   AliInfo("QA performed for following detectors:") ; 
318   for ( Int_t det = 0; det < AliQA::kNDET; det++) {
319     if (fFoundDetectors.Contains(AliQA::GetDetName(det))) {
320       printf("%s, ",AliQA::GetDetName(det)) ; 
321       fFoundDetectors.ReplaceAll(AliQA::GetDetName(det), "") ; 
322     }   
323   }
324   printf("\n") ; 
325   rv = kTRUE ; 
326
327   return rv ; 
328   
329 }
330
331 //_____________________________________________________________________________
332 Bool_t AliQAChecker::Run(AliQA::DETECTORINDEX_t det, AliQA::TASKINDEX_t task, TObject * obj)
333 {
334         // run the Quality Assurance Checker for detector det, for task task starting from data in list
335
336         AliQACheckerBase * qac = GetDetQAChecker(det) ; 
337         if (qac)
338                 AliDebug(1, Form("QA checker found for %s", AliQA::GetDetName(det).Data())) ;
339         if (!qac)
340                 AliError(Form("QA checker not found for %s", AliQA::GetDetName(det).Data())) ; 
341   
342         AliQA::ALITASK_t index = AliQA::kNULLTASK ; 
343         if ( task == AliQA::kRAWS ) 
344                 index = AliQA::kRAW ; 
345         else if ( task == AliQA::kHITS ) 
346                 index = AliQA::kSIM ; 
347         else if ( task == AliQA::kSDIGITS ) 
348                 index = AliQA::kSIM ; 
349         else if ( task == AliQA::kDIGITS ) 
350                 index = AliQA::kSIM ; 
351         else if ( task == AliQA::kRECPOINTS ) 
352                 index = AliQA::kREC ; 
353         else if ( task == AliQA::kTRACKSEGMENTS ) 
354                 index = AliQA::kREC ; 
355         else if ( task == AliQA::kRECPARTICLES ) 
356                 index = AliQA::kREC ; 
357         else if ( task == AliQA::kESDS ) 
358                 index = AliQA::kESD ; 
359
360         TDirectory * refDir    = NULL ; 
361         TObjArray * refOCDBDir = NULL ; 
362         qac->Init(det) ; 
363         GetRefSubDir(AliQA::GetDetName(det), AliQA::GetTaskName(task), refDir, refOCDBDir) ;
364         if ( refDir || refOCDBDir)  // references found
365           qac->SetRefandData(refDir, refOCDBDir) ; 
366         
367   TString className(obj->ClassName()) ; 
368   if (className.Contains(TObjArray::Class()->GetName())) {
369     qac->Run(index, static_cast<TObjArray *>(obj)) ; 
370   } else if (className.Contains(TNtupleD::Class()->GetName())) {
371     qac->Run(index, static_cast<TNtupleD *>(obj)) ; 
372   } else {
373     AliError(Form("%s class not implemented", className.Data())) ; 
374     return kFALSE ; 
375   }
376         return kTRUE ; 
377 }