Skip to content

Commit

Permalink
Adding cluster size to track extra (AliceO2Group#12044)
Browse files Browse the repository at this point in the history
* Add ITS cluster size to the AO2D

* Add TracksExtra_001

* Update readerhelper

* Add cluster sizes to AB

* Remove its cluster map

* Please consider the following formatting changes

* Add table versioning

* Fix comments

Co-authored-by: Jan Fiete <[email protected]>

* Fix comments (2)

Co-authored-by: Jan Fiete <[email protected]>

* Set old TrackExtra as default

* Fix data descriptor for trackextra

* Please consider the following formatting changes

* Fix test

* Clean commented code

* Fix comment (3)

Co-authored-by: Jan Fiete <[email protected]>

* Move dyn columns to versioning namespace

* Update Framework/Core/include/Framework/AnalysisDataModel.h

* Add braces + unsigned shorts

* Move cluster sizes to uint8_t

* Swap pattern and clsizes order

---------

Co-authored-by: Maximiliano Puccio <[email protected]>
Co-authored-by: ALICE Action Bot <[email protected]>
Co-authored-by: Jan Fiete <[email protected]>
  • Loading branch information
4 people authored Oct 19, 2023
1 parent b7107e6 commit 997cb57
Show file tree
Hide file tree
Showing 12 changed files with 224 additions and 56 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -122,13 +122,39 @@ class TrackITS : public o2::track::TrackParCov
void setNextROFbit(bool toggle = true) { setUserField((getUserField() & ~kNextROF) | (-toggle & kNextROF)); }
bool hasHitInNextROF() const { return getUserField() & kNextROF; }

void setClusterSize(int l, int size)
{
if (l >= 8) {
return;
}
if (size > 15) {
size = 15;
}
mClusterSizes &= ~(0xf << (l * 4));
mClusterSizes |= (size << (l * 4));
}

int getClusterSize(int l)
{
if (l >= 8) {
return 0;
}
return (mClusterSizes >> (l * 4)) & 0xf;
}

int getClusterSizes() const
{
return mClusterSizes;
}

private:
o2::track::TrackParCov mParamOut; ///< parameter at largest radius
ClusRefs mClusRef; ///< references on clusters
float mChi2 = 0.; ///< Chi2 for this track
uint32_t mPattern = 0; ///< layers pattern
unsigned int mClusterSizes = 0u;

ClassDefNV(TrackITS, 5);
ClassDefNV(TrackITS, 6);
};

class TrackITSExt : public TrackITS
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,12 +25,35 @@ namespace itsmft
// can refer to max 15 indices in the vector of total length <268435456, i.e. 17895697 tracks in worst case
struct TrkClusRef : public o2::dataformats::RangeRefComp<4> {
using o2::dataformats::RangeRefComp<4>::RangeRefComp;
uint32_t clsizes = 0; ///< cluster sizes for each layer
uint16_t pattern = 0; ///< layers pattern

GPUd() int getNClusters() const { return getEntries(); }
bool hasHitOnLayer(int i) { return pattern & (0x1 << i); }

ClassDefNV(TrkClusRef, 1);
void setClusterSize(int l, int size)
{
if (l >= 8)
return;
if (size > 15)
size = 15;
clsizes &= ~(0xf << (l * 4));
clsizes |= (size << (l * 4));
}

int getClusterSize(int l)
{
if (l >= 8)
return 0;
return (clsizes >> (l * 4)) & 0xf;
}

int getClusterSizes() const
{
return clsizes;
}

ClassDefNV(TrkClusRef, 2);
};

} // namespace itsmft
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -356,6 +356,7 @@ class AODProducerWorkflowDPL : public Task
struct TrackExtraInfo {
float tpcInnerParam = 0.f;
uint32_t flags = 0;
uint32_t itsClusterSizes = 0u;
uint8_t itsClusterMap = 0;
uint8_t tpcNClsFindable = 0;
int8_t tpcNClsFindableMinusFound = 0;
Expand Down
3 changes: 3 additions & 0 deletions Detectors/AOD/src/AODProducerWorkflowSpec.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -2729,6 +2729,9 @@ DataProcessorSpec getAODProducerWorkflowSpec(GID::mask_t src, bool enableSV, boo
dataRequest->requestStrangeTracks(useMC);
LOGF(info, "requestStrangeTracks Finish");
}
if (src[GID::ITS]) {
dataRequest->requestClusters(GIndex::getSourcesMask("ITS"), false);
}
if (src[GID::TPC]) {
dataRequest->requestClusters(GIndex::getSourcesMask("TPC"), false); // no need to ask for TOF clusters as they are requested with TOF tracks
}
Expand Down
77 changes: 39 additions & 38 deletions Detectors/GlobalTracking/include/GlobalTracking/MatchTPCITS.h
Original file line number Diff line number Diff line change
Expand Up @@ -89,7 +89,7 @@ namespace tpc
{
class TrackTPC;
class VDriftCorrFact;
}
} // namespace tpc

namespace gpu
{
Expand Down Expand Up @@ -127,7 +127,7 @@ struct TrackLocTPC : public o2::track::TrackParCov {
float timeErr = 0.f; ///< time sigma (makes sense for constrained tracks only)
int sourceID = 0; ///< TPC track origin in
o2::dataformats::GlobalTrackID gid{}; // global track source ID (TPC track may be part of it)
int matchID = MinusOne; ///< entry (non if MinusOne) of its matchTPC struct in the mMatchesTPC
int matchID = MinusOne; ///< entry (non if MinusOne) of its matchTPC struct in the mMatchesTPC
Constraint_t constraint{Constrained};

float getCorrectedTime(float dt) const // return time0 corrected for extra drift (to match certain Z)
Expand All @@ -148,9 +148,9 @@ struct TrackLocITS : public o2::track::TrackParCov {
enum : uint16_t { CloneBefore = 0x1,
CloneAfter = 0x2 };
o2::math_utils::Bracketf_t tBracket; ///< bracketing time in \mus
int sourceID = 0; ///< track origin id
int roFrame = MinusOne; ///< ITS readout frame assigned to this track
int matchID = MinusOne; ///< entry (non if MinusOne) of its matchCand struct in the mMatchesITS
int sourceID = 0; ///< track origin id
int roFrame = MinusOne; ///< ITS readout frame assigned to this track
int matchID = MinusOne; ///< entry (non if MinusOne) of its matchCand struct in the mMatchesITS
bool hasCloneBefore() const { return getUserField() & CloneBefore; }
bool hasCloneAfter() const { return getUserField() & CloneAfter; }
int getCloneShift() const { return hasCloneBefore() ? -1 : (hasCloneAfter() ? 1 : 0); }
Expand Down Expand Up @@ -536,13 +536,13 @@ class MatchTPCITS
float correctTPCTrack(o2::track::TrackParCov& trc, const TrackLocTPC& tTPC, const InteractionCandidate& cand) const; // RS FIXME will be needed for refit
//================================================================

bool mInitDone = false; ///< flag init already done
bool mFieldON = true; ///< flag for field ON/OFF
bool mCosmics = false; ///< flag cosmics mode
bool mMCTruthON = false; ///< flag availability of MC truth
float mBz = 0; ///< nominal Bz
int mTFCount = 0; ///< internal TF counter for debugger
int mNThreads = 1; ///< number of OMP threads
bool mInitDone = false; ///< flag init already done
bool mFieldON = true; ///< flag for field ON/OFF
bool mCosmics = false; ///< flag cosmics mode
bool mMCTruthON = false; ///< flag availability of MC truth
float mBz = 0; ///< nominal Bz
int mTFCount = 0; ///< internal TF counter for debugger
int mNThreads = 1; ///< number of OMP threads
o2::InteractionRecord mStartIR{0, 0}; ///< IR corresponding to the start of the TF

///========== Parameters to be set externally, e.g. from CCDB ====================
Expand All @@ -566,27 +566,27 @@ class MatchTPCITS
///< assigned time0 and its track Z position (converted from mTPCTimeEdgeZSafeMargin)
float mTPCTimeEdgeTSafeMargin = 0.f;
float mTPCExtConstrainedNSigmaInv = 0.f; // inverse for NSigmas for TPC time-interval from external constraint time sigma
int mITSROFrameLengthInBC = 0; ///< ITS RO frame in BC (for ITS cont. mode only)
float mITSROFrameLengthMUS = -1.; ///< ITS RO frame in \mus
float mITSTimeResMUS = -1.; ///< nominal ITS time resolution derived from ROF
float mITSROFrameLengthMUSInv = -1.; ///< ITS RO frame in \mus inverse
int mITSTimeBiasInBC = 0; ///< ITS RO frame shift in BCs, i.e. t_i = (I_ROF*mITSROFrameLengthInBC + mITSTimeBiasInBC)*BCLength_MUS
float mITSTimeBiasMUS = 0.; ///< ITS RO frame shift in \mus, i.e. t_i = (I_ROF*mITSROFrameLengthInBC)*BCLength_MUS + mITSTimeBiasMUS
float mTPCVDrift = -1.; ///< TPC drift speed in cm/microseconds
float mTPCVDriftInv = -1.; ///< inverse TPC nominal drift speed in cm/microseconds
float mTPCDriftTimeOffset = 0; ///< drift time offset in mus
float mTPCTBinMUS = 0.; ///< TPC time bin duration in microseconds
float mTPCTBinNS = 0.; ///< TPC time bin duration in ns
float mTPCTBinMUSInv = 0.; ///< inverse TPC time bin duration in microseconds
float mZ2TPCBin = 0.; ///< conversion coeff from Z to TPC time-bin
float mTPCBin2Z = 0.; ///< conversion coeff from TPC time-bin to Z
float mNTPCBinsFullDrift = 0.; ///< max time bin for full drift
float mTPCZMax = 0.; ///< max drift length
float mTPCmeanX0Inv = 1. / 31850.; ///< TPC gas 1/X0
int mITSROFrameLengthInBC = 0; ///< ITS RO frame in BC (for ITS cont. mode only)
float mITSROFrameLengthMUS = -1.; ///< ITS RO frame in \mus
float mITSTimeResMUS = -1.; ///< nominal ITS time resolution derived from ROF
float mITSROFrameLengthMUSInv = -1.; ///< ITS RO frame in \mus inverse
int mITSTimeBiasInBC = 0; ///< ITS RO frame shift in BCs, i.e. t_i = (I_ROF*mITSROFrameLengthInBC + mITSTimeBiasInBC)*BCLength_MUS
float mITSTimeBiasMUS = 0.; ///< ITS RO frame shift in \mus, i.e. t_i = (I_ROF*mITSROFrameLengthInBC)*BCLength_MUS + mITSTimeBiasMUS
float mTPCVDrift = -1.; ///< TPC drift speed in cm/microseconds
float mTPCVDriftInv = -1.; ///< inverse TPC nominal drift speed in cm/microseconds
float mTPCDriftTimeOffset = 0; ///< drift time offset in mus
float mTPCTBinMUS = 0.; ///< TPC time bin duration in microseconds
float mTPCTBinNS = 0.; ///< TPC time bin duration in ns
float mTPCTBinMUSInv = 0.; ///< inverse TPC time bin duration in microseconds
float mZ2TPCBin = 0.; ///< conversion coeff from Z to TPC time-bin
float mTPCBin2Z = 0.; ///< conversion coeff from TPC time-bin to Z
float mNTPCBinsFullDrift = 0.; ///< max time bin for full drift
float mTPCZMax = 0.; ///< max drift length
float mTPCmeanX0Inv = 1. / 31850.; ///< TPC gas 1/X0

float mMinTPCTrackPtInv = 999.; ///< cutoff on TPC track inverse pT
float mMinITSTrackPtInv = 999.; ///< cutoff on ITS track inverse pT
bool mVDriftCalibOn = false; ///< flag to produce VDrift calibration data
bool mVDriftCalibOn = false; ///< flag to produce VDrift calibration data
o2::tpc::VDriftCorrFact mTPCDrift{};
o2::gpu::CorrectionMapsHelper* mTPCCorrMapsHelper = nullptr;

Expand All @@ -601,12 +601,14 @@ class MatchTPCITS
const o2::globaltracking::RecoContainer* mRecoCont = nullptr;
///>>>------ these are input arrays which should not be modified by the matching code
// since this info is provided by external device
gsl::span<const o2::tpc::TrackTPC> mTPCTracksArray; ///< input TPC tracks span
gsl::span<const o2::tpc::TPCClRefElem> mTPCTrackClusIdx; ///< input TPC track cluster indices span
gsl::span<const o2::itsmft::ROFRecord> mITSTrackROFRec; ///< input ITS tracks ROFRecord span
gsl::span<const o2::its::TrackITS> mITSTracksArray; ///< input ITS tracks span
gsl::span<const int> mITSTrackClusIdx; ///< input ITS track cluster indices span
std::vector<ITSCluster> mITSClustersArray; ///< ITS clusters created in loadInput
gsl::span<const o2::tpc::TrackTPC> mTPCTracksArray; ///< input TPC tracks span
gsl::span<const o2::tpc::TPCClRefElem> mTPCTrackClusIdx; ///< input TPC track cluster indices span
gsl::span<const o2::itsmft::ROFRecord> mITSTrackROFRec; ///< input ITS tracks ROFRecord span
gsl::span<const o2::its::TrackITS> mITSTracksArray; ///< input ITS tracks span
gsl::span<const int> mITSTrackClusIdx; ///< input ITS track cluster indices span
std::vector<ITSCluster> mITSClustersArray; ///< ITS clusters created in loadInput
std::vector<uint8_t> mITSClusterSizes; ///< ITS cluster sizes created in loadInput

gsl::span<const o2::itsmft::ROFRecord> mITSClusterROFRec; ///< input ITS clusters ROFRecord span
gsl::span<const o2::ft0::RecPoints> mFITInfo; ///< optional input FIT info span

Expand All @@ -624,6 +626,7 @@ class MatchTPCITS
size_t mNMatches = 0;
size_t mNCalibPrelim = 0;
size_t mNMatchesControl = 0;

size_t mNABRefsClus = 0;
float mAB2MatchGuess = 0.2; // heuristic guess about fraction of AB matches in total matches
std::vector<InteractionCandidate> mInteractions; ///< possible interaction times
Expand Down Expand Up @@ -693,7 +696,6 @@ class MatchTPCITS
static constexpr std::string_view TimerName[] = {"Total", "PrepareITS", "PrepareTPC", "DoMatching", "SelectBest", "Refit",
"ABSeeds", "ABMatching", "ABWinners", "ABRefit", "IO", "Debug"};
TStopwatch mTimer[NStopWatches];

};

//______________________________________________
Expand All @@ -714,7 +716,6 @@ inline bool MatchTPCITS::isDisabledITS(const TrackLocITS& t) const { return t.ma
//______________________________________________
inline bool MatchTPCITS::isDisabledTPC(const TrackLocTPC& t) const { return t.matchID < 0; }


} // namespace globaltracking
} // namespace o2

Expand Down
35 changes: 29 additions & 6 deletions Detectors/GlobalTracking/src/MatchTPCITS.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -155,6 +155,7 @@ void MatchTPCITS::clear()
mITSROFTimes.clear();
mITSTrackROFContMapping.clear();
mITSClustersArray.clear();
mITSClusterSizes.clear();
mTPCABSeeds.clear();
mTPCABIndexCache.clear();
mABWinnersIDs.clear();
Expand Down Expand Up @@ -309,7 +310,7 @@ bool MatchTPCITS::validateTPCMatch(int iTPC)
if (rcITS.nextRecID == Validated) {
return false;
}
if (rcITS.partnerID == iTPC) { // is best matching TPC track for this ITS track actually iTPC?
if (rcITS.partnerID == iTPC) { // is best matching TPC track for this ITS track actually iTPC?
int cloneID = tITS.getCloneShift(); // check if there is a clone of tITS
while (cloneID) {
cloneID += rcTPC.partnerID;
Expand Down Expand Up @@ -580,6 +581,27 @@ bool MatchTPCITS::prepareITSData()
auto pattIt = patterns.begin();
mITSClustersArray.reserve(clusITS.size());
o2::its::ioutils::convertCompactClusters(clusITS, pattIt, mITSClustersArray, mITSDict);

// ITS clusters sizes
mITSClusterSizes.reserve(clusITS.size());
auto pattIt2 = patterns.begin();
for (auto& clus : clusITS) {
auto pattID = clus.getPatternID();
unsigned int npix;
if (pattID == o2::itsmft::CompCluster::InvalidPatternID || mITSDict->isGroup(pattID)) {
o2::itsmft::ClusterPattern patt;
patt.acquirePattern(pattIt2);
npix = patt.getNPixels();
} else {
npix = mITSDict->getNpixels(pattID);
}
if (npix < 255) {
mITSClusterSizes.push_back(npix);
} else {
mITSClusterSizes.push_back(255);
}
}

if (mMCTruthON) {
mITSClsLabels = inp.mcITSClusters.get();
}
Expand Down Expand Up @@ -1295,21 +1317,21 @@ bool MatchTPCITS::refitTrackTPCITS(int iTPC, int& iITS, pmr::vector<o2::dataform
const auto& itsTrOrig = mITSTracksArray[tITS.sourceID];

auto& trfit = matchedTracks.emplace_back(tTPC, tITS); // create a copy of TPC track at xRef
trfit.getParamOut().setUserField(0); // reset eventual clones flag
trfit.getParamOut().setUserField(0); // reset eventual clones flag
// in continuos mode the Z of TPC track is meaningless, unless it is CE crossing
// track (currently absent, TODO)
if (!mCompareTracksDZ) {
trfit.setZ(tITS.getZ()); // fix the seed Z
}
float deltaT = (trfit.getZ() - tTPC.getZ()) * mTPCVDriftInv; // time correction in \mus
float timeErr = tTPC.constraint == TrackLocTPC::Constrained ? tTPC.timeErr : std::sqrt(tITS.getSigmaZ2() + tTPC.getSigmaZ2()) * mTPCVDriftInv; // estimate the error on time
float deltaT = (trfit.getZ() - tTPC.getZ()) * mTPCVDriftInv; // time correction in \mus
float timeErr = tTPC.constraint == TrackLocTPC::Constrained ? tTPC.timeErr : std::sqrt(tITS.getSigmaZ2() + tTPC.getSigmaZ2()) * mTPCVDriftInv; // estimate the error on time
if (timeErr > mITSTimeResMUS && tTPC.constraint != TrackLocTPC::Constrained) {
timeErr = mITSTimeResMUS; // chose smallest error
deltaT = tTPC.constraint == TrackLocTPC::ASide ? tITS.tBracket.mean() - tTPC.time0 : tTPC.time0 - tITS.tBracket.mean();
}
timeErr += mParams->globalTimeExtraErrorMUS;
float timeC = tTPC.getCorrectedTime(deltaT) + mParams->globalTimeBiasMUS; /// precise time estimate, optionally corrected for bias
if (timeC < 0) { // RS TODO similar check is needed for other edge of TF
float timeC = tTPC.getCorrectedTime(deltaT) + mParams->globalTimeBiasMUS; /// precise time estimate, optionally corrected for bias
if (timeC < 0) { // RS TODO similar check is needed for other edge of TF
if (timeC + std::min(timeErr, mParams->tfEdgeTimeToleranceMUS * mTPCTBinMUSInv) < 0) {
matchedTracks.pop_back(); // destroy failed track
return false;
Expand Down Expand Up @@ -1845,6 +1867,7 @@ void MatchTPCITS::refitABWinners(pmr::vector<o2::dataformats::TrackTPCITS>& matc
ABTrackletClusterIDs.push_back(winL.clID);
ncl++;
clref.pattern |= 0x1 << winL.layerID;
clref.setClusterSize(winL.layerID, mITSClusterSizes[winL.clID]);
if (mMCTruthON) {
accountClusterLabel(winL.clID);
}
Expand Down
7 changes: 7 additions & 0 deletions Detectors/ITSMFT/ITS/tracking/include/ITStracking/TimeFrame.h
Original file line number Diff line number Diff line change
Expand Up @@ -129,6 +129,7 @@ class TimeFrame
const gsl::span<const MCCompLabel> getClusterLabels(int layerId, const Cluster& cl) const;
const gsl::span<const MCCompLabel> getClusterLabels(int layerId, const int clId) const;
int getClusterExternalIndex(int layerId, const int clId) const;
int getClusterSize(int clusterId);

std::vector<MCCompLabel>& getTrackletsLabel(int layer) { return mTrackletLabels[layer]; }
std::vector<MCCompLabel>& getCellsLabel(int layer) { return mCellLabels[layer]; }
Expand Down Expand Up @@ -244,6 +245,7 @@ class TimeFrame
std::vector<float> mMSangles;
std::vector<float> mPhiCuts;
std::vector<float> mPositionResolution;
std::vector<uint8_t> mClusterSize;
std::vector<bool> mMultiplicityCutMask;
std::vector<std::array<float, 2>> mPValphaX; /// PV x and alpha for track propagation
std::vector<std::vector<Cluster>> mUnsortedClusters;
Expand Down Expand Up @@ -424,6 +426,11 @@ inline const gsl::span<const MCCompLabel> TimeFrame::getClusterLabels(int layerI
return mClusterLabels->getLabels(mClusterExternalIndices[layerId][clId]);
}

inline int TimeFrame::getClusterSize(int clusterId)
{
return mClusterSize[clusterId];
}

inline int TimeFrame::getClusterExternalIndex(int layerId, const int clId) const
{
return mClusterExternalIndices[layerId][clId];
Expand Down
11 changes: 11 additions & 0 deletions Detectors/ITSMFT/ITS/tracking/src/TimeFrame.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -175,6 +175,8 @@ int TimeFrame::loadROFrameData(gsl::span<o2::itsmft::ROFRecord> rofs,
geom->fillMatrixCache(o2::math_utils::bit2Mask(o2::math_utils::TransformType::T2L, o2::math_utils::TransformType::L2G));

mNrof = 0;
mClusterSize.clear();
mClusterSize.reserve(clusters.size());
for (auto& rof : rofs) {
for (int clusterId{rof.getFirstEntry()}; clusterId < rof.getFirstEntry() + rof.getNEntries(); ++clusterId) {
auto& c = clusters[clusterId];
Expand All @@ -184,18 +186,27 @@ int TimeFrame::loadROFrameData(gsl::span<o2::itsmft::ROFRecord> rofs,
auto pattID = c.getPatternID();
o2::math_utils::Point3D<float> locXYZ;
float sigmaY2 = DefClusError2Row, sigmaZ2 = DefClusError2Col, sigmaYZ = 0; // Dummy COG errors (about half pixel size)
unsigned int clusterSize{0};
if (pattID != itsmft::CompCluster::InvalidPatternID) {
sigmaY2 = dict->getErr2X(pattID);
sigmaZ2 = dict->getErr2Z(pattID);
if (!dict->isGroup(pattID)) {
locXYZ = dict->getClusterCoordinates(c);
clusterSize = dict->getNpixels(pattID);
} else {
o2::itsmft::ClusterPattern patt(pattIt);
locXYZ = dict->getClusterCoordinates(c, patt);
clusterSize = patt.getNPixels();
}
} else {
o2::itsmft::ClusterPattern patt(pattIt);
locXYZ = dict->getClusterCoordinates(c, patt, false);
clusterSize = patt.getNPixels();
}
if (clusterSize < 255) {
mClusterSize.push_back(clusterSize);
} else {
mClusterSize.push_back(255);
}
auto sensorID = c.getSensorID();
// Inverse transformation to the local --> tracking
Expand Down
1 change: 1 addition & 0 deletions Detectors/ITSMFT/ITS/workflow/src/TrackerSpec.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -296,6 +296,7 @@ void TrackerDPL::run(ProcessingContext& pc)
for (int ic = TrackITSExt::MaxClusters; ic--;) { // track internally keeps in->out cluster indices, but we want to store the references as out->in!!!
auto clid = trc.getClusterIndex(ic);
if (clid >= 0) {
trc.setClusterSize(ic, mTimeFrame->getClusterSize(clid));
allClusIdx.push_back(clid);
nclf++;
}
Expand Down
Loading

0 comments on commit 997cb57

Please sign in to comment.