]> git.uio.no Git - u/mrichter/AliRoot.git/blob - MUON/AliMUONRawData.cxx
Add rawdata header & offset on DDL number (Christian)
[u/mrichter/AliRoot.git] / MUON / AliMUONRawData.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 // MUON Raw Data generator in ALICE-MUON
19 //
20 // This class v-1:
21 // * generates raw data for MUON tracker only (for the moment)
22 // * a simple mapping is used (see below)
23 // * the bus patch id is calculated but not stored properly in the raw data
24 //   this has to be changed
25 // one DDL per 1/2 chamber is created for both cathode.
26 //
27 ////////////////////////////////////
28
29 #include "AliMUONRawData.h"
30 #include "AliMUONDigit.h"
31 #include "AliMUONConstants.h"
32 #include "AliMUONData.h"
33 #include "AliMUONDDLTracker.h"
34 #include "AliRun.h" 
35 #include "AliRunLoader.h"
36 #include "AliLoader.h"
37 #include "AliBitPacking.h" 
38 #include "AliRawDataHeader.h"
39
40 const Int_t AliMUONRawData::fgkDefaultPrintLevel = 0;
41
42 ClassImp(AliMUONRawData) // Class implementation in ROOT context
43
44 //__________________________________________________________________________
45 AliMUONRawData::AliMUONRawData(AliLoader* loader)
46   : TObject()
47 {
48   // Standard Constructor
49  
50   fDebug           = 0;
51   fNCh             = 0;
52   fNTrackingCh     = 0;
53   fNTriggerCh      = 0;
54   fMUONData        = 0;
55
56   fPrintLevel = fgkDefaultPrintLevel;
57
58   // initialize loader's
59   fLoader = loader;
60
61   // initialize container
62   fMUONData  = new AliMUONData(fLoader,"MUON","MUON");
63 }
64
65 //__________________________________________________________________________
66 AliMUONRawData::AliMUONRawData()
67   : TObject(),
68     fNCh(0),
69     fNTrackingCh(0),
70     fNTriggerCh(0),
71     fMUONData(0),
72     fPrintLevel(fgkDefaultPrintLevel),
73     fDebug(0),
74     fLoader(0)
75 {
76   // Default Constructor
77 }
78
79 //_______________________________________________________________________
80 AliMUONRawData::AliMUONRawData (const AliMUONRawData& rhs)
81   : TObject(rhs)
82 {
83 // Protected copy constructor
84
85   Fatal("AliMUONRawData", "Not implemented.");
86 }
87
88 //_______________________________________________________________________
89 AliMUONRawData & 
90 AliMUONRawData::operator=(const AliMUONRawData& rhs)
91 {
92 // Protected assignement operator
93
94   if (this == &rhs) return *this;
95
96   Fatal("operator=", "Not implemented.");
97     
98   return *this;  
99 }
100
101 //__________________________________________________________________________
102 AliMUONRawData::~AliMUONRawData(void)
103 {
104   if (fMUONData)
105     delete fMUONData;
106   return;
107 }
108 //____________________________________________________________________
109 Int_t AliMUONRawData::WriteRawData()
110 {
111  // convert digits of the current event to raw data
112
113
114   Int_t DDLId;
115   Char_t name[20];
116
117   fLoader->LoadDigits("READ");
118   fMUONData->SetTreeAddress("D");
119   //  printf("je suis dans WriteRawData\n");
120
121   for (Int_t ich = 0; ich < AliMUONConstants::NTrackingCh(); ich++) {
122
123     // open files
124     DDLId = ich * 2  + 0x900;
125     sprintf(name, "MUON_%d.ddl",DDLId);
126     fFile1 = fopen(name,"w");
127
128     DDLId = (ich * 2) + 1 + 0x900 ;
129     sprintf(name, "MUON_%d.ddl",DDLId);
130     fFile2 = fopen(name,"w");
131
132     WriteDDL(ich);
133   
134     // reset and close
135     fclose(fFile1);
136     fclose(fFile2);
137     fMUONData->ResetDigits();
138   }
139   
140   return kTRUE;
141 }
142 //____________________________________________________________________
143 Int_t AliMUONRawData::WriteDDL(Int_t iCh)
144 {
145
146   TClonesArray* muonDigits = 0;
147
148   // DDL event one per half chamber
149   AliMUONDDLTracker* eventDDL1;
150   AliMUONDDLTracker* eventDDL2;
151
152   // data format
153   Char_t parity = 0x4;
154   UShort_t manuId;
155   UChar_t channelId;
156   UShort_t charge;
157   Int_t busPatchId;
158
159   UInt_t word;
160   Int_t nWord;
161   Int_t dummy;
162
163   Int_t offsetX = 0; // offet row
164   Int_t offsetY = 0; // offset columns
165   Int_t offsetCath = 0; //offset from one cathod to the other
166   Int_t maxChannel = 0; // maximum nb of channel in 1/2 chamber
167   Int_t id;
168
169   Int_t nDigits;
170   AliMUONDigit* digit;
171
172   AliRawDataHeader header;
173
174   eventDDL1 = new AliMUONDDLTracker();
175   eventDDL2 = new AliMUONDDLTracker();
176
177   for (Int_t iCath = 0; iCath < 2; iCath++) {
178
179     if (fPrintLevel)
180       printf("WriteDDL chamber %d and cathode %d\n", iCh+1, iCath);
181
182     fMUONData->ResetDigits();
183     fMUONData->GetCathode(iCath);
184     muonDigits = fMUONData->Digits(iCh);
185
186     nDigits = muonDigits->GetEntriesFast();
187     if (fPrintLevel)
188       printf("ndigits = %d\n",nDigits);
189
190     // open DDL file, on per 1/2 chamber
191  
192     for (Int_t idig = 0; idig < nDigits; idig++) {
193
194       digit = (AliMUONDigit*) muonDigits->UncheckedAt(idig);
195
196       switch (iCh+1) {
197       case 1:
198       case 2:
199       case 3:
200       case 4:
201         offsetX = 512;
202         offsetY = 256;
203         offsetCath = 65536;
204         maxChannel = (offsetY * offsetX + 2* offsetY + offsetCath);
205         break;
206       case 5:
207       case 6:
208       case 7:
209       case 8:
210       case 9:
211       case 10:
212         offsetX = 1024;
213         offsetY = 0;
214         offsetCath = 65536;
215         maxChannel = (256 * offsetX + offsetX + offsetCath);
216         break;
217       }
218       // dummy mapping
219       // manu Id directly from a matrix 8*8, same segmentation for B and NB
220       // 50 buspatches for 1/2 chamber
221  
222       id =  (TMath::Abs(digit->PadX()) * offsetX + digit->PadY() + offsetY +
223              offsetCath*iCath);
224       busPatchId = id/50;
225
226       Int_t inBusId =  (id - maxChannel/50 * busPatchId);// id channel in buspatch
227       Int_t manuPerBus = (maxChannel/(50*64)); // number of manus per buspatch
228
229       // 64 manu cards for one buspatch
230       manuId = inBusId/manuPerBus;
231       manuId &= 0x7FF; // 11 bits 
232
233       // channel id
234       channelId = (inBusId % manuPerBus);
235       channelId &= 0x3F; // 6 bits
236
237       // charge
238       charge = digit->Signal();
239       charge &= 0xFFF;
240
241       if (fPrintLevel)
242         printf("id: %d, busPatchId %d, manuId: %d, channelId: %d, padx: %d pady %d, charge %d\n",
243                id, busPatchId, manuId, channelId, digit->PadX(), digit->PadY(), digit->Signal());
244       //packing word
245       AliBitPacking::PackWord((UInt_t)parity,word,29,31);
246       AliBitPacking::PackWord((UInt_t)manuId,word,18,28);
247       AliBitPacking::PackWord((UInt_t)channelId,word,12,17);
248       AliBitPacking::PackWord((UInt_t)charge,word,0,11);
249
250       // set  DDL Event
251       if (digit->PadX() > 0) {
252         eventDDL1->SetRawData(word);
253         eventDDL1->SetBusPatchId(busPatchId); // information not usable only last bus patch stored
254       } else {
255         eventDDL2->SetRawData(word);
256         eventDDL2->SetBusPatchId(busPatchId);
257       }
258       if (fPrintLevel) {
259         printf("word: 0x%x, ",word);
260         printf("manuId back %d, ",eventDDL1->GetManuId(eventDDL1->GetLength()-1));
261         printf("channelId back %d, ",eventDDL1->GetChannelId(eventDDL1->GetLength()-1));
262         printf("charge back %d\n",eventDDL1->GetCharge(eventDDL1->GetLength()-1));
263       }
264     }
265   }
266   // write DDL event
267   nWord = eventDDL1->GetLength();
268   if (nWord > 0) { // not empty event
269     header.fSize = nWord*4 + sizeof(AliRawDataHeader) + 12; // include EoD & length
270     fwrite((char*)(&header),sizeof(header),1,fFile1);
271     fwrite(eventDDL1->GetAddress(),sizeof(int),nWord+2,fFile1);
272     dummy = eventDDL1->GetEoD(); 
273     fwrite(&dummy,sizeof(int),1,fFile1);// could be nicer !
274   }
275   nWord = eventDDL2->GetLength();
276   if (nWord > 0) {
277     header.fSize = nWord*4 + sizeof(AliRawDataHeader) + 12;
278     fwrite((char*)(&header),sizeof(header),1,fFile2);
279     fwrite(eventDDL2->GetAddress(),sizeof(int),nWord+2,fFile2);
280     dummy = eventDDL2->GetEoD();
281     fwrite(&dummy,sizeof(int),1,fFile2);
282   }
283   delete eventDDL1;
284   delete eventDDL2;
285   return kTRUE;
286 }