1 /**************************************************************************
2 * Copyright(c) 1998-2007, ALICE Experiment at CERN, All rights reserved. *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
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 **************************************************************************/
19 * @file AliHLTMUONUtils.cxx
20 * @author Artur Szostak <artursz@iafrica.com>
22 * @brief Implementation of AliHLTMUONUtils utility routines.
25 #include "AliHLTMUONUtils.h"
26 #include "AliHLTMUONConstants.h"
27 #include "AliHLTMUONTriggerRecordsBlockStruct.h"
28 #include "AliHLTMUONTrigRecsDebugBlockStruct.h"
29 #include "AliHLTMUONTriggerChannelsBlockStruct.h"
30 #include "AliHLTMUONRecHitsBlockStruct.h"
31 #include "AliHLTMUONClustersBlockStruct.h"
32 #include "AliHLTMUONChannelsBlockStruct.h"
33 #include "AliHLTMUONMansoTracksBlockStruct.h"
34 #include "AliHLTMUONMansoCandidatesBlockStruct.h"
35 #include "AliHLTMUONSinglesDecisionBlockStruct.h"
36 #include "AliHLTMUONPairsDecisionBlockStruct.h"
40 AliHLTUInt32_t AliHLTMUONUtils::PackTriggerRecordFlags(
41 AliHLTMUONParticleSign sign, const bool hitset[4]
47 case kSignMinus: flags = 0x80000000; break;
48 case kSignPlus: flags = 0x40000000; break;
49 default: flags = 0x00000000; break;
52 return flags | (hitset[0] ? 0x1 : 0) | (hitset[1] ? 0x2 : 0)
53 | (hitset[2] ? 0x4 : 0) | (hitset[3] ? 0x8 : 0);
57 void AliHLTMUONUtils::UnpackTriggerRecordFlags(
58 AliHLTUInt32_t flags, AliHLTMUONParticleSign& sign, bool hitset[4]
61 AliHLTUInt32_t signbits = flags & 0xC0000000;
64 case 0x80000000: sign = kSignMinus; break;
65 case 0x40000000: sign = kSignPlus; break;
66 default: sign = kSignUnknown; break;
68 hitset[0] = (flags & 0x1) == 0x1;
69 hitset[1] = (flags & 0x2) == 0x2;
70 hitset[2] = (flags & 0x4) == 0x4;
71 hitset[3] = (flags & 0x8) == 0x8;
75 AliHLTUInt32_t AliHLTMUONUtils::PackTrackDecisionBits(bool highPt, bool lowPt)
77 return (highPt ? 0x2 : 0) | (lowPt ? 0x1 : 0);
81 void AliHLTMUONUtils::UnpackTrackDecisionBits(
82 AliHLTUInt32_t bits, bool& highPt, bool& lowPt
85 lowPt = (bits & 0x1) == 1;
86 highPt = (bits & 0x2) == 1;
90 AliHLTUInt32_t AliHLTMUONUtils::PackPairDecisionBits(
91 bool highMass, bool lowMass, bool unlike,
92 AliHLTUInt8_t highPtCount, AliHLTUInt8_t lowPtCount
95 assert( highPtCount + lowPtCount <= 2 );
96 // highMass and lowMass must be false if unlike is false:
97 assert( not unlike ? (highMass == false and lowMass == false) : true );
99 return (highMass ? 0x40 : 0) | (lowMass ? 0x20 : 0) | (unlike ? 0x10 : 0)
100 | ((highPtCount & 0x3) << 2) | (lowPtCount & 0x3);
104 void AliHLTMUONUtils::UnpackPairDecisionBits(
105 AliHLTUInt32_t bits, bool& highMass, bool& lowMass, bool& unlike,
106 AliHLTUInt8_t& highPtCount, AliHLTUInt8_t& lowPtCount
109 highMass = (bits & 0x40) == 1;
110 lowMass = (bits & 0x20) == 1;
111 unlike = (bits & 0x10) == 1;
112 highPtCount = (bits & 0xC) >> 2;
113 lowPtCount = bits & 0x3;
117 AliHLTUInt32_t AliHLTMUONUtils::PackSpecBits(
121 // Pack the bits into the following format:
122 // bit: [ 31 - 22 ][ 21 ][ 20 ][ 19 - 0 ]
123 // field: [ reserved, set to zero ][ TRGDDL2816 ][ TRGDDL2817 ][ TRKDDLS ]
124 // Meaning of field acronyms:
125 // TRGDDL2816 - Trigger DDL number 2816.
126 // TRGDDL2817 - Trigger DDL number 2817.
127 // TRKDDLS - Tracking DDL flags where bit 0 will be for DDL number 2560,
128 // bit 1 for DDL no. 2561 etc. up to bit 19 which is for DDL 2579.
129 AliHLTUInt32_t bits = 0;
130 for (int i = 0; i < 22; i++)
131 bits |= (ddl[i] ? 0x1 : 0x0) << i;
136 void AliHLTMUONUtils::UnpackSpecBits(
137 AliHLTUInt32_t bits, bool ddl[22]
140 // Perform the inverse operation of PackSpecBits.
141 for (int i = 0; i < 22; i++)
142 ddl[i] = ((bits >> i) & 0x1) == 1;
146 bool AliHLTMUONUtils::HeaderOk(
147 const AliHLTMUONTriggerRecordsBlockStruct& block,
151 // The block must have the correct type.
152 if (block.fHeader.fType != kTriggerRecordsDataBlock)
154 if (reason != NULL) *reason = kHeaderContainsWrongType;
158 // The block's record width must be the correct size.
159 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONTriggerRecordStruct))
161 if (reason != NULL) *reason = kHeaderContainsWrongRecordWidth;
169 bool AliHLTMUONUtils::HeaderOk(const AliHLTMUONTrigRecsDebugBlockStruct& block)
171 // The block must have the correct type.
172 if (block.fHeader.fType != kTrigRecsDebugDataBlock) return false;
173 // The block's record width must be the correct size.
174 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONTrigRecInfoStruct))
180 bool AliHLTMUONUtils::HeaderOk(const AliHLTMUONTriggerChannelsBlockStruct& block)
182 // The block must have the correct type.
183 if (block.fHeader.fType != kTriggerChannelsDataBlock) return false;
184 // The block's record width must be the correct size.
185 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONTriggerChannelStruct))
191 bool AliHLTMUONUtils::HeaderOk(const AliHLTMUONRecHitsBlockStruct& block)
193 // The block must have the correct type.
194 if (block.fHeader.fType != kRecHitsDataBlock) return false;
195 // The block's record width must be the correct size.
196 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONRecHitStruct))
202 bool AliHLTMUONUtils::HeaderOk(const AliHLTMUONClustersBlockStruct& block)
204 // The block must have the correct type.
205 if (block.fHeader.fType != kClustersDataBlock) return false;
206 // The block's record width must be the correct size.
207 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONClusterStruct))
213 bool AliHLTMUONUtils::HeaderOk(const AliHLTMUONChannelsBlockStruct& block)
215 // The block must have the correct type.
216 if (block.fHeader.fType != kChannelsDataBlock) return false;
217 // The block's record width must be the correct size.
218 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONChannelStruct))
224 bool AliHLTMUONUtils::HeaderOk(const AliHLTMUONMansoTracksBlockStruct& block)
226 // The block must have the correct type.
227 if (block.fHeader.fType != kMansoTracksDataBlock) return false;
228 // The block's record width must be the correct size.
229 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONMansoTrackStruct))
235 bool AliHLTMUONUtils::HeaderOk(const AliHLTMUONMansoCandidatesBlockStruct& block)
237 // The block must have the correct type.
238 if (block.fHeader.fType != kMansoCandidatesDataBlock) return false;
239 // The block's record width must be the correct size.
240 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONMansoCandidateStruct))
246 bool AliHLTMUONUtils::HeaderOk(const AliHLTMUONSinglesDecisionBlockStruct& block)
248 // The block must have the correct type.
249 if (block.fHeader.fType != kSinglesDecisionDataBlock) return false;
250 // The block's record width must be the correct size.
251 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONTrackDecisionStruct))
257 bool AliHLTMUONUtils::HeaderOk(const AliHLTMUONPairsDecisionBlockStruct& block)
259 // The block must have the correct type.
260 if (block.fHeader.fType != kPairsDecisionDataBlock) return false;
261 // The block's record width must be the correct size.
262 if (block.fHeader.fRecordWidth != sizeof(AliHLTMUONPairDecisionStruct))
268 bool AliHLTMUONUtils::IntegrityOk(const AliHLTMUONTriggerRecordStruct& tr)
270 // Make sure that the reserved bits in the fFlags field are set
272 if ((tr.fFlags & 0x3FFFFFF0) != 0) return false;
274 // Make sure the sign is not invalid.
275 if ((tr.fFlags & 0xC0000000) == 3) return false;
277 // Check that fHit[i] is nil if the corresponding bit in the
278 // flags word is zero.
279 const AliHLTMUONRecHitStruct& nilhit
280 = AliHLTMUONConstants::NilRecHitStruct();
281 if ((tr.fFlags & 0x1) == 0 and tr.fHit[0] != nilhit) return false;
282 if ((tr.fFlags & 0x2) == 0 and tr.fHit[1] != nilhit) return false;
283 if ((tr.fFlags & 0x4) == 0 and tr.fHit[2] != nilhit) return false;
284 if ((tr.fFlags & 0x8) == 0 and tr.fHit[3] != nilhit) return false;
290 bool AliHLTMUONUtils::IntegrityOk(const AliHLTMUONTriggerRecordsBlockStruct& block)
292 if (not HeaderOk(block)) return false;
294 // Check if any ID is duplicated.
295 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
297 AliHLTInt32_t id = block.fTriggerRecord[i].fId;
298 for (AliHLTUInt32_t j = i+1; i < block.fHeader.fNrecords; j++)
300 if (id == block.fTriggerRecord[j].fId)
305 // Check integrity of individual trigger records.
306 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
308 if (not IntegrityOk(block.fTriggerRecord[i])) return false;
315 bool AliHLTMUONUtils::IntegrityOk(const AliHLTMUONTrigRecsDebugBlockStruct& block)
317 if (not HeaderOk(block)) return false;
322 bool AliHLTMUONUtils::IntegrityOk(const AliHLTMUONTriggerChannelsBlockStruct& block)
324 if (not HeaderOk(block)) return false;
329 bool AliHLTMUONUtils::IntegrityOk(const AliHLTMUONRecHitsBlockStruct& block)
331 if (not HeaderOk(block)) return false;
336 bool AliHLTMUONUtils::IntegrityOk(const AliHLTMUONClustersBlockStruct& block)
338 if (not HeaderOk(block)) return false;
340 // Check if any ID is duplicated.
341 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
343 AliHLTInt32_t id = block.fCluster[i].fId;
344 for (AliHLTUInt32_t j = i+1; i < block.fHeader.fNrecords; j++)
346 if (id == block.fCluster[j].fId)
355 bool AliHLTMUONUtils::IntegrityOk(const AliHLTMUONChannelsBlockStruct& block)
357 if (not HeaderOk(block)) return false;
362 bool AliHLTMUONUtils::IntegrityOk(const AliHLTMUONMansoTrackStruct& track)
364 // Make sure that the reserved bits in the fFlags field are set
366 if ((track.fFlags & 0x3FFFFFF0) != 0) return false;
368 // Make sure the sign is not invalid.
369 if ((track.fFlags & 0xC0000000) == 0xC0000000) return false;
371 // Check that fHit[i] is nil if the corresponding bit in the
372 // flags word is zero.
373 const AliHLTMUONRecHitStruct& nilhit
374 = AliHLTMUONConstants::NilRecHitStruct();
375 if ((track.fFlags & 0x1) == 0 and track.fHit[0] != nilhit) return false;
376 if ((track.fFlags & 0x2) == 0 and track.fHit[1] != nilhit) return false;
377 if ((track.fFlags & 0x4) == 0 and track.fHit[2] != nilhit) return false;
378 if ((track.fFlags & 0x8) == 0 and track.fHit[3] != nilhit) return false;
384 bool AliHLTMUONUtils::IntegrityOk(const AliHLTMUONMansoTracksBlockStruct& block)
386 if (not HeaderOk(block)) return false;
388 // Check if any ID is duplicated.
389 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
391 AliHLTInt32_t id = block.fTrack[i].fId;
392 for (AliHLTUInt32_t j = i+1; i < block.fHeader.fNrecords; j++)
394 if (id == block.fTrack[j].fId)
399 // Check that the tracks have integrity.
400 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
402 if (not IntegrityOk(block.fTrack[i])) return false;
409 bool AliHLTMUONUtils::IntegrityOk(const AliHLTMUONMansoCandidatesBlockStruct& block)
411 if (not HeaderOk(block)) return false;
413 // Check that the tracks have integrity.
414 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
416 if (not IntegrityOk(block.fCandidate[i].fTrack)) return false;
423 bool AliHLTMUONUtils::IntegrityOk(const AliHLTMUONTrackDecisionStruct& decision)
425 // Make sure that the reserved bits in the fTriggerBits field are set
427 if ((decision.fTriggerBits & 0xFFFFFFFC) != 0) return false;
432 bool AliHLTMUONUtils::IntegrityOk(const AliHLTMUONSinglesDecisionBlockStruct& block)
434 if (not HeaderOk(block)) return false;
436 // Check that the trigger bits for each track have integrity.
437 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
439 if (not IntegrityOk(block.fDecision[i])) return false;
446 bool AliHLTMUONUtils::IntegrityOk(const AliHLTMUONPairDecisionStruct& decision)
448 // Make sure that the reserved bits in the fTriggerBits field are set
450 if ((decision.fTriggerBits & 0xFFFFFF80) != 0) return false;
452 // The high mass or low mass bits can only be set if unlike bit is set.
453 if ((decision.fTriggerBits & 0x00000010) == 0
454 and (decision.fTriggerBits & 0x00000060) != 0
458 // Neither the high pt (hipt) or low pt (lopt) count bits can be > 2.
459 // And the sum must not be > 2.
460 AliHLTUInt8_t lowPtCount = (decision.fTriggerBits & 0x00000003);
461 AliHLTUInt8_t highPtCount = (decision.fTriggerBits & 0x0000000C) >> 2;
462 if (lowPtCount + highPtCount > 2) return false;
468 bool AliHLTMUONUtils::IntegrityOk(const AliHLTMUONPairsDecisionBlockStruct& block)
470 if (not HeaderOk(block)) return false;
472 // Check that the trigger bits for each track pair have integrity.
473 for (AliHLTUInt32_t i = 0; i < block.fHeader.fNrecords; i++)
475 if (not IntegrityOk(block.fDecision[i])) return false;