60718aaaa6c9c03aed62f50fef1b502b0104cb6e
[u/mrichter/AliRoot.git] / HMPID / AliHMPIDRawStream.cxx
1 /**************************************************************************
2  * Copyright(c) 1998-1999, 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 ///////////////////////////////////////////////////////////////////////////////
17 ///
18 /// This is a class for reading the HMPID raw data
19 /// The format of the raw data corresponds to the one
20 /// which was documented by Paolo Martinengo.
21 ///
22 ///////////////////////////////////////////////////////////////////////////////
23
24 #include "AliHMPIDRawStream.h"
25 #include "AliRawReader.h"
26 #include "AliLog.h"
27 #include "AliDAQ.h"
28
29 ClassImp(AliHMPIDRawStream)
30
31 //_____________________________________________________________________________
32 AliHMPIDRawStream::AliHMPIDRawStream(AliRawReader* rawReader) :
33   fDDLNumber(-1),
34   fRawReader(rawReader),
35   fData(NULL),
36   fPosition(-1)
37 {
38   // Constructor
39   Init();
40
41   fRawReader->Reset();
42   fRawReader->Select("HMPID");
43 }
44
45 //_____________________________________________________________________________
46 AliHMPIDRawStream::~AliHMPIDRawStream()
47 {
48   // destructor
49 }
50
51 //_____________________________________________________________________________
52 void AliHMPIDRawStream::Init()
53 {
54   // Initalize the container
55   // with the pad charges
56   for(Int_t i = 0; i < kNRows; i++)
57     for(Int_t j = 0; j < kNDILOGICAdd; j++)
58       for(Int_t k = 0; k < kNPadAdd; k++)
59         fCharge[i][j][k] = -1;
60 }
61
62 //_____________________________________________________________________________
63 void AliHMPIDRawStream::Reset()
64 {
65   // reset raw stream params
66
67   // Reinitalize the containers
68   Init();
69
70   fDDLNumber = -1;
71   fPosition = -1;
72   fData = NULL;
73
74   if (fRawReader) fRawReader->Reset();
75 }
76
77 //_____________________________________________________________________________
78 Bool_t AliHMPIDRawStream::Next()
79 {
80   // read next DDL raw data from the VZERO raw data stream
81   // return kFALSE in case of error or no data left
82
83   do {
84     if (!fRawReader->ReadNextData(fData)) return kFALSE;
85   } while (fRawReader->GetDataSize() == 0);
86
87   if (fRawReader->GetDataSize() != 47148) {
88     fRawReader->AddFatalErrorLog(kRawDataSizeErr,Form("size %d != 47148",fRawReader->GetDataSize()));
89     AliWarning(Form("Wrong HMPID raw data size: %d, expected 47148 bytes!",fRawReader->GetDataSize()));
90     return kTRUE;
91   }
92   fDDLNumber = fRawReader->GetDDLID();
93   fPosition = 0;
94
95   Init();
96
97   // Look over rows
98   for(Int_t iRow = 1; iRow < kNRows; iRow++) {
99     // Read row marker
100     UInt_t rowMarker = GetNextWord() & 0x1ffffff;
101     if (rowMarker != 0x1ea32a8) {
102       fRawReader->AddMajorErrorLog(kRowMarkerErr);
103       AliWarning(Form("Wrong row marker %x for row %d, expected 0xx1ea32a8!",rowMarker,iRow));
104       return kTRUE;
105     }
106     UInt_t dilogic = 0, row = 0;
107     for(Int_t iDILOGIC = 1; iDILOGIC < kNDILOGICAdd; iDILOGIC++) {
108       // Read pad charges
109       for(Int_t iPad = 0; iPad < kNPadAdd; iPad++) {
110         UInt_t data = GetNextWord();
111         row = (data >> 22) & 0x1f;
112         if (row < 1 || row >= kNRows) {
113           fRawReader->AddMajorErrorLog(kWrongRowErr,Form("row %d",row));
114           AliWarning(Form("Wrong row index: %d, expected (1 -> %d)!",row,kNRows));
115           row = iRow;
116         }
117         dilogic = (data >> 18) & 0xf;
118         if (dilogic < 1 || dilogic >= kNDILOGICAdd) {
119           fRawReader->AddMajorErrorLog(kWrongDilogicErr,Form("dil %d",dilogic));
120           AliWarning(Form("Wrong DILOGIC index: %d, expected (1 -> %d)!",dilogic,kNDILOGICAdd));
121           dilogic = iDILOGIC;
122         }
123         UInt_t pad = (data >> 12) & 0x3f;
124         if (pad >= kNPadAdd) {
125           fRawReader->AddMajorErrorLog(kWrongPadErr,Form("pad %d",pad));
126           AliWarning(Form("Wrong pad index: %d, expected (0 -> %d)!",pad,kNPadAdd));
127           pad = iPad;
128         }
129         fCharge[row][dilogic][pad] = data & 0xfff;
130       }
131       // Now read the end-of-event word
132       UInt_t eOfEvent = GetNextWord() & 0xfffffff;
133       if (!((eOfEvent >> 27) & 0x1)) {
134         fRawReader->AddMajorErrorLog(kEoEFlagErr);
135         AliWarning(Form("Missing end-of-event flag! (%x)",eOfEvent));
136         return kTRUE;
137       }
138       UInt_t wc = eOfEvent & 0x7f;
139       if (wc != 48) {
140         fRawReader->AddMajorErrorLog(kEoESizeErr,Form("eoe size=%d",wc));
141         AliWarning(Form("Wrong end-of-event word-count:%d, expected 48!",wc));
142         return kTRUE;
143       }
144       UInt_t da = (eOfEvent >> 18) & 0xf;
145       if (da != dilogic) {
146         fRawReader->AddMajorErrorLog(kEoEDILOGICErr,Form("eoe dil %d != %d",da,dilogic));
147         AliWarning(Form("Wrong DILOGIC address found in end-of-event: %d, expected %d!",da,dilogic));
148         return kTRUE;
149       }
150       UInt_t ca = (eOfEvent >> 22) & 0x1f;
151       if (ca != row) {
152         fRawReader->AddMajorErrorLog(kEoERowErr,Form("eoe row %d != %d",ca,row));
153         AliWarning(Form("Wrong row index found in end-of-event: %d, expected %d!",ca,row));
154         return kTRUE;
155       }
156     }
157
158     // Read the segment marker
159     // One maker per 8 rows
160     if (iRow%8 == 0) {
161       UInt_t segWord = GetNextWord();
162       if ((segWord >> 8) != 0xab0f58) {
163         fRawReader->AddMajorErrorLog(kBadSegWordErr);
164         AliWarning(Form("Wrong segment word signature: %x, expected 0xab0f58!",(segWord >> 8)));
165         return kTRUE;
166       }
167       if ((segWord & 0xff) != (((UInt_t)iRow + 7) / 8)) {
168         fRawReader->AddMajorErrorLog(kWrongSegErr,Form("seg %d != %d",segWord & 0xff,(iRow + 7) / 8));
169         AliWarning(Form("Segment index (%d) does not correspond to the one expected from row index (%d)!",segWord & 0xff,(iRow + 7) / 8));
170         return kTRUE;
171       }
172     }
173   }    
174   return kTRUE;
175 }
176
177 //_____________________________________________________________________________
178 UInt_t AliHMPIDRawStream::GetNextWord()
179 {
180   // This method returns the next 32 bit word
181   // inside the raw data payload.
182   // The method is supposed to be endian (platform)
183   // independent.
184   if (!fData || fPosition < 0) AliFatal("Raw data payload buffer is not yet initialized !");
185
186   UInt_t word = 0;
187   word |= fData[fPosition++];
188   word |= fData[fPosition++] << 8;
189   word |= fData[fPosition++] << 16;
190   word |= fData[fPosition++] << 24;
191
192   return word;
193 }
194
195 //_____________________________________________________________________________
196 Short_t AliHMPIDRawStream::GetCharge(Int_t row, Int_t dilogic, Int_t pad) const
197 {
198   // The method returns the charge collected
199   // in a particular channel
200   // Return -1 in case the charge from the channels
201   // has not been read or invalid arguments
202
203   if (row < 1 || row >= kNRows) {
204     AliError(Form("Wrong row index %d!",row));
205     return 0;
206   }
207
208   if (dilogic < 1 || dilogic >= kNDILOGICAdd) {
209     AliError(Form("Wrong DILOGIC address %d!",dilogic));
210     return 0;
211   }
212   
213   if (pad >= kNPadAdd) {
214     AliError(Form("Wrong pad index %d!",pad));
215     return 0;
216   }
217
218   return fCharge[row][dilogic][pad];
219 }