From 7a9e2cbc725dd85750e72462bb664042926b8135 Mon Sep 17 00:00:00 2001 From: Felix Schlepper Date: Mon, 2 Nov 2026 09:24:07 +0100 Subject: [PATCH 1/3] ALICE3: TRK/FT3 digitizer response matrix on the heap, not the stack Signed-off-by: Felix Schlepper --- .../simulation/include/TRKFT3Simulation/Digitizer.h | 2 +- .../TRKFT3/common/simulation/src/Digitizer.cxx | 12 ++++++------ 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/Detectors/Upgrades/ALICE3/TRKFT3/common/simulation/include/TRKFT3Simulation/Digitizer.h b/Detectors/Upgrades/ALICE3/TRKFT3/common/simulation/include/TRKFT3Simulation/Digitizer.h index 7b06df5601208..d0cf085d971a0 100644 --- a/Detectors/Upgrades/ALICE3/TRKFT3/common/simulation/include/TRKFT3Simulation/Digitizer.h +++ b/Detectors/Upgrades/ALICE3/TRKFT3/common/simulation/include/TRKFT3Simulation/Digitizer.h @@ -93,7 +93,7 @@ class Digitizer void setDeadChannelsMap(const o2::itsmft::NoiseMap* mp) { mDeadChanMap = mp; } private: - void processHit(const o2::trkft3::Hit& hit, uint32_t& maxFr, int evID, int srcID, int rofLayer); + void processHit(const o2::trkft3::Hit& hit, uint32_t& maxFr, int evID, int srcID, int rofLayer, std::vector& respMatrix); void registerDigits(o2::trkft3::ChipDigitsContainer& chip, uint32_t roFrame, float toaInROF, int nROF, uint16_t row, uint16_t col, int nEle, o2::MCCompLabel& lbl, int layer); diff --git a/Detectors/Upgrades/ALICE3/TRKFT3/common/simulation/src/Digitizer.cxx b/Detectors/Upgrades/ALICE3/TRKFT3/common/simulation/src/Digitizer.cxx index 493f321c765bc..bf18e5d0110f9 100644 --- a/Detectors/Upgrades/ALICE3/TRKFT3/common/simulation/src/Digitizer.cxx +++ b/Detectors/Upgrades/ALICE3/TRKFT3/common/simulation/src/Digitizer.cxx @@ -139,13 +139,14 @@ void Digitizer::process(const std::vector* hits, int evID, int srcID return (*hits)[lhs].GetDetectorID() < (*hits)[rhs].GetDetectorID(); }); LOG(info) << "Processing " << nHits << " hits"; + std::vector respMatrix; // the hits' charge response, reused from hit to hit within the event for (int i : hitIdx | std::views::filter([&](int idx) { if (layer < 0) { return true; } return getROFLayer((*hits)[idx].GetDetectorID()) == layer; })) { - processHit((*hits)[i], mROFrameMax, evID, srcID, layer); + processHit((*hits)[i], mROFrameMax, evID, srcID, layer, respMatrix); } } @@ -253,7 +254,7 @@ void Digitizer::fillOutputContainer(uint32_t frameLast, int layer) //_______________________________________________________________________ template -void Digitizer::processHit(const o2::trkft3::Hit& hit, uint32_t& maxFr, int evID, int srcID, int rofLayer) +void Digitizer::processHit(const o2::trkft3::Hit& hit, uint32_t& maxFr, int evID, int srcID, int rofLayer, std::vector& respMatrix) { int chipID = hit.GetDetectorID(); //// the chip ID at the moment is not referred to the chip but to a wider detector element (e.g. quarter of layer or disk in VD, stave in ML, half stave in OT) int subDetID = mGeometry->getSubDetID(chipID); @@ -394,8 +395,7 @@ void Digitizer::processHit(const o2::trkft3::Hit& hit, uint32_t& maxFr, i } int rowSpan = rowE - rowS + 1, colSpan = colE - colS + 1; // size of plaquet where some response is expected - float respMatrix[rowSpan][colSpan]; // response accumulated here - std::fill(&respMatrix[0][0], &respMatrix[0][0] + rowSpan * colSpan, 0.f); + respMatrix.assign(static_cast(rowSpan) * colSpan, 0.f); // response accumulated here, row by row float nElectrons = hit.GetEnergyLoss() * mParams.getEnergyToNElectrons(); // total number of deposited electrons nElectrons *= nStepsInv; // N electrons injected per step @@ -463,7 +463,7 @@ void Digitizer::processHit(const o2::trkft3::Hit& hit, uint32_t& maxFr, i if (colDest < 0 || colDest >= colSpan) { continue; } - respMatrix[rowDest][colDest] += rspmat->getValue(irow, icol, mSimRespOrientation ? !flipRow : flipRow, flipCol); + respMatrix[rowDest * colSpan + colDest] += rspmat->getValue(irow, icol, mSimRespOrientation ? !flipRow : flipRow, flipCol); } } } @@ -475,7 +475,7 @@ void Digitizer::processHit(const o2::trkft3::Hit& hit, uint32_t& maxFr, i for (int irow = rowSpan; irow--;) { // irow ranging from 4 to 0 uint16_t rowIS = irow + rowS; // row distant irow from the row of the hit start for (int icol = colSpan; icol--;) { // icol ranging from 4 to 0 - float nEleResp = respMatrix[irow][icol]; // value of the probability of the response in this pixel + float nEleResp = respMatrix[irow * colSpan + icol]; // value of the probability of the response in this pixel if (nEleResp <= 1.e-36) { continue; } From b23b5fb65df6b90eef5c7f744e05893b7d303a94 Mon Sep 17 00:00:00 2001 From: Felix Schlepper Date: Mon, 2 Nov 2026 09:24:07 +0100 Subject: [PATCH 2/3] ITSMFT: digitizer response matrix on the heap, not the stack Signed-off-by: Felix Schlepper --- .../simulation/include/ITSMFTSimulation/Digitizer.h | 2 +- Detectors/ITSMFT/common/simulation/src/Digitizer.cxx | 12 ++++++------ 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/Detectors/ITSMFT/common/simulation/include/ITSMFTSimulation/Digitizer.h b/Detectors/ITSMFT/common/simulation/include/ITSMFTSimulation/Digitizer.h index 6c1caa4a0b1e9..14bc81e790abb 100644 --- a/Detectors/ITSMFT/common/simulation/include/ITSMFTSimulation/Digitizer.h +++ b/Detectors/ITSMFT/common/simulation/include/ITSMFTSimulation/Digitizer.h @@ -102,7 +102,7 @@ class Digitizer : public TObject } private: - void processHit(const o2::itsmft::Hit& hit, uint32_t& maxFr, int evID, int srcID, int lay); + void processHit(const o2::itsmft::Hit& hit, uint32_t& maxFr, int evID, int srcID, int lay, std::vector& respMatrix); void registerDigits(ChipDigitsContainer& chip, uint32_t roFrame, float tInROF, int nROF, uint16_t row, uint16_t col, int nEle, o2::MCCompLabel& lbl, int lay); diff --git a/Detectors/ITSMFT/common/simulation/src/Digitizer.cxx b/Detectors/ITSMFT/common/simulation/src/Digitizer.cxx index 6508661feee0e..8eaf5e700cf60 100644 --- a/Detectors/ITSMFT/common/simulation/src/Digitizer.cxx +++ b/Detectors/ITSMFT/common/simulation/src/Digitizer.cxx @@ -128,13 +128,14 @@ void Digitizer::process(const std::vector* hits, int evID, int srcID, int l std::sort(hitIdx.begin(), hitIdx.end(), [hits](auto lhs, auto rhs) { return (*hits)[lhs].GetDetectorID() < (*hits)[rhs].GetDetectorID(); }); + std::vector respMatrix; // the hits' charge response, reused from hit to hit within the event for (int i : hitIdx | std::views::filter([&](int idx) { if (layer < 0) { return true; } return mGeometry->getLayer((*hits)[idx].GetDetectorID()) == layer; })) { - processHit((*hits)[i], mROFrameMax, evID, srcID, layer); + processHit((*hits)[i], mROFrameMax, evID, srcID, layer, respMatrix); } // in the triggered mode store digits after every MC event @@ -256,7 +257,7 @@ void Digitizer::fillOutputContainer(uint32_t frameLast, int layer) } //_______________________________________________________________________ -void Digitizer::processHit(const o2::itsmft::Hit& hit, uint32_t& maxFr, int evID, int srcID, int lay) +void Digitizer::processHit(const o2::itsmft::Hit& hit, uint32_t& maxFr, int evID, int srcID, int lay, std::vector& respMatrix) { // convert single hit to digits auto chipID = hit.GetDetectorID(); @@ -347,8 +348,7 @@ void Digitizer::processHit(const o2::itsmft::Hit& hit, uint32_t& maxFr, int evID } int rowSpan = rowE - rowS + 1, colSpan = colE - colS + 1; // size of plaquet where some response is expected - float respMatrix[rowSpan][colSpan]; // response accumulated here - std::fill(&respMatrix[0][0], &respMatrix[0][0] + rowSpan * colSpan, 0.f); + respMatrix.assign(static_cast(rowSpan) * colSpan, 0.f); // response accumulated here, row by row float nElectrons = hit.GetEnergyLoss() * mParams.getEnergyToNElectrons(); // total number of deposited electrons nElectrons *= nStepsInv; // N electrons injected per step @@ -397,7 +397,7 @@ void Digitizer::processHit(const o2::itsmft::Hit& hit, uint32_t& maxFr, int evID if (colDest < 0 || colDest >= colSpan) { continue; } - respMatrix[rowDest][colDest] += rspmat->getValue(irow, icol, flipRow, flipCol); + respMatrix[rowDest * colSpan + colDest] += rspmat->getValue(irow, icol, flipRow, flipCol); } } } @@ -409,7 +409,7 @@ void Digitizer::processHit(const o2::itsmft::Hit& hit, uint32_t& maxFr, int evID for (int irow = rowSpan; irow--;) { uint16_t rowIS = irow + rowS; for (int icol = colSpan; icol--;) { - float nEleResp = respMatrix[irow][icol]; + float nEleResp = respMatrix[irow * colSpan + icol]; if (!nEleResp) { continue; } From 1b5c051411249b6f3738f118f2c46fd1e58a8497 Mon Sep 17 00:00:00 2001 From: Felix Schlepper Date: Mon, 2 Nov 2026 09:24:07 +0100 Subject: [PATCH 3/3] ITS3: digitizer response matrix on the heap, not the stack Signed-off-by: Felix Schlepper --- .../simulation/include/ITS3Simulation/Digitizer.h | 2 +- Detectors/Upgrades/ITS3/simulation/src/Digitizer.cxx | 12 ++++++------ 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/Detectors/Upgrades/ITS3/simulation/include/ITS3Simulation/Digitizer.h b/Detectors/Upgrades/ITS3/simulation/include/ITS3Simulation/Digitizer.h index 90dda6fd67393..1f977b6988c57 100644 --- a/Detectors/Upgrades/ITS3/simulation/include/ITS3Simulation/Digitizer.h +++ b/Detectors/Upgrades/ITS3/simulation/include/ITS3Simulation/Digitizer.h @@ -86,7 +86,7 @@ class Digitizer : public TObject void setDeadChannelsMap(const o2::itsmft::NoiseMap* mp) { mDeadChanMap = mp; } private: - void processHit(const o2::itsmft::Hit& hit, uint32_t& maxFr, int evID, int srcID, int layer); + void processHit(const o2::itsmft::Hit& hit, uint32_t& maxFr, int evID, int srcID, int layer, std::vector& respMatrix); void registerDigits(o2::its3::ChipDigitsContainer& chip, uint32_t roFrame, float tInROF, int nROF, uint16_t row, uint16_t col, int nEle, o2::MCCompLabel& lbl, int layer); diff --git a/Detectors/Upgrades/ITS3/simulation/src/Digitizer.cxx b/Detectors/Upgrades/ITS3/simulation/src/Digitizer.cxx index dbad61e48526e..d07fb53b7220e 100644 --- a/Detectors/Upgrades/ITS3/simulation/src/Digitizer.cxx +++ b/Detectors/Upgrades/ITS3/simulation/src/Digitizer.cxx @@ -95,13 +95,14 @@ void Digitizer::process(const std::vector* hits, int evID, int srcI [hits](auto lhs, auto rhs) { return (*hits)[lhs].GetDetectorID() < (*hits)[rhs].GetDetectorID(); }); + std::vector respMatrix; // the hits' charge response, reused from hit to hit within the event for (int i : hitIdx | std::views::filter([&](int idx) { if (layer < 0) { return true; } return mGeometry->getLayer((*hits)[idx].GetDetectorID()) == layer; })) { - processHit((*hits)[i], mROFrameMax, evID, srcID, layer); + processHit((*hits)[i], mROFrameMax, evID, srcID, layer, respMatrix); } // in the triggered mode store digits after every MC event // TODO: in the real triggered mode this will not be needed, this is actually for the @@ -218,7 +219,7 @@ void Digitizer::fillOutputContainer(uint32_t frameLast, int layer) } } -void Digitizer::processHit(const o2::itsmft::Hit& hit, uint32_t& maxFr, int evID, int srcID, int lay) +void Digitizer::processHit(const o2::itsmft::Hit& hit, uint32_t& maxFr, int evID, int srcID, int lay, std::vector& respMatrix) { // convert single hit to digits auto chipID = hit.GetDetectorID(); @@ -336,8 +337,7 @@ void Digitizer::processHit(const o2::itsmft::Hit& hit, uint32_t& maxFr, int evID colE = std::min(colE, maxNcols - 1); int rowSpan = rowE - rowS + 1, colSpan = colE - colS + 1; // size of plaquet where some response is expected - float respMatrix[rowSpan][colSpan]; // response accumulated here - std::fill(&respMatrix[0][0], &respMatrix[0][0] + rowSpan * colSpan, 0.f); + respMatrix.assign(static_cast(rowSpan) * colSpan, 0.f); // response accumulated here, row by row float nElectrons = hit.GetEnergyLoss() * mParams.getEnergyToNElectrons(); // total number of deposited electrons nElectrons *= nStepsInv; // N electrons injected per step @@ -401,7 +401,7 @@ void Digitizer::processHit(const o2::itsmft::Hit& hit, uint32_t& maxFr, int evID if (colDest < 0 || colDest >= colSpan) { continue; } - respMatrix[rowDest][colDest] += rspmat->getValue(irow, icol, ((chip.isIB() && mSimRespIBOrientation) ? !flipRow : flipRow), flipCol); + respMatrix[rowDest * colSpan + colDest] += rspmat->getValue(irow, icol, ((chip.isIB() && mSimRespIBOrientation) ? !flipRow : flipRow), flipCol); } } } @@ -413,7 +413,7 @@ void Digitizer::processHit(const o2::itsmft::Hit& hit, uint32_t& maxFr, int evID for (int irow = rowSpan; irow--;) { uint16_t rowIS = irow + rowS; for (int icol = colSpan; icol--;) { - float nEleResp = respMatrix[irow][icol]; + float nEleResp = respMatrix[irow * colSpan + icol]; if (nEleResp <= 1.e-36) { continue; }