diff --git a/core/base/CbmTrackingDetectorInterfaceBase.h b/core/base/CbmTrackingDetectorInterfaceBase.h index 33cfb21e19676dbeec1777ea3b6600b832be07f5..857d51502968abdd7b129a534e7b880d03906997 100644 --- a/core/base/CbmTrackingDetectorInterfaceBase.h +++ b/core/base/CbmTrackingDetectorInterfaceBase.h @@ -15,6 +15,8 @@ #include "CbmHit.h" #include "CbmPixelHit.h" +#include "FairMCPoint.h" + #include <array> #include <string> #include <tuple> @@ -51,17 +53,16 @@ public: /// @return Local index of the tracking station virtual int GetTrackingStationIndex(const CbmHit* hit) const = 0; + /// @brief Gets a tracking station of a FairMCPoint + /// @param point A pointer to FairMCHit + /// @return Local index of the tracking station + virtual int GetTrackingStationIndex(const FairMCPoint* point) const = 0; + /// @brief Gets a tracking station by the address of element /// @param address Unique element address /// @return Local index of the tracking station virtual int GetTrackingStationIndex(int address) const = 0; - /// @brief Gets a tracking station index of MC point - /// @param zPos z-coordinate of hit/point position [cm] - /// - /// The function searches for the closest station in beam axis direction - int GetTrackingStationIndex(double zPos) const; - /// @brief Gets upper bound of a station along the X-axis /// @param stationId Tracking station ID in the setup (NOTE: must be in range [0..GetNstations()-1]) /// @return Size of station along the X-axis [cm] @@ -120,26 +121,4 @@ public: std::string ToString() const; }; -// ********************************************************** -// ** Template and inline function implementations ** -// ********************************************************** - -// --------------------------------------------------------------------------------------------------------------------- -// -inline int CbmTrackingDetectorInterfaceBase::GetTrackingStationIndex(double zPos) const -{ - double bestDist = 1.e+20; // arbitrary large number - int nStations = GetNtrackingStations(); - int iStSelected = -1; - for (int iSt = 0; iSt < nStations; ++iSt) { - auto dist = std::fabs(zPos - GetZref(iSt)); - if (dist < bestDist) { - bestDist = dist; - iStSelected = iSt; - } - } - return iStSelected; -} - - #endif // CbmTrackingDetectorInterfaceBase_h diff --git a/core/detectors/much/CbmMuchTrackingInterface.h b/core/detectors/much/CbmMuchTrackingInterface.h index 8989e4719c7fdf28b55201d5a2c0dead1e549517..8449b0b05f85306f0127b2a09384ddd0e6e70939 100644 --- a/core/detectors/much/CbmMuchTrackingInterface.h +++ b/core/detectors/much/CbmMuchTrackingInterface.h @@ -99,6 +99,14 @@ public: + CbmMuchGeoScheme::GetLayerIndex(address); } + /// @brief Gets a tracking station of a FairMCPoint + /// @param point A pointer to FairMCHit + /// @return Local index of the tracking station + int GetTrackingStationIndex(const FairMCPoint* point) const + { + return GetTrackingStationIndex(point->GetDetectorID()); + } + // TODO: SZh 30.08.2023: Provide automatic definintion of bounds /// @brief Gets upper bound of a station along the X-axis /// @param stationId Tracking station ID in the setup (NOTE: must be in range [0..GetNstations()-1]) diff --git a/core/detectors/mvd/CbmMvdTrackingInterface.h b/core/detectors/mvd/CbmMvdTrackingInterface.h index 5c75038dcf3cb2a223fd69d626bc03d0da394de2..17b397b97a2fe68c063c4d7b9d9f587595493d33 100644 --- a/core/detectors/mvd/CbmMvdTrackingInterface.h +++ b/core/detectors/mvd/CbmMvdTrackingInterface.h @@ -12,19 +12,20 @@ #ifndef CbmMvdTrackingInterface_h #define CbmMvdTrackingInterface_h 1 -#include "CbmHit.h" // for CbmHit -#include "CbmMvdDetectorId.h" // for CbmMvdDetectorId -#include "CbmMvdHit.h" // for CbmMvdHit -#include "CbmMvdStationPar.h" // for CbmMvdStationPar -#include "CbmTrackingDetectorInterfaceBase.h" // for CbmTrackingDetectorInt... +#include "CbmHit.h" +#include "CbmMvdDetectorId.h" +#include "CbmMvdHit.h" +#include "CbmMvdStationPar.h" +#include "CbmTrackingDetectorInterfaceBase.h" #include <FairTask.h> // for InitStatus, FairTask #include <Rtypes.h> // for ClassDef #include <TMath.h> // for Pi -#include <algorithm> // for min, max -#include <string> // for string +#include <algorithm> +#include <limits> +#include <string> class TBuffer; class TClass; @@ -93,6 +94,14 @@ public: return hitMvd->GetStationNr(); } + /// @brief Gets a tracking station of a FairMCPoint + /// @param point A pointer to FairMCHit + /// @return Local index of the tracking station + int GetTrackingStationIndex(const FairMCPoint* point) const + { + return GetTrackingStationIndex(point->GetDetectorID()); + } + /// @brief Gets a tracking station by the address of element (detectorID in terms of MVD) /// @param detectorId Unique element address (detectorID in terms of MVD) /// @return Local index of the tracking station diff --git a/core/detectors/sts/CbmStsTrackingInterface.h b/core/detectors/sts/CbmStsTrackingInterface.h index 941a597ece86a1f40986e80fbe7119cd7ca15ffb..6853da15d9332285a82cb4009feb8209b4f3ccfa 100644 --- a/core/detectors/sts/CbmStsTrackingInterface.h +++ b/core/detectors/sts/CbmStsTrackingInterface.h @@ -83,6 +83,14 @@ public: /// @return Local index of the tracking station int GetTrackingStationIndex(int address) const { return CbmStsSetup::Instance()->GetStationNumber(address); } + /// @brief Gets a tracking station of a FairMCPoint + /// @param point A pointer to FairMCHit + /// @return Local index of the tracking station + int GetTrackingStationIndex(const FairMCPoint* point) const + { + return GetTrackingStationIndex(point->GetDetectorID()); + } + /// @brief Gets upper edge of a station along the X-axis /// @param stationId Tracking station ID in the setup (NOTE: must be in range [0..GetNstations()-1]) /// @return Size of station along the X-axis [cm] diff --git a/core/detectors/tof/CbmTofTrackingInterface.h b/core/detectors/tof/CbmTofTrackingInterface.h index 1ae4ff16a373499432fde15b0687bc47237e61c2..638173a41a50a0e046a7f06a74f1504d6d92c6c1 100644 --- a/core/detectors/tof/CbmTofTrackingInterface.h +++ b/core/detectors/tof/CbmTofTrackingInterface.h @@ -79,6 +79,14 @@ public: return iSt; } + /// @brief Gets a tracking station of a FairMCPoint + /// @param point A pointer to FairMCHit + /// @return Local index of the tracking station + int GetTrackingStationIndex(const FairMCPoint* point) const + { + return GetTrackingStationIndex(point->GetDetectorID()); + } + // TODO: SZh. 10.09.2023: Provide automatic selection /// @brief Gets upper bound of a station along the X-axis /// @param stationId Tracking station ID in the setup (NOTE: must be in range [0..GetNstations()-1]) diff --git a/core/detectors/trd/CbmTrdTrackingInterface.h b/core/detectors/trd/CbmTrdTrackingInterface.h index c1215c303f40ee5a3a5805b521731e0bc4c9a31f..cdb4d23938a8af71172c2b7aec548d555ea6ac82 100644 --- a/core/detectors/trd/CbmTrdTrackingInterface.h +++ b/core/detectors/trd/CbmTrdTrackingInterface.h @@ -73,6 +73,14 @@ public: /// @return Local index of the tracking station int GetTrackingStationIndex(int address) const { return CbmTrdAddress::GetLayerId(address); } + /// @brief Gets a tracking station of a FairMCPoint + /// @param point A pointer to FairMCHit + /// @return Local index of the tracking station + int GetTrackingStationIndex(const FairMCPoint* point) const + { + return GetTrackingStationIndex(point->GetDetectorID()); + } + /// @brief Gets upper edge of a station along the X-axis /// @param stationId Tracking station ID in the setup (NOTE: must be in range [0..GetNstations()-1]) /// @return Size of station along the X-axis [cm] diff --git a/macro/mcbm/CMakeLists.txt b/macro/mcbm/CMakeLists.txt index 945dea38171292c02ade0f2b379741880932f7c1..3b5c13838932d67092ad74b6457a919def30cc05 100644 --- a/macro/mcbm/CMakeLists.txt +++ b/macro/mcbm/CMakeLists.txt @@ -140,6 +140,7 @@ ForEach(setup IN LISTS cbm_setup) EndForEach(setup IN LISTS cbm_setup) Install(FILES .rootrc mcbm_transport.C mcbm_digi.C mcbm_reco_event.C mcbm_match_check.C mcbm_hadron_analysis.C mcbm_qa.C + mcbm_transport_boxgen.C DESTINATION share/cbmroot/macro/mcbm ) Install(DIRECTORY modules DESTINATION share/cbmroot/macro/mcbm) diff --git a/macro/mcbm/mcbm_transport_boxgen.C b/macro/mcbm/mcbm_transport_boxgen.C new file mode 100644 index 0000000000000000000000000000000000000000..e867d1202303e5576ffdb2eb4b96434732c5059d --- /dev/null +++ b/macro/mcbm/mcbm_transport_boxgen.C @@ -0,0 +1,174 @@ +/* Copyright (C) 2023 GSI Helmholtzzentrum fuer Schwerionenforschung, Darmstadt + SPDX-License-Identifier: GPL-3.0-only + Authors: Sergei Zharko [committer] */ + +void SetTrack(CbmTransport*, Double_t, Int_t, Double_t, Double_t, Double_t); + +/// @brief Function to run a mCBM transport with a box generator +/// @param nEvents Number of events +/// @param setupName Name of the setup +/// @param output Prefix of the output name +/// @param overwrite Flag: if overwrite output +/// @param randomSeed Seed of the random generator +/// @param pdg PDG code for particles to generate +/// @param multiplicity Multiplicity of generated particles +// clang-format off +void mcbm_transport_boxgen(Int_t nEvents = 10, + // const char* setupName = "mcbm_beam_2022_08", + // const char* setupName = "mcbm_beam_2022_07", + // const char* setupName = "mcbm_beam_2022_06", + // const char* setupName = "mcbm_beam_2022_05", + // const char* setupName = "mcbm_beam_2022_04", + // const char* setupName = "mcbm_beam_2022_03", + // const char* setupName = "mcbm_beam_2022_02", + // const char* setupName = "mcbm_beam_2022_01", + // const char* setupName = "mcbm_beam_2022_06_16_gold", + const char* setupName = "mcbm_beam_2022_05_23_nickel", + // const char* setupName = "mcbm_beam_2022_03_28_uranium", + // const char* setupName = "mcbm_beam_2022_03_27_iron", + // const char* setupName = "mcbm_beam_2022_03_22_iron", + // const char* setupName = "mcbm_beam_2022_03_20_iron", + // const char* setupName = "mcbm_beam_2022_03_09_carbon", + // const char* setupName = "mcbm_beam_2021_07_surveyed", + // const char* setupName = "mcbm_beam_2021_04", + // const char* setupName = "mcbm_beam_2021_03", + // const char* setupName = "mcbm_beam_2020_03", + // const char* setupName = "mcbm_beam_2019_11", + // const char* setupName = "mcbm_beam_2019_03", + // const char* setupName = "sis18_mcbm_25deg_long", + const char* output = "data/test", + Bool_t overwrite = kTRUE, + int randomSeed = 1, + int pdg = 2212, + int multiplicity = 1 + ) +// clang-format on +{ + // --- Define the beam angle ---------------------------------------------- + Double_t beamRotY = 25.; + // ------------------------------------------------------------------------ + + // --- Define the target geometry ----------------------------------------- + // + // The target is not part of the setup, since one and the same setup can + // and will be used with different targets. + // The target is constructed as a tube in z direction with the specified + // diameter (in x and y) and thickness (in z). It will be placed at the + // specified position as daughter volume of the volume present there. It is + // in the responsibility of the user that no overlaps or extrusions are + // created by the placement of the target. + // + TString targetElement = "Gold"; + Double_t targetPosX = 0.; // target x position in global c.s. [cm] + Double_t targetPosY = 0.; // target y position in global c.s. [cm] + Double_t targetPosZ = 0.; // target z position in global c.s. [cm] + + // Double_t targetThickness = 0.1; // full thickness in cm + // Double_t targetDiameter = 0.5; // diameter in cm + // Double_t targetRotY = 25.; // target rotation angle around the y axis [deg] + + Double_t targetThickness = 0.025; // mCBM thin gold target 0.25 mm = 0.025 cm thickness + Double_t targetDiameter = 1.5; // mCBM target width 15 mm = 1.5 cm + // Double_t targetDiameter = 0.1; // set small target for window acceptance plots + Double_t targetRotY = beamRotY; // target rotation angle around the y axis [deg] + // ------------------------------------------------------------------------ + + // --- Logger settings ---------------------------------------------------- + FairLogger::GetLogger()->SetLogScreenLevel("INFO"); + FairLogger::GetLogger()->SetLogVerbosityLevel("VERYHIGH"); + // ------------------------------------------------------------------------ + + + // ----- Environment -------------------------------------------------- + TString myName = "mcbm_transport_boxgen"; // this macro's name for screen output + TString srcDir = gSystem->Getenv("VMCWORKDIR"); // top source directory + // ------------------------------------------------------------------------ + + + // ----- In- and output file names ------------------------------------ + TString dataset(output); + TString outFile = dataset + ".tra.root"; + TString parFile = dataset + ".par.root"; + TString geoFile = dataset + ".geo.root"; + std::cout << "Output file: " << outFile << '\n'; + std::cout << "Parameters file: " << parFile << '\n'; + std::cout << "Geometry file: " << geoFile << '\n'; + std::cout << '\n'; + // ------------------------------------------------------------------------ + + + // ----- Timer -------------------------------------------------------- + TStopwatch timer; + timer.Start(); + // ------------------------------------------------------------------------ + + + // ----- Transport run -------------------------------------------------- + CbmTransport run; + + // ----- Box generator of a single ----------------------- + FairBoxGenerator* boxGen = new FairBoxGenerator(pdg, multiplicity); + boxGen->SetPRange(0.1, 3.); + boxGen->SetPhiRange(0., 360.); + boxGen->SetThetaRange(0, 50.); + boxGen->SetCosTheta(); + boxGen->Init(); + run.AddInput(boxGen); + // ----- Box generator of a single proton per event ----------------------- + + run.SetOutFileName(outFile, overwrite); + run.SetParFileName(parFile); + run.SetGeoFileName(geoFile); + run.LoadSetup(setupName); + run.SetField(new CbmFieldConst()); + run.SetTarget(targetElement, targetThickness, targetDiameter, targetPosX, targetPosY, targetPosZ, + targetRotY * TMath::DegToRad()); + run.SetBeamPosition(0., 0., 0.1, 0.1); // Beam width 1 mm is assumed + run.SetBeamAngle(beamRotY * TMath::DegToRad(), 0.); + if (nEvents <= 10) // store only for small number of events + run.StoreTrajectories(); + run.SetRandomSeed(randomSeed); + run.Run(nEvents); + // ------------------------------------------------------------------------ + + + // ----- Finish ------------------------------------------------------- + timer.Stop(); + Double_t rtime = timer.RealTime(); + Double_t ctime = timer.CpuTime(); + std::cout << std::endl << std::endl; + std::cout << "Macro finished successfully." << std::endl; + std::cout << "Output file is " << outFile << std::endl; + std::cout << "Parameter file is " << parFile << std::endl; + std::cout << "Real time " << rtime << " s, CPU time " << ctime << "s" << std::endl << std::endl; + // ------------------------------------------------------------------------ + + + // ----- Resource monitoring ------------------------------------------ + FairSystemInfo sysInfo; + Float_t maxMemory = sysInfo.GetMaxMemory(); + std::cout << "<DartMeasurement name=\"MaxMemory\" type=\"numeric/double\">"; + std::cout << maxMemory; + std::cout << "</DartMeasurement>" << std::endl; + + Float_t cpuUsage = ctime / rtime; + std::cout << "<DartMeasurement name=\"CpuLoad\" type=\"numeric/double\">"; + std::cout << cpuUsage; + std::cout << "</DartMeasurement>" << std::endl; + + + std::cout << " Test passed" << std::endl; + std::cout << " All ok " << std::endl; + // ------------------------------------------------------------------------ +} + + +void SetTrack(CbmTransport* run, Double_t beamRotY, Int_t pdgid, Double_t x, Double_t y, Double_t z) +{ + TVector3 v; + v.SetXYZ(x, y, z); + v.RotateY(-beamRotY * acos(-1.) / 180.); + cout << "X " << v.X() << " Y " << v.Y() << " Z " << v.Z() << endl; + + run->AddInput(new FairParticleGenerator(pdgid, 1, v.X(), v.Y(), v.Z())); // single electron along beam axis +} diff --git a/macro/qa/qa_compare_ca.C b/macro/qa/qa_compare_ca.C index 4204ae75ff35d9ca3bf897884f478b1af75b674b..3bc59effd5b419a213df06a3f32c8ef16d909923 100644 --- a/macro/qa/qa_compare_ca.C +++ b/macro/qa/qa_compare_ca.C @@ -36,7 +36,7 @@ int qa_compare_ca( pQaChecker->SetFromYAML(configName); // Read file-object map //// ----- Run comparision routine - pQaChecker->Process("PB"); + pQaChecker->Process("P"); //// ----- Scan results bool res = pQaChecker->Scan(); // true - objects are the same, false - objects differ diff --git a/reco/L1/CMakeLists.txt b/reco/L1/CMakeLists.txt index 4f849847864423aae9a64785775450b71a7ca249..f13f88b3ac3afdde0a7c110cc9eeacbfc10a6960 100644 --- a/reco/L1/CMakeLists.txt +++ b/reco/L1/CMakeLists.txt @@ -69,6 +69,7 @@ set(SRCS L1Algo/utils/L1AlgoPulls.cxx L1Algo/utils/CaUvConverter.cxx + catools/CaToolsHitRecord.cxx catools/CaToolsMCData.cxx catools/CaToolsMCPoint.cxx catools/CaToolsMCTrack.cxx diff --git a/reco/L1/CbmCaMCModule.cxx b/reco/L1/CbmCaMCModule.cxx index 25632feb4c7b1a4b9dbdc21b3a330113cc4b2b15..44c364231074f6c49929aa4f619d7c2437f33f03 100644 --- a/reco/L1/CbmCaMCModule.cxx +++ b/reco/L1/CbmCaMCModule.cxx @@ -50,6 +50,13 @@ bool MCModule::InitRun() try { LOG(info) << "CA MC Module: initializing CA tracking Monte-Carlo module... "; + // Detector interfaces + if (fvbUseDet[L1DetectorID::kMvd]) { fvpDetInterface[L1DetectorID::kMvd] = CbmMvdTrackingInterface::Instance(); } + if (fvbUseDet[L1DetectorID::kSts]) { fvpDetInterface[L1DetectorID::kSts] = CbmStsTrackingInterface::Instance(); } + if (fvbUseDet[L1DetectorID::kMuch]) { fvpDetInterface[L1DetectorID::kMuch] = CbmMuchTrackingInterface::Instance(); } + if (fvbUseDet[L1DetectorID::kTrd]) { fvpDetInterface[L1DetectorID::kTrd] = CbmTrdTrackingInterface::Instance(); } + if (fvbUseDet[L1DetectorID::kTof]) { fvpDetInterface[L1DetectorID::kTof] = CbmTofTrackingInterface::Instance(); } + auto fairManager = FairRootManager::Instance(); assert(fairManager); @@ -89,6 +96,7 @@ try { InitMatchesBranch("TrdHitMatch", L1DetectorID::kTrd); InitMatchesBranch("TofHitMatch", L1DetectorID::kTof); + // Check initialization this->CheckInit(); @@ -158,6 +166,7 @@ void MCModule::ProcessEvent(CbmEvent*) {} // void MCModule::InitTrackInfo() { + // FIXME: Reconstructable criteria initialization should be verified! // ----- Initialize stations arrangement and hit indexes fpMCData->InitTrackInfo(*fpvQaHits); @@ -169,7 +178,7 @@ void MCModule::InitTrackInfo() isRec &= aTrk.GetP() > CbmL1Constants::MinRecoMom; // Cut on max number of points on station - isRec &= aTrk.GetMaxNofPointsOnStation() <= 4; + isRec &= aTrk.GetMaxNofPointsOnStation() <= 3; bool isAdd = isRec; // is track additional @@ -360,18 +369,19 @@ void MCModule::ReadMCPointsForDetector<L1DetectorID::kTof>() // Select station index for a point double zPos = pExtPoint->GetZ(); - float bestDist = 1000.; // arbitrary large length [cm] - int iStSelected = -1; // local geometry index of TOF station - - for (int iStLocGeo = 0; iStLocGeo < nTofStationsGeo; ++iStLocGeo) { - int iStActive = fpParameters->GetStationIndexActive(iStLocGeo, L1DetectorID::kTof); - if (iStActive < 0) { continue; } // station is not used in tracking - const L1Station& station = fpParameters->GetStation(iStActive); - if (fabs(zPos - station.fZ[0]) < bestDist) { - bestDist = fabs(zPos - station.fZ[0]); - iStSelected = iStLocGeo; - } - } + //float bestDist = 1000.; // arbitrary large length [cm] + //int iStSelected = -1; // local geometry index of TOF station + + //for (int iStLocGeo = 0; iStLocGeo < nTofStationsGeo; ++iStLocGeo) { + // int iStActive = fpParameters->GetStationIndexActive(iStLocGeo, L1DetectorID::kTof); + // if (iStActive < 0) { continue; } // station is not used in tracking + // const L1Station& station = fpParameters->GetStation(iStActive); + // if (fabs(zPos - station.fZ[0]) < bestDist) { + // bestDist = fabs(zPos - station.fZ[0]); + // iStSelected = iStLocGeo; + // } + //} + int iStSelected = CbmTofTrackingInterface::Instance()->GetTrackingStationIndex(pExtPoint->GetDetectorID()); int iTrack = fpMCData->FindInternalTrackIndex(pExtPoint->GetTrackID(), iEvent, iFile); assert(iTrack > -1); diff --git a/reco/L1/CbmCaMCModule.h b/reco/L1/CbmCaMCModule.h index d02e0339cf904511b493c7c81906d09cf7d96cdc..ba885d05fb0936446721e7fb0f05965842776f37 100644 --- a/reco/L1/CbmCaMCModule.h +++ b/reco/L1/CbmCaMCModule.h @@ -19,11 +19,16 @@ #include "CbmMCTrack.h" #include "CbmMatch.h" #include "CbmMuchPoint.h" +#include "CbmMuchTrackingInterface.h" #include "CbmMvdPoint.h" +#include "CbmMvdTrackingInterface.h" #include "CbmStsPoint.h" +#include "CbmStsTrackingInterface.h" #include "CbmTimeSlice.h" #include "CbmTofPoint.h" +#include "CbmTofTrackingInterface.h" #include "CbmTrdPoint.h" +#include "CbmTrdTrackingInterface.h" #include "TClonesArray.h" #include "TDatabasePDG.h" @@ -233,6 +238,8 @@ namespace cbm::ca CbmMCDataObject* fpMCEventHeader = nullptr; ///< MC event header CbmMCDataArray* fpMCTracks = nullptr; ///< MC tracks input + DetIdArr_t<CbmTrackingDetectorInterfaceBase*> fvpDetInterface = {{nullptr}}; ///< Tracking detector interface + DetIdArr_t<CbmMCDataArray*> fvpBrPoints = {{nullptr}}; ///< Array of points vs. detector DetIdArr_t<TClonesArray*> fvpBrHitMatches = {{nullptr}}; ///< Array of hit match branches vs. detector @@ -325,85 +332,52 @@ std::optional<::ca::tools::MCPoint> cbm::ca::MCModule::FillMCPoint(int iExtId, i TVector3 posOut; // Position at exist of station [cm] TVector3 momIn; // 3-momentum at entrance to station [GeV/c] TVector3 momOut; // 3-momentum at exit of station [GeV/c] - double time = undef::kD; // Time of MC point (after beginning of the event) [ns] - int iTmcExt = undef::kI32; // Track ID in the external container auto* pBrPoints = fvpBrPoints[DetID]; + PointTypes_t::at<DetID>* pExtPoint = dynamic_cast<PointTypes_t::at<DetID>*>(pBrPoints->Get(iFile, iEvent, iExtId)); + if (!pExtPoint) { + LOG(warn) << "CbmCaMCModule: " << kDetName[DetID] << " MC point with iExtId = " << iExtId << ", iEvent = " << iEvent + << ", iFile = " << iFile << " does not exist"; + return std::nullopt; + } if constexpr (L1DetectorID::kMvd == DetID) { - auto* pExtPoint = dynamic_cast<CbmMvdPoint*>(pBrPoints->Get(iFile, iEvent, iExtId)); - if (!pExtPoint) { - LOG(warn) << "CbmCaMCModule: MVD MC point with iExtId = " << iExtId << ", iEvent = " << iEvent - << ", iFile = " << iFile << " does not exist"; - return std::nullopt; - } pExtPoint->Position(posIn); pExtPoint->PositionOut(posOut); pExtPoint->Momentum(momIn); pExtPoint->MomentumOut(momOut); - time = pExtPoint->GetTime(); - iTmcExt = pExtPoint->GetTrackID(); } // STS else if constexpr (L1DetectorID::kSts == DetID) { - auto* pExtPoint = dynamic_cast<CbmStsPoint*>(pBrPoints->Get(iFile, iEvent, iExtId)); - if (!pExtPoint) { - LOG(warn) << "CbmCaMCModule: STS MC point with iExtId = " << iExtId << ", iEvent = " << iEvent - << ", iFile = " << iFile << " does not exist"; - return std::nullopt; - } pExtPoint->Position(posIn); pExtPoint->PositionOut(posOut); pExtPoint->Momentum(momIn); pExtPoint->MomentumOut(momOut); - time = pExtPoint->GetTime(); - iTmcExt = pExtPoint->GetTrackID(); } // MuCh else if constexpr (L1DetectorID::kMuch == DetID) { - auto* pExtPoint = dynamic_cast<CbmMuchPoint*>(pBrPoints->Get(iFile, iEvent, iExtId)); - if (!pExtPoint) { - LOG(warn) << "CbmCaMCModule: MuCh MC point with iExtId = " << iExtId << ", iEvent = " << iEvent - << ", iFile = " << iFile << " does not exist"; - return std::nullopt; - } pExtPoint->Position(posIn); pExtPoint->PositionOut(posOut); pExtPoint->Momentum(momIn); pExtPoint->Momentum(momOut); - time = pExtPoint->GetTime(); - iTmcExt = pExtPoint->GetTrackID(); } // TRD else if constexpr (L1DetectorID::kTrd == DetID) { - auto* pExtPoint = dynamic_cast<CbmTrdPoint*>(pBrPoints->Get(iFile, iEvent, iExtId)); - if (!pExtPoint) { - LOG(warn) << "CbmCaMCModule: TRD MC point with iExtId = " << iExtId << ", iEvent = " << iEvent - << ", iFile = " << iFile << " does not exist"; - return std::nullopt; - } pExtPoint->Position(posIn); pExtPoint->PositionOut(posOut); pExtPoint->Momentum(momIn); pExtPoint->MomentumOut(momOut); - time = pExtPoint->GetTime(); - iTmcExt = pExtPoint->GetTrackID(); } // TOF else if constexpr (L1DetectorID::kTof == DetID) { - auto* pExtPoint = dynamic_cast<CbmTofPoint*>(pBrPoints->Get(iFile, iEvent, iExtId)); - if (!pExtPoint) { - LOG(warn) << "CbmCaMCModule: TOF MC point with iExtId = " << iExtId << ", iEvent = " << iEvent - << ", iFile = " << iFile << " does not exist"; - return std::nullopt; - } pExtPoint->Position(posIn); pExtPoint->Position(posOut); pExtPoint->Momentum(momIn); pExtPoint->Momentum(momOut); - time = pExtPoint->GetTime(); - iTmcExt = pExtPoint->GetTrackID(); } + double time = pExtPoint->GetTime(); + int iTmcExt = pExtPoint->GetTrackID(); + if (iTmcExt < 0) { LOG(warn) << "CbmCaMCModule: For MC point with iExtId = " << iExtId << ", iEvent = " << iEvent << ", iFile = " << iFile << " MC track is undefined (has ID = " << iTmcExt << ')'; @@ -413,35 +387,12 @@ std::optional<::ca::tools::MCPoint> cbm::ca::MCModule::FillMCPoint(int iExtId, i TVector3 momMid = 0.5 * (momIn + momOut); // // ----- Get station index - int stationID = undef::kI32; // Index of station in the array of active tracking stations - int nStationsGeo = fpParameters->GetNstationsGeometry(DetID); - // MVD, STS TODO: Try to extend for MuCh and TRD - if constexpr (L1DetectorID::kMvd == DetID || L1DetectorID::kSts == DetID) { - // Determine active station global index - double bestDist = 1.e+20; - for (int iStLocGeo = 0; iStLocGeo < nStationsGeo; ++iStLocGeo) { - int iStActive = fpParameters->GetStationIndexActive(iStLocGeo, DetID); - if (iStActive < 0) { continue; } - const L1Station& station = fpParameters->GetStation(iStActive); - double dist = posIn.Z() - station.fZ[0]; - if (fabs(dist) < fabs(bestDist)) { - bestDist = dist; - stationID = iStActive; - } - } - } - // MuCh, TRD - else if constexpr (L1DetectorID::kMuch == DetID || L1DetectorID::kTrd == DetID) { - // Offset for MuCh - 2.5 cm, for TRD - 20. cm. TODO: Where did these values came from? - double offset = (L1DetectorID::kMuch == DetID) ? 2.5 : 20.; - for (int iStLocGeo = 0; iStLocGeo < nStationsGeo; ++iStLocGeo) { - int iStActive = fpParameters->GetStationIndexActive(iStLocGeo, DetID); - if (iStActive < 0) { continue; } - const L1Station& station = fpParameters->GetStation(iStActive); - if (posMid.Z() > station.fZ[0] - offset) { stationID = iStActive; } - } - } + int iStLoc = fvpDetInterface[DetID]->GetTrackingStationIndex(pExtPoint); + int stationID = fpParameters->GetStationIndexActive(iStLoc, DetID); + if constexpr (L1DetectorID::kTof != DetID) { // ???? + if (stationID == -1) { return std::nullopt; } // Skip points from inactive stations + } // Update point time with event time time += fpMCEventList->GetEventTime(iEvent, iFile); diff --git a/reco/L1/CbmCaTimeSliceReader.cxx b/reco/L1/CbmCaTimeSliceReader.cxx index b47900dccecb67d16432900453f7bfbe6ec49fbe..94d7ff9af8644e06f9fa61cc8029ba97dbae27d3 100644 --- a/reco/L1/CbmCaTimeSliceReader.cxx +++ b/reco/L1/CbmCaTimeSliceReader.cxx @@ -422,6 +422,7 @@ void TimeSliceReader::StoreHitRecord(const HitRecord& hitRecord) aHitQa.iStation = hitRecord.fStaId; aHitQa.x = hitRecord.fX; aHitQa.y = hitRecord.fY; + aHitQa.z = hitRecord.fZ; aHitQa.dx = sqrt(hitRecord.fDx2); aHitQa.dy = sqrt(hitRecord.fDy2); aHitQa.dxy = hitRecord.fDxy; diff --git a/reco/L1/CbmCaTimeSliceReader.h b/reco/L1/CbmCaTimeSliceReader.h index 966abdefefbb644850d529a47e13680662149f58..271f3c4286275b4cce0a65c91aeac69476099af1 100644 --- a/reco/L1/CbmCaTimeSliceReader.h +++ b/reco/L1/CbmCaTimeSliceReader.h @@ -299,8 +299,10 @@ int cbm::ca::TimeSliceReader::ReadHitsForDetector() } // Save hit to data structures - this->StoreHitRecord(hitRecord); - ++nHitsStored; + if (hitRecord.Accept()) { + this->StoreHitRecord(hitRecord); + ++nHitsStored; + } } // iH return nHitsStored; diff --git a/reco/L1/CbmL1.cxx b/reco/L1/CbmL1.cxx index bf0a7c1cdd5f357226fbb5d2b540c6cc263a6fae..3b57facba89b7ebff79aa389d65f2a1670e330ac 100644 --- a/reco/L1/CbmL1.cxx +++ b/reco/L1/CbmL1.cxx @@ -663,6 +663,11 @@ InitStatus CbmL1::Init() fMonitor.SetKeyName(EMonitorKey::kEvent, "N events"); fMonitor.SetKeyName(EMonitorKey::kRecoTrack, "N reco tracks"); fMonitor.SetKeyName(EMonitorKey::kRecoHit, "N hits"); + fMonitor.SetKeyName(EMonitorKey::kDiscardedHitMvd, "N discarded hits in MVD"); + fMonitor.SetKeyName(EMonitorKey::kDiscardedHitSts, "N discarded hits in STS"); + fMonitor.SetKeyName(EMonitorKey::kDiscardedHitMuch, "N discarded hits in MUCH"); + fMonitor.SetKeyName(EMonitorKey::kDiscardedHitTrd, "N discarded hits in TRD"); + fMonitor.SetKeyName(EMonitorKey::kDiscardedHitTof, "N discarded hits in TOF"); fMonitor.SetRatioKeys({EMonitorKey::kEvent, EMonitorKey::kRecoTrack}); fMonitor.Reset(); @@ -811,6 +816,44 @@ void CbmL1::Reconstruct(CbmEvent* event) // TrackMatch(); + + // ****** DEBUG: BEGIN + if constexpr (0) { + using std::setw; + { + LOG(info) << "---------- Reco track sample"; + int id = 0; + if (fvRecoTracks.size()) { LOG(info) << setw(4) << "No." << ' ' << fvRecoTracks[0].ToString(3, true); } + for (const auto& trk : fvRecoTracks) { + LOG(info) << setw(4) << (id++) << ' ' << trk.ToString(3); + } + } + { + LOG(info) << "---------- Reco hit sample"; + int id = 0; + if (fvHitDebugInfo.size()) { LOG(info) << setw(4) << "No." << ' ' << fvHitDebugInfo[0].ToString(3, true); } + for (const auto& h : fvHitDebugInfo) { + LOG(info) << setw(4) << (id++) << ' ' << h.ToString(3); + } + } + if (fPerformance) { + LOG(info) << "---------- MC tracks sample"; + int id = 0; + if (fvMCTracks.size()) { LOG(info) << setw(4) << "No." << ' ' << fvMCTracks[0].ToString(3, true); } + for (const auto& trk : fvMCTracks) { + if (trk.Hits.size() || trk.Points.size()) { LOG(info) << setw(4) << (id++) << ' ' << trk.ToString(3); } + } + } + if (fPerformance) { + LOG(info) << "---------- MC points sample"; + int id = 0; + if (fvMCPoints.size()) { LOG(info) << setw(4) << "No." << ' ' << fvMCPoints[0].ToString(3, true); } + for (const auto& p : fvMCPoints) { + LOG(info) << setw(4) << (id++) << ' ' << p.ToString(3); + } + } + } + // ****** DEBUG: END EfficienciesPerformance(); HistoPerformance(); TrackFitPerformance(); diff --git a/reco/L1/CbmL1.h b/reco/L1/CbmL1.h index ce0b0b4f4d611a8c353dd95db28dbeef8b6dbd57..b3e751dbe64a2ff9a03d9a13c7033b3bbd30d4e3 100644 --- a/reco/L1/CbmL1.h +++ b/reco/L1/CbmL1.h @@ -261,9 +261,14 @@ public: // Tracking monitor (prototype) enum class EMonitorKey { - kEvent, - kRecoTrack, - kRecoHit, + kEvent, ///< Number of processed events + kRecoTrack, ///< Number of reconstructed tracks + kRecoHit, ///< Number of reconstructed hits + kDiscardedHitMvd, ///< Number of discarded hits in MVD + kDiscardedHitSts, ///< Number of discarded hits in STS + kDiscardedHitMuch, ///< Number of discarded hits in MuCh + kDiscardedHitTrd, ///< Number of discarded hits in TRD + kDiscardedHitTof, ///< Number of discarded hits in TOF kEND }; diff --git a/reco/L1/CbmL1Constants.h b/reco/L1/CbmL1Constants.h index cb17176fdaa22eabe896e9944056b9f5bcfebe0e..da461cc131442b3d0dcdc0f1061f6104ad576ce2 100644 --- a/reco/L1/CbmL1Constants.h +++ b/reco/L1/CbmL1Constants.h @@ -14,4 +14,6 @@ namespace CbmL1Constants const int MinNStations = 4; // min number of stations on track to be reconstructable } // namespace CbmL1Constants +// FIXME: This values should be read from iterations! + #endif diff --git a/reco/L1/CbmL1Hit.h b/reco/L1/CbmL1Hit.h index 92b76f8770f3458d57cb2c7a111c84f007639396..d6090ad65b3696b16494f078e7a1af75bb22c0f2 100644 --- a/reco/L1/CbmL1Hit.h +++ b/reco/L1/CbmL1Hit.h @@ -79,6 +79,9 @@ public: /// @brief Gets y component of position [cm] double GetY() const { return y; } + /// @brief Gets z component of position [cm] + double GetZ() const { return z; } + /// @brief Sets index of matched MC point /// @param pointID Internal index of MC point void SetMCPointIndex(int pointID) { fPointID = pointID; } @@ -92,6 +95,7 @@ public: using std::setfill; using std::setw; std::stringstream msg; + msg.precision(4); if (header) { msg << setw(8) << setfill(' ') << "ext. ID" << ' '; msg << setw(8) << setfill(' ') << "int. ID" << ' '; @@ -100,6 +104,7 @@ public: msg << setw(8) << setfill(' ') << "MC p. ID" << ' '; msg << setw(14) << setfill(' ') << "x [cm]" << ' '; msg << setw(14) << setfill(' ') << "y [cm]" << ' '; + msg << setw(14) << setfill(' ') << "z [cm]" << ' '; msg << setw(14) << setfill(' ') << "time [ns]" << ' '; if (verbose > 0) { msg << setw(14) << setfill(' ') << "dx [cm]" << ' '; @@ -116,6 +121,7 @@ public: msg << setw(8) << setfill(' ') << GetMCPointIndex() << ' '; msg << setw(14) << setfill(' ') << x << ' '; msg << setw(14) << setfill(' ') << y << ' '; + msg << setw(14) << setfill(' ') << z << ' '; msg << setw(14) << setfill(' ') << time << ' '; if (verbose > 0) { msg << setw(14) << setfill(' ') << dx << ' '; @@ -134,6 +140,7 @@ public: int Det; ///< detector subsystem ID double x; ///< x coordinate of position [cm] double y; ///< y coordinate of position [cm] + double z; ///< z coordinate of position [cm] double time; ///< hit time [ns] double dx; ///< x coordinate error [cm] double dy; ///< y coordinate error [cm] diff --git a/reco/L1/CbmL1MCPoint.h b/reco/L1/CbmL1MCPoint.h index 3760a0a4e0fa87fee80287068e9059d3b8775a97..5055de0a1c0148519d9c82f4aa9bb8017eea6562 100644 --- a/reco/L1/CbmL1MCPoint.h +++ b/reco/L1/CbmL1MCPoint.h @@ -78,47 +78,62 @@ struct CbmL1MCPoint { if (verbose < 1) { return std::string(); } std::stringstream msg; + msg.precision(4); if (printHeader) { if (verbose > 0) { - msg << std::setw(10) << std::setfill(' ') << "track ID" << ' '; - msg << std::setw(10) << std::setfill(' ') << "mother ID" << '|'; - msg << std::setw(10) << std::setfill(' ') << "station ID" << '|'; - msg << std::setw(10) << std::setfill(' ') << "PDG" << ' '; - msg << std::setw(10) << std::setfill(' ') << "m [GeV/c2]" << ' '; - msg << std::setw(10) << std::setfill(' ') << "q [e]" << '|'; - msg << std::setw(14) << std::setfill(' ') << "t [ns]" << ' '; - msg << std::setw(14) << std::setfill(' ') << "x [cm]" << ' '; - msg << std::setw(14) << std::setfill(' ') << "y [cm]" << ' '; - msg << std::setw(14) << std::setfill(' ') << "z [cm]" << '|'; + msg << std::setw(10) << "track ID" << ' '; + msg << std::setw(10) << "mother ID" << '|'; + msg << std::setw(10) << "station ID" << '|'; + msg << std::setw(10) << "PDG" << ' '; + if (verbose > 3) { + msg << std::setw(10) << "m [GeV/c2]" << ' '; + msg << std::setw(10) << "q [e]" << '|'; + } + msg << std::setw(14) << "t [ns]" << ' '; + msg << std::setw(14) << "x [cm]" << ' '; + msg << std::setw(14) << "y [cm]" << ' '; + msg << std::setw(14) << "z [cm]" << '|'; if (verbose > 1) { - msg << std::setw(14) << std::setfill(' ') << "zIn [cm]" << ' '; - msg << std::setw(14) << std::setfill(' ') << "zOut [cm]" << '|'; - msg << std::setw(14) << std::setfill(' ') << "p [GeV/c]" << '|'; - msg << std::setw(10) << std::setfill(' ') << "point ID" << ' '; - msg << std::setw(10) << std::setfill(' ') << "event ID" << ' '; - msg << std::setw(10) << std::setfill(' ') << "file ID" << ' '; + msg << std::setw(14) << "zIn [cm]" << ' '; + msg << std::setw(14) << "zOut [cm]" << '|'; + msg << std::setw(14) << "p [GeV/c]" << '|'; + msg << std::setw(10) << "point ID" << ' '; + if (verbose > 3) { + msg << std::setw(10) << "event ID" << ' '; + msg << std::setw(10) << "file ID" << ' '; + } + msg << std::setw(16) << "hit indices" << ' '; } } } else { if (verbose > 0) { - msg << std::setw(10) << std::setfill(' ') << ID << ' '; - msg << std::setw(10) << std::setfill(' ') << mother_ID << '|'; - msg << std::setw(10) << std::setfill(' ') << iStation << '|'; - msg << std::setw(10) << std::setfill(' ') << pdg << ' '; - msg << std::setw(10) << std::setfill(' ') << mass << ' '; - msg << std::setw(10) << std::setfill(' ') << q << '|'; - msg << std::setw(14) << std::setfill(' ') << time << ' '; - msg << std::setw(14) << std::setfill(' ') << x << ' '; - msg << std::setw(14) << std::setfill(' ') << y << ' '; - msg << std::setw(14) << std::setfill(' ') << z << '|'; + msg << std::setw(10) << ID << ' '; + msg << std::setw(10) << mother_ID << '|'; + msg << std::setw(10) << iStation << '|'; + msg << std::setw(10) << pdg << ' '; + if (verbose > 3) { + msg << std::setw(10) << mass << ' '; + msg << std::setw(10) << q << '|'; + } + msg << std::setw(14) << time << ' '; + msg << std::setw(14) << x << ' '; + msg << std::setw(14) << y << ' '; + msg << std::setw(14) << z << '|'; if (verbose > 1) { - msg << std::setw(14) << std::setfill(' ') << zIn << ' '; - msg << std::setw(14) << std::setfill(' ') << zOut << '|'; - msg << std::setw(14) << std::setfill(' ') << p << '|'; - msg << std::setw(10) << std::setfill(' ') << pointId << ' '; - msg << std::setw(10) << std::setfill(' ') << event << ' '; - msg << std::setw(10) << std::setfill(' ') << file << ' '; + msg << std::setw(14) << zIn << ' '; + msg << std::setw(14) << zOut << '|'; + msg << std::setw(14) << p << '|'; + msg << std::setw(10) << pointId << ' '; + if (verbose > 3) { + msg << std::setw(10) << event << ' '; + msg << std::setw(10) << file << ' '; + } + std::stringstream msgHits; + for (int iH : hitIds) { + msgHits << iH << ' '; + } + msg << std::setw(16) << msgHits.str() << ' '; } } } diff --git a/reco/L1/CbmL1ReadEvent.cxx b/reco/L1/CbmL1ReadEvent.cxx index d8248eb8440d86d2452c542c4246aef128ab056a..df15dbfcc10116f5405f83b5bd69a02194bbec2d 100644 --- a/reco/L1/CbmL1ReadEvent.cxx +++ b/reco/L1/CbmL1ReadEvent.cxx @@ -69,7 +69,7 @@ struct TmpHit { int iStripF; ///< index of front strip int iStripB; ///< index of back strip int iStation; ///< index of station - int64_t fDataStream; ///< global index of detector module + int64_t fDataStream; ///< global index of detector module (4 left bits -- station number, other - address) int ExtIndex; ///< index of hit in the external TClonesArray array (NOTE: negative for MVD) double x; ///< position of hit along x axis [cm] double y; ///< position of hit along y axis [cm] @@ -85,6 +85,44 @@ struct TmpHit { double rangeT; ///< hit range in T [ns] int Det; + + static constexpr bool kVerboseAccept = true; + /// @brief Tests quality of the hit (eg., if one of its quantity is nan) + /// @return true Hit is passed and send to the CaCore + /// @return false Hit is discarded due to corrupted quantity values + bool IfAccept() const + { + if constexpr (kVerboseAccept) { + std::stringstream msg; + if (std::isnan(x) || std::isinf(x)) { msg << ", x = " << x; } + if (std::isnan(y) || std::isinf(y)) { msg << ", y = " << y; } + if (std::isnan(z) || std::isinf(z)) { msg << ", z = " << z; } + if (std::isnan(time) || std::isinf(time)) { msg << ", t = " << time; } + if (std::isnan(dx2) || std::isinf(dx2)) { msg << ", dx2 = " << dx2; } + if (std::isnan(dy2) || std::isinf(dy2)) { msg << ", dy2 = " << dy2; } + if (std::isnan(dxy) || std::isinf(dxy)) { msg << ", dxy = " << dxy; } + if (std::isnan(dt2) || std::isinf(dt2)) { msg << ", dt2 = " << dt2; } + const auto& sMsg = msg.str(); + if (sMsg.size()) { + LOG(warn) << "CbmL1: Discarding hit " << ExtIndex << ": det = " << Det + << ", addr = " << static_cast<int32_t>(fDataStream) << ", " << sMsg; + return false; + } + } + else { + bool res = true; + res = res && !(std::isnan(x) || std::isinf(x)); + res = res && !(std::isnan(y) || std::isinf(y)); + res = res && !(std::isnan(z) || std::isinf(z)); + res = res && !(std::isnan(time) || std::isinf(time)); + res = res && !(std::isnan(dx2) || std::isinf(dx2)); + res = res && !(std::isnan(dy2) || std::isinf(dy2)); + res = res && !(std::isnan(dt2) || std::isinf(dt2)); + res = res && !(std::isnan(dxy) || std::isinf(dxy)); + return res; + } + return true; + } }; @@ -187,22 +225,10 @@ void CbmL1::ReadEvent(CbmEvent* event) for (Int_t iMC = 0; iMC < fNpointsMvdInEvent; iMC++) { CbmL1MCPoint MC; if (!ReadMCPoint(&MC, iMC, iFile, iEvent, 0)) { - MC.iStation = -1; - const L1Station* sta = fpAlgo->GetParameters()->GetStations().begin(); - double bestDist = 1.e20; - for (Int_t iSt = 0; iSt < fNMvdStationsGeom; iSt++) { - // use z_in since z_out is sometimes very wrong - // due to a problem in transport - int iStActive = fpAlgo->GetParameters()->GetStationIndexActive(iSt, L1DetectorID::kMvd); - if (iStActive == -1) { continue; } - double d = (MC.zIn - sta[iStActive].fZ[0]); - if (fabs(d) < fabs(bestDist)) { - bestDist = d; - MC.iStation = iStActive; - } - } - assert(MC.iStation >= 0); - if (fabs(maxDeviation) < fabs(bestDist)) { maxDeviation = bestDist; } + CbmMvdPoint* pPoint = static_cast<CbmMvdPoint*>(fpMvdPoints->Get(iFile, iEvent, iMC)); + int iStLoc = CbmMvdTrackingInterface::Instance()->GetTrackingStationIndex(pPoint); + MC.iStation = fpAlgo->GetParameters()->GetStationIndexActive(iStLoc, L1DetectorID::kMvd); + if (MC.iStation < 0) { continue; } // Reject MC points from inactive stations auto itTrack = fmMCTracksLinksMap.find(CbmL1LinkKey(MC.ID, iEvent, iFile)); assert(itTrack != fmMCTracksLinksMap.cend()); MC.ID = itTrack->second; @@ -225,22 +251,10 @@ void CbmL1::ReadEvent(CbmEvent* event) for (Int_t iMC = 0; iMC < nMC; iMC++) { CbmL1MCPoint MC; if (!ReadMCPoint(&MC, iMC, iFile, iEvent, 1)) { - MC.iStation = -1; - const L1Station* sta = fpAlgo->GetParameters()->GetStations().begin(); - double bestDist = 1.e20; - for (Int_t iSt = 0; iSt < fNStsStationsGeom; iSt++) { - int iStActive = fpAlgo->GetParameters()->GetStationIndexActive(iSt, L1DetectorID::kSts); - if (iStActive == -1) { continue; } - // use z_in since z_out is sometimes very wrong - // due to a problem in transport - double d = (MC.zIn - sta[iStActive].fZ[0]); - if (fabs(d) < fabs(bestDist)) { - bestDist = d; - MC.iStation = iStActive; - } - } - assert(MC.iStation >= 0); - if (fabs(maxDeviation) < fabs(bestDist)) { maxDeviation = bestDist; } + auto* pPoint = static_cast<CbmStsPoint*>(fpStsPoints->Get(iFile, iEvent, iMC)); + int iStLoc = CbmStsTrackingInterface::Instance()->GetTrackingStationIndex(pPoint->GetDetectorID()); + MC.iStation = fpAlgo->GetParameters()->GetStationIndexActive(iStLoc, L1DetectorID::kSts); + if (MC.iStation < 0) { continue; } // Reject MC points from inactive stations auto itTrack = fmMCTracksLinksMap.find(CbmL1LinkKey(MC.ID, iEvent, iFile)); assert(itTrack != fmMCTracksLinksMap.cend()); MC.ID = itTrack->second; @@ -279,13 +293,9 @@ void CbmL1::ReadEvent(CbmEvent* event) for (Int_t iMC = 0; iMC < fpTrdPoints->Size(iFile, iEvent); iMC++) { CbmL1MCPoint MC; if (!ReadMCPoint(&MC, iMC, iFile, iEvent, 3)) { - MC.iStation = -1; - const L1Station* sta = fpAlgo->GetParameters()->GetStations().begin(); - for (Int_t iSt = 0; iSt < fNTrdStationsGeom; iSt++) { - int iStActive = fpAlgo->GetParameters()->GetStationIndexActive(iSt, L1DetectorID::kTrd); - if (iStActive < 0) { continue; } - if (MC.z > sta[iStActive].fZ[0] - 20.0) { MC.iStation = iStActive; } - } + auto* pPoint = static_cast<CbmTrdPoint*>(fpTrdPoints->Get(iFile, iEvent, iMC)); + int iStLoc = CbmTrdTrackingInterface::Instance()->GetTrackingStationIndex(pPoint->GetDetectorID()); + MC.iStation = fpAlgo->GetParameters()->GetStationIndexActive(iStLoc, L1DetectorID::kSts); if (MC.iStation < 0) { continue; } // Reject MC points from inactive stations auto itTrack = fmMCTracksLinksMap.find(CbmL1LinkKey(MC.ID, iEvent, iFile)); assert(itTrack != fmMCTracksLinksMap.cend()); @@ -342,30 +352,20 @@ void CbmL1::ReadEvent(CbmEvent* event) MC.iStation = -1; const L1Station* sta = fpAlgo->GetParameters()->GetStations().begin(); - float dist = 1000; - int iSta = -1; - int iStaGlob = -1; - for (int iSt = 0; iSt < fNTofStationsGeom; iSt++) { - int iStActive = fpAlgo->GetParameters()->GetStationIndexActive(iSt, L1DetectorID::kTof); - if (iStActive == -1) { continue; } - if (fabs(MC.z - sta[iStActive].fZ[0]) < dist) { - dist = fabs(MC.z - sta[iStActive].fZ[0]); - iSta = iSt; - iStaGlob = iStActive; - } - } - - MC.iStation = fpAlgo->GetParameters()->GetStationIndexActive(iSta, L1DetectorID::kTof); - assert(MC.iStation >= 0); + auto* pPoint = static_cast<CbmTofPoint*>(fpTofPoints->Get(iFile, iEvent, iMC)); + int iStLoc = CbmTofTrackingInterface::Instance()->GetTrackingStationIndex(pPoint->GetDetectorID()); + MC.iStation = fpAlgo->GetParameters()->GetStationIndexActive(iStLoc, L1DetectorID::kTof); + if (MC.iStation < 0) { continue; } // In case of inactive station auto itTrack = fmMCTracksLinksMap.find(CbmL1LinkKey(MC.ID, iEvent, iFile)); assert(itTrack != fmMCTracksLinksMap.cend()); int iTrack = itTrack->second; - - if (iSta >= 0) { - if (fabs(sta[iStaGlob].fZ[0] - MC.z) < vTofPointToTrackdZ[iSta][iTrack]) { - vTofPointToTrack[iSta][iTrack] = iMC; - vTofPointToTrackdZ[iSta][iTrack] = fabs(sta[iStaGlob].fZ[0] - MC.z); + if (iStLoc >= 0) { + // Select the closest point to the station + // NOTE: Probably, there is no sence to select the closest point to the station center + if (fabs(sta[MC.iStation].fZ[0] - MC.z) < vTofPointToTrackdZ[iStLoc][iTrack]) { + vTofPointToTrack[iStLoc][iTrack] = iMC; + vTofPointToTrackdZ[iStLoc][iTrack] = fabs(sta[MC.iStation].fZ[0] - MC.z); } } } @@ -477,10 +477,13 @@ void CbmL1::ReadEvent(CbmEvent* event) th.iMC = fPerformance ? MatchHitWithMc<L1DetectorID::kMvd>(hitIndex) : -1; th.fDataStream = (static_cast<int64_t>(th.Det) << 60) | h->GetAddress(); //if( th.iMC >=0 ) // DEBUG !!!! - { + if (th.IfAccept()) { tmpHits.push_back(th); nMvdHits++; } + else { + fMonitor.Increment(EMonitorKey::kDiscardedHitMvd); + } } // for j } // if fpMvdHits @@ -541,9 +544,13 @@ void CbmL1::ReadEvent(CbmEvent* event) th.iMC = fPerformance ? MatchHitWithMc<L1DetectorID::kSts>(hitIndex) : -1; th.fDataStream = (static_cast<int64_t>(th.Det) << 60) | h->GetAddress(); - tmpHits.push_back(th); - nStsHits++; - + if (th.IfAccept()) { + tmpHits.push_back(th); + nStsHits++; + } + else { + fMonitor.Increment(EMonitorKey::kDiscardedHitSts); + } } // for j } // if fpStsHits @@ -592,8 +599,13 @@ void CbmL1::ReadEvent(CbmEvent* event) } th.iMC = fPerformance ? MatchHitWithMc<L1DetectorID::kMuch>(th.ExtIndex) : -1; th.fDataStream = (static_cast<int64_t>(th.Det) << 60) | h->GetAddress(); - tmpHits.push_back(th); - nMuchHits++; + if (th.IfAccept()) { + tmpHits.push_back(th); + nMuchHits++; + } + else { + fMonitor.Increment(EMonitorKey::kDiscardedHitMuch); + } } // for j } // if listMuchHits @@ -660,8 +672,13 @@ void CbmL1::ReadEvent(CbmEvent* event) th.iMC = fPerformance ? MatchHitWithMc<L1DetectorID::kTrd>(hitIndex) : -1; th.fDataStream = (static_cast<int64_t>(th.Det) << 60) | h->GetAddress(); - tmpHits.push_back(th); - nTrdHits++; + if (th.IfAccept()) { + tmpHits.push_back(th); + nTrdHits++; + } + else { + fMonitor.Increment(EMonitorKey::kDiscardedHitTrd); + } } // for fpTrdHits } // read TRD hits @@ -723,9 +740,13 @@ void CbmL1::ReadEvent(CbmEvent* event) th.iMC = fPerformance ? MatchHitWithMc<L1DetectorID::kTof>(hitIndex) : -1; th.fDataStream = (static_cast<int64_t>(th.Det) << 60) | h->GetAddress(); - tmpHits.push_back(th); - nTofHits++; - + if (th.IfAccept()) { + tmpHits.push_back(th); + nTofHits++; + } + else { + fMonitor.Increment(EMonitorKey::kDiscardedHitTof); + } } // for j } // if listTofHits @@ -763,6 +784,7 @@ void CbmL1::ReadEvent(CbmEvent* event) s.iStation = th.iStation; s.x = th.x; s.y = th.y; + s.z = th.z; s.dx = sqrt(th.dx2); s.dy = sqrt(th.dy2); s.dxy = th.dxy; diff --git a/reco/L1/CbmL1Track.cxx b/reco/L1/CbmL1Track.cxx index 271fd8649beebf522a7343eb66768f3cfd711488..d7aec0a2f65f2d179bec9cc0e5b03a85eeec13dc 100644 --- a/reco/L1/CbmL1Track.cxx +++ b/reco/L1/CbmL1Track.cxx @@ -36,8 +36,8 @@ std::string CbmL1Track::ToString(int verbose, bool header) const msg << setw(12) << setfill(' ') << GetTx() << ' '; msg << setw(8) << setfill(' ') << GetNofHits() << ' '; msg << setw(8) << setfill(' ') << GetNofMCTracks() << ' '; - msg << setw(12) << setfill(' ') << GetMatchedMCTrackIndex() << ' '; msg << setw(12) << setfill(' ') << (mcTracks.size() ? mcTracks[0]->ID : -1) << ' '; + msg << setw(12) << setfill(' ') << GetMatchedMCTrackIndex() << ' '; msg << setw(8) << setfill(' ') << IsGhost() << ' '; msg << setw(8) << setfill(' ') << GetMaxPurity() << ' '; msg << '\n'; diff --git a/reco/L1/catools/CaToolsHitRecord.cxx b/reco/L1/catools/CaToolsHitRecord.cxx new file mode 100644 index 0000000000000000000000000000000000000000..2286b1273005a65672b19fd79344ee2d63dad3a6 --- /dev/null +++ b/reco/L1/catools/CaToolsHitRecord.cxx @@ -0,0 +1,54 @@ +/* Copyright (C) 2023 GSI Helmholtzzentrum fuer Schwerionenforschung, Darmstadt + SPDX-License-Identifier: GPL-3.0-only + Authors: Sergei Zharko [committer] */ + +/// \file CbmCaHitRecord.h +/// \brief An implementation for cbm::ca::HitRecord structure +/// \since 17.09.2023 +/// \author S.Zharko <s.zharko@gsi.de> + +#include "CaToolsHitRecord.h" + +#include "Logger.h" + +#include <sstream> + +#include <cmath> + +using ca::tools::HitRecord; + +// --------------------------------------------------------------------------------------------------------------------- +// +bool HitRecord::Accept() const +{ + if constexpr (kVerboseAccept) { + std::stringstream msg; + if (std::isnan(fX) || std::isinf(fX)) { msg << ", x = " << fX; } + if (std::isnan(fY) || std::isinf(fY)) { msg << ", y = " << fY; } + if (std::isnan(fZ) || std::isinf(fZ)) { msg << ", z = " << fZ; } + if (std::isnan(fT) || std::isinf(fT)) { msg << ", t = " << fT; } + if (std::isnan(fDx2) || std::isinf(fDx2)) { msg << ", dx2 = " << fDx2; } + if (std::isnan(fDy2) || std::isinf(fDy2)) { msg << ", dy2 = " << fDy2; } + if (std::isnan(fDxy) || std::isinf(fDxy)) { msg << ", dxy = " << fDxy; } + if (std::isnan(fDt2) || std::isinf(fDt2)) { msg << ", dt2 = " << fDt2; } + const auto& sMsg = msg.str(); + if (sMsg.size()) { + LOG(warn) << "HitRecord: Discarding hit " << fExtId << ": det = " << fDet + << ", addr = " << static_cast<int32_t>(fDataStream) << ", " << sMsg; + return false; + } + } + else { + bool res = true; + res = res && !(std::isnan(fX) || std::isinf(fX)); + res = res && !(std::isnan(fY) || std::isinf(fY)); + res = res && !(std::isnan(fZ) || std::isinf(fZ)); + res = res && !(std::isnan(fT) || std::isinf(fT)); + res = res && !(std::isnan(fDx2) || std::isinf(fDx2)); + res = res && !(std::isnan(fDy2) || std::isinf(fDy2)); + res = res && !(std::isnan(fDt2) || std::isinf(fDt2)); + res = res && !(std::isnan(fDxy) || std::isinf(fDxy)); + return res; + } + return true; +} diff --git a/reco/L1/catools/CaToolsHitRecord.h b/reco/L1/catools/CaToolsHitRecord.h index c5d91fd958deb25cc7e7aa5f2a8444e067054c97..98d99a982a4609b5f8c1c3808492294654a44aba 100644 --- a/reco/L1/catools/CaToolsHitRecord.h +++ b/reco/L1/catools/CaToolsHitRecord.h @@ -38,6 +38,12 @@ namespace ca::tools int fStripF = -2; ///< index of front strip int fStripB = -2; ///< index of back strip int fDet = -2; ///< detector ID + + /// @brief Tests hit quality (for example, if all the quantities are not nan) + /// @return true Hit is accepted + /// @return false Hit is discarded + static constexpr bool kVerboseAccept = true; + bool Accept() const; }; } // namespace ca::tools diff --git a/reco/L1/catools/CaToolsMCPoint.cxx b/reco/L1/catools/CaToolsMCPoint.cxx index 3df6aaea5d13ed8cbd7ce203cd3ff577ac7272f6..fc3cc474c44bab32a9e3ef50208dee4f8d644691 100644 --- a/reco/L1/catools/CaToolsMCPoint.cxx +++ b/reco/L1/catools/CaToolsMCPoint.cxx @@ -22,49 +22,64 @@ std::string MCPoint::ToString(int verbose, bool printHeader) const if (verbose < 1) { return std::string(); } std::stringstream msg; + msg.precision(4); if (printHeader) { if (verbose > 0) { - msg << std::setw(10) << std::setfill(' ') << "track ID" << ' '; - msg << std::setw(10) << std::setfill(' ') << "mother ID" << '|'; - msg << std::setw(10) << std::setfill(' ') << "station ID" << '|'; - msg << std::setw(10) << std::setfill(' ') << "PDG" << ' '; - msg << std::setw(10) << std::setfill(' ') << "m [GeV/c2]" << ' '; - msg << std::setw(10) << std::setfill(' ') << "q [e]" << '|'; - msg << std::setw(14) << std::setfill(' ') << "t [ns]" << ' '; - msg << std::setw(14) << std::setfill(' ') << "x [cm]" << ' '; - msg << std::setw(14) << std::setfill(' ') << "y [cm]" << ' '; - msg << std::setw(14) << std::setfill(' ') << "z [cm]" << '|'; + msg << std::setw(10) << "track ID" << ' '; + msg << std::setw(10) << "mother ID" << '|'; + msg << std::setw(10) << "station ID" << '|'; + msg << std::setw(10) << "PDG" << ' '; + if (verbose > 3) { + msg << std::setw(10) << "m [GeV/c2]" << ' '; + msg << std::setw(10) << "q [e]" << '|'; + } + msg << std::setw(14) << "t [ns]" << ' '; + msg << std::setw(14) << "x [cm]" << ' '; + msg << std::setw(14) << "y [cm]" << ' '; + msg << std::setw(14) << "z [cm]" << '|'; if (verbose > 1) { - msg << std::setw(14) << std::setfill(' ') << "zIn [cm]" << ' '; - msg << std::setw(14) << std::setfill(' ') << "zOut [cm]" << '|'; - msg << std::setw(14) << std::setfill(' ') << "p [GeV/c]" << '|'; - msg << std::setw(10) << std::setfill(' ') << "point ID" << ' '; - msg << std::setw(10) << std::setfill(' ') << "point ID (ext)" << ' '; - msg << std::setw(10) << std::setfill(' ') << "event ID" << ' '; - msg << std::setw(10) << std::setfill(' ') << "file ID" << ' '; + msg << std::setw(14) << "zIn [cm]" << ' '; + msg << std::setw(14) << "zOut [cm]" << '|'; + msg << std::setw(14) << "p [GeV/c]" << '|'; + msg << std::setw(10) << "point ID" << ' '; + msg << std::setw(10) << "point ID (ext)" << ' '; + if (verbose > 3) { + msg << std::setw(10) << "event ID" << ' '; + msg << std::setw(10) << "file ID" << ' '; + } + msg << std::setw(16) << "hit indices" << ' '; } } } else { if (verbose > 0) { - msg << std::setw(10) << std::setfill(' ') << fTrackId << ' '; - msg << std::setw(10) << std::setfill(' ') << fMotherId << '|'; - msg << std::setw(10) << std::setfill(' ') << fStationId << '|'; - msg << std::setw(10) << std::setfill(' ') << fPdgCode << ' '; - msg << std::setw(10) << std::setfill(' ') << fMass << ' '; - msg << std::setw(10) << std::setfill(' ') << fCharge << '|'; - msg << std::setw(14) << std::setfill(' ') << fTime << ' '; - msg << std::setw(14) << std::setfill(' ') << fPos[0] << ' '; - msg << std::setw(14) << std::setfill(' ') << fPos[1] << ' '; - msg << std::setw(14) << std::setfill(' ') << fPos[2] << '|'; + msg << std::setw(10) << fTrackId << ' '; + msg << std::setw(10) << fMotherId << '|'; + msg << std::setw(10) << fStationId << '|'; + msg << std::setw(10) << fPdgCode << ' '; + if (verbose > 3) { + msg << std::setw(10) << fMass << ' '; + msg << std::setw(10) << fCharge << '|'; + } + msg << std::setw(14) << fTime << ' '; + msg << std::setw(14) << fPos[0] << ' '; + msg << std::setw(14) << fPos[1] << ' '; + msg << std::setw(14) << fPos[2] << '|'; if (verbose > 1) { - msg << std::setw(14) << std::setfill(' ') << fPosIn[2] << ' '; - msg << std::setw(14) << std::setfill(' ') << fPosOut[2] << '|'; - msg << std::setw(14) << std::setfill(' ') << this->GetP() << '|'; - msg << std::setw(10) << std::setfill(' ') << fId << ' '; - msg << std::setw(10) << std::setfill(' ') << fLinkKey.fIndex << ' '; - msg << std::setw(10) << std::setfill(' ') << fLinkKey.fEvent << ' '; - msg << std::setw(10) << std::setfill(' ') << fLinkKey.fFile << ' '; + msg << std::setw(14) << fPosIn[2] << ' '; + msg << std::setw(14) << fPosOut[2] << '|'; + msg << std::setw(14) << this->GetP() << '|'; + msg << std::setw(10) << fId << ' '; + msg << std::setw(10) << fLinkKey.fIndex << ' '; + if (verbose > 3) { + msg << std::setw(10) << fLinkKey.fEvent << ' '; + msg << std::setw(10) << fLinkKey.fFile << ' '; + } + std::stringstream msgHits; + for (int iH : fvHitIndexes) { + msgHits << iH << ' '; + } + msg << std::setw(16) << msgHits.str() << ' '; } } } diff --git a/reco/L1/qa/CbmCaInputQaBase.cxx b/reco/L1/qa/CbmCaInputQaBase.cxx index a955b55639f7cf2148733d0ddba3b7e7167b0c91..4b54e7c81b9db7f5fa9715d384d27a6869e295ec 100644 --- a/reco/L1/qa/CbmCaInputQaBase.cxx +++ b/reco/L1/qa/CbmCaInputQaBase.cxx @@ -736,9 +736,15 @@ InitStatus CbmCaInputQaBase<DetID>::InitDataBranches() frYmin[i] -= dy; frYmax[i] += dy; - double dz = 0.05 * fabs(frZmax[i] - frZmin[i]); - frZmin[i] -= dz; - frZmax[i] += dz; + if constexpr (L1DetectorID::kMuch == DetID) { + frZmin[i] -= 40; + frZmax[i] += 40; + } + else { + double dz = 0.05 * fabs(frZmax[i] - frZmin[i]); + frZmin[i] -= dz; + frZmax[i] += dz; + } } @@ -906,7 +912,7 @@ InitStatus CbmCaInputQaBase<DetID>::InitHistograms() // Difference between MC input z and hit z coordinates sN = (TString) "point_hit_delta_z" + nsuff; sT = (TString) "Distance between " + detName + " point and hit along z axis" + tsuff + ";z_{reco} - z_{MC} [cm]"; - fvph_point_hit_delta_z[iSt] = MakeQaObject<TH1F>(sF + sN, sT, fNbins, -0.05, 0.05); + fvph_point_hit_delta_z[iSt] = MakeQaObject<TH1F>(sF + sN, sT, fNbins, fRangeDzHitPoint[0], fRangeDzHitPoint[1]); sN = (TString) "res_x" + nsuff; sT = (TString) "Residuals for X" + tsuff + ";x_{reco} - x_{MC} [cm]"; diff --git a/reco/L1/qa/CbmCaInputQaBase.h b/reco/L1/qa/CbmCaInputQaBase.h index cc0272beabb84478c6faa9f6b0bdb240501a6ce3..d3a8292d899ee419e2a075dc299f34f4c0fcc65b 100644 --- a/reco/L1/qa/CbmCaInputQaBase.h +++ b/reco/L1/qa/CbmCaInputQaBase.h @@ -185,6 +185,8 @@ protected: std::array<double, 2> fRResV = {kNAN, kNAN}; ///< Range for residual of v coordinate [cm] std::array<double, 2> fRResT = {kNAN, kNAN}; ///< Range for residual of time [ns] + std::array<double, 2> fRangeDzHitPoint = {-0.05, 0.05}; ///< Range for z-pos difference of the hit and point [cm] + // NOTE: Pull binning is fixed by convention, since it is used for hit finder calibrations. Please, // do not modify! static constexpr int kNbinsPull = 200; diff --git a/reco/L1/qa/CbmCaInputQaMuch.cxx b/reco/L1/qa/CbmCaInputQaMuch.cxx index c39121e8c42434cf6ed4b0c4388761292577da89..18644b723a102e0572e86ea4ae8074050d55816e 100644 --- a/reco/L1/qa/CbmCaInputQaMuch.cxx +++ b/reco/L1/qa/CbmCaInputQaMuch.cxx @@ -53,6 +53,7 @@ void CbmCaInputQaMuch::DefineParameters() SetRange(fRResU, -2.00, 2.00); SetRange(fRResV, -4.00, 4.00); SetRange(fRResT, -5.00, 5.00); + SetRange(fRangeDzHitPoint, -50., 50.); // QA result selection criteria SetRange(fEffRange, 10.0, 30.0); ///< Range for hit efficiency approximation fResMeanThrsh = 0.50; ///< Maximum allowed deviation of residual mean from zero [sigma] diff --git a/reco/L1/qa/CbmCaOutputQa.cxx b/reco/L1/qa/CbmCaOutputQa.cxx index 121e8359885ebf416757747846f7774a5b438003..abb6e8b7ed5017becb156be1bf59424a66f117ba 100644 --- a/reco/L1/qa/CbmCaOutputQa.cxx +++ b/reco/L1/qa/CbmCaOutputQa.cxx @@ -627,6 +627,48 @@ InitStatus OutputQa::InitTimeSlice() fpMCModule->MatchRecoAndMC(); } + // ****** DEBUG: BEGIN + if constexpr (0) { + using std::setw; + { + LOG(info) << "---------- Reco track sample"; + int id = 0; + if (fvRecoTracks.size()) { LOG(info) << setw(4) << "No." << ' ' << fvRecoTracks[0].ToString(3, true); } + for (const auto& trk : fvRecoTracks) { + LOG(info) << setw(4) << (id++) << ' ' << trk.ToString(3); + } + } + { + LOG(info) << "---------- Reco hit sample"; + int id = 0; + if (fvHits.size()) { LOG(info) << setw(4) << "No." << ' ' << fvHits[0].ToString(3, true); } + for (const auto& h : fvHits) { + LOG(info) << setw(4) << (id++) << ' ' << h.ToString(3); + } + } + if (IsMCUsed()) { + LOG(info) << "---------- MC tracks sample"; + int id = 0; + if (fMCData.GetTrackContainer().size()) { + LOG(info) << setw(4) << "No." << ' ' << fMCData.GetTrack(0).ToString(3, true); + } + for (const auto& trk : fMCData.GetTrackContainer()) { + if (trk.GetNofHits() || trk.GetNofPoints()) { LOG(info) << setw(4) << (id++) << ' ' << trk.ToString(3); } + } + } + if (IsMCUsed()) { + LOG(info) << "---------- MC points sample"; + int id = 0; + if (fMCData.GetPointContainer().size()) { + LOG(info) << setw(4) << "No." << ' ' << fMCData.GetPoint(0).ToString(3, true); + } + for (const auto& p : fMCData.GetPointContainer()) { + LOG(info) << setw(4) << (id++) << ' ' << p.ToString(3); + } + } + } + // ****** DEBUG: END + LOG_IF(info, fVerbose > 1) << fName << ": Data sample consists of " << nHits << " hits, " << nRecoTracks << " reco tracks, " << nMCTracks << " MC tracks, " << nMCPoints << " MC points"; diff --git a/reco/L1/qa/CbmCaOutputQa.h b/reco/L1/qa/CbmCaOutputQa.h index cabc82c0b8d852103c180e729664856671c22e79..afa5c54f0ead843d6e50671ed4fe53d81824645e 100644 --- a/reco/L1/qa/CbmCaOutputQa.h +++ b/reco/L1/qa/CbmCaOutputQa.h @@ -164,7 +164,7 @@ namespace cbm::ca void SetMcbmTrackingMode() { fTrackingMode = ECbmCaTrackingMode::kMCBM; } /// @brief Sets performance mode - /// @param mode Performance mode (3 is default: TODO - test) + /// @param mode Performance mode (1 is default: TODO - test) void SetPerformanceMode(int mode) { fPerformanceMode = mode; } ClassDef(OutputQa, 0); @@ -231,7 +231,7 @@ namespace cbm::ca bool fbUseTrd = false; ///< is TRD used bool fbUseTof = false; ///< is TOF used - int fPerformanceMode = 3; ///< Performance mode + int fPerformanceMode = 1; ///< Performance mode ECbmCaTrackingMode fTrackingMode = ECbmCaTrackingMode::kSTS; ///< Tracking mode