]> git.uio.no Git - u/mrichter/AliRoot.git/blame - HLT/MUON/OnlineAnalysis/AliHLTMUONTriggerReconstructorComponent.cxx
Fixing coverty warnings for NULL pointer dereferencing.
[u/mrichter/AliRoot.git] / HLT / MUON / OnlineAnalysis / AliHLTMUONTriggerReconstructorComponent.cxx
CommitLineData
6efe69e7 1/**************************************************************************
b39b98c8 2 * This file is property of and copyright by the ALICE HLT Project *
6efe69e7 3 * All rights reserved. *
4 * *
5 * Primary Authors: *
6 * Indranil Das <indra.das@saha.ac.in> *
b39b98c8 7 * Artur Szostak <artursz@iafrica.com> *
6efe69e7 8 * *
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 *
b39b98c8 14 * about the suitability of this software for any purpose. It is *
6efe69e7 15 * provided "as is" without express or implied warranty. *
16 **************************************************************************/
17
1d8ae082 18// $Id$
6efe69e7 19
6253e09b 20///
21/// @file AliHLTMUONTriggerReconstructorComponent.cxx
22/// @author Indranil Das <indra.das@saha.ac.in>, Artur Szostak <artursz@iafrica.com>
61d982d3 23/// @date 18 Sep 2007
6253e09b 24/// @brief Implementation of the trigger DDL reconstructor component.
25///
6efe69e7 26
6efe69e7 27#include "AliHLTMUONTriggerReconstructorComponent.h"
960d54ad 28#include "AliHLTMUONTriggerReconstructor.h"
29#include "AliHLTMUONHitReconstructor.h"
30#include "AliHLTMUONConstants.h"
2b7af22a 31#include "AliHLTMUONCalculations.h"
b39b98c8 32#include "AliHLTMUONUtils.h"
227e7192 33#include "AliHLTMUONDataBlockWriter.h"
69c14678 34#include "AliRawDataHeader.h"
c95cf30c 35#include "AliCDBManager.h"
36#include "AliCDBStorage.h"
37#include "AliGeomManager.h"
38#include "AliMUONGeometryTransformer.h"
39#include "AliMUONGeometryDetElement.h"
40#include "AliMpCDB.h"
41#include "AliMpDDLStore.h"
42#include "AliMpPad.h"
43#include "AliMpSegmentation.h"
44#include "AliMpDEIterator.h"
45#include "AliMpVSegmentation.h"
46#include "AliMpDEManager.h"
47#include "AliMpLocalBoard.h"
48#include "AliMpTriggerCrate.h"
227e7192 49#include <cstdlib>
50#include <cerrno>
5d1682b9 51#include <cassert>
b39b98c8 52#include <fstream>
6efe69e7 53
c95cf30c 54
6efe69e7 55ClassImp(AliHLTMUONTriggerReconstructorComponent)
b39b98c8 56
57
227e7192 58AliHLTMUONTriggerReconstructorComponent::AliHLTMUONTriggerReconstructorComponent() :
154cba94 59 AliHLTMUONProcessor(),
227e7192 60 fTrigRec(NULL),
b39b98c8 61 fDDL(-1),
80590aa1 62 fWarnForUnexpecedBlock(false),
a3d4b6ba 63 fStopOnOverflow(false),
2b7af22a 64 fUseCrateId(true),
2b7af22a 65 fZmiddleSpecified(false),
66 fBLSpecified(false),
67 fLutInitialised(false)
960d54ad 68{
6253e09b 69 ///
70 /// Default constructor.
71 ///
960d54ad 72}
73
6efe69e7 74
75AliHLTMUONTriggerReconstructorComponent::~AliHLTMUONTriggerReconstructorComponent()
960d54ad 76{
6253e09b 77 ///
78 /// Default destructor.
79 ///
a6b16447 80
81 if (fTrigRec != NULL) delete fTrigRec;
960d54ad 82}
83
6efe69e7 84
85const char* AliHLTMUONTriggerReconstructorComponent::GetComponentID()
960d54ad 86{
6253e09b 87 ///
88 /// Inherited from AliHLTComponent. Returns the component ID.
89 ///
90
227e7192 91 return AliHLTMUONConstants::TriggerReconstructorId();
960d54ad 92}
93
94
ffb64d3e 95void AliHLTMUONTriggerReconstructorComponent::GetInputDataTypes(AliHLTComponentDataTypeList& list)
960d54ad 96{
6253e09b 97 ///
98 /// Inherited from AliHLTProcessor. Returns the list of expected input data types.
99 ///
100
227e7192 101 list.clear();
668eee9f 102 list.push_back( AliHLTMUONConstants::DDLRawDataType() );
960d54ad 103}
6efe69e7 104
6efe69e7 105
106AliHLTComponentDataType AliHLTMUONTriggerReconstructorComponent::GetOutputDataType()
960d54ad 107{
6253e09b 108 ///
462e3880 109 /// Inherited from AliHLTComponent. Returns kAliHLTMultipleDataType.
6253e09b 110 ///
111
462e3880 112 return kAliHLTMultipleDataType;
113}
114
115
116int AliHLTMUONTriggerReconstructorComponent::GetOutputDataTypes(AliHLTComponentDataTypeList& list)
117{
118 /// Inherited from AliHLTComponent. Returns the output data types.
119
120 assert( list.empty() );
121 list.push_back( AliHLTMUONConstants::TriggerRecordsBlockDataType() );
122 list.push_back( AliHLTMUONConstants::TrigRecsDebugBlockDataType() );
123 return list.size();
960d54ad 124}
6efe69e7 125
6efe69e7 126
227e7192 127void AliHLTMUONTriggerReconstructorComponent::GetOutputDataSize(
128 unsigned long& constBase, double& inputMultiplier
129 )
960d54ad 130{
6253e09b 131 ///
132 /// Inherited from AliHLTComponent. Returns an estimate of the expected output data size.
133 ///
134
979076f8 135 constBase = sizeof(AliHLTMUONTriggerRecordsBlockWriter::HeaderType) + 1024*1024;
c2e03d6e 136 inputMultiplier = 4;
960d54ad 137}
6efe69e7 138
139
6efe69e7 140AliHLTComponent* AliHLTMUONTriggerReconstructorComponent::Spawn()
960d54ad 141{
6253e09b 142 ///
143 /// Inherited from AliHLTComponent. Creates a new object instance.
144 ///
145
227e7192 146 return new AliHLTMUONTriggerReconstructorComponent;
960d54ad 147}
148
6efe69e7 149
960d54ad 150int AliHLTMUONTriggerReconstructorComponent::DoInit(int argc, const char** argv)
6efe69e7 151{
6253e09b 152 ///
153 /// Inherited from AliHLTComponent.
154 /// Parses the command line parameters and initialises the component.
155 ///
156
b39b98c8 157 HLTInfo("Initialising dHLT trigger reconstructor component.");
6efe69e7 158
ffb64d3e 159 // Inherit the parents functionality.
160 int result = AliHLTMUONProcessor::DoInit(argc, argv);
161 if (result != 0) return result;
162
a6b16447 163 // Make sure to cleanup fTrigRec if it is still there for some reason.
164 if (fTrigRec != NULL)
165 {
166 delete fTrigRec;
167 fTrigRec = NULL;
168 }
169
a6b16447 170 fDDL = -1;
b39b98c8 171 fWarnForUnexpecedBlock = false;
a3d4b6ba 172 fStopOnOverflow = false;
173 fUseCrateId = true;
2b7af22a 174 fZmiddleSpecified = false;
175 fBLSpecified = false;
176 fLutInitialised = false;
960d54ad 177
b39b98c8 178 const char* lutFileName = NULL;
c95cf30c 179 bool useCDB = false;
a3d4b6ba 180 bool suppressPartialTrigs = true;
a5d4696f 181 bool tryRecover = false;
2b7af22a 182 bool useLocalId = true;
462e3880 183 bool makeDebugInfo = false;
aae30cc5 184 bool dontPrintWrongEventError = false;
2b7af22a 185 double zmiddle = 0;
186 double bfieldintegral = 0;
b39b98c8 187
188 for (int i = 0; i < argc; i++)
189 {
ffb64d3e 190 // To keep the legacy behaviour we need to have the following check
191 // for -cdbpath here, before ArgumentAlreadyHandled.
192 if (strcmp(argv[i], "-cdbpath") == 0)
193 {
194 useCDB = true;
195 }
196
197 if (ArgumentAlreadyHandled(i, argv[i])) continue;
198
6ec6a7c1 199 if (strcmp( argv[i], "-lut" ) == 0)
b39b98c8 200 {
2b7af22a 201 if (lutFileName != NULL)
202 {
203 HLTWarning("LUT path was already specified."
204 " Will replace previous value given by -lut."
205 );
206 }
207
b39b98c8 208 if ( argc <= i+1 )
209 {
2b7af22a 210 HLTError("The lookup table filename was not specified." );
a6b16447 211 return -EINVAL;
b39b98c8 212 }
213
214 lutFileName = argv[i+1];
215
216 i++;
217 continue;
218 }
219
6ec6a7c1 220 if (strcmp( argv[i], "-ddl" ) == 0)
b39b98c8 221 {
2b7af22a 222 if (fDDL != -1)
223 {
224 HLTWarning("DDL number was already specified."
225 " Will replace previous value given by -ddl or -ddlid."
226 );
227 }
228
b39b98c8 229 if ( argc <= i+1 )
230 {
ffb64d3e 231 HLTError("DDL number not specified. It must be in the range [21..22]");
a6b16447 232 return -EINVAL;
b39b98c8 233 }
234
235 char* cpErr = NULL;
236 unsigned long num = strtoul(argv[i+1], &cpErr, 0);
237 if (cpErr == NULL or *cpErr != '\0')
238 {
5e67b742 239 HLTError("Cannot convert '%s' to a DDL Number.", argv[i+1]);
a6b16447 240 return -EINVAL;
b39b98c8 241 }
242 if (num < 21 or 22 < num)
243 {
a3d4b6ba 244 HLTError("The DDL number must be in the range [21..22].");
a6b16447 245 return -EINVAL;
b39b98c8 246 }
247 fDDL = num - 1; // Convert to DDL number in the range 0..21
248
249 i++;
250 continue;
251 }
c95cf30c 252
a3d4b6ba 253 if (strcmp( argv[i], "-ddlid" ) == 0)
254 {
2b7af22a 255 if (fDDL != -1)
256 {
257 HLTWarning("DDL number was already specified."
258 " Will replace previous value given by -ddl or -ddlid."
259 );
260 }
261
a3d4b6ba 262 if ( argc <= i+1 )
263 {
ffb64d3e 264 HLTError("DDL equipment ID number not specified. It must be in the range [2816..2817]");
a3d4b6ba 265 return -EINVAL;
266 }
267
268 char* cpErr = NULL;
269 unsigned long num = strtoul(argv[i+1], &cpErr, 0);
270 if (cpErr == NULL or *cpErr != '\0')
271 {
272 HLTError("Cannot convert '%s' to a DDL equipment ID Number.", argv[i+1]);
a3d4b6ba 273 return -EINVAL;
274 }
275 fDDL = AliHLTMUONUtils::EquipIdToDDLNumber(num); // Convert to DDL number in the range 0..21
276 if (fDDL < 20 or 21 < fDDL)
277 {
278 HLTError("The DDL equipment ID number must be in the range [2816..2817].");
a3d4b6ba 279 return -EINVAL;
280 }
281
282 i++;
283 continue;
284 }
285
c95cf30c 286 if (strcmp( argv[i], "-cdb" ) == 0)
287 {
288 useCDB = true;
289 continue;
290 }
2b7af22a 291
292 if (strcmp( argv[i], "-zmiddle" ) == 0)
293 {
294 if (fZmiddleSpecified)
295 {
296 HLTWarning("The Z coordinate for the middle of the dipole was already specified."
297 " Will replace previous value given by -zmiddle."
298 );
299 }
300
301 if ( argc <= i+1 )
302 {
ffb64d3e 303 HLTError("The Z coordinate for the middle of the dipole was not specified.");
2b7af22a 304 return -EINVAL;
305 }
306
307 char* cpErr = NULL;
308 zmiddle = strtod(argv[i+1], &cpErr);
309 if (cpErr == NULL or *cpErr != '\0')
310 {
311 HLTError("Cannot convert '%s' to a valid floating point number.",
312 argv[i+1]
313 );
2b7af22a 314 return -EINVAL;
315 }
316
317 fZmiddleSpecified = true;
318 i++;
319 continue;
320 }
321
322 if (strcmp( argv[i], "-bfieldintegral" ) == 0)
323 {
324 if (fBLSpecified)
325 {
326 HLTWarning("The magnetic field integral was already specified."
327 " Will replace previous value given by -bfieldintegral."
328 );
329 }
330
331 if ( argc <= i+1 )
332 {
333 HLTError("The magnetic field integral was not specified." );
2b7af22a 334 return -EINVAL;
335 }
336
337 char* cpErr = NULL;
338 bfieldintegral = strtod(argv[i+1], &cpErr);
339 if (cpErr == NULL or *cpErr != '\0')
340 {
341 HLTError("Cannot convert '%s' to a valid floating point number.",
342 argv[i+1]
343 );
2b7af22a 344 return -EINVAL;
345 }
346
347 fBLSpecified = true;
348 i++;
349 continue;
350 }
351
6ec6a7c1 352 if (strcmp( argv[i], "-warn_on_unexpected_block" ) == 0)
b39b98c8 353 {
354 fWarnForUnexpecedBlock = true;
355 continue;
356 }
c95cf30c 357
6ec6a7c1 358 if (strcmp( argv[i], "-suppress_partial_triggers" ) == 0)
b39b98c8 359 {
a3d4b6ba 360 suppressPartialTrigs = true;
361 continue;
362 }
363
364 if (strcmp( argv[i], "-generate_partial_triggers" ) == 0)
365 {
366 suppressPartialTrigs = false;
367 continue;
368 }
369
370 if (strcmp( argv[i], "-stop_on_buffer_overflow" ) == 0)
371 {
372 fStopOnOverflow = true;
b39b98c8 373 continue;
374 }
375
a5d4696f 376 if (strcmp( argv[i], "-tryrecover" ) == 0)
377 {
378 tryRecover = true;
379 continue;
380 }
381
a3d4b6ba 382 if (strcmp( argv[i], "-dont_use_crateid" ) == 0)
383 {
384 fUseCrateId = false;
385 continue;
386 }
387
2b7af22a 388 if (strcmp( argv[i], "-dont_use_localid" ) == 0)
389 {
390 useLocalId = false;
391 continue;
392 }
393
462e3880 394 if (strcmp( argv[i], "-makedebuginfo" ) == 0)
395 {
396 makeDebugInfo = true;
397 continue;
398 }
399
aae30cc5 400 if (strcmp( argv[i], "-dontprintwrongeventerror" ) == 0)
401 {
402 dontPrintWrongEventError = true;
403 continue;
404 }
405
ffb64d3e 406 HLTError("Unknown option '%s'.", argv[i]);
a6b16447 407 return -EINVAL;
c95cf30c 408
a6b16447 409 } // for loop
b39b98c8 410
ffb64d3e 411 try
412 {
413 fTrigRec = new AliHLTMUONTriggerReconstructor();
414 }
415 catch (const std::bad_alloc&)
416 {
417 HLTError("Could not allocate more memory for the trigger reconstructor component.");
418 return -ENOMEM;
419 }
420
2b7af22a 421 if (fZmiddleSpecified and useCDB)
422 {
423 HLTWarning("The -cdb or -cdbpath parameter was specified, which indicates that"
424 " this component should read from the CDB, but then the -zmiddle argument"
425 " was also used. Will override the value from CDB with the command"
426 " line parameter given."
427 );
428 }
429 if (fBLSpecified and useCDB)
430 {
431 HLTWarning("The -cdb or -cdbpath parameter was specified, which indicates that"
432 " this component should read from the CDB, but then the -bfieldintegral"
433 " argument was also used. Will override the value from CDB with the"
434 " command line parameter given."
435 );
436 }
437
438 if (lutFileName != NULL and useCDB == true)
439 {
440 HLTWarning("The -cdb or -cdbpath parameter was specified, which indicates that"
441 " this component should read from the CDB, but then the -lut argument"
442 " was also used. Will ignore the -lut option and load from CDB anyway."
443 );
444 }
445
c95cf30c 446 if (lutFileName == NULL) useCDB = true;
447
ffb64d3e 448 if (fDDL == -1 and not DelaySetup())
b39b98c8 449 {
450 HLTWarning("DDL number not specified. Cannot check if incomming data is valid.");
960d54ad 451 }
960d54ad 452
2b7af22a 453 if (useCDB)
b39b98c8 454 {
ffb64d3e 455 if (not DelaySetup())
2b7af22a 456 {
457 HLTInfo("Loading lookup table information from CDB for DDL %d (ID = %d).",
458 fDDL+1, AliHLTMUONUtils::DDLNumberToEquipId(fDDL)
459 );
4e22efc4 460 result = ReadLutFromCDB();
2b7af22a 461 if (result != 0)
462 {
463 // Error messages already generated in ReadLutFromCDB.
464 delete fTrigRec; // Make sure to delete fTrigRec to avoid partial initialisation.
465 fTrigRec = NULL;
466 return result;
467 }
468 fLutInitialised = true;
469 }
960d54ad 470 }
2b7af22a 471 else
b39b98c8 472 {
c95cf30c 473 HLTInfo("Loading lookup table information from file %s.", lutFileName);
4e22efc4 474 result = ReadLookUpTable(lutFileName);
2b7af22a 475 if (result != 0)
476 {
477 // Error messages already generated in ReadLookUpTable.
478 delete fTrigRec; // Make sure to delete fTrigRec to avoid partial initialisation.
479 fTrigRec = NULL;
480 return result;
481 }
482 fLutInitialised = true;
c95cf30c 483 }
2b7af22a 484
485 if (fZmiddleSpecified) AliHLTMUONCalculations::Zf(zmiddle);
486 if (fBLSpecified) AliHLTMUONCalculations::QBL(bfieldintegral);
487
ffb64d3e 488 if (not DelaySetup())
c95cf30c 489 {
2b7af22a 490 if (not fZmiddleSpecified or not fBLSpecified)
491 {
492 HLTInfo("Loading configuration parameters from CDB for DDL %d (ID = %d).",
493 fDDL+1, AliHLTMUONUtils::DDLNumberToEquipId(fDDL)
494 );
495
4e22efc4 496 result = ReadConfigFromCDB(not fZmiddleSpecified, not fBLSpecified);
2b7af22a 497 if (result != 0)
498 {
499 // Error messages already generated in ReadConfigFromCDB.
500 delete fTrigRec; // Make sure to delete fTrigRec to avoid partial initialisation.
501 fTrigRec = NULL;
502 return result;
503 }
504 }
505 else
506 {
507 // Print the debug messages here since ReadConfigFromCDB does not get called,
508 // in-which the debug messages would have been printed.
509 HLTDebug("Using the following configuration parameters:");
510 HLTDebug(" Middle of dipole Z coordinate = %f cm", AliHLTMUONCalculations::Zf());
511 HLTDebug(" Magnetic field integral = %f T.m", AliHLTMUONCalculations::QBL());
512 }
960d54ad 513 }
b39b98c8 514
a3d4b6ba 515 fTrigRec->SuppressPartialTriggers(suppressPartialTrigs);
a5d4696f 516 fTrigRec->TryRecover(tryRecover);
a3d4b6ba 517 fTrigRec->UseCrateId(fUseCrateId);
2b7af22a 518 fTrigRec->UseLocalId(useLocalId);
462e3880 519 fTrigRec->StoreDebugInfo(makeDebugInfo);
aae30cc5 520 fTrigRec->DontPrintWrongEventError(dontPrintWrongEventError);
a5d4696f 521
b39b98c8 522 return 0;
6efe69e7 523}
524
960d54ad 525
6efe69e7 526int AliHLTMUONTriggerReconstructorComponent::DoDeinit()
960d54ad 527{
6253e09b 528 ///
529 /// Inherited from AliHLTComponent. Performs a cleanup of the component.
530 ///
531
b39b98c8 532 HLTInfo("Deinitialising dHLT trigger reconstructor component.");
227e7192 533
b39b98c8 534 if (fTrigRec != NULL)
227e7192 535 {
536 delete fTrigRec;
537 fTrigRec = NULL;
538 }
539 return 0;
960d54ad 540}
6efe69e7 541
227e7192 542
960d54ad 543int AliHLTMUONTriggerReconstructorComponent::DoEvent(
544 const AliHLTComponentEventData& evtData,
b39b98c8 545 const AliHLTComponentBlockData* blocks,
ffb64d3e 546 AliHLTComponentTriggerData& trigData,
b39b98c8 547 AliHLTUInt8_t* outputPtr,
960d54ad 548 AliHLTUInt32_t& size,
ffb64d3e 549 AliHLTComponentBlockDataList& outputBlocks
960d54ad 550 )
551{
6253e09b 552 ///
553 /// Inherited from AliHLTProcessor. Processes the new event data.
554 ///
555
2b7af22a 556 // Initialise the LUT and configuration parameters from CDB if we were
557 // requested to initialise only when the first event was received.
ffb64d3e 558 if (DelaySetup())
2b7af22a 559 {
560 // Use the specification given by the first data block if we
561 // have not been given a DDL number on the command line.
562 if (fDDL == -1)
563 {
48ccb241 564 bool blockFound = false;
565 for (AliHLTUInt32_t n = 0; n < evtData.fBlockCnt and not blockFound; n++)
566 {
567 if (blocks[n].fDataType != AliHLTMUONConstants::DDLRawDataType()) continue;
568 blockFound = true;
569
570 fDDL = AliHLTMUONUtils::SpecToDDLNumber(blocks[n].fSpecification);
571
572 if (fDDL == -1)
573 {
574 HLTError("Received a data block with a specification (0x%8.8X)"
575 " indicating multiple DDL data sources, but we must only"
576 " receive raw DDL data from one trigger station DDL.",
577 blocks[n].fSpecification
578 );
579 return -EPROTO;
580 }
581 }
582
583 if (not blockFound)
2b7af22a 584 {
585 HLTError("The initialisation from CDB of the component has"
586 " been delayed to the first received event. However,"
48ccb241 587 " no raw DDL data blocks have been found in the first event."
2b7af22a 588 );
589 return -ENOENT;
590 }
2b7af22a 591 }
592
593 // Check that the LUT was not already loaded in DoInit.
594 if (not fLutInitialised)
595 {
596 HLTInfo("Loading lookup table information from CDB for DDL %d (ID = %d).",
597 fDDL+1, AliHLTMUONUtils::DDLNumberToEquipId(fDDL)
598 );
599 int result = ReadLutFromCDB();
600 if (result != 0) return result;
601 fLutInitialised = true;
602 }
603
604 // Load the configuration paramters from CDB if they have not been given
605 // on the command line.
606 if (not fZmiddleSpecified or not fBLSpecified)
607 {
608 HLTInfo("Loading configuration parameters from CDB for DDL %d (ID = %d).",
609 fDDL+1, AliHLTMUONUtils::DDLNumberToEquipId(fDDL)
610 );
611 int result = ReadConfigFromCDB(not fZmiddleSpecified, not fBLSpecified);
612 if (result != 0) return result;
613 }
614
ffb64d3e 615 DoneDelayedSetup();
2b7af22a 616 }
617
227e7192 618 // Process an event
619 unsigned long totalSize = 0; // Amount of memory currently consumed in bytes.
6efe69e7 620
227e7192 621 HLTDebug("Processing event %llu with %u input data blocks.",
622 evtData.fEventID, evtData.fBlockCnt
623 );
6efe69e7 624
227e7192 625 // Loop over all input blocks in the event and run the trigger DDL
626 // reconstruction algorithm on the raw data.
627 for (AliHLTUInt32_t n = 0; n < evtData.fBlockCnt; n++)
628 {
450e0b36 629 HLTDebug("Handling block: %u, with fDataType = '%s', fPtr = %p and fSize = %u bytes.",
630 n, DataType2Text(blocks[n].fDataType).c_str(), blocks[n].fPtr, blocks[n].fSize
227e7192 631 );
632
668eee9f 633 if (blocks[n].fDataType != AliHLTMUONConstants::DDLRawDataType()
634 or not AliHLTMUONUtils::IsTriggerDDL(blocks[n].fSpecification)
635 )
227e7192 636 {
637 // Log a message indicating that we got a data block that we
638 // do not know how to handle.
5d1682b9 639 if (fWarnForUnexpecedBlock)
450e0b36 640 HLTWarning("Received a data block of a type we cannot handle: '%s', spec: 0x%X",
641 DataType2Text(blocks[n].fDataType).c_str(), blocks[n].fSpecification
5d1682b9 642 );
4e22efc4 643#ifdef __DEBUG
5d1682b9 644 else
450e0b36 645 HLTDebug("Received a data block of a type we cannot handle: '%s', spec: 0x%X",
646 DataType2Text(blocks[n].fDataType).c_str(), blocks[n].fSpecification
5d1682b9 647 );
4e22efc4 648#endif
5d1682b9 649
227e7192 650 continue;
651 }
652
406c5bc3 653 AliHLTInt32_t receivedDDL = AliHLTMUONUtils::SpecToDDLNumber(blocks[n].fSpecification);
a6b16447 654 if (fDDL != -1)
b39b98c8 655 {
406c5bc3 656 if (receivedDDL != fDDL)
a6b16447 657 {
a3d4b6ba 658 HLTWarning("Received raw data from DDL %d (ID = %d),"
659 " but expect data only from DDL %d (ID = %d).",
660 receivedDDL+1, AliHLTMUONUtils::DDLNumberToEquipId(receivedDDL),
661 fDDL+1, AliHLTMUONUtils::DDLNumberToEquipId(fDDL)
662 );
a6b16447 663 }
b39b98c8 664 }
665
227e7192 666 // Create a new output data block and initialise the header.
667 AliHLTMUONTriggerRecordsBlockWriter block(outputPtr+totalSize, size-totalSize);
668 if (not block.InitCommonHeader())
669 {
69c14678 670 HLTError("There is not enough space in the output buffer for the new data block."
462e3880 671 " We require at least %u bytes, but have %u bytes left.",
227e7192 672 sizeof(AliHLTMUONTriggerRecordsBlockWriter::HeaderType),
673 block.BufferSize()
674 );
675 break;
676 }
677
69c14678 678 AliHLTUInt32_t totalDDLSize = blocks[n].fSize;
679 if (totalDDLSize < sizeof(AliRawDataHeader))
680 {
681 HLTError("Raw data block %d is %d bytes in size and is too short to"
682 " possibly contain valid DDL raw data. We expect it to have"
683 " at least %d bytes for the commond data header.",
684 n, totalDDLSize, sizeof(AliRawDataHeader)
685 );
686 continue;
687 }
3240b3ce 688 AliRawDataHeader* header = reinterpret_cast<AliRawDataHeader*>(blocks[n].fPtr);
69c14678 689 AliHLTUInt32_t payloadSize = totalDDLSize - sizeof(AliRawDataHeader);
a5d4696f 690 AliHLTUInt8_t* buffer = reinterpret_cast<AliHLTUInt8_t*>(header + 1);
227e7192 691 AliHLTUInt32_t nofTrigRec = block.MaxNumberOfEntries();
a5d4696f 692
693 // Decode if this is a scalar event or not.
694 bool scalarEvent = ((header->GetL1TriggerMessage() & 0x1) == 0x1);
695
406c5bc3 696 // Remember: the following does NOT change the mapping!
697 // It is just to generate unique trigger record IDs.
698 fTrigRec->SetDDL(receivedDDL);
699
80590aa1 700 bool runOk = fTrigRec->Run(
a5d4696f 701 buffer, payloadSize, scalarEvent,
a3d4b6ba 702 block.GetArray(), nofTrigRec
80590aa1 703 );
704 if (not runOk)
227e7192 705 {
154cba94 706 HLTError("Error while processing the trigger DDL reconstruction algorithm.");
ffb64d3e 707 if (DumpDataOnError()) DumpEvent(evtData, blocks, trigData, outputPtr, size, outputBlocks);
a3d4b6ba 708 if (not fTrigRec->OverflowedOutputBuffer()
709 or (fTrigRec->OverflowedOutputBuffer() and fStopOnOverflow)
710 )
711 {
712 size = totalSize; // Must tell the framework how much buffer space was used.
713 return -EIO;
714 }
227e7192 715 }
716
717 // nofTrigRec should now contain the number of triggers actually found
718 // and filled into the output data block, so we can set this number.
719 assert( nofTrigRec <= block.MaxNumberOfEntries() );
720 block.SetNumberOfEntries(nofTrigRec);
721
722 HLTDebug("Number of trigger records found is %d", nofTrigRec);
723
724 // Fill a block data structure for our output block.
725 AliHLTComponentBlockData bd;
726 FillBlockData(bd);
727 bd.fPtr = outputPtr;
728 // This block's start (offset) is after all other blocks written so far.
729 bd.fOffset = totalSize;
730 bd.fSize = block.BytesUsed();
731 bd.fDataType = AliHLTMUONConstants::TriggerRecordsBlockDataType();
732 bd.fSpecification = blocks[n].fSpecification;
733 outputBlocks.push_back(bd);
734
735 HLTDebug("Created a new output data block at fPtr = %p,"
462e3880 736 " with fOffset = %u (0x%.X) and fSize = %u bytes.",
227e7192 737 bd.fPtr, bd.fOffset, bd.fOffset, bd.fSize
738 );
739
740 // Increase the total amount of data written so far to our output memory.
741 totalSize += block.BytesUsed();
462e3880 742
743 if (fTrigRec->StoreDebugInfo())
744 {
745 // Create a new output data block and initialise the header.
746 AliHLTMUONTrigRecsDebugBlockWriter infoblock(outputPtr+totalSize, size-totalSize);
747 if (not infoblock.InitCommonHeader())
748 {
749 HLTError("There is not enough space in the output buffer for the new debug"
750 " data block. We require at least %u bytes, but have %u bytes left.",
751 sizeof(AliHLTMUONTrigRecsDebugBlockWriter::HeaderType),
752 infoblock.BufferSize()
753 );
754 break;
755 }
756
757 infoblock.SetNumberOfEntries(fTrigRec->InfoBufferCount());
758 for (AliHLTUInt32_t i = 0; i < fTrigRec->InfoBufferCount(); ++i)
759 {
760 infoblock[i] = fTrigRec->InfoBuffer()[i];
761 }
762 fTrigRec->ZeroInfoBuffer();
763
764 // Fill the block data structure for our output block.
765 AliHLTComponentBlockData bd2;
766 FillBlockData(bd2);
767 bd2.fPtr = outputPtr;
768 // This block's start (offset) is after all other blocks written so far.
769 bd2.fOffset = totalSize;
770 bd2.fSize = infoblock.BytesUsed();
771 bd2.fDataType = AliHLTMUONConstants::TrigRecsDebugBlockDataType();
772 bd2.fSpecification = blocks[n].fSpecification;
773 outputBlocks.push_back(bd2);
774
775 HLTDebug("Created a new output data block for debug information at fPtr = %p,"
776 " with fOffset = %u (0x%.X) and fSize = %u bytes.",
777 bd2.fPtr, bd2.fOffset, bd2.fOffset, bd2.fSize
778 );
779
780 // Increase the total amount of data written so far to our output memory.
781 totalSize += infoblock.BytesUsed();
782 }
227e7192 783 }
960d54ad 784
227e7192 785 // Finally we set the total size of output memory we consumed.
786 size = totalSize;
787 return 0;
960d54ad 788}
789
6efe69e7 790
2b7af22a 791int AliHLTMUONTriggerReconstructorComponent::Reconfigure(
792 const char* cdbEntry, const char* componentId
793 )
794{
795 /// Inherited from AliHLTComponent. This method will reload CDB configuration
796 /// entries for this component from the CDB.
797 /// \param cdbEntry If this is NULL then it is assumed that all CDB entries should
798 /// be reloaded. Otherwise a particular value for 'cdbEntry' will trigger
799 /// reloading of the LUT if the path contains 'MUON/', but the other
800 /// configuration parameters will be loaded if 'cdbEntry' contains
801 /// "HLT/ConfigMUON/TriggerReconstructor".
802 /// \param componentId The name of the component in the current chain.
803
ad9d297e 804 TString path = cdbEntry;
805 bool startsWithMUON = path.Index("MUON/", 5, 0, TString::kExact) == 0;
806 bool givenConfigPath = (path == AliHLTMUONConstants::TriggerReconstructorCDBPath());
2b7af22a 807
808 if (cdbEntry == NULL or startsWithMUON or givenConfigPath)
809 {
810 HLTInfo("Reading new configuration entries from CDB for component '%s'.", componentId);
811 }
812
813 if (cdbEntry == NULL or startsWithMUON)
814 {
815 int result = ReadLutFromCDB();
816 if (result != 0) return result;
817 }
818
819 if (cdbEntry == NULL or givenConfigPath)
820 {
821 int result = ReadConfigFromCDB();
822 if (result != 0) return result;
823 }
824
825 return 0;
826}
827
828
829int AliHLTMUONTriggerReconstructorComponent::ReadPreprocessorValues(const char* modules)
830{
831 /// Inherited from AliHLTComponent.
832 /// Updates the configuration of this component if either HLT or MUON have
833 /// been specified in the 'modules' list.
834
835 TString mods = modules;
836 if (mods.Contains("ALL") or (mods.Contains("HLT") and mods.Contains("MUON")))
837 {
838 return Reconfigure(NULL, GetComponentID());
839 }
840 if (mods.Contains("HLT"))
841 {
842 return Reconfigure(AliHLTMUONConstants::TriggerReconstructorCDBPath(), GetComponentID());
843 }
844 if (mods.Contains("MUON"))
845 {
846 return Reconfigure("MUON/*", GetComponentID());
847 }
848 return 0;
849}
850
851
c95cf30c 852int AliHLTMUONTriggerReconstructorComponent::ReadLookUpTable(const char* lutpath)
6efe69e7 853{
6253e09b 854 ///
855 /// Read in the lookup table from file.
856 ///
857
b39b98c8 858 assert(fTrigRec != NULL);
6efe69e7 859
b39b98c8 860 fstream file;
861 file.open(lutpath, fstream::binary | fstream::in);
862 if (not file)
863 {
864 HLTError("Could not open file: %s", lutpath);
c95cf30c 865 return -ENOENT;
b39b98c8 866 }
867
868 file.read(reinterpret_cast<char*>(fTrigRec->LookupTableBuffer()), fTrigRec->LookupTableSize());
869 if (file.eof())
870 {
871 HLTError("The file %s was too short to contain a valid lookup table for this component.", lutpath);
872 file.close();
c95cf30c 873 return -EIO;
b39b98c8 874 }
c95cf30c 875 if (file.fail())
b39b98c8 876 {
877 HLTError("Could not read from file: %s", lutpath);
878 file.close();
c95cf30c 879 return -EIO;
880 }
881
882 file.close();
883 return 0;
884}
885
886
2b7af22a 887int AliHLTMUONTriggerReconstructorComponent::ReadConfigFromCDB(
888 bool setZmiddle, bool setBL
889 )
890{
891 /// Reads this component's configuration parameters from the CDB.
892 /// These include the middle of the dipole Z coordinate (zmiddle) and the
893 /// integrated magnetic field of the dipole.
894 /// \param setZmiddle Indicates if the zmiddle parameter should be set
895 /// (default true).
896 /// \param setBL Indicates if the integrated magnetic field parameter should
897 /// be set (default true).
898 /// \return 0 if no errors occured and negative error code compatible with
899 /// the HLT framework on errors.
900
901 const char* pathToEntry = AliHLTMUONConstants::TriggerReconstructorCDBPath();
902
903 TMap* map = NULL;
904 int result = FetchTMapFromCDB(pathToEntry, map);
905 if (result != 0) return result;
906
907 Double_t value = 0;
908 if (setZmiddle)
909 {
910 result = GetFloatFromTMap(map, "zmiddle", value, pathToEntry, "dipole middle Z coordinate");
911 if (result != 0) return result;
912 AliHLTMUONCalculations::Zf(value);
913 }
914
915 if (setBL)
916 {
bc5cb6d6 917 Double_t bfieldintegral;
918 result = FetchFieldIntegral(bfieldintegral);
919 if (result == 0)
920 {
921 AliHLTMUONCalculations::QBL(bfieldintegral);
922 }
923 else
924 {
925 HLTWarning("Failed to load the magnetic field integral from GRP information.");
926 result = GetFloatFromTMap(map, "bfieldintegral", value, pathToEntry, "integrated magnetic field");
927 if (result != 0) return result;
928 HLTWarning(Form("Using deprecated magnetic field integral value of %f T.m.", value));
929 AliHLTMUONCalculations::QBL(value);
930 }
2b7af22a 931 }
932
933 HLTDebug("Using the following configuration parameters:");
934 HLTDebug(" Middle of dipole Z coordinate = %f cm", AliHLTMUONCalculations::Zf());
935 HLTDebug(" Magnetic field integral = %f T.m", AliHLTMUONCalculations::QBL());
936
937 return 0;
938}
939
940
ffc1a6f6 941int AliHLTMUONTriggerReconstructorComponent::ReadLutFromCDB()
c95cf30c 942{
943 /// Loads the lookup table containing channel and geometrical position
944 /// information about trigger strips from CDB.
ffc1a6f6 945 ///
946 /// \note To override the default CDB path and / or run number the
947 /// SetCDBPathAndRunNo(cdbPath, run) method should be called before this
948 /// method.
949 ///
c95cf30c 950 /// \return 0 on success and non zero codes for errors.
951
952 if (fDDL == -1)
953 {
954 HLTError("No DDL number specified for which to load LUT data from CDB.");
955 return -EINVAL;
956 }
957
ffc1a6f6 958 int result = FetchMappingStores();
dba14d7d 959 // Error message already generated in FetchMappingStores.
960 if (result != 0) return result;
c95cf30c 961 AliMpDDLStore* ddlStore = AliMpDDLStore::Instance();
dba14d7d 962
c95cf30c 963 AliMpSegmentation* segmentation = AliMpSegmentation::Instance();
964 if (segmentation == NULL)
965 {
966 HLTError("Could not find segmentation mapping (AliMpSegmentation) instance.");
967 return -EIO;
968 }
969
61d982d3 970 // Only load geometry if not already loaded.
971 if (AliGeomManager::GetGeometry() == NULL)
972 {
973 AliGeomManager::LoadGeometry();
974 }
c95cf30c 975 AliMUONGeometryTransformer transformer;
976 if (not transformer.LoadGeometryData())
977 {
978 HLTError("Could not load geometry into transformer.");
979 return -ENOENT;
980 }
981
982 AliHLTMUONTriggerRecoLookupTable* lookupTable = fTrigRec->LookupTableBuffer();
983
a3d4b6ba 984 for (Int_t i = 0; i < 16; i++)
c95cf30c 985 for (Int_t j = 0; j < 16; j++)
986 for (Int_t k = 0; k < 4; k++)
987 for (Int_t n = 0; n < 2; n++)
988 for (Int_t m = 0; m < 16; m++)
989 {
a090ff22 990 lookupTable->fRow[i][j][k][n][m].fIdFlags = 0x0;
c95cf30c 991 lookupTable->fRow[i][j][k][n][m].fX = 0;
992 lookupTable->fRow[i][j][k][n][m].fY = 0;
993 lookupTable->fRow[i][j][k][n][m].fZ = 0;
994 }
995
996 AliMpDEIterator detElemIter;
997 for (Int_t iReg = 0; iReg < 8; iReg++)
998 {
999 AliMpTriggerCrate* crate = ddlStore->GetTriggerCrate(fDDL, iReg);
1000 if (crate == NULL)
1001 {
a3d4b6ba 1002 HLTError("Could not get crate mapping for regional header = %d"
1003 " and DDL %d (ID = %d).",
1004 iReg, fDDL+1, AliHLTMUONUtils::DDLNumberToEquipId(fDDL)
1005 );
1006 continue;
1007 }
1008 // Depending on the value of fUseCrateId, use either the crate ID as would
1009 // be found in the regional header structures or the sequencial index number
1010 // of the structure.
1011 UInt_t crateId = (fUseCrateId ? crate->GetId() : iReg);
1012 if (crateId >= 16)
1013 {
1014 HLTError("The crate ID number (%d) for regional header = %d and"
1015 " DDL %d (ID = %d) is too big. It should be in the range [0..15]",
1016 crateId, iReg, fDDL+1, AliHLTMUONUtils::DDLNumberToEquipId(fDDL)
1017 );
c95cf30c 1018 continue;
1019 }
1020
1021 for (Int_t iLocBoard = 0; iLocBoard < 16; iLocBoard++)
1022 {
1023 Int_t boardId = crate->GetLocalBoardId(iLocBoard);
1024 if (boardId == 0) continue;
1025
1026 AliMpLocalBoard* localBoard = ddlStore->GetLocalBoard(boardId);
1027 if (localBoard == NULL)
1028 {
a3d4b6ba 1029 HLTError("Could not get local board: %d.", boardId);
c95cf30c 1030 continue;
1031 }
1032
1033 // skip copy cards
1034 if (! localBoard->IsNotified()) continue;
1035
1036 for (Int_t iChamber = 0; iChamber < 4; iChamber++)
1037 {
1038 Int_t detElemId = ddlStore->GetDEfromLocalBoard(boardId, iChamber);
1039
a090ff22 1040 AliHLTUInt32_t idflags = AliHLTMUONUtils::PackRecHitFlags(iChamber+10, detElemId);
1041
c95cf30c 1042 const AliMUONGeometryDetElement* detElemTransform = transformer.GetDetElement(detElemId);
1043 if (detElemTransform == NULL)
1044 {
a3d4b6ba 1045 HLTError("Got NULL pointer for geometry transformer"
1046 " for detection element ID = %d.",
1047 detElemId
1048 );
c95cf30c 1049 continue;
1050 }
1051
1052 for (Int_t iCathode = 0; iCathode <= 1; iCathode++)
1053 {
1054 const AliMpVSegmentation* seg = segmentation->GetMpSegmentation(
1055 detElemId, AliMp::GetCathodType(iCathode)
1056 );
1057
1058 for (Int_t bitxy = 0; bitxy < 16; bitxy++)
1059 {
1060 Int_t offset = 0;
1061 if (iCathode && localBoard->GetSwitch(6)) offset = -8;
1062
53eb3786 1063// just use this switch for simplicity for two different but shortly after each other applied changes
1064#ifndef HAVE_NOT_MUON_ALIMPPAD_GETPOSITION
168e9c4d 1065 AliMpPad pad = seg->PadByLocation(boardId, bitxy+offset, kFALSE);
53eb3786 1066#else // old AliMpPad functionality < r 31742
1067 AliMpPad pad = seg->PadByLocation(AliMpIntPair(boardId, bitxy+offset), kFALSE);
1068#endif //HAVE_NOT_MUON_ALIMPPAD_GETPOSITION
c95cf30c 1069
1070 if (! pad.IsValid())
1071 {
1072 // There is no pad associated with the given local board and bit pattern.
1073 continue;
1074 }
1075
1076 // Get the global coodinates of the pad.
53eb3786 1077#ifndef HAVE_NOT_MUON_ALIMPPAD_GETPOSITION
6e97fbb8 1078 Float_t lx = pad.GetPositionX();
1079 Float_t ly = pad.GetPositionY();
53eb3786 1080#else // old AliMpPad functionality < r 31769
1081 Float_t lx = pad.Position().X();
1082 Float_t ly = pad.Position().Y();
1083#endif //HAVE_NOT_MUON_ALIMPPAD_GETPOSITION
c95cf30c 1084 Float_t gx, gy, gz;
1085 detElemTransform->Local2Global(lx, ly, 0, gx, gy, gz);
1086
1087 // Fill the LUT
a3d4b6ba 1088 lookupTable->fRow[crateId][iLocBoard][iChamber][iCathode][bitxy].fIdFlags = idflags;
1089 lookupTable->fRow[crateId][iLocBoard][iChamber][iCathode][bitxy].fX = gx;
1090 lookupTable->fRow[crateId][iLocBoard][iChamber][iCathode][bitxy].fY = gy;
1091 lookupTable->fRow[crateId][iLocBoard][iChamber][iCathode][bitxy].fZ = gz;
c95cf30c 1092 }
1093 }
1094 }
1095 }
1096 }
61d982d3 1097
c95cf30c 1098 return 0;
1099}
1100
1101
1102bool AliHLTMUONTriggerReconstructorComponent::GenerateLookupTable(
1103 AliHLTInt32_t ddl, const char* filename,
2b7af22a 1104 const char* cdbPath, Int_t run, bool useCrateId
c95cf30c 1105 )
1106{
1107 /// Generates a binary file containing the lookup table (LUT) from the
1108 /// CDB, which can be used for the trigger reconstructor component later.
1109 /// @param ddl Must be the DDL for which to generate the DDL,
1110 /// in the range [20..21].
1111 /// @param filename The name of the LUT file to generate.
1112 /// @param cdbPath The CDB path to use.
1113 /// @param run The run number to use for the CDB.
2b7af22a 1114 /// @param useCrateId Indicates that the crate ID should be used rather
1115 /// than a sequencial number.
c95cf30c 1116 /// @return True if the generation of the LUT file succeeded.
1117
1118 AliHLTMUONTriggerReconstructorComponent comp;
1119
1120 if (ddl < 20 or 21 < ddl)
1121 {
1122 std::cerr << "ERROR: the DDL number must be in the range [20..21]." << std::endl;
1123 return false;
1124 }
1125
1126 char ddlNum[32];
1127 char runNum[32];
1128 sprintf(ddlNum, "%d", ddl+1);
1129 sprintf(runNum, "%d", run);
2b7af22a 1130 int argc = 7;
1131 const char* argv[8] = {"-ddl", ddlNum, "-cdbpath", cdbPath, "-run", runNum, "-dont_use_crateid", NULL};
1132 if (useCrateId)
1133 {
1134 argv[6] = NULL;
1135 argc--;
1136 }
1137 int result = comp.DoInit(argc, argv);
c95cf30c 1138 if (result != 0)
1139 {
1140 // Error message already generated in DoInit.
b39b98c8 1141 return false;
1142 }
1143
c95cf30c 1144 std::fstream file(filename, std::ios::out);
1145 if (not file)
1146 {
1147 std::cerr << "ERROR: could not open file: " << filename << std::endl;
1148 return false;
1149 }
1150
1151 file.write(
1152 reinterpret_cast<char*>(comp.fTrigRec->LookupTableBuffer()),
1153 comp.fTrigRec->LookupTableSize()
1154 );
1155 if (not file)
1156 {
a3d4b6ba 1157 std::cerr << "ERROR: There was a problem writing to the file: " << filename << std::endl;
c95cf30c 1158 return false;
1159 }
b39b98c8 1160 file.close();
c95cf30c 1161
1162 comp.DoDeinit();
1163
b39b98c8 1164 return true;
960d54ad 1165}