Skip to content

Commit a060997

Browse files
victor-gonzalezVictor
andauthored
[PWGCF] DptDpt - Tracking the ITS dead chips (#10237)
Co-authored-by: Victor <victor@cern.ch>
1 parent bd1aafc commit a060997

File tree

1 file changed

+76
-8
lines changed

1 file changed

+76
-8
lines changed

PWGCF/TwoParticleCorrelations/Tasks/perRunQc.cxx

Lines changed: 76 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -8,16 +8,25 @@
88
// In applying this license CERN does not waive the privileges and immunities
99
// granted to it by virtue of its status as an Intergovernmental Organization
1010
// or submit itself to any jurisdiction.
11-
//
12-
// Minimal example to run this task:
13-
// o2-analysis-centrality-table -b --configuration json://configuration.json | o2-analysis-timestamp -b --configuration json://configuration.json | o2-analysis-event-selection -b --configuration json://configuration.json | o2-analysis-multiplicity-table -b --configuration json://configuration.json | o2-analysis-lf-zdcsp -b --configuration json://configuration.json --aod-file @input_data.txt --aod-writer-json OutputDirector.json
11+
12+
/// \file perRunQc.cxx
13+
/// \brief basic per run check of the ITS dead chips and of the hadronic interaction rate
14+
/// \author victor.gonzalez.sebastian@gmail.com
1415

1516
#include <array>
1617
#include <cmath>
18+
#include <unordered_map>
19+
#include <memory>
20+
#include <vector>
1721

1822
#include "CCDB/BasicCCDBManager.h"
1923
#include "Common/CCDB/ctpRateFetcher.h"
2024

25+
#include "DataFormatsParameters/AggregatedRunInfo.h"
26+
#include "DataFormatsITSMFT/NoiseMap.h" // missing include in TimeDeadMap.h
27+
#include "DataFormatsITSMFT/TimeDeadMap.h"
28+
#include "ITSMFTReconstruction/ChipMappingITS.h"
29+
2130
#include "Framework/AnalysisDataModel.h"
2231
#include "Framework/AnalysisTask.h"
2332
#include "Framework/ASoAHelpers.h"
@@ -35,17 +44,22 @@ using BCsWithTimestamps = soa::Join<aod::BCs, aod::Timestamps>;
3544

3645
namespace perrunqatask
3746
{
47+
static const int32_t nBCsPerOrbit = o2::constants::lhc::LHCMaxBunches;
3848
std::unordered_map<int, TH2*> gHadronicRate;
49+
std::unordered_map<int, std::vector<std::shared_ptr<TH2>>> gDeadChipsVsOrbitInLayer;
50+
std::unordered_map<int, std::shared_ptr<TH1>> gCollisionOrbitBefore;
51+
std::unordered_map<int, std::shared_ptr<TH1>> gCollisionOrbitAfter;
3952

4053
TH2* gCurrentHadronicRate;
54+
std::shared_ptr<TH1> gCurrentCollisionOrbitBefore;
55+
std::shared_ptr<TH1> gCurrentCollisionOrbitAfter;
4156
} // namespace perrunqatask
4257

4358
struct DptDptPerRunQa {
4459

4560
Service<o2::ccdb::BasicCCDBManager> ccdb;
4661

4762
int mRunNumber{-1};
48-
uint64_t mSOR{0};
4963
double mMinSeconds{-1.};
5064

5165
ctpRateFetcher mRateFetcher;
@@ -62,13 +76,63 @@ struct DptDptPerRunQa {
6276
mRunNumber = bc.runNumber();
6377
if (gHadronicRate.find(mRunNumber) == gHadronicRate.end()) {
6478
auto runDuration = ccdb->getRunDuration(mRunNumber);
65-
mSOR = runDuration.first;
79+
uint64_t mSOR = runDuration.first;
6680
mMinSeconds = std::floor(mSOR * 1.e-3); /// round tsSOR to the highest integer lower than tsSOR
6781
double maxSec = std::ceil(runDuration.second * 1.e-3); /// round tsEOR to the lowest integer higher than tsEOR
6882
const AxisSpec axisSeconds{static_cast<int>(maxSec - mMinSeconds), 0, maxSec - mMinSeconds, "Seconds since SOR"};
6983
gHadronicRate[mRunNumber] = mHistos.add<TH2>(Form("%i/hadronicRate", mRunNumber), ";Time since SOR (s);Hadronic rate (kHz)", kTH2D, {{static_cast<int>((maxSec - mMinSeconds) / 20.f), 0, maxSec - mMinSeconds, "Seconds since SOR"}, {1010, 0., 1010.}}).get();
84+
85+
/* initializing the ITS chips dead map*/
86+
/* inspired in DPG/Tasks/AOTEvent/eventSelectionQa.cxx */
87+
auto runInfo = o2::parameters::AggregatedRunInfo::buildAggregatedRunInfo(o2::ccdb::BasicCCDBManager::instance(), mRunNumber);
88+
int64_t tsSOR = runInfo.sor;
89+
int64_t tsEOR = runInfo.eor;
90+
o2::itsmft::TimeDeadMap* itsDeadMap = ccdb->getForTimeStamp<o2::itsmft::TimeDeadMap>("ITS/Calib/TimeDeadMap", (tsSOR + tsEOR) / 2);
91+
auto itsDeadMapOrbits = itsDeadMap->getEvolvingMapKeys(); // roughly every second, ~350 TFs = 350x32 orbits
92+
if (itsDeadMapOrbits.size() > 0) {
93+
std::vector<double> itsDeadMapOrbitsDouble(itsDeadMapOrbits.begin(), itsDeadMapOrbits.end());
94+
const AxisSpec axisItsDeadMapOrbits{itsDeadMapOrbitsDouble};
95+
gDeadChipsVsOrbitInLayer[mRunNumber] = std::vector<std::shared_ptr<TH2>>(o2::itsmft::ChipMappingITS::NLayers, nullptr);
96+
for (int layer = 0; layer < o2::itsmft::ChipMappingITS::NLayers; ++layer) {
97+
int nChips = o2::itsmft::ChipMappingITS::getNChipsOnLayer(layer);
98+
double idFirstChip = o2::itsmft::ChipMappingITS::getFirstChipsOnLayer(layer);
99+
gDeadChipsVsOrbitInLayer[mRunNumber][layer] = mHistos.add<TH2>(TString::Format("%d/Before/hDeadChipsVsOrbitInLayer%d", mRunNumber, layer),
100+
TString::Format("Dead chips in ITS layer %d, before;orbit; chip", layer),
101+
kTH2C, {axisItsDeadMapOrbits, {nChips, idFirstChip, idFirstChip + nChips}});
102+
}
103+
gCollisionOrbitBefore[mRunNumber] = mHistos.add<TH1>(TString::Format("%d/Before/hCollisionOrbitB", mRunNumber), "Collision orbit before; orbit", kTH1I, {axisItsDeadMapOrbits});
104+
gCollisionOrbitAfter[mRunNumber] = mHistos.add<TH1>(TString::Format("%d/After/hCollisionOrbitA", mRunNumber), "Collision orbit; orbit", kTH1I, {axisItsDeadMapOrbits});
105+
LOGF(info, "Created the histograms");
106+
107+
std::vector<uint16_t> vClosest;
108+
for (const auto& orbit : itsDeadMapOrbits) {
109+
itsDeadMap->getMapAtOrbit(orbit, vClosest);
110+
for (size_t iel = 0; iel < vClosest.size(); iel++) {
111+
// dead chips are stored as ranges
112+
// vClosest contains first and last chip ids in the range
113+
// last chip id in the range is marked with 0x8000 bit set to 1
114+
uint16_t w1 = vClosest[iel];
115+
bool isLastInSequence = (w1 & 0x8000) == 0;
116+
uint16_t w2 = isLastInSequence ? w1 + 1 : vClosest[iel + 1];
117+
uint16_t chipId1 = w1 & 0x7FFF;
118+
uint16_t chipId2 = w2 & 0x7FFF;
119+
for (int chipId = chipId1; chipId < chipId2; chipId++) {
120+
for (int layer = 0; layer < o2::itsmft::ChipMappingITS::NLayers; ++layer) {
121+
gDeadChipsVsOrbitInLayer[mRunNumber][layer]->Fill(orbit, chipId, 1);
122+
}
123+
}
124+
}
125+
}
126+
LOGF(info, "Initializing the current ones");
127+
gCurrentCollisionOrbitBefore = gCollisionOrbitBefore[mRunNumber];
128+
gCurrentCollisionOrbitAfter = gCollisionOrbitAfter[mRunNumber];
129+
} else {
130+
gCurrentCollisionOrbitBefore = nullptr;
131+
gCurrentCollisionOrbitAfter = nullptr;
132+
}
70133
}
71134
gCurrentHadronicRate = gHadronicRate[mRunNumber];
135+
LOGF(info, "Getting out");
72136
}
73137

74138
void init(o2::framework::InitContext&)
@@ -78,20 +142,24 @@ struct DptDptPerRunQa {
78142
ccdb->setFatalWhenNull(false);
79143
}
80144

81-
void process(soa::Join<aod::Collisions, aod::DptDptCFCollisionsInfo>::iterator const& collision, aod::BCsWithTimestamps const&)
145+
void process(soa::Join<aod::Collisions, aod::EvSels, aod::DptDptCFCollisionsInfo>::iterator const& collision, aod::BCsWithTimestamps const&)
82146
{
83147
using namespace perrunqatask;
84148
using namespace analysis::dptdptfilter;
85149

150+
auto bc = collision.bc_as<aod::BCsWithTimestamps>();
151+
initCCDB(bc);
152+
int64_t orbit = bc.globalBC() / nBCsPerOrbit;
153+
gCurrentCollisionOrbitBefore->Fill(orbit);
154+
86155
if (!collision.collisionaccepted()) {
87156
return;
88157
}
89158

90-
auto bc = collision.bc_as<aod::BCsWithTimestamps>();
91-
initCCDB(bc);
92159
double hadronicRate = mRateFetcher.fetch(ccdb.service, bc.timestamp(), mRunNumber, "T0VTX") * 1.e-3; //
93160
double seconds = bc.timestamp() * 1.e-3 - mMinSeconds;
94161
gCurrentHadronicRate->Fill(seconds, hadronicRate);
162+
gCurrentCollisionOrbitAfter->Fill(orbit);
95163
}
96164
};
97165

0 commit comments

Comments
 (0)