Now also optionally generating and rootifying track candidates for debugging.
Some bug fixes for handling strip information in AliHLTMUONTriggerReconstructorComponent.
Adding default field integrals and generation macro CreateCDBFieldIntegrals.C.
Adding macro for displaying dHLT rootified output data DisplaydHLTData.C.
};
const AliHLTMUONTrigRecInfoStruct
-AliHLTMUONConstants::fgkNilTrigRecInfoStruct = {0, {0, 0, 0, 0}, 0, 0, {0, 0, 0, 0, 0}};
+AliHLTMUONConstants::fgkNilTrigRecInfoStruct = {
+ 0, {0, 0, 0, 0}, 0, 0,
+ {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}, {0, 0, 0, 0, 0}
+};
const AliHLTMUONRecHitStruct
AliHLTMUONConstants::fgkNilRecHitStruct = {0, 0, 0, 0};
const char* AliHLTMUONConstants::fgkHitReconstructorCDBPath = "HLT/ConfigMUON/HitReconstructor";
const char* AliHLTMUONConstants::fgkMansoTrackerFSMCDBPath = "HLT/ConfigMUON/MansoTrackerFSM";
const char* AliHLTMUONConstants::fgkDecisionComponentCDBPath = "HLT/ConfigMUON/DecisionComponent";
-
+const char* AliHLTMUONConstants::fgkFieldIntegralsCDBPath = "HLT/ConfigMUON/FieldIntegrals";
return fgkDecisionComponentCDBPath;
}
+ static const char* FieldIntegralsCDBPath()
+ {
+ return fgkFieldIntegralsCDBPath;
+ }
+
/// Returns the typical X (non-bending plane) resolution of the hit reconstruction (units = cm).
static double DefaultNonBendingReso() { return 0.144; }
static const char* fgkHitReconstructorCDBPath; // Path to CDB entry for the hit reconstruction component.
static const char* fgkMansoTrackerFSMCDBPath; // Path to CDB entry for the Manso FSM tracker component.
static const char* fgkDecisionComponentCDBPath; // Path to CDB entry for trigger decision component.
+ static const char* fgkFieldIntegralsCDBPath; // Path to CDB entry for magnetic field integrals.
ClassDef(AliHLTMUONConstants, 0); // Interface class to dHLT constants.
};
fHit[1] = hit8;
fHit[2] = hit9;
fHit[3] = hit10;
+ for (int i = 0; i < 4; i++)
+ {
+ fRoICentre[i] = TVector3(0, 0, 0);
+ fRoIRadius[i] = -1;
+ }
}
cout << "Used Zmiddle = " << fZmiddle << " cm and QBL = "
<< fQBL << " T.m for the momentum calculation." << endl;
+ cout << "Region of interest information:" << endl;
+ streamsize w = cout.width();
+ ios::fmtflags f = cout.flags();
+ cout << setw(9) << "Chamber"
+ << setw(12) << "X (cm)"
+ << setw(12) << "Y (cm)"
+ << setw(12) << "Z (cm)"
+ << setw(12) << "Radius (cm)" << endl;
+ for (int i = 0; i < 4; i++)
+ {
+ cout << setw(9) << i+11;
+ if (fRoIRadius[i] != -1)
+ {
+ cout << setw(12) << fRoICentre[i].X()
+ << setw(12) << fRoICentre[i].Y()
+ << setw(12) << fRoICentre[i].Z()
+ << setw(12) << fRoIRadius[i];
+ }
+ else
+ {
+ cout << setw(12) << "-"
+ << setw(12) << "-"
+ << setw(12) << "-"
+ << setw(12) << "-";
+ }
+ cout << endl;
+ }
+ cout.width(w); // reset the field width to previous value.
+ cout.flags(f); // reset the flags to previous values.
+
for (int i = 0; i < 4; i++)
{
cout << "===== Hit on chamber: " << i+7 << " =====" << endl;
and fHit[0] == track.fHit[0] and fHit[1] == track.fHit[1]
and fHit[2] == track.fHit[2] and fHit[3] == track.fHit[3];
}
+
+
+void AliHLTMUONMansoTrack::SetDebugData(Float_t zmiddle, Float_t bfieldintegral)
+{
+ // Sets the extra debugging information.
+
+ fZmiddle = zmiddle;
+ fQBL = bfieldintegral;
+}
+
+
+const TVector3& AliHLTMUONMansoTrack::RoICentre(Int_t chamber) const
+{
+ // Returns the ragion of interest centre point for a given chamber.
+
+ if (7 <= chamber and chamber <= 10) return fRoICentre[chamber - 7];
+
+ AliError(Form(
+ "Chamber number %d is not in the valid range [7..10].",
+ int(chamber)
+ ));
+ static TVector3 zeroVector(0, 0, 0);
+ return zeroVector;
+}
+
+
+Float_t AliHLTMUONMansoTrack::RoIRadius(Int_t chamber) const
+{
+ // Returns the ragion of interest radius for a given chamber.
+
+ if (7 <= chamber and chamber <= 10) return fRoIRadius[chamber - 7];
+
+ AliError(Form(
+ "Chamber number %d is not in the valid range [7..10].",
+ int(chamber)
+ ));
+ return -1;
+}
+
+
+void AliHLTMUONMansoTrack::SetRoI(Int_t chamber, Float_t x, Float_t y, Float_t z, Float_t r)
+{
+ // Returns the ragion of interest radius for a given chamber.
+
+ if (7 <= chamber and chamber <= 10)
+ {
+ fRoICentre[chamber - 7] = TVector3(x, y, z);
+ fRoIRadius[chamber - 7] = r;
+ }
+ else
+ {
+ AliError(Form(
+ "Chamber number %d is not in the valid range [7..10].",
+ int(chamber)
+ ));
+ }
+}
* the calculation of the momentum. Value returned in (T.m) tesla metres.
*/
Float_t QBL() const { return fQBL; }
+
+ /**
+ * Sets the extra debugging information.
+ * @param zmiddle The Z coordinate of the middle of the magnetic field
+ * assumed during momentum calculation.
+ * @param bfieldintegral The integrated magnetic field strength assumed
+ * during momentum calculation.
+ */
+ void SetDebugData(Float_t zmiddle, Float_t bfieldintegral);
+
+ /**
+ * Returns the Region of Interest (RoI) centre point for the given chamber.
+ * \param chamber Specifies the chamber for which to return the centre point.
+ * Valid values are in the range [7..10].
+ * \return The RoI centre or a zero vector if the RoI is not set or the
+ * chamber is an incorrect value.
+ */
+ const TVector3& RoICentre(Int_t chamber) const;
+
+ /**
+ * Returns the Region of Interest (RoI) radius for the given chamber.
+ * \param chamber Specifies the chamber for which to return the radius.
+ * Valid values are in the range [7..10].
+ * \return The RoI radius or -1 if the RoI is not set or the chamber is
+ * an incorrect value.
+ */
+ Float_t RoIRadius(Int_t chamber) const;
+
+ /**
+ * Sets the Region of Interest (RoI) on the given chamber.
+ * \param chamber Specifies the chamber for which to return the radius.
+ * Valid values are in the range [7..10].
+ * \param x X coordinate of the RoI centre point.
+ * \param y Y coordinate of the RoI centre point.
+ * \param z Z coordinate of the RoI centre point.
+ * \param r radius of the RoI.
+ */
+ void SetRoI(Int_t chamber, Float_t x, Float_t y, Float_t z, Float_t r);
private:
Float_t fChi2; ///< Chi squared of fit.
const AliHLTMUONTriggerRecord* fTrigRec; ///< Corresponding trigger record.
const AliHLTMUONRecHit* fHit[4]; ///< Particle hits on tracking chambers 7 to 10.
+ TVector3 fRoICentre[4]; ///< Region of Interest centre points.
+ Float_t fRoIRadius[4]; ///< Region of Interest radii.
// The following is debugging information and may not be filled if the
// dHLT components were not set to produce this information.
///
#include "AliHLTMUONProcessor.h"
+#include "AliHLTMUONConstants.h"
#include "AliMUONRecoParam.h"
#include "AliCDBManager.h"
#include "AliCDBStorage.h"
#include "AliCDBEntry.h"
+#include "AliGRPManager.h"
+#include "AliGRPObject.h"
+#include "AliMagF.h"
#include "AliMpCDB.h"
#include "AliMpDDLStore.h"
#include "AliMpDEStore.h"
+#include "TGeoGlobalMagField.h"
#include "TMap.h"
#include "TObjString.h"
#include "TString.h"
}
+int AliHLTMUONProcessor::FetchFieldIntegral(Double_t& bfieldintegral) const
+{
+ // Fetches the correct dipole magnetic field integral to use.
+
+ Float_t currentL3 = 0;
+ Float_t currentDip = 0;
+
+ if (TGeoGlobalMagField::Instance() == NULL or
+ (TGeoGlobalMagField::Instance() != NULL and TGeoGlobalMagField::Instance()->GetField() == NULL)
+ )
+ {
+ HLTWarning("The magnetic field has not been set in TGeoGlobalMagField."
+ " Will try and load the GRP entry directly."
+ );
+
+ AliGRPManager grpman;
+ if (not grpman.ReadGRPEntry() or grpman.GetGRPData() == NULL)
+ {
+ HLTError("GRP entry could not be loaded.");
+ return -EIO;
+ }
+
+ const AliGRPObject* grp = grpman.GetGRPData();
+ Char_t polarityL3 = grp->GetL3Polarity();
+ Char_t polarityDip = grp->GetDipolePolarity();
+ currentL3 = grp->GetL3Current(AliGRPObject::kMean);
+ currentDip = grp->GetDipoleCurrent(AliGRPObject::kMean);
+ if (polarityL3 == AliGRPObject::GetInvalidChar())
+ {
+ HLTError("L3 polarity in GRP is invalid.");
+ return -EPROTO;
+ }
+ if (polarityDip == AliGRPObject::GetInvalidChar())
+ {
+ HLTError("Dipole polarity in GRP is invalid.");
+ return -EPROTO;
+ }
+ if (currentL3 == AliGRPObject::GetInvalidFloat())
+ {
+ HLTError("L3 current in GRP is invalid.");
+ return -EPROTO;
+ }
+ if (currentDip == AliGRPObject::GetInvalidFloat())
+ {
+ HLTError("Dipole current in GRP is invalid.");
+ return -EPROTO;
+ }
+ if (grp->IsPolarityConventionLHC())
+ {
+ currentL3 *= (polarityL3 ? -1:1);
+ currentDip *= (polarityDip ? -1:1);
+ }
+ else
+ {
+ currentL3 *= (polarityL3 ? -1:1);
+ currentDip *= (polarityDip ? 1:-1);
+ }
+ }
+ else
+ {
+ TVirtualMagField* vfield = TGeoGlobalMagField::Instance()->GetField();
+ AliMagF* field = dynamic_cast<AliMagF*>(vfield);
+ if (vfield->IsA() != AliMagF::Class() and field != NULL)
+ {
+ HLTError(Form(
+ "The magnetic field is not of type AliMagF."
+ " Do not know how to handle class of type '%s'.",
+ vfield->ClassName()
+ ));
+ return -EPROTO;
+ }
+ currentL3 = field->GetCurrentSol();
+ currentDip = field->GetCurrentDip();
+ }
+
+ const char* path = AliHLTMUONConstants::FieldIntegralsCDBPath();
+ TMap* map = NULL;
+ int result = FetchTMapFromCDB(path, map);
+ if (result != 0) return result;
+ const char* paramName = Form("L3_current=%0.2e;Dipole_current=%0.2e", currentL3, currentDip);
+ Double_t value;
+ result = GetFloatFromTMap(map, paramName, value, path);
+ if (result != 0) return result;
+ bfieldintegral = value;
+ return 0;
+}
+
+
int AliHLTMUONProcessor::LoadRecoParamsFromCDB(AliMUONRecoParam*& params) const
{
/// Fetches the reconstruction parameters object from the CDB for MUON.
const char* pathToEntry = NULL, const char* prettyName = NULL
) const;
+ /**
+ * Loads the appropriate field integral from the CDB based on the currently
+ * loaded global magnetic field in TGeoGlobalMagField. If the global field is
+ * not loaded then we try load the GRP entry to figure out the correct integral.
+ * [out] \param bfieldintegral Will be filled with the dipole magnetic field
+ * integral value to use.
+ * \return Zero if the field integral could be found and is valid. Otherwise an
+ * error code is returned, which is compatible with the HLT framework.
+ */
+ int FetchFieldIntegral(Double_t& bfieldintegral) const;
+
/**
* Fetches the reconstruction parameters object from the CDB for MUON.
* [out] \param params This will be filled with the reconstruction
<< setw(12) << "DetElemID" << endl;
for (int i = 0; i < 4; i++)
{
- cout << setw(9) << i+11
- << setw(14) << fHit[i].X()
- << setw(12) << fHit[i].Y()
- << setw(12) << fHit[i].Z()
- << setw(12) << fDetElemId[i]
- << endl;
+ cout << setw(9) << i+11;
+ if (fDetElemId[i] != -1)
+ {
+ cout << setw(14) << fHit[i].X()
+ << setw(12) << fHit[i].Y()
+ << setw(12) << fHit[i].Z()
+ << setw(12) << fDetElemId[i]
+ << endl;
+ }
+ else
+ {
+ cout << setw(14) << "-"
+ << setw(12) << "-"
+ << setw(12) << "-"
+ << setw(12) << "-"
+ << endl;
+ }
}
cout << setw(9) << "Chamber"
<< setw(18+17*2) << "X bit patterns for local boards"
);
for (int k = 0; k < 4; k++)
{
+ if (not hitset[k]) continue;
Int_t detElemId = AliHLTMUONUtils::GetDetElemIdFromFlags(t.fHit[k].fFlags);
tr->SetHit(k+11, t.fHit[k].fX, t.fHit[k].fY, t.fHit[k].fZ, detElemId);
}
0, 0, 0, 0, 0, sourceDDL
);
}
-
- for (Int_t j = 0; j < 4; ++j)
+ else
{
- if (triginfo.fDetElemId[j] != trigrec->DetElemId(j+11))
+ for (Int_t j = 0; j < 4; ++j)
{
- HLTWarning("Found a trigger record with a hit on chamber %d with a different"
- " detector element ID %d than the debug information %d.",
- j, trigrec->DetElemId(j+11), triginfo.fDetElemId[j]
- );
+ if (trigrec->DetElemId(j+11) != -1 and triginfo.fDetElemId[j] != trigrec->DetElemId(j+11))
+ {
+ HLTWarning("Found a trigger record with a hit on chamber %d with a different"
+ " detector element ID %d than the debug information %d.",
+ j, trigrec->DetElemId(j+11), triginfo.fDetElemId[j]
+ );
+ }
}
}
}
}
+ std::map<AliHLTInt32_t, AliHLTMUONMansoTrack*> trackMap;
+
// Now we can look for tracks to add. We needed the ROOT trigger records
// and reco hits created before we can create track objects.
for (block = GetFirstInputBlock(AliHLTMUONConstants::MansoTracksBlockDataType());
for (AliHLTUInt32_t n = 0; n < inblock.Nentries(); n++)
{
const AliHLTMUONMansoTrackStruct& t = inblock[n];
-
- AliHLTMUONParticleSign sign;
- bool hitset[4];
- AliHLTMUONUtils::UnpackMansoTrackFlags(
- t.fFlags, sign, hitset
- );
-
- // Try find the trigger record in 'event'.
- const AliHLTMUONTriggerRecord* trigrec = NULL;
- for (Int_t k = 0; k < event.Array().GetEntriesFast(); k++)
- {
- if (event.Array()[k]->IsA() != AliHLTMUONTriggerRecord::Class())
- continue;
- const AliHLTMUONTriggerRecord* tk =
- static_cast<const AliHLTMUONTriggerRecord*>(event.Array()[k]);
- if (tk->Id() == t.fTrigRec)
- {
- trigrec = tk;
- break;
- }
- }
-
- // Now try find the hits in 'event'.
- // If they cannot be found then create new ones.
- const AliHLTMUONRecHit* hit7 = NULL;
- const AliHLTMUONRecHit* hit8 = NULL;
- const AliHLTMUONRecHit* hit9 = NULL;
- const AliHLTMUONRecHit* hit10 = NULL;
- for (Int_t k = 0; k < event.Array().GetEntriesFast(); k++)
- {
- if (event.Array()[k]->IsA() != AliHLTMUONRecHit::Class())
- continue;
- const AliHLTMUONRecHit* h =
- static_cast<const AliHLTMUONRecHit*>(event.Array()[k]);
-
- if (hitset[0] and h->X() == t.fHit[0].fX and h->Y() == t.fHit[0].fY
- and h->Z() == t.fHit[0].fZ)
- {
- hit7 = h;
- }
- if (hitset[1] and h->X() == t.fHit[1].fX and h->Y() == t.fHit[1].fY
- and h->Z() == t.fHit[1].fZ)
- {
- hit8 = h;
- }
- if (hitset[2] and h->X() == t.fHit[2].fX and h->Y() == t.fHit[2].fY
- and h->Z() == t.fHit[2].fZ)
- {
- hit9 = h;
- }
- if (hitset[3] and h->X() == t.fHit[3].fX and h->Y() == t.fHit[3].fY
- and h->Z() == t.fHit[3].fZ)
- {
- hit10 = h;
- }
- }
- AliHLTMUONRecHit* newhit;
- if (hitset[0] and hit7 == NULL)
- {
- newhit = new AliHLTMUONRecHit(t.fHit[0].fX, t.fHit[0].fY, t.fHit[0].fZ);
- event.Add(newhit);
- hit7 = newhit;
- }
- if (hitset[1] and hit8 == NULL)
- {
- newhit = new AliHLTMUONRecHit(t.fHit[1].fX, t.fHit[1].fY, t.fHit[1].fZ);
- event.Add(newhit);
- hit8 = newhit;
- }
- if (hitset[2] and hit9 == NULL)
+ trackMap[t.fId] = AddTrack(event, t);
+ }
+ }
+
+ // Look for Manso track candidates to add the debug info to the tracks.
+ for (block = GetFirstInputBlock(AliHLTMUONConstants::MansoCandidatesBlockDataType());
+ block != NULL;
+ block = GetNextInputBlock()
+ )
+ {
+ specification |= block->fSpecification;
+ AliHLTMUONMansoCandidatesBlockReader inblock(block->fPtr, block->fSize);
+ if (not BlockStructureOk(inblock))
+ {
+ if (DumpDataOnError()) DumpEvent(evtData, trigData);
+ continue;
+ }
+
+ for (AliHLTUInt32_t n = 0; n < inblock.Nentries(); n++)
+ {
+ const AliHLTMUONMansoCandidateStruct& tc = inblock[n];
+ AliHLTMUONMansoTrack* mtrack = trackMap[tc.fTrack.fId];
+ if (mtrack == NULL)
{
- newhit = new AliHLTMUONRecHit(t.fHit[2].fX, t.fHit[2].fY, t.fHit[2].fZ);
- event.Add(newhit);
- hit9 = newhit;
+ // If we got here then we could not find the corresponding Manso
+ // track. So we need to create and add a new track object.
+ mtrack = AddTrack(event, tc.fTrack);
}
- if (hitset[3] and hit10 == NULL)
+ mtrack->SetDebugData(tc.fZmiddle, tc.fBl);
+ for (AliHLTUInt32_t i = 0; i < 4; ++i)
{
- newhit = new AliHLTMUONRecHit(t.fHit[3].fX, t.fHit[3].fY, t.fHit[3].fZ);
- event.Add(newhit);
- hit10 = newhit;
+ if (tc.fRoI[i] == AliHLTMUONConstants::NilMansoRoIStruct()) continue;
+ mtrack->SetRoI(i+7, tc.fRoI[i].fX, tc.fRoI[i].fY, tc.fRoI[i].fZ, tc.fRoI[i].fRadius);
}
-
- AliHLTMUONMansoTrack* tr = new AliHLTMUONMansoTrack(
- t.fId, sign, t.fPx, t.fPy, t.fPz, t.fChi2,
- trigrec, hit7, hit8, hit9, hit10
- );
- event.Add(tr);
}
}
return 0;
}
+
+AliHLTMUONMansoTrack* AliHLTMUONRootifierComponent::AddTrack(
+ AliHLTMUONEvent& event, const AliHLTMUONMansoTrackStruct& track
+ )
+{
+ // Converts the track structure and adds it to the event object.
+
+ AliHLTMUONParticleSign sign;
+ bool hitset[4];
+ AliHLTMUONUtils::UnpackMansoTrackFlags(
+ track.fFlags, sign, hitset
+ );
+
+ // Try find the trigger record in 'event'.
+ const AliHLTMUONTriggerRecord* trigrec = NULL;
+ for (Int_t k = 0; k < event.Array().GetEntriesFast(); k++)
+ {
+ if (event.Array()[k]->IsA() != AliHLTMUONTriggerRecord::Class())
+ continue;
+ const AliHLTMUONTriggerRecord* tk =
+ static_cast<const AliHLTMUONTriggerRecord*>(event.Array()[k]);
+ if (tk->Id() == track.fTrigRec)
+ {
+ trigrec = tk;
+ break;
+ }
+ }
+
+ // Now try find the hits in 'event'.
+ // If they cannot be found then create new ones.
+ const AliHLTMUONRecHit* hit7 = NULL;
+ const AliHLTMUONRecHit* hit8 = NULL;
+ const AliHLTMUONRecHit* hit9 = NULL;
+ const AliHLTMUONRecHit* hit10 = NULL;
+ for (Int_t k = 0; k < event.Array().GetEntriesFast(); k++)
+ {
+ if (event.Array()[k]->IsA() != AliHLTMUONRecHit::Class())
+ continue;
+ const AliHLTMUONRecHit* h =
+ static_cast<const AliHLTMUONRecHit*>(event.Array()[k]);
+
+ if (hitset[0] and h->X() == track.fHit[0].fX and h->Y() == track.fHit[0].fY
+ and h->Z() == track.fHit[0].fZ)
+ {
+ hit7 = h;
+ }
+ if (hitset[1] and h->X() == track.fHit[1].fX and h->Y() == track.fHit[1].fY
+ and h->Z() == track.fHit[1].fZ)
+ {
+ hit8 = h;
+ }
+ if (hitset[2] and h->X() == track.fHit[2].fX and h->Y() == track.fHit[2].fY
+ and h->Z() == track.fHit[2].fZ)
+ {
+ hit9 = h;
+ }
+ if (hitset[3] and h->X() == track.fHit[3].fX and h->Y() == track.fHit[3].fY
+ and h->Z() == track.fHit[3].fZ)
+ {
+ hit10 = h;
+ }
+ }
+ AliHLTMUONRecHit* newhit;
+ if (hitset[0] and hit7 == NULL)
+ {
+ newhit = new AliHLTMUONRecHit(track.fHit[0].fX, track.fHit[0].fY, track.fHit[0].fZ);
+ event.Add(newhit);
+ hit7 = newhit;
+ }
+ if (hitset[1] and hit8 == NULL)
+ {
+ newhit = new AliHLTMUONRecHit(track.fHit[1].fX, track.fHit[1].fY, track.fHit[1].fZ);
+ event.Add(newhit);
+ hit8 = newhit;
+ }
+ if (hitset[2] and hit9 == NULL)
+ {
+ newhit = new AliHLTMUONRecHit(track.fHit[2].fX, track.fHit[2].fY, track.fHit[2].fZ);
+ event.Add(newhit);
+ hit9 = newhit;
+ }
+ if (hitset[3] and hit10 == NULL)
+ {
+ newhit = new AliHLTMUONRecHit(track.fHit[3].fX, track.fHit[3].fY, track.fHit[3].fZ);
+ event.Add(newhit);
+ hit10 = newhit;
+ }
+
+ AliHLTMUONMansoTrack* tr = new AliHLTMUONMansoTrack(
+ track.fId, sign, track.fPx, track.fPy, track.fPz, track.fChi2,
+ trigrec, hit7, hit8, hit9, hit10
+ );
+ event.Add(tr);
+ return tr;
+}
#include "AliHLTMUONProcessor.h"
+class AliHLTMUONEvent;
+class AliHLTMUONMansoTrack;
+extern "C" struct AliHLTMUONMansoTrackStruct;
+
/**
* \class AliHLTMUONRootifierComponent
* \brief Converts dHLT raw data blocks into ROOT objects.
AliHLTMUONRootifierComponent(const AliHLTMUONRootifierComponent& /*object*/);
AliHLTMUONRootifierComponent& operator = (const AliHLTMUONRootifierComponent& /*object*/);
+ /**
+ * This method creates a AliHLTMUONMansoTrack object from the track structure
+ * and adds it to the dHLT event object.
+ * \param event The dHLT event object.
+ * \param track The track structure to convert and add to the event.
+ */
+ AliHLTMUONMansoTrack* AddTrack(AliHLTMUONEvent& event, const AliHLTMUONMansoTrackStruct& track);
+
bool fWarnForUnexpecedBlock; /// Flag indicating if we should log a warning if we got a block of an unexpected type.
ClassDef(AliHLTMUONRootifierComponent, 0); // Converter component of dHLT raw data.
/// \param hitset Flags indicating which hits were set in the trigger record.
/// \return true if the line could be fitted or false otherwise.
+ bool lineOk = FitLine(trigger, hitset);
+ if (lineOk)
+ {
+ // Calculate ideal points on chambers 11 and 13:
+ fgIdealX1 = fgMzx * fgIdealZ1 + fgCzx;
+ fgIdealY1 = fgMzy * fgIdealZ1 + fgCzy;
+ fgIdealX2 = fgMzx * fgIdealZ2 + fgCzx;
+ fgIdealY2 = fgMzy * fgIdealZ2 + fgCzy;
+ }
+ return lineOk;
+}
+
+
+bool AliHLTMUONCalculations::FitLine(
+ const AliHLTMUONTriggerRecordStruct& trigger,
+ const bool hitset[4]
+ )
+{
+ /// Performs a straight line fit to the trigger record hits which are indicated
+ /// by the hitset flags array.
+ /// \param trigger The trigger record structure to which we fit a line.
+ /// \param hitset Flags indicating which hits to use and were set in the trigger record.
+ /// \return true if the line could be fitted or false otherwise.
+
AliHLTFloat32_t sumX = 0;
AliHLTFloat32_t sumY = 0;
AliHLTFloat32_t sumZ = 0;
fgCzx = meanX - fgMzx * meanZ;
fgCzy = meanY - fgMzy * meanZ;
- // Calculate ideal points on chambers 11 and 13:
- fgIdealX1 = fgMzx * fgIdealZ1 + fgCzx;
- fgIdealY1 = fgMzy * fgIdealZ1 + fgCzy;
- fgIdealX2 = fgMzx * fgIdealZ2 + fgCzx;
- fgIdealY2 = fgMzy * fgIdealZ2 + fgCzy;
-
return true;
}
{
/// Calculates the chi squared value for the set of data points given
/// the fitted slope and coefficient parameters previously fitted by
- /// LineFit(x, y, z, n);
+ /// one of FitLine(x, y, z, n) or FitLineToTriggerRecord
/// The fgSigmaX2 and fgSigmaY2 are used as the variance for the X and
/// Y coordinates respectively. Note we assume that the covariance terms
/// are zero.
}
return chi2;
}
+
+
+AliHLTFloat32_t AliHLTMUONCalculations::AliHLTMUONCalculations::ComputeChi2(
+ const AliHLTMUONTriggerRecordStruct& trigger,
+ const bool hitset[4]
+ )
+{
+ /// Calculates the chi squared value for trigger record using the hits
+ /// indicated by the hitset array.
+ /// \param trigger The trigger record structure for which we compute the chi squared value.
+ /// \param hitset Flags indicating which hits to use and were set in the trigger record.
+ /// \return The chi squared value or -1 if it could not be calculated.
+
+ if (not FitLine(trigger, hitset)) return -1;
+ AliHLTFloat32_t chi2 = 0;
+ for (AliHLTUInt32_t i = 0; i < 4; i++)
+ {
+ if (hitset[i])
+ {
+ AliHLTFloat32_t residualX = fgMzx * trigger.fHit[i].fZ + fgCzx - trigger.fHit[i].fX;
+ AliHLTFloat32_t residualY = fgMzy * trigger.fHit[i].fZ + fgCzy - trigger.fHit[i].fY;
+ chi2 += residualX*residualX/fgSigmaX2 + residualY*residualY/fgSigmaY2;
+ }
+ }
+ return chi2;
+}
const bool hitset[4]
);
+ static bool FitLine(
+ const AliHLTMUONTriggerRecordStruct& trigger,
+ const bool hitset[4]
+ );
+
static AliHLTFloat32_t IdealZ1() { return fgIdealZ1; }
static void IdealZ1(AliHLTFloat32_t value) { fgIdealZ1 = value; }
static AliHLTFloat32_t IdealZ2() { return fgIdealZ2; }
const AliHLTFloat32_t* z, AliHLTUInt32_t n
);
+ static AliHLTFloat32_t ComputeChi2(
+ const AliHLTMUONTriggerRecordStruct& trigger,
+ const bool hitset[4]
+ );
+
static AliHLTFloat32_t SigmaX2() { return fgSigmaX2; }
static void SigmaX2(AliHLTFloat32_t value) { fgSigmaX2 = (value != 0 ? value : 1.); }
static AliHLTFloat32_t SigmaY2() { return fgSigmaY2; }
/**************************************************************************
- * This file is property of and copyright by the ALICE HLT Project *
+ * This file is property of and copyright by the ALICE HLT Project *
* All rights reserved. *
* *
* Primary Authors: *
* without fee, provided that the above copyright notice appears in all *
* copies and that both the copyright notice and this permission notice *
* appear in the supporting documentation. The authors make no claims *
- * about the suitability of this software for any purpose. It is *
+ * about the suitability of this software for any purpose. It is *
* provided "as is" without express or implied warranty. *
**************************************************************************/
#include "AliHLTMUONCalculations.h"
#include "AliHLTMUONConstants.h"
#include "AliHLTMUONUtils.h"
+#include "AliHLTMUONTriggerRecordsBlockStruct.h"
+#include "AliHLTMUONMansoTracksBlockStruct.h"
+#include "AliHLTMUONMansoCandidatesBlockStruct.h"
#include <cmath>
AliHLTMUONMansoTrackerFSM::AliHLTMUONMansoTrackerFSM() :
+ AliHLTLogging(),
fCallback(NULL),
fSm4state(kSM4Idle),
fSm5state(kSM5Idle),
fSt5rec(),
fFoundPoint(),
fTriggerId(-1),
- fTrackId(0)
+ fTrackId(0),
+ fMakeCandidates(false),
+ fCandidatesCount(0),
+ fCandidatesSize(0),
+ fCandidates(NULL)
{
// Default constructor
}
+AliHLTMUONMansoTrackerFSM::~AliHLTMUONMansoTrackerFSM()
+{
+ // Default destructor cleans up any allocated memory.
+
+ if (fCandidates != NULL) delete [] fCandidates;
+}
+
+
void AliHLTMUONMansoTrackerFSM::FindTrack(const AliHLTMUONTriggerRecordStruct& trigger)
{
// Tries to find the track from the trigger seed.
// that method could call one of our methods again, so we need to be
// in a consistant internal state.
fSm5state = kWaitChamber10;
+
+ if (fMakeCandidates)
+ {
+ fMc1.fCandidate = AddTrackCandidate();
+ if (fMc1.fCandidate != NULL)
+ {
+ *fMc1.fCandidate = AliHLTMUONConstants::NilMansoCandidateStruct();
+ fMc1.fCandidate->fTrack.fId = -1;
+ fMc1.fCandidate->fTrack.fTrigRec = fTriggerId;
+ fMc1.fCandidate->fTrack.fChi2 = -1;
+ fMc1.fCandidate->fZmiddle = AliHLTMUONCalculations::Zf();
+ fMc1.fCandidate->fBl = AliHLTMUONCalculations::QBL();
+ fMc1.fCandidate->fRoI[3].fX = fMc1.fRoi.Centre().fX;
+ fMc1.fCandidate->fRoI[3].fY = fMc1.fRoi.Centre().fY;
+ fMc1.fCandidate->fRoI[3].fZ = fMc1.fRoi.Centre().fZ;
+ fMc1.fCandidate->fRoI[3].fRadius = fMc1.fRoi.Radius();
+ }
+ }
AliHLTFloat32_t left, right, bottom, top;
fMc1.fRoi.GetBoundaryBox(left, right, bottom, top);
track.fFlags = AliHLTMUONUtils::PackMansoTrackFlags(
AliHLTMUONCalculations::Sign(), hitset
);
+
+ if (fMakeCandidates)
+ {
+ AliHLTMUONMansoCandidateStruct* candidate = fSt5rec->fTag.fCandidate;
+ if (candidate != NULL)
+ {
+ candidate->fTrack = track;
+ }
+ }
+
return calculated;
}
switch (fSm4state)
{
case kWaitChamber7:
- fSm4state = kWaitMoreChamber7;
-
+ // We switch state below.
+
case kWaitMoreChamber7:
for (AliHLTUInt32_t j = 0; j < count; j++)
{
// Check that the cluster actually is in our region of interest on station 4.
if ( data->fRoi.Contains(cluster) )
{
+ // Go to next wait state only if we actually found anything in the RoI.
+ fSm4state = kWaitMoreChamber7;
+
DebugTrace("Adding cluster [" << cluster.fX << ", " << cluster.fY << "] from chamber 7.");
AliStation4Data* newdata = fSt4points.Add();
newdata->fClusterPoint = cluster;
switch (fSm4state)
{
case kWaitChamber8:
- fSm4state = kWaitMoreChamber8;
fSt4chamber = kChamber8;
-
+
case kWaitMoreChamber8:
for (AliHLTUInt32_t j = 0; j < count; j++)
{
// Check that the cluster actually is in our region of interest on station 4.
if ( data->fRoi.Contains(cluster) )
{
+ // Go to next wait state only if we actually found anything in the RoI.
+ fSm4state = kWaitMoreChamber8;
+
DebugTrace("Adding cluster [" << cluster.fX << ", " << cluster.fY << "] from chamber 8.");
AliStation4Data* newdata = fSt4points.Add();
newdata->fClusterPoint = cluster;
switch (fSm5state)
{
case kWaitChamber9:
- fSm5state = kWaitMoreChamber9;
fSm4state = kWaitChamber8; // Start SM4.
-
+
case kWaitMoreChamber9:
for (AliHLTUInt32_t j = 0; j < count; j++)
{
// Check that the cluster actually is in our region of interest on station 5.
if ( fMc1.fRoi.Contains(cluster) )
{
+ // Go to next wait state only if we actually found anything in the RoI.
+ fSm5state = kWaitMoreChamber9;
+
DebugTrace("Adding cluster [" << cluster.fX << ", " << cluster.fY << "] from chamber 9.");
AliStation5Data* data = fSt5data.Add();
data->fClusterPoint = cluster;
- ProjectToStation4(data, fgZ9); // This adds a new request for station 4.
+ ProjectToStation4(data, fgZ9, 2); // This adds a new request for station 4.
}
}
break;
switch (fSm5state)
{
case kWaitChamber10:
- fSm5state = kWaitMoreChamber10;
fSm4state = kWaitChamber8; // Start SM4.
case kWaitMoreChamber10:
// Check that the cluster actually is in our region of interest on station 5.
if ( fMc1.fRoi.Contains(cluster) )
{
+ // Go to next wait state only if we actually found anything in the RoI.
+ fSm5state = kWaitMoreChamber10;
+
DebugTrace("Adding cluster [" << cluster.fX << ", " << cluster.fY << "] from chamber 10.");
AliStation5Data* data = fSt5data.Add();
data->fClusterPoint = cluster;
- ProjectToStation4(data, fgZ10); // This adds a new request for station 4.
+ ProjectToStation4(data, fgZ10, 3); // This adds a new request for station 4.
}
}
break;
AliStation5Data* data = fSt5data.Add();
data->fClusterPoint = rec->fClusterPoint;
data->fTag.fLine = rec->fTag.fLine;
+ data->fTag.fCandidate = rec->fTag.fCandidate;
// Rebuild a region of interest for chamber 7.
// Remember the parameters a and b are station specific.
data->fTag.fChamber = kChamber7;
data->fTag.fRoi.Create(p7, fgA7, fgB7);
+ if (fMakeCandidates and data->fTag.fCandidate != NULL)
+ {
+ data->fTag.fCandidate->fRoI[0].fX = data->fTag.fRoi.Centre().fX;
+ data->fTag.fCandidate->fRoI[0].fY = data->fTag.fRoi.Centre().fY;
+ data->fTag.fCandidate->fRoI[0].fZ = data->fTag.fRoi.Centre().fZ;
+ data->fTag.fCandidate->fRoI[0].fRadius = data->fTag.fRoi.Radius();
+ }
+
AliHLTFloat32_t left, right, bottom, top;
data->fTag.fRoi.GetBoundaryBox(left, right, bottom, top);
// Make request for chamber 7 data.
// No clusters found on chamber 10 so we need to make a request for
// clusters from chamber 9:
AliHLTMUONRecHitStruct p9 = fMc1.fLine.FindIntersectWithXYPlain( fgZ9 );
-
+
// Build a region of interest for tracking station 5 (chamber 9).
// Remember the parameters a and b are station specific.
fMc1.fChamber = kChamber9;
fMc1.fRoi.Create(p9, fgA9, fgB9);
-
+
+ if (fMakeCandidates and fMc1.fCandidate != NULL)
+ {
+ fMc1.fCandidate->fRoI[2].fX = fMc1.fRoi.Centre().fX;
+ fMc1.fCandidate->fRoI[2].fY = fMc1.fRoi.Centre().fY;
+ fMc1.fCandidate->fRoI[2].fZ = fMc1.fRoi.Centre().fZ;
+ fMc1.fCandidate->fRoI[2].fRadius = fMc1.fRoi.Radius();
+ }
+
AliHLTFloat32_t left, right, bottom, top;
fMc1.fRoi.GetBoundaryBox(left, right, bottom, top);
RequestClusters(left, right, bottom, top, kChamber9, &fMc1);
void AliHLTMUONMansoTrackerFSM::ProjectToStation4(
- AliStation5Data* data, register AliHLTFloat32_t station5z
+ AliStation5Data* data, AliHLTFloat32_t station5z, AliHLTUInt32_t chamberSt5
)
{
// Perform chamber specific operations:
|| fSm4state == kWaitChamber7
|| fSm4state == kWaitMoreChamber7
);
+ assert( chamberSt5 == 2 or chamberSt5 == 3 );
AliTagData* tag = &data->fTag;
+ int chamber = 0;
if (fSm4state == kWaitChamber8 || fSm4state == kWaitMoreChamber8)
{
// Form the vector line between trigger station 1 and tracking station 5,
// Build a region of interest for tracking station 4.
tag->fChamber = kChamber8;
tag->fRoi.Create(intercept, fgA8, fgB8);
+ chamber = 1;
}
else
{
// Build a region of interest for tracking station 4.
tag->fChamber = kChamber7;
tag->fRoi.Create(intercept, fgA7, fgB7);
+ chamber = 0;
+ }
+
+ if (fMakeCandidates)
+ {
+ // Make a copy of the track candidate if the exisiting track candidate
+ // has already had its point on the given chamber filled.
+ if (fMc1.fCandidate != NULL and
+ fMc1.fCandidate->fTrack.fHit[chamberSt5] == AliHLTMUONConstants::NilRecHitStruct()
+ )
+ {
+ tag->fCandidate = fMc1.fCandidate;
+ }
+ else
+ {
+ tag->fCandidate = AddTrackCandidate();
+ if (tag->fCandidate != NULL) *tag->fCandidate = *fMc1.fCandidate;
+ }
+ // Now fill the cluster point found on station 5 and RoI on station 4.
+ if (tag->fCandidate != NULL)
+ {
+ tag->fCandidate->fTrack.fHit[chamberSt5] = data->fClusterPoint;
+ tag->fCandidate->fRoI[chamber].fX = tag->fRoi.Centre().fX;
+ tag->fCandidate->fRoI[chamber].fY = tag->fRoi.Centre().fY;
+ tag->fCandidate->fRoI[chamber].fZ = tag->fRoi.Centre().fZ;
+ tag->fCandidate->fRoI[chamber].fRadius = tag->fRoi.Radius();
+ }
}
// Make the request for clusters from station 4.
NoTrackFound();
}
+
+AliHLTMUONMansoCandidateStruct* AliHLTMUONMansoTrackerFSM::AddTrackCandidate()
+{
+ // Adds a new track candidate to the fCandidates list and returns a pointer
+ // to the new structure.
+
+ // First allocate or reallocate buffer if necessary.
+ if (fCandidates == NULL)
+ {
+ try
+ {
+ fCandidates = new AliHLTMUONMansoCandidateStruct[1024];
+ }
+ catch (...)
+ {
+ HLTError("Could not allocate buffer space for Manso track candidates.");
+ return NULL;
+ }
+ fCandidatesSize = 1024;
+ }
+ else if (fCandidatesCount >= fCandidatesSize)
+ {
+ AliHLTMUONMansoCandidateStruct* newbuf = NULL;
+ try
+ {
+ newbuf = new AliHLTMUONMansoCandidateStruct[fCandidatesSize*2];
+ }
+ catch (...)
+ {
+ HLTError("Could not allocate more buffer space for Manso track candidates.");
+ return NULL;
+ }
+ for (AliHLTUInt32_t i = 0; i < fCandidatesSize; ++i) newbuf[i] = fCandidates[i];
+ delete [] fCandidates;
+ fCandidates = newbuf;
+ fCandidatesSize = fCandidatesSize*2;
+ }
+
+ return &fCandidates[fCandidatesCount++];
+}
#ifndef ALIHLTMUONMANSOTRACKERFSM_H
#define ALIHLTMUONMANSOTRACKERFSM_H
/**************************************************************************
- * This file is property of and copyright by the ALICE HLT Project *
+ * This file is property of and copyright by the ALICE HLT Project *
* All rights reserved. *
* *
* Primary Authors: *
* without fee, provided that the above copyright notice appears in all *
* copies and that both the copyright notice and this permission notice *
* appear in the supporting documentation. The authors make no claims *
- * about the suitability of this software for any purpose. It is *
+ * about the suitability of this software for any purpose. It is *
* provided "as is" without express or implied warranty. *
**************************************************************************/
/// @brief Declaration of the AliHLTMUONMansoTrackerFSM class which implements the Manso tracking algorithm.
///
+#include "AliHLTLogging.h"
#include "AliHLTMUONDataTypes.h"
#include "AliHLTMUONList.h"
#include "AliHLTMUONCountedList.h"
#include "AliHLTMUONRecHitsBlockStruct.h"
-#include "AliHLTMUONTriggerRecordsBlockStruct.h"
-#include "AliHLTMUONMansoTracksBlockStruct.h"
#include "AliHLTMUONMansoTrackerFSMCallback.h"
#include <cassert>
+extern "C" struct AliHLTMUONTriggerRecordStruct;
+extern "C" struct AliHLTMUONMansoTrackStruct;
+extern "C" struct AliHLTMUONMansoCandidateStruct;
+
/**
* The AliHLTMUONMansoTrackerFSM implements the Manso tracking
* algorithm as a finite state machine, which partially reconstructs
* tracks in the muon spectrometer.
*/
-class AliHLTMUONMansoTrackerFSM
+class AliHLTMUONMansoTrackerFSM : public AliHLTLogging
{
public:
AliHLTMUONMansoTrackerFSM();
- virtual ~AliHLTMUONMansoTrackerFSM() {}
+ virtual ~AliHLTMUONMansoTrackerFSM();
/* This is the starting point for the tracking algorithm. The tracker is
{
fCallback = callback;
};
-
+
+ /// Returns the flag indicating if track candidates are stored.
+ bool MakeCandidates() const { return fMakeCandidates; }
+
+ /// Sets the flag to indicate if track candidates are stored or not.
+ void MakeCandidates(bool value) { fMakeCandidates = value; }
+
+ /// Returns the number of track candidates found in the list returned by TrackCandidates().
+ AliHLTUInt32_t TrackCandidatesCount() const { return fCandidatesCount; }
+
+ /// Returns the array of track candidates.
+ const AliHLTMUONMansoCandidateStruct* TrackCandidates() const { return fCandidates; }
+
+ /// Removes all the elements in the track candidates array.
+ void ZeroTrackCandidatesList() { fCandidatesCount = 0; }
/* Get and set methods for the a and b parameters used to build the region
of interests. Refer to AliRegionOfInterest for details about a and b parameters.
bool Contains(AliHLTMUONRecHitStruct p) const;
void GetBoundaryBox(AliHLTFloat32_t& left, AliHLTFloat32_t& right, AliHLTFloat32_t& bottom, AliHLTFloat32_t& top) const;
+
+ /// Returns the centre point of the region of interest.
+ const AliHLTMUONRecHitStruct& Centre() const { return fCentre; }
+
+ /// Returns the radius of the region of interest disk.
+ AliHLTFloat32_t Radius() const { return fRs; }
private:
class AliTagData
{
public:
- AliTagData() : fChamber(kChamber1), fRoi(), fLine() {};
+ AliTagData() : fChamber(kChamber1), fRoi(), fLine(), fCandidate(NULL) {};
AliHLTMUONChamberName fChamber; // The chamber on which the region of interest lies.
AliRegionOfInterest fRoi; // Region of interest on the next station.
AliLine fLine; // line between a cluster point and the previous station.
+ AliHLTMUONMansoCandidateStruct* fCandidate; // Track candidate related to the RoI.
};
class AliStation5Data
void EndOfClustersChamber9();
void EndOfClustersChamber10();
- void ProjectToStation4(AliStation5Data* data, register AliHLTFloat32_t station5z);
+ void ProjectToStation4(AliStation5Data* data, AliHLTFloat32_t station5z, AliHLTUInt32_t chamberSt5);
void ProcessClusters();
#ifdef DEBUG
AliHLTInt32_t fTriggerId; // The current ID number of the trigger record being processed.
AliHLTInt32_t fTrackId; // Track ID counter for the current track.
+ bool fMakeCandidates; // Indicates if the track candidates should be recorded.
+ AliHLTUInt32_t fCandidatesCount; // The number of track candidates in the fCandidates list.
+ AliHLTUInt32_t fCandidatesSize; // Number of elements that the fCandidates list can store.
+ AliHLTMUONMansoCandidateStruct* fCandidates; // The track candidates buffer.
/* To request clusters from the boundary box specified by the 'left', 'right',
'top' and 'bottom' boundaries and on the given chamber use this method call.
assert( fCallback != NULL );
fCallback->NoTrackFound(this);
};
+
+ /**
+ * Adds a new track candidate to the fCandidates list and returns the pointer
+ * to the new structure to be filled.
+ * \returns a pointer to the new structure and NULL if we ran out of space.
+ */
+ AliHLTMUONMansoCandidateStruct* AddTrackCandidate();
private:
/**************************************************************************
- * This file is property of and copyright by the ALICE HLT Project *
+ * This file is property of and copyright by the ALICE HLT Project *
* All rights reserved. *
* *
* Primary Authors: *
* without fee, provided that the above copyright notice appears in all *
* copies and that both the copyright notice and this permission notice *
* appear in the supporting documentation. The authors make no claims *
- * about the suitability of this software for any purpose. It is *
+ * about the suitability of this software for any purpose. It is *
* provided "as is" without express or implied warranty. *
**************************************************************************/
FreeMemory();
fWarnForUnexpecedBlock = false;
+ bool makeCandidates = false;
ResetCanLoadFlags();
double zmiddle = 0;
double bfieldintegral = 0;
fWarnForUnexpecedBlock = true;
continue;
}
-
+
+ if (strcmp(argv[i], "-makecandidates") == 0)
+ {
+ makeCandidates = true;
+ continue;
+ }
+
HLTError("Unknown option '%s'.", argv[i]);
return -EINVAL;
}
return -ENOMEM;
}
fTracker->SetCallback(this);
+ fTracker->MakeCandidates(makeCandidates);
// Set all the parameters that were found on the command line.
if (not fCanLoadZmiddle) AliHLTMUONCalculations::Zf(zmiddle);
if (fCanLoadBL)
{
- result = GetFloatFromTMap(map, "bfieldintegral", value, pathToEntry, "integrated magnetic field");
- if (result != 0) return result;
- AliHLTMUONCalculations::QBL(value);
+ Double_t bfieldintegral;
+ result = FetchFieldIntegral(bfieldintegral);
+ if (result == 0)
+ {
+ AliHLTMUONCalculations::QBL(bfieldintegral);
+ }
+ else
+ {
+ HLTWarning("Failed to load the magnetic field integral from GRP information.");
+ result = GetFloatFromTMap(map, "bfieldintegral", value, pathToEntry, "integrated magnetic field");
+ if (result != 0) return result;
+ HLTWarning(Form("Using deprecated magnetic field integral value of %f T.m.", value));
+ AliHLTMUONCalculations::QBL(value);
+ }
}
if (fCanLoadA[0])
bd.fDataType = AliHLTMUONConstants::MansoTracksBlockDataType();
bd.fSpecification = specification;
outputBlocks.push_back(bd);
- size = block.BytesUsed();
-
+ AliHLTUInt32_t totalSize = block.BytesUsed();
+
+ if (fTracker->MakeCandidates())
+ {
+ AliHLTMUONMansoCandidatesBlockWriter candidatesBlock(outputPtr+totalSize, size-totalSize);
+ if (not candidatesBlock.InitCommonHeader())
+ {
+ HLTError("Buffer overflowed. There are only %d bytes left in the buffer,"
+ " but we need a minimum of %d bytes.",
+ size, sizeof(AliHLTMUONMansoCandidatesBlockWriter::HeaderType)
+ );
+ if (DumpDataOnError()) DumpEvent(evtData, blocks, trigData, outputPtr, size, outputBlocks);
+ size = 0; // Important to tell framework that nothing was generated.
+ return -ENOBUFS;
+ }
+
+ // Fill in the output block buffer.
+ candidatesBlock.SetNumberOfEntries(fTracker->TrackCandidatesCount());
+ for (AliHLTUInt32_t i = 0; i < fTracker->TrackCandidatesCount(); ++i)
+ {
+ candidatesBlock[i] = fTracker->TrackCandidates()[i];
+ }
+
+ fTracker->ZeroTrackCandidatesList();
+
+ AliHLTComponentBlockData bdc;
+ FillBlockData(bdc);
+ bdc.fPtr = outputPtr;
+ bdc.fOffset = totalSize;
+ bdc.fSize = candidatesBlock.BytesUsed();
+ bdc.fDataType = AliHLTMUONConstants::MansoCandidatesBlockDataType();
+ bdc.fSpecification = specification;
+ outputBlocks.push_back(bdc);
+ totalSize += candidatesBlock.BytesUsed();
+ }
+
+ size = totalSize;
return 0;
}
#ifndef AliHLTMUONMANSOTRACKERFSMCOMPONENT_H
#define AliHLTMUONMANSOTRACKERFSMCOMPONENT_H
/**************************************************************************
- * This file is property of and copyright by the ALICE HLT Project *
+ * This file is property of and copyright by the ALICE HLT Project *
* All rights reserved. *
* *
* Primary Authors: *
* without fee, provided that the above copyright notice appears in all *
* copies and that both the copyright notice and this permission notice *
* appear in the supporting documentation. The authors make no claims *
- * about the suitability of this software for any purpose. It is *
+ * about the suitability of this software for any purpose. It is *
* provided "as is" without express or implied warranty. *
**************************************************************************/
* \li -dumppath <i>path</i> <br>
* Allows one to specify the path in which to dump the received data blocks
* if an error occurs. <br>
+ * \li -makecandidates <br>
+ * Indicates if the Manso track candidates data block should be generated.
+ * This kind of information is useful for debugging. <br>
*
* <h2>Standard configuration:</h2>
* This component should normally be configured with no extra options.
#include "AliHLTMUONUtils.h"
#include "AliHLTMUONConstants.h"
#include "AliHLTMUONCalculations.h"
+#include "AliMUONConstants.h"
#include "AliRawDataHeader.h"
#include <vector>
#include <cassert>
// here is to perform the bitwise or to form the correct strip pattern.
UShort_t mergedPattern[3] = {patterns[i][0], patterns[i][1], patterns[i][2]};
const AliHLTMUONTriggerRecoLutRow& lutnext = fLookupTable.fRow[fCurrentCrateId][locIdnext][i][1][0];
- const AliHLTMUONTriggerRecoLutRow& lutcurr = fLookupTable.fRow[fCurrentCrateId][locIdnext][i][1][0];
- const AliHLTMUONTriggerRecoLutRow& lutprev = fLookupTable.fRow[fCurrentCrateId][locIdnext][i][1][0];
+ const AliHLTMUONTriggerRecoLutRow& lutcurr = fLookupTable.fRow[fCurrentCrateId][locIdcurr][i][1][0];
+ const AliHLTMUONTriggerRecoLutRow& lutprev = fLookupTable.fRow[fCurrentCrateId][locIdprev][i][1][0];
if (lutprev.fX == lutcurr.fX and lutprev.fY == lutcurr.fY and lutprev.fZ == lutcurr.fZ)
{
mergedPattern[0] |= patterns[i][1];
else if (xpos[i] >= 0)
{
strips[i] = mergedPattern[0];
- locId[i] = locIdnext;
+ locId[i] = locIdprev;
}
else
{
if (hitset[i]) continue; // Leave the found hits alone.
if (stripPosX[i] != -1)
{
- // Got X strip but no hit so Y strip is missing.
+ // Got X strip but no hit, so Y strip is missing.
// Thus we have a good Y coordinate but poor X.
const AliHLTMUONTriggerRecoLutRow& lut = GetLutRowX(stripPosX[i], i);
trigger.fHit[i].fFlags = lut.fIdFlags;
}
else if (stripPosY[i] != -1)
{
- // Got Y strip but no hit so X strip is missing.
+ // Got Y strip but no hit, so X strip is missing.
// Thus we have a good X coordinate but poor Y.
const AliHLTMUONTriggerRecoLutRow& lut =
fLookupTable.fRow[fCurrentCrateId][locId[i]][i][1][stripPosY[i]];
}
}
}
+
+ // If 4 hits found then check if they are all good, otherwise find the 3
+ // best fitting ones.
+ if (hitCount > 3)
+ {
+ AliHLTFloat32_t dx = AliMUONConstants::TriggerNonBendingReso();
+ AliHLTFloat32_t dy = AliMUONConstants::TriggerBendingReso();
+ AliHLTMUONCalculations::SigmaX2(dx*dx);
+ AliHLTMUONCalculations::SigmaY2(dy*dy);
+
+ AliHLTFloat32_t chi2 = AliHLTMUONCalculations::ComputeChi2(trigger, hitset);
+ if (chi2 != -1 and chi2 > 5.*4) // check 5 sigma cut.
+ {
+ // Poor fit so look for best 3 points.
+ int worstHit = -1;
+ AliHLTFloat32_t bestchi2 = 1e38;
+ for (int j = 0; j < 4; j++)
+ {
+ bool tmphitset[4] = {true, true, true, true};
+ tmphitset[j] = false;
+ AliHLTFloat32_t tmpchi2 = AliHLTMUONCalculations::ComputeChi2(trigger, tmphitset);
+ if (tmpchi2 * 4 < chi2 * 3 and tmpchi2 < bestchi2)
+ {
+ bestchi2 = tmpchi2;
+ worstHit = j;
+ }
+ }
+ if (worstHit != -1)
+ {
+ for (int j = 0; j < 4; j++) hitset[j] = true;
+ hitset[worstHit] = false;
+ trigger.fHit[worstHit] = AliHLTMUONConstants::NilRecHitStruct();
+ }
+ }
+ }
// Construct the ID from the running counter fTrigRecId and use the
// regional counter, local counter and DDL id for the bottom 8 bits.
}
catch (...)
{
- HLTError("Could not allocate buffer space for debug information.");
+ HLTError("Could not allocate more buffer space for debug information.");
return;
}
for (AliHLTUInt32_t i = 0; i < fInfoBufferSize; ++i) newbuf[i] = fInfoBuffer[i];
if (setBL)
{
- result = GetFloatFromTMap(map, "bfieldintegral", value, pathToEntry, "integrated magnetic field");
- if (result != 0) return result;
- AliHLTMUONCalculations::QBL(value);
+ Double_t bfieldintegral;
+ result = FetchFieldIntegral(bfieldintegral);
+ if (result == 0)
+ {
+ AliHLTMUONCalculations::QBL(bfieldintegral);
+ }
+ else
+ {
+ HLTWarning("Failed to load the magnetic field integral from GRP information.");
+ result = GetFloatFromTMap(map, "bfieldintegral", value, pathToEntry, "integrated magnetic field");
+ if (result != 0) return result;
+ HLTWarning(Form("Using deprecated magnetic field integral value of %f T.m.", value));
+ AliHLTMUONCalculations::QBL(value);
+ }
}
HLTDebug("Using the following configuration parameters:");
--- /dev/null
+/**************************************************************************
+ * This file is property of and copyright by the ALICE HLT Project *
+ * All rights reserved. *
+ * *
+ * Primary Authors: *
+ * Artur Szostak <artursz@iafrica.com> *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+// $Id: DisplaydHLTData.C 37070 2009-11-20 13:53:08Z aszostak $
+
+/**
+ * \ingroup macros
+ * \file CreateCDBFieldIntegrals.C
+ * \brief Macro for creating and storing the magnetic field integrals in the CDB.
+ *
+ * This macro calculates the magnetic field integrals for the dipole magnet and
+ * writes them into the CDB under the HLT/ConfigMUON/FieldIntegrals path.
+ * These are then used by the online dHLT reconstruction components during
+ * momentum estimation of the tracks found.
+ * The simplest method to run this macro is with the following command:
+ * \code
+ * > aliroot -b -q -l CreateCDBFieldIntegrals.C
+ * \endcode
+ *
+ * \author Artur Szostak <artursz@iafrica.com>
+ */
+
+#if !defined(__CINT__) || defined(__MAKECINT__)
+#include "AliCDBManager.h"
+#include "AliCDBStorage.h"
+#include "AliCDBEntry.h"
+#include "AliGRPManager.h"
+#include "AliHLTMUONConstants.h"
+#include "AliMagF.h"
+#include "TMap.h"
+#include "TArrayD.h"
+#include "TObjString.h"
+#include "TString.h"
+#include "TVector3.h"
+#include "TMath.h"
+#include "TSystem.h"
+#include <iostream>
+using std::cout;
+using std::cerr;
+using std::endl;
+#endif
+
+/**
+ * Calculates the average magnetic field integral for the dipole magnet given the
+ * L3 solenoid current and dipole magnet current.
+ * [in] \param currentL3 The current in the L3 solenoid magnet.
+ * [in] \param currentDip The current in the dipole magnet.
+ * [out] \param result The magnetic field integral result.
+ * [in] \param sqrts The centre of mass energy for the beams.
+ * [in] \param beamtype The beam type as given the AliMagF, eg. p-p, A-A or none.
+ * \note The sign of the current indicates the polarity setting for the magnet.
+ * \returns true if the magnetic field was calculated successfully and false otherwise.
+ */
+bool CalculateIntegral(
+ Float_t currentL3, Float_t currentDip, Float_t& result,
+ Float_t sqrts = 0, const char* beamtype = "none"
+ )
+{
+ AliMagF* fld = AliMagF::CreateFieldMap(currentL3, currentDip, AliMagF::kConvLHC, kFALSE, sqrts, beamtype);
+ if (fld == NULL) return false;
+
+ TArrayD totals;
+ for (int theta = 171; theta <= 179; ++theta)
+ for (int phi = 0; phi < 360; phi += 10)
+ {
+ TVector3 dr;
+ dr.SetMagThetaPhi(1, theta*TMath::Pi()/180., phi*TMath::Pi()/180.);
+ Double_t dx = 1e-3 * dr.Mag();
+
+ TVector3 r(0, 0, 0);
+ int nsteps = 0;
+ Double_t total = 0;
+ while (r.Z() > -1700 && nsteps < 10000)
+ {
+ Double_t p[3] = {r.X(), r.Y(), r.Z()};
+ Double_t b[3];
+ fld->Field(p, b);
+ total += b[0] * dx;
+ ++nsteps;
+ r += dr;
+ }
+
+ totals.Set(totals.GetSize()+1);
+ totals[totals.GetSize()-1] = total;
+ }
+
+ result = - TMath::Mean(totals.GetSize(), totals.GetArray());
+ Float_t rms = TMath::RMS(totals.GetSize(), totals.GetArray());
+
+ cout << "Integrated field value = " << result
+ << " +/- " << rms
+ << ", for L3 current = " << currentL3
+ << ", dipole current = " << currentDip << endl;
+ return true;
+}
+
+/**
+ * Calculates the magnetic field integrals for the dipole magnet and stores them
+ * into the CDB.
+ * \param cdbPath The path to the local storage.
+ * \param version The version of the CDB entry.
+ * \param firstRun = The first run number for which the CDB entry is valid.
+ * \param lastRun = The last run number for which the CDB entry is valid.
+ * \param sqrts The centre of mass energy for the beams.
+ * \param beamtype The beam type as given the AliMagF, eg. p-p, A-A or none.
+ */
+void CreateCDBFieldIntegrals(
+ const char* cdbPath = "local://$ALICE_ROOT/OCDB",
+ Int_t version = 0,
+ Int_t firstRun = 0,
+ Int_t lastRun = AliCDBRunRange::Infinity(),
+ Float_t sqrts = 0,
+ const char* beamtype = "none"
+ )
+{
+ // Get the CDB manager and storage.
+ AliCDBManager* cdbManager = AliCDBManager::Instance();
+ if (cdbManager == NULL)
+ {
+ cerr << "ERROR: Global CDB manager object does not exist." << endl;
+ return;
+ }
+ AliCDBStorage* storage = cdbManager->GetStorage(cdbPath);
+ if (storage == NULL)
+ {
+ cerr << "ERROR: Could not get storage for: " << cdbPath << endl;
+ return;
+ }
+
+ const int nL3Current = 5;
+ const int nDipCurrent = 3;
+ Float_t currentL3[nL3Current] = {-30e3, -12e3, 0, 12e3, 30e3};
+ Float_t currentDip[nDipCurrent] = {-6e3, 0, 6e3};
+
+ // Create and store the configuration parameters for the trigger reconstructor.
+ TMap* params = new TMap;
+ params->SetOwner(kTRUE);
+ for (int i = 0; i < nL3Current; ++i)
+ for (int j = 0; j < nDipCurrent; ++j)
+ {
+ if (currentL3[i]*currentDip[j] < 0) continue; // Skip invalid combinations.
+ Float_t bfieldintegral;
+ if (! CalculateIntegral(currentL3[i], currentDip[j], bfieldintegral, sqrts, beamtype)) continue;
+ const char* paramName = Form("L3_current=%0.2e;Dipole_current=%0.2e", currentL3[i], currentDip[j]);
+ const char* paramValue = Form("%8.8f", bfieldintegral);
+ params->Add(new TObjString(paramName), new TObjString(paramValue));
+ }
+
+ const char* path = AliHLTMUONConstants::FieldIntegralsCDBPath();
+ AliCDBId id(path, firstRun, lastRun, version);
+ AliCDBMetaData* metaData = new AliCDBMetaData();
+ metaData->SetResponsible("dimuon HLT");
+ metaData->SetComment("Magnetic field integral parameters for dimuon HLT.");
+ storage->Put(params, id, metaData);
+}
/**
* Generates default CDB entries in the given CDB storage (local by default)
* \param cdbPath The path to the local storage.
- * \param version = 0,
- * \param firstRun = 0,
- * \param lastRun = AliCDBRunRange::Infinity()
+ * \param version The version of the CDB entry.
+ * \param firstRun = The first run number for which the CDB entry is valid.
+ * \param lastRun = The last run number for which the CDB entry is valid.
* \param zmiddle The middle of the dipole field (cm) used by AliHLTMUONTriggerReconstructorComponent and AliHLTMUONMansoTrackerFSMComponent.
* \param bfieldintegral The dipole magnetic field integral (T.m) used by AliHLTMUONTriggerReconstructorComponent and AliHLTMUONMansoTrackerFSMComponent.
* \param dccut DC cut applied to channels by AliHLTMUONHitReconstructorComponent.
--- /dev/null
+/**************************************************************************
+ * This file is property of and copyright by the ALICE HLT Project *
+ * All rights reserved. *
+ * *
+ * Primary Authors: *
+ * Artur Szostak <artursz@iafrica.com> *
+ * *
+ * Permission to use, copy, modify and distribute this software and its *
+ * documentation strictly for non-commercial purposes is hereby granted *
+ * without fee, provided that the above copyright notice appears in all *
+ * copies and that both the copyright notice and this permission notice *
+ * appear in the supporting documentation. The authors make no claims *
+ * about the suitability of this software for any purpose. It is *
+ * provided "as is" without express or implied warranty. *
+ **************************************************************************/
+
+// $Id: DisplaydHLTData.C 37070 2009-11-20 13:53:08Z aszostak $
+
+/**
+ * \ingroup macros
+ * \file DisplaydHLTData.C
+ * \brief Macro for displaying rootified dHLT data generated with RunChain.C
+ *
+ * This macro is used to display the dHLT data generated by the RunChain.C macro
+ * with the "root" option for making the output data. Optionally the dHLTRawData.root
+ * file which is generated during a AliRoot offline reconstruction can also be
+ * displayed using this macro.
+ * After having generated the dHLT raw data file (called <i>output.root</i> for example)
+ * the following command can be executed in an alieve session to display both
+ * MUON and dHLT data:
+ * \code
+ * > gSystem->Load("libAliHLTMUON.so");
+ * > .L $ALICE_ROOT/EVE/macros/alieve_init.C
+ * > .L $ALICE_ROOT/EVE/alice-macros/event_goto.C
+ * > .L $ALICE_ROOT/EVE/alice-macros/MUON_displayData.C
+ * > .L $ALICE_ROOT/HLT/MUON/macros/DisplaydHLTData.C
+ * > alieve_init("OCDBpath","DataPath",EventNumber);
+ * > MUON_displayData(1,1,1);
+ * > DisplaydHLTData("output.root");
+ * \endcode
+ * Where <i>OCDBpath</i> should be replaced by the path to the OCDB database,
+ * <i>DataPath</i> should be the directory of the raw data or raw data root file and
+ * <i>EventNumber</i> is the event number to load.
+ *
+ * \author Artur Szostak <artursz@iafrica.com>
+ */
+
+#if !defined(__CINT__) || defined(__MAKECINT__)
+#include "AliEveEventManager.h"
+#include "AliHLTMUONTriggerRecord.h"
+#include "AliHLTMUONRecHit.h"
+#include "AliHLTMUONMansoTrack.h"
+#include "AliHLTMUONEvent.h"
+#include "TEveManager.h"
+#include "TEveElement.h"
+#include "TEvePointSet.h"
+#include "TEveStraightLineSet.h"
+#include "TArrayD.h"
+#include "TFile.h"
+#include "TString.h"
+#include "TClassTable.h"
+#include "TSystem.h"
+#include <iostream>
+using std::cerr;
+using std::endl;
+#endif
+
+
+TFile* gDHLTFile = NULL;
+
+void FillData(Int_t eventId);
+
+
+void DisplaydHLTData(const char* dHLTfilename = "output.root")
+{
+ // Display dHLT data.
+
+ if (gClassTable->GetID("AliHLTMUONEvent") < 0)
+ {
+ gSystem->Load("libAliHLTMUON.so");
+ }
+
+ if (AliEveEventManager::GetMaster() == NULL)
+ {
+ cerr << "ERROR: alieve event not initialised, use alieve_init(...)" << endl;
+ return;
+ }
+
+ gEve->DisableRedraw();
+
+ TString filename = dHLTfilename;
+ TString tmpfilename = filename;
+ if (gSystem->FindFile("", tmpfilename) == NULL)
+ {
+ tmpfilename = filename;
+ if (gSystem->FindFile(".", tmpfilename) == NULL)
+ {
+ TString filename = TString(AliEveEventManager::GetMaster()->GetTitle());
+ filename += "/";
+ filename += dHLTfilename;
+ }
+ }
+ if (gDHLTFile == NULL)
+ {
+ gDHLTFile = new TFile(filename.Data(), "READ");
+ }
+ else if (filename != gDHLTFile->GetName())
+ {
+ delete gDHLTFile;
+ gDHLTFile = new TFile(filename.Data(), "READ");
+ }
+
+ FillData(AliEveEventManager::GetMaster()->GetEventId());
+
+ gEve->Redraw3D(kTRUE);
+ gEve->EnableRedraw();
+}
+
+
+void FillData(TEveElementList* list, const AliHLTMUONTriggerRecord* trigrec)
+{
+ // Count the number of points in the trigger record.
+ Int_t pointCount = 0;
+ for (int i = 11; i <= 14; ++i)
+ {
+ if (trigrec->Hit(i) != TVector3(0,0,0)) ++pointCount;
+ }
+
+ // Create and fill the point set for the trigger record.
+ TEvePointSet* pointset = new TEvePointSet(pointCount);
+ pointset->SetName(Form("TriggerRecord%d", trigrec->Id()));
+ pointset->SetTitle(Form("dHLT trigger record ID = %d", trigrec->Id()));
+ pointset->SetMarkerStyle(28);
+ pointset->SetMarkerColor(kYellow);
+ pointset->SetMarkerSize(3);
+ Int_t ipnt = 0;
+ for (int i = 11; i <= 14; ++i)
+ {
+ if (trigrec->Hit(i) == TVector3(0,0,0)) continue;
+ pointset->SetPoint(ipnt, trigrec->Hit(i).X(), trigrec->Hit(i).Y(), trigrec->Hit(i).Z());
+ ++ipnt;
+ }
+
+ list->AddElement(pointset);
+}
+
+
+void FillData(TEveElementList* list, const AliHLTMUONMansoTrack* track)
+{
+ // Count the points in the track.
+ Int_t pointCount = 0;
+ for (int i = 7; i <= 10; ++i)
+ {
+ const AliHLTMUONRecHit* hit = track->Hit(i);
+ if (hit != NULL) ++pointCount;
+ }
+ const AliHLTMUONTriggerRecord* trigrec = track->TriggerRecord();
+ if (trigrec != NULL)
+ {
+ for (int i = 11; i <= 14; ++i)
+ {
+ if (trigrec->Hit(i) != TVector3(0,0,0)) ++pointCount;
+ }
+ }
+
+ // Create and fill the point set for the track.
+ TEvePointSet* pointset = new TEvePointSet(pointCount);
+ pointset->SetName(Form("Track%d", track->Id()));
+ pointset->SetTitle(Form("dHLT track ID = %d", track->Id()));
+ if (track->Id() != -1)
+ {
+ pointset->SetMarkerStyle(20);
+ pointset->SetMarkerColor(kGreen);
+ pointset->SetMarkerSize(1.5);
+ }
+ else
+ {
+ pointset->SetMarkerStyle(28);
+ pointset->SetMarkerColor(kYellow);
+ pointset->SetMarkerSize(3);
+ }
+ Int_t ipnt = 0;
+ if (trigrec != NULL)
+ {
+ for (int i = 11; i <= 14; ++i)
+ {
+ if (trigrec->Hit(i) == TVector3(0,0,0)) continue;
+ pointset->SetPoint(ipnt, trigrec->Hit(i).X(), trigrec->Hit(i).Y(), trigrec->Hit(i).Z());
+ ++ipnt;
+ }
+ }
+ for (int j = 7; j <= 10; ++j)
+ {
+ const AliHLTMUONRecHit* hit = track->Hit(j);
+ if (hit == NULL) continue;
+ pointset->SetPoint(ipnt, hit->X(), hit->Y(), hit->Z());
+ ++ipnt;
+ }
+
+ for (int j = 7; j <= 10; ++j)
+ {
+ if (track->RoIRadius(j) == -1) continue;
+ TEveStraightLineSet* roi = new TEveStraightLineSet(
+ Form("RoI%d", j),
+ Form("Region of interest for chamber %d", j)
+ );
+ Float_t p0x = track->RoICentre(j).X() + track->RoIRadius(j);
+ Float_t p0y = track->RoICentre(j).Y();
+ Float_t p0z = track->RoICentre(j).Z();
+ Float_t p1x = p0x;
+ Float_t p1y = p0y;
+ Float_t p1z = p0z;
+ for (int i = 0; i < 32; ++i)
+ {
+ Double_t t = Double_t(i) / 32. * 2. * TMath::Pi();
+ Float_t p2x = track->RoICentre(j).X() + track->RoIRadius(j)*cos(t);
+ Float_t p2y = track->RoICentre(j).Y() + track->RoIRadius(j)*sin(t);
+ Float_t p2z = track->RoICentre(j).Z();
+ roi->AddLine(p1x, p1y, p1z, p2x, p2y, p2z);
+ p1x = p2x;
+ p1y = p2y;
+ p1z = p2z;
+ }
+ roi->AddLine(p1x, p1y, p1z, p0x, p0y, p0z);
+ pointset->AddElement(roi);
+ }
+
+ list->AddElement(pointset);
+}
+
+
+void FillData(Int_t eventId)
+{
+ AliHLTMUONEvent* dhltEvent = dynamic_cast<AliHLTMUONEvent*>( gDHLTFile->Get(Form("AliHLTMUONEvent;%d", eventId+1)) );
+ if (dhltEvent == NULL)
+ {
+ cerr << "ERROR: Could not find dHLT data for event " << eventId << endl;
+ return;
+ }
+
+ TEveElementList* list = new TEveElementList("dHLTData", "dHLT data");
+ gEve->AddElement(list);
+
+ TArrayD px, py, pz;
+ for (int i = 0; i < dhltEvent->DataObjects().GetEntriesFast(); i++)
+ {
+ if (dhltEvent->DataObjects()[i]->IsA() == AliHLTMUONRecHit::Class())
+ {
+ const AliHLTMUONRecHit* hit = dynamic_cast<const AliHLTMUONRecHit*>( dhltEvent->DataObjects()[i] );
+ px.Set(px.GetSize()+1);
+ py.Set(py.GetSize()+1);
+ pz.Set(pz.GetSize()+1);
+ px[px.GetSize()-1] = hit->X();
+ py[py.GetSize()-1] = hit->Y();
+ pz[pz.GetSize()-1] = hit->Z();
+ continue;
+ }
+ else if (dhltEvent->DataObjects()[i]->IsA() == AliHLTMUONTriggerRecord::Class())
+ {
+ const AliHLTMUONTriggerRecord* trigrec = dynamic_cast<const AliHLTMUONTriggerRecord*>( dhltEvent->DataObjects()[i] );
+ FillData(list, trigrec);
+ }
+ else if (dhltEvent->DataObjects()[i]->IsA() == AliHLTMUONMansoTrack::Class())
+ {
+ const AliHLTMUONMansoTrack* track = dynamic_cast<const AliHLTMUONMansoTrack*>( dhltEvent->DataObjects()[i] );
+ FillData(list, track);
+ }
+ }
+
+ TEvePointSet* mps = new TEvePointSet(px.GetSize());
+ mps->SetName("RecHits");
+ mps->SetTitle("dHLT reconstructed hits");
+ mps->SetMarkerStyle(28);
+ mps->SetMarkerColor(kYellow);
+ mps->SetMarkerSize(3);
+ for (int i = 0; i < px.GetSize(); ++i)
+ {
+ mps->SetPoint(i, px[i], py[i], pz[i]);
+ }
+ list->AddElement(mps);
+}
#if !defined(__CINT__) || defined(__MAKECINT__)
#include "AliRawReader.h"
#include "AliHLTOfflineInterface.h"
+#include "AliCDBStorage.h"
#include "AliCDBManager.h"
#include "AliHLTSystem.h"
#include "AliHLTConfiguration.h"
// full chains.
if (buildTrackerComp)
{
- AliHLTConfiguration tracker("tracker", "MUONMansoTrackerFSM", "recDDL13 recDDL14 recDDL15 recDDL16 recDDL17 recDDL18 recDDL19 recDDL20 recDDL21 recDDL22", "");
+ AliHLTConfiguration tracker(
+ "tracker",
+ "MUONMansoTrackerFSM",
+ "recDDL13 recDDL14 recDDL15 recDDL16 recDDL17 recDDL18 recDDL19 recDDL20 recDDL21 recDDL22",
+ "-makecandidates"
+ );
}
// Build the dHLT trigger decision component if enabled.