]>
Commit | Line | Data |
---|---|---|
a1408c4b | 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 | ||
a0b62fd1 | 19 | // @file AliHLTGlobalEsdConverterComponent.cxx |
20 | // @author Matthias Richter | |
21 | // @date | |
22 | // @brief Global ESD converter component. | |
23 | // | |
a1408c4b | 24 | |
25 | // see header file for class documentation | |
26 | // or | |
27 | // refer to README to build package | |
28 | // or | |
29 | // visit http://web.ift.uib.no/~kjeks/doc/alice-hlt | |
30 | ||
31 | #include <cassert> | |
32 | #include "AliHLTGlobalEsdConverterComponent.h" | |
33 | #include "AliHLTGlobalBarrelTrack.h" | |
34 | #include "AliHLTExternalTrackParam.h" | |
093b64dc | 35 | #include "AliHLTTrackMCLabel.h" |
6117ef63 | 36 | #include "AliHLTCTPData.h" |
331d51c5 | 37 | #include "AliHLTErrorGuard.h" |
a1408c4b | 38 | #include "AliESDEvent.h" |
39 | #include "AliESDtrack.h" | |
f064ef44 | 40 | #include "AliESDMuonTrack.h" |
fe0324de | 41 | #include "AliESDMuonCluster.h" |
a1408c4b | 42 | #include "AliCDBEntry.h" |
43 | #include "AliCDBManager.h" | |
18ada816 | 44 | #include "AliPID.h" |
a1408c4b | 45 | #include "TTree.h" |
46 | #include "TList.h" | |
f064ef44 | 47 | #include "TClonesArray.h" |
9a9467ed | 48 | #include "AliHLTESDCaloClusterMaker.h" |
49 | #include "AliHLTCaloClusterDataStruct.h" | |
50 | #include "AliHLTCaloClusterReader.h" | |
51 | #include "AliESDCaloCluster.h" | |
331d51c5 | 52 | #include "AliESDVZERO.h" |
d9386025 | 53 | #include "AliHLTGlobalVertexerComponent.h" |
b7449dbe | 54 | #include "AliHLTVertexFinderBase.h" |
a1408c4b | 55 | |
56 | /** ROOT macro for the implementation of ROOT specific class methods */ | |
57 | ClassImp(AliHLTGlobalEsdConverterComponent) | |
58 | ||
59 | AliHLTGlobalEsdConverterComponent::AliHLTGlobalEsdConverterComponent() | |
60 | : AliHLTProcessor() | |
a1408c4b | 61 | , fWriteTree(0) |
093b64dc | 62 | , fVerbosity(0) |
8b7a0f3c | 63 | , fESD(NULL) |
a8714ffa | 64 | , fSolenoidBz(-5.00668) |
57a4102f | 65 | , fBenchmark("EsdConverter") |
a1408c4b | 66 | { |
67 | // see header file for class documentation | |
68 | // or | |
69 | // refer to README to build package | |
70 | // or | |
71 | // visit http://web.ift.uib.no/~kjeks/doc/alice-hlt | |
72 | } | |
73 | ||
74 | AliHLTGlobalEsdConverterComponent::~AliHLTGlobalEsdConverterComponent() | |
75 | { | |
76 | // see header file for class documentation | |
77 | if (fESD) delete fESD; | |
78 | fESD=NULL; | |
79 | } | |
80 | ||
81 | int AliHLTGlobalEsdConverterComponent::Configure(const char* arguments) | |
82 | { | |
83 | // see header file for class documentation | |
84 | int iResult=0; | |
85 | if (!arguments) return iResult; | |
86 | ||
87 | TString allArgs=arguments; | |
88 | TString argument; | |
89 | int bMissingParam=0; | |
90 | ||
91 | TObjArray* pTokens=allArgs.Tokenize(" "); | |
92 | if (pTokens) { | |
93 | for (int i=0; i<pTokens->GetEntries() && iResult>=0; i++) { | |
d7d775b6 | 94 | argument=((TObjString*)pTokens->At(i))->String(); |
a1408c4b | 95 | if (argument.IsNull()) continue; |
96 | ||
97 | if (argument.CompareTo("-solenoidBz")==0) { | |
98 | if ((bMissingParam=(++i>=pTokens->GetEntries()))) break; | |
75970b8d | 99 | HLTWarning("argument -solenoidBz is deprecated, magnetic field set up globally (%f)", GetBz()); |
a1408c4b | 100 | continue; |
101 | } else { | |
102 | HLTError("unknown argument %s", argument.Data()); | |
103 | iResult=-EINVAL; | |
104 | break; | |
105 | } | |
106 | } | |
107 | delete pTokens; | |
108 | } | |
109 | if (bMissingParam) { | |
110 | HLTError("missing parameter for argument %s", argument.Data()); | |
111 | iResult=-EINVAL; | |
112 | } | |
113 | ||
114 | return iResult; | |
115 | } | |
116 | ||
117 | int AliHLTGlobalEsdConverterComponent::Reconfigure(const char* cdbEntry, const char* chainId) | |
118 | { | |
119 | // see header file for class documentation | |
120 | int iResult=0; | |
75970b8d | 121 | const char* path=NULL; |
a1408c4b | 122 | const char* defaultNotify=""; |
123 | if (cdbEntry) { | |
124 | path=cdbEntry; | |
125 | defaultNotify=" (default)"; | |
126 | } | |
127 | if (path) { | |
128 | HLTInfo("reconfigure from entry %s%s, chain id %s", path, defaultNotify,(chainId!=NULL && chainId[0]!=0)?chainId:"<none>"); | |
129 | AliCDBEntry *pEntry = AliCDBManager::Instance()->Get(path/*,GetRunNo()*/); | |
130 | if (pEntry) { | |
131 | TObjString* pString=dynamic_cast<TObjString*>(pEntry->GetObject()); | |
132 | if (pString) { | |
d7d775b6 | 133 | HLTInfo("received configuration object string: \'%s\'", pString->String().Data()); |
134 | iResult=Configure(pString->String().Data()); | |
a1408c4b | 135 | } else { |
136 | HLTError("configuration object \"%s\" has wrong type, required TObjString", path); | |
137 | } | |
138 | } else { | |
139 | HLTError("can not fetch object \"%s\" from CDB", path); | |
140 | } | |
141 | } | |
142 | ||
143 | return iResult; | |
144 | } | |
145 | ||
146 | void AliHLTGlobalEsdConverterComponent::GetInputDataTypes(AliHLTComponentDataTypeList& list) | |
147 | { | |
148 | // see header file for class documentation | |
149 | list.push_back(kAliHLTDataTypeTrack); | |
150 | list.push_back(kAliHLTDataTypeTrackMC); | |
9a9467ed | 151 | list.push_back(kAliHLTDataTypeCaloCluster); |
0973c527 | 152 | list.push_back(kAliHLTDataTypedEdx ); |
7f167a74 | 153 | list.push_back(kAliHLTDataTypeESDVertex ); |
f064ef44 | 154 | list.push_back(kAliHLTDataTypeESDObject); |
155 | list.push_back(kAliHLTDataTypeTObject); | |
d9963894 | 156 | list.push_back(kAliHLTDataTypeGlobalVertexer); |
b7449dbe | 157 | list.push_back(kAliHLTDataTypeV0Finder); // array of track ids for V0s |
158 | list.push_back(kAliHLTDataTypeKFVertex); // KFVertex object from vertexer | |
159 | list.push_back(kAliHLTDataTypePrimaryFinder); // array of track ids for prim vertex | |
331d51c5 | 160 | list.push_back(kAliHLTDataTypeESDContent); |
a1408c4b | 161 | } |
162 | ||
163 | AliHLTComponentDataType AliHLTGlobalEsdConverterComponent::GetOutputDataType() | |
164 | { | |
165 | // see header file for class documentation | |
7a9de6d1 | 166 | return kAliHLTDataTypeESDObject|kAliHLTDataOriginOut; |
a1408c4b | 167 | } |
168 | ||
169 | void AliHLTGlobalEsdConverterComponent::GetOutputDataSize(unsigned long& constBase, double& inputMultiplier) | |
170 | { | |
171 | // see header file for class documentation | |
172 | constBase=2000000; | |
173 | inputMultiplier=10.0; | |
174 | } | |
175 | ||
176 | int AliHLTGlobalEsdConverterComponent::DoInit(int argc, const char** argv) | |
177 | { | |
178 | // see header file for class documentation | |
179 | int iResult=0; | |
180 | TString argument=""; | |
181 | int bMissingParam=0; | |
a1408c4b | 182 | |
d57fc872 | 183 | // default list of skiped ESD objects |
184 | TString skipObjects= | |
185 | // "AliESDRun," | |
186 | // "AliESDHeader," | |
421e1221 | 187 | // "AliESDZDC," |
d57fc872 | 188 | "AliESDFMD," |
189 | // "AliESDVZERO," | |
190 | // "AliESDTZERO," | |
191 | // "TPCVertex," | |
192 | // "SPDVertex," | |
193 | // "PrimaryVertex," | |
194 | // "AliMultiplicity," | |
195 | // "PHOSTrigger," | |
196 | // "EMCALTrigger," | |
197 | // "SPDPileupVertices," | |
198 | // "TrkPileupVertices," | |
199 | "Cascades," | |
200 | "Kinks," | |
201 | "AliRawDataErrorLogs," | |
202 | "AliESDACORDE"; | |
203 | ||
f167b631 | 204 | iResult=Reconfigure(NULL, NULL); |
205 | TString allArgs = ""; | |
206 | for ( int i = 0; i < argc; i++ ) { | |
207 | if ( !allArgs.IsNull() ) allArgs += " "; | |
208 | allArgs += argv[i]; | |
209 | } | |
a1408c4b | 210 | |
f167b631 | 211 | TObjArray* pTokens=allArgs.Tokenize(" "); |
212 | if (pTokens) { | |
213 | for (int i=0; i<pTokens->GetEntries() && iResult>=0; i++) { | |
d7d775b6 | 214 | argument=((TObjString*)pTokens->At(i))->String(); |
f167b631 | 215 | if (argument.IsNull()) continue; |
216 | ||
217 | // -notree | |
218 | if (argument.CompareTo("-notree")==0) { | |
219 | fWriteTree=0; | |
220 | ||
221 | // -tree | |
222 | } else if (argument.CompareTo("-tree")==0) { | |
223 | fWriteTree=1; | |
224 | } else if (argument.CompareTo("-solenoidBz")==0) { | |
225 | if ((bMissingParam=(++i>=pTokens->GetEntries()))) break; | |
d7d775b6 | 226 | HLTInfo("Magnetic Field set to: %s", ((TObjString*)pTokens->At(i))->String().Data()); |
d57fc872 | 227 | HLTWarning("argument '-solenoidBz' is deprecated, solenoid field initiaized from CDB settings"); |
f167b631 | 228 | continue; |
d57fc872 | 229 | } else if (argument.Contains("-skipobject=")) { |
230 | argument.ReplaceAll("-skipobject=", ""); | |
231 | skipObjects=argument; | |
f167b631 | 232 | } else { |
233 | HLTError("unknown argument %s", argument.Data()); | |
d57fc872 | 234 | iResult=-EINVAL; |
f167b631 | 235 | break; |
236 | } | |
a1408c4b | 237 | } |
238 | } | |
239 | if (bMissingParam) { | |
240 | HLTError("missing parameter for argument %s", argument.Data()); | |
241 | iResult=-EINVAL; | |
242 | } | |
243 | ||
75970b8d | 244 | fSolenoidBz=GetBz(); |
245 | ||
a1408c4b | 246 | if (iResult>=0) { |
247 | fESD = new AliESDEvent; | |
248 | if (fESD) { | |
249 | fESD->CreateStdContent(); | |
d57fc872 | 250 | |
251 | // remove some of the objects which are not needed | |
252 | if (fESD->GetList() && !skipObjects.IsNull()) { | |
253 | pTokens=skipObjects.Tokenize(","); | |
254 | if (pTokens) { | |
255 | const char* id=NULL; | |
256 | TIter next(pTokens); | |
257 | TObject* pObject=NULL; | |
258 | while ((pObject=next())!=NULL) { | |
d7d775b6 | 259 | id=((TObjString*)pObject)->String().Data(); |
a0b62fd1 | 260 | TObject* pObj=fESD->GetList()->FindObject(id); |
261 | if (pObj) { | |
d57fc872 | 262 | HLTDebug("removing object %s", id); |
a0b62fd1 | 263 | fESD->GetList()->Remove(pObj); |
264 | delete pObj; | |
d57fc872 | 265 | } else { |
266 | HLTWarning("failed to remove object '%s' from ESD", id); | |
267 | } | |
268 | } | |
d57fc872 | 269 | fESD->GetStdContent(); |
270 | delete pTokens; | |
271 | } | |
272 | } | |
a1408c4b | 273 | } else { |
274 | iResult=-ENOMEM; | |
275 | } | |
6117ef63 | 276 | |
277 | SetupCTPData(); | |
a1408c4b | 278 | } |
279 | ||
57a4102f | 280 | fBenchmark.SetTimer(0,"total"); |
281 | ||
a1408c4b | 282 | return iResult; |
283 | } | |
284 | ||
285 | int AliHLTGlobalEsdConverterComponent::DoDeinit() | |
286 | { | |
287 | // see header file for class documentation | |
288 | if (fESD) delete fESD; | |
289 | fESD=NULL; | |
290 | ||
291 | return 0; | |
292 | } | |
293 | ||
294 | int AliHLTGlobalEsdConverterComponent::DoEvent(const AliHLTComponentEventData& /*evtData*/, | |
6117ef63 | 295 | AliHLTComponentTriggerData& trigData) |
a1408c4b | 296 | { |
297 | // see header file for class documentation | |
298 | int iResult=0; | |
299 | if (!fESD) return -ENODEV; | |
300 | ||
57a4102f | 301 | if (IsDataEvent()) fBenchmark.StartNewEvent(); |
302 | fBenchmark.Start(0); | |
303 | ||
a1408c4b | 304 | AliESDEvent* pESD = fESD; |
305 | ||
306 | pESD->Reset(); | |
307 | pESD->SetMagneticField(fSolenoidBz); | |
6117ef63 | 308 | pESD->SetRunNumber(GetRunNo()); |
6700298e | 309 | pESD->SetPeriodNumber(GetPeriodNumber()); |
310 | pESD->SetOrbitNumber(GetOrbitNumber()); | |
311 | pESD->SetBunchCrossNumber(GetBunchCrossNumber()); | |
312 | pESD->SetTimeStamp(GetTimeStamp()); | |
a1408c4b | 313 | |
6117ef63 | 314 | const AliHLTCTPData* pCTPData=CTPData(); |
315 | if (pCTPData) { | |
16e6f752 | 316 | AliHLTTriggerMask_t mask=pCTPData->ActiveTriggers(trigData); |
6117ef63 | 317 | for (int index=0; index<gkNCTPTriggerClasses; index++) { |
16e6f752 | 318 | if ((mask&(AliHLTTriggerMask_t(0x1)<<index)) == 0) continue; |
6117ef63 | 319 | pESD->SetTriggerClass(pCTPData->Name(index), index); |
320 | } | |
16e6f752 | 321 | //first 50 triggers |
322 | AliHLTTriggerMask_t mask50; | |
323 | mask50.set(); // set all bits | |
324 | mask50 >>= 50; // shift 50 right | |
325 | pESD->SetTriggerMask((mask&mask50).to_ulong()); | |
9eee9fe9 | 326 | //next 50 |
16e6f752 | 327 | pESD->SetTriggerMaskNext50((mask>>50).to_ulong()); |
6117ef63 | 328 | } |
329 | ||
a1408c4b | 330 | TTree* pTree = NULL; |
331 | if (fWriteTree) | |
332 | pTree = new TTree("esdTree", "Tree with HLT ESD objects"); | |
333 | ||
334 | if (pTree) { | |
335 | pTree->SetDirectory(0); | |
336 | } | |
337 | ||
81509fd3 | 338 | if ((iResult=ProcessBlocks(pTree, pESD))>=0) { |
a1408c4b | 339 | // TODO: set the specification correctly |
340 | if (pTree) { | |
341 | // the esd structure is written to the user info and is | |
342 | // needed in te ReadFromTree method to read all objects correctly | |
343 | pTree->GetUserInfo()->Add(pESD); | |
344 | pESD->WriteToTree(pTree); | |
7a9de6d1 | 345 | iResult=PushBack(pTree, kAliHLTDataTypeESDTree|kAliHLTDataOriginOut, 0); |
a1408c4b | 346 | } else { |
7a9de6d1 | 347 | iResult=PushBack(pESD, kAliHLTDataTypeESDObject|kAliHLTDataOriginOut, 0); |
a1408c4b | 348 | } |
57a4102f | 349 | fBenchmark.AddOutput(GetLastObjectSize()); |
a1408c4b | 350 | } |
351 | if (pTree) { | |
352 | // clear user info list to prevent objects from being deleted | |
353 | pTree->GetUserInfo()->Clear(); | |
354 | delete pTree; | |
355 | } | |
57a4102f | 356 | |
357 | fBenchmark.Stop(0); | |
358 | HLTInfo( fBenchmark.GetStatistics() ); | |
359 | ||
a1408c4b | 360 | return iResult; |
361 | } | |
362 | ||
363 | int AliHLTGlobalEsdConverterComponent::ProcessBlocks(TTree* pTree, AliESDEvent* pESD) | |
364 | { | |
365 | // see header file for class documentation | |
366 | ||
367 | int iResult=0; | |
368 | int iAddedDataBlocks=0; | |
369 | ||
b7449dbe | 370 | // check if there is an ESD block in the input and copy its content first to the |
371 | // ESD | |
372 | const TObject* pEsdObj = GetFirstInputObject(kAliHLTDataTypeESDObject, "AliESDEvent"); | |
373 | AliESDEvent* pInputESD=NULL; | |
374 | if (pEsdObj) pInputESD=dynamic_cast<AliESDEvent*>(const_cast<TObject*>(pEsdObj)); | |
375 | if (pInputESD) { | |
376 | pInputESD->GetStdContent(); | |
377 | *pESD=*pInputESD; | |
378 | } | |
379 | if (GetNextInputObject()!=NULL) { | |
380 | HLTWarning("handling of multiple ESD input objects not implemented, skipping input"); | |
381 | } | |
382 | ||
a1408c4b | 383 | // Barrel tracking |
e85f2e31 | 384 | // tracks are based on the TPC tracks, and only updated from the ITS information |
385 | // Sequence: | |
386 | // 1) extract MC information for TPC and ITS from specific data blocks and store in | |
387 | // intermediate vector arrays | |
388 | // 2) extract TPC tracks, update with MC labels if available, the track parameters | |
389 | // are estimated at the first cluster position | |
390 | // 2.1) propagate to last cluster position and update kTPCout, sets also outer param (fOp) | |
391 | // 2.2) update kTPCin, sets also inner param (fIp) and TPC inner param (fTPCInner) | |
392 | // 2.3) update kTPCrefit using the same parameters at the first cluster position | |
393 | // HLT has strictly spoking no refit, but we want the flag to be set | |
394 | // can be changed to be done after all the individual barrel detector parameters | |
395 | // have been updated by looping over the tracks again | |
396 | // 3) extract ITS tracks, the tracks are actually TPC tracks updated from the ITS | |
397 | // tracking information | |
398 | // 3.1) TODO 2010-07-12: handle ITS standalone tracks by updating kITSout before kITSin | |
399 | // 3.2) update with kITSin | |
400 | // TODO 2010-07-12 find out if the kITSrefit has to be set as well | |
401 | // 4) extract TRD tracks and add to ESD | |
402 | // TODO 2010-07-12 at the moment there is no matching or merging of TPC and TRD tracks | |
331d51c5 | 403 | // 5) Add Trigger Detectors |
404 | // VZERO, ZDC | |
e85f2e31 | 405 | |
406 | // 1) first read MC information (if present) | |
eb60b0c1 | 407 | std::map<int,int> mcLabelsTPC; |
d72d9d99 | 408 | std::map<int,int> mcLabelsITS; |
093b64dc | 409 | |
410 | for (const AliHLTComponentBlockData* pBlock=GetFirstInputBlock(kAliHLTDataTypeTrackMC|kAliHLTDataOriginTPC); | |
411 | pBlock!=NULL; pBlock=GetNextInputBlock()) { | |
57a4102f | 412 | |
413 | fBenchmark.AddInput(pBlock->fSize); | |
414 | ||
093b64dc | 415 | AliHLTTrackMCData* dataPtr = reinterpret_cast<AliHLTTrackMCData*>( pBlock->fPtr ); |
416 | if (sizeof(AliHLTTrackMCData)+dataPtr->fCount*sizeof(AliHLTTrackMCLabel)==pBlock->fSize) { | |
417 | for( unsigned int il=0; il<dataPtr->fCount; il++ ){ | |
418 | AliHLTTrackMCLabel &lab = dataPtr->fLabels[il]; | |
eb60b0c1 | 419 | mcLabelsTPC[lab.fTrackID] = lab.fMCLabel; |
093b64dc | 420 | } |
421 | } else { | |
422 | HLTWarning("data mismatch in block %s (0x%08x): count %d, size %d -> ignoring track MC information", | |
423 | DataType2Text(pBlock->fDataType).c_str(), pBlock->fSpecification, | |
424 | dataPtr->fCount, pBlock->fSize); | |
425 | } | |
426 | } | |
d72d9d99 | 427 | |
428 | for (const AliHLTComponentBlockData* pBlock=GetFirstInputBlock(kAliHLTDataTypeTrackMC|kAliHLTDataOriginITS); | |
429 | pBlock!=NULL; pBlock=GetNextInputBlock()) { | |
430 | ||
431 | fBenchmark.AddInput(pBlock->fSize); | |
432 | ||
433 | AliHLTTrackMCData* dataPtr = reinterpret_cast<AliHLTTrackMCData*>( pBlock->fPtr ); | |
434 | if (sizeof(AliHLTTrackMCData)+dataPtr->fCount*sizeof(AliHLTTrackMCLabel)==pBlock->fSize) { | |
435 | for( unsigned int il=0; il<dataPtr->fCount; il++ ){ | |
436 | AliHLTTrackMCLabel &lab = dataPtr->fLabels[il]; | |
437 | mcLabelsITS[lab.fTrackID] = lab.fMCLabel; | |
438 | } | |
439 | } else { | |
440 | HLTWarning("data mismatch in block %s (0x%08x): count %d, size %d -> ignoring track MC information", | |
441 | DataType2Text(pBlock->fDataType).c_str(), pBlock->fSpecification, | |
442 | dataPtr->fCount, pBlock->fSize); | |
443 | } | |
444 | } | |
445 | ||
093b64dc | 446 | |
0973c527 | 447 | // read dEdx information (if present) |
e85f2e31 | 448 | // TODO 2010-07-12 this needs to be verified |
0973c527 | 449 | |
450 | AliHLTFloat32_t *dEdxTPC = 0; | |
451 | Int_t ndEdxTPC = 0; | |
452 | for (const AliHLTComponentBlockData* pBlock=GetFirstInputBlock(kAliHLTDataTypedEdx|kAliHLTDataOriginTPC); | |
e38918a2 | 453 | pBlock!=NULL; pBlock=NULL/*GetNextInputBlock() there is only one block*/) { |
57a4102f | 454 | fBenchmark.AddInput(pBlock->fSize); |
0973c527 | 455 | dEdxTPC = reinterpret_cast<AliHLTFloat32_t*>( pBlock->fPtr ); |
72a916d9 | 456 | ndEdxTPC = pBlock->fSize / (3*sizeof(AliHLTFloat32_t)); |
0973c527 | 457 | } |
458 | ||
e85f2e31 | 459 | // 2) convert the TPC tracks to ESD tracks |
a1408c4b | 460 | for (const AliHLTComponentBlockData* pBlock=GetFirstInputBlock(kAliHLTDataTypeTrack|kAliHLTDataOriginTPC); |
461 | pBlock!=NULL; pBlock=GetNextInputBlock()) { | |
b7449dbe | 462 | if (pInputESD && pInputESD->GetNumberOfTracks()>0) { |
463 | HLTWarning("Tracks array already filled from the input esd block, additional filling from TPC tracks block might cause inconsistent content"); | |
464 | } | |
57a4102f | 465 | fBenchmark.AddInput(pBlock->fSize); |
a1408c4b | 466 | vector<AliHLTGlobalBarrelTrack> tracks; |
81509fd3 | 467 | if ((iResult=AliHLTGlobalBarrelTrack::ConvertTrackDataArray(reinterpret_cast<const AliHLTTracksData*>(pBlock->fPtr), pBlock->fSize, tracks))>=0) { |
a1408c4b | 468 | for (vector<AliHLTGlobalBarrelTrack>::iterator element=tracks.begin(); |
469 | element!=tracks.end(); element++) { | |
470 | Float_t points[4] = { | |
2cb809a5 | 471 | static_cast<Float_t>(element->GetX()), |
472 | static_cast<Float_t>(element->GetY()), | |
473 | static_cast<Float_t>(element->GetLastPointX()), | |
474 | static_cast<Float_t>(element->GetLastPointY()) | |
a1408c4b | 475 | }; |
093b64dc | 476 | |
477 | Int_t mcLabel = -1; | |
eb60b0c1 | 478 | if( mcLabelsTPC.find(element->TrackID())!=mcLabelsTPC.end() ) |
479 | mcLabel = mcLabelsTPC[element->TrackID()]; | |
093b64dc | 480 | element->SetLabel( mcLabel ); |
481 | ||
a1408c4b | 482 | AliESDtrack iotrack; |
550ecaab | 483 | |
484 | // for the moment, the number of clusters are not set when processing the | |
485 | // kTPCin update, only at kTPCout | |
486 | // there ar emainly three parameters updated for kTPCout | |
487 | // number of clusters | |
488 | // chi2 | |
489 | // pid signal | |
490 | // The first one can be updated already at that stage here, while the two others | |
491 | // eventually require to update from the ITS tracks before. The exact scheme | |
ab700b08 | 492 | // needs to be checked |
c3261a7d | 493 | iotrack.SetID( element->TrackID() ); |
e85f2e31 | 494 | |
495 | // 2.1 set kTPCout | |
496 | // TODO 2010-07-12 disabled for the moment because of bug | |
497 | // https://savannah.cern.ch/bugs/index.php?69875 | |
498 | // the propagation does not work, there is an offset in z | |
499 | // propagate to last cluster and update parameters with flag kTPCout | |
500 | // Note: updating with flag kITSout further down will overwrite the outer | |
501 | // parameter again so this can be done only for ITS standalone tracks, meaning | |
502 | // tracks in the ITS not associated with any TPC track | |
503 | // HLT does not provide such standalone tracking | |
c3261a7d | 504 | { |
f167b631 | 505 | AliHLTGlobalBarrelTrack outPar(*element); |
114e074b | 506 | //outPar.AliExternalTrackParam::PropagateTo( element->GetLastPointX(), fSolenoidBz ); |
507 | const Int_t N=10; // number of steps. | |
508 | const Float_t xRange = element->GetLastPointX() - element->GetX(); | |
509 | const Float_t xStep = xRange / N ; | |
510 | for(int i = 1; i <= N; ++i) { | |
511 | if(!outPar.AliExternalTrackParam::PropagateTo(element->GetX() + xStep * i, fSolenoidBz)) break; | |
512 | } | |
b9838c05 | 513 | outPar.SetLabel(element->GetLabel()); |
114e074b | 514 | iotrack.UpdateTrackParams(&outPar,AliESDtrack::kTPCout); |
c3261a7d | 515 | } |
e85f2e31 | 516 | // 2.2 TPC tracking estimates parameters at first cluster |
ab700b08 | 517 | iotrack.UpdateTrackParams(&(*element),AliESDtrack::kTPCin); |
e85f2e31 | 518 | |
519 | // 2.3 use the same parameters also for kTPCrefit, there is no proper refit in HLT | |
520 | // maybe this can be done later, however also the inner parameter is changed which | |
521 | // is used as a reference point in the display. That point should be at the first | |
522 | // TPC cluster | |
523 | iotrack.UpdateTrackParams(&(*element),AliESDtrack::kTPCrefit); | |
a1408c4b | 524 | iotrack.SetTPCPoints(points); |
0973c527 | 525 | if( element->TrackID()<ndEdxTPC ){ |
72a916d9 | 526 | AliHLTFloat32_t *val = &(dEdxTPC[3*element->TrackID()]); |
5c2dca91 | 527 | iotrack.SetTPCsignal( val[0], val[1], (UChar_t) val[2] ); |
7e32fedf | 528 | //AliTPCseed s; |
529 | //s.Set( element->GetX(), element->GetAlpha(), | |
530 | //element->GetParameter(), element->GetCovariance() ); | |
72a916d9 | 531 | //s.SetdEdx( val[0] ); |
7e32fedf | 532 | //s.CookPID(); |
533 | //iotrack.SetTPCpid(s.TPCrPIDs() ); | |
0973c527 | 534 | } else { |
535 | if( dEdxTPC ) HLTWarning("Wrong number of dEdx TPC labels"); | |
536 | } | |
b9838c05 | 537 | iotrack.SetLabel(mcLabel); |
7fd2e09c | 538 | pESD->AddTrack(&iotrack); |
093b64dc | 539 | if (fVerbosity>0) element->Print(); |
a1408c4b | 540 | } |
093b64dc | 541 | HLTInfo("converted %d track(s) to AliESDtrack and added to ESD", tracks.size()); |
a1408c4b | 542 | iAddedDataBlocks++; |
543 | } else if (iResult<0) { | |
093b64dc | 544 | HLTError("can not extract tracks from data block of type %s (specification %08x) of size %d: error %d", |
545 | DataType2Text(pBlock->fDataType).c_str(), pBlock->fSpecification, pBlock->fSize, iResult); | |
a1408c4b | 546 | } |
547 | } | |
548 | ||
7f167a74 | 549 | |
550 | // Get ITS SPD vertex | |
57a4102f | 551 | for( const AliHLTComponentBlockData *i= GetFirstInputBlock(kAliHLTDataTypeESDVertex|kAliHLTDataOriginITS); i!=NULL; i=GetNextInputBlock() ){ |
552 | fBenchmark.AddInput(i->fSize); | |
553 | } | |
7f167a74 | 554 | |
555 | for ( const TObject *iter = GetFirstInputObject(kAliHLTDataTypeESDVertex|kAliHLTDataOriginITS); iter != NULL; iter = GetNextInputObject() ) { | |
556 | AliESDVertex *vtx = dynamic_cast<AliESDVertex*>(const_cast<TObject*>( iter ) ); | |
557 | pESD->SetPrimaryVertexSPD( vtx ); | |
558 | } | |
559 | ||
e85f2e31 | 560 | // 3.1. now update ESD tracks with the ITSOut info |
561 | // updating track parameters with flag kITSout will overwrite parameter set above with flag kTPCout | |
562 | // TODO 2010-07-12 there are some issues with this updating sequence, for the moment update with | |
563 | // flag kITSout is disabled, would require | |
564 | // a) to update kTPCout after kITSout | |
565 | // b) update only for ITS standalone tracks. The HLT ITS tracker does not provide standalone | |
566 | // tracking, every track is related to a TPC track | |
567 | // Furthermore there seems to be a bug as the data blocks describe track parameters around the | |
568 | // vertex, not at the outer ITS | |
569 | // bug https://savannah.cern.ch/bugs/index.php?69872 | |
f167b631 | 570 | for (const AliHLTComponentBlockData* pBlock=GetFirstInputBlock(kAliHLTDataTypeTrack|kAliHLTDataOriginITSOut); |
cd60a73f | 571 | pBlock!=NULL; pBlock=GetNextInputBlock()) { |
57a4102f | 572 | fBenchmark.AddInput(pBlock->fSize); |
cd60a73f | 573 | vector<AliHLTGlobalBarrelTrack> tracks; |
574 | if ((iResult=AliHLTGlobalBarrelTrack::ConvertTrackDataArray(reinterpret_cast<const AliHLTTracksData*>(pBlock->fPtr), pBlock->fSize, tracks))>0) { | |
575 | for (vector<AliHLTGlobalBarrelTrack>::iterator element=tracks.begin(); | |
576 | element!=tracks.end(); element++) { | |
cd60a73f | 577 | int tpcID=element->TrackID(); |
578 | // the ITS tracker assigns the TPC track used as seed for a certain track to | |
579 | // the trackID | |
580 | if( tpcID<0 || tpcID>=pESD->GetNumberOfTracks()) continue; | |
cd60a73f | 581 | AliESDtrack *tESD = pESD->GetTrack( tpcID ); |
b9838c05 | 582 | element->SetLabel(tESD->GetLabel()); |
e85f2e31 | 583 | // 2010-07-12 disabled, see above, bugfix https://savannah.cern.ch/bugs/index.php?69872 |
584 | //if( tESD ) tESD->UpdateTrackParams( &(*element), AliESDtrack::kITSout ); | |
a1408c4b | 585 | } |
cd60a73f | 586 | } |
587 | } | |
18ada816 | 588 | |
e85f2e31 | 589 | // 3.2. now update ESD tracks with the ITS info |
f167b631 | 590 | for (const AliHLTComponentBlockData* pBlock=GetFirstInputBlock(kAliHLTDataTypeTrack|kAliHLTDataOriginITS); |
b7ed2eb4 | 591 | pBlock!=NULL; pBlock=GetNextInputBlock()) { |
57a4102f | 592 | fBenchmark.AddInput(pBlock->fSize); |
b7ed2eb4 | 593 | vector<AliHLTGlobalBarrelTrack> tracks; |
594 | if ((iResult=AliHLTGlobalBarrelTrack::ConvertTrackDataArray(reinterpret_cast<const AliHLTTracksData*>(pBlock->fPtr), pBlock->fSize, tracks))>0) { | |
595 | for (vector<AliHLTGlobalBarrelTrack>::iterator element=tracks.begin(); | |
596 | element!=tracks.end(); element++) { | |
b7ed2eb4 | 597 | int tpcID=element->TrackID(); |
598 | // the ITS tracker assigns the TPC track used as seed for a certain track to | |
599 | // the trackID | |
600 | if( tpcID<0 || tpcID>=pESD->GetNumberOfTracks()) continue; | |
d72d9d99 | 601 | Int_t mcLabel = -1; |
602 | if( mcLabelsITS.find(element->TrackID())!=mcLabelsITS.end() ) | |
603 | mcLabel = mcLabelsITS[element->TrackID()]; | |
b7ed2eb4 | 604 | AliESDtrack *tESD = pESD->GetTrack( tpcID ); |
b9838c05 | 605 | if (!tESD) continue; |
eb60b0c1 | 606 | // the labels for the TPC and ITS tracking params can be different, e.g. |
607 | // there can be a decay. The ITS label should then be the better one, the | |
608 | // TPC label is saved in a member of AliESDtrack | |
609 | if (mcLabel>=0) { | |
610 | // upadte only if the ITS label is available, otherwise keep TPC label | |
611 | element->SetLabel( mcLabel ); | |
e85f2e31 | 612 | } else { |
613 | // bugfix https://savannah.cern.ch/bugs/?69713 | |
614 | element->SetLabel( tESD->GetLabel() ); | |
b9838c05 | 615 | } |
b9838c05 | 616 | tESD->UpdateTrackParams( &(*element), AliESDtrack::kITSin ); |
617 | ||
618 | // TODO: add a proper refit | |
619 | //tESD->UpdateTrackParams( &(*element), AliESDtrack::kTPCrefit ); | |
b7ed2eb4 | 620 | } |
621 | } | |
622 | } | |
623 | ||
d9386025 | 624 | // update with vertices and vertex-fitted tracks |
b7449dbe | 625 | // output of the GlobalVertexerComponent |
d9386025 | 626 | for (const AliHLTComponentBlockData* pBlock=GetFirstInputBlock(kAliHLTDataTypeGlobalVertexer); |
627 | pBlock!=NULL; pBlock=GetNextInputBlock()) { | |
57a4102f | 628 | fBenchmark.AddInput(pBlock->fSize); |
d9386025 | 629 | AliHLTGlobalVertexerComponent::FillESD( pESD, reinterpret_cast<AliHLTGlobalVertexerComponent::AliHLTGlobalVertexerData* >(pBlock->fPtr) ); |
630 | } | |
631 | ||
b7449dbe | 632 | // update with vertices and vertex-fitted tracks |
633 | // output of PrimaryVertexer and V0Finder components | |
634 | TObject* pBase = (TObject*)GetFirstInputObject(kAliHLTDataTypeKFVertex | kAliHLTDataOriginOut); | |
635 | if (pBase) { | |
636 | AliKFVertex* kfVertex = dynamic_cast<AliKFVertex *>(pBase); | |
637 | if (kfVertex) { | |
638 | const AliHLTComponentBlockData* pP = GetFirstInputBlock(kAliHLTDataTypePrimaryFinder | kAliHLTDataOriginOut); | |
639 | if (pP && pP->fSize && pP->fPtr) { | |
640 | const AliHLTComponentBlockData* pV0 = GetFirstInputBlock(kAliHLTDataTypeV0Finder | kAliHLTDataOriginOut); | |
641 | if (pV0 && pV0->fPtr && pInputESD && pInputESD->GetNumberOfV0s()>0) { | |
642 | const int* v0s = static_cast<const int*>(pV0->fPtr); | |
643 | HLTWarning("V0 array already filled from the input esd block, additional filling from V0 block of %d entries might cause inconsistent content", v0s[0]); | |
644 | } | |
645 | AliHLTVertexFinderBase::FillESD(pESD, kfVertex, pP->fPtr, pV0?pV0->fPtr:NULL); | |
646 | } else | |
647 | HLTWarning("Problem with primary finder's data block"); | |
648 | } else { | |
649 | HLTWarning("primary vertex block of wrong type, expecting AliKFVertex instead of %s", pBase->GetName()); | |
650 | } | |
651 | } else { | |
652 | // throw an error if there is a V0 data block which can not be handled without | |
653 | // the AliKFVertex object | |
654 | if (GetFirstInputBlock(kAliHLTDataTypeV0Finder | kAliHLTDataOriginOut)!=NULL) { | |
655 | ALIHLTERRORGUARD(1, "missing AliKFVertex object ignoring V0 data block of type %s", | |
656 | DataType2Text(kAliHLTDataTypeV0Finder|kAliHLTDataOriginOut).c_str()); | |
657 | } | |
658 | } | |
659 | ||
0d2e4e41 | 660 | // Fill DCA parameters for TPC tracks |
e85f2e31 | 661 | // TODO 2010-07-12 this propagates also the TPC inner param to beamline |
662 | // sounds not very reasonable | |
663 | // https://savannah.cern.ch/bugs/index.php?69873 | |
7fd2e09c | 664 | for (int i=0; i<pESD->GetNumberOfTracks(); i++) { |
0d2e4e41 | 665 | if (!pESD->GetTrack(i) || |
666 | !pESD->GetTrack(i)->GetTPCInnerParam() ) continue; | |
7fd2e09c | 667 | pESD->GetTrack(i)->RelateToVertexTPC(pESD->GetPrimaryVertexTracks(), fSolenoidBz, 1000 ); |
0d2e4e41 | 668 | } |
669 | ||
b9838c05 | 670 | // loop over all tracks and set the TPC refit flag by updating with the |
671 | // original TPC inner parameter if not yet set | |
672 | // TODO: replace this by a proper refit | |
673 | // code is comented for the moment as it does not fully solve the problems with | |
674 | // the display | |
e85f2e31 | 675 | // - would set the main parameters to the TPC inner wall again, or |
676 | // - changes the inner param if the parameters are propagated, so we loose the track | |
677 | // reference point for the display | |
678 | // with the current sequence we have the latter case as the DCA operations above | |
679 | // change the TPC inner parameters | |
b9838c05 | 680 | /* |
681 | for (int i=0; i<pESD->GetNumberOfTracks(); i++) { | |
682 | if (!pESD->GetTrack(i) || | |
683 | !pESD->GetTrack(i)->GetTPCInnerParam() || | |
684 | pESD->GetTrack(i)->IsOn(AliESDtrack::kTPCrefit)) continue; | |
685 | AliESDtrack* tESD=pESD->GetTrack(i); | |
686 | AliHLTGlobalBarrelTrack inner(*tESD->GetTPCInnerParam()); | |
687 | inner.SetLabel(tESD->GetLabel()); | |
688 | tESD->UpdateTrackParams(&inner, AliESDtrack::kTPCrefit); | |
689 | } | |
690 | */ | |
b7ed2eb4 | 691 | |
e85f2e31 | 692 | // 4. convert the HLT TRD tracks to ESD tracks |
18ada816 | 693 | for (const AliHLTComponentBlockData* pBlock=GetFirstInputBlock(kAliHLTDataTypeTrack | kAliHLTDataOriginTRD); |
694 | pBlock!=NULL; pBlock=GetNextInputBlock()) { | |
57a4102f | 695 | fBenchmark.AddInput(pBlock->fSize); |
18ada816 | 696 | vector<AliHLTGlobalBarrelTrack> tracks; |
697 | if ((iResult=AliHLTGlobalBarrelTrack::ConvertTrackDataArray(reinterpret_cast<const AliHLTTracksData*>(pBlock->fPtr), pBlock->fSize, tracks))>0) { | |
698 | for (vector<AliHLTGlobalBarrelTrack>::iterator element=tracks.begin(); | |
699 | element!=tracks.end(); element++) { | |
700 | ||
701 | Double_t TRDpid[AliPID::kSPECIES], eProb(0.2), restProb((1-eProb)/(AliPID::kSPECIES-1)); //eprob(element->GetTRDpid...); | |
702 | for(Int_t i=0; i<AliPID::kSPECIES; i++){ | |
703 | switch(i){ | |
704 | case AliPID::kElectron: TRDpid[AliPID::kElectron]=eProb; break; | |
705 | default: TRDpid[i]=restProb; break; | |
706 | } | |
707 | } | |
708 | ||
709 | AliESDtrack iotrack; | |
0d096bba | 710 | iotrack.UpdateTrackParams(&(*element),AliESDtrack::kTRDout); |
0b745718 | 711 | iotrack.SetStatus(AliESDtrack::kTRDin); |
18ada816 | 712 | iotrack.SetTRDpid(TRDpid); |
713 | ||
714 | pESD->AddTrack(&iotrack); | |
715 | if (fVerbosity>0) element->Print(); | |
716 | } | |
717 | HLTInfo("converted %d track(s) to AliESDtrack and added to ESD", tracks.size()); | |
718 | iAddedDataBlocks++; | |
719 | } else if (iResult<0) { | |
720 | HLTError("can not extract tracks from data block of type %s (specification %08x) of size %d: error %d", | |
721 | DataType2Text(pBlock->fDataType).c_str(), pBlock->fSpecification, pBlock->fSize, iResult); | |
722 | } | |
723 | } | |
b4479a87 | 724 | for (const AliHLTComponentBlockData* pBlock=GetFirstInputBlock(kAliHLTDataTypeCaloCluster | kAliHLTDataOriginAny); pBlock!=NULL; pBlock=GetNextInputBlock()) |
9a9467ed | 725 | { |
57a4102f | 726 | fBenchmark.AddInput(pBlock->fSize); |
9a9467ed | 727 | AliHLTCaloClusterHeaderStruct *caloClusterHeaderPtr = reinterpret_cast<AliHLTCaloClusterHeaderStruct*>(pBlock->fPtr); |
728 | ||
729 | HLTDebug("%d HLT clusters from spec: 0x%X", caloClusterHeaderPtr->fNClusters, pBlock->fSpecification); | |
730 | ||
2a24cbbe | 731 | //AliHLTCaloClusterReader reader; |
732 | //reader.SetMemory(caloClusterHeaderPtr); | |
9a9467ed | 733 | |
734 | AliHLTESDCaloClusterMaker clusterMaker; | |
735 | ||
736 | int nClusters = clusterMaker.FillESD(pESD, caloClusterHeaderPtr); | |
2a24cbbe | 737 | |
9a9467ed | 738 | HLTInfo("converted %d cluster(s) to AliESDCaloCluster and added to ESD", nClusters); |
739 | iAddedDataBlocks++; | |
740 | } | |
f064ef44 | 741 | |
331d51c5 | 742 | // 5) Add Trigger Detectors |
743 | // VZERO, ZDC | |
744 | ||
745 | // FIXME: the size of all input blocks can be added in one loop | |
746 | for (const AliHLTComponentBlockData* pBlock=GetFirstInputBlock(kAliHLTDataTypeESDContent|kAliHLTDataOriginVZERO); | |
747 | pBlock!=NULL; pBlock=GetNextInputBlock()) { | |
748 | fBenchmark.AddInput(pBlock->fSize); | |
749 | } | |
750 | ||
751 | for ( const TObject *pObject = GetFirstInputObject(kAliHLTDataTypeESDContent|kAliHLTDataOriginVZERO); | |
752 | pObject != NULL; pObject = GetNextInputObject() ) { | |
753 | AliESDVZERO *esdVZERO = dynamic_cast<AliESDVZERO*>(const_cast<TObject*>( pObject ) ); | |
754 | if (esdVZERO) { | |
755 | pESD->SetVZEROData( esdVZERO ); | |
756 | break; | |
757 | } else { | |
758 | ALIHLTERRORGUARD(1, "input object of data type %s is not of class AliESDVZERO", | |
759 | DataType2Text(kAliHLTDataTypeESDContent|kAliHLTDataOriginVZERO).c_str()); | |
760 | } | |
761 | } | |
762 | ||
421e1221 | 763 | // FIXME: the size of all input blocks can be added in one loop |
764 | for (const AliHLTComponentBlockData* pBlock=GetFirstInputBlock(kAliHLTDataTypeESDContent|kAliHLTDataOriginZDC); | |
765 | pBlock!=NULL; pBlock=GetNextInputBlock()) { | |
766 | fBenchmark.AddInput(pBlock->fSize); | |
767 | } | |
768 | for ( const TObject *pObject = GetFirstInputObject(kAliHLTDataTypeESDContent|kAliHLTDataOriginZDC); | |
769 | pObject != NULL; pObject = GetNextInputObject() ) { | |
770 | AliESDZDC *esdZDC = dynamic_cast<AliESDZDC*>(const_cast<TObject*>( pObject ) ); | |
771 | if (esdZDC) { | |
8cd67fda | 772 | #ifndef HAVE_NOT_ALIZDCRECONSTRUCTOR_r43770 |
421e1221 | 773 | pESD->SetZDCData( esdZDC ); |
8cd67fda | 774 | #else |
775 | ALIHLTERRORGUARD(1, "Processing of ZDC data requires AliRoot r43770m skipping data block of type %s", | |
776 | DataType2Text(kAliHLTDataTypeESDContent|kAliHLTDataOriginZDC).c_str()); | |
777 | #endif | |
421e1221 | 778 | break; |
779 | } else { | |
780 | ALIHLTERRORGUARD(1, "input object of data type %s is not of class AliESDZDC", | |
781 | DataType2Text(kAliHLTDataTypeESDContent|kAliHLTDataOriginZDC).c_str()); | |
782 | } | |
783 | } | |
784 | ||
fe0324de | 785 | // Add tracks and clusters from MUON. |
57a4102f | 786 | for( const AliHLTComponentBlockData *i= GetFirstInputBlock(kAliHLTAnyDataType | kAliHLTDataOriginMUON); i!=NULL; i=GetNextInputBlock() ){ |
787 | fBenchmark.AddInput(i->fSize); | |
788 | } | |
789 | ||
f064ef44 | 790 | for (const TObject* obj = GetFirstInputObject(kAliHLTAnyDataType | kAliHLTDataOriginMUON); |
791 | obj != NULL; | |
792 | obj = GetNextInputObject() | |
793 | ) | |
794 | { | |
795 | const TClonesArray* tracklist = NULL; | |
fe0324de | 796 | const TClonesArray* clusterlist = NULL; |
f064ef44 | 797 | if (obj->IsA() == AliESDEvent::Class()) |
798 | { | |
799 | const AliESDEvent* event = static_cast<const AliESDEvent*>(obj); | |
800 | HLTDebug("Received a MUON ESD with specification: 0x%X", GetSpecification(obj)); | |
801 | if (event->GetList() == NULL) continue; | |
802 | tracklist = dynamic_cast<const TClonesArray*>(event->GetList()->FindObject("MuonTracks")); | |
803 | if (tracklist == NULL) continue; | |
fe0324de | 804 | clusterlist = dynamic_cast<const TClonesArray*>(event->GetList()->FindObject("MuonClusters")); |
805 | if (clusterlist == NULL) continue; | |
f064ef44 | 806 | } |
807 | else if (obj->IsA() == TClonesArray::Class()) | |
808 | { | |
fe0324de | 809 | if (!strcmp(obj->GetName(), "MuonTracks")) { |
810 | tracklist = static_cast<const TClonesArray*>(obj); | |
811 | HLTDebug("Received a MUON TClonesArray of tracks with specification: 0x%X", GetSpecification(obj)); | |
812 | } else { | |
813 | clusterlist = static_cast<const TClonesArray*>(obj); | |
814 | HLTDebug("Received a MUON TClonesArray of clusters with specification: 0x%X", GetSpecification(obj)); | |
815 | } | |
f064ef44 | 816 | } |
817 | else | |
818 | { | |
819 | // Cannot handle this object type. | |
820 | continue; | |
821 | } | |
fe0324de | 822 | // copy tracks |
823 | if (tracklist) { | |
824 | HLTDebug("Received %d MUON tracks.", tracklist->GetEntriesFast()); | |
825 | if (tracklist->GetEntriesFast() > 0) | |
826 | { | |
827 | const AliESDMuonTrack* track = dynamic_cast<const AliESDMuonTrack*>(tracklist->UncheckedAt(0)); | |
828 | if (track == NULL) | |
829 | { | |
830 | HLTError(Form("%s from MUON does not contain AliESDMuonTrack objects.", obj->ClassName())); | |
831 | continue; | |
832 | } | |
833 | } | |
834 | for (Int_t i = 0; i < tracklist->GetEntriesFast(); ++i) | |
f064ef44 | 835 | { |
fe0324de | 836 | AliESDMuonTrack* track = pESD->NewMuonTrack(); |
837 | *track = *(static_cast<const AliESDMuonTrack*>(tracklist->UncheckedAt(i))); | |
a1408c4b | 838 | } |
f064ef44 | 839 | } |
fe0324de | 840 | // copy clusters |
841 | if (clusterlist) { | |
842 | HLTDebug("Received %d MUON clusters.", clusterlist->GetEntriesFast()); | |
843 | if (clusterlist->GetEntriesFast() > 0) | |
844 | { | |
845 | const AliESDMuonCluster* cluster = dynamic_cast<const AliESDMuonCluster*>(clusterlist->UncheckedAt(0)); | |
846 | if (cluster == NULL) | |
847 | { | |
848 | HLTError(Form("%s from MUON does not contain AliESDMuonCluster objects.", obj->ClassName())); | |
849 | continue; | |
850 | } | |
851 | } | |
852 | for (Int_t i = 0; i < clusterlist->GetEntriesFast(); ++i) | |
853 | { | |
854 | AliESDMuonCluster* cluster = pESD->NewMuonCluster(); | |
855 | *cluster = *(static_cast<const AliESDMuonCluster*>(clusterlist->UncheckedAt(i))); | |
856 | } | |
f064ef44 | 857 | } |
858 | } | |
859 | ||
860 | if (iAddedDataBlocks>0 && pTree) { | |
861 | pTree->Fill(); | |
862 | } | |
a1408c4b | 863 | |
864 | if (iResult>=0) iResult=iAddedDataBlocks; | |
865 | return iResult; | |
866 | } |