From d3ad989b18a7775dcc40b456a9ebfe3da765bd69 Mon Sep 17 00:00:00 2001 From: Francesco Mazzaschi <43742195+fmazzasc@users.noreply.github.com> Date: Tue, 19 Dec 2023 08:07:42 +0100 Subject: [PATCH] Add workflow for ITS PID study (#12478) * Add workflow for ITS PID study * Update author * Update author in the header * Add MC matching + fix output name * Add custom BB resolution * Update PIDStudy.cxx Co-authored-by: Matteo Concas --------- Co-authored-by: Matteo Concas --- .../ITS/postprocessing/studies/CMakeLists.txt | 1 + .../ITSStudies/ITSStudiesConfigParam.h | 9 + .../studies/include/ITSStudies/PIDStudy.h | 36 ++ .../studies/src/ITSStudiesConfigParam.cxx | 2 + .../studies/src/ITSStudiesLinkDef.h | 2 + .../postprocessing/studies/src/PIDStudy.cxx | 351 ++++++++++++++++++ .../standalone-postprocessing-workflow.cxx | 8 +- 7 files changed, 408 insertions(+), 1 deletion(-) create mode 100644 Detectors/ITSMFT/ITS/postprocessing/studies/include/ITSStudies/PIDStudy.h create mode 100644 Detectors/ITSMFT/ITS/postprocessing/studies/src/PIDStudy.cxx diff --git a/Detectors/ITSMFT/ITS/postprocessing/studies/CMakeLists.txt b/Detectors/ITSMFT/ITS/postprocessing/studies/CMakeLists.txt index a4448aa1e9bc1..6cc53dfa6ea90 100644 --- a/Detectors/ITSMFT/ITS/postprocessing/studies/CMakeLists.txt +++ b/Detectors/ITSMFT/ITS/postprocessing/studies/CMakeLists.txt @@ -12,6 +12,7 @@ o2_add_library(ITSPostprocessing SOURCES src/ImpactParameter.cxx src/AvgClusSize.cxx + src/PIDStudy.cxx src/ITSStudiesConfigParam.cxx src/TrackCheck.cxx src/Helpers.cxx diff --git a/Detectors/ITSMFT/ITS/postprocessing/studies/include/ITSStudies/ITSStudiesConfigParam.h b/Detectors/ITSMFT/ITS/postprocessing/studies/include/ITSStudies/ITSStudiesConfigParam.h index 8399d01d818fb..0f8d416bfeb09 100644 --- a/Detectors/ITSMFT/ITS/postprocessing/studies/include/ITSStudies/ITSStudiesConfigParam.h +++ b/Detectors/ITSMFT/ITS/postprocessing/studies/include/ITSStudies/ITSStudiesConfigParam.h @@ -73,6 +73,15 @@ struct ITSAvgClusSizeParamConfig : public o2::conf::ConfigurableParamHelper { + std::string outFileName = "its_PIDStudy.root"; + // default: average 2023 from C. Sonnabend, Nov 2023: ([0.217553 4.02762 0.00850178 2.33324 0.880904 ]) + // to-do: grab from CCDB when available + float mBBpars[5] = {0.217553, 4.02762, 0.00850178, 2.33324, 0.880904}; + float mBBres = 0.07; // default: 7% resolution + O2ParamDef(PIDStudyParamConfig, "PIDStudyParam"); +}; + struct ITSImpactParameterParamConfig : public o2::conf::ConfigurableParamHelper { std::string outFileName = "its_ImpParameter.root"; int minNumberOfContributors = 0; diff --git a/Detectors/ITSMFT/ITS/postprocessing/studies/include/ITSStudies/PIDStudy.h b/Detectors/ITSMFT/ITS/postprocessing/studies/include/ITSStudies/PIDStudy.h new file mode 100644 index 0000000000000..54c7e5f387e90 --- /dev/null +++ b/Detectors/ITSMFT/ITS/postprocessing/studies/include/ITSStudies/PIDStudy.h @@ -0,0 +1,36 @@ +// Copyright 2019-2020 CERN and copyright holders of ALICE O2. +// See https://alice-o2.web.cern.ch/copyright for details of the copyright holders. +// All rights not expressly granted are reserved. +// +// This software is distributed under the terms of the GNU General Public +// License v3 (GPL Version 3), copied verbatim in the file "COPYING". +// +// In applying this license CERN does not waive the privileges and immunities +// granted to it by virtue of its status as an Intergovernmental Organization +// or submit itself to any jurisdiction. + +/// \file PIDStudy.h +/// \author Francesco Mazzaschi, fmazzasc@cern.ch + +#ifndef O2_PID_STUDY_H +#define O2_PID_STUDY_H + +#include "Framework/DataProcessorSpec.h" +#include "ReconstructionDataFormats/GlobalTrackID.h" +#include + +namespace o2 +{ +namespace its +{ +namespace study +{ + +using mask_t = o2::dataformats::GlobalTrackID::mask_t; + +o2::framework::DataProcessorSpec getPIDStudy(mask_t srcTracksMask, mask_t srcClustersMask, bool useMC, std::shared_ptr kineReader); +} // namespace study +} // namespace its +} // namespace o2 + +#endif \ No newline at end of file diff --git a/Detectors/ITSMFT/ITS/postprocessing/studies/src/ITSStudiesConfigParam.cxx b/Detectors/ITSMFT/ITS/postprocessing/studies/src/ITSStudiesConfigParam.cxx index 7652f175434da..1ece01a94e456 100644 --- a/Detectors/ITSMFT/ITS/postprocessing/studies/src/ITSStudiesConfigParam.cxx +++ b/Detectors/ITSMFT/ITS/postprocessing/studies/src/ITSStudiesConfigParam.cxx @@ -18,10 +18,12 @@ namespace its namespace study { static auto& sAvgClusSizeParamITS = o2::its::study::ITSAvgClusSizeParamConfig::Instance(); +static auto& sPIDStudyParamITS = o2::its::study::PIDStudyParamConfig::Instance(); static auto& sCheckTracksParamsITS = o2::its::study::ITSCheckTracksParamConfig::Instance(); static auto& sImpactParameterParamsITS = o2::its::study::ITSImpactParameterParamConfig::Instance(); O2ParamImpl(o2::its::study::ITSAvgClusSizeParamConfig); +O2ParamImpl(o2::its::study::PIDStudyParamConfig); O2ParamImpl(o2::its::study::ITSCheckTracksParamConfig); O2ParamImpl(o2::its::study::ITSImpactParameterParamConfig); diff --git a/Detectors/ITSMFT/ITS/postprocessing/studies/src/ITSStudiesLinkDef.h b/Detectors/ITSMFT/ITS/postprocessing/studies/src/ITSStudiesLinkDef.h index 4bf0900ebad48..182bdc9e6c851 100644 --- a/Detectors/ITSMFT/ITS/postprocessing/studies/src/ITSStudiesLinkDef.h +++ b/Detectors/ITSMFT/ITS/postprocessing/studies/src/ITSStudiesLinkDef.h @@ -16,8 +16,10 @@ #pragma link off all functions; #pragma link C++ class o2::its::study::ITSAvgClusSizeParamConfig + ; +#pragma link C++ class o2::its::study::PIDStudyParamConfig + ; #pragma link C++ class o2::its::study::ITSImpactParameterParamConfig + ; #pragma link C++ class o2::conf::ConfigurableParamHelper < o2::its::study::ITSAvgClusSizeParamConfig> + ; +#pragma link C++ class o2::conf::ConfigurableParamHelper < o2::its::study::PIDStudyParamConfig> + ; #pragma link C++ class o2::conf::ConfigurableParamHelper < o2::its::study::ITSCheckTracksParamConfig> + ; #pragma link C++ class o2::conf::ConfigurableParamHelper < o2::its::study::ITSImpactParameterParamConfig> + ; #pragma link C++ function o2::its::studies::makeLogBinning + ; diff --git a/Detectors/ITSMFT/ITS/postprocessing/studies/src/PIDStudy.cxx b/Detectors/ITSMFT/ITS/postprocessing/studies/src/PIDStudy.cxx new file mode 100644 index 0000000000000..4b0f553eb774b --- /dev/null +++ b/Detectors/ITSMFT/ITS/postprocessing/studies/src/PIDStudy.cxx @@ -0,0 +1,351 @@ +// Copyright 2019-2020 CERN and copyright holders of ALICE O2. +// See https://alice-o2.web.cern.ch/copyright for details of the copyright holders. +// All rights not expressly granted are reserved. +// +// This software is distributed under the terms of the GNU General Public +// License v3 (GPL Version 3), copied verbatim in the file "COPYING". +// +// In applying this license CERN does not waive the privileges and immunities +// granted to it by virtue of its status as an Intergovernmental Organization +// or submit itself to any jurisdiction. + +/// \file PIDStudy.cxx +/// \brief Study to evaluate the PID performance of the ITS +/// \author Francesco Mazzaschi, fmazzasc@cern.ch + +#include "ITSStudies/PIDStudy.h" +#include "ITSStudies/ITSStudiesConfigParam.h" + +#include "Framework/Task.h" +#include "ITSBase/GeometryTGeo.h" +#include "Steer/MCKinematicsReader.h" +#include "DetectorsBase/GRPGeomHelper.h" +#include "ITStracking/IOUtils.h" +#include "CommonUtils/TreeStreamRedirector.h" +#include "DataFormatsParameters/GRPObject.h" +#include "DataFormatsITS/TrackITS.h" +#include "DataFormatsTPC/TrackTPC.h" +#include "ReconstructionDataFormats/TrackTPCITS.h" +#include "DataFormatsGlobalTracking/RecoContainer.h" +#include "ReconstructionDataFormats/GlobalTrackID.h" +#include "ReconstructionDataFormats/PrimaryVertex.h" +#include "ReconstructionDataFormats/PID.h" +#include "ReconstructionDataFormats/V0.h" +#include "ReconstructionDataFormats/Track.h" +#include "ReconstructionDataFormats/DCA.h" +#include "SimulationDataFormat/MCTrack.h" +#include "SimulationDataFormat/MCCompLabel.h" +#include "DetectorsCommonDataFormats/DetID.h" +#include "DataFormatsTPC/PIDResponse.h" + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +namespace o2 +{ +namespace its +{ +namespace study +{ +using namespace o2::framework; +using namespace o2::globaltracking; + +using GTrackID = o2::dataformats::GlobalTrackID; +using PVertex = o2::dataformats::PrimaryVertex; +using V0 = o2::dataformats::V0; +using ITSCluster = o2::BaseCluster; +using mask_t = o2::dataformats::GlobalTrackID::mask_t; +using Track = o2::track::TrackParCov; +using TrackITS = o2::its::TrackITS; +using TrackTPC = o2::tpc::TrackTPC; +using TrackITSTPC = o2::dataformats::TrackTPCITS; +using PIDResponse = o2::tpc::PIDResponse; +using DCA = o2::dataformats::DCA; +using PID = o2::track::PID; + +// structure for storing the output tree +struct particle { + // mc properties + int pdg = -1; + bool fakeMatch = 0; + // reco properties + int sign = -1; + float p, pt, pTPC, pITS, eta, phi, tgL, chi2ITS, chi2TPC, chi2ITSTPC; + int nClusTPC; + float dEdx, nSigmaDeu, nSigmaP, nSigmaK, nSigmaPi, nSigmaE; + int clSizeL0, clSizeL1, clSizeL2, clSizeL3, clSizeL4, clSizeL5, clSizeL6; + std::array clSizesITS; +}; + +class PIDStudy : public Task +{ + public: + PIDStudy(std::shared_ptr dr, + std::shared_ptr gr, + bool isMC, + std::shared_ptr kineReader) : mDataRequest{dr}, mGGCCDBRequest(gr), mUseMC(isMC), mKineReader(kineReader){}; + ~PIDStudy() final = default; + void init(InitContext& ic) final; + void run(ProcessingContext&) final; + void endOfStream(EndOfStreamContext&) final; + void finaliseCCDB(ConcreteDataMatcher&, void*) final; + void setClusterDictionary(const o2::itsmft::TopologyDictionary* d) { mDict = d; } + + private: + // Other functions + void process(o2::globaltracking::RecoContainer&); + void loadData(o2::globaltracking::RecoContainer&); + + // Helper functions + void saveOutput(); + void updateTimeDependentParams(ProcessingContext& pc); + void getClusterSizes(std::vector&, const gsl::span, gsl::span::iterator&, const o2::itsmft::TopologyDictionary*); + std::array getTrackClusterSizes(const TrackITS& track); + float computeNSigma(PID pid, TrackTPC& tpcTrack, float resolution); + + // Running options + bool mUseMC; + + PIDResponse mPIDresponse; + float mBBres; + // Data + std::shared_ptr mGGCCDBRequest; + std::shared_ptr mDataRequest; + std::vector mClusterSizes; + gsl::span mClusters; + gsl::span mInputITSidxs; + const o2::itsmft::TopologyDictionary* mDict = nullptr; + + std::unique_ptr mDBGOut; + std::string mOutName; + std::shared_ptr mKineReader; +}; + +void PIDStudy::init(InitContext& ic) +{ + o2::base::GRPGeomHelper::instance().setRequest(mGGCCDBRequest); + LOGP(info, "Starting average cluster size study..."); + + if (mUseMC) { // for counting the missed K0shorts + mKineReader = std::make_unique("collisioncontext.root"); + } + auto& params = o2::its::study::PIDStudyParamConfig::Instance(); + mOutName = params.outFileName; + mPIDresponse.setBetheBlochParams(params.mBBpars); + mBBres = params.mBBres; + LOGP(info, "PID size study initialized."); + + // prepare output tree + mDBGOut = std::make_unique(mOutName.c_str(), "recreate"); +} + +void PIDStudy::run(ProcessingContext& pc) +{ + // auto geom = o2::its::GeometryTGeo::Instance(); + o2::globaltracking::RecoContainer recoData; + recoData.collectData(pc, *mDataRequest.get()); + updateTimeDependentParams(pc); // Make sure this is called after recoData.collectData, which may load some conditions + process(recoData); +} + +void PIDStudy::getClusterSizes(std::vector& clusSizeVec, const gsl::span ITSclus, gsl::span::iterator& pattIt, const o2::itsmft::TopologyDictionary* mdict) +{ + for (unsigned int iClus{0}; iClus < ITSclus.size(); ++iClus) { + auto& clus = ITSclus[iClus]; + auto pattID = clus.getPatternID(); + int npix; + o2::itsmft::ClusterPattern patt; + + if (pattID == o2::itsmft::CompCluster::InvalidPatternID || mdict->isGroup(pattID)) { + patt.acquirePattern(pattIt); + npix = patt.getNPixels(); + } else { + npix = mdict->getNpixels(pattID); + patt = mdict->getPattern(pattID); + } + clusSizeVec[iClus] = npix; + } +} + +void PIDStudy::loadData(o2::globaltracking::RecoContainer& recoData) +{ + mInputITSidxs = recoData.getITSTracksClusterRefs(); + mClusters = recoData.getITSClusters(); + auto clusPatt = recoData.getITSClustersPatterns(); + mClusterSizes.resize(mClusters.size()); + auto pattIt = clusPatt.begin(); + getClusterSizes(mClusterSizes, mClusters, pattIt, mDict); +} + +void PIDStudy::process(o2::globaltracking::RecoContainer& recoData) +{ + loadData(recoData); + auto ITSTPCtracks = recoData.getTPCITSTracks(); + LOGP(debug, "Found {} ITSTPC tracks.", ITSTPCtracks.size()); + + gsl::span mcLabelsITS, mcLabelsTPC; + if (mUseMC) { + mcLabelsITS = recoData.getITSTracksMCLabels(); + mcLabelsTPC = recoData.getTPCTracksMCLabels(); + LOGP(debug, "Found {} ITS labels.", mcLabelsITS.size()); + LOGP(debug, "Found {} TPC labels.", mcLabelsTPC.size()); + } + + for (unsigned int iTrack{0}; iTrack < ITSTPCtracks.size(); ++iTrack) { + + auto& ITSTPCtrack = ITSTPCtracks[iTrack]; + if (ITSTPCtrack.getRefITS().getSource() == GTrackID::ITSAB) { // excluding Afterburned tracks + continue; + } + particle part; + auto ITStrack = recoData.getITSTrack(ITSTPCtrack.getRefITS()); + auto TPCtrack = recoData.getTPCTrack(ITSTPCtrack.getRefTPC()); + + if (mUseMC) { + // MC info + auto& mcLabelITS = mcLabelsITS[ITSTPCtrack.getRefITS().getIndex()]; + auto& mcLabelTPC = mcLabelsTPC[ITSTPCtrack.getRefTPC().getIndex()]; + if (mcLabelITS.getTrackID() != (int)mcLabelTPC.getTrackID()) { + part.fakeMatch = 1; + } + auto mctrk = mKineReader->getTrack(mcLabelITS); + part.pdg = mctrk->GetPdgCode(); + } + + part.sign = ITSTPCtrack.getSign(); + part.clSizesITS = getTrackClusterSizes(ITStrack); + part.p = ITSTPCtrack.getP(); + part.pt = ITSTPCtrack.getPt(); + part.pTPC = TPCtrack.getP(); + part.pITS = ITStrack.getP(); + part.eta = ITSTPCtrack.getEta(); + part.phi = ITSTPCtrack.getPhi(); + part.tgL = ITSTPCtrack.getTgl(); + part.chi2ITS = ITStrack.getChi2(); + part.chi2TPC = TPCtrack.getChi2(); + part.chi2ITSTPC = ITSTPCtrack.getChi2Match(); + + part.clSizeL0 = part.clSizesITS[0]; + part.clSizeL1 = part.clSizesITS[1]; + part.clSizeL2 = part.clSizesITS[2]; + part.clSizeL3 = part.clSizesITS[3]; + part.clSizeL4 = part.clSizesITS[4]; + part.clSizeL5 = part.clSizesITS[5]; + part.clSizeL6 = part.clSizesITS[6]; + + // PID info + part.dEdx = TPCtrack.getdEdx().dEdxTotTPC; + part.nClusTPC = TPCtrack.getNClusters(); + // 7% resolution for all particles + part.nSigmaDeu = computeNSigma(PID::Deuteron, TPCtrack, mBBres); + part.nSigmaP = computeNSigma(PID::Proton, TPCtrack, mBBres); + part.nSigmaK = computeNSigma(PID::Kaon, TPCtrack, mBBres); + part.nSigmaPi = computeNSigma(PID::Pion, TPCtrack, mBBres); + part.nSigmaE = computeNSigma(PID::Electron, TPCtrack, mBBres); + + if (mUseMC) { + (*mDBGOut) << "outTree" + << "pdg=" << part.pdg << "fakeMatch=" << part.fakeMatch; + } + (*mDBGOut) << "outTree" + << "sign=" << part.sign << "p=" << part.p << "pt=" << part.pt << "pTPC=" << part.pTPC << "pITS=" << part.pITS + << "eta=" << part.eta << "phi=" << part.phi << "tgL=" << part.tgL << "chi2ITS=" << part.chi2ITS << "chi2TPC=" + << part.chi2TPC << "chi2ITSTPC=" << part.chi2ITSTPC << "dEdx=" << part.dEdx << "nClusTPC=" << part.nClusTPC + << "nSigmaDeu=" << part.nSigmaDeu << "nSigmaP=" << part.nSigmaP << "nSigmaK=" << part.nSigmaK << "nSigmaPi=" + << part.nSigmaPi << "nSigmaE=" << part.nSigmaE << "clSizeL0=" << part.clSizeL0 << "clSizeL1=" << part.clSizeL1 + << "clSizeL2=" << part.clSizeL2 << "clSizeL3=" << part.clSizeL3 << "clSizeL4=" << part.clSizeL4 << "clSizeL5=" + << part.clSizeL5 << "clSizeL6=" << part.clSizeL6 << "\n"; + } +} + +std::array PIDStudy::getTrackClusterSizes(const TrackITS& track) +{ + auto geom = o2::its::GeometryTGeo::Instance(); + std::array clusSizes = {-1, -1, -1, -1, -1, -1, -1}; + auto firstClus = track.getFirstClusterEntry(); + auto ncl = track.getNumberOfClusters(); + for (int icl = 0; icl < ncl; icl++) { + auto& clus = mClusters[mInputITSidxs[firstClus + icl]]; + auto& clSize = mClusterSizes[mInputITSidxs[firstClus + icl]]; + auto layer = geom->getLayer(clus.getSensorID()); + clusSizes[layer] = clSize; + } + return clusSizes; +} + +void PIDStudy::updateTimeDependentParams(ProcessingContext& pc) +{ + o2::base::GRPGeomHelper::instance().checkUpdates(pc); + static bool initOnceDone = false; + if (!initOnceDone) { // this param need to be queried only once + initOnceDone = true; + o2::its::GeometryTGeo* geom = o2::its::GeometryTGeo::Instance(); + geom->fillMatrixCache(o2::math_utils::bit2Mask(o2::math_utils::TransformType::T2L, o2::math_utils::TransformType::T2GRot, o2::math_utils::TransformType::T2G)); + } +} + +void PIDStudy::saveOutput() +{ + mDBGOut.reset(); + LOGP(info, "Stored histograms into {}", mOutName.c_str()); +} + +void PIDStudy::endOfStream(EndOfStreamContext& ec) +{ + // saveOutput(); +} + +void PIDStudy::finaliseCCDB(ConcreteDataMatcher& matcher, void* obj) +{ + if (o2::base::GRPGeomHelper::instance().finaliseCCDB(matcher, obj)) { + return; + } + // o2::base::GRPGeomHelper::instance().finaliseCCDB(matcher, obj); + if (matcher == ConcreteDataMatcher("ITS", "CLUSDICT", 0)) { + setClusterDictionary((const o2::itsmft::TopologyDictionary*)obj); + return; + } +} + +float PIDStudy::computeNSigma(PID pid, TrackTPC& tpcTrack, float resolution) +{ + float nSigma = -999; + float bb = mPIDresponse.getExpectedSignal(tpcTrack, pid); + if (tpcTrack.getdEdx().dEdxTotTPC > 0) { + nSigma = (tpcTrack.getdEdx().dEdxTotTPC - bb) / (resolution * bb); + } + return nSigma; +} + +DataProcessorSpec getPIDStudy(mask_t srcTracksMask, mask_t srcClustersMask, bool useMC, std::shared_ptr kineReader) +{ + std::vector outputs; + auto dataRequest = std::make_shared(); + dataRequest->requestTracks(srcTracksMask, useMC); + dataRequest->requestClusters(srcClustersMask, useMC); + + auto ggRequest = std::make_shared(false, // orbitResetTime + true, // GRPECS=true + false, // GRPLHCIF + false, // GRPMagField + false, // askMatLUT + o2::base::GRPGeomRequest::Aligned, // geometry + dataRequest->inputs, + true); + return DataProcessorSpec{ + "its-pid-study", + dataRequest->inputs, + outputs, + AlgorithmSpec{adaptFromTask(dataRequest, ggRequest, useMC, kineReader)}, + Options{}}; +} +} // namespace study +} // namespace its +} // namespace o2 diff --git a/Detectors/ITSMFT/ITS/postprocessing/workflow/standalone-postprocessing-workflow.cxx b/Detectors/ITSMFT/ITS/postprocessing/workflow/standalone-postprocessing-workflow.cxx index d760d2aeb075d..d7416f8415bcf 100644 --- a/Detectors/ITSMFT/ITS/postprocessing/workflow/standalone-postprocessing-workflow.cxx +++ b/Detectors/ITSMFT/ITS/postprocessing/workflow/standalone-postprocessing-workflow.cxx @@ -20,6 +20,7 @@ // Include studies hereafter #include "ITSStudies/ImpactParameter.h" #include "ITSStudies/AvgClusSize.h" +#include "ITSStudies/PIDStudy.h" #include "ITSStudies/TrackCheck.h" #include "Steer/MCKinematicsReader.h" @@ -42,6 +43,7 @@ void customize(std::vector& workflowOptions) {"disable-root-input", VariantType::Bool, false, {"disable root-files input reader"}}, {"disable-mc", VariantType::Bool, false, {"disable MC propagation even if available"}}, {"cluster-size-study", VariantType::Bool, false, {"Perform the average cluster size study"}}, + {"pid-study", VariantType::Bool, false, {"Perform the PID study"}}, {"track-study", VariantType::Bool, false, {"Perform the track study"}}, {"impact-parameter-study", VariantType::Bool, false, {"Perform the impact parameter study"}}, {"configKeyValues", VariantType::String, "", {"Semicolon separated key=value strings ..."}}}; @@ -54,7 +56,7 @@ void customize(std::vector& workflowOptions) WorkflowSpec defineDataProcessing(ConfigContext const& configcontext) { WorkflowSpec specs; - GID::mask_t allowedSourcesTrc = GID::getSourcesMask("ITS,ITS-TPC-TRD-TOF,ITS-TPC-TOF,ITS-TPC,ITS-TPC-TRD"); + GID::mask_t allowedSourcesTrc = GID::getSourcesMask("ITS,TPC,ITS-TPC-TRD-TOF,ITS-TPC-TOF,ITS-TPC,ITS-TPC-TRD"); GID::mask_t allowedSourcesClus = GID::getSourcesMask("ITS"); // Update the (declared) parameters if changed from the command line @@ -83,6 +85,10 @@ WorkflowSpec defineDataProcessing(ConfigContext const& configcontext) anyStudy = true; specs.emplace_back(o2::its::study::getAvgClusSizeStudy(srcTrc, srcCls, useMC, mcKinematicsReader)); } + if (configcontext.options().get("pid-study")) { + anyStudy = true; + specs.emplace_back(o2::its::study::getPIDStudy(srcTrc, srcCls, useMC, mcKinematicsReader)); + } if (configcontext.options().get("track-study")) { anyStudy = true; specs.emplace_back(o2::its::study::getTrackCheckStudy(GID::getSourcesMask("ITS"), GID::getSourcesMask("ITS"), useMC, mcKinematicsReader));