]> git.uio.no Git - u/mrichter/AliRoot.git/blob - HLT/rec/AliHLTOUTHomerCollection.cxx
- new gain calibb
[u/mrichter/AliRoot.git] / HLT / rec / AliHLTOUTHomerCollection.cxx
1 // $Id$
2
3 //**************************************************************************
4 //* This file is property of and copyright by the ALICE HLT Project        * 
5 //* ALICE Experiment at CERN, All rights reserved.                         *
6 //*                                                                        *
7 //* Primary Authors: Matthias Richter <Matthias.Richter@ift.uib.no>        *
8 //*                  for The ALICE HLT Project.                            *
9 //*                                                                        *
10 //* Permission to use, copy, modify and distribute this software and its   *
11 //* documentation strictly for non-commercial purposes is hereby granted   *
12 //* without fee, provided that the above copyright notice appears in all   *
13 //* copies and that both the copyright notice and this permission notice   *
14 //* appear in the supporting documentation. The authors make no claims     *
15 //* about the suitability of this software for any purpose. It is          *
16 //* provided "as is" without express or implied warranty.                  *
17 //**************************************************************************
18
19 /** @file   AliHLTOUTHomerCollection.cxx
20     @author Matthias Richter
21     @date   
22     @brief  General collection for HLTOUT data in DDL format.
23 */
24
25 #include "AliHLTOUTHomerCollection.h"
26 #include "AliHLTHOMERLibManager.h"
27 #include "AliHLTHOMERReader.h"
28 #include "AliRawDataHeader.h"
29 #include "AliHLTEsdManager.h"
30 #include "AliDAQ.h"
31
32 /** ROOT macro for the implementation of ROOT specific class methods */
33 ClassImp(AliHLTOUTHomerCollection)
34
35 AliHLTOUTHomerCollection::AliHLTOUTHomerCollection(int event, AliHLTEsdManager* pEsdManager)
36   :
37   AliHLTOUTHomerBuffer(NULL, 0),
38   fpCurrent(NULL),
39   fEvent(event),
40   fpEsdManager(pEsdManager)
41 {
42   // see header file for class documentation
43   // or
44   // refer to README to build package
45   // or
46   // visit http://web.ift.uib.no/~kjeks/doc/alice-hlt
47 }
48
49 const int AliHLTOUTHomerCollection::fgkIdShift=16;
50
51 AliHLTOUTHomerCollection::~AliHLTOUTHomerCollection()
52 {
53   // see header file for class documentation
54   if (fpManager) {
55     if (fpCurrent) fpManager->DeleteReader(fpCurrent);
56     fpCurrent=NULL;
57   }
58 }
59
60 int AliHLTOUTHomerCollection::GenerateIndex()
61 {
62   // see header file for class documentation
63   // step through all HLT ddls, create HOMER readers and
64   // scan data block
65   int iResult=0;
66   if (fpManager) {
67     Reset();
68     int firstLink=AliDAQ::DdlIDOffset("HLT");
69     int nofDDLs=AliDAQ::NumberOfDdls("HLT");
70     SelectEquipment(-1,firstLink, firstLink+nofDDLs);
71     UChar_t* pSrc=NULL;
72     while (ReadNextData(pSrc) && pSrc!=NULL && iResult>=0) {
73       AliHLTUInt32_t id=(GetEquipmentId());
74       unsigned int size=GetDataSize();
75
76       AliHLTHOMERReader* pReader=OpenReader(pSrc, size);
77
78       // we use the equipment id to identify the different homer blocks 
79       id<<=fgkIdShift;
80       if (pReader) {
81         iResult=ScanReader(pReader, id);
82         fpManager->DeleteReader(pReader);
83       }
84     }
85   } else {
86     iResult=-ENODEV;
87   }
88   return iResult;
89 }
90
91 int AliHLTOUTHomerCollection::GetDataBuffer(AliHLTUInt32_t index, const AliHLTUInt8_t* &pBuffer, 
92                                       AliHLTUInt32_t& size)
93 {
94   // see header file for class documentation
95   int iResult=0;
96   pBuffer=NULL;
97   size=0;
98   if (fpManager) {
99     Int_t id = Int_t(index>>fgkIdShift);
100     AliHLTUInt32_t blockNo=index&((0x1<<fgkIdShift)-1);
101
102     // block from the same ddl requested?
103     if (fpCurrent && GetEquipmentId()!=id) {
104       fpManager->DeleteReader(fpCurrent);
105       fpCurrent=NULL;
106     }
107
108     // open ddl for equipment id and create HOMER reader
109     if (!fpCurrent) {
110       Reset();
111       SelectEquipment(-1, id, id);
112       UChar_t* pSrc=NULL;
113       if (ReadNextData(pSrc) && pSrc!=NULL) {
114         int srcSize=GetDataSize();
115         fpCurrent=OpenReader(pSrc, srcSize);
116         if (fpCurrent && fpCurrent->ReadNextEvent()!=0) {
117           iResult=-ENODATA;
118         }
119       } else {
120         iResult=-ENOSYS;
121       }
122     }
123
124     // get data
125     if (fpCurrent) {
126       AliHLTMonitoringReader* pReader=fpCurrent;
127       if ((pBuffer=static_cast<const AliHLTUInt8_t*>(pReader->GetBlockData(blockNo)))!=NULL) {
128         size=pReader->GetBlockDataLength(blockNo);
129       } else {
130         iResult=-ENOENT;
131       }
132     }
133   } else {
134     iResult=-ENODEV;
135   }
136   return iResult;
137 }
138
139 AliHLTHOMERReader* AliHLTOUTHomerCollection::OpenReader(UChar_t* pSrc, unsigned int size)
140 {
141   // see header file for class documentation
142   unsigned int offset=sizeof(AliHLTOUTEventHeader);
143   const AliRawDataHeader* pCDH=GetDataHeader();
144   AliHLTUInt32_t id=(GetEquipmentId());
145   AliHLTUInt32_t statusFlags=pCDH->GetStatus();
146   AliHLTOUTEventHeader* pHLTHeader=reinterpret_cast<AliHLTOUTEventHeader*>(pSrc);
147
148   // consistency check for the block size
149   if (pHLTHeader->fLength>size) {
150     HLTError("can not treat HLT data block %d: size mismatch, header %d, but buffer is %d", id, pHLTHeader->fLength, size);
151     return NULL;
152   } else if (pHLTHeader->fLength<size-3) {
153     // data payload is aligned to 32bit, so there can be a difference by at most 3 bytes
154     HLTWarning("size mismatch in HLT data block %d: header %d, but buffer is %d", id, pHLTHeader->fLength, size);
155   }
156
157   // determine the offset of the homer block
158   // the HLT header is mandatory, HLT decision and HLT
159   // payload are optional. HLT decision is always before HLT
160   // payload if existent.
161   if (statusFlags&(0x1<<kCDHFlagsHLTDecision)) {
162     // the block contains HLT decision data, this is just
163     // skipped here
164     AliHLTUInt32_t* pDecisionLen=reinterpret_cast<AliHLTUInt32_t*>(pSrc+offset);
165     if ((*pDecisionLen)*sizeof(AliHLTUInt32_t)+offset<size) {
166       // the first 32bit word specifies the number of 32bit words in the
167       // decision block -> +1 for this length word
168       offset+=((*pDecisionLen)+1)*sizeof(AliHLTUInt32_t);
169     } else {
170       HLTWarning("size mismatch: HLT decision block bigger than total block length, skipping ...");
171       return NULL;
172     }
173   }
174
175   // check if there is payload
176   if (!(statusFlags&(0x1<<kCDHFlagsHLTPayload))) return NULL;
177
178   // continue if there is no data left in the buffer
179   if (offset>=pHLTHeader->fLength) {
180     HLTWarning("no HLT payload available, but bit is set, skipping ...");
181     return NULL;
182   }
183
184   // check for the HOME descriptor type id
185   AliHLTUInt64_t* pHomerDesc=reinterpret_cast<AliHLTUInt64_t*>(pSrc+offset);
186   if (*(pHomerDesc+kID_64b_Offset) != HOMER_BLOCK_DESCRIPTOR_TYPEID && 
187       ByteSwap64(*(pHomerDesc+kID_64b_Offset)) != HOMER_BLOCK_DESCRIPTOR_TYPEID) {
188     HLTWarning("format error: can not find HOMER block descriptor typid, skipping this data block");
189     return NULL;
190   }
191
192   AliHLTUInt64_t eventId=pHLTHeader->fEventIDHigh;
193   eventId = eventId<<32;
194   eventId|=pHLTHeader->fEventIDLow;
195   SetEventId(eventId);
196   return fpManager->OpenReaderBuffer(pSrc+offset, pHLTHeader->fLength-offset);
197 }
198
199 int AliHLTOUTHomerCollection::WriteESD(const AliHLTUInt8_t* pBuffer, AliHLTUInt32_t size, AliHLTComponentDataType dt, AliESDEvent* tgtesd) const
200 {
201   // see header file for class documentation
202   if (!pBuffer && size<=0) return -EINVAL;
203   int iResult=0;
204   if (fpEsdManager) {
205     fpEsdManager->WriteESD(pBuffer, size, dt, tgtesd, GetCurrentEventNo());
206   }
207   return iResult;
208 }