]>
Commit | Line | Data |
---|---|---|
e0679afb | 1 | /************************************************************************** |
bc5cb6d6 | 2 | * This file is property of and copyright by the ALICE HLT Project * |
b92524d0 | 3 | * All rights reserved. * |
e0679afb | 4 | * * |
b92524d0 | 5 | * Primary Authors: * |
6 | * Artur Szostak <artursz@iafrica.com> * | |
e0679afb | 7 | * * |
8 | * Permission to use, copy, modify and distribute this software and its * | |
9 | * documentation strictly for non-commercial purposes is hereby granted * | |
10 | * without fee, provided that the above copyright notice appears in all * | |
11 | * copies and that both the copyright notice and this permission notice * | |
12 | * appear in the supporting documentation. The authors make no claims * | |
bc5cb6d6 | 13 | * about the suitability of this software for any purpose. It is * |
e0679afb | 14 | * provided "as is" without express or implied warranty. * |
15 | **************************************************************************/ | |
16 | ||
1d8ae082 | 17 | // $Id$ |
e0679afb | 18 | |
a3d4b6ba | 19 | /// |
20 | /// @file AliHLTMUONMansoTrackerFSM.cxx | |
21 | /// @author Artur Szostak <artursz@iafrica.com> | |
22 | /// @date 29 May 2007 | |
23 | /// @brief Implementation of AliHLTMUONMansoTrackerFSM class. | |
24 | /// | |
25 | /// Implementation of AliHLTMUONMansoTrackerFSM class which implements the Manso | |
26 | /// tracking algorithm as a finite state machine, which partially reconstructs | |
27 | /// tracks in the muon spectrometer. | |
51c79947 | 28 | |
e0679afb | 29 | #include "AliHLTMUONMansoTrackerFSM.h" |
30 | #include "AliHLTMUONCalculations.h" | |
b92524d0 | 31 | #include "AliHLTMUONConstants.h" |
e0679afb | 32 | #include "AliHLTMUONUtils.h" |
bc5cb6d6 | 33 | #include "AliHLTMUONTriggerRecordsBlockStruct.h" |
34 | #include "AliHLTMUONMansoTracksBlockStruct.h" | |
35 | #include "AliHLTMUONMansoCandidatesBlockStruct.h" | |
e0679afb | 36 | #include <cmath> |
37 | ||
38 | ||
39 | #ifdef DEBUG | |
40 | #include <ostream> | |
41 | namespace | |
42 | { | |
43 | ||
44 | std::ostream& operator << (std::ostream& os, AliHLTMUONMansoTrackerFSM::StatesSM4 state) | |
45 | { | |
46 | switch (state) | |
47 | { | |
48 | case AliHLTMUONMansoTrackerFSM::kSM4Idle: os << "kSM4Idle"; break; | |
49 | case AliHLTMUONMansoTrackerFSM::kWaitChamber8: os << "kWaitChamber8"; break; | |
50 | case AliHLTMUONMansoTrackerFSM::kWaitMoreChamber8: os << "kWaitMoreChamber8"; break; | |
51 | case AliHLTMUONMansoTrackerFSM::kWaitChamber7: os << "kWaitChamber7"; break; | |
52 | case AliHLTMUONMansoTrackerFSM::kWaitMoreChamber7: os << "kWaitMoreChamber7"; break; | |
b92524d0 | 53 | default: os << "FAULT!!"; |
e0679afb | 54 | } |
55 | return os; | |
56 | } | |
57 | ||
58 | std::ostream& operator << (std::ostream& os, AliHLTMUONMansoTrackerFSM::StatesSM5 state) | |
59 | { | |
60 | switch (state) | |
61 | { | |
62 | case AliHLTMUONMansoTrackerFSM::kSM5Idle: os << "kSM5Idle"; break; | |
63 | case AliHLTMUONMansoTrackerFSM::kWaitChamber10: os << "kWaitChamber10"; break; | |
64 | case AliHLTMUONMansoTrackerFSM::kWaitMoreChamber10: os << "kWaitMoreChamber10"; break; | |
65 | case AliHLTMUONMansoTrackerFSM::kWaitChamber9: os << "kWaitChamber9"; break; | |
66 | case AliHLTMUONMansoTrackerFSM::kWaitMoreChamber9: os << "kWaitMoreChamber9"; break; | |
67 | case AliHLTMUONMansoTrackerFSM::kSM5Done: os << "kSM5Done"; break; | |
b92524d0 | 68 | default: os << "FAULT!!"; |
e0679afb | 69 | } |
70 | return os; | |
71 | } | |
72 | ||
73 | } // end of namespace | |
74 | #endif // DEBUG | |
75 | ||
76 | ||
77 | // Deviate from the Manso implementation by allowing a and b | |
78 | // parameters per chamber and not just per station. | |
79 | // The default values are derived from the work done in | |
80 | // "A first algorithm for dimuon High Level Trigger" | |
81 | // Ref ID: ALICE-INT-2002-04 version 1.0 | |
82 | AliHLTFloat32_t AliHLTMUONMansoTrackerFSM::fgA7 = 0.016f; | |
83 | AliHLTFloat32_t AliHLTMUONMansoTrackerFSM::fgB7 = 2.0f; | |
84 | AliHLTFloat32_t AliHLTMUONMansoTrackerFSM::fgA8 = 0.016f; | |
85 | AliHLTFloat32_t AliHLTMUONMansoTrackerFSM::fgB8 = 2.0f; | |
86 | AliHLTFloat32_t AliHLTMUONMansoTrackerFSM::fgA9 = 0.020f; | |
87 | AliHLTFloat32_t AliHLTMUONMansoTrackerFSM::fgB9 = 3.0f; | |
88 | AliHLTFloat32_t AliHLTMUONMansoTrackerFSM::fgA10 = 0.020f; | |
89 | AliHLTFloat32_t AliHLTMUONMansoTrackerFSM::fgB10 = 3.0f; | |
b92524d0 | 90 | AliHLTFloat32_t AliHLTMUONMansoTrackerFSM::fgZ7 = -1274.5f; |
91 | AliHLTFloat32_t AliHLTMUONMansoTrackerFSM::fgZ8 = -1305.5f; | |
92 | AliHLTFloat32_t AliHLTMUONMansoTrackerFSM::fgZ9 = -1408.6f; | |
93 | AliHLTFloat32_t AliHLTMUONMansoTrackerFSM::fgZ10 = -1439.6f; | |
94 | AliHLTFloat32_t AliHLTMUONMansoTrackerFSM::fgZ11 = -1603.5f; | |
95 | AliHLTFloat32_t AliHLTMUONMansoTrackerFSM::fgZ13 = -1703.5f; | |
e0679afb | 96 | |
97 | ||
b92524d0 | 98 | void AliHLTMUONMansoTrackerFSM::AliRegionOfInterest::Create( |
99 | AliHLTMUONRecHitStruct p, AliHLTFloat32_t a, AliHLTFloat32_t b | |
100 | ) | |
e0679afb | 101 | { |
102 | // Creates a region of interest specific to the Manso algorithm from a point and | |
103 | // two Manso specific parameters. | |
104 | ||
105 | fCentre = p; | |
106 | // Compute the radius Rp | |
b92524d0 | 107 | AliHLTFloat32_t rp = (AliHLTFloat32_t) sqrt( p.fX * p.fX + p.fY * p.fY ); |
e0679afb | 108 | |
109 | // The radius Rs for the region of interest is computed from the | |
110 | // specification given in the document: | |
111 | // "A first algorithm for dimuon High Level Trigger" | |
112 | // Ref ID: ALICE-INT-2002-04 version 1.0 | |
113 | // equation: | |
114 | // Rs = a * Rp + b | |
115 | // given on page 3 section 4. | |
116 | fRs = a * rp + b; | |
117 | } | |
118 | ||
119 | ||
b92524d0 | 120 | bool AliHLTMUONMansoTrackerFSM::AliRegionOfInterest::Contains(AliHLTMUONRecHitStruct p) const |
e0679afb | 121 | { |
122 | // Compute the distance between the centre of the region of interest and | |
123 | // the point p. This distance must be less than the radius of the region | |
124 | // of interest for p to be contained in the region of interest. | |
b92524d0 | 125 | register AliHLTFloat32_t lx = fCentre.fX - p.fX; |
126 | register AliHLTFloat32_t ly = fCentre.fY - p.fY; | |
e0679afb | 127 | register AliHLTFloat32_t r = (AliHLTFloat32_t) sqrt( lx * lx + ly * ly ); |
128 | DebugTrace("\tAliRegionOfInterest::Contains : p = " << p | |
129 | << " , centre = " << fCentre << " , r = " << r << " , Rs = " << fRs | |
130 | ); | |
131 | return r <= fRs; | |
132 | } | |
133 | ||
134 | ||
135 | void AliHLTMUONMansoTrackerFSM::AliRegionOfInterest::GetBoundaryBox( | |
b92524d0 | 136 | AliHLTFloat32_t& left, AliHLTFloat32_t& right, |
137 | AliHLTFloat32_t& bottom, AliHLTFloat32_t& top | |
e0679afb | 138 | ) const |
139 | { | |
140 | // Works out the smallest boundary box that will contain the region of interest. | |
141 | ||
b92524d0 | 142 | left = fCentre.fX - fRs; |
143 | right = fCentre.fX + fRs; | |
144 | bottom = fCentre.fY - fRs; | |
145 | top = fCentre.fY + fRs; | |
e0679afb | 146 | } |
147 | ||
148 | ||
b92524d0 | 149 | AliHLTMUONMansoTrackerFSM::AliVertex::AliVertex( |
150 | AliHLTFloat32_t x, AliHLTFloat32_t y, AliHLTFloat32_t z | |
151 | ) | |
e0679afb | 152 | : fX(x), fY(y), fZ(z) |
153 | { | |
154 | // Constructor for vertex. | |
e0679afb | 155 | } |
156 | ||
157 | ||
b92524d0 | 158 | AliHLTMUONMansoTrackerFSM::AliVertex::AliVertex(AliHLTMUONRecHitStruct xy, AliHLTFloat32_t z) |
159 | : fX(xy.fX), fY(xy.fY), fZ(z) | |
e0679afb | 160 | { |
161 | // Construct vertex from a point on the XY plane and z coordinate. | |
e0679afb | 162 | } |
163 | ||
164 | ||
165 | AliHLTMUONMansoTrackerFSM::AliLine::AliLine( | |
b92524d0 | 166 | AliHLTFloat32_t ax, AliHLTFloat32_t ay, AliHLTFloat32_t az, |
167 | AliHLTFloat32_t bx, AliHLTFloat32_t by, AliHLTFloat32_t bz | |
168 | ) : | |
169 | fMx(ax - bx), | |
170 | fMy(ay - by), | |
171 | fMz(az - bz), | |
172 | fCx(bx), | |
173 | fCy(by), | |
174 | fCz(bz) | |
e0679afb | 175 | { |
176 | // Construct a line defined by L = M*t + C = (A-B)*t + B | |
177 | // where M and C are 3D vectors and t is a free parameter. | |
178 | // A = (ax, ay, az) and B = (bx, by, bz) | |
e0679afb | 179 | } |
180 | ||
181 | ||
182 | AliHLTMUONMansoTrackerFSM::AliLine::AliLine(AliVertex a, AliVertex b) : | |
b92524d0 | 183 | fMx(a.X() - b.X()), |
184 | fMy(a.Y() - b.Y()), | |
185 | fMz(a.Z() - b.Z()), | |
186 | fCx(b.X()), | |
187 | fCy(b.Y()), | |
188 | fCz(b.Z()) | |
e0679afb | 189 | { |
190 | // Contruct a line to go through two vertices a and b. | |
e0679afb | 191 | } |
192 | ||
193 | ||
b92524d0 | 194 | AliHLTMUONRecHitStruct AliHLTMUONMansoTrackerFSM::AliLine::FindIntersectWithXYPlain( |
195 | AliHLTFloat32_t z | |
196 | ) const | |
e0679afb | 197 | { |
198 | // Find the point of intersection of the line and the XY plane at z. | |
199 | ||
d85ab19c | 200 | AliHLTFloat32_t t; |
201 | if (fMz != 0) // Should not have a ray perpendicular to the beam axis. | |
202 | t = (z - fCz) / fMz; | |
203 | else | |
204 | t = 0; | |
b92524d0 | 205 | AliHLTMUONRecHitStruct p; |
4e22efc4 | 206 | p.fFlags = 0; |
b92524d0 | 207 | p.fX = fMx*t + fCx; |
208 | p.fY = fMy*t + fCy; | |
209 | p.fZ = z; | |
210 | return p; | |
e0679afb | 211 | } |
212 | ||
213 | ||
214 | AliHLTMUONMansoTrackerFSM::AliHLTMUONMansoTrackerFSM() : | |
bc5cb6d6 | 215 | AliHLTLogging(), |
e0679afb | 216 | fCallback(NULL), |
217 | fSm4state(kSM4Idle), | |
218 | fSm5state(kSM5Idle), | |
219 | fRequestsCompleted(0), | |
220 | fSt4chamber(kChamber1), | |
221 | fV1(), | |
222 | fMc1(), | |
e0679afb | 223 | fSt5data(), |
e0679afb | 224 | fSt4points(), |
225 | fSt5rec(), | |
b92524d0 | 226 | fFoundPoint(), |
227 | fTriggerId(-1), | |
bc5cb6d6 | 228 | fTrackId(0), |
229 | fMakeCandidates(false), | |
230 | fCandidatesCount(0), | |
231 | fCandidatesSize(0), | |
232 | fCandidates(NULL) | |
e0679afb | 233 | { |
234 | // Default constructor | |
235 | } | |
236 | ||
237 | ||
bc5cb6d6 | 238 | AliHLTMUONMansoTrackerFSM::~AliHLTMUONMansoTrackerFSM() |
239 | { | |
240 | // Default destructor cleans up any allocated memory. | |
241 | ||
242 | if (fCandidates != NULL) delete [] fCandidates; | |
243 | } | |
244 | ||
245 | ||
5def1693 | 246 | void AliHLTMUONMansoTrackerFSM::FindTrack(const AliHLTMUONTriggerRecordStruct& trigger) |
247 | { | |
248 | // Tries to find the track from the trigger seed. | |
249 | ||
250 | DebugTrace("SM5 state = " << fSm5state << " , SM4 state = " << fSm4state); | |
251 | DebugTrace("Processing trigger with ID = " << trigger.fId); | |
252 | ||
253 | fTriggerId = trigger.fId; | |
254 | ||
a3d4b6ba | 255 | // Set Z coordinates of ideal point on trigger track to be nominal |
256 | // chamber 11 and 13 positions. | |
257 | AliHLTMUONCalculations::IdealZ1(fgZ11); | |
258 | AliHLTMUONCalculations::IdealZ2(fgZ13); | |
259 | ||
260 | if (not AliHLTMUONCalculations::FitLineToTriggerRecord(trigger)) | |
b92524d0 | 261 | { |
262 | NoTrackFound(); | |
263 | return; | |
264 | } | |
a3d4b6ba | 265 | fV1 = AliVertex( |
266 | AliHLTMUONCalculations::IdealX1(), | |
267 | AliHLTMUONCalculations::IdealY1(), | |
268 | AliHLTMUONCalculations::IdealZ1() | |
269 | ); | |
270 | AliVertex v2 = AliVertex( | |
271 | AliHLTMUONCalculations::IdealX2(), | |
272 | AliHLTMUONCalculations::IdealY2(), | |
273 | AliHLTMUONCalculations::IdealZ2() | |
274 | ); | |
b92524d0 | 275 | |
5def1693 | 276 | DebugTrace("Using fV1 = {x = " << fV1.X() << ", y = " << fV1.Y() << ", " << fV1.Z() << "}"); |
277 | DebugTrace("Using v2 = {x = " << v2.X() << ", y = " << v2.Y() << ", " << v2.Z() << "}"); | |
e0679afb | 278 | |
279 | // Form the vector line between the above two impact points and | |
280 | // find the crossing point of the line with chamber 10 (i.e. station 5). | |
281 | fMc1.fLine = AliLine(fV1, v2); | |
b92524d0 | 282 | AliHLTMUONRecHitStruct p10 = fMc1.fLine.FindIntersectWithXYPlain( fgZ10 ); |
e0679afb | 283 | |
284 | // Build a region of interest for tracking station 5 (chamber 10). | |
285 | // Remember the parameters a and b are station specific. | |
286 | fMc1.fChamber = kChamber10; | |
287 | fMc1.fRoi.Create(p10, fgA10, fgB10); | |
288 | ||
289 | // Make SM5 state transition before the call to RequestClusters since | |
290 | // that method could call one of our methods again, so we need to be | |
291 | // in a consistant internal state. | |
292 | fSm5state = kWaitChamber10; | |
bc5cb6d6 | 293 | |
294 | if (fMakeCandidates) | |
295 | { | |
296 | fMc1.fCandidate = AddTrackCandidate(); | |
297 | if (fMc1.fCandidate != NULL) | |
298 | { | |
299 | *fMc1.fCandidate = AliHLTMUONConstants::NilMansoCandidateStruct(); | |
300 | fMc1.fCandidate->fTrack.fId = -1; | |
301 | fMc1.fCandidate->fTrack.fTrigRec = fTriggerId; | |
302 | fMc1.fCandidate->fTrack.fChi2 = -1; | |
303 | fMc1.fCandidate->fZmiddle = AliHLTMUONCalculations::Zf(); | |
304 | fMc1.fCandidate->fBl = AliHLTMUONCalculations::QBL(); | |
305 | fMc1.fCandidate->fRoI[3].fX = fMc1.fRoi.Centre().fX; | |
306 | fMc1.fCandidate->fRoI[3].fY = fMc1.fRoi.Centre().fY; | |
307 | fMc1.fCandidate->fRoI[3].fZ = fMc1.fRoi.Centre().fZ; | |
308 | fMc1.fCandidate->fRoI[3].fRadius = fMc1.fRoi.Radius(); | |
309 | } | |
310 | } | |
e0679afb | 311 | |
312 | AliHLTFloat32_t left, right, bottom, top; | |
313 | fMc1.fRoi.GetBoundaryBox(left, right, bottom, top); | |
314 | RequestClusters(left, right, bottom, top, kChamber10, &fMc1); | |
315 | } | |
316 | ||
317 | ||
b92524d0 | 318 | void AliHLTMUONMansoTrackerFSM::ReturnClusters( |
319 | void* tag, const AliHLTMUONRecHitStruct* clusters, | |
320 | AliHLTUInt32_t count | |
321 | ) | |
e0679afb | 322 | { |
b92524d0 | 323 | // Implementation of AliHLTMUONMansoTrackerFSM::ReturnClusters. |
e0679afb | 324 | |
b92524d0 | 325 | assert( count > 0 ); |
326 | assert( clusters != NULL ); | |
e0679afb | 327 | |
328 | AliTagData* data = (AliTagData*)tag; | |
329 | DebugTrace("Got AliHLTMUONMansoTrackerFSM::ReturnClusters(tag = " << tag | |
330 | << ", chamber = " << data->fChamber | |
331 | << ", clusters = " << clusters << ", count = " << count << ")" | |
332 | ); | |
333 | DebugTrace("SM5 state = " << fSm5state << " , SM4 state = " << fSm4state); | |
334 | ||
335 | switch (data->fChamber) | |
336 | { | |
337 | case kChamber7: ReceiveClustersChamber7(clusters, count, data); break; | |
338 | case kChamber8: ReceiveClustersChamber8(clusters, count, data); break; | |
339 | case kChamber9: ReceiveClustersChamber9(clusters, count); break; | |
340 | case kChamber10: ReceiveClustersChamber10(clusters, count); break; | |
341 | default: | |
342 | // Error | |
343 | DebugTrace("ERROR: Got tag with an invalid value: " << data->fChamber); | |
344 | } | |
345 | } | |
346 | ||
347 | ||
348 | void AliHLTMUONMansoTrackerFSM::EndOfClusters(void* tag) | |
349 | { | |
b92524d0 | 350 | // Implementation of AliHLTMUONMansoTrackerFSM::EndOfClusters. |
e0679afb | 351 | |
352 | AliTagData* data = (AliTagData*)tag; | |
353 | DebugTrace("Got AliHLTMUONMansoTrackerFSM::EndOfClusters(chamber = " << data->fChamber << ")"); | |
354 | DebugTrace("SM5 state = " << fSm5state << " , SM4 state = " << fSm4state); | |
355 | ||
356 | switch (data->fChamber) | |
357 | { | |
358 | case kChamber7: EndOfClustersChamber7(); break; | |
359 | case kChamber8: EndOfClustersChamber8(); break; | |
360 | case kChamber9: EndOfClustersChamber9(); break; | |
361 | case kChamber10: EndOfClustersChamber10(); break; | |
362 | default: | |
363 | // Error | |
364 | DebugTrace("ERROR: Got tag with an invalid value: " << data->fChamber); | |
365 | } | |
366 | } | |
367 | ||
368 | ||
b92524d0 | 369 | bool AliHLTMUONMansoTrackerFSM::FillTrackData(AliHLTMUONMansoTrackStruct& track) |
e0679afb | 370 | { |
b92524d0 | 371 | // Implementation of AliHLTMUONMansoTrackerFSM::FillTrackData |
e0679afb | 372 | |
373 | DebugTrace("FillTrack: st5 = " << fSt5rec->fClusterPoint << ", st4 = " << fFoundPoint->fClusterPoint); | |
374 | ||
406c5bc3 | 375 | // Construct the track ID from the running counter fTrackId and the |
376 | // bottom 8 bits of fTriggerId which will make this unique for an event. | |
d24a4636 | 377 | // 0x100 is forced for the Manso component. |
378 | track.fId = (fTrackId << 10) | 0x100 | (fTriggerId & 0xFF); | |
406c5bc3 | 379 | |
d24a4636 | 380 | // Increment the track ID and warp it around at 0x1FFFFF since the |
381 | // bottom 8 bits are copied from fTriggerId, bits 8 and 9 are forced to 01 | |
382 | // and the sign bit in track.fId must be positive. | |
383 | fTrackId = (fTrackId + 1) & 0x001FFFFF; | |
b92524d0 | 384 | |
385 | track.fTrigRec = fTriggerId; | |
386 | ||
387 | AliHLTFloat32_t x1 = fFoundPoint->fClusterPoint.fX; | |
388 | AliHLTFloat32_t y1 = fFoundPoint->fClusterPoint.fY; | |
389 | AliHLTFloat32_t z1 = fFoundPoint->fClusterPoint.fZ; | |
390 | AliHLTFloat32_t y2 = fSt5rec->fClusterPoint.fY; | |
391 | AliHLTFloat32_t z2 = fSt5rec->fClusterPoint.fZ; | |
392 | ||
393 | bool calculated = AliHLTMUONCalculations::ComputeMomentum(x1, y1, y2, z1, z2); | |
394 | ||
395 | track.fPx = AliHLTMUONCalculations::Px(); | |
396 | track.fPy = AliHLTMUONCalculations::Py(); | |
397 | track.fPz = AliHLTMUONCalculations::Pz(); | |
398 | DebugTrace("Calculated Px = " << track.fPx << ", Py = " << track.fPy | |
399 | << ", Pz = " << track.fPx | |
400 | ); | |
e0679afb | 401 | DebugTrace("\tusing x1 = " << x1 << " , y1 = " << y1 << " , y2 = " << y2 |
b92524d0 | 402 | << " , z1 = " << z1 << " , z2 = " << z2 |
e0679afb | 403 | ); |
e0679afb | 404 | |
b92524d0 | 405 | track.fChi2 = 0; |
e0679afb | 406 | |
b92524d0 | 407 | bool hitset[4]; |
408 | // Depending on which chamber we found reconstructed hits, fill the hit | |
409 | // in the appropriate location. This is done for station 4 then 5. | |
e0679afb | 410 | if (fSt4chamber == kChamber8) |
411 | { | |
b92524d0 | 412 | track.fHit[0] = AliHLTMUONConstants::NilRecHitStruct(); |
413 | hitset[0] = false; | |
414 | track.fHit[1] = fFoundPoint->fClusterPoint; | |
415 | hitset[1] = true; | |
e0679afb | 416 | } |
417 | else | |
418 | { | |
b92524d0 | 419 | track.fHit[0] = fFoundPoint->fClusterPoint; |
420 | hitset[0] = true; | |
421 | track.fHit[1] = AliHLTMUONConstants::NilRecHitStruct(); | |
422 | hitset[1] = false; | |
e0679afb | 423 | } |
424 | if (fMc1.fChamber == kChamber10) | |
425 | { | |
b92524d0 | 426 | track.fHit[2] = AliHLTMUONConstants::NilRecHitStruct(); |
427 | hitset[2] = false; | |
428 | track.fHit[3] = fSt5rec->fClusterPoint; | |
429 | hitset[3] = true; | |
e0679afb | 430 | } |
431 | else | |
432 | { | |
b92524d0 | 433 | track.fHit[2] = fSt5rec->fClusterPoint; |
434 | hitset[2] = true; | |
435 | track.fHit[3] = AliHLTMUONConstants::NilRecHitStruct(); | |
436 | hitset[3] = false; | |
e0679afb | 437 | } |
b92524d0 | 438 | |
439 | track.fFlags = AliHLTMUONUtils::PackMansoTrackFlags( | |
440 | AliHLTMUONCalculations::Sign(), hitset | |
441 | ); | |
bc5cb6d6 | 442 | |
443 | if (fMakeCandidates) | |
444 | { | |
445 | AliHLTMUONMansoCandidateStruct* candidate = fSt5rec->fTag.fCandidate; | |
446 | if (candidate != NULL) | |
447 | { | |
448 | candidate->fTrack = track; | |
449 | } | |
450 | } | |
451 | ||
b92524d0 | 452 | return calculated; |
e0679afb | 453 | } |
454 | ||
455 | ||
456 | void AliHLTMUONMansoTrackerFSM::Reset() | |
457 | { | |
b92524d0 | 458 | // Implementation of AliHLTMUONMansoTrackerFSM::Reset |
e0679afb | 459 | |
460 | DebugTrace("SM5 state = " << fSm5state << " , SM4 state = " << fSm4state); | |
461 | fSt5data.Clear(); | |
462 | fSt4points.Clear(); | |
463 | fSm4state = kSM4Idle; | |
464 | fSm5state = kSM5Idle; | |
465 | fRequestsCompleted = 0; | |
b92524d0 | 466 | fTriggerId = -1; |
e0679afb | 467 | } |
468 | ||
469 | ||
470 | // Note: In the following ReceiveClustersXXX and EndOfClustersXXX methods we make | |
471 | // the state machine transitions before calls to RequestClusters, FoundTrack, | |
472 | // NoTrackFound or EndOfClusterRequests. This is important since the callback | |
473 | // object will make recursive calls to the tracker's methods so we need to maintain | |
474 | // a consistant internal state. | |
475 | // The same would go for updating internal variables. | |
476 | // In general one should only call the callback methods at the end of any of the | |
477 | // following routines. | |
478 | ||
479 | void AliHLTMUONMansoTrackerFSM::ReceiveClustersChamber7( | |
b92524d0 | 480 | const AliHLTMUONRecHitStruct* clusters, AliHLTUInt32_t count, |
481 | const AliTagData* data | |
e0679afb | 482 | ) |
483 | { | |
484 | // State change method for Station 4 state machine. | |
485 | ||
486 | switch (fSm4state) | |
487 | { | |
488 | case kWaitChamber7: | |
bc5cb6d6 | 489 | // We switch state below. |
490 | ||
e0679afb | 491 | case kWaitMoreChamber7: |
b92524d0 | 492 | for (AliHLTUInt32_t j = 0; j < count; j++) |
e0679afb | 493 | { |
b92524d0 | 494 | AliHLTMUONRecHitStruct cluster = clusters[j]; |
e0679afb | 495 | // Check that the cluster actually is in our region of interest on station 4. |
496 | if ( data->fRoi.Contains(cluster) ) | |
497 | { | |
bc5cb6d6 | 498 | // Go to next wait state only if we actually found anything in the RoI. |
499 | fSm4state = kWaitMoreChamber7; | |
500 | ||
b92524d0 | 501 | DebugTrace("Adding cluster [" << cluster.fX << ", " << cluster.fY << "] from chamber 7."); |
502 | AliStation4Data* newdata = fSt4points.Add(); | |
e0679afb | 503 | newdata->fClusterPoint = cluster; |
504 | newdata->fSt5tag = data; | |
505 | } | |
506 | } | |
507 | break; | |
508 | ||
509 | default: | |
510 | DebugTrace("ERROR: Unexpected state for SM4 in AliHLTMUONMansoTrackerFSM::ReceiveClustersChamber7!"); | |
511 | } | |
512 | } | |
513 | ||
514 | ||
515 | void AliHLTMUONMansoTrackerFSM::ReceiveClustersChamber8( | |
b92524d0 | 516 | const AliHLTMUONRecHitStruct* clusters, AliHLTUInt32_t count, |
517 | const AliTagData* data | |
e0679afb | 518 | ) |
519 | { | |
520 | // State change method for Station 4 state machine. | |
521 | ||
522 | switch (fSm4state) | |
523 | { | |
524 | case kWaitChamber8: | |
e0679afb | 525 | fSt4chamber = kChamber8; |
bc5cb6d6 | 526 | |
e0679afb | 527 | case kWaitMoreChamber8: |
b92524d0 | 528 | for (AliHLTUInt32_t j = 0; j < count; j++) |
e0679afb | 529 | { |
b92524d0 | 530 | AliHLTMUONRecHitStruct cluster = clusters[j]; |
e0679afb | 531 | // Check that the cluster actually is in our region of interest on station 4. |
532 | if ( data->fRoi.Contains(cluster) ) | |
533 | { | |
bc5cb6d6 | 534 | // Go to next wait state only if we actually found anything in the RoI. |
535 | fSm4state = kWaitMoreChamber8; | |
536 | ||
b92524d0 | 537 | DebugTrace("Adding cluster [" << cluster.fX << ", " << cluster.fY << "] from chamber 8."); |
538 | AliStation4Data* newdata = fSt4points.Add(); | |
e0679afb | 539 | newdata->fClusterPoint = cluster; |
540 | newdata->fSt5tag = data; | |
541 | } | |
542 | } | |
543 | break; | |
544 | ||
545 | default: | |
546 | DebugTrace("ERROR: Unexpected state for SM4 in AliHLTMUONMansoTrackerFSM::ReceiveClustersChamber8!"); | |
547 | } | |
548 | } | |
549 | ||
550 | ||
b92524d0 | 551 | void AliHLTMUONMansoTrackerFSM::ReceiveClustersChamber9( |
552 | const AliHLTMUONRecHitStruct* clusters, AliHLTUInt32_t count | |
553 | ) | |
e0679afb | 554 | { |
555 | // State change method for Station 5 state machine. | |
556 | ||
557 | switch (fSm5state) | |
558 | { | |
559 | case kWaitChamber9: | |
e0679afb | 560 | fSm4state = kWaitChamber8; // Start SM4. |
bc5cb6d6 | 561 | |
e0679afb | 562 | case kWaitMoreChamber9: |
b92524d0 | 563 | for (AliHLTUInt32_t j = 0; j < count; j++) |
e0679afb | 564 | { |
b92524d0 | 565 | AliHLTMUONRecHitStruct cluster = clusters[j]; |
e0679afb | 566 | // Check that the cluster actually is in our region of interest on station 5. |
567 | if ( fMc1.fRoi.Contains(cluster) ) | |
568 | { | |
bc5cb6d6 | 569 | // Go to next wait state only if we actually found anything in the RoI. |
570 | fSm5state = kWaitMoreChamber9; | |
571 | ||
b92524d0 | 572 | DebugTrace("Adding cluster [" << cluster.fX << ", " << cluster.fY << "] from chamber 9."); |
573 | AliStation5Data* data = fSt5data.Add(); | |
e0679afb | 574 | data->fClusterPoint = cluster; |
bc5cb6d6 | 575 | ProjectToStation4(data, fgZ9, 2); // This adds a new request for station 4. |
e0679afb | 576 | } |
577 | } | |
578 | break; | |
579 | ||
580 | default: | |
581 | DebugTrace("ERROR: Unexpected state for SM5 in AliHLTMUONMansoTrackerFSM::ReceiveClustersChamber9!"); | |
582 | } | |
583 | } | |
584 | ||
585 | ||
b92524d0 | 586 | void AliHLTMUONMansoTrackerFSM::ReceiveClustersChamber10( |
587 | const AliHLTMUONRecHitStruct* clusters, AliHLTUInt32_t count | |
588 | ) | |
e0679afb | 589 | { |
590 | // State change method for Station 5 state machine. | |
591 | ||
592 | switch (fSm5state) | |
593 | { | |
594 | case kWaitChamber10: | |
e0679afb | 595 | fSm4state = kWaitChamber8; // Start SM4. |
596 | ||
597 | case kWaitMoreChamber10: | |
b92524d0 | 598 | for (AliHLTUInt32_t j = 0; j < count; j++) |
e0679afb | 599 | { |
b92524d0 | 600 | AliHLTMUONRecHitStruct cluster = clusters[j]; |
e0679afb | 601 | // Check that the cluster actually is in our region of interest on station 5. |
602 | if ( fMc1.fRoi.Contains(cluster) ) | |
603 | { | |
bc5cb6d6 | 604 | // Go to next wait state only if we actually found anything in the RoI. |
605 | fSm5state = kWaitMoreChamber10; | |
606 | ||
b92524d0 | 607 | DebugTrace("Adding cluster [" << cluster.fX << ", " << cluster.fY << "] from chamber 10."); |
608 | AliStation5Data* data = fSt5data.Add(); | |
e0679afb | 609 | data->fClusterPoint = cluster; |
bc5cb6d6 | 610 | ProjectToStation4(data, fgZ10, 3); // This adds a new request for station 4. |
e0679afb | 611 | } |
612 | } | |
613 | break; | |
614 | ||
615 | default: | |
616 | DebugTrace("ERROR: Unexpected state for SM5 in AliHLTMUONMansoTrackerFSM::ReceiveClustersChamber10!"); | |
617 | } | |
618 | } | |
619 | ||
620 | ||
621 | void AliHLTMUONMansoTrackerFSM::EndOfClustersChamber7() | |
622 | { | |
623 | // State change method for Station 4 state machine. | |
624 | ||
625 | fRequestsCompleted++; // Increment the number of requests completed for station 4. | |
626 | DebugTrace("fRequestsCompleted = " << fRequestsCompleted ); | |
627 | ||
628 | switch (fSm4state) | |
629 | { | |
630 | case kWaitChamber7: | |
631 | // If all data from station 5 is received and no data found on | |
632 | // chambers 7 or 8 then we can not find a track. | |
633 | if (fSm5state == kSM5Done) NoTrackFound(); | |
634 | break; | |
635 | ||
636 | case kWaitMoreChamber7: | |
637 | if (fRequestsCompleted == fSt5data.Count() && fSm5state == kSM5Done) | |
638 | ProcessClusters(); | |
639 | break; | |
640 | ||
641 | default: | |
642 | DebugTrace("ERROR: Unexpected state for SM4 in AliHLTMUONMansoTrackerFSM::EndOfClustersChamber7!"); | |
643 | } | |
644 | } | |
645 | ||
646 | ||
647 | void AliHLTMUONMansoTrackerFSM::EndOfClustersChamber8() | |
648 | { | |
649 | // State change method for Station 4 state machine. | |
650 | ||
651 | fRequestsCompleted++; // Increment the number of requests completed for station 4. | |
652 | DebugTrace("fRequestsCompleted = " << fRequestsCompleted ); | |
653 | ||
654 | switch (fSm4state) | |
655 | { | |
656 | case kWaitChamber7: | |
657 | // Ignore. The requests for chamber 8 are already re-requested below. | |
658 | break; | |
659 | ||
660 | case kWaitChamber8: | |
661 | { | |
662 | fSm4state = kWaitChamber7; | |
e0679afb | 663 | fSt4chamber = kChamber7; |
664 | ||
665 | // We need to resend the requests for chamber 8, but change the request | |
666 | // to get data for chamber 7 instead: | |
b92524d0 | 667 | AliHLTUInt32_t reqlistsize = fSt5data.Count(); |
e0679afb | 668 | DebugTrace("Re-requesting clusters from chamber 7... reqlistsize = " << reqlistsize); |
669 | ||
670 | Station5List::Iterator rec = fSt5data.First(); | |
b92524d0 | 671 | for (AliHLTUInt32_t i = 0; i < reqlistsize; i++, rec++) |
e0679afb | 672 | { |
673 | // Need to create a new st5 data block for the request. | |
b92524d0 | 674 | AliStation5Data* data = fSt5data.Add(); |
e0679afb | 675 | data->fClusterPoint = rec->fClusterPoint; |
676 | data->fTag.fLine = rec->fTag.fLine; | |
bc5cb6d6 | 677 | data->fTag.fCandidate = rec->fTag.fCandidate; |
e0679afb | 678 | |
679 | // Rebuild a region of interest for chamber 7. | |
680 | // Remember the parameters a and b are station specific. | |
b92524d0 | 681 | AliHLTMUONRecHitStruct p7 = data->fTag.fLine.FindIntersectWithXYPlain( fgZ7 ); |
e0679afb | 682 | data->fTag.fChamber = kChamber7; |
683 | data->fTag.fRoi.Create(p7, fgA7, fgB7); | |
684 | ||
bc5cb6d6 | 685 | if (fMakeCandidates and data->fTag.fCandidate != NULL) |
686 | { | |
687 | data->fTag.fCandidate->fRoI[0].fX = data->fTag.fRoi.Centre().fX; | |
688 | data->fTag.fCandidate->fRoI[0].fY = data->fTag.fRoi.Centre().fY; | |
689 | data->fTag.fCandidate->fRoI[0].fZ = data->fTag.fRoi.Centre().fZ; | |
690 | data->fTag.fCandidate->fRoI[0].fRadius = data->fTag.fRoi.Radius(); | |
691 | } | |
692 | ||
e0679afb | 693 | AliHLTFloat32_t left, right, bottom, top; |
694 | data->fTag.fRoi.GetBoundaryBox(left, right, bottom, top); | |
695 | // Make request for chamber 7 data. | |
696 | RequestClusters(left, right, bottom, top, kChamber7, &data->fTag); | |
697 | } | |
698 | } | |
699 | break; | |
700 | ||
701 | case kWaitMoreChamber8: | |
702 | if (fRequestsCompleted == fSt5data.Count() && fSm5state == kSM5Done) | |
703 | ProcessClusters(); | |
704 | break; | |
705 | ||
706 | default: | |
707 | DebugTrace("ERROR: Unexpected state for SM4 in AliHLTMUONMansoTrackerFSM::EndOfClustersChamber8!"); | |
708 | } | |
709 | } | |
710 | ||
711 | ||
712 | void AliHLTMUONMansoTrackerFSM::EndOfClustersChamber9() | |
713 | { | |
714 | // State change method for Station 5 state machine. | |
715 | ||
716 | switch (fSm5state) | |
717 | { | |
718 | case kWaitChamber9: | |
719 | fSm5state = kSM5Done; | |
720 | EndOfClusterRequests(); | |
721 | NoTrackFound(); | |
722 | break; | |
723 | ||
724 | case kWaitMoreChamber9: | |
725 | fSm5state = kSM5Done; | |
726 | EndOfClusterRequests(); | |
727 | if (fRequestsCompleted == fSt5data.Count()) | |
728 | ProcessClusters(); | |
729 | break; | |
730 | ||
731 | default: | |
732 | DebugTrace("ERROR: Unexpected state for SM5 in AliHLTMUONMansoTrackerFSM::EndOfClustersChamber9!"); | |
733 | } | |
734 | } | |
735 | ||
736 | ||
737 | void AliHLTMUONMansoTrackerFSM::EndOfClustersChamber10() | |
738 | { | |
739 | // State change method for Station 5 state machine. | |
740 | ||
741 | switch (fSm5state) | |
742 | { | |
743 | case kWaitChamber10: | |
744 | { | |
745 | fSm5state = kWaitChamber9; | |
e0679afb | 746 | |
747 | // No clusters found on chamber 10 so we need to make a request for | |
748 | // clusters from chamber 9: | |
b92524d0 | 749 | AliHLTMUONRecHitStruct p9 = fMc1.fLine.FindIntersectWithXYPlain( fgZ9 ); |
bc5cb6d6 | 750 | |
e0679afb | 751 | // Build a region of interest for tracking station 5 (chamber 9). |
752 | // Remember the parameters a and b are station specific. | |
753 | fMc1.fChamber = kChamber9; | |
754 | fMc1.fRoi.Create(p9, fgA9, fgB9); | |
bc5cb6d6 | 755 | |
756 | if (fMakeCandidates and fMc1.fCandidate != NULL) | |
757 | { | |
758 | fMc1.fCandidate->fRoI[2].fX = fMc1.fRoi.Centre().fX; | |
759 | fMc1.fCandidate->fRoI[2].fY = fMc1.fRoi.Centre().fY; | |
760 | fMc1.fCandidate->fRoI[2].fZ = fMc1.fRoi.Centre().fZ; | |
761 | fMc1.fCandidate->fRoI[2].fRadius = fMc1.fRoi.Radius(); | |
762 | } | |
763 | ||
e0679afb | 764 | AliHLTFloat32_t left, right, bottom, top; |
765 | fMc1.fRoi.GetBoundaryBox(left, right, bottom, top); | |
766 | RequestClusters(left, right, bottom, top, kChamber9, &fMc1); | |
767 | } | |
768 | break; | |
769 | ||
770 | case kWaitMoreChamber10: | |
771 | fSm5state = kSM5Done; | |
772 | EndOfClusterRequests(); | |
773 | if (fRequestsCompleted == fSt5data.Count()) | |
774 | ProcessClusters(); | |
775 | break; | |
776 | ||
777 | default: | |
778 | DebugTrace("ERROR: Unexpected state for SM5 in AliHLTMUONMansoTrackerFSM::EndOfClustersChamber10!"); | |
779 | } | |
780 | } | |
781 | ||
782 | ||
b92524d0 | 783 | void AliHLTMUONMansoTrackerFSM::ProjectToStation4( |
bc5cb6d6 | 784 | AliStation5Data* data, AliHLTFloat32_t station5z, AliHLTUInt32_t chamberSt5 |
b92524d0 | 785 | ) |
e0679afb | 786 | { |
787 | // Perform chamber specific operations: | |
788 | // Since certain states of SM4 means that it is fetching for Chamber8 | |
789 | // and other states are for fetching from Chamber7. We need to make | |
790 | // requests for the correct chamber. | |
b92524d0 | 791 | assert( fSm4state == kWaitChamber8 |
e0679afb | 792 | || fSm4state == kWaitMoreChamber8 |
793 | || fSm4state == kWaitChamber7 | |
794 | || fSm4state == kWaitMoreChamber7 | |
795 | ); | |
bc5cb6d6 | 796 | assert( chamberSt5 == 2 or chamberSt5 == 3 ); |
e0679afb | 797 | AliTagData* tag = &data->fTag; |
bc5cb6d6 | 798 | int chamber = 0; |
e0679afb | 799 | if (fSm4state == kWaitChamber8 || fSm4state == kWaitMoreChamber8) |
800 | { | |
801 | // Form the vector line between trigger station 1 and tracking station 5, | |
802 | // and find the intersection point of the line with station 4 (chamber8). | |
803 | AliLine line51( AliVertex(data->fClusterPoint, station5z), fV1 ); | |
b92524d0 | 804 | AliHLTMUONRecHitStruct intercept = line51.FindIntersectWithXYPlain( fgZ8 ); |
e0679afb | 805 | tag->fLine = line51; |
806 | ||
807 | // Build a region of interest for tracking station 4. | |
808 | tag->fChamber = kChamber8; | |
809 | tag->fRoi.Create(intercept, fgA8, fgB8); | |
bc5cb6d6 | 810 | chamber = 1; |
e0679afb | 811 | } |
812 | else | |
813 | { | |
814 | // Form the vector line between trigger station 1 and tracking station 5, | |
815 | // and find the intersection point of the line with station 4 (chamber7). | |
816 | AliLine line51( AliVertex(data->fClusterPoint, station5z), fV1 ); | |
b92524d0 | 817 | AliHLTMUONRecHitStruct intercept = line51.FindIntersectWithXYPlain( fgZ7 ); |
e0679afb | 818 | tag->fLine = line51; |
819 | ||
820 | // Build a region of interest for tracking station 4. | |
821 | tag->fChamber = kChamber7; | |
822 | tag->fRoi.Create(intercept, fgA7, fgB7); | |
bc5cb6d6 | 823 | chamber = 0; |
824 | } | |
825 | ||
826 | if (fMakeCandidates) | |
827 | { | |
828 | // Make a copy of the track candidate if the exisiting track candidate | |
829 | // has already had its point on the given chamber filled. | |
830 | if (fMc1.fCandidate != NULL and | |
831 | fMc1.fCandidate->fTrack.fHit[chamberSt5] == AliHLTMUONConstants::NilRecHitStruct() | |
832 | ) | |
833 | { | |
834 | tag->fCandidate = fMc1.fCandidate; | |
835 | } | |
836 | else | |
837 | { | |
838 | tag->fCandidate = AddTrackCandidate(); | |
f35e9b91 | 839 | if (tag->fCandidate != NULL and fMc1.fCandidate != NULL) *tag->fCandidate = *fMc1.fCandidate; |
bc5cb6d6 | 840 | } |
841 | // Now fill the cluster point found on station 5 and RoI on station 4. | |
842 | if (tag->fCandidate != NULL) | |
843 | { | |
844 | tag->fCandidate->fTrack.fHit[chamberSt5] = data->fClusterPoint; | |
845 | tag->fCandidate->fRoI[chamber].fX = tag->fRoi.Centre().fX; | |
846 | tag->fCandidate->fRoI[chamber].fY = tag->fRoi.Centre().fY; | |
847 | tag->fCandidate->fRoI[chamber].fZ = tag->fRoi.Centre().fZ; | |
848 | tag->fCandidate->fRoI[chamber].fRadius = tag->fRoi.Radius(); | |
849 | } | |
e0679afb | 850 | } |
851 | ||
852 | // Make the request for clusters from station 4. | |
853 | AliHLTFloat32_t left, right, bottom, top; | |
854 | tag->fRoi.GetBoundaryBox(left, right, bottom, top); | |
855 | RequestClusters(left, right, bottom, top, tag->fChamber, tag); | |
856 | } | |
857 | ||
858 | ||
859 | void AliHLTMUONMansoTrackerFSM::ProcessClusters() | |
860 | { | |
861 | // Process clusters that have been received. | |
862 | // This is called once all clusters have been found. | |
863 | ||
864 | DebugTrace("ProcessClusters..."); | |
865 | ||
866 | // Check if the cluster point list on station 4 is empty. | |
867 | // If it is then we have not found any tracks. | |
868 | fFoundPoint = fSt4points.First(); | |
869 | if (fFoundPoint == fSt4points.End()) | |
870 | { | |
871 | NoTrackFound(); | |
872 | return; | |
873 | } | |
874 | ||
875 | fSt5rec = fSt5data.First(); | |
876 | if (fSt5rec != fSt5data.End()) | |
877 | { | |
878 | // Only look at station 5 data records that are for the found chamber number. | |
879 | // Note: either we only have chamber 8 data or we have chamber 7 data followed | |
880 | // by chamber 8 data. | |
881 | // Thus if we hit records that we are not interested in already then the list | |
882 | // contains no interesting data and we can signal no track found. | |
883 | if (fSt5rec->fTag.fChamber != fSt4chamber) | |
884 | { | |
885 | NoTrackFound(); | |
886 | return; | |
887 | } | |
888 | ||
889 | // For all combinations of cluster point pairs from station 4 and 5 | |
890 | // signal a found track: | |
891 | do | |
892 | { | |
893 | DebugTrace("\tfSt5rec->fTag.chamber = " << fSt5rec->fTag.fChamber | |
894 | << " , fSt4chamber = " << fSt4chamber | |
895 | ); | |
896 | ||
897 | for (fFoundPoint = fSt4points.First(); fFoundPoint != fSt4points.End(); fFoundPoint++) | |
898 | { | |
899 | if (fFoundPoint->fSt5tag == &fSt5rec->fTag) | |
900 | FoundTrack(); | |
901 | } | |
902 | ||
903 | fSt5rec++; // Get next station 5 cluster point. | |
904 | } while (fSt5rec != fSt5data.End() && fSt5rec->fTag.fChamber == fSt4chamber); | |
905 | } | |
906 | else | |
907 | NoTrackFound(); | |
908 | } | |
909 | ||
bc5cb6d6 | 910 | |
911 | AliHLTMUONMansoCandidateStruct* AliHLTMUONMansoTrackerFSM::AddTrackCandidate() | |
912 | { | |
913 | // Adds a new track candidate to the fCandidates list and returns a pointer | |
914 | // to the new structure. | |
915 | ||
916 | // First allocate or reallocate buffer if necessary. | |
917 | if (fCandidates == NULL) | |
918 | { | |
919 | try | |
920 | { | |
921 | fCandidates = new AliHLTMUONMansoCandidateStruct[1024]; | |
922 | } | |
923 | catch (...) | |
924 | { | |
925 | HLTError("Could not allocate buffer space for Manso track candidates."); | |
926 | return NULL; | |
927 | } | |
928 | fCandidatesSize = 1024; | |
929 | } | |
930 | else if (fCandidatesCount >= fCandidatesSize) | |
931 | { | |
932 | AliHLTMUONMansoCandidateStruct* newbuf = NULL; | |
933 | try | |
934 | { | |
935 | newbuf = new AliHLTMUONMansoCandidateStruct[fCandidatesSize*2]; | |
936 | } | |
937 | catch (...) | |
938 | { | |
939 | HLTError("Could not allocate more buffer space for Manso track candidates."); | |
940 | return NULL; | |
941 | } | |
942 | for (AliHLTUInt32_t i = 0; i < fCandidatesSize; ++i) newbuf[i] = fCandidates[i]; | |
943 | delete [] fCandidates; | |
944 | fCandidates = newbuf; | |
945 | fCandidatesSize = fCandidatesSize*2; | |
946 | } | |
947 | ||
948 | return &fCandidates[fCandidatesCount++]; | |
949 | } |