]> git.uio.no Git - u/mrichter/AliRoot.git/blob - PMD/AliPMDRawStream.cxx
AliTPCclustererKr.h -
[u/mrichter/AliRoot.git] / PMD / AliPMDRawStream.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 /* $Id$ */
17
18 ///////////////////////////////////////////////////////////////////////////////
19 ///
20 /// This class provides access to PMD digits in raw data.
21 ///
22 /// It loops over all PMD digits in the raw data given by the AliRawReader.
23 /// The Next method goes to the next digit. If there are no digits left
24 /// it returns kFALSE.
25 /// Several getters provide information about the current digit.
26 ///
27 ///////////////////////////////////////////////////////////////////////////////
28
29 #include <Riostream.h>
30 #include <TObjArray.h>
31 #include <TString.h>
32 #include <TSystem.h>
33
34 #include "AliLog.h"
35 #include "AliPMDBlockHeader.h"
36 #include "AliPMDDspHeader.h"
37 #include "AliPMDPatchBusHeader.h"
38 #include "AliPMDddldata.h"
39 #include "AliPMDRawStream.h"
40 #include "AliRawReader.h"
41
42 ClassImp(AliPMDRawStream)
43
44
45 //_____________________________________________________________________________
46 AliPMDRawStream::AliPMDRawStream(AliRawReader* rawReader) :
47   fRawReader(rawReader)
48 {
49 // create an object to read PMD raw digits
50
51   fRawReader->Select("PMD");
52 }
53
54 //_____________________________________________________________________________
55 AliPMDRawStream::AliPMDRawStream(const AliPMDRawStream& stream) :
56   TObject(stream),
57   fRawReader(NULL)
58 {
59 // copy constructor
60
61   AliFatal("Copy constructor not implemented");
62 }
63
64 //_____________________________________________________________________________
65 AliPMDRawStream& AliPMDRawStream::operator = (const AliPMDRawStream& 
66                                               /* stream */)
67 {
68 // assignment operator
69
70   AliFatal("operator = assignment operator not implemented");
71   return *this;
72 }
73
74 //_____________________________________________________________________________
75 AliPMDRawStream::~AliPMDRawStream()
76 {
77 // destructor
78
79 }
80
81
82 //_____________________________________________________________________________
83
84 Bool_t AliPMDRawStream::DdlData(Int_t indexDDL, TObjArray *pmdddlcont)
85 {
86 // read the next raw digit
87 // returns kFALSE if there is no digit left
88
89
90   AliPMDddldata *pmdddldata;
91
92   if (!fRawReader->ReadHeader()) return kFALSE;
93   Int_t  iddl  = fRawReader->GetDDLID();
94   Int_t dataSize = fRawReader->GetDataSize();
95   Int_t totaldataword = dataSize/4;
96
97   if (dataSize <= 0) return kFALSE;
98   if (indexDDL != iddl)
99     {
100       AliWarning("Mismatch in the DDL index");
101       fRawReader->AddFatalErrorLog(kDDLIndexMismatch);
102       return kFALSE;
103     }
104
105   UInt_t *buffer;
106   buffer = new UInt_t[totaldataword];
107   UInt_t data;
108   for (Int_t i = 0; i < totaldataword; i++)
109     {
110       fRawReader->ReadNextInt(data);
111       buffer[i] = data;
112     }
113
114   // --- Open the mapping file
115
116   TString fileName(gSystem->Getenv("ALICE_ROOT"));
117   if(iddl == 0)
118     {
119       fileName += "/PMD/PMD_Mapping_ddl0.dat";
120     }
121   else if(iddl == 1)
122     {
123       fileName += "/PMD/PMD_Mapping_ddl1.dat";
124     }
125   else if(iddl == 2)
126     {
127       fileName += "/PMD/PMD_Mapping_ddl2.dat";
128     }
129   else if(iddl == 3)
130     {
131       fileName += "/PMD/PMD_Mapping_ddl3.dat";
132     }
133   else if(iddl == 4)
134     {
135       fileName += "/PMD/PMD_Mapping_ddl4.dat";
136     }
137   else if(iddl == 5)
138     {
139       fileName += "/PMD/PMD_Mapping_ddl5.dat";
140     }
141
142   ifstream infile;
143   infile.open(fileName.Data(), ios::in); // ascii file
144   if(!infile) {
145     AliError(Form("Could not read the mapping file for DDL No = %d",iddl));
146     fRawReader->AddFatalErrorLog(kNoMappingFile,Form("ddl=%d",iddl));
147   }
148   
149   Int_t modulePerDDL = 0;
150   if (iddl < 4)
151     {
152       modulePerDDL = 6;
153     }
154   else if (iddl == 4 || iddl == 5)
155     {
156       modulePerDDL = 12;
157     }
158
159   const Int_t kNPatchBus = 51;
160   
161   Int_t modno, totPatchBus, bPatchBus, ePatchBus;
162   Int_t ibus, totmcm, rows, rowe, cols, cole;
163   Int_t moduleNo[kNPatchBus], mcmperBus[kNPatchBus];
164   Int_t startRowBus[kNPatchBus], endRowBus[kNPatchBus];
165   Int_t startColBus[kNPatchBus], endColBus[kNPatchBus];
166
167   for (ibus = 0; ibus < kNPatchBus; ibus++)
168     {
169       mcmperBus[ibus]   = -1;
170       startRowBus[ibus] = -1;
171       endRowBus[ibus]   = -1;
172       startColBus[ibus] = -1;
173       endColBus[ibus]   = -1;
174     }
175
176   for (Int_t im = 0; im < modulePerDDL; im++)
177     {
178       infile >> modno;
179       infile >> totPatchBus >> bPatchBus >> ePatchBus;
180       
181       for(Int_t i=0; i<totPatchBus; i++)
182         {
183           infile >> ibus >> totmcm >> rows >> rowe >> cols >> cole;
184
185           moduleNo[ibus]     = modno;
186           mcmperBus[ibus]    = totmcm;
187           startRowBus[ibus]  = rows;
188           endRowBus[ibus]    = rowe;
189           startColBus[ibus]  = cols;
190           endColBus[ibus]    = cole;
191         }
192     }
193
194   infile.close();
195
196   AliPMDBlockHeader    blockHeader;
197   AliPMDDspHeader      dspHeader;
198   AliPMDPatchBusHeader pbusHeader;
199
200   const Int_t kblHLen   = blockHeader.GetHeaderLength();
201   const Int_t kdspHLen  = dspHeader.GetHeaderLength();
202   const Int_t kpbusHLen = pbusHeader.GetHeaderLength();
203   
204   Int_t parity;
205   Int_t idet, ismn;
206   Int_t irow = -1;
207   Int_t icol = -1;
208
209   Int_t blHeaderWord[8];
210   Int_t dspHeaderWord[10];
211   Int_t pbusHeaderWord[4];
212
213   Int_t ilowLimit       = 0;
214   Int_t iuppLimit       = 0;
215   Int_t blRawDataLength = 0;
216   Int_t iwordcount      = 0;
217
218
219   for (Int_t iblock = 0; iblock < 2; iblock++)
220     {
221       ilowLimit = iuppLimit;
222       iuppLimit = ilowLimit + kblHLen;
223
224       for (Int_t i = ilowLimit; i < iuppLimit; i++)
225         {
226           blHeaderWord[i-ilowLimit] = (Int_t) buffer[i];
227         }
228
229       blockHeader.SetHeader(blHeaderWord);
230
231       blRawDataLength = blockHeader.GetRawDataLength();
232
233       for (Int_t idsp = 0; idsp < 5; idsp++)
234         {
235           ilowLimit = iuppLimit;
236           iuppLimit = ilowLimit + kdspHLen;
237
238           for (Int_t i = ilowLimit; i < iuppLimit; i++)
239             {
240               iwordcount++;
241               dspHeaderWord[i-ilowLimit] = (Int_t) buffer[i];
242             }
243           dspHeader.SetHeader(dspHeaderWord);
244
245           for (ibus = 0; ibus < 5; ibus++)
246             {
247               ilowLimit = iuppLimit;
248               iuppLimit = ilowLimit + kpbusHLen;
249
250               for (Int_t i = ilowLimit; i < iuppLimit; i++)
251                 {
252                   iwordcount++;
253                   pbusHeaderWord[i-ilowLimit] = (Int_t) buffer[i];
254                 }
255               pbusHeader.SetHeader(pbusHeaderWord);
256               Int_t rawdatalength = pbusHeader.GetRawDataLength();
257               Int_t pbusid = pbusHeader.GetPatchBusId();
258
259               ilowLimit = iuppLimit;
260               iuppLimit = ilowLimit + rawdatalength;
261
262               Int_t imodule = moduleNo[pbusid];
263
264
265               for (Int_t iword = ilowLimit; iword < iuppLimit; iword++)
266                 {
267                   iwordcount++;
268                   data = buffer[iword];
269
270                   Int_t isig =  data & 0x0FFF;
271                   Int_t ich  = (data >> 12) & 0x003F;
272                   Int_t imcm = (data >> 18) & 0x07FF;
273                   Int_t ibit = (data >> 31) & 0x0001;
274                   parity = ComputeParity(data);
275                   if (ibit != parity)
276                     {
277                       AliWarning("ComputeParity:: Parity Error");
278                       fRawReader->AddMajorErrorLog(kParityError);
279                     }
280
281                   ConvertDDL2SMN(iddl, imodule, ismn, idet);
282
283                   GetRowCol(iddl, ismn, pbusid, imcm, ich, 
284                             startRowBus, endRowBus,
285                             startColBus, endColBus,
286                             irow, icol);
287
288                   TransformH2S(ismn, irow, icol);
289
290                   pmdddldata = new AliPMDddldata();
291
292                   pmdddldata->SetDetector(idet);
293                   pmdddldata->SetSMN(ismn);
294                   pmdddldata->SetModule(imodule);
295                   pmdddldata->SetPatchBusId(pbusid);
296                   pmdddldata->SetMCM(imcm);
297                   pmdddldata->SetChannel(ich);
298                   pmdddldata->SetRow(irow);
299                   pmdddldata->SetColumn(icol);
300                   pmdddldata->SetSignal(isig);
301                   pmdddldata->SetParityBit(ibit);
302                   
303                   pmdddlcont->Add(pmdddldata);
304                   
305                 } // data word loop
306
307               if (iwordcount == blRawDataLength) break;
308
309             } // patch bus loop
310
311           if (dspHeader.GetPaddingWord() == 1) iuppLimit++;
312           if (iwordcount == blRawDataLength) break;
313
314         } // end of DSP
315       if (iwordcount == blRawDataLength) break;
316
317     } // end of BLOCK
318   
319   delete [] buffer;
320
321   return kTRUE;
322 }
323 //_____________________________________________________________________________
324 void AliPMDRawStream::GetRowCol(Int_t ddlno, Int_t smn, Int_t pbusid,
325                                 UInt_t mcmno, UInt_t chno,
326                                 Int_t startRowBus[], Int_t endRowBus[],
327                                 Int_t startColBus[], Int_t endColBus[],
328                                 Int_t &row, Int_t &col) const
329 {
330 // decode: ddlno, patchbusid, mcmno, chno -> um, row, col
331
332
333
334   UInt_t iCh[64];
335
336   static const UInt_t kChDdl01[64] = { 9, 6, 5, 10, 1, 2, 0, 3,
337                                        13, 7, 4, 11, 8, 14, 12, 15,
338                                        16, 19, 17, 23, 20, 27, 24, 18,
339                                        28, 31, 29, 30, 21, 26, 25, 22,
340                                        41, 38, 37, 42, 33, 34, 32, 35,
341                                        45, 39, 36, 43, 40, 46, 44, 47,
342                                        48, 51, 49, 55, 52, 59, 56, 50,
343                                        60, 63, 61, 62, 53, 58, 57, 54 };
344     
345   static const UInt_t kChDdl23[64] = { 54, 57, 58, 53, 62, 61, 63, 60,
346                                        50, 56, 59, 52, 55, 49, 51, 48,
347                                        47, 44, 46, 40, 43, 36, 39, 45,
348                                        35, 32, 34, 33, 42, 37, 38, 41,
349                                        22, 25, 26, 21, 30, 29, 31, 28,
350                                        18, 24, 27, 20, 23, 17, 19, 16,
351                                        15, 12, 14, 8, 11, 4, 7, 13,
352                                        3, 0, 2, 1, 10, 5, 6, 9 };
353   
354   static const UInt_t kChDdl41[64] = { 53, 58, 57, 54, 61, 62, 60, 63,
355                                        49, 59, 56, 55, 52, 50, 48, 51,
356                                        44, 47, 45, 43, 40, 39, 36, 46,
357                                        32, 35, 33, 34, 41, 38, 37, 42,
358                                        21, 26, 25, 22, 29, 30, 28, 31,
359                                        17, 27, 24, 23, 20, 18, 16, 19,
360                                        12, 15, 13, 11, 8, 7, 4, 14,
361                                        0, 3, 1, 2, 9, 6, 5, 10 };
362   
363   static const UInt_t kChDdl42[64] = { 10, 5, 6, 9, 2, 1, 3, 0,
364                                        14, 4, 7, 8, 11, 13, 15, 12,
365                                        19, 16, 18, 20, 23, 24, 27, 17,
366                                        31, 28, 30, 29, 22, 25, 26, 21,
367                                        42, 37, 38, 41, 34, 33, 35, 32,
368                                        46, 36, 39, 40, 43, 45, 47, 44,
369                                        51, 48, 50, 52, 55, 56, 59, 49,
370                                        63, 60, 62, 61, 54, 57, 58, 53 };
371   
372   static const UInt_t kChDdl51[64] = { 10, 5, 6, 9, 2, 1, 3, 0,
373                                        14, 4, 7, 8, 11, 13, 15, 12,
374                                        19, 16, 18, 20, 23, 24, 27, 17,
375                                        31, 28, 30, 29, 22, 25, 26, 21,
376                                        42, 37, 38, 41, 34, 33, 35, 32,
377                                        46, 36, 39, 40, 43, 45, 47, 44,
378                                        51, 48, 50, 52, 55, 56, 59, 49,
379                                        63, 60, 62, 61, 54, 57, 58, 53 };
380   
381   static const UInt_t kChDdl52[64] = { 53, 58, 57, 54, 61, 62, 60, 63,
382                                        49, 59, 56, 55, 52, 50, 48, 51,
383                                        44, 47, 45, 43, 40, 39, 36, 46,
384                                        32, 35, 33, 34, 41, 38, 37, 42,
385                                        21, 26, 25, 22, 29, 30, 28, 31,
386                                        17, 27, 24, 23, 20, 18, 16, 19,
387                                        12, 15, 13, 11, 8, 7, 4, 14,
388                                        0, 3, 1, 2, 9, 6, 5, 10 };
389   
390   for (Int_t i = 0; i < 64; i++)
391   {
392       if (ddlno == 0 || ddlno == 1) iCh[i] = kChDdl01[i];
393       if (ddlno == 2 || ddlno == 3) iCh[i] = kChDdl23[i];
394       
395       if (ddlno == 4 && smn < 6)                iCh[i] = kChDdl41[i];
396       if (ddlno == 4 && (smn >= 18 && smn < 24))iCh[i] = kChDdl42[i];
397       if (ddlno == 5 && (smn >= 12 && smn < 18))iCh[i] = kChDdl51[i];
398       if (ddlno == 5 && (smn >=  6 && smn < 12))iCh[i] = kChDdl52[i];
399   }
400   
401   
402   Int_t rowcol  = iCh[chno];
403   Int_t irownew = rowcol/4;
404   Int_t icolnew = rowcol%4;
405
406   if (ddlno == 0 )
407     {
408       row = startRowBus[pbusid] + irownew;
409       col = startColBus[pbusid] + (mcmno-1)*4 + icolnew;
410     }
411   else if (ddlno == 1)
412     {
413     row = endRowBus[pbusid] - (15 - irownew);
414     col = startColBus[pbusid] + (mcmno-1)*4 + icolnew;
415     
416     }
417   else if (ddlno == 2 )
418     {
419       row = startRowBus[pbusid] + irownew;
420       col = endColBus[pbusid] - (mcmno-1)*4 - (3 - icolnew);
421     }
422   else if (ddlno == 3)
423     {
424     row = endRowBus[pbusid] - (15 - irownew);
425     col = endColBus[pbusid] - (mcmno-1)*4 - (3 - icolnew);
426     }
427   else if (ddlno == 4 )
428     {
429       if (pbusid  < 19)
430         {
431           if (mcmno <= 12)
432             {
433               // Add 16 to skip the 1st 15 rows
434               row = startRowBus[pbusid] + irownew + 16;
435               col = startColBus[pbusid] + (mcmno-1)*4 + icolnew;
436             }
437           else if(mcmno > 12)
438             {
439               row = startRowBus[pbusid] + irownew;
440               col = startColBus[pbusid] + (mcmno-12-1)*4 + icolnew;
441             }
442         }
443       else if(pbusid > 18)
444         {
445           if (mcmno <= 12)
446             {
447               col = endColBus[pbusid] - (mcmno-1)*4 - (3 - icolnew); 
448
449               if(endRowBus[pbusid] - startRowBus[pbusid] > 16)
450                 row = endRowBus[pbusid] - (15 - irownew) - 16 ;
451               else
452                 row = endRowBus[pbusid] - (15 - irownew) ;
453             }
454           else if(mcmno > 12)
455             {
456               row = endRowBus[pbusid] - (15 - irownew)  ;
457               col = endColBus[pbusid] - (mcmno - 12 - 1)*4 - (3 - icolnew);
458             }
459         }
460     }
461   else if (ddlno == 5)
462     {
463       if (pbusid  <= 18)
464         {
465           if (mcmno > 12)
466             {
467               // Subtract 16 to skip the 1st 15 rows
468               row = endRowBus[pbusid] - 16 -(15 - irownew);
469               col = startColBus[pbusid] + (mcmno-12 -1)*4 + icolnew;
470             }
471           else
472             {
473               row = endRowBus[pbusid]  - (15 - irownew) ;
474               col = startColBus[pbusid] + (mcmno -1)*4 + icolnew;
475             }
476
477         }
478       
479       else if (pbusid > 18)
480         {
481           if(mcmno > 12)
482             {
483               // Add 16 to skip the 1st 15 rows
484               row = startRowBus[pbusid] + irownew + 16;
485               col = endColBus[pbusid] - (mcmno - 12 - 1)*4 - (3 - icolnew);
486             }
487           else 
488             {
489               row = startRowBus[pbusid] + irownew ;
490               col = endColBus[pbusid] - (mcmno - 1)*4 - (3 - icolnew); 
491             }
492         }
493     }
494   
495 }
496 //_____________________________________________________________________________
497 void AliPMDRawStream::ConvertDDL2SMN(Int_t iddl, Int_t imodule,
498                                      Int_t &smn, Int_t &detector) const
499 {
500   // This converts the DDL number (0 to 5), Module Number (0-47)
501   // to Serial module number in one detector (SMN : 0-23) and
502   // detector number (0:PRE plane, 1:CPV plane)
503   if (iddl < 4)
504     {
505       smn = imodule;
506       detector = 0;
507     }
508   else
509     {
510       smn = imodule - 24;
511       detector = 1;
512     }
513 }
514 //_____________________________________________________________________________
515
516 void AliPMDRawStream::TransformH2S(Int_t smn, Int_t &row, Int_t &col) const
517 {
518   // This does the transformation of the hardware coordinate to
519   // software 
520   // i.e., For SuperModule 0 &1, instead of 96x48(hardware),
521   // it is 48x96 (software)
522   // For Supermodule 3 & 4, 48x96
523
524   Int_t irownew  = 0;
525   Int_t icolnew  = 0;
526
527   if(smn < 12)
528     {
529       irownew = col;
530       icolnew = row;
531     }
532   else if(smn >= 12 && smn < 24)
533     {
534       irownew = row;
535       icolnew = col;
536     }
537
538   row = irownew;
539   col = icolnew;
540 }
541 //_____________________________________________________________________________
542 Int_t AliPMDRawStream::ComputeParity(Int_t data)
543 {
544 // Calculate the parity bit
545
546   Int_t count = 0;
547   for(Int_t j = 0; j<29; j++)
548     {
549       if (data & 0x01 ) count++;
550       data >>= 1;
551     }
552   
553   Int_t parity = count%2;
554
555   return parity;
556 }
557
558 //_____________________________________________________________________________