]> git.uio.no Git - u/mrichter/AliRoot.git/blob - MUON/AliMUONRawStreamTrackerHP.h
- AliMUONRawStreamTrackerHP can also return all header structures.
[u/mrichter/AliRoot.git] / MUON / AliMUONRawStreamTrackerHP.h
1 #ifndef ALIMUONRAWSTREAMTRACKERHP_H
2 #define ALIMUONRAWSTREAMTRACKERHP_H
3 /* This file is property of and copyright by the ALICE HLT Project        *
4  * ALICE Experiment at CERN, All rights reserved.                         *
5  * See cxx source for full Copyright notice                               */
6
7 /* $Id$*/
8
9 ///
10 /// \file   AliMUONRawStreamTrackerHP.h
11 /// \author Artur Szostak <artursz@iafrica.com>
12 /// \date   29-11-2007
13 /// \brief  Declaration of the high performance decoder for muon trigger chamber raw streams.
14 ///
15
16 #include "AliMUONVRawStreamTracker.h"
17 #include "AliMUONTrackerDDLDecoder.h"
18
19 class AliMUONRawStreamTrackerHP : public AliMUONVRawStreamTracker
20 {
21 public:
22         class AliDspHeader;
23         class AliBusPatch;
24
25         /// Default constructor.
26         AliMUONRawStreamTrackerHP();
27         
28         /// Constructor for setting the raw reader.
29         AliMUONRawStreamTrackerHP(AliRawReader* rawReader);
30         
31         /// Default destructor.
32         virtual ~AliMUONRawStreamTrackerHP();
33         
34         // The following public methods are all inherited from AliMUONVRawStreamTracker:
35         
36         /// Initialize iterator
37         virtual void First();
38         
39         /// DDL iterator 
40         virtual Bool_t NextDDL();
41         
42         /// Whether the iteration is finished or not
43         virtual Bool_t IsDone() const;
44         
45         /// Nothing is actually done in the AddErrorMessage method because we log
46         /// the error messages as we find them in AliDecoderEventHandler::OnError().
47         virtual void AddErrorMessage() { };
48         
49         /// Advance one step in the iteration. Returns false if finished.
50         virtual Bool_t Next(Int_t& busPatchId,
51                                 UShort_t& manuId, UChar_t& manuChannel,
52                                 UShort_t& adc);
53         
54         /// Returns the next batch of decoded channel data.
55         const AliBusPatch* Next()
56         {
57                 do {
58                         if (fCurrentBusPatch != fDecoder.GetHandler().EndOfBusPatch()) return fCurrentBusPatch++;
59                 } while (NextDDL());
60                 return NULL;
61         }
62         
63         /// Return maximum number of blocks per DDL allowed.
64         virtual Int_t GetMaxBlock() const { return (Int_t) fDecoder.MaxBlocks(); }
65         /// Return maximum number of Dsp per block allowed.
66         virtual Int_t GetMaxDsp() const { return (Int_t) fDecoder.MaxDSPs(); }
67         /// Return maximum number of Buspatch per Dsp allowed.
68         virtual Int_t GetMaxBus() const { return (Int_t) fDecoder.MaxBusPatches(); }
69         
70         /// Set maximum number of blocks per DDL allowed.
71         virtual void SetMaxBlock(Int_t blk);
72         /// Set maximum number of Dsp per block allowed.
73         virtual void SetMaxDsp(Int_t dsp);
74         /// Set maximum number of Buspatch per Dsp allowed.
75         virtual void SetMaxBus(Int_t bus);
76         
77         /// Return number of the current DDL.
78         virtual Int_t GetDDL() const { return fDDL - 1; }
79         
80         /// check error/Warning presence
81         virtual Bool_t IsErrorMessage() const { return fHadError; }
82         
83         /// Get number of parity errors
84         Int_t   GetParityErrors() const
85         {
86                 return (Int_t) fDecoder.GetHandler().ParityErrorCount();
87         }
88
89         /// Get number of glitch errors
90         Int_t   GetGlitchErrors() const
91         {
92                 return (Int_t) fDecoder.GetHandler().GlitchErrorCount();
93         }
94
95         /// Get number of padding word errors
96         Int_t   GetPaddingErrors() const
97         {
98                 return (Int_t) fDecoder.GetHandler().PaddingErrorCount();
99         }
100
101         /// Set warnings flag to disable warnings on data errors.
102         void DisableWarnings() { fDecoder.GetHandler().Warnings(kFALSE); }
103         /// Set warnings flag to enable warnings on data errors.
104         void EnableWarnings() { fDecoder.GetHandler().Warnings(kTRUE); }
105
106         /// Returns the "try to recover from errors" flag.
107         Bool_t TryRecover() const { return Bool_t(fDecoder.TryRecover()); }
108         
109         /// Sets the "try to recover from errors" flag.
110         /// i.e. should the decoder try to recover from errors found in the
111         /// payload headers.
112         void TryRecover(Bool_t value) { fDecoder.TryRecover(bool(value)); }
113         
114         /// Light weight interface class to the block header data.
115         class AliBlockHeader
116         {
117         public:
118                 /// Default constructor.
119                 AliBlockHeader(
120                                 AliDspHeader* dspArray = NULL,
121                                 const AliMUONBlockHeaderStruct* header = NULL
122                         )
123                         : fNext(NULL), fDspCount(0), fFirstDsp(dspArray), fHeader(header)
124                 {
125                 }
126                 
127                 /// Implement shallow copying in the copy constructor.
128                 AliBlockHeader(const AliBlockHeader& o) :
129                         fNext(o.fNext), fDspCount(o.fDspCount), fFirstDsp(o.fFirstDsp), fHeader(o.fHeader)
130                 {
131                 }
132                 
133                 /// Implement shallow copying in the assignment operator.
134                 AliBlockHeader& operator = (const AliBlockHeader& object)
135                 {
136                         memcpy(this, &object, sizeof(AliBlockHeader));
137                         return *this;
138                 }
139         
140                 /// Default destructor.
141                 ~AliBlockHeader() {};
142         
143                 /// Return data key word for CRT header
144                 Int_t   GetDataKey()        const {assert(fHeader != NULL); return fHeader->fDataKey;}
145                 /// Return total length of block structure (w/o padding word)
146                 Int_t   GetTotalLength()    const {assert(fHeader != NULL); return fHeader->fTotalLength;}
147                 /// Return length of raw data
148                 Int_t   GetLength()         const {assert(fHeader != NULL); return fHeader->fLength;}
149                 /// Return Dsp id
150                 Int_t   GetDspId()          const {assert(fHeader != NULL); return fHeader->fDSPId;}
151                 /// Return L0 trigger word
152                 Int_t   GetL0Trigger()      const {assert(fHeader != NULL); return fHeader->fL0Trigger;}
153                 /// Return Bunch Crossing for mini-event id (see TDR chapter 8)
154                 Int_t   GetMiniEventId()    const {assert(fHeader != NULL); return fHeader->fMiniEventId;}
155                 /// Return Event Id in bunch crossing
156                 Int_t   GetEventId1()       const {assert(fHeader != NULL); return fHeader->fEventId1;}
157                 /// Return Event Id in orbit number
158                 Int_t   GetEventId2()       const {assert(fHeader != NULL); return fHeader->fEventId2;}
159         
160                 /// Return the header's raw data.
161                 const AliMUONBlockHeaderStruct* GetHeader() {return fHeader;}
162                 
163                 /// Return the next block header.
164                 const AliBlockHeader* Next() const { return fNext; }
165                 
166                 /// Returns the first AliDspHeader class in this block.
167                 const AliDspHeader* GetFirstDspHeader() const { return fFirstDsp; }
168                 
169                 /// Returns the number of DSPs within this block.
170                 UInt_t GetDspCount() const { return fDspCount; }
171         
172                 /// Return the i'th DSP in this block.
173                 const AliDspHeader* GetDspHeader(UInt_t i) const
174                 {
175                         return i < fDspCount ? GetFirstDspHeader() + i : NULL;
176                 }
177                 
178                 /// Sets the next block header.
179                 void SetNext(const AliBlockHeader* next) { fNext = next; }
180
181                 /// Increments the DSP count.
182                 void IncDspCount() { fDspCount++; };
183                 
184                 /// Print the contents of the header to screen.
185                 void Print() const;
186         
187         private:
188         
189                 const AliBlockHeader* fNext;  ///< Pointer to next block.
190                 UInt_t fDspCount;    ///< The number of AliDspHeader objects found in the array pointed to by fFirstDsp.
191                 const AliDspHeader* fFirstDsp;  ///< The first DSP associated with this block.
192                 const AliMUONBlockHeaderStruct*  fHeader;  ///< Pointer to header in DDL payload.
193         };
194         
195         /// Light weight interface class to the DSP header data.
196         class AliDspHeader
197         {
198         public:
199                 /// Default constructor.
200                 AliDspHeader(
201                                 const AliBlockHeader* block = NULL,
202                                 const AliBusPatch* busPatchArray = NULL,
203                                 const AliMUONDSPHeaderStruct* header = NULL
204                         ) :
205                         fBlock(block), fNext(NULL), fBusPatchCount(0),
206                         fFirstBusPatch(busPatchArray), fHeader(header)
207                 {
208                 }
209                 
210                 /// Implement shallow copying in the copy constructor.
211                 AliDspHeader(const AliDspHeader& o) :
212                         fBlock(o.fBlock), fNext(o.fNext), fBusPatchCount(o.fBusPatchCount),
213                         fFirstBusPatch(o.fFirstBusPatch), fHeader(o.fHeader)
214                 {
215                 }
216                 
217                 /// Implement shallow copying in the assignment operator.
218                 AliDspHeader& operator = (const AliDspHeader& object)
219                 {
220                         memcpy(this, &object, sizeof(AliDspHeader));
221                         return *this;
222                 }
223         
224                 /// Default destructor.
225                 ~AliDspHeader() {};
226         
227                 /// Return Data key word for FRT header
228                 Int_t   GetDataKey()        const {assert(fHeader != NULL); return fHeader->fDataKey;}
229                 /// Return total length of block structure
230                 Int_t   GetTotalLength()    const {assert(fHeader != NULL); return fHeader->fTotalLength;}
231                 /// Return length of raw data
232                 Int_t   GetLength()         const {assert(fHeader != NULL); return fHeader->fLength;}
233                 /// Return Dsp id
234                 Int_t   GetDspId()          const {assert(fHeader != NULL); return fHeader->fDSPId;}
235                 /// Return L1 accept in Block Structure (CRT)
236                 Int_t   GetBlkL1ATrigger()  const {assert(fHeader != NULL); return fHeader->fBlkL1ATrigger;}
237                 /// Return Mini Event Id in bunch crossing
238                 Int_t   GetMiniEventId()    const {assert(fHeader != NULL); return fHeader->fMiniEventId;}
239                 /// Return Number of L1 accept in DSP Structure (FRT)
240                 Int_t   GetL1ATrigger()     const {assert(fHeader != NULL); return fHeader->fL1ATrigger;}
241                 /// Return Number of L1 reject in DSP Structure (FRT)
242                 Int_t   GetL1RTrigger()     const {assert(fHeader != NULL); return fHeader->fL1RTrigger;}
243                 /// Return padding dummy word for 64 bits transfer
244                 UInt_t  GetPaddingWord()    const {assert(fHeader != NULL); return fHeader->fPaddingWord;}
245                 /// Return Error word
246                 Int_t   GetErrorWord()      const {assert(fHeader != NULL); return fHeader->fErrorWord;}
247         
248                 /// Return raw data of header
249                 const AliMUONDSPHeaderStruct* GetHeader() {return fHeader;}
250                 
251                 /// Return the parent block header.
252                 const AliBlockHeader* GetBlockHeader() const { return fBlock; }
253                 
254                 /// Return the next DSP header.
255                 const AliDspHeader* Next() const { return fNext; }
256                 
257                 /// Returns the first AliBusPatch class in this DSP.
258                 const AliBusPatch* GetFirstBusPatch() const { return fFirstBusPatch; }
259                 
260                 /// Returns the number of bus patches within this DSP.
261                 UInt_t GetBusPatchCount() const { return fBusPatchCount; }
262         
263                 /// Return the i'th bus patch in this DSP.
264                 const AliBusPatch* GetBusPatch(UInt_t i) const
265                 {
266                         return i < fBusPatchCount ? GetFirstBusPatch() + i : NULL;
267                 }
268         
269                 /// Sets the next DSP header.
270                 void SetNext(const AliDspHeader* next) { fNext = next; }
271
272                 /// Increments the bus patch count.
273                 void IncBusPatchCount() { fBusPatchCount++; };
274                 
275                 /// Print the contents of the header to screen.
276                 void Print() const;
277         
278         private:
279         
280                 const AliBlockHeader* fBlock;  ///< Pointer to parent block structure.
281                 const AliDspHeader* fNext;  ///< Pointer to next DSP.
282                 UInt_t fBusPatchCount;    ///< The number of AliDspHeader objects found in the array pointed to by fFirstBusPatch
283                 const AliBusPatch* fFirstBusPatch;  ///< The first bus patch of this DSP.
284                 const AliMUONDSPHeaderStruct*  fHeader;  ///< Pointer to header in DDL payload.
285         };
286         
287         /// Light weight interface class to the bus patch data.
288         class AliBusPatch
289         {
290         public:
291                 /// Default constructor.
292                 AliBusPatch(
293                                 const AliDspHeader* dsp = NULL,
294                                 const AliMUONBusPatchHeaderStruct* header = NULL,
295                                 const UInt_t* data = NULL,
296                                 const Bool_t* parityOk = NULL
297                         ) :
298                         fDSP(dsp),
299                         fNext(NULL),
300                         fHeader(header),
301                         fData(data),
302                         fParityOk(parityOk)
303                 {
304                 }
305                 
306                 /// Implement shallow copying in the copy constructor.
307                 AliBusPatch(const AliBusPatch& o) :
308                         fDSP(o.fDSP),
309                         fNext(o.fNext),
310                         fHeader(o.fHeader),
311                         fData(o.fData),
312                         fParityOk(o.fParityOk)
313                 {
314                 }
315                 
316                 /// Implement shallow copying in the assignment operator.
317                 AliBusPatch& operator = (const AliBusPatch& object)
318                 {
319                         memcpy(this, &object, sizeof(AliBusPatch));
320                         return *this;
321                 }
322         
323                 /// Default destructor.
324                 ~AliBusPatch() {};
325                 
326                 /// Return Data key word for bus patch header.
327                 Int_t   GetDataKey()     const {assert(fHeader != NULL); return fHeader->fDataKey;}
328                 /// Return total length of buspatch structure
329                 Int_t   GetTotalLength() const {assert(fHeader != NULL); return fHeader->fTotalLength;}
330                 /// Return length of raw data
331                 Int_t   GetLength()      const {assert(fHeader != NULL); return fHeader->fLength;}
332                 /// Return bus patch id
333                 Int_t   GetBusPatchId()  const {assert(fHeader != NULL); return fHeader->fBusPatchId;}
334
335                 /// Return raw data of header
336                 const AliMUONBusPatchHeaderStruct* GetHeader() {return fHeader;}
337                 /// Return raw digit data
338                 const UInt_t* GetData()  const {return fData;}
339                 /// Returns the number of raw data words within this bus patch.
340                 UInt_t GetDataCount() const { return (UInt_t)GetLength(); }
341
342                 /// Returns the parity bit of the n'th raw data word.
343                 Char_t GetParity(UInt_t n) const
344                 {
345                         assert( fHeader != NULL and n < fHeader->fLength );
346                         return (Char_t)(fData[n] >> 31) &  0x1;
347                 }
348                 
349                 /// Returns the MANU ID of the n'th raw data word.
350                 UShort_t GetManuId(UInt_t n) const
351                 {
352                         assert( fHeader != NULL and n < fHeader->fLength );
353                         return (UShort_t)(fData[n] >> 18) &  0x7FF;
354                 }
355                 
356                 /// Returns the channel ID of the n'th raw data word.
357                 UChar_t GetChannelId(UInt_t n) const
358                 {
359                         assert( fHeader != NULL and n < fHeader->fLength );
360                         return (Char_t)(fData[n] >> 12) & 0x3F;
361                 }
362                 
363                 /// Returns the charge/signal of the n'th raw data word.
364                 UShort_t GetCharge(UInt_t n) const
365                 {
366                         assert( fHeader != NULL and n < fHeader->fLength );
367                         return (UShort_t)(fData[n] & 0xFFF);
368                 }
369                 
370                 /// Returns the n'th raw data word.
371                 UInt_t GetData(UInt_t n) const
372                 {
373                         assert( fHeader != NULL and n < fHeader->fLength );
374                         return fData[n];
375                 }
376                 
377                 /// Returns kTRUE if the parity of the n'th raw data word is OK
378                 /// and kFALSE otherwise.
379                 Bool_t IsParityOk(UInt_t n) const
380                 {
381                         assert( fHeader != NULL and n < fHeader->fLength );
382                         return fParityOk[n];
383                 }
384                 
385                 /// Unpacks and returns the fields of the n'th raw data word. kTRUE
386                 /// is returned if the data word's parity was OK and kFALSE otherwise.
387                 Bool_t GetData(UInt_t n, UShort_t& manuId, UChar_t& channelId, UShort_t& adc) const
388                 {
389                         assert( fHeader != NULL and n < fHeader->fLength );
390                         AliMUONTrackerDDLDecoderEventHandler::UnpackADC(fData[n], manuId, channelId, adc);
391                         return fParityOk[n];
392                 }
393                 
394                 /// Return the parent block header.
395                 const AliDspHeader* GetDspHeader() const { return fDSP; }
396                 
397                 /// Return the next bus patch header.
398                 const AliBusPatch* Next() const { return fNext; }
399                 
400                 /// Sets the next bus patch.
401                 void SetNext(const AliBusPatch* next) { fNext = next; }
402                 
403                 /// Print the contents of the bus patch to screen.
404                 void Print(const Option_t* opt = "") const;
405         
406         private:
407         
408                 const AliDspHeader* fDSP;   ///< The DSP this bus patch belongs to.
409                 const AliBusPatch* fNext;  ///< Next bus patch object in the DSP.
410                 const AliMUONBusPatchHeaderStruct*  fHeader;  ///< Pointer to bus patch in DDL payload.
411                 const UInt_t* fData;  ///< Pointer to the bus patch data.
412                 const Bool_t* fParityOk;  ///< Array of flags indicating if the parity of the given data word in fData is good or not.          
413         };
414         
415         /// Return the number of blocks in the DDL payload.
416         UInt_t GetBlockCount() const
417         {
418                 return fDecoder.GetHandler().BlockCount();
419         }
420         
421         /// Return the first block header.
422         const AliBlockHeader* GetFirstBlockHeader() const
423         {
424                 return fDecoder.GetHandler().BlockHeader(0);
425         }
426         
427         /// Return the i'th block header or NULL if not found.
428         const AliBlockHeader* GetBlockHeader(UInt_t i) const
429         {
430                 return fDecoder.GetHandler().BlockHeader(i);
431         }
432         
433         /// Returns the number of DSPs for the given block number.
434         UInt_t GetDspCount(UInt_t block) const
435         {
436                 const AliBlockHeader* b = GetBlockHeader(block);
437                 return b != NULL ? b->GetDspCount() : 0;
438         }
439         
440         /// Returns the i'th DSP header for the given block number or NULL if not found.
441         const AliDspHeader* GetDspHeader(UInt_t block, UInt_t i) const
442         {
443                 const AliBlockHeader* b = GetBlockHeader(block);
444                 return b != NULL ? b->GetDspHeader(i) : NULL;
445         }
446         
447         /// Returns the number of bus patches for the given block and dsp number.
448         UInt_t GetBusPatchCount(UInt_t block, UInt_t dsp) const
449         {
450                 const AliDspHeader* d = GetDspHeader(block, dsp);
451                 return d != NULL ? d->GetBusPatchCount() : 0;
452         }
453         
454         /// Returns the i'th bus patch for the given block and dsp.
455         const AliBusPatch* GetBusPatch(UInt_t block, UInt_t dsp, UInt_t i) const
456         {
457                 const AliDspHeader* d = GetDspHeader(block, dsp);
458                 return d != NULL ? d->GetBusPatch(i) : NULL;
459         }
460
461         /// Returns the current bus patch being decoded or NULL if none found.
462         const AliBusPatch* CurrentBusPatch() const
463         {
464                 return (fCurrentBusPatch != fDecoder.GetHandler().EndOfBusPatch()) ?
465                         fCurrentBusPatch : NULL;
466         }
467
468         /// Returns the current DSP being decoded or NULL if none found.
469         const AliDspHeader* CurrentDspHeader() const
470         {
471                 const AliBusPatch* busPatch = CurrentBusPatch();
472                 return (busPatch != NULL) ? busPatch->GetDspHeader() : NULL;
473         }
474
475         /// Returns the current block header being decoded or NULL if none found.
476         const AliBlockHeader* CurrentBlockHeader() const
477         {
478                 const AliDspHeader* dsp = CurrentDspHeader();
479                 return (dsp != NULL) ? dsp->GetBlockHeader() : NULL;
480         }
481
482 private:
483
484         // Do not allow copying of this class.
485         /// Not implemented
486         AliMUONRawStreamTrackerHP(const AliMUONRawStreamTrackerHP& stream);
487         /// Not implemented
488         AliMUONRawStreamTrackerHP& operator = (const AliMUONRawStreamTrackerHP& stream);
489         
490         /// This is the custom event handler (callback interface) class which
491         /// unpacks raw data words and fills an internal buffer with decoded digits
492         /// as they are decoded by the high performance decoder.
493         /// Any errors are logged to the parent AliMUONVRawStreamTracker, so one
494         /// must set this pointer appropriately before decoding and DDL payload.
495         class AliDecoderEventHandler : public AliMUONTrackerDDLDecoderEventHandler
496         {
497         public:
498         
499                 /// Default constructor.
500                 AliDecoderEventHandler();
501                 /// Default destructor.
502                 virtual ~AliDecoderEventHandler();
503                 
504                 /// Sets the internal arrays based on the maximum number of structures allowed.
505                 void SetMaxStructs(UInt_t maxBlocks, UInt_t maxDsps, UInt_t maxBusPatches);
506                 
507                 /// Sets the raw stream object which should be the parent of this class.
508                 void SetRawStream(AliMUONVRawStreamTracker* rawStream) { fRawStream = rawStream; }
509                 
510                 /// Return the number of blocks found in the payload.
511                 UInt_t BlockCount() const { return fBlockCount; };
512                 
513                 /// Return the i'th block structure.
514                 const AliBlockHeader* BlockHeader(UInt_t i) const
515                 {
516                         return i < fBlockCount ? &fBlocks[i] : NULL;
517                 }
518
519                 /// Return the first bus patch decoded.
520                 const AliBusPatch* FirstBusPatch() const { return fBusPatches; }
521
522                 /// Returns the marker to the end of bus patches. i.e. one position past the last bus patch.
523                 const AliBusPatch* EndOfBusPatch() const { return fEndOfBusPatches; }
524
525                 /// Returns the number of parity errors found in the DDL.
526                 UInt_t ParityErrorCount() const { return fParityErrors; }
527                 /// Returns the number of glitch errors found in the DDL.
528                 UInt_t GlitchErrorCount() const { return fGlitchErrors; }
529                 /// Returns the number of padding errors found in the DDL.
530                 UInt_t PaddingErrorCount() const { return fPaddingErrors; }
531
532                 /// Returns the warnings flag.
533                 Bool_t Warnings() const { return fWarnings; }
534                 /// Sets the warnings flag.
535                 void Warnings(Bool_t value) { fWarnings = value; }
536                 
537                 // The following methods are inherited from AliMUONTrackerDDLDecoderEventHandler:
538                 
539                 /// New buffer handler.
540                 void OnNewBuffer(const void* buffer, UInt_t bufferSize);
541
542                 /// End of buffer handler marks the end of bus patches.
543                 void OnEndOfBuffer(const void* /*buffer*/, UInt_t /*bufferSize*/)
544                 {
545                         fEndOfBusPatches = fCurrentBusPatch+1;
546                 }
547                 
548                 /// New block handler is called by the decoder whenever a new block
549                 /// structure is found. We just mark the new block and increment the
550                 /// internal counter.
551                 void OnNewBlock(const AliMUONBlockHeaderStruct* header, const void* /*data*/)
552                 {
553                         assert( fBlockCount < (UInt_t)fRawStream->GetMaxBlock() and header != NULL );
554                         if (fBlockCount > 0) fCurrentBlock->SetNext(fCurrentBlock+1);  // Link the block unless it is the first one.
555                         *(++fCurrentBlock) = AliBlockHeader(fCurrentDSP+1, header);
556                         fBlockCount++;
557                 }
558                 
559                 /// New DSP handler is called by the decoder whenever a new DSP
560                 /// structure is found. We just mark the DSP and increment the
561                 /// appropriate counters.
562                 void OnNewDSP(const AliMUONDSPHeaderStruct* header, const void* /*data*/)
563                 {
564                         assert( fCurrentBlock->GetDspCount() < (UInt_t)fRawStream->GetMaxDsp() and header != NULL );
565                         if (fCurrentBlock->GetDspCount() > 0) fCurrentDSP->SetNext(fCurrentDSP+1); // Link the DSP unless it is the first one.
566                         *(++fCurrentDSP) = AliDspHeader(fCurrentBlock, fCurrentBusPatch+1, header);
567                         fCurrentBlock->IncDspCount();
568                 }
569                 
570                 /// New bus patch handler.
571                 /// This is called by the high performance decoder when a new bus patch
572                 /// is found within the DDL payload.
573                 void OnNewBusPatch(const AliMUONBusPatchHeaderStruct* header, const void* data)
574                 {
575                         assert( fCurrentDSP->GetBusPatchCount() < (UInt_t)fRawStream->GetMaxBus() and header != NULL and data != NULL );
576                         if (fCurrentDSP->GetBusPatchCount() > 0) fCurrentBusPatch->SetNext(fCurrentBusPatch+1); // Link the bus patch unless it is the first one.
577                         *(++fCurrentBusPatch) = AliBusPatch(fCurrentDSP, header, reinterpret_cast<const UInt_t*>(data), fCurrentParityOkFlag+1);
578                         fCurrentDSP->IncBusPatchCount();
579                 }
580                 
581                 /// Raw data word handler.
582                 void OnData(UInt_t /*data*/, bool parityError)
583                 {
584                         assert( fCurrentParityOkFlag < fParityOk + fMaxChannels );
585                         *(++fCurrentParityOkFlag) = Bool_t(not parityError);
586                 }
587                 
588                 /// Error handler.
589                 void OnError(ErrorCode error, const void* location);
590         
591         private:
592         
593                 // Do not allow copying of this class.
594                 /// Not implemented
595                 AliDecoderEventHandler(const AliDecoderEventHandler& /*obj*/);
596                 /// Not implemented
597                 AliDecoderEventHandler& operator = (const AliDecoderEventHandler& /*obj*/);
598
599                 AliMUONVRawStreamTracker* fRawStream; //!< Pointer to the parent raw stream object.
600                 const void* fBufferStart;   //!< Pointer to the start of the current DDL payload buffer.
601                 UInt_t fBlockCount;  //!< Number of blocks filled in fBlocks.
602                 AliBlockHeader* fBlocks;  //!< Array of blocks. [0..fMaxBlocks-1]
603                 AliDspHeader* fDSPs;      //!< Array of DSPs. [0..fMaxDsps*fMaxBlocks-1]
604                 AliBusPatch* fBusPatches; //!< Array of bus patches. [0..fMaxBusPatches*fMaxDsps*fMaxBlocks-1]
605                 AliBusPatch* fEndOfBusPatches;  //!< Marks the last bus patch.
606                 UInt_t fMaxChannels;   //!< Maximum number of elements that can be stored in fParityOk.
607                 Bool_t* fParityOk;     //!< Array of flags for indicating if the parity is good for a raw data word.
608                 AliBlockHeader* fCurrentBlock;  //!< Current block in fBlocks.
609                 AliDspHeader* fCurrentDSP;      //!< Current DSP in fDSPs.
610                 AliBusPatch* fCurrentBusPatch;  //!< Current bus patch in fBusPatches.
611                 Bool_t* fCurrentParityOkFlag;  //!< Current parity flag to be set in fParityOk.
612                 UInt_t fParityErrors;   //!< Number of parity errors found in DDL.
613                 UInt_t fGlitchErrors;   //!< Number of glitch errors found in DDL.
614                 UInt_t fPaddingErrors;  //!< Number of padding errors found in DDL.
615                 Bool_t fWarnings;       //!< Flag indicating if we should generate a warning for errors.
616         };
617         
618         AliMUONTrackerDDLDecoder<AliDecoderEventHandler> fDecoder;  //!< The decoder for the DDL payload.
619         Int_t fDDL;         //!< The current DDL number being handled.
620         Int_t fBufferSize;  //!< This is the buffer size in bytes of fBuffer.
621         UChar_t* fBuffer;   //!< This is the buffer in which we store the DDL payload read from AliRawReader.
622         const AliBusPatch* fCurrentBusPatch;  //!< The current data word to return by Next().
623         const UInt_t* fCurrentData;  //!< The current data word to return by Next().
624         const UInt_t* fEndOfData;  //!< The last data word in the current bus patch.
625         Bool_t fHadError;   //!< Flag indicating if there was a decoding error or not.
626         Bool_t fDone;       //!< Flag indicating if the iteration is done or not.
627
628         ClassDef(AliMUONRawStreamTrackerHP, 0) // High performance decoder for reading MUON raw digits from tracking chamber DDL data.
629 };
630
631 #endif  // ALIMUONRAWSTREAMTRACKERHP_H
632