Initial version of the RCU ALTRO V3 format encoder. It derives from the old encoder...
[u/mrichter/AliRoot.git] / RAW / AliAltroBufferV3.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 // Interface to the Altro format
17 // to read and write digits
18 // To be used in Alice Data Challenges 
19 // and in the compression of the RAW data
20
21 #include "AliAltroBufferV3.h"
22 #include "AliRawDataHeaderSim.h"
23 #include "AliLog.h"
24 #include "AliFstream.h"
25
26 ClassImp(AliAltroBufferV3)
27
28 //_____________________________________________________________________________
29 AliAltroBufferV3::AliAltroBufferV3(const char* fileName, AliAltroMapping *mapping):
30 AliAltroBuffer(fileName,mapping),
31   fN(0)
32 {
33   // Constructor
34 }
35
36 //_____________________________________________________________________________
37 AliAltroBufferV3::~AliAltroBufferV3()
38 {
39 // destructor
40
41   if (fVerbose) Info("~AliAltroBufferV3", "File Created");
42
43   delete fFile;
44
45 }
46
47 //_____________________________________________________________________________
48 AliAltroBufferV3::AliAltroBufferV3(const AliAltroBufferV3& source):
49   AliAltroBuffer(source),
50   fN(source.fN)
51 {
52 // Copy Constructor
53
54   Fatal("AliAltroBufferV3", "copy constructor not implemented");
55 }
56
57 //_____________________________________________________________________________
58 AliAltroBufferV3& AliAltroBufferV3::operator = (const AliAltroBufferV3& /*source*/)
59 {
60 //Assigment operator
61
62   Fatal("operator =", "assignment operator not implemented");
63   return *this;
64 }
65
66 //_____________________________________________________________________________
67 void AliAltroBufferV3::FillBuffer(Int_t val)
68 {
69 //Fills the Buffer with 16 ten bits words and write into a file 
70
71   if ((val > 0x3FF) || (val < 0)) {
72     Error("FillBuffer", "Value out of range (10 bits): %d", val);
73     val = 0x3FF;
74   }
75
76   if (fN >= (kMaxWords-1)) {
77     Error("FillBuffer","Altro channel can't have more than 1024 10-bit words!");
78     return;
79   }
80
81   fArray[fN++] = val;
82 }
83
84 //_____________________________________________________________________________
85 void AliAltroBufferV3::WriteTrailer(Int_t wordsNumber, Short_t hwAddress)
86 {
87   //Writes a trailer (header) of 32 bits using
88   //a given hardware adress
89   UInt_t temp = hwAddress & 0xFFF;
90   temp = (wordsNumber << 16) & 0x3FF;
91   temp |= (0x1 << 30);
92
93   fFile->WriteBuffer((char *)(&temp),sizeof(UInt_t));
94
95   ReverseAndWrite();
96 }
97
98 //_____________________________________________________________________________
99 void AliAltroBufferV3::ReverseAndWrite()
100 {
101   // Reverse the altro data order and
102   // write the buffer to the file
103   UInt_t temp = 0;
104   Int_t shift = 20;
105   for(Int_t i = fN; i >= 0; i--) {
106     temp |= (fArray[i] << shift);
107     shift -= 10;
108     if (shift < 0) {
109       fFile->WriteBuffer((char *)(&temp),sizeof(UInt_t));
110       temp = 0;
111       shift = 20;
112     }
113   }
114
115   if (shift != 20) {
116     fFile->WriteBuffer((char *)(&temp),sizeof(UInt_t));
117   }
118
119   fN = 0;
120 }
121
122 //_____________________________________________________________________________
123 void AliAltroBufferV3::WriteRCUTrailer(Int_t rcuId)
124 {
125   // Writes the RCU trailer
126   // rcuId the is serial number of the corresponding
127   // RCU. The basic format of the trailer can be
128   // found in the RCU manual.
129   // This method should be called at the end of
130   // raw data writing.
131
132   UInt_t currentFilePos = fFile->Tellp();
133   UInt_t size = currentFilePos-fDataHeaderPos;
134   size -= sizeof(AliRawDataHeader);
135   
136   if ((size % 5) != 0) {
137     AliFatal(Form("The current raw data payload is not a mutiple of 5 (%d) ! Can not write the RCU trailer !",size));
138     return;
139   }
140
141   // Now put the size in unit of number of 40bit words
142   size /= 5;
143   fFile->WriteBuffer((char *)(&size),sizeof(UInt_t));
144
145   // Now several not yet full defined fields
146   // In principle they are supposed to contain
147   // information about the sampling frequency,
148   // L1 phase, list of 'dead' FECs, etc.
149   //  UInt_t buffer[n];
150   //  fFile->WriteBuffer((char *)(buffer),sizeof(UInt_t)*n);
151   
152   //  Now the RCU identifier and size of the trailer
153   //  FOr the moment the triler size is 2 32-bit words
154   UInt_t buffer = (2 & 0x7F);
155   buffer |= ((rcuId & 0x1FF) << 7);
156   buffer |= 0xAAAA << 16;
157   fFile->WriteBuffer((char *)(&buffer),sizeof(UInt_t));
158
159 }