]> git.uio.no Git - u/mrichter/AliRoot.git/blame - HLT/MUON/OnlineAnalysis/AliHLTMUONHitReconstructorComponent.cxx
Adding function to retrieve Q normalization
[u/mrichter/AliRoot.git] / HLT / MUON / OnlineAnalysis / AliHLTMUONHitReconstructorComponent.cxx
CommitLineData
b0201cbe 1/**************************************************************************
ffc1a6f6 2 * This file is property of and copyright by the ALICE HLT Project *
960d54ad 3 * All rights reserved. *
b0201cbe 4 * *
960d54ad 5 * Primary Authors: *
6 * Indranil Das <indra.das@saha.ac.in> *
ffc1a6f6 7 * Artur Szostak <artursz@iafrica.com> *
b0201cbe 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 *
ffc1a6f6 14 * about the suitability of this software for any purpose. It is *
b0201cbe 15 * provided "as is" without express or implied warranty. *
16 **************************************************************************/
17
18/* $Id$ */
19
6253e09b 20///
ffc1a6f6 21/// @file AliHLTMUONHitReconstructorComponent.cxx
22/// @author Indranil Das <indra.das@saha.ac.in> | <indra.ehep@gmail.com>, Artur Szostak <artursz@iafrica.com>
23/// @date 28 May 2007
24/// @brief Implementation of the hit Reconstruction processing component.
6253e09b 25///
26/// The HitRec Component is designed to deal the rawdata inputfiles to findout the
27/// the reconstructed hits. The output is send to the output block for further
28/// processing.
29///
30/// Author : Indranil Das ( indra.das@saha.ac.in || indra.ehep@gmail.com )
31///
b0201cbe 32
960d54ad 33#include "AliHLTMUONRecHitsBlockStruct.h"
b0201cbe 34#include "AliHLTMUONHitReconstructorComponent.h"
b12fe461 35#include "AliHLTMUONHitReconstructor.h"
960d54ad 36#include "AliHLTMUONConstants.h"
668eee9f 37#include "AliHLTMUONUtils.h"
5ff5f960 38#include "AliHLTMUONDataBlockWriter.h"
a6b16447 39#include "AliHLTMUONHitReconstructor.h"
b0201cbe 40#include "AliHLTLogging.h"
41#include "AliHLTSystem.h"
42#include "AliHLTDefinitions.h"
29486e5a 43#include <cstdlib>
44#include <cerrno>
45#include <cassert>
93a75941 46#include <fstream>
b0201cbe 47
ffc1a6f6 48#include "TMap.h"
49
50//STEER
ee3678d3 51#include "AliCDBManager.h"
52#include "AliGeomManager.h"
53
54//MUON
55#include "AliMUONGeometryTransformer.h"
56#include "AliMUONCalibrationData.h"
57#include "AliMUONVCalibParam.h"
58
a6b16447 59//MUON/mapping
ee3678d3 60#include "AliMpCDB.h"
61#include "AliMpPad.h"
62#include "AliMpSegmentation.h"
63#include "AliMpDDLStore.h"
64#include "AliMpDEIterator.h"
65#include "AliMpVSegmentation.h"
66#include "AliMpDEManager.h"
67#include "AliMpDetElement.h"
68
b0201cbe 69ClassImp(AliHLTMUONHitReconstructorComponent)
70
71
29486e5a 72AliHLTMUONHitReconstructorComponent::AliHLTMUONHitReconstructorComponent() :
154cba94 73 AliHLTMUONProcessor(),
29486e5a 74 fHitRec(NULL),
a6b16447 75 fDDL(-1),
93a75941 76 fLutSize(0),
77 fLut(NULL),
ee3678d3 78 fIdToEntry(),
ffc1a6f6 79 fWarnForUnexpecedBlock(false),
80 fDelaySetup(false)
b0201cbe 81{
6253e09b 82 ///
83 /// Default constructor.
84 ///
b0201cbe 85}
86
960d54ad 87
b0201cbe 88AliHLTMUONHitReconstructorComponent::~AliHLTMUONHitReconstructorComponent()
89{
6253e09b 90 ///
91 /// Default destructor.
92 ///
ee3678d3 93
94 if (fHitRec != NULL)
95 {
96 delete fHitRec;
97 }
93a75941 98 if (fLut != NULL)
99 {
878cb83d 100 delete [] fLut;
93a75941 101 }
960d54ad 102}
b0201cbe 103
960d54ad 104const char* AliHLTMUONHitReconstructorComponent::GetComponentID()
105{
6253e09b 106 ///
107 /// Inherited from AliHLTComponent. Returns the component ID.
108 ///
109
29486e5a 110 return AliHLTMUONConstants::HitReconstructorId();
b0201cbe 111}
112
b0201cbe 113
960d54ad 114void AliHLTMUONHitReconstructorComponent::GetInputDataTypes( std::vector<AliHLTComponentDataType>& list)
115{
6253e09b 116 ///
117 /// Inherited from AliHLTProcessor. Returns the list of expected input data types.
118 ///
119
29486e5a 120 list.clear();
668eee9f 121 list.push_back( AliHLTMUONConstants::DDLRawDataType() );
960d54ad 122}
b0201cbe 123
b0201cbe 124
960d54ad 125AliHLTComponentDataType AliHLTMUONHitReconstructorComponent::GetOutputDataType()
126{
6253e09b 127 ///
128 /// Inherited from AliHLTComponent. Returns the output data type.
129 ///
130
29486e5a 131 return AliHLTMUONConstants::RecHitsBlockDataType();
960d54ad 132}
b0201cbe 133
b0201cbe 134
960d54ad 135void AliHLTMUONHitReconstructorComponent::GetOutputDataSize( unsigned long& constBase, double& inputMultiplier )
136{
6253e09b 137 ///
138 /// Inherited from AliHLTComponent. Returns an estimate of the expected output data size.
139 ///
140
13f09bc1 141 constBase = sizeof(AliHLTMUONRecHitsBlockWriter::HeaderType);
29486e5a 142 inputMultiplier = 1;
960d54ad 143}
b0201cbe 144
b0201cbe 145
960d54ad 146AliHLTComponent* AliHLTMUONHitReconstructorComponent::Spawn()
147{
6253e09b 148 ///
149 /// Inherited from AliHLTComponent. Creates a new object instance.
150 ///
151
29486e5a 152 return new AliHLTMUONHitReconstructorComponent;
960d54ad 153}
b0201cbe 154
b0201cbe 155
29486e5a 156int AliHLTMUONHitReconstructorComponent::DoInit(int argc, const char** argv)
960d54ad 157{
6253e09b 158 ///
159 /// Inherited from AliHLTComponent.
160 /// Parses the command line parameters and initialises the component.
161 ///
b0201cbe 162
ee3678d3 163 HLTInfo("Initialising dHLT hit reconstruction component.");
960d54ad 164
93a75941 165 // Must make sure that fHitRec and fLut is deleted if it is still
166 // allocated for whatever reason.
a6b16447 167 FreeMemory();
168
ee3678d3 169 try
170 {
171 fHitRec = new AliHLTMUONHitReconstructor();
960d54ad 172 }
ee3678d3 173 catch (const std::bad_alloc&)
b8d467da 174 {
ee3678d3 175 HLTError("Could not allocate more memory for the hit reconstructor component.");
176 return -ENOMEM;
b8d467da 177 }
960d54ad 178
a6b16447 179 // Initialise fields with default values then parse the command line.
180 fDDL = -1;
181 fIdToEntry.clear();
ee3678d3 182 fWarnForUnexpecedBlock = false;
ffc1a6f6 183 fDelaySetup = false;
a6b16447 184
ee3678d3 185 const char* lutFileName = NULL;
186 const char* cdbPath = NULL;
187 Int_t run = -1;
188 bool useCDB = false;
a5d4696f 189 bool tryRecover = false;
ffc1a6f6 190 AliHLTInt32_t dccut = -1;
ee3678d3 191
192 for (int i = 0; i < argc; i++)
193 {
194 HLTDebug("argv[%d] == %s", i, argv[i]);
195
196 if (strcmp( argv[i], "-ddl" ) == 0)
197 {
ffc1a6f6 198 if (fDDL != -1)
199 {
200 HLTWarning("DDL number was already specified."
201 " Will replace previous value given by -ddl or -ddlid."
202 );
203 }
204
ee3678d3 205 if (argc <= i+1)
206 {
207 HLTError("The DDL number was not specified. Must be in the range [13..20].");
a6b16447 208 FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
209 return -EINVAL;
ee3678d3 210 }
211
212 char* cpErr = NULL;
213 unsigned long num = strtoul( argv[i+1], &cpErr, 0 );
214 if (cpErr == NULL or *cpErr != '\0')
215 {
93a75941 216 HLTError("Cannot convert '%s' to DDL a number.", argv[i+1] );
a6b16447 217 FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
218 return -EINVAL;
ee3678d3 219 }
220 if (num < 13 or 20 < num)
221 {
222 HLTError("The DDL number must be in the range [13..20].");
a6b16447 223 FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
224 return -EINVAL;
ee3678d3 225 }
93a75941 226 fDDL = num - 1; // convert to range [12..19]
ee3678d3 227
228 i++;
229 continue;
230 } // -ddl argument
231
a3d4b6ba 232 if (strcmp( argv[i], "-ddlid" ) == 0)
233 {
ffc1a6f6 234 if (fDDL != -1)
235 {
236 HLTWarning("DDL number was already specified."
237 " Will replace previous value given by -ddl or -ddlid."
238 );
239 }
240
a3d4b6ba 241 if ( argc <= i+1 )
242 {
243 HLTError("DDL equipment ID number not specified. It must be in the range [2572..2579]" );
244 FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
245 return -EINVAL;
246 }
247
248 char* cpErr = NULL;
249 unsigned long num = strtoul(argv[i+1], &cpErr, 0);
250 if (cpErr == NULL or *cpErr != '\0')
251 {
252 HLTError("Cannot convert '%s' to a DDL equipment ID Number.", argv[i+1]);
253 FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
254 return -EINVAL;
255 }
256 fDDL = AliHLTMUONUtils::EquipIdToDDLNumber(num); // Convert to DDL number in the range 0..21
257 if (fDDL < 12 or 19 < fDDL)
258 {
259 HLTError("The DDL equipment ID number must be in the range [2572..2579].");
260 FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
261 return -EINVAL;
262 }
263
264 i++;
265 continue;
266 }
267
ee3678d3 268 if (strcmp( argv[i], "-lut" ) == 0)
269 {
ffc1a6f6 270 if (lutFileName != NULL)
271 {
272 HLTWarning("LUT path was already specified."
273 " Will replace previous value given by -lut."
274 );
275 }
276
ee3678d3 277 if (argc <= i+1)
278 {
279 HLTError("The lookup table filename was not specified.");
a6b16447 280 FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
281 return -EINVAL;
ee3678d3 282 }
283 lutFileName = argv[i+1];
284 i++;
285 continue;
286 } // -lut argument
287
288 if (strcmp( argv[i], "-cdb" ) == 0)
289 {
290 useCDB = true;
291 continue;
292 } // -cdb argument
293
294 if (strcmp( argv[i], "-cdbpath" ) == 0)
295 {
ffc1a6f6 296 if (cdbPath != NULL)
297 {
298 HLTWarning("CDB path was already specified."
299 " Will replace previous value given by -cdbpath."
300 );
301 }
302
ee3678d3 303 if ( argc <= i+1 )
304 {
305 HLTError("The CDB path was not specified." );
a6b16447 306 FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
307 return -EINVAL;
ee3678d3 308 }
309 cdbPath = argv[i+1];
310 useCDB = true;
311 i++;
312 continue;
313 } // -cdb argument
314
315 if (strcmp( argv[i], "-run" ) == 0)
316 {
ffc1a6f6 317 if (run != -1)
318 {
319 HLTWarning("Run number was already specified."
320 " Will replace previous value given by -run."
321 );
322 }
323
ee3678d3 324 if ( argc <= i+1 )
325 {
ffc1a6f6 326 HLTError("The run number was not specified." );
a6b16447 327 FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
328 return -EINVAL;
ee3678d3 329 }
330
331 char* cpErr = NULL;
ffc1a6f6 332 run = Int_t( strtol(argv[i+1], &cpErr, 0) );
333 if (cpErr == NULL or *cpErr != '\0' or run < 0)
ee3678d3 334 {
335 HLTError("Cannot convert '%s' to a valid run number."
ffc1a6f6 336 " Expected a positive integer value.", argv[i+1]
ee3678d3 337 );
a6b16447 338 FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
339 return -EINVAL;
ee3678d3 340 }
341
342 i++;
343 continue;
344 } // -run argument
ffc1a6f6 345
346 if (strcmp( argv[i], "-dccut" ) == 0)
347 {
348 if (dccut != -1)
349 {
350 HLTWarning("DC cut parameter was already specified."
351 " Will replace previous value given by -dccut."
352 );
353 }
354
355 if ( argc <= i+1 )
356 {
357 HLTError("No DC cut value was specified. It should be a positive integer value." );
358 FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
359 return -EINVAL;
360 }
361
362 char* cpErr = NULL;
363 dccut = AliHLTInt32_t( strtol(argv[i+1], &cpErr, 0) );
364 if (cpErr == NULL or *cpErr != '\0' or dccut < 0)
365 {
366 HLTError("Cannot convert '%s' to a valid DC cut value."
367 " Expected a positive integer value.", argv[i+1]
368 );
369 FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
370 return -EINVAL;
371 }
372
373 i++;
374 continue;
375 }
376
377 if (strcmp( argv[i], "-delaysetup" ) == 0)
378 {
379 fDelaySetup = true;
380 continue;
381 }
ee3678d3 382
383 if (strcmp( argv[i], "-warn_on_unexpected_block" ) == 0)
384 {
385 fWarnForUnexpecedBlock = true;
386 continue;
387 }
a5d4696f 388
389 if (strcmp( argv[i], "-tryrecover" ) == 0)
390 {
391 tryRecover = true;
392 continue;
393 }
ee3678d3 394
395 HLTError("Unknown option '%s'", argv[i]);
a6b16447 396 FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
397 return -EINVAL;
ee3678d3 398
399 } // for loop
400
2b7af22a 401 if (dccut != -1 and useCDB)
402 {
403 HLTWarning("The -cdb or -cdbpath parameter was specified, which indicates that"
404 " this component should read from the CDB, but then the -dccut argument"
405 " was also used. Will override the value from CDB with the command"
406 " line DC cut parameter given."
407 );
408 }
409
410 if (lutFileName != NULL and useCDB == true)
411 {
412 HLTWarning("The -cdb or -cdbpath parameter was specified, which indicates that"
413 " this component should read from the CDB, but then the -lut argument"
414 " was also used. Will ignore the -lut option and load from CDB anyway."
415 );
416 }
417
93a75941 418 if (lutFileName == NULL) useCDB = true;
419
ffc1a6f6 420 if (fDDL == -1 and not fDelaySetup)
a6b16447 421 {
422 HLTWarning("DDL number not specified. Cannot check if incomming data is valid.");
423 }
424
ffc1a6f6 425 if (cdbPath != NULL or run != -1)
426 {
427 int result = SetCDBPathAndRunNo(cdbPath, run);
428 if (result != 0)
429 {
430 // Error messages already generated in SetCDBPathAndRunNo.
431 FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
432 return result;
433 }
434 }
435
ee3678d3 436 if (useCDB)
437 {
ffc1a6f6 438 if (not fDelaySetup)
439 {
440 HLTInfo("Loading lookup table information from CDB for DDL %d (ID = %d).",
441 fDDL+1, AliHLTMUONUtils::DDLNumberToEquipId(fDDL)
442 );
443 int result = ReadLutFromCDB();
444 if (result != 0)
445 {
446 // Error messages already generated in ReadLutFromCDB.
447 FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
448 return result;
449 }
450 fHitRec->SetLookUpTable(fLut, &fIdToEntry);
451 }
960d54ad 452 }
ee3678d3 453 else
454 {
93a75941 455 HLTInfo("Loading lookup table information from file %s.", lutFileName);
ffc1a6f6 456 int result = ReadLookUpTable(lutFileName);
457 if (result != 0)
458 {
459 // Error messages already generated in ReadLookUpTable.
460 FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
461 return result;
462 }
463 fHitRec->SetLookUpTable(fLut, &fIdToEntry);
ee3678d3 464 }
ffc1a6f6 465
466 if (dccut == -1)
ee3678d3 467 {
ffc1a6f6 468 if (not fDelaySetup)
469 {
470 HLTInfo("Loading DC cut parameters from CDB for DDL %d (ID = %d).",
471 fDDL+1, AliHLTMUONUtils::DDLNumberToEquipId(fDDL)
472 );
473 int result = ReadDCCutFromCDB();
474 if (result != 0)
475 {
476 // Error messages already generated in ReadDCCutFromCDB.
477 FreeMemory(); // Make sure we cleanup to avoid partial initialisation.
478 return result;
479 }
2b7af22a 480 }
481 else
482 {
483 // Print the debug messages here since ReadDCCutFromCDB does not get called,
484 // in-which the debug messages would have been printed.
ffc1a6f6 485 HLTDebug("Using DC cut parameter of %d ADC channels.", fHitRec->GetDCCut());
486 }
487 }
488 else
489 {
ffc1a6f6 490 fHitRec->SetDCCut(dccut);
491 HLTDebug("Using DC cut parameter of %d ADC channels.", fHitRec->GetDCCut());
ee3678d3 492 }
493
a5d4696f 494 fHitRec->TryRecover(tryRecover);
ee3678d3 495
496 return 0;
b0201cbe 497}
498
960d54ad 499
500int AliHLTMUONHitReconstructorComponent::DoDeinit()
501{
6253e09b 502 ///
503 /// Inherited from AliHLTComponent. Performs a cleanup of the component.
504 ///
505
ee3678d3 506 HLTInfo("Deinitialising dHLT hit reconstruction component.");
a6b16447 507 FreeMemory();
ee3678d3 508 return 0;
b0201cbe 509}
510
b0201cbe 511
ffc1a6f6 512int AliHLTMUONHitReconstructorComponent::Reconfigure(
513 const char* cdbEntry, const char* componentId
514 )
515{
516 /// Inherited from AliHLTComponent. This method will reload CDB configuration
517 /// entries for this component from the CDB.
518 /// \param cdbEntry If this is NULL then it is assumed that all CDB entries should
519 /// be reloaded. Otherwise a particular value for 'cdbEntry' will trigger
520 /// reloading of the LUT if the path contains 'MUON/' and reloading of the DC
2b7af22a 521 /// cut parameter if 'cdbEntry' equals "HLT/ConfigMUON/HitReconstructor".
522 /// \param componentId The name of the component in the current chain.
523
524 bool startsWithMUON = TString(cdbEntry).Index("MUON/", 5, 0, TString::kExact) == 0;
525 bool givenConfigPath = strcmp(cdbEntry, AliHLTMUONConstants::HitReconstructorCDBPath()) == 0;
ffc1a6f6 526
2b7af22a 527 if (cdbEntry == NULL or startsWithMUON or givenConfigPath)
ffc1a6f6 528 {
2b7af22a 529 HLTInfo("Reading new configuration entries from CDB for component '%s'.", componentId);
530 }
ffc1a6f6 531
2b7af22a 532 if (cdbEntry == NULL or startsWithMUON)
533 {
534 // First clear the current LUT data and then load in the new values.
535 if (fLut != NULL)
ffc1a6f6 536 {
2b7af22a 537 delete [] fLut;
538 fLut = NULL;
539 fLutSize = 0;
ffc1a6f6 540 }
541
2b7af22a 542 fIdToEntry.clear();
543
544 int result = ReadLutFromCDB();
545 if (result != 0) return result;
546 fHitRec->SetLookUpTable(fLut, &fIdToEntry);
547 }
548
549 if (cdbEntry == NULL or not startsWithMUON)
550 {
551 int result = ReadDCCutFromCDB();
552 if (result != 0) return result;
ffc1a6f6 553 }
554
555 return 0;
556}
557
558
559int AliHLTMUONHitReconstructorComponent::ReadPreprocessorValues(const char* modules)
560{
561 /// Inherited from AliHLTComponent.
562 /// Updates the configuration of this component if either HLT or MUON have
563 /// been specified in the 'modules' list.
564
565 TString mods = modules;
566 if (mods.Contains("ALL") or (mods.Contains("HLT") and mods.Contains("MUON")))
567 {
568 return Reconfigure(NULL, GetComponentID());
569 }
570 if (mods.Contains("HLT"))
571 {
572 return Reconfigure(AliHLTMUONConstants::HitReconstructorCDBPath(), GetComponentID());
573 }
574 if (mods.Contains("MUON"))
575 {
576 return Reconfigure("MUON/*", GetComponentID());
577 }
578 return 0;
579}
580
581
960d54ad 582int AliHLTMUONHitReconstructorComponent::DoEvent(
583 const AliHLTComponentEventData& evtData,
b8d467da 584 const AliHLTComponentBlockData* blocks,
585 AliHLTComponentTriggerData& /*trigData*/,
586 AliHLTUInt8_t* outputPtr,
960d54ad 587 AliHLTUInt32_t& size,
588 std::vector<AliHLTComponentBlockData>& outputBlocks
589 )
590{
6253e09b 591 ///
592 /// Inherited from AliHLTProcessor. Processes the new event data.
593 ///
594
ffc1a6f6 595 // Initialise the LUT and DC cut parameter from CDB if we were requested
596 // to initialise only when the first event was received.
597 if (fDelaySetup)
598 {
599 // Use the specification given by the first data block if we
600 // have not been given a DDL number on the command line.
601 if (fDDL == -1)
602 {
48ccb241 603 bool blockFound = false;
604 for (AliHLTUInt32_t n = 0; n < evtData.fBlockCnt and not blockFound; n++)
605 {
606 if (blocks[n].fDataType != AliHLTMUONConstants::DDLRawDataType()) continue;
607 blockFound = true;
608
609 fDDL = AliHLTMUONUtils::SpecToDDLNumber(blocks[n].fSpecification);
610
611 if (fDDL == -1)
612 {
613 HLTError("Received a data block with a specification (0x%8.8X)"
614 " indicating multiple DDL data sources, but we must only"
615 " receive raw DDL data from one tracking station DDL.",
616 blocks[n].fSpecification
617 );
618 return -EPROTO;
619 }
620 }
621
622 if (not blockFound)
ffc1a6f6 623 {
624 HLTError("The initialisation from CDB of the component has"
625 " been delayed to the first received event. However,"
48ccb241 626 " no raw DDL data blocks have been found in the first event."
ffc1a6f6 627 );
628 return -ENOENT;
629 }
ffc1a6f6 630 }
631
632 // Check that the LUT was not already loaded in DoInit.
633 if (fLut == NULL)
634 {
635 HLTInfo("Loading lookup table information from CDB for DDL %d (ID = %d).",
636 fDDL+1, AliHLTMUONUtils::DDLNumberToEquipId(fDDL)
637 );
638 int result = ReadLutFromCDB();
639 if (result != 0) return result;
640
641 fHitRec->SetLookUpTable(fLut, &fIdToEntry);
642 }
643
644 // Check that the DC cut was not already loaded in DoInit.
645 if (fHitRec->GetDCCut() == -1)
646 {
647 HLTInfo("Loading DC cut parameters from CDB for DDL %d (ID = %d).",
648 fDDL+1, AliHLTMUONUtils::DDLNumberToEquipId(fDDL)
649 );
650 int result = ReadDCCutFromCDB();
651 if (result != 0) return result;
ffc1a6f6 652 }
653
654 fDelaySetup = false;
655 }
656
657 if (fLut == NULL)
658 {
659 HLTFatal("Lookup table not loaded! Cannot continue processing data.");
660 return -ENOENT;
661 }
662
29486e5a 663 // Process an event
664 unsigned long totalSize = 0; // Amount of memory currently consumed in bytes.
b0201cbe 665
29486e5a 666 HLTDebug("Processing event %llu with %u input data blocks.",
667 evtData.fEventID, evtData.fBlockCnt
668 );
669
670 // Loop over all input blocks in the event
450e0b36 671 for (AliHLTUInt32_t n = 0; n < evtData.fBlockCnt; n++)
5ff5f960 672 {
450e0b36 673 HLTDebug("Handling block: %u, with fDataType = '%s', fPtr = %p and fSize = %u bytes.",
674 n, DataType2Text(blocks[n].fDataType).c_str(), blocks[n].fPtr, blocks[n].fSize
5ff5f960 675 );
29486e5a 676
668eee9f 677 if (blocks[n].fDataType != AliHLTMUONConstants::DDLRawDataType()
678 or not AliHLTMUONUtils::IsTrackerDDL(blocks[n].fSpecification)
679 )
29486e5a 680 {
681 // Log a message indicating that we got a data block that we
682 // do not know how to handle.
29486e5a 683 if (fWarnForUnexpecedBlock)
450e0b36 684 HLTWarning("Received a data block of a type we cannot handle: '%s', spec: 0x%X",
685 DataType2Text(blocks[n].fDataType).c_str(), blocks[n].fSpecification
29486e5a 686 );
687 else
450e0b36 688 HLTDebug("Received a data block of a type we cannot handle: '%s', spec: 0x%X",
689 DataType2Text(blocks[n].fDataType).c_str(), blocks[n].fSpecification
29486e5a 690 );
691
692 continue;
693 }
694
a6b16447 695 if (fDDL != -1)
ee3678d3 696 {
a3d4b6ba 697 AliHLTInt32_t receivedDDL = AliHLTMUONUtils::SpecToDDLNumber(blocks[n].fSpecification);
698 if (receivedDDL != fDDL)
a6b16447 699 {
a3d4b6ba 700 HLTWarning("Received raw data from DDL %d (ID = %d),"
701 " but expect data only from DDL %d (ID = %d).",
702 receivedDDL+1, AliHLTMUONUtils::DDLNumberToEquipId(receivedDDL),
703 fDDL+1, AliHLTMUONUtils::DDLNumberToEquipId(fDDL)
704 );
a6b16447 705 }
ee3678d3 706 }
707
29486e5a 708 // Create a new output data block and initialise the header.
709 AliHLTMUONRecHitsBlockWriter block(outputPtr+totalSize, size-totalSize);
710 if (not block.InitCommonHeader())
711 {
8bade2be 712 HLTError("There is not enough space in the output buffer for the new data block."
29486e5a 713 " We require at least %u bytes, but have %u bytes left.",
714 sizeof(AliHLTMUONRecHitsBlockWriter::HeaderType),
715 block.BufferSize()
716 );
717 break;
718 }
719
720 AliHLTUInt32_t totalDDLSize = blocks[n].fSize / sizeof(AliHLTUInt32_t);
721 AliHLTUInt32_t ddlRawDataSize = totalDDLSize - fHitRec->GetkDDLHeaderSize();
649ab027 722 AliHLTUInt32_t* buffer = reinterpret_cast<AliHLTUInt32_t*>(
723 reinterpret_cast<char*>(blocks[n].fPtr) + blocks[n].fOffset
724 ) + fHitRec->GetkDDLHeaderSize();
29486e5a 725 AliHLTUInt32_t nofHit = block.MaxNumberOfEntries();
726
ee3678d3 727#ifdef DEBUG
29486e5a 728 HLTDebug("=========== Dumping DDL payload buffer ==========");
729 for (AliHLTUInt32_t j = 0; j < totalDDLSize; j++)
730 HLTDebug("buffer[%d] : %x",j,buffer[j]);
731 HLTDebug("================== End of dump =================");
ee3678d3 732#endif // DEBUG
29486e5a 733
734 if (not fHitRec->Run(buffer, ddlRawDataSize, block.GetArray(), nofHit))
735 {
154cba94 736 HLTError("Error while processing the hit reconstruction algorithm.");
29486e5a 737 size = totalSize; // Must tell the framework how much buffer space was used.
a6b16447 738 return -EIO;
29486e5a 739 }
740
741 // nofHit should now contain the number of reconstructed hits actually found
742 // and filled into the output data block, so we can set this number.
743 assert( nofHit <= block.MaxNumberOfEntries() );
744 block.SetNumberOfEntries(nofHit);
745
746 HLTDebug("Number of reconstructed hits found is %d", nofHit);
747
748 // Fill a block data structure for our output block.
749 AliHLTComponentBlockData bd;
750 FillBlockData(bd);
751 bd.fPtr = outputPtr;
752 // This block's start (offset) is after all other blocks written so far.
753 bd.fOffset = totalSize;
754 bd.fSize = block.BytesUsed();
755 bd.fDataType = AliHLTMUONConstants::RecHitsBlockDataType();
756 bd.fSpecification = blocks[n].fSpecification;
757 outputBlocks.push_back(bd);
758
759 // Increase the total amount of data written so far to our output memory
760 totalSize += block.BytesUsed();
5ff5f960 761 }
29486e5a 762 // Finally we set the total size of output memory we consumed.
763 size = totalSize;
764
765 return 0;
b0201cbe 766}
767
768
a6b16447 769void AliHLTMUONHitReconstructorComponent::FreeMemory()
770{
771 /// Deletes any allocated objects if they are allocated else nothing is
772 /// done for objects not yet allocated.
773 /// This is used as a helper method to make sure the corresponding pointers
93a75941 774 /// are NULL and we get back to a well defined state.
a6b16447 775
776 if (fHitRec != NULL)
777 {
778 delete fHitRec;
779 fHitRec = NULL;
780 }
93a75941 781 if (fLut != NULL)
782 {
878cb83d 783 delete [] fLut;
93a75941 784 fLut = NULL;
785 fLutSize = 0;
786 }
a6b16447 787
788 fIdToEntry.clear();
789}
790
791
93a75941 792int AliHLTMUONHitReconstructorComponent::ReadLookUpTable(const char* lutFileName)
ee3678d3 793{
93a75941 794 /// Read in the lookup table from a text file.
795 /// Note that this method could leave fLut allocated which is cleaned up
796 /// by DoInit with a call to FreeMemory().
797
798 assert( fLut == NULL );
799 assert( fLutSize == 0 );
800 assert( fIdToEntry.empty() );
801
802 std::ifstream file(lutFileName);
803 if (not file.good())
804 {
805 HLTError("Could not open the LUT file %s", lutFileName);
806 return -ENOENT;
807 }
808
809 // First count the number of lines of text in the LUT file before decoding.
810 // This is not the most optimal. It would be better to read and decode at the
811 // same time but we are not allowed to use STL and ROOT containers are too
812 // heavy for this task. At least this is done only at the start of run.
813 std::string str;
814 AliHLTUInt32_t lineCount = 0;
815 while (std::getline(file, str)) lineCount++;
816 if (not file.eof())
817 {
818 HLTError("There was a problem reading the LUT file %s", lutFileName);
819 return -EIO;
820 }
821 if (lineCount == 0)
822 {
823 HLTWarning("The LUT file %s was empty.", lutFileName);
824 }
825
826 // Add one extra LUT line for the first element which is used as a sentinel value.
827 lineCount++;
828
829 try
830 {
831 fLut = new AliHLTMUONHitRecoLutRow[lineCount];
832 fLutSize = lineCount;
833 }
834 catch (const std::bad_alloc&)
835 {
836 HLTError("Could not allocate more memory for the lookuptable.");
837 return -ENOMEM;
838 }
839
840 // Initialise the sentinel value.
841 fLut[0].fDetElemId = 0;
842 fLut[0].fIX = 0;
843 fLut[0].fIY = 0;
844 fLut[0].fRealX = 0.0;
845 fLut[0].fRealY = 0.0;
846 fLut[0].fRealZ = 0.0;
847 fLut[0].fHalfPadSize = 0.0;
848 fLut[0].fPlane = -1;
849 fLut[0].fPed = -1;
850 fLut[0].fSigma = -1;
851 fLut[0].fA0 = -1;
852 fLut[0].fA1 = -1;
853 fLut[0].fThres = -1;
854 fLut[0].fSat = -1;
855
856 // Clear the eof flag and start reading from the beginning of the file again.
857 file.clear();
858 file.seekg(0, std::ios::beg);
859 if (not file.good())
860 {
861 HLTError("There was a problem seeking in the LUT file %s", lutFileName);
862 return -EIO;
863 }
864
865 AliHLTInt32_t idManuChannel;
866 for (AliHLTUInt32_t i = 1; i < fLutSize; i++)
867 {
868 if (std::getline(file, str).fail())
869 {
870 HLTError("There was a problem reading line %d of LUT file %s", i, lutFileName);
871 return -EIO;
872 }
873
874 int result = sscanf(
875 str.c_str(), "%d\t%d\t%d\t%d\t%e\t%e\t%e\t%e\t%d\t%e\t%e\t%e\t%e\t%d\t%d",
876 &idManuChannel, &fLut[i].fDetElemId, &fLut[i].fIX,
877 &fLut[i].fIY, &fLut[i].fRealX,
878 &fLut[i].fRealY, &fLut[i].fRealZ,
879 &fLut[i].fHalfPadSize, &fLut[i].fPlane,
880 &fLut[i].fPed, &fLut[i].fSigma, &fLut[i].fA0,
881 &fLut[i].fA1, &fLut[i].fThres, &fLut[i].fSat
882 );
883
884 if (result != 15)
885 {
886 HLTError("Line %d in LUT file %s does not contain 15 elements.", i, lutFileName);
887 return -EIO;
888 }
889
890 fIdToEntry[idManuChannel] = i;
891 }
892
893 return 0;
ee3678d3 894}
895
896
ffc1a6f6 897int AliHLTMUONHitReconstructorComponent::ReadLutFromCDB()
b0201cbe 898{
dba14d7d 899 /// Reads LUT from CDB.
ffc1a6f6 900 /// To override the default CDB path and / or run number the
901 /// SetCDBPathAndRunNo(cdbPath, run) method should be called before this
902 /// method.
93a75941 903
904 assert( fLut == NULL );
905 assert( fLutSize == 0 );
906 assert( fIdToEntry.empty() );
907
a3d4b6ba 908 if (fDDL == -1)
909 {
910 HLTError("No DDL number specified for which to load LUT data from CDB.");
911 return -EINVAL;
912 }
913
93a75941 914 std::vector<AliHLTMUONHitRecoLutRow> lutList;
915 AliHLTMUONHitRecoLutRow lut;
916 AliHLTUInt32_t iEntry = 0;
917
ffc1a6f6 918 int result = FetchMappingStores();
dba14d7d 919 // Error message already generated in FetchMappingStores.
920 if (result != 0) return result;
93a75941 921 AliMpDDLStore* ddlStore = AliMpDDLStore::Instance();
dba14d7d 922
93a75941 923 AliMpSegmentation* mpSegFactory = AliMpSegmentation::Instance();
924 if (mpSegFactory == NULL)
925 {
926 HLTError("Could not find segmentation mapping (AliMpSegmentation) instance.");
927 return -EIO;
928 }
929
61d982d3 930 // Only load geometry if not already loaded.
931 if (AliGeomManager::GetGeometry() == NULL)
932 {
933 AliGeomManager::LoadGeometry();
934 }
93a75941 935 AliMUONGeometryTransformer chamberGeometryTransformer;
936 if (not chamberGeometryTransformer.LoadGeometryData())
937 {
938 HLTError("Failed to load geomerty data.");
939 return -ENOENT;
940 }
941
ffc1a6f6 942 AliMUONCalibrationData calibData(AliCDBManager::Instance()->GetRun());
93a75941 943
944 Int_t chamberId;
945
946 for(Int_t iCh = 6; iCh < 10; iCh++)
947 {
948 chamberId = iCh;
949
950 AliMpDEIterator it;
951 for ( it.First(chamberId); ! it.IsDone(); it.Next() )
952 {
953 Int_t detElemId = it.CurrentDEId();
954 int iDDL = ddlStore->GetDetElement(detElemId)->GetDdlId();
955 if (iDDL != fDDL) continue;
956
957 for (Int_t iCath = 0 ; iCath <= 1 ; iCath++)
958 {
959 AliMp::CathodType cath;
960
961 if(iCath == 0)
962 cath = AliMp::kCath0;
963 else
964 cath = AliMp::kCath1;
965
966 const AliMpVSegmentation* seg = mpSegFactory->GetMpSegmentation(detElemId, cath);
967 AliMp::PlaneType plane = seg->PlaneType();
968 Int_t maxIX = seg->MaxPadIndexX();
969 Int_t maxIY = seg->MaxPadIndexY();
970
971 Int_t idManuChannel, manuId, channelId, buspatchId;
972 AliHLTFloat32_t padSizeX, padSizeY;
973 AliHLTFloat32_t halfPadSize;
974 Double_t realX, realY, realZ;
975 Double_t localX, localY, localZ;
976 Float_t calibA0Coeff,calibA1Coeff,pedestal,sigma;
977 Int_t thresold,saturation;
978
979 // Pad Info of a slat to print in lookuptable
980 for (Int_t iX = 0; iX<= maxIX ; iX++)
981 for (Int_t iY = 0; iY<= maxIY ; iY++)
982 {
983 if (not seg->HasPad(AliMpIntPair(iX,iY))) continue;
984
985 AliMpPad pad = seg->PadByIndices(AliMpIntPair(iX,iY), kFALSE);
986
987 // Getting Manu id
988 manuId = pad.GetLocation().GetFirst();
989 manuId &= 0x7FF; // 11 bits
990
991 buspatchId = ddlStore->GetBusPatchId(detElemId,manuId);
992
993 // Getting channel id
994 channelId = pad.GetLocation().GetSecond();
995 channelId &= 0x3F; // 6 bits
996
997 idManuChannel = buspatchId << 11;
998 idManuChannel = (idManuChannel | manuId) << 6;
999 idManuChannel |= channelId;
1000
1001 localX = pad.Position().X();
1002 localY = pad.Position().Y();
1003 localZ = 0.0;
1004
1005 chamberGeometryTransformer.Local2Global(
1006 detElemId,localX,localY,localZ,
1007 realX,realY,realZ
1008 );
1009
1010 padSizeX = pad.Dimensions().X();
1011 padSizeY = pad.Dimensions().Y();
1012
1013 calibA0Coeff = (calibData.Gains(detElemId, manuId))->ValueAsFloat(channelId, 0);
1014 calibA1Coeff = (calibData.Gains(detElemId, manuId))->ValueAsFloat(channelId, 1);
1015 thresold = (calibData.Gains(detElemId, manuId))->ValueAsInt(channelId, 2);
1016 saturation = (calibData.Gains(detElemId, manuId))->ValueAsInt(channelId, 4);
1017
1018 pedestal = (calibData.Pedestals(detElemId, manuId))->ValueAsFloat(channelId, 0);
1019 sigma = (calibData.Pedestals(detElemId, manuId))->ValueAsFloat(channelId, 1);
1020
1021 if (plane == 0)
1022 halfPadSize = padSizeX;
1023 else
1024 halfPadSize = padSizeY;
1025
1026 fIdToEntry[idManuChannel] = iEntry+1;
1027
1028 lut.fDetElemId = detElemId;
1029 lut.fIX = iX;
1030 lut.fIY = iY;
1031 lut.fRealX = realX;
1032 lut.fRealY = realY;
1033 lut.fRealZ = realZ;
1034 lut.fHalfPadSize = halfPadSize;
1035 lut.fPlane = plane;
1036 lut.fPed = pedestal;
1037 lut.fSigma = sigma;
1038 lut.fA0 = calibA0Coeff;
1039 lut.fA1 = calibA1Coeff;
1040 lut.fThres = thresold;
1041 lut.fSat = saturation;
1042
1043 lutList.push_back(lut);
1044 iEntry++;
1045 } // iX, iY loop
1046 } // iCath loop
1047 } // detElemId loop
1048 } // ichamber loop
1049
1050 try
1051 {
1052 // Use iEntry+1 since we add one extra LUT line for the first element
1053 // which is used as a sentinel value.
1054 fLut = new AliHLTMUONHitRecoLutRow[iEntry+1];
1055 fLutSize = iEntry+1;
1056 }
1057 catch (const std::bad_alloc&)
1058 {
1059 HLTError("Could not allocate more memory for the lookuptable.");
1060 return -ENOMEM;
1061 }
1062
1063 // Initialise the sentinel value.
1064 fLut[0].fDetElemId = 0;
1065 fLut[0].fIX = 0;
1066 fLut[0].fIY = 0;
1067 fLut[0].fRealX = 0.0;
1068 fLut[0].fRealY = 0.0;
1069 fLut[0].fRealZ = 0.0;
1070 fLut[0].fHalfPadSize = 0.0;
1071 fLut[0].fPlane = -1;
1072 fLut[0].fPed = -1;
1073 fLut[0].fSigma = -1;
1074 fLut[0].fA0 = -1;
1075 fLut[0].fA1 = -1;
1076 fLut[0].fThres = -1;
1077 fLut[0].fSat = -1;
1078
1079 for (AliHLTUInt32_t i = 0; i < iEntry; i++)
1080 fLut[i+1] = lutList[i];
1081
1082 return 0;
b0201cbe 1083}
1084
b0201cbe 1085
2b7af22a 1086int AliHLTMUONHitReconstructorComponent::ReadDCCutFromCDB()
ffc1a6f6 1087{
1088 /// Reads the DC cut parameter from the CDB.
1089
1090 const char* pathToEntry = AliHLTMUONConstants::HitReconstructorCDBPath();
ffc1a6f6 1091
1092 TMap* map = NULL;
1093 int result = FetchTMapFromCDB(pathToEntry, map);
1094 if (result != 0) return result;
1095
1096 Int_t value = 0;
1097 result = GetPositiveIntFromTMap(map, "dccut", value, pathToEntry, "DC cut");
1098 if (result != 0) return result;
1099
1100 assert(fHitRec != NULL);
1101 fHitRec->SetDCCut(value);
1102
2b7af22a 1103 HLTDebug("Using DC cut parameter of %d ADC channels.", fHitRec->GetDCCut());
1104
ffc1a6f6 1105 return 0;
1106}
1107
1108
93a75941 1109bool AliHLTMUONHitReconstructorComponent::GenerateLookupTable(
1110 AliHLTInt32_t ddl, const char* filename,
ee3678d3 1111 const char* cdbPath, Int_t run
1112 )
b0201cbe 1113{
93a75941 1114 /// Generates a ASCII text file containing the lookup table (LUT) from
1115 /// the CDB, which can be used for the hit reconstructor component later.
1116 /// @param ddl Must be the DDL for which to generate the DDL,
1117 /// in the range [13..20].
1118 /// @param filename The name of the LUT file to generate.
1119 /// @param cdbPath The CDB path to use.
1120 /// @param run The run number to use for the CDB.
1121 /// @return True if the generation of the LUT file succeeded.
1122
1123 AliHLTMUONHitReconstructorComponent comp;
1124
1125 if (ddl < 12 or 19 < ddl)
1126 {
1127 std::cerr << "ERROR: the DDL number must be in the range [12..19]." << std::endl;
1128 return false;
1129 }
1130
1131 comp.fDDL = ddl;
ffc1a6f6 1132 if (comp.SetCDBPathAndRunNo(cdbPath, run) != 0) return false;
1133 if (comp.ReadLutFromCDB() != 0) return false;
93a75941 1134
1135 char str[1024*4];
1136 std::fstream file(filename, std::ios::out);
1137 if (not file)
1138 {
1139 std::cerr << "ERROR: could not open file: " << filename << std::endl;
1140 return false;
1141 }
1142
1143 assert( comp.fLut != NULL );
1144
1145 for (IdManuChannelToEntry::iterator id = comp.fIdToEntry.begin();
1146 id != comp.fIdToEntry.end();
1147 id++
1148 )
1149 {
1150 AliHLTInt32_t idManuChannel = id->first;
1151 AliHLTInt32_t row = id->second;
ee3678d3 1152
ffc1a6f6 1153 assert( AliHLTUInt32_t(row) < comp.fLutSize );
ee3678d3 1154
93a75941 1155 sprintf(str, "%d\t%d\t%d\t%d\t%.15e\t%.15e\t%.15e\t%.15e\t%d\t%.15e\t%.15e\t%.15e\t%.15e\t%d\t%d",
1156 idManuChannel, comp.fLut[row].fDetElemId, comp.fLut[row].fIX,
1157 comp.fLut[row].fIY, comp.fLut[row].fRealX,
1158 comp.fLut[row].fRealY, comp.fLut[row].fRealZ,
1159 comp.fLut[row].fHalfPadSize, comp.fLut[row].fPlane,
1160 comp.fLut[row].fPed, comp.fLut[row].fSigma, comp.fLut[row].fA0,
1161 comp.fLut[row].fA1, comp.fLut[row].fThres, comp.fLut[row].fSat
1162 );
ee3678d3 1163
93a75941 1164 file << str << endl;
1165 if (file.fail())
1166 {
1167 std::cerr << "ERROR: There was an I/O error when writing to the file: "
1168 << filename << std::endl;
1169 return false;
1170 }
1171 }
1172
1173 return true;
b0201cbe 1174}