]> git.uio.no Git - u/mrichter/AliRoot.git/blame - HLT/MUON/AliHLTMUONUtils.cxx
Fixing memory handling of AliHLTMUONHitReconstructorComponent during error conditions...
[u/mrichter/AliRoot.git] / HLT / MUON / AliHLTMUONUtils.cxx
CommitLineData
26a4668d 1/**************************************************************************
2 * Copyright(c) 1998-2007, ALICE Experiment at CERN, All rights reserved. *
3 * *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
6 * *
7 * Permission to use, copy, modify and distribute this software and its *
8 * documentation strictly for non-commercial purposes is hereby granted *
9 * without fee, provided that the above copyright notice appears in all *
10 * copies and that both the copyright notice and this permission notice *
11 * appear in the supporting documentation. The authors make no claims *
12 * about the suitability of this software for any purpose. It is *
13 * provided "as is" without express or implied warranty. *
14 **************************************************************************/
15
16/* $Id$ */
17
6253e09b 18///
19/// @file AliHLTMUONUtils.cxx
20/// @author Artur Szostak <artursz@iafrica.com>
21/// @date
22/// @brief Implementation of AliHLTMUONUtils utility routines.
23///
26a4668d 24
25#include "AliHLTMUONUtils.h"
b727f838 26#include "AliHLTMUONConstants.h"
c8ec7c7e 27#include "AliHLTMUONTriggerRecordsBlockStruct.h"
28#include "AliHLTMUONTrigRecsDebugBlockStruct.h"
29#include "AliHLTMUONTriggerChannelsBlockStruct.h"
30#include "AliHLTMUONRecHitsBlockStruct.h"
31#include "AliHLTMUONClustersBlockStruct.h"
32#include "AliHLTMUONChannelsBlockStruct.h"
90a74d7a 33#include "AliHLTMUONMansoTracksBlockStruct.h"
34#include "AliHLTMUONMansoCandidatesBlockStruct.h"
35#include "AliHLTMUONSinglesDecisionBlockStruct.h"
b12fe461 36#include "AliHLTMUONPairsDecisionBlockStruct.h"
f68b4e0e 37#include <cstring>
90a74d7a 38#include <cassert>
26a4668d 39
40
b727f838 41AliHLTUInt32_t AliHLTMUONUtils::PackTriggerRecordFlags(
e6357f88 42 AliHLTMUONParticleSign sign, const bool hitset[4]
b727f838 43 )
26a4668d 44{
6253e09b 45 ///
46 /// This packs the given parameters into the bits of a word appropriate
47 /// for AliHLTMUONTriggerRecordStruct::fFlags.
48 /// @param sign The particle sign.
49 /// @param hitset Flags to indicate if the corresponding fHits[i] elements
50 /// was set/filled.
51 /// @return Returns the 32 bit packed word.
52 ///
53
b727f838 54 AliHLTUInt32_t flags;
55 switch (sign)
56 {
57 case kSignMinus: flags = 0x80000000; break;
58 case kSignPlus: flags = 0x40000000; break;
59 default: flags = 0x00000000; break;
60 }
26a4668d 61
b727f838 62 return flags | (hitset[0] ? 0x1 : 0) | (hitset[1] ? 0x2 : 0)
63 | (hitset[2] ? 0x4 : 0) | (hitset[3] ? 0x8 : 0);
64}
65
66
67void AliHLTMUONUtils::UnpackTriggerRecordFlags(
90a74d7a 68 AliHLTUInt32_t flags, AliHLTMUONParticleSign& sign, bool hitset[4]
b727f838 69 )
70{
6253e09b 71 ///
72 /// This unpacks the AliHLTMUONTriggerRecordStruct::fFlags bits into
73 /// its component fields.
74 /// @param flags The flags from an AliHLTMUONTriggerRecordStruct structure.
75 /// @param sign Sets this to the particle sign.
76 /// @param hitset Sets the array elements to indicate if the corresponding
77 /// fHits[i] element was set/filled.
78 ///
79
b727f838 80 AliHLTUInt32_t signbits = flags & 0xC0000000;
81 switch (signbits)
82 {
83 case 0x80000000: sign = kSignMinus; break;
84 case 0x40000000: sign = kSignPlus; break;
85 default: sign = kSignUnknown; break;
86 }
e6357f88 87 hitset[0] = (flags & 0x1) == 0x1;
88 hitset[1] = (flags & 0x2) == 0x2;
89 hitset[2] = (flags & 0x4) == 0x4;
90 hitset[3] = (flags & 0x8) == 0x8;
b727f838 91}
92
93
90a74d7a 94AliHLTUInt32_t AliHLTMUONUtils::PackTrackDecisionBits(bool highPt, bool lowPt)
95{
6253e09b 96 ///
97 /// This packs the given parameters into the bits of a word appropriate
98 /// for AliHLTMUONTrackDecisionStruct::fTriggerBits.
99 /// @param highPt Has the track passed the high pt cut.
100 /// @param lowPt Has the track passed the low pt cut.
101 /// @return Returns the 32 bit packed word.
102 ///
103
90a74d7a 104 return (highPt ? 0x2 : 0) | (lowPt ? 0x1 : 0);
105}
106
107
108void AliHLTMUONUtils::UnpackTrackDecisionBits(
109 AliHLTUInt32_t bits, bool& highPt, bool& lowPt
110 )
111{
6253e09b 112 ///
113 /// This unpacks the AliHLTMUONTrackDecisionStruct::fTriggerBits bits into
114 /// its component fields.
115 /// @param bits The trigger bits from an AliHLTMUONTrackDecisionStruct
116 /// structure.
117 /// @param highPt Sets this to the value of the high pt cut bit.
118 /// @param lowPt Sets this to the value of the low pt cut bit.
119 ///
120
fc310e19 121 lowPt = (bits & 0x1) == 0x1;
122 highPt = (bits & 0x2) == 0x2;
90a74d7a 123}
124
125
126AliHLTUInt32_t AliHLTMUONUtils::PackPairDecisionBits(
127 bool highMass, bool lowMass, bool unlike,
128 AliHLTUInt8_t highPtCount, AliHLTUInt8_t lowPtCount
129 )
130{
6253e09b 131 ///
132 /// This packs the given parameters into the bits of a word appropriate
133 /// for AliHLTMUONPairDecisionStruct::fTriggerBits.
134 ///
135 /// @param highMass Has the track pair passed the high invariant mass cut.
136 /// @param lowMass Has the track pair passed the low invariant mass cut.
137 /// @param unlike Does the track pair have unlike signs.
138 /// @param highPtCount The number of tracks that passed the high pt cut
139 /// in the pair.
140 /// @param lowPtCount The number of tracks that passed the low pt cut
141 /// in the pair.
142 /// @return Returns the 32 bit packed word.
143 ///
144 /// Note: Must have highPtCount + lowPtCount <= 2 and unlike == true if
145 /// highMass or lowMass is true.
146 ///
147
90a74d7a 148 assert( highPtCount + lowPtCount <= 2 );
149 // highMass and lowMass must be false if unlike is false:
150 assert( not unlike ? (highMass == false and lowMass == false) : true );
151
152 return (highMass ? 0x40 : 0) | (lowMass ? 0x20 : 0) | (unlike ? 0x10 : 0)
153 | ((highPtCount & 0x3) << 2) | (lowPtCount & 0x3);
154}
155
156
157void AliHLTMUONUtils::UnpackPairDecisionBits(
158 AliHLTUInt32_t bits, bool& highMass, bool& lowMass, bool& unlike,
159 AliHLTUInt8_t& highPtCount, AliHLTUInt8_t& lowPtCount
160 )
161{
6253e09b 162 ///
163 /// This unpacks the AliHLTMUONPairDecisionStruct::fTriggerBits bits into
164 /// its component fields.
165 /// @param bits The trigger bits from an AliHLTMUONPairDecisionStruct
166 /// structure.
167 /// @param highMass Sets this to the value of the high invariant mass cut bit.
168 /// @param lowMass Sets this to the value of the low invariant mass cut bit.
169 /// @param unlike Sets this if the pair is unlike sign.
170 /// @param highPtCount Sets this to the high pt count bits.
171 /// @param lowPtCount Sets this to the low pt count bits.
172 ///
173
fc310e19 174 highMass = (bits & 0x40) == 0x40;
175 lowMass = (bits & 0x20) == 0x20;
176 unlike = (bits & 0x10) == 0x10;
90a74d7a 177 highPtCount = (bits & 0xC) >> 2;
178 lowPtCount = bits & 0x3;
179}
180
181
e6357f88 182AliHLTUInt32_t AliHLTMUONUtils::PackSpecBits(
183 const bool ddl[22]
184 )
185{
6253e09b 186 ///
187 /// This packs the given parameters into the 32bit Pub/Sub specification
188 /// word in the data block descriptor.
189 ///
190 /// @param ddl The list of DDLs forming part of the readout. ddl[0]
191 /// indicates DDL number 2560, ddl[1] is for DDL 2561 and so
192 /// on up to ddl[19]. ddl[20] and ddl[21] will be for the
193 /// trigger DDLs 2816 and 2817 respectively.
194 /// @return Returns the 32 bit packed specification word.
195 ///
196
e6357f88 197 // Pack the bits into the following format:
198 // bit: [ 31 - 22 ][ 21 ][ 20 ][ 19 - 0 ]
80606a9f 199 // field: [ reserved, set to zero ][ TRGDDL2817 ][ TRGDDL2816 ][ TRKDDLS ]
e6357f88 200 // Meaning of field acronyms:
201 // TRGDDL2816 - Trigger DDL number 2816.
202 // TRGDDL2817 - Trigger DDL number 2817.
203 // TRKDDLS - Tracking DDL flags where bit 0 will be for DDL number 2560,
204 // bit 1 for DDL no. 2561 etc. up to bit 19 which is for DDL 2579.
205 AliHLTUInt32_t bits = 0;
206 for (int i = 0; i < 22; i++)
207 bits |= (ddl[i] ? 0x1 : 0x0) << i;
208 return bits;
209}
210
211
212void AliHLTMUONUtils::UnpackSpecBits(
213 AliHLTUInt32_t bits, bool ddl[22]
214 )
215{
6253e09b 216 ///
217 /// This unpacks the AliHLTMUONPairDecisionStruct::fTriggerBits bits into
218 /// its component fields.
219 /// @param bits The Pub/Sub specification word from a data block descriptor.
220 /// @param ddl The output list of DDLs forming part of the readout. ddl[0]
221 /// indicates DDL number 2560, ddl[1] is for DDL 2561 and so
222 /// on up to ddl[19]. ddl[20] and ddl[21] will be for the
223 /// trigger DDLs 2816 and 2817 respectively.
224 ///
225
e6357f88 226 // Perform the inverse operation of PackSpecBits.
227 for (int i = 0; i < 22; i++)
228 ddl[i] = ((bits >> i) & 0x1) == 1;
229}
230
231
86b774d9 232AliHLTInt32_t AliHLTMUONUtils::DDLNumberToEquipId(AliHLTInt32_t ddlNo)
233{
234 ///
235 /// This method converts the DDL number for the muon spectrometer in the
236 /// range [0..21] to the equipment ID number.
237 /// @param ddlNo The DDL number in the range [0..21].
238 /// @return Returns the equipment ID number or -1 if ddlNo was invalid.
239 ///
240
241 if (0 <= ddlNo and ddlNo <= 19)
242 {
243 return 2560 + ddlNo;
244 }
245 else if (20 <= ddlNo and ddlNo <= 21)
246 {
247 return 2816 + (ddlNo - 20);
248 }
249 else
250 {
251 return -1;
252 }
253}
254
255
256AliHLTInt32_t AliHLTMUONUtils::EquipIdToDDLNumber(AliHLTInt32_t id)
257{
258 ///
259 /// This method converts the equipment ID number for a muon spectrometer
260 /// DDL to the DDL number in the range [0..21].
261 /// @param id The equipment ID of the DDL.
262 /// @return Returns the DDL number in the range [0..21] or -1 if the
263 /// equipment ID was invalid.
264 ///
265
266 if (2560 <= id and id <= 2560+19)
267 {
268 return id - 2560;
269 }
270 else if (2816 <= id and id <= 2817)
271 {
272 return id - 2816 + 20;
273 }
274 else
275 {
276 return -1;
277 }
278}
279
280
281AliHLTInt32_t AliHLTMUONUtils::SpecToEquipId(AliHLTUInt32_t spec)
282{
283 ///
284 /// This method converts a 32 bit data block specification for a MUON-HLT
285 /// data block into its corresponding DDL equipment ID number.
286 /// It is assumed that the specification is for a data block comming from
287 /// a single DDL source. If more than one DDL contributed to the data block
288 /// then -1 is returned.
289 /// @param spec The 32 bit specification for a data block.
290 /// @return Returns the equipment ID corresponding to the specification
291 /// or -1 if the specification was invalid.
292 ///
293
294 for (AliHLTInt32_t ddlNo = 0; ddlNo < 20; ddlNo++)
295 {
296 if (spec == AliHLTUInt32_t(0x1 << ddlNo))
297 return ddlNo + 2560;
298 }
299 for (AliHLTInt32_t ddlNo = 20; ddlNo < 22; ddlNo++)
300 {
301 if (spec == AliHLTUInt32_t(0x1 << ddlNo))
302 return ddlNo - 20 + 2816;
303 }
304 return -1;
305}
306
307
308AliHLTUInt32_t AliHLTMUONUtils::EquipIdToSpec(AliHLTInt32_t id)
309{
310 ///
311 /// This method converts a equipment ID number for a DDL into its corresponding
312 /// 32 bit data block specification for the MUON-HLT.
313 /// @param id The equipment ID number of the DDL.
314 /// @return Returns the 32 bit data block specification or 0x0 if the
315 /// equipment ID was invalid.
316 ///
317
318 if (2560 <= id and id <= 2560+19)
319 {
320 return 0x1 << (id - 2560);
321 }
322 else if (2816 <= id and id <= 2817)
323 {
324 return 0x1 << (id - 2816 + 20);
325 }
326 else
327 {
328 return 0x0;
329 }
330}
331
332
333AliHLTInt32_t AliHLTMUONUtils::SpecToDDLNumber(AliHLTUInt32_t spec)
334{
335 ///
336 /// This method converts a 32 bit data block specification for a MUON-HLT
337 /// data block into its corresponding DDL number in the range [0..21].
338 /// It is assumed that the specification is for a data block comming from
339 /// a single DDL source. If more than one DDL contributed to the data block
340 /// then -1 is returned.
341 /// @param spec The 32 bit specification for a data block.
342 /// @return Returns the corresponding DDL number for the specification
343 /// or -1 if the specification was invalid.
344 ///
345
346 for (AliHLTInt32_t ddlNo = 0; ddlNo < 22; ddlNo++)
347 {
348 if (spec == AliHLTUInt32_t(0x1 << ddlNo))
349 return ddlNo;
350 }
351 return -1;
352}
353
354
355AliHLTUInt32_t AliHLTMUONUtils::DDLNumberToSpec(AliHLTInt32_t ddlNo)
356{
357 ///
358 /// This method converts a DDL number in the range [0..21] into its
359 /// corresponding 32 bit data block specification for the MUON-HLT.
360 /// @param ddlNo The equipment ID number of the DDL.
361 /// @return Returns the 32 bit data block specification or 0x0 if the
362 /// DDL number was invalid (out of range).
363 ///
364
365 if (0 <= ddlNo and ddlNo <= 21)
366 {
367 return 0x1 << ddlNo;
368 }
369 else
370 {
371 return 0x0;
372 }
373}
374
375
f68b4e0e 376AliHLTMUONDataBlockType AliHLTMUONUtils::ParseCommandLineTypeString(const char* type)
377{
378 /// Parses the string containing the type name of a dHLT data block and
379 /// returns the corresponding AliHLTMUONDataBlockType value.
380 /// \param type The string containing the type name.
381 /// \returns The data block type or kUnknownDataBlock if the type name
382 /// is invalid.
383
384 if (strcmp(type, "trigrecs") == 0)
385 {
386 return kTriggerRecordsDataBlock;
387 }
388 else if (strcmp(type, "trigrecsdebug") == 0)
389 {
390 return kTrigRecsDebugDataBlock;
391 }
392 else if (strcmp(type, "trigchannels") == 0)
393 {
394 return kTriggerChannelsDataBlock;
395 }
396 else if (strcmp(type, "rechits") == 0)
397 {
398 return kRecHitsDataBlock;
399 }
400 else if (strcmp(type,"channels") == 0)
401 {
402 return kChannelsDataBlock;
403 }
404 else if (strcmp(type,"clusters") == 0)
405 {
406 return kClustersDataBlock;
407 }
408 else if (strcmp(type, "mansotracks") == 0)
409 {
410 return kMansoTracksDataBlock;
411 }
412 else if (strcmp(type, "mansocandidates") == 0)
413 {
414 return kMansoCandidatesDataBlock;
415 }
416 else if (strcmp(type, "singlesdecision") == 0)
417 {
418 return kSinglesDecisionDataBlock;
419 }
420 else if (strcmp(type, "pairsdecision") == 0)
421 {
422 return kPairsDecisionDataBlock;
423 }
424
425 return kUnknownDataBlock;
426}
427
428
878cb83d 429const char* AliHLTMUONUtils::FailureReasonToString(WhyNotValid reason)
430{
431 /// This method converts the WhyNotValid enumeration to a string representation.
432
433 switch (reason)
434 {
435 case kNoReason: return "kNoReason";
436 case kHeaderContainsWrongType: return "kHeaderContainsWrongType";
437 case kHeaderContainsWrongRecordWidth: return "kHeaderContainsWrongRecordWidth";
438 case kReservedBitsNotZero: return "kReservedBitsNotZero";
439 case kParticleSignBitsNotValid: return "kParticleSignBitsNotValid";
440 case kHitNotMarkedAsNil: return "kHitNotMarkedAsNil";
441 case kFoundDuplicateIDs: return "kFoundDuplicateIDs";
442 case kPtValueNotValid: return "kPtValueNotValid";
443 case kFoundDuplicateTriggers: return "kFoundDuplicateTriggers";
444 case kPairTrackIdsAreIdentical: return "kPairTrackIdsAreIdentical";
445 case kMassValueNotValid: return "kMassValueNotValid";
446 case kLowPtCountInvalid: return "kLowPtCountInvalid";
447 case kHighPtCountInvalid: return "kHighPtCountInvalid";
448 default: return "INVALID";
449 }
450}
451
452
453const char* AliHLTMUONUtils::FailureReasonToMessage(WhyNotValid reason)
454{
455 /// This method returns a string containing a user readable message explaining
456 /// the reason for failure described by the WhyNotValid enumeration.
457
458 switch (reason)
459 {
460 case kNoReason:
461 return "There was no problem with the data block.";
462 case kHeaderContainsWrongType:
463 return "The common data header contains an incorrect type identifier.";
464 case kHeaderContainsWrongRecordWidth:
465 return "The common data header contains an incorrect data record width.";
466 case kReservedBitsNotZero:
467 return "Reserved bits have not been set to zero.";
468 case kParticleSignBitsNotValid:
469 return "The particle sign bits are not a valid value.";
470 case kHitNotMarkedAsNil:
471 return "A hit was marked as not found, but the corresponding hit"
472 " structure was not set to nil.";
473 case kFoundDuplicateIDs:
474 return "Found duplicate data record identifiers, but they should all be unique.";
475 case kPtValueNotValid:
476 return "The pT value is not positive, nor -1 indicating an invalid value.";
477 case kFoundDuplicateTriggers:
478 return "Found duplicate trigger decisions.";
479 case kPairTrackIdsAreIdentical:
480 return "The track identifiers of the track pair are identical.";
481 case kMassValueNotValid:
482 return "The invariant mass value is not positive, nor -1 indicating an invalid value.";
483 case kLowPtCountInvalid:
484 return "The low pT trigger count is greater than 2, which is invalid.";
485 case kHighPtCountInvalid:
486 return "The high pT trigger count is greater than 2, which is invalid.";
487 default:
488 return "UNKNOWN REASON CODE";
489 }
490}
491
492
698c9498 493bool AliHLTMUONUtils::HeaderOk(
494 const AliHLTMUONTriggerRecordsBlockStruct& block,
495 WhyNotValid* reason
496 )
b727f838 497{
878cb83d 498 /// Method used to check if the header information corresponds to the
499 /// supposed type of the raw dHLT data block.
500 /// [in] \param block The data block to check.
501 /// [out] \param reason If this is not NULL, then it will be filled with
502 /// the reason code describing why the header is not valid, if and
503 /// only if a problem is found with the data.
504 /// \returns true if there is no problem with the header and false otherwise.
6253e09b 505
b727f838 506 // The block must have the correct type.
698c9498 507 if (block.fHeader.fType != kTriggerRecordsDataBlock)
508 {
509 if (reason != NULL) *reason = kHeaderContainsWrongType;
510 return false;
511 }
512
90a74d7a 513 // The block's record width must be the correct size.
b727f838 514 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONTriggerRecordStruct))
698c9498 515 {
516 if (reason != NULL) *reason = kHeaderContainsWrongRecordWidth;
26a4668d 517 return false;
698c9498 518 }
519
b727f838 520 return true;
521}
26a4668d 522
90a74d7a 523
878cb83d 524bool AliHLTMUONUtils::HeaderOk(
525 const AliHLTMUONTrigRecsDebugBlockStruct& block,
526 WhyNotValid* reason
527 )
c8ec7c7e 528{
878cb83d 529 /// Method used to check if the header information corresponds to the
530 /// supposed type of the raw dHLT data block.
531 /// [in] \param block The data block to check.
532 /// [out] \param reason If this is not NULL, then it will be filled with
533 /// the reason code describing why the header is not valid, if and
534 /// only if a problem is found with the data.
535 /// \returns true if there is no problem with the header and false otherwise.
6253e09b 536
c8ec7c7e 537 // The block must have the correct type.
878cb83d 538 if (block.fHeader.fType != kTrigRecsDebugDataBlock)
539 {
540 if (reason != NULL) *reason = kHeaderContainsWrongType;
541 return false;
542 }
543
90a74d7a 544 // The block's record width must be the correct size.
c8ec7c7e 545 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONTrigRecInfoStruct))
878cb83d 546 {
547 if (reason != NULL) *reason = kHeaderContainsWrongRecordWidth;
c8ec7c7e 548 return false;
878cb83d 549 }
550
c8ec7c7e 551 return true;
552}
553
90a74d7a 554
878cb83d 555bool AliHLTMUONUtils::HeaderOk(
556 const AliHLTMUONTriggerChannelsBlockStruct& block,
557 WhyNotValid* reason
558 )
c8ec7c7e 559{
878cb83d 560 /// Method used to check if the header information corresponds to the
561 /// supposed type of the raw dHLT data block.
562 /// [in] \param block The data block to check.
563 /// [out] \param reason If this is not NULL, then it will be filled with
564 /// the reason code describing why the header is not valid, if and
565 /// only if a problem is found with the data.
566 /// \returns true if there is no problem with the header and false otherwise.
6253e09b 567
c8ec7c7e 568 // The block must have the correct type.
878cb83d 569 if (block.fHeader.fType != kTriggerChannelsDataBlock)
570 {
571 if (reason != NULL) *reason = kHeaderContainsWrongType;
572 return false;
573 }
574
90a74d7a 575 // The block's record width must be the correct size.
c8ec7c7e 576 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONTriggerChannelStruct))
878cb83d 577 {
578 if (reason != NULL) *reason = kHeaderContainsWrongRecordWidth;
c8ec7c7e 579 return false;
878cb83d 580 }
581
c8ec7c7e 582 return true;
583}
584
90a74d7a 585
878cb83d 586bool AliHLTMUONUtils::HeaderOk(
587 const AliHLTMUONRecHitsBlockStruct& block,
588 WhyNotValid* reason
589 )
b727f838 590{
878cb83d 591 /// Method used to check if the header information corresponds to the
592 /// supposed type of the raw dHLT data block.
593 /// [in] \param block The data block to check.
594 /// [out] \param reason If this is not NULL, then it will be filled with
595 /// the reason code describing why the header is not valid, if and
596 /// only if a problem is found with the data.
597 /// \returns true if there is no problem with the header and false otherwise.
6253e09b 598
b727f838 599 // The block must have the correct type.
878cb83d 600 if (block.fHeader.fType != kRecHitsDataBlock)
601 {
602 if (reason != NULL) *reason = kHeaderContainsWrongType;
603 return false;
604 }
605
90a74d7a 606 // The block's record width must be the correct size.
b727f838 607 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONRecHitStruct))
878cb83d 608 {
609 if (reason != NULL) *reason = kHeaderContainsWrongRecordWidth;
26a4668d 610 return false;
878cb83d 611 }
612
b727f838 613 return true;
614}
26a4668d 615
90a74d7a 616
878cb83d 617bool AliHLTMUONUtils::HeaderOk(
618 const AliHLTMUONClustersBlockStruct& block,
619 WhyNotValid* reason
620 )
b727f838 621{
878cb83d 622 /// Method used to check if the header information corresponds to the
623 /// supposed type of the raw dHLT data block.
624 /// [in] \param block The data block to check.
625 /// [out] \param reason If this is not NULL, then it will be filled with
626 /// the reason code describing why the header is not valid, if and
627 /// only if a problem is found with the data.
628 /// \returns true if there is no problem with the header and false otherwise.
6253e09b 629
b727f838 630 // The block must have the correct type.
878cb83d 631 if (block.fHeader.fType != kClustersDataBlock)
632 {
633 if (reason != NULL) *reason = kHeaderContainsWrongType;
634 return false;
635 }
636
90a74d7a 637 // The block's record width must be the correct size.
b727f838 638 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONClusterStruct))
878cb83d 639 {
640 if (reason != NULL) *reason = kHeaderContainsWrongRecordWidth;
b727f838 641 return false;
878cb83d 642 }
643
b727f838 644 return true;
645}
26a4668d 646
90a74d7a 647
878cb83d 648bool AliHLTMUONUtils::HeaderOk(
649 const AliHLTMUONChannelsBlockStruct& block,
650 WhyNotValid* reason
651 )
b727f838 652{
878cb83d 653 /// Method used to check if the header information corresponds to the
654 /// supposed type of the raw dHLT data block.
655 /// [in] \param block The data block to check.
656 /// [out] \param reason If this is not NULL, then it will be filled with
657 /// the reason code describing why the header is not valid, if and
658 /// only if a problem is found with the data.
659 /// \returns true if there is no problem with the header and false otherwise.
6253e09b 660
b727f838 661 // The block must have the correct type.
878cb83d 662 if (block.fHeader.fType != kChannelsDataBlock)
663 {
664 if (reason != NULL) *reason = kHeaderContainsWrongType;
665 return false;
666 }
667
90a74d7a 668 // The block's record width must be the correct size.
b727f838 669 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONChannelStruct))
878cb83d 670 {
671 if (reason != NULL) *reason = kHeaderContainsWrongRecordWidth;
26a4668d 672 return false;
878cb83d 673 }
674
b727f838 675 return true;
676}
677
678
878cb83d 679bool AliHLTMUONUtils::HeaderOk(
680 const AliHLTMUONMansoTracksBlockStruct& block,
681 WhyNotValid* reason
682 )
90a74d7a 683{
878cb83d 684 /// Method used to check if the header information corresponds to the
685 /// supposed type of the raw dHLT data block.
686 /// [in] \param block The data block to check.
687 /// [out] \param reason If this is not NULL, then it will be filled with
688 /// the reason code describing why the header is not valid, if and
689 /// only if a problem is found with the data.
690 /// \returns true if there is no problem with the header and false otherwise.
6253e09b 691
90a74d7a 692 // The block must have the correct type.
878cb83d 693 if (block.fHeader.fType != kMansoTracksDataBlock)
694 {
695 if (reason != NULL) *reason = kHeaderContainsWrongType;
696 return false;
697 }
698
90a74d7a 699 // The block's record width must be the correct size.
700 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONMansoTrackStruct))
878cb83d 701 {
702 if (reason != NULL) *reason = kHeaderContainsWrongRecordWidth;
90a74d7a 703 return false;
878cb83d 704 }
705
90a74d7a 706 return true;
707}
708
709
878cb83d 710bool AliHLTMUONUtils::HeaderOk(
711 const AliHLTMUONMansoCandidatesBlockStruct& block,
712 WhyNotValid* reason
713 )
90a74d7a 714{
878cb83d 715 /// Method used to check if the header information corresponds to the
716 /// supposed type of the raw dHLT data block.
717 /// [in] \param block The data block to check.
718 /// [out] \param reason If this is not NULL, then it will be filled with
719 /// the reason code describing why the header is not valid, if and
720 /// only if a problem is found with the data.
721 /// \returns true if there is no problem with the header and false otherwise.
6253e09b 722
90a74d7a 723 // The block must have the correct type.
878cb83d 724 if (block.fHeader.fType != kMansoCandidatesDataBlock)
725 {
726 if (reason != NULL) *reason = kHeaderContainsWrongType;
727 return false;
728 }
729
90a74d7a 730 // The block's record width must be the correct size.
731 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONMansoCandidateStruct))
878cb83d 732 {
733 if (reason != NULL) *reason = kHeaderContainsWrongRecordWidth;
90a74d7a 734 return false;
878cb83d 735 }
736
90a74d7a 737 return true;
738}
739
740
878cb83d 741bool AliHLTMUONUtils::HeaderOk(
742 const AliHLTMUONSinglesDecisionBlockStruct& block,
743 WhyNotValid* reason
744 )
90a74d7a 745{
878cb83d 746 /// Method used to check if the header information corresponds to the
747 /// supposed type of the raw dHLT data block.
748 /// [in] \param block The data block to check.
749 /// [out] \param reason If this is not NULL, then it will be filled with
750 /// the reason code describing why the header is not valid, if and
751 /// only if a problem is found with the data.
752 /// \returns true if there is no problem with the header and false otherwise.
6253e09b 753
90a74d7a 754 // The block must have the correct type.
878cb83d 755 if (block.fHeader.fType != kSinglesDecisionDataBlock)
756 {
757 if (reason != NULL) *reason = kHeaderContainsWrongType;
758 return false;
759 }
760
90a74d7a 761 // The block's record width must be the correct size.
762 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONTrackDecisionStruct))
878cb83d 763 {
764 if (reason != NULL) *reason = kHeaderContainsWrongRecordWidth;
90a74d7a 765 return false;
878cb83d 766 }
767
90a74d7a 768 return true;
769}
770
771
878cb83d 772bool AliHLTMUONUtils::HeaderOk(
773 const AliHLTMUONPairsDecisionBlockStruct& block,
774 WhyNotValid* reason
775 )
90a74d7a 776{
878cb83d 777 /// Method used to check if the header information corresponds to the
778 /// supposed type of the raw dHLT data block.
779 /// [in] \param block The data block to check.
780 /// [out] \param reason If this is not NULL, then it will be filled with
781 /// the reason code describing why the header is not valid, if and
782 /// only if a problem is found with the data.
783 /// \returns true if there is no problem with the header and false otherwise.
6253e09b 784
90a74d7a 785 // The block must have the correct type.
878cb83d 786 if (block.fHeader.fType != kPairsDecisionDataBlock)
787 {
788 if (reason != NULL) *reason = kHeaderContainsWrongType;
789 return false;
790 }
791
90a74d7a 792 // The block's record width must be the correct size.
793 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONPairDecisionStruct))
878cb83d 794 {
795 if (reason != NULL) *reason = kHeaderContainsWrongRecordWidth;
90a74d7a 796 return false;
878cb83d 797 }
798
90a74d7a 799 return true;
800}
801
802
878cb83d 803bool AliHLTMUONUtils::IntegrityOk(
804 const AliHLTMUONTriggerRecordStruct& tr,
805 WhyNotValid* reason
806 )
90a74d7a 807{
878cb83d 808 /// This method is used to check more extensively if the integrity of the
809 /// trigger record structure is OK and returns true in that case.
810 /// [in] \param tr The trigger record structure to check.
811 /// [out] \param reason If this is not NULL, then it will be filled with
812 /// the reason code describing why the structure is not valid, if and
813 /// only if a problem is found with the data.
814 /// \returns true if there is no problem with the structure and false otherwise.
6253e09b 815
90a74d7a 816 // Make sure that the reserved bits in the fFlags field are set
817 // to zero.
878cb83d 818 if ((tr.fFlags & 0x3FFFFFF0) != 0)
819 {
820 if (reason != NULL) *reason = kReservedBitsNotZero;
821 return false;
822 }
90a74d7a 823
824 // Make sure the sign is not invalid.
878cb83d 825 if ((tr.fFlags & 0xC0000000) == 0xC0000000)
826 {
827 if (reason != NULL) *reason = kParticleSignBitsNotValid;
828 return false;
829 }
90a74d7a 830
831 // Check that fHit[i] is nil if the corresponding bit in the
832 // flags word is zero.
833 const AliHLTMUONRecHitStruct& nilhit
834 = AliHLTMUONConstants::NilRecHitStruct();
878cb83d 835 if ( ((tr.fFlags & 0x1) == 0 and tr.fHit[0] != nilhit) or
836 ((tr.fFlags & 0x2) == 0 and tr.fHit[1] != nilhit) or
837 ((tr.fFlags & 0x4) == 0 and tr.fHit[2] != nilhit) or
838 ((tr.fFlags & 0x8) == 0 and tr.fHit[3] != nilhit)
839 )
840 {
841 if (reason != NULL) *reason = kHitNotMarkedAsNil;
842 return false;
843 }
90a74d7a 844
845 return true;
846}
847
848
878cb83d 849bool AliHLTMUONUtils::IntegrityOk(
850 const AliHLTMUONTriggerRecordsBlockStruct& block,
851 WhyNotValid* reason,
852 AliHLTUInt32_t* recordNum
853 )
b727f838 854{
878cb83d 855 /// This method is used to check more extensively if the integrity of the
856 /// dHLT raw internal data block is OK and returns true in that case.
857 /// [in] \param block The trigger record data block to check.
858 /// [out] \param reason If this is not NULL, then it will be filled with
859 /// the reason code describing why the data block is not valid, if and
860 /// only if a problem is found with the data.
861 /// [out] \param recordNum If this is not NULL, then it will be filled with
862 /// the number of the trigger record that had a problem. This value will
863 /// only contain a valid value if 'reason' contains one of:
864 /// - kReservedBitsNotZero
865 /// - kParticleSignBitsNotValid
866 /// - kHitNotMarkedAsNil
867 /// \returns true if there is no problem with the data and false otherwise.
6253e09b 868
878cb83d 869 if (not HeaderOk(block, reason)) return false;
23ad6161 870
871 const AliHLTMUONTriggerRecordStruct* triggerRecord =
872 reinterpret_cast<const AliHLTMUONTriggerRecordStruct*>(&block + 1);
26a4668d 873
b727f838 874 // Check if any ID is duplicated.
875 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
876 {
23ad6161 877 AliHLTInt32_t id = triggerRecord[i].fId;
b727f838 878 for (AliHLTUInt32_t j = i+1; i < block.fHeader.fNrecords; j++)
879 {
23ad6161 880 if (id == triggerRecord[j].fId)
878cb83d 881 {
882 if (reason != NULL) *reason = kFoundDuplicateIDs;
b727f838 883 return false;
878cb83d 884 }
b727f838 885 }
886 }
887
90a74d7a 888 // Check integrity of individual trigger records.
b727f838 889 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
890 {
878cb83d 891 if (not IntegrityOk(triggerRecord[i], reason))
892 {
893 if (recordNum != NULL) *recordNum = i;
894 return false;
895 }
b727f838 896 }
897
898 return true;
899}
900
90a74d7a 901
878cb83d 902bool AliHLTMUONUtils::IntegrityOk(
903 const AliHLTMUONTrigRecsDebugBlockStruct& block,
904 WhyNotValid* reason
905 )
c8ec7c7e 906{
878cb83d 907 /// This method is used to check more extensively if the integrity of the
908 /// dHLT raw internal data block is OK and returns true in that case.
909 /// [in] \param block The trigger record debugging information data block to check.
910 /// [out] \param reason If this is not NULL, then it will be filled with
911 /// the reason code describing why the data block is not valid, if and
912 /// only if a problem is found with the data.
913 /// \returns true if there is no problem with the data and false otherwise.
6253e09b 914
878cb83d 915 if (not HeaderOk(block, reason)) return false;
c8ec7c7e 916 return true;
917}
918
90a74d7a 919
878cb83d 920bool AliHLTMUONUtils::IntegrityOk(
921 const AliHLTMUONTriggerChannelsBlockStruct& block,
922 WhyNotValid* reason
923 )
c8ec7c7e 924{
878cb83d 925 /// This method is used to check more extensively if the integrity of the
926 /// dHLT raw internal data block is OK and returns true in that case.
927 /// [in] \param block The trigger channels data block to check.
928 /// [out] \param reason If this is not NULL, then it will be filled with
929 /// the reason code describing why the data block is not valid, if and
930 /// only if a problem is found with the data.
931 /// \returns true if there is no problem with the data and false otherwise.
6253e09b 932
878cb83d 933 if (not HeaderOk(block, reason)) return false;
c8ec7c7e 934 return true;
935}
b727f838 936
90a74d7a 937
878cb83d 938bool AliHLTMUONUtils::IntegrityOk(
939 const AliHLTMUONRecHitsBlockStruct& block,
940 WhyNotValid* reason
941 )
b727f838 942{
878cb83d 943 /// This method is used to check more extensively if the integrity of the
944 /// dHLT raw internal data block is OK and returns true in that case.
945 /// [in] \param block The reconstructed hits data block to check.
946 /// [out] \param reason If this is not NULL, then it will be filled with
947 /// the reason code describing why the data block is not valid, if and
948 /// only if a problem is found with the data.
949 /// \returns true if there is no problem with the data and false otherwise.
6253e09b 950
878cb83d 951 if (not HeaderOk(block, reason)) return false;
b727f838 952 return true;
953}
954
955
878cb83d 956bool AliHLTMUONUtils::IntegrityOk(
957 const AliHLTMUONClustersBlockStruct& block,
958 WhyNotValid* reason
959 )
b727f838 960{
878cb83d 961 /// This method is used to check more extensively if the integrity of the
962 /// dHLT raw internal data block is OK and returns true in that case.
963 /// [in] \param block The clusters data block to check.
964 /// [out] \param reason If this is not NULL, then it will be filled with
965 /// the reason code describing why the data block is not valid, if and
966 /// only if a problem is found with the data.
967 /// \returns true if there is no problem with the data and false otherwise.
6253e09b 968
878cb83d 969 if (not HeaderOk(block, reason)) return false;
b727f838 970
23ad6161 971 const AliHLTMUONClusterStruct* cluster =
972 reinterpret_cast<const AliHLTMUONClusterStruct*>(&block + 1);
973
c8ec7c7e 974 // Check if any ID is duplicated.
975 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
976 {
23ad6161 977 AliHLTInt32_t id = cluster[i].fId;
c8ec7c7e 978 for (AliHLTUInt32_t j = i+1; i < block.fHeader.fNrecords; j++)
979 {
23ad6161 980 if (id == cluster[j].fId)
878cb83d 981 {
982 if (reason != NULL) *reason = kFoundDuplicateIDs;
c8ec7c7e 983 return false;
878cb83d 984 }
c8ec7c7e 985 }
986 }
987
b727f838 988 return true;
989}
990
90a74d7a 991
878cb83d 992bool AliHLTMUONUtils::IntegrityOk(
993 const AliHLTMUONChannelsBlockStruct& block,
994 WhyNotValid* reason
995 )
b727f838 996{
878cb83d 997 /// This method is used to check more extensively if the integrity of the
998 /// dHLT raw internal data block is OK and returns true in that case.
999 /// [in] \param block The ADC channels data block to check.
1000 /// [out] \param reason If this is not NULL, then it will be filled with
1001 /// the reason code describing why the data block is not valid, if and
1002 /// only if a problem is found with the data.
1003 /// \returns true if there is no problem with the data and false otherwise.
6253e09b 1004
878cb83d 1005 if (not HeaderOk(block, reason)) return false;
26a4668d 1006 return true;
1007}
90a74d7a 1008
1009
878cb83d 1010bool AliHLTMUONUtils::IntegrityOk(
1011 const AliHLTMUONMansoTrackStruct& track,
1012 WhyNotValid* reason
1013 )
90a74d7a 1014{
878cb83d 1015 /// This method is used to check more extensively if the integrity of the
1016 /// Manso track structure is OK and returns true in that case.
1017 /// [in] \param track The track structure to check.
1018 /// [out] \param reason If this is not NULL, then it will be filled with
1019 /// the reason code describing why the structure is not valid, if and
1020 /// only if a problem is found with the data.
1021 /// \returns true if there is no problem with the structure and false otherwise.
6253e09b 1022
90a74d7a 1023 // Make sure that the reserved bits in the fFlags field are set
1024 // to zero.
878cb83d 1025 if ((track.fFlags & 0x3FFFFFF0) != 0)
1026 {
1027 if (reason != NULL) *reason = kReservedBitsNotZero;
1028 return false;
1029 }
90a74d7a 1030
1031 // Make sure the sign is not invalid.
878cb83d 1032 if ((track.fFlags & 0xC0000000) == 0xC0000000)
1033 {
1034 if (reason != NULL) *reason = kParticleSignBitsNotValid;
1035 return false;
1036 }
90a74d7a 1037
1038 // Check that fHit[i] is nil if the corresponding bit in the
1039 // flags word is zero.
1040 const AliHLTMUONRecHitStruct& nilhit
1041 = AliHLTMUONConstants::NilRecHitStruct();
878cb83d 1042 if ( ((track.fFlags & 0x1) == 0 and track.fHit[0] != nilhit) or
1043 ((track.fFlags & 0x2) == 0 and track.fHit[1] != nilhit) or
1044 ((track.fFlags & 0x4) == 0 and track.fHit[2] != nilhit) or
1045 ((track.fFlags & 0x8) == 0 and track.fHit[3] != nilhit)
1046 )
1047 {
1048 if (reason != NULL) *reason = kHitNotMarkedAsNil;
1049 return false;
1050 }
90a74d7a 1051
1052 return true;
1053}
1054
1055
878cb83d 1056bool AliHLTMUONUtils::IntegrityOk(
1057 const AliHLTMUONMansoTracksBlockStruct& block,
1058 WhyNotValid* reason,
1059 AliHLTUInt32_t* recordNum
1060 )
90a74d7a 1061{
878cb83d 1062 /// This method is used to check more extensively if the integrity of the
1063 /// dHLT raw internal data block is OK and returns true in that case.
1064 /// [in] \param block The Manso track data block to check.
1065 /// [out] \param reason If this is not NULL, then it will be filled with
1066 /// the reason code describing why the data block is not valid, if and
1067 /// only if a problem is found with the data.
1068 /// [out] \param recordNum If this is not NULL, then it will be filled with
1069 /// the number of the track that had a problem. This value will only
1070 /// contain a valid value if 'reason' contains one of:
1071 /// - kReservedBitsNotZero
1072 /// - kParticleSignBitsNotValid
1073 /// - kHitNotMarkedAsNil
1074 /// \returns true if there is no problem with the data and false otherwise.
6253e09b 1075
878cb83d 1076 if (not HeaderOk(block, reason)) return false;
90a74d7a 1077
23ad6161 1078 const AliHLTMUONMansoTrackStruct* track =
1079 reinterpret_cast<const AliHLTMUONMansoTrackStruct*>(&block + 1);
1080
878cb83d 1081 // Check if any track ID is duplicated.
90a74d7a 1082 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
1083 {
23ad6161 1084 AliHLTInt32_t id = track[i].fId;
90a74d7a 1085 for (AliHLTUInt32_t j = i+1; i < block.fHeader.fNrecords; j++)
1086 {
23ad6161 1087 if (id == track[j].fId)
878cb83d 1088 {
1089 if (reason != NULL) *reason = kFoundDuplicateIDs;
90a74d7a 1090 return false;
878cb83d 1091 }
90a74d7a 1092 }
1093 }
1094
1095 // Check that the tracks have integrity.
1096 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
1097 {
878cb83d 1098 if (not IntegrityOk(track[i], reason))
1099 {
1100 if (recordNum != NULL) *recordNum = i;
1101 return false;
1102 }
90a74d7a 1103 }
1104
1105 return true;
1106}
1107
1108
878cb83d 1109bool AliHLTMUONUtils::IntegrityOk(
1110 const AliHLTMUONMansoCandidatesBlockStruct& block,
1111 WhyNotValid* reason,
1112 AliHLTUInt32_t* recordNum
1113 )
90a74d7a 1114{
878cb83d 1115 /// This method is used to check more extensively if the integrity of the
1116 /// dHLT raw internal data block is OK and returns true in that case.
1117 /// [in] \param block The Manso track candidate data block to check.
1118 /// [out] \param reason If this is not NULL, then it will be filled with
1119 /// the reason code describing why the data block is not valid, if and
1120 /// only if a problem is found with the data.
1121 /// [out] \param recordNum If this is not NULL, then it will be filled with
1122 /// the number of the track candidate that had a problem. This value will
1123 /// only contain a valid value if 'reason' contains one of:
1124 /// - kReservedBitsNotZero
1125 /// - kParticleSignBitsNotValid
1126 /// - kHitNotMarkedAsNil
1127 /// \returns true if there is no problem with the data and false otherwise.
6253e09b 1128
878cb83d 1129 if (not HeaderOk(block, reason)) return false;
90a74d7a 1130
23ad6161 1131 const AliHLTMUONMansoCandidateStruct* candidate =
1132 reinterpret_cast<const AliHLTMUONMansoCandidateStruct*>(&block + 1);
1133
878cb83d 1134 // Check if any candidate track ID is duplicated.
1135 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
1136 {
1137 AliHLTInt32_t id = candidate[i].fTrack.fId;
1138 for (AliHLTUInt32_t j = i+1; i < block.fHeader.fNrecords; j++)
1139 {
1140 if (id == candidate[j].fTrack.fId)
1141 {
1142 if (reason != NULL) *reason = kFoundDuplicateIDs;
1143 return false;
1144 }
1145 }
1146 }
1147
90a74d7a 1148 // Check that the tracks have integrity.
1149 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
1150 {
878cb83d 1151 if (not IntegrityOk(candidate[i].fTrack, reason))
1152 {
1153 if (recordNum != NULL) *recordNum = i;
1154 return false;
1155 }
90a74d7a 1156 }
1157
1158 return true;
1159}
1160
1161
878cb83d 1162bool AliHLTMUONUtils::IntegrityOk(
1163 const AliHLTMUONTrackDecisionStruct& decision,
1164 WhyNotValid* reason
1165 )
90a74d7a 1166{
878cb83d 1167 /// This method is used to check more extensively if the integrity of the
1168 /// single track trigger decision structure is OK and returns true in that case.
1169 /// [in] \param decision The trigger decision structure to check.
1170 /// [out] \param reason If this is not NULL, then it will be filled with
1171 /// the reason code describing why the structure is not valid, if and
1172 /// only if a problem is found with the data.
1173 /// \returns true if there is no problem with the structure and false otherwise.
6253e09b 1174
90a74d7a 1175 // Make sure that the reserved bits in the fTriggerBits field are set
1176 // to zero.
878cb83d 1177 if ((decision.fTriggerBits & 0xFFFFFFFC) != 0)
1178 {
1179 if (reason != NULL) *reason = kReservedBitsNotZero;
1180 return false;
1181 }
1182
1183 // The pT should be -1 or a positive number.
1184 if (decision.fPt != -1. and decision.fPt < 0.)
1185 {
1186 if (reason != NULL) *reason = kPtValueNotValid;
1187 return false;
1188 }
1189
90a74d7a 1190 return true;
1191}
1192
1193
878cb83d 1194bool AliHLTMUONUtils::IntegrityOk(
1195 const AliHLTMUONSinglesDecisionBlockStruct& block,
1196 WhyNotValid* reason,
1197 AliHLTUInt32_t* recordNum
1198 )
90a74d7a 1199{
878cb83d 1200 /// This method is used to check more extensively if the integrity of the
1201 /// dHLT raw internal data block is OK and returns true in that case.
1202 /// [in] \param block The single track trigger decision data block to check.
1203 /// [out] \param reason If this is not NULL, then it will be filled with
1204 /// the reason code describing why the data block is not valid, if and
1205 /// only if a problem is found with the data.
1206 /// [out] \param recordNum If this is not NULL, then it will be filled with
1207 /// the number of the trigger decisions that had a problem. This value will
1208 /// only contain a valid value if 'reason' contains one of:
1209 /// - kReservedBitsNotZero
1210 /// - kPtValueNotValid
1211 /// \returns true if there is no problem with the data and false otherwise.
6253e09b 1212
878cb83d 1213 if (not HeaderOk(block, reason)) return false;
23ad6161 1214
1215 const AliHLTMUONTrackDecisionStruct* decision =
1216 reinterpret_cast<const AliHLTMUONTrackDecisionStruct*>(&block + 1);
90a74d7a 1217
878cb83d 1218 // Check that there are no duplicate trigger entries.
1219 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
1220 {
1221 AliHLTInt32_t id = decision[i].fTrackId;
1222 for (AliHLTUInt32_t j = i+1; i < block.fHeader.fNrecords; j++)
1223 {
1224 if (id == decision[j].fTrackId)
1225 {
1226 if (reason != NULL) *reason = kFoundDuplicateTriggers;
1227 return false;
1228 }
1229 }
1230 }
1231
90a74d7a 1232 // Check that the trigger bits for each track have integrity.
1233 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
1234 {
878cb83d 1235 if (not IntegrityOk(decision[i], reason))
1236 {
1237 if (recordNum != NULL) *recordNum = i;
1238 return false;
1239 }
90a74d7a 1240 }
1241
1242 return true;
1243}
1244
1245
878cb83d 1246bool AliHLTMUONUtils::IntegrityOk(
1247 const AliHLTMUONPairDecisionStruct& decision,
1248 WhyNotValid* reason
1249 )
90a74d7a 1250{
878cb83d 1251 /// This method is used to check more extensively if the integrity of the
1252 /// track pair trigger decision structure is OK and returns true in that case.
1253 /// [in] \param decision The trigger decision structure to check.
1254 /// [out] \param reason If this is not NULL, then it will be filled with
1255 /// the reason code describing why the structure is not valid, if and
1256 /// only if a problem is found with the data.
1257 /// \returns true if there is no problem with the structure and false otherwise.
6253e09b 1258
90a74d7a 1259 // Make sure that the reserved bits in the fTriggerBits field are set
1260 // to zero.
878cb83d 1261 if ((decision.fTriggerBits & 0xFFFFFF80) != 0)
1262 {
1263 if (reason != NULL) *reason = kReservedBitsNotZero;
1264 return false;
1265 }
90a74d7a 1266
878cb83d 1267 // Check that the track IDs are not the same.
1268 if (decision.fTrackAId == decision.fTrackBId)
1269 {
1270 if (reason != NULL) *reason = kPairTrackIdsAreIdentical;
1271 return false;
1272 }
1273
1274 // The invariant mass should be -1 or a positive number.
1275 if (decision.fInvMass != -1. and decision.fInvMass < 0.)
1276 {
1277 if (reason != NULL) *reason = kMassValueNotValid;
90a74d7a 1278 return false;
878cb83d 1279 }
90a74d7a 1280
1281 // Neither the high pt (hipt) or low pt (lopt) count bits can be > 2.
90a74d7a 1282 AliHLTUInt8_t lowPtCount = (decision.fTriggerBits & 0x00000003);
1283 AliHLTUInt8_t highPtCount = (decision.fTriggerBits & 0x0000000C) >> 2;
878cb83d 1284 if (lowPtCount > 2)
1285 {
1286 if (reason != NULL) *reason = kLowPtCountInvalid;
1287 return false;
1288 }
1289 if (highPtCount > 2)
1290 {
1291 if (reason != NULL) *reason = kHighPtCountInvalid;
1292 return false;
1293 }
90a74d7a 1294
1295 return true;
1296}
1297
1298
878cb83d 1299bool AliHLTMUONUtils::IntegrityOk(
1300 const AliHLTMUONPairsDecisionBlockStruct& block,
1301 WhyNotValid* reason,
1302 AliHLTUInt32_t* recordNum
1303 )
90a74d7a 1304{
878cb83d 1305 /// This method is used to check more extensively if the integrity of the
1306 /// dHLT raw internal data block is OK and returns true in that case.
1307 /// [in] \param block The track pair trigger decision data block to check.
1308 /// [out] \param reason If this is not NULL, then it will be filled with
1309 /// the reason code describing why the data block is not valid, if and
1310 /// only if a problem is found with the data.
1311 /// [out] \param recordNum If this is not NULL, then it will be filled with
1312 /// the number of the trigger decisions that had a problem. This value will
1313 /// only contain a valid value if 'reason' contains one of:
1314 /// - kReservedBitsNotZero
1315 /// - kPairTrackIdsAreIdentical
1316 /// - kMassValueNotValid
1317 /// - kLowPtCountInvalid
1318 /// - kHighPtCountInvalid
1319 /// \returns true if there is no problem with the data and false otherwise.
6253e09b 1320
878cb83d 1321 if (not HeaderOk(block, reason)) return false;
90a74d7a 1322
23ad6161 1323 const AliHLTMUONPairDecisionStruct* decision =
1324 reinterpret_cast<const AliHLTMUONPairDecisionStruct*>(&block + 1);
1325
878cb83d 1326 // Check that there are no duplicate trigger entries.
1327 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
1328 {
1329 AliHLTInt32_t ta = decision[i].fTrackAId;
1330 AliHLTInt32_t tb = decision[i].fTrackBId;
1331 for (AliHLTUInt32_t j = i+1; i < block.fHeader.fNrecords; j++)
1332 {
1333 if (ta == decision[j].fTrackAId and tb == decision[j].fTrackBId)
1334 {
1335 if (reason != NULL) *reason = kFoundDuplicateTriggers;
1336 return false;
1337 }
1338 }
1339 }
1340
90a74d7a 1341 // Check that the trigger bits for each track pair have integrity.
1342 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
1343 {
878cb83d 1344 if (not IntegrityOk(decision[i], reason))
1345 {
1346 if (recordNum != NULL) *recordNum = i;
1347 return false;
1348 }
90a74d7a 1349 }
1350
1351 return true;
1352}