1 /**************************************************************************
2 * This file is property of and copyright by the ALICE HLT Project *
3 * ALICE Experiment at CERN, All rights reserved. *
5 * Primary Authors: Artur Szostak <artursz@iafrica.com> *
6 * for The ALICE HLT Project. *
8 * Permission to use, copy, modify and distribute this software and its *
9 * documentation strictly for non-commercial purposes is hereby granted *
10 * without fee, provided that the above copyright notice appears in all *
11 * copies and that both the copyright notice and this permission notice *
12 * appear in the supporting documentation. The authors make no claims *
13 * about the suitability of this software for any purpose. It is *
14 * provided "as is" without express or implied warranty. *
15 **************************************************************************/
18 * @file testGlobalTriggerComponent.C
19 * @author Artur Szostak <artursz@iafrica.com>
22 * This macro is used to test the AliHLTGlobalTriggerComponent class.
23 * A number of tests are run with the AliHLTSystem framework to check that
24 * the automatically generated global trigger logic is generated correctly.
27 #if defined(__CINT__) && (! defined(__MAKECINT__))
28 #error This macro must be compiled. Try running as testGlobalTriggerComponent.C++
31 #if !defined(__CINT__) || defined(__MAKECINT__)
33 #include "TClassTable.h"
36 #include "AliHLTReadoutList.h"
37 #include "AliHLTTriggerDomain.h"
38 #include "AliHLTTriggerDecision.h"
39 #include "AliHLTGlobalTriggerDecision.h"
40 #include "AliHLTSystem.h"
41 #include "AliHLTConfiguration.h"
42 #include "AliHLTConfigurationHandler.h"
43 #include "Riostream.h"
47 * Generates some sample input data and writes it into 8 files named
48 * testInputFile1.root ... testInputFile8.root
50 void GenerateInputData()
52 if (gClassTable->GetID("AliHLTGlobalTriggerComponent") < 0)
54 gSystem->Load("libAliHLTUtil.so");
55 gSystem->Load("libAliHLTTRD.so");
56 gSystem->Load("libAliHLTTrigger.so");
59 AliHLTReadoutList readoutList1("TPC");
60 AliHLTTriggerDomain triggerDomain1;
61 triggerDomain1.Add("CLUSTERS", "TPC ");
62 triggerDomain1.Add("TRACKS", "TPC ");
63 triggerDomain1.Add(readoutList1);
64 AliHLTTriggerDecision decision1(true, "triggerTPC", triggerDomain1, "TPC has data");
66 AliHLTReadoutList readoutList2a("MUONTRK");
67 AliHLTReadoutList readoutList2b("MUONTRG");
68 AliHLTTriggerDomain triggerDomain2;
69 triggerDomain2.Add("TRACKS", "MUON");
70 triggerDomain2.Add(readoutList2a);
71 triggerDomain2.Add(readoutList2b);
72 AliHLTTriggerDecision decision2(true, "triggerMUON", triggerDomain2, "MUON has data");
74 AliHLTReadoutList readoutList3("ITSSSD");
75 AliHLTTriggerDomain triggerDomain3;
76 triggerDomain3.Add("*******", "SSD ");
77 triggerDomain3.Add(readoutList3);
78 AliHLTTriggerDecision decision3(true, "triggerSSD", triggerDomain3, "SSD has data");
80 TFile* file = new TFile("testInputFile1.root", "RECREATE");
81 decision1.Write("triggerTPC");
82 decision2.Write("triggerMUON");
83 decision3.Write("triggerSSD");
86 file = new TFile("testInputFile2.root", "RECREATE");
87 decision1.Write("triggerTPC");
90 file = new TFile("testInputFile3.root", "RECREATE");
91 decision2.Write("triggerMUON");
94 file = new TFile("testInputFile4.root", "RECREATE");
95 decision3.Write("triggerSSD");
98 file = new TFile("testInputFile5.root", "RECREATE");
99 decision1.Write("triggerTPC");
100 decision2.Write("triggerMUON");
103 file = new TFile("testInputFile6.root", "RECREATE");
104 decision1.Write("triggerTPC");
105 decision3.Write("triggerSSD");
108 file = new TFile("testInputFile7.root", "RECREATE");
109 decision2.Write("triggerMUON");
110 decision3.Write("triggerSSD");
113 file = new TFile("testInputFile8.root", "RECREATE");
118 * Runs a small global trigger test chain with the different configuration as specified
119 * in TriggerConfig.C.
120 * \param config The configuration version to pass to TriggerConfig.C
121 * \param usecint If true then the global trigger component uses CINT to interpret
122 * the code rather than compiling it.
123 * \param debug If true then the global trigger component generates extra debug
124 * statements in the on the fly AliHLTGlobalTriggerImp_*.cxx file.
125 * \param numOfEvents The number of events to run the chain for.
126 * \param customClass Names the custom class that should be loaded from the file
127 * <i>\<customClass\>.cxx</i>. This is useful for debugging only. i.e. you can
128 * edit a generated logic file and test it by hand.
130 void RunTrigger(int config = 0, bool usecint = false, bool debug = false, int numOfEvents = 8, const char* customClass = NULL)
133 sys.fpConfigurationHandler->SetLocalLoggingLevel(kHLTLogAll);
134 sys.LoadComponentLibraries("libAliHLTUtil.so");
135 sys.LoadComponentLibraries("libAliHLTTRD.so");
136 sys.LoadComponentLibraries("libAliHLTTrigger.so");
139 AliLog::SetGlobalLogLevel(AliLog::kMaxType);
140 sys.SetGlobalLoggingLevel(kHLTLogAll);
143 TString cmdline = "-datatype ROOTTOBJ 'HLT ' ";
144 for (int i = 1; i <= 8; i++)
146 if (i > 1) cmdline += " -nextevent";
147 cmdline += Form(" -datafile testInputFile%d.root", i);
149 AliHLTConfiguration pub("pub", "ROOTFilePublisher", NULL, cmdline.Data());
151 cmdline = Form("-config TriggerConfig.C(%d) -includepath $ALICE_ROOT/include -includepath $ALICE_ROOT/HLT/BASE"
152 " -includepath $ALICE_ROOT/HLT/trigger -include AliHLTEventSummary.h",
155 if (customClass != NULL) cmdline += Form(" -usecode %s.cxx %s", customClass, customClass);
156 if (usecint) cmdline += " -cint";
157 if (debug) cmdline += " -debug";
158 AliHLTConfiguration proc("proc", "HLTGlobalTrigger", "pub", cmdline.Data());
160 AliHLTConfiguration sink("sink", "ROOTFileWriter", "proc", "-datafile testOutputFile.root -concatenate-events");
162 sys.BuildTaskList("sink");
163 sys.Run(numOfEvents);
167 * Checks that a particular decision is as expected and prints error messages
169 * \param testName The name of the test being run.
170 * \param eventNum The number of the event being checked.
171 * \param decision The global trigger decision being checked.
172 * \param expectedResult The expected global trigger result.
173 * \param expectedDomain The expected resulting global trigger domain.
174 * \param expectedDescription The expected resulting trigger description.
175 * \returns true if the decision is as expected.
178 const char* testName,
180 AliHLTGlobalTriggerDecision* decision,
182 AliHLTTriggerDomain expectedDomain,
183 TString expectedDescription
186 if (decision == NULL)
188 cerr << "ERROR (Test: " << testName
189 << "): No decision found where expected for event "
190 << eventNum << "." << endl;
193 if (decision->Result() != expectedResult)
195 cerr << "ERROR (Test: " << testName
196 << "): The result does not match the expected value for event "
197 << eventNum << ". Got " << decision->Result() << " but expected "
198 << expectedResult << "." << endl;
201 if (decision->TriggerDomain() != expectedDomain)
203 cerr << "ERROR (Test: " << testName
204 << "): The domain does not match the expected value for event "
205 << eventNum << ". Got:" << endl;
206 decision->TriggerDomain().Print();
207 cout << "but expected:" << endl;
208 expectedDomain.Print();
211 if (decision->Description() != expectedDescription)
213 cerr << "ERROR (Test: " << testName
214 << "): The description does not match the expected value for event "
215 << eventNum << ". Got '" << decision->Description() << "' but expected '"
216 << expectedDescription << "'." << endl;
223 /// Routine for checking the result of the PriorityGroupTestConfig() config in TriggerConfig.C
224 bool CheckPriorityGroupTestConfig(const char* testName = "Priority group config")
226 AliHLTGlobalTriggerDecision* decision = NULL;
229 AliHLTTriggerDomain domainTPC("CLUSTERS:TPC ,TRACKS:TPC ");
230 domainTPC.Add(AliHLTReadoutList("TPC"));
231 AliHLTTriggerDomain domainMUON("TRACKS:MUON");
232 domainMUON.Add(AliHLTReadoutList("MUONTRK"));
233 domainMUON.Add(AliHLTReadoutList("MUONTRG"));
234 AliHLTTriggerDomain domainSSD("*******:SSD ");
235 domainSSD.Add(AliHLTReadoutList("ITSSSD"));
237 TFile* file = new TFile("testOutputFile.root", "READ");
239 // Triggers in events (i.e. input triggers):
240 // event 1: TPC MUON SSD
248 decision = dynamic_cast<AliHLTGlobalTriggerDecision*>(file->Get("HLTGlobalTrigger;1"));
249 result = Check(testName, 1, decision, true, domainSSD, "Fast SSD trigger");
250 if (! result) goto cleanup;
251 decision = dynamic_cast<AliHLTGlobalTriggerDecision*>(file->Get("HLTGlobalTrigger;2"));
252 result = Check(testName, 2, decision, true, domainTPC, "TPC trigger");
253 if (! result) goto cleanup;
254 decision = dynamic_cast<AliHLTGlobalTriggerDecision*>(file->Get("HLTGlobalTrigger;3"));
255 result = Check(testName, 3, decision, true, domainMUON, "MUON trigger");
256 if (! result) goto cleanup;
257 decision = dynamic_cast<AliHLTGlobalTriggerDecision*>(file->Get("HLTGlobalTrigger;4"));
258 result = Check(testName, 4, decision, true, domainSSD, "MUON trigger");
259 if (! result) goto cleanup;
260 decision = dynamic_cast<AliHLTGlobalTriggerDecision*>(file->Get("HLTGlobalTrigger;5"));
261 result = Check(testName, 5, decision, true, domainMUON, "MUON trigger");
262 if (! result) goto cleanup;
263 decision = dynamic_cast<AliHLTGlobalTriggerDecision*>(file->Get("HLTGlobalTrigger;6"));
264 result = Check(testName, 6, decision, true, domainSSD, "Fast SSD trigger");
265 if (! result) goto cleanup;
266 decision = dynamic_cast<AliHLTGlobalTriggerDecision*>(file->Get("HLTGlobalTrigger;7"));
267 result = Check(testName, 7, decision, true, domainMUON | domainSSD, "MUON trigger");
268 if (! result) goto cleanup;
269 decision = dynamic_cast<AliHLTGlobalTriggerDecision*>(file->Get("HLTGlobalTrigger;8"));
270 result = Check(testName, 8, decision, false, AliHLTTriggerDomain(), "No trigger");
271 if (! result) goto cleanup;
277 if (decision != NULL)
279 cout << "========== Dumping incorrect decision ========== " << endl;
287 /// Routine for checking the result of the SingleGroupTestConfig() config in TriggerConfig.C
288 bool CheckSingleGroupTestConfig(const char* testName = "Single group config")
290 AliHLTGlobalTriggerDecision* decision = NULL;
293 AliHLTTriggerDomain domainTPC("CLUSTERS:TPC ,TRACKS:TPC ");
294 domainTPC.Add(AliHLTReadoutList("TPC"));
295 AliHLTTriggerDomain domainMUON("TRACKS:MUON");
296 domainMUON.Add(AliHLTReadoutList("MUONTRK"));
297 domainMUON.Add(AliHLTReadoutList("MUONTRG"));
298 AliHLTTriggerDomain domainSSD("*******:SSD ");
299 domainSSD.Add(AliHLTReadoutList("ITSSSD"));
301 TFile* file = new TFile("testOutputFile.root", "READ");
303 // Triggers in events (i.e. input triggers):
304 // event 1: TPC MUON SSD
312 decision = dynamic_cast<AliHLTGlobalTriggerDecision*>(file->Get("HLTGlobalTrigger;1"));
313 result = Check(testName, 1, decision, true, domainTPC | domainMUON | domainSSD, "TPC trigger,MUON trigger,SSD trigger");
314 if (! result) goto cleanup;
315 decision = dynamic_cast<AliHLTGlobalTriggerDecision*>(file->Get("HLTGlobalTrigger;2"));
316 result = Check(testName, 2, decision, true, domainTPC, "TPC trigger");
317 if (! result) goto cleanup;
318 decision = dynamic_cast<AliHLTGlobalTriggerDecision*>(file->Get("HLTGlobalTrigger;3"));
319 result = Check(testName, 3, decision, true, domainMUON, "MUON trigger");
320 if (! result) goto cleanup;
321 decision = dynamic_cast<AliHLTGlobalTriggerDecision*>(file->Get("HLTGlobalTrigger;4"));
322 result = Check(testName, 4, decision, true, domainSSD, "SSD trigger");
323 if (! result) goto cleanup;
324 decision = dynamic_cast<AliHLTGlobalTriggerDecision*>(file->Get("HLTGlobalTrigger;5"));
325 result = Check(testName, 5, decision, true, domainTPC | domainMUON, "TPC trigger,MUON trigger");
326 if (! result) goto cleanup;
327 decision = dynamic_cast<AliHLTGlobalTriggerDecision*>(file->Get("HLTGlobalTrigger;6"));
328 result = Check(testName, 6, decision, true, domainTPC | domainSSD, "TPC trigger,SSD trigger");
329 if (! result) goto cleanup;
330 decision = dynamic_cast<AliHLTGlobalTriggerDecision*>(file->Get("HLTGlobalTrigger;7"));
331 result = Check(testName, 7, decision, true, domainMUON | domainSSD, "MUON trigger,SSD trigger");
332 if (! result) goto cleanup;
333 decision = dynamic_cast<AliHLTGlobalTriggerDecision*>(file->Get("HLTGlobalTrigger;8"));
334 result = Check(testName, 8, decision, false, AliHLTTriggerDomain(), "");
335 if (! result) goto cleanup;
341 if (decision != NULL)
343 cout << "========== Dumping incorrect decision ========== " << endl;
351 typedef bool (*CheckFunctionType)(const char* testName);
354 * This will check the results of a global trigger run with a particular checking
355 * routine and for different combinations of -cint and -debug flags passed to the
356 * global trigger component.
357 * It is important to check these flag combinations to make sure that everything
358 * is functioning the same under all the different combinations as it should.
359 * \param function The checking routine to use.
360 * \param version The trigger menu configuration version to use in <i>RunTrigger</i>.
361 * \param testName The name of the test being run.
362 * \param numOfEvents The number of events to run the chain for.
363 * \param customClass Name of the custom class as passed to <i>RunTrigger</i>.
364 * \returns true if the different checks succeeded and false otherwise.
366 bool CheckDifferentModes(CheckFunctionType function, int version, const char* testName, int numOfEvents = 8, const char* customClass = NULL)
368 TString name = testName;
369 RunTrigger(version, false, false, numOfEvents, customClass);
370 if (! function(testName)) return false;
371 gSystem->Exec("rm -f testOutputFile.root"); // Cleanup output file for next test.
374 name += " interpreted with CINT";
375 RunTrigger(version, true, false, numOfEvents, customClass);
376 if (! function(testName)) return false;
377 gSystem->Exec("rm -f testOutputFile.root"); // Cleanup output file for next test.
380 name += " in debug mode";
381 RunTrigger(version, false, true, numOfEvents, customClass);
382 if (! function(testName)) return false;
383 gSystem->Exec("rm -f testOutputFile.root"); // Cleanup output file for next test.
386 name += " interpreted with CINT in debug mode";
387 RunTrigger(version, true, true, numOfEvents, customClass);
388 if (! function(testName)) return false;
389 gSystem->Exec("rm -f testOutputFile.root"); // Cleanup output file for next test.
395 * Runs several tests for the AliHLTGlobalTriggerComponent class.
396 * We specifically test if the global trigger menu configuration is interpreted
397 * correctly and the trigger logic generated correctly on the fly.
398 * \param numOfEvents The number of events to run the chain for.
399 * \param customClass Name of the custom class as passed to <i>CheckDifferentModes</i>.
400 * \returns true if the different checks succeeded and false otherwise.
402 bool testGlobalTriggerComponent(int numOfEvents = 8, const char* customClass = NULL)
406 if (! CheckDifferentModes(CheckPriorityGroupTestConfig, 0, "Priority group config", numOfEvents, customClass)) return false;
407 if (! CheckDifferentModes(CheckSingleGroupTestConfig, 1, "Single group config", numOfEvents, customClass)) return false;
409 // Cleanup all temporary files generated.
410 gSystem->Exec("rm -f testOutputFile.root testInputFile*.root AliHLTGlobalTriggerImpl*");
418 int main(int /*argc*/, const char** /*argv*/)
420 gSystem->Exec("if test ! -f TriggerConfig.C ; then cp $ALICE_ROOT/HLT/trigger/test/TriggerConfig.C ./; fi");
421 bool resultOk = testGlobalTriggerComponent();
422 if (not resultOk) return 1;
426 #endif // __MAKECINT__