]> git.uio.no Git - u/mrichter/AliRoot.git/blob - HLT/trigger/AliHLTTriggerAgent.cxx
Fixes for coverity
[u/mrichter/AliRoot.git] / HLT / trigger / AliHLTTriggerAgent.cxx
1 // $Id$
2
3 //**************************************************************************
4 //* This file is property of and copyright by the ALICE HLT Project        * 
5 //* ALICE Experiment at CERN, All rights reserved.                         *
6 //*                                                                        *
7 //* Primary Authors: Matthias Richter <Matthias.Richter@ift.uib.no>        *
8 //*                  for The ALICE HLT Project.                            *
9 //*                                                                        *
10 //* Permission to use, copy, modify and distribute this software and its   *
11 //* documentation strictly for non-commercial purposes is hereby granted   *
12 //* without fee, provided that the above copyright notice appears in all   *
13 //* copies and that both the copyright notice and this permission notice   *
14 //* appear in the supporting documentation. The authors make no claims     *
15 //* about the suitability of this software for any purpose. It is          *
16 //* provided "as is" without express or implied warranty.                  *
17 //**************************************************************************
18
19 /** @file   AliHLTTriggerAgent.cxx
20     @author Matthias Richter
21     @date   
22     @brief  Agent of the libAliHLTTrigger library
23 */
24
25 #include <cassert>
26 #include "AliHLTTriggerAgent.h"
27 #include "AliHLTTriggerDecision.h"
28 #include "AliHLTGlobalTriggerDecision.h"
29 #include "AliHLTOUT.h"
30 #include "AliHLTMessage.h"
31 #include "AliESDEvent.h"
32 #include "TObjString.h"
33 #include "TObjArray.h"
34 #include "TArrayC.h"
35 #include "TFile.h"
36 #include "TTree.h"
37
38 // header files of library components
39 #include "AliHLTTriggerBarrelMultiplicity.h"
40 #include "AliHLTD0Trigger.h"
41 #include "AliHLTTriggerITSMultiplicity.h"
42 #include "AliHLTTriggerBarrelGeomMultiplicity.h"
43 #include "AliHLTGlobalTriggerComponent.h"
44 #include "AliHLTTriggerPhosClusterEnergy.h"
45 #include "AliHLTTriggerEmcalClusterEnergy.h"
46 #include "AliHLTTriggerPhosMip.h"
47 #include "AliHLTTriggerTrdClusterMultiplicity.h"
48 #include "AliHLTTriggerGammaConversion.h"
49 #include "AliHLTMuonSpectroTriggerComponent.h"
50 #include "AliHLTUpcTriggerComponent.h"
51 #include "AliHLTTriggerCosmics.h"
52 #include "AliHLTTriggerCounterComponent.h"
53
54
55 /** global instance for agent registration */
56 AliHLTTriggerAgent gAliHLTTriggerAgent;
57
58 /** ROOT macro for the implementation of ROOT specific class methods */
59 ClassImp(AliHLTTriggerAgent)
60
61 AliHLTTriggerAgent::AliHLTTriggerAgent()
62   : AliHLTModuleAgent("Trigger")
63   , fTriggerDecisionHandler(NULL)
64 {
65   // see header file for class documentation
66   // or
67   // refer to README to build package
68   // or
69   // visit http://web.ift.uib.no/~kjeks/doc/alice-hlt
70 }
71
72 AliHLTTriggerAgent::~AliHLTTriggerAgent()
73 {
74   // see header file for class documentation
75 }
76
77 int AliHLTTriggerAgent::RegisterComponents(AliHLTComponentHandler* pHandler) const
78 {
79   // see header file for class documentation
80   assert(pHandler);
81   if (!pHandler) return -EINVAL;
82   pHandler->AddComponent(new AliHLTGlobalTriggerComponent);
83   pHandler->AddComponent(new AliHLTTriggerBarrelMultiplicity);
84   pHandler->AddComponent(new AliHLTTriggerITSMultiplicity);
85   pHandler->AddComponent(new AliHLTD0Trigger);
86   pHandler->AddComponent(new AliHLTTriggerBarrelGeomMultiplicity);
87   pHandler->AddComponent(new AliHLTTriggerPhosClusterEnergy); 
88   pHandler->AddComponent(new AliHLTTriggerEmcalClusterEnergy); 
89   pHandler->AddComponent(new AliHLTTriggerPhosMip); 
90   pHandler->AddComponent(new AliHLTTriggerTrdClusterMultiplicity);
91   pHandler->AddComponent(new AliHLTTriggerGammaConversion);
92   pHandler->AddComponent(new AliHLTMuonSpectroTriggerComponent);
93   pHandler->AddComponent(new AliHLTUpcTriggerComponent);
94   pHandler->AddComponent(new AliHLTTriggerCosmics);
95   pHandler->AddComponent(new AliHLTTriggerCounterComponent);
96   return 0;
97 }
98
99 int AliHLTTriggerAgent::CreateConfigurations(AliHLTConfigurationHandler* pHandler,
100                                             AliRawReader* rawReader,
101                                             AliRunLoader* runloader) const
102 {
103   // see header file for class documentation
104   if (!pHandler) return -EINVAL;
105
106   TString triggerInputs;
107   TString triggerOutputs;
108   TString configurationId;
109   /////////////////////////////////////////////////////////////////////////////////////
110   //
111   // a central barrel charged particle multiplicity trigger
112   configurationId="TRIGGER-Barrel-Multiplicity";
113
114   // define the inputs for the BarrelMultiplicityTrigger
115   triggerInputs="GLOBAL-esd-converter";
116
117   // check for the availibility
118   TObjArray* pTokens=triggerInputs.Tokenize(" ");
119   triggerInputs="";
120   if (pTokens) {
121     for (int n=0; n<pTokens->GetEntriesFast(); n++) {
122       TString module=((TObjString*)pTokens->At(n))->GetString();
123       if (pHandler->FindConfiguration(module.Data())) {
124         triggerInputs+=module;
125         triggerInputs+=" ";
126       }
127     }
128     delete pTokens;
129   }
130
131   TString arg;
132   if (triggerInputs.Length()>0) {
133     // define multiple instances of the BarrelMultiplicityTrigger with different settings
134     HLTInfo("Configuring inputs for %s: %s", configurationId.Data(), triggerInputs.Data());
135     pHandler->CreateConfiguration(configurationId.Data(), "BarrelMultiplicityTrigger", triggerInputs.Data(), "");
136     if (triggerOutputs.Length()>0) triggerOutputs+=" ";
137     triggerOutputs+=configurationId;
138
139     configurationId="TRIGGER-Barrel-HighMultiplicity";
140     arg="-triggername BarrelHighMultiplicity";
141     pHandler->CreateConfiguration(configurationId.Data(), "BarrelMultiplicityTrigger", triggerInputs.Data(), arg.Data());
142     if (triggerOutputs.Length()>0) triggerOutputs+=" ";
143     triggerOutputs+=configurationId;
144
145     configurationId="TRIGGER-Barrel-Pt_v01";
146     arg="-triggername BarrelPt_v01";
147     pHandler->CreateConfiguration(configurationId.Data(), "BarrelMultiplicityTrigger", triggerInputs.Data(), arg.Data());
148     if (triggerOutputs.Length()>0) triggerOutputs+=" ";
149     triggerOutputs+=configurationId;
150
151     configurationId="TRIGGER-Barrel-Pt_v02";
152     arg="-triggername BarrelPt_v02";
153     pHandler->CreateConfiguration(configurationId.Data(), "BarrelMultiplicityTrigger", triggerInputs.Data(), arg.Data());
154     if (triggerOutputs.Length()>0) triggerOutputs+=" ";
155     triggerOutputs+=configurationId;
156
157     configurationId="TRIGGER-Barrel-Pt_v03";
158     arg="-triggername BarrelPt_v03";
159     pHandler->CreateConfiguration(configurationId.Data(), "BarrelMultiplicityTrigger", triggerInputs.Data(), arg.Data());
160     if (triggerOutputs.Length()>0) triggerOutputs+=" ";
161     triggerOutputs+=configurationId;
162   } else {
163     HLTWarning("No inputs for %s found, skipping component", configurationId.Data());
164   }
165   
166   /////////////////////////////////////////////////////////////////////////////////////
167   // The muon spectrometer trigger
168   configurationId = "TRIGGER-Muon-Spectrometer";
169
170   // define the inputsfor the muon spectrometer trigger.
171   if (pHandler->FindConfiguration("dHLT-sim-fromRaw")) {
172     triggerInputs = "dHLT-sim-fromRaw";
173   }
174   else if (pHandler->FindConfiguration("dHLT-sim")) {
175     triggerInputs = "dHLT-sim";
176   }
177   else if (pHandler->FindConfiguration("dHLT-sim-fromMC")) {
178     triggerInputs = "dHLT-sim-fromMC";
179   }
180
181   if (triggerInputs.Length() > 0) {
182     HLTInfo("Configuring inputs for %s: %s", configurationId.Data(), triggerInputs.Data());
183     pHandler->CreateConfiguration(configurationId.Data(), "MuonSpectroTrigger", triggerInputs.Data(), "-makestats");
184     if (triggerOutputs.Length() > 0) triggerOutputs += " ";
185     triggerOutputs += configurationId;
186   } else {
187     HLTWarning("No inputs for %s found, skipping component.", configurationId.Data());
188   }
189
190   /////////////////////////////////////////////////////////////////////////////////////
191   // D0 trigger
192   configurationId = "TRIGGER-D0";
193   if(runloader && !rawReader){
194     // simulation without simulated raw data
195     // use ESD as input
196     triggerInputs="GLOBAL-esd-converter ";
197   }
198   else{
199     // simulation with simulated raw data, or raw data reconstruction
200     // use input from ITS tracker and vertexer directly
201     triggerInputs="ITS-tracker GLOBAL-vertexer";
202   }
203
204   // check for the availibility of inputs
205   pTokens=triggerInputs.Tokenize(" ");
206   triggerInputs="";
207   if (pTokens) {
208     for (int n=0; n<pTokens->GetEntriesFast(); n++) {
209       TString module=((TObjString*)pTokens->At(n))->GetString();
210       if (pHandler->FindConfiguration(module.Data())) {
211         triggerInputs+=module;
212         triggerInputs+=" ";
213       }
214     }
215     delete pTokens;
216   }
217
218   TString argD0 = "";
219   if (triggerInputs.Length()>0) {
220     HLTInfo("Configuring inputs for %s: %s", configurationId.Data(), triggerInputs.Data());
221     pHandler->CreateConfiguration(configurationId.Data(), "D0Trigger", triggerInputs.Data(), argD0.Data());
222     // FIXME: due to a rare segfault for reconstruction of PbPb data the
223     // component is temporarily excluded
224     // https://savannah.cern.ch/bugs/?72590
225     //if (triggerOutputs.Length()>0) triggerOutputs+=" ";
226     //triggerOutputs+=configurationId;
227   } else {
228     HLTWarning("No inputs for %s found, skipping component", configurationId.Data());
229   }
230
231   /////////////////////////////////////////////////////////////////////////////////////
232   //
233   // the global trigger component
234   configurationId="GLOBAL-Trigger";
235   HLTInfo("setting inputs for %s: %s", configurationId.Data(), triggerOutputs.IsNull()?"none":triggerOutputs.Data());
236   pHandler->CreateConfiguration(configurationId.Data(), "HLTGlobalTrigger", triggerOutputs.Data(), "");
237   
238   return 0;
239 }
240
241 const char* AliHLTTriggerAgent::GetReconstructionChains(AliRawReader* /*rawReader*/,
242                                                     AliRunLoader* runloader) const
243 {
244   // see header file for class documentation
245   if (runloader) {
246     // reconstruction chains for AliRoot simulation
247     // Note: run loader is only available while running embedded into
248     // AliRoot simulation
249
250     // currently disabled due to a problem compiling the runtime trigger library
251     return "GLOBAL-Trigger";
252   }
253   return NULL;
254 }
255
256 const char* AliHLTTriggerAgent::GetRequiredComponentLibraries() const
257 {
258   // see header file for class documentation
259
260   return "";
261 }
262
263 int AliHLTTriggerAgent::GetHandlerDescription(AliHLTComponentDataType dt,
264                                            AliHLTUInt32_t /*spec*/,
265                                           AliHLTOUTHandlerDesc& desc) const
266 {
267   // see header file for class documentation
268
269   // handler of the trigger decisions {'ROOTTOBJ':'HLT '}
270   // currently stored as a TObject with the common data type and origin
271   // HLTOUT. However we might need a separate data type in order to
272   // avoid interference with other handlers
273   // the handler produces an ESD object in order to be merged to the
274   // hltEsd afterwards
275   // 2009-11-17 adding the data tyepes for (global) trigger decisions
276   // the TObject data types stays for a while in order to preserve
277   // backward compatibility
278   if (dt==(kAliHLTDataTypeTObject|kAliHLTDataOriginOut) ||
279       dt==kAliHLTDataTypeTriggerDecision ||
280       dt==kAliHLTDataTypeGlobalTrigger) {
281     desc=AliHLTOUTHandlerDesc(AliHLTModuleAgent::kEsd, dt, GetModuleId());
282     return 1;
283   }
284
285   // handler for the HLT readou list and trigger data data blocks {'HLTRDLST':'HLT '}
286   if (dt==AliHLTComponentDataTypeInitializer("HLTRDLST", kAliHLTDataOriginOut) ||
287       dt==AliHLTComponentDataTypeInitializer("HLTTRGDT", kAliHLTDataOriginOut)) {
288       desc=AliHLTOUTHandlerDesc(kProprietary, dt, GetModuleId());
289       return 1;
290   }
291
292   return 0;
293 }
294
295 AliHLTOUTHandler* AliHLTTriggerAgent::GetOutputHandler(AliHLTComponentDataType dt,
296                                                        AliHLTUInt32_t /*spec*/)
297 {
298   // see header file for class documentation
299
300   // raw data blocks to be fed into offline reconstruction
301   if ((dt==(kAliHLTDataTypeTObject|kAliHLTDataOriginOut) ||
302        (dt==kAliHLTDataTypeTriggerDecision) ||
303        (dt==kAliHLTDataTypeGlobalTrigger))) {
304     if (!fTriggerDecisionHandler) {
305       fTriggerDecisionHandler=new AliHLTTriggerAgent::AliHLTTriggerDecisionHandler;
306     }
307     return fTriggerDecisionHandler;
308   }
309
310   // handler for the HLT readou list and trigger data data blocks {'HLTRDLST':'HLT '}
311   if (dt==AliHLTComponentDataTypeInitializer("HLTRDLST", kAliHLTDataOriginOut) ||
312       dt==AliHLTComponentDataTypeInitializer("HLTTRGDT", kAliHLTDataOriginOut)) {
313     return NULL;
314   }
315
316   return NULL;
317 }
318
319 int AliHLTTriggerAgent::DeleteOutputHandler(AliHLTOUTHandler* pInstance)
320 {
321   // see header file for class documentation
322   if (pInstance==NULL) return -EINVAL;
323
324   if (pInstance==fTriggerDecisionHandler) {
325     delete fTriggerDecisionHandler;
326     fTriggerDecisionHandler=NULL;
327   }
328
329   return 0;
330 }
331
332 AliHLTTriggerAgent::AliHLTTriggerDecisionHandler::AliHLTTriggerDecisionHandler()
333   : AliHLTOUTHandler() 
334   , fESD(NULL)
335   , fpData(NULL)
336   , fSize(0)
337   , fpESDfile(NULL)
338   , fpESDtree(NULL)
339 {
340   // see header file for class documentation
341 }
342
343 AliHLTTriggerAgent::AliHLTTriggerDecisionHandler::~AliHLTTriggerDecisionHandler()
344 {
345   // see header file for class documentation
346   if (fpESDtree) {
347     fpESDtree->GetUserInfo()->Clear();
348     delete fpESDtree;
349   }
350   fpESDtree=NULL;
351
352   if (fpESDfile) {
353     fpESDfile->Close();
354     delete fpESDfile;
355   }
356   fpESDfile=NULL;
357
358   if (fESD) delete fESD;
359   fESD=NULL;
360
361   if (fpData) delete fpData;
362   fpData=NULL;
363   fSize=0;
364 }
365
366 int AliHLTTriggerAgent::AliHLTTriggerDecisionHandler::ProcessData(AliHLTOUT* pData)
367 {
368   // see header file for class documentation
369   if (!pData) return -EINVAL;
370   int iResult=0;
371   AliHLTGlobalTriggerDecision* pGlobalDecision=NULL;
372   TObjArray triggerDecisions;
373   triggerDecisions.SetOwner(kTRUE);
374   for (iResult=pData->SelectFirstDataBlock(); iResult>=0; iResult=pData->SelectNextDataBlock()) {
375     AliHLTComponentDataType dt=kAliHLTVoidDataType;
376     AliHLTUInt32_t spec=kAliHLTVoidDataSpec;
377     if ((iResult=pData->GetDataBlockDescription(dt, spec))<0) break;
378     TObject* pObject=pData->GetDataObject();
379     if (pObject) {
380       if(dt==kAliHLTDataTypeGlobalTrigger) {
381         if (!pGlobalDecision) {
382           if ((pGlobalDecision=dynamic_cast<AliHLTGlobalTriggerDecision*>(pObject))==NULL ||
383               (pGlobalDecision=dynamic_cast<AliHLTGlobalTriggerDecision*>(pGlobalDecision->Clone()))==NULL) {
384             HLTFatal("can not convert object of name %s (%s) to HLTGlobalTriggerDecsion according to data type", pObject->GetName(), pObject->Class()->GetName());
385           }
386         } else {
387           HLTWarning("multiple HLT GlobalTrigger decision objects, ignoring all but the first one");
388         }
389       } else if (dt==kAliHLTDataTypeTriggerDecision) {
390         if (pObject->IsA() == AliHLTTriggerDecision::Class() &&
391             !(pObject->IsA() == AliHLTGlobalTriggerDecision::Class())) {
392           AliHLTTriggerDecision* pDecision=dynamic_cast<AliHLTTriggerDecision*>(pObject);
393           if (pDecision) {
394             if (pGlobalDecision) {
395               // add directly
396               pGlobalDecision->AddTriggerInput(*pDecision);
397             } else {
398               // schedule
399               triggerDecisions.Add(pDecision->Clone());
400             }
401           } else {
402             HLTFatal("can not convert object of name %s (%s) to HLT TriggerDecsion according to data type", pObject->GetName(), pObject->Class()->GetName());
403           }
404         }
405       } else if (dt==(kAliHLTDataTypeTObject|kAliHLTDataOriginOut)){
406         // this is the branch for keeping compatibility
407         // the first version of the trigger framework was using the kAliHLTDataTypeTObject
408         // data type instead of the specific data types for HLT triggers
409           // this effects the cosmic data taken Sep to Oct 2009
410         if (pObject->IsA() == AliHLTGlobalTriggerDecision::Class()) {
411           if (!pGlobalDecision) {
412             if ((pGlobalDecision=dynamic_cast<AliHLTGlobalTriggerDecision*>(pObject))==NULL ||
413                 (pGlobalDecision=dynamic_cast<AliHLTGlobalTriggerDecision*>(pGlobalDecision->Clone()))==NULL) {
414               HLTFatal("can not convert object of name %s (%s) to HLTGlobalTriggerDecsion according to data type", pObject->GetName(), pObject->Class()->GetName());
415             }
416           } else {
417             HLTWarning("multiple HLT GlobalTrigger decision objects, ignoring all but the first one");
418           }
419         } else if (pObject->IsA() == AliHLTTriggerDecision::Class()) {
420           AliHLTTriggerDecision* pDecision=dynamic_cast<AliHLTTriggerDecision*>(pObject);
421           if (pDecision) {
422             if (pGlobalDecision) {
423               // add directly
424               pGlobalDecision->AddTriggerInput(*pDecision);
425             } else {
426               // schedule
427               triggerDecisions.Add(pDecision->Clone());
428             }
429           } else {
430             HLTFatal("can not convert object of name %s (%s) to HLT TriggerDecsion according to data type", pObject->GetName(), pObject->Class()->GetName());
431           }
432         }
433       }
434       pData->ReleaseDataObject(pObject);
435       pObject=NULL;
436     } else {
437       HLTError("can not get TObject from HLTOUT buffer");
438       iResult=-ENODATA;
439     }
440   }
441   // -ENOENT just signals that there  are no more entries
442   if (iResult==-ENOENT) iResult=0;
443
444   if (pGlobalDecision) {
445     for (int i=0; i<triggerDecisions.GetEntriesFast(); i++) {
446       if (triggerDecisions[i]) {
447         pGlobalDecision->AddTriggerInput(*((AliHLTTriggerDecision*)triggerDecisions[i]));
448       }
449     }
450     triggerDecisions.Delete();
451     AliHLTTriggerDecision* pDecision=pGlobalDecision;
452     {
453       if (pDecision) {
454         //pDecision->Print();
455         HLTDebug("extracted %s", pDecision->GetName());
456         if (!fESD) {
457           // create the ESD container, but without std content
458           fESD = new AliESDEvent;
459         }
460         if (!fpData) fpData=new TArrayC;
461         if (fESD && fpData) {
462           fESD->Reset();
463           TObject* pESDObject=fESD->FindListObject("HLTGlobalTrigger");
464           if (pESDObject) {
465             // copy the content to the already existing object
466             pDecision->Copy(*pESDObject);
467           } else {
468             // add a new object
469             fESD->AddObject(pDecision->Clone());
470           }
471           WriteESD();
472           AliHLTMessage* pMsg=AliHLTMessage::Stream(fESD);
473           if (pMsg) {
474             if (!pMsg->CompBuffer()) {
475               fSize=pMsg->Length();
476               fpData->Set(fSize, pMsg->Buffer());
477             } else {
478               fSize=pMsg->CompLength();
479               fpData->Set(fSize, pMsg->CompBuffer());
480             }
481             delete pMsg;
482             pMsg=NULL;
483           } else {
484             HLTError("streaming of objects failed");
485           }
486         } else {
487           HLTError("memory allocation failed");
488           iResult=-ENOMEM;
489         }
490       }
491     }
492     delete pGlobalDecision;
493     pGlobalDecision=NULL;
494   } else {
495     HLTError("no global trigger found in data collection");
496   }
497
498   if (iResult>=0) {
499     return fSize;
500   }
501   fSize=0;
502   return iResult;
503 }
504
505 int AliHLTTriggerAgent::AliHLTTriggerDecisionHandler::GetProcessedData(const AliHLTUInt8_t* &pData)
506 {
507   // see header file for class documentation
508   if (!fpData) {
509     pData=NULL;
510     return 0;
511   }
512
513   pData=reinterpret_cast<AliHLTUInt8_t*>(fpData->GetArray());
514   return fSize;
515 }
516
517 int AliHLTTriggerAgent::AliHLTTriggerDecisionHandler::ReleaseProcessedData(const AliHLTUInt8_t* pData, int size)
518 {
519   // see header file for class documentation
520   int iResult=0;
521   if (!fpData || size != fSize ||
522       const_cast<AliHLTUInt8_t*>(pData) != reinterpret_cast<AliHLTUInt8_t*>(fpData->GetArray())) {
523     HLTError("attempt to release to wrong data buffer %p size %d, expected %p size %d", pData, size, fpData?fpData->GetArray():NULL, fSize);
524   }
525   fSize=0;
526   return iResult;
527 }
528
529 int AliHLTTriggerAgent::AliHLTTriggerDecisionHandler::WriteESD()
530 {
531   // see header file for class documentation
532   int iResult=0;
533   if (!fESD) return 0;
534   if (!fpESDfile) {
535     fpESDfile=new TFile("HLTdecision.root", "RECREATE");
536   }
537   if (!fpESDtree) {
538     fpESDtree=new TTree("HLTesdTree", "Tree with HLT ESD containing HLT decision");
539     if (fpESDtree) {
540       fESD->WriteToTree(fpESDtree);
541       fpESDtree->GetUserInfo()->Add(fESD);
542     }
543   }
544   if (!fpESDfile || !fpESDtree) return -ENOMEM;
545
546   fpESDtree->Fill();
547   fpESDfile->cd();
548   fpESDtree->Write(fpESDtree->GetName(),TObject::kOverwrite);
549
550   return iResult;
551 }