Updated SNM Glauber fit
[u/mrichter/AliRoot.git] / HLT / TPCLib / AliHLTTPCClusterTransformationComponent.cxx
1
2 //***************************************************************************
3 //* This file is property of and copyright by the ALICE HLT Project         *
4 //* ALICE Experiment at CERN, All rights reserved.                          *
5 //*                                                                         *
6 //* Primary Authors: Sergey Gorbunov <sergey.gorbunov@fias.uni-frankfurt.de *
7 //*                  for The ALICE HLT Project.                             *
8 //*                                                                         *
9 //* Permission to use, copy, modify and distribute this software and its    *
10 //* documentation strictly for non-commercial purposes is hereby granted    *
11 //* without fee, provided that the above copyright notice appears in all    *
12 //* copies and that both the copyright notice and this permission notice    *
13 //* appear in the supporting documentation. The authors make no claims      *
14 //* about the suitability of this software for any purpose. It is           *
15 //* provided "as is" without express or implied warranty.                   *
16 //***************************************************************************
17
18 /** @file   AliHLTTPCClusterTransformationComponent.cxx
19     @author Sergey Gorbunov
20     @date   
21     @brief 
22 */
23
24 #include "AliHLTTPCClusterTransformationComponent.h"
25 #include "AliHLTTPCClusterTransformation.h"
26 #include "AliHLTTPCDefinitions.h"
27 #include "AliHLTTPCTransform.h"
28 #include "AliHLTTPCRawCluster.h"
29 #include "AliHLTTPCClusterDataFormat.h"
30 #include "AliHLTErrorGuard.h"
31
32 #include "AliCDBManager.h"
33 #include "AliCDBEntry.h"
34 #include "AliTPCcalibDB.h"
35
36 #include "TMath.h"
37 #include "TObjString.h" 
38 #include <cstdlib>
39 #include <cerrno>
40 #include <sys/time.h>
41
42 using namespace std;
43
44 ClassImp(AliHLTTPCClusterTransformationComponent) //ROOT macro for the implementation of ROOT specific class methods
45
46 const char* AliHLTTPCClusterTransformationComponent::fgkOCDBEntryClusterTransformation="HLT/ConfigTPC/TPCClusterTransformation";
47
48 AliHLTTPCClusterTransformation AliHLTTPCClusterTransformationComponent::fgTransform;
49 Bool_t AliHLTTPCClusterTransformationComponent::fgTimeInitialisedFromEvent = 0;
50
51 AliHLTTPCClusterTransformationComponent::AliHLTTPCClusterTransformationComponent()
52 :
53 fDataId(kFALSE),
54 fBenchmark("ClusterTransformation")
55 {
56   // see header file for class documentation
57   // or
58   // refer to README to build package
59   // or
60   // visit http://web.ift.uib.no/~kjeks/doc/alice-hlt  
61
62   fBenchmark.Reset();
63   fBenchmark.SetTimer(0,"total");
64 }
65
66 AliHLTTPCClusterTransformationComponent::~AliHLTTPCClusterTransformationComponent()
67
68   // destructor
69 }
70
71 const char* AliHLTTPCClusterTransformationComponent::GetComponentID() { 
72 // see header file for class documentation
73
74   return "TPCClusterTransformation";
75 }
76
77 void AliHLTTPCClusterTransformationComponent::GetInputDataTypes( vector<AliHLTComponentDataType>& list) { 
78   // see header file for class documentation
79
80   list.clear(); 
81   list.push_back( AliHLTTPCDefinitions::fgkRawClustersDataType  | kAliHLTDataOriginTPC  );
82   list.push_back(AliHLTTPCDefinitions::fgkAliHLTDataTypeClusterMCInfo | kAliHLTDataOriginTPC );
83 }
84
85 AliHLTComponentDataType AliHLTTPCClusterTransformationComponent::GetOutputDataType() { 
86   // see header file for class documentation
87
88   return kAliHLTMultipleDataType;
89 }
90
91 int AliHLTTPCClusterTransformationComponent::GetOutputDataTypes(AliHLTComponentDataTypeList& tgtList) { 
92   // see header file for class documentation
93
94   tgtList.clear();
95   tgtList.push_back(AliHLTTPCDefinitions::fgkClustersDataType| kAliHLTDataOriginTPC);
96   tgtList.push_back(AliHLTTPCDefinitions::fgkAliHLTDataTypeClusterMCInfo | kAliHLTDataOriginTPC );
97   return tgtList.size();
98 }
99
100 void AliHLTTPCClusterTransformationComponent::GetOutputDataSize( unsigned long& constBase, double& inputMultiplier ) { 
101   // see header file for class documentation
102   constBase = 0;
103   inputMultiplier = 2.0;
104 }
105
106 AliHLTComponent* AliHLTTPCClusterTransformationComponent::Spawn() { 
107   // see header file for class documentation
108
109   return new AliHLTTPCClusterTransformationComponent();
110 }
111         
112 int AliHLTTPCClusterTransformationComponent::DoInit( int argc, const char** argv ) 
113
114   // see header file for class documentation
115   
116   AliTPCcalibDB *calib=AliTPCcalibDB::Instance();  
117   if(!calib){
118     HLTError("AliTPCcalibDB does not exist");
119     return -ENOENT;
120   }
121   calib->SetRun(GetRunNo());
122   calib->UpdateRunInformations(GetRunNo());
123   
124   if( !fgTransform.IsInitialised() ){
125     int err = fgTransform.Init( GetBz(), GetTimeStamp() );
126     if( err!=0 ){
127       HLTError(Form("Cannot retrieve offline transform from AliTPCcalibDB, AliHLTTPCClusterTransformation returns %d",err));
128       return -ENOENT;
129     }
130   }
131
132   fDataId = kFALSE;
133
134   int iResult=0;
135   //!! iResult = ConfigureFromCDBTObjString(fgkOCDBEntryClusterTransformation);
136
137   if (iResult>=0 && argc>0)
138     iResult=ConfigureFromArgumentString(argc, argv);
139
140   return iResult;
141 } // end DoInit()
142
143 int AliHLTTPCClusterTransformationComponent::DoDeinit() { 
144   // see header file for class documentation   
145   fgTransform.DeInit();
146   return 0;
147 }
148
149 int AliHLTTPCClusterTransformationComponent::Reconfigure(const char* /*cdbEntry*/, const char* /*chainId*/) { 
150   // see header file for class documentation
151   fDataId = kFALSE;
152   return 0;//!! ConfigureFromCDBTObjString(fgkOCDBEntryClusterTransformation);
153 }
154
155 int AliHLTTPCClusterTransformationComponent::ScanConfigurationArgument(int argc, const char** argv){
156
157   // see header file for class documentation
158
159   if (argc<=0) return 0;
160   int i=0;
161   TString argument=argv[i];
162
163   if (argument.CompareTo("-change-dataId")==0){
164     HLTDebug("Change data ID received.");
165     fDataId = kTRUE;
166     return 1;
167   }
168   
169   HLTInfo("Unknown argument %s",argv[i]);
170
171   // unknown argument
172   return -EINVAL;
173 }
174
175
176 int AliHLTTPCClusterTransformationComponent::DoEvent(const AliHLTComponentEventData& evtData, 
177                                                   const AliHLTComponentBlockData* blocks, 
178                                                   AliHLTComponentTriggerData& /*trigData*/, AliHLTUInt8_t* outputPtr, 
179                                                   AliHLTUInt32_t& size, 
180                                                   vector<AliHLTComponentBlockData>& outputBlocks ){
181   // see header file for class documentation
182  
183   UInt_t maxOutSize = size;
184   size = 0;
185   int iResult = 0;
186   if(!IsDataEvent()) return 0;
187
188   if( !fgTransform.IsInitialised() ){
189     HLTError(" TPC Transformation is not initialised ");
190     return -ENOENT;    
191   }
192
193   fBenchmark.StartNewEvent();
194   fBenchmark.Start(0);
195
196   // Initialise the transformation here once more for the case of off-line reprocessing
197   if( !fgTimeInitialisedFromEvent ){
198     Long_t currentTime = static_cast<AliHLTUInt32_t>(time(NULL));
199     Long_t eventTimeStamp = GetTimeStamp();
200     if( TMath::Abs( fgTransform.GetCurrentTimeStamp() - eventTimeStamp )>60 && 
201         TMath::Abs( currentTime - eventTimeStamp)>60*60*5 ){
202       int err = fgTransform.SetCurrentTimeStamp( eventTimeStamp );
203       if( err!=0 ){
204         HLTError(Form("Cannot set time stamp, AliHLTTPCClusterTransformation returns %d",err));
205         return -ENOENT;
206       }
207     }
208     fgTimeInitialisedFromEvent = 1;
209   }
210
211   for( unsigned long ndx=0; ndx<evtData.fBlockCnt; ndx++ ){
212     
213     const AliHLTComponentBlockData *iter   = blocks+ndx;
214     
215     fBenchmark.AddInput(iter->fSize);
216     
217     HLTDebug("Event 0x%08LX (%Lu) received datatype: %s - required datatype: %s or $s",
218              evtData.fEventID, evtData.fEventID, 
219              DataType2Text( iter->fDataType).c_str(), 
220              DataType2Text(AliHLTTPCDefinitions::fgkRawClustersDataType).c_str(), DataType2Text(AliHLTTPCDefinitions::fgkAliHLTDataTypeClusterMCInfo).c_str());                       
221  
222     if(iter->fDataType == (AliHLTTPCDefinitions::fgkAliHLTDataTypeClusterMCInfo | kAliHLTDataOriginTPC) ){
223       // simply forward MC labels
224       
225       if( size+iter->fSize > maxOutSize ){
226         HLTWarning( "Output buffer (%db) is too small, required %db", maxOutSize, size+iter->fSize);
227         iResult  = -ENOSPC;
228         break;
229       }
230
231       memcpy( outputPtr, iter->fPtr, iter->fSize );
232       
233       AliHLTComponentBlockData bd;
234       FillBlockData( bd );
235       bd.fOffset = size;
236       bd.fSize = iter->fSize;
237       bd.fSpecification = iter->fSpecification;     
238       bd.fDataType = iter->fDataType;
239       outputBlocks.push_back( bd );     
240       fBenchmark.AddOutput(bd.fSize);    
241       size   += bd.fSize;
242       outputPtr += bd.fSize;
243       continue;
244     }
245
246     if(iter->fDataType != (AliHLTTPCDefinitions::fgkRawClustersDataType  | kAliHLTDataOriginTPC)) continue;                        
247         
248     UInt_t minSlice     = AliHLTTPCDefinitions::GetMinSliceNr(*iter); 
249     UInt_t minPartition = AliHLTTPCDefinitions::GetMinPatchNr(*iter);
250
251     float padpitch=1.0;
252     if ((int)minPartition<AliHLTTPCTransform::GetNRowLow())
253       padpitch=AliHLTTPCTransform::GetPadPitchWidthLow();
254     else
255       padpitch=AliHLTTPCTransform::GetPadPitchWidthUp();
256     float zwidth=AliHLTTPCTransform::GetZWidth();
257
258     fBenchmark.SetName(Form("ClusterTransform slice %d patch %d",minSlice,minPartition));
259
260     HLTDebug("minSlice: %d, minPartition: %d", minSlice, minPartition);
261     
262     AliHLTTPCRawClusterData* rawClusters = (AliHLTTPCRawClusterData*)(iter->fPtr);
263     if( !rawClusters ) continue;
264
265     AliHLTTPCClusterData* outPtr  = (AliHLTTPCClusterData*)outputPtr;
266     outPtr->fSpacePointCnt=0;
267
268     long maxPoints = ((long)maxOutSize-size-sizeof(AliHLTTPCClusterData))/sizeof(AliHLTTPCSpacePointData);
269   
270     if( rawClusters->fCount > maxPoints ){
271       HLTWarning("No more space to add clusters, exiting!");
272       iResult  = -ENOSPC;
273       break;
274     }
275   
276     for( UInt_t icl=0; icl<rawClusters->fCount; icl++){
277       
278       const AliHLTTPCRawCluster &cl = rawClusters->fClusters[icl];
279
280       AliHLTTPCSpacePointData& c=outPtr->fSpacePoints[outPtr->fSpacePointCnt];
281       int padrow=cl.GetPadRow();
282       if (padrow<0) {
283         // something wrong here, padrow is stored in the cluster header
284         // word which has bit pattern 0x3 in bits bit 30 and 31 which was
285         // not recognized
286         ALIHLTERRORGUARD(1, "can not read cluster header word");
287         break;
288       }
289       padrow+=AliHLTTPCTransform::GetFirstRow(minPartition);
290       AliHLTUInt32_t charge=cl.GetCharge();
291
292       float pad=cl.GetPad();
293       float time=cl.GetTime();
294       float sigmaY2=cl.GetSigmaY2();
295       float sigmaZ2=cl.GetSigmaZ2();
296       sigmaY2*=padpitch*padpitch;
297       sigmaZ2*=zwidth*zwidth;
298       c.SetPadRow(padrow);
299       c.SetCharge(charge);
300       c.SetSigmaY2(sigmaY2);
301       c.SetSigmaZ2(sigmaZ2);
302       c.SetQMax(cl.GetQMax());
303
304       Float_t xyz[3];
305       int err = fgTransform.Transform( minSlice, padrow, pad, time, xyz );       
306       if( err!=0 ){
307         HLTWarning(Form("Cannot transform the cluster, AliHLTTPCClusterTransformation returns error %d, %s",err, fgTransform.GetLastError()));
308         continue;
309       }
310       c.SetX(xyz[0]);
311       c.SetY(xyz[1]);
312       c.SetZ(xyz[2]);
313
314       // set the cluster ID so that the cluster dump printout is the same for FCF and SCF
315       c.SetID( minSlice, minPartition, outPtr->fSpacePointCnt );
316          
317       HLTDebug("Cluster number %d: %f, Y: %f, Z: %f, charge: %d \n", outPtr->fSpacePointCnt, cluster.fX, cluster.fY, cluster.fZ, (UInt_t)cluster.fCharge);
318          
319       outPtr->fSpacePointCnt++; 
320     } // end of loop over clusters
321       
322     HLTDebug("Number of found clusters: %d", outPtr->fSpacePointCnt);
323      
324     UInt_t mysize = sizeof(AliHLTTPCClusterData) + sizeof(AliHLTTPCSpacePointData)*outPtr->fSpacePointCnt;
325     
326     AliHLTComponentBlockData bd;
327     FillBlockData( bd );
328     bd.fOffset = size;
329     bd.fSize = mysize;
330     bd.fSpecification = iter->fSpecification;     
331     if(fDataId==kFALSE) bd.fDataType = AliHLTTPCDefinitions::fgkClustersDataType;
332     else                bd.fDataType = AliHLTTPCDefinitions::fgkAlterClustersDataType;
333     
334     //HLTDebug("datatype: %s", DataType2Text(bd.fDataType).c_str());
335      
336     outputBlocks.push_back( bd );
337      
338     fBenchmark.AddOutput(bd.fSize);    
339     size   += mysize;
340     outputPtr += mysize; 
341  
342   } // end of loop over data blocks  
343   
344   fBenchmark.Stop(0);
345   HLTInfo(fBenchmark.GetStatistics());
346   
347   return iResult;
348 } // end DoEvent()
349
350
351
352 void AliHLTTPCClusterTransformationComponent::GetOCDBObjectDescription( TMap* const targetMap)
353 {
354   // Get a list of OCDB object description needed for the particular component
355   if (!targetMap) return;
356   
357   // OCDB entries for component arguments
358
359   //!! targetMap->Add(new TObjString(fgkOCDBEntryClusterTransformation), new TObjString("component argument for the charge threshold"));
360   
361   // OCDB entries to be fetched by the TAXI (access via the AliTPCcalibDB class)
362   targetMap->Add(new TObjString("TPC/Calib/Parameters"),    new TObjString("unknown content"));
363   targetMap->Add(new TObjString("TPC/Calib/TimeDrift"),     new TObjString("drift velocity calibration"));
364   targetMap->Add(new TObjString("TPC/Calib/TimeGain"),     new TObjString("time gain  calibration"));
365   targetMap->Add(new TObjString("TPC/Calib/Temperature"),   new TObjString("temperature map"));
366   targetMap->Add(new TObjString("TPC/Calib/PadGainFactor"), new TObjString("gain factor pad by pad"));
367   targetMap->Add(new TObjString("TPC/Calib/ClusterParam"),  new TObjString("cluster parameters"));
368   targetMap->Add(new TObjString("TPC/Calib/Correction"),  new TObjString("coreection"));
369   targetMap->Add(new TObjString("TPC/Calib/RecoParam"),  new TObjString("reconstruction parameters"));
370  
371   // OCDB entries needed to be fetched by the Pendolino
372   targetMap->Add(new TObjString("TPC/Calib/AltroConfig"), new TObjString("contains the altro config, e.g. info about the L0 trigger timing"));
373   targetMap->Add(new TObjString("GRP/CTP/CTPtiming"),     new TObjString("content used in the cluster coordinate transformation in relation to the L0 trigger timing"));
374
375   // OCDB entries necessary for replaying data on the HLT cluster
376   targetMap->Add(new TObjString("GRP/GRP/Data"), new TObjString("contains magnetic field info"));  
377  
378   // OCDB entries needed to suppress fatals/errors/warnings during reconstruction
379   targetMap->Add(new TObjString("TPC/Calib/Distortion"),  new TObjString("distortion map"));
380   targetMap->Add(new TObjString("TPC/Calib/GainFactorDedx"), new TObjString("gain factor dedx"));
381   targetMap->Add(new TObjString("TPC/Calib/PadTime0"),    new TObjString("time0 offset pad by pad"));
382   targetMap->Add(new TObjString("TPC/Calib/PadNoise"),    new TObjString("pad noise values"));
383   targetMap->Add(new TObjString("TPC/Calib/Pedestals"),   new TObjString("pedestal info"));
384   targetMap->Add(new TObjString("TPC/Calib/Pulser"),      new TObjString("pulser info"));
385   targetMap->Add(new TObjString("TPC/Calib/CE"),          new TObjString("CE laser calibration result"));
386   targetMap->Add(new TObjString("TPC/Calib/Raw"),         new TObjString("unknown content"));
387   targetMap->Add(new TObjString("TPC/Calib/QA"),          new TObjString("not important"));
388   targetMap->Add(new TObjString("TPC/Calib/Mapping"),     new TObjString("unknown content"));
389   targetMap->Add(new TObjString("TPC/Calib/Goofie"),      new TObjString("Goofie values, not used at the moment (05.03.2010)"));
390   targetMap->Add(new TObjString("TPC/Calib/HighVoltage"), new TObjString("high voltage values, not used"));
391   targetMap->Add(new TObjString("TPC/Calib/Ref"),         new TObjString("unknown content"));
392 }