Belle II Software development
KLMDigitizerModule.cc
1/**************************************************************************
2 * basf2 (Belle II Analysis Software Framework) *
3 * Author: The Belle II Collaboration *
4 * *
5 * See git log for contributors and copyright holders. *
6 * This file is licensed under LGPL-3.0, see LICENSE.md. *
7 **************************************************************************/
8
9/* Own header. */
10#include <klm/modules/KLMDigitizer/KLMDigitizerModule.h>
11
12/* KLM headers. */
13#include <klm/dataobjects/KLMChannelIndex.h>
14#include <klm/dataobjects/KLMScintillatorFirmwareFitResult.h>
15#include <klm/simulation/ScintillatorSimulator.h>
16
17/* Basf2 headers. */
18#include <framework/dataobjects/BackgroundMetaData.h>
19#include <mdst/dataobjects/MCParticle.h>
20
21/* ROOT headers. */
22#include <TRandom.h>
23
24using namespace Belle2;
25
26REG_MODULE(KLMDigitizer);
27
32
33public:
34
41 bool operator()(const MCParticle* particle1, const MCParticle* particle2) const
42 {
43 return particle1->getIndex() < particle2->getIndex();
44 }
45};
46
48 Module(),
49 m_Time(&(KLMTime::Instance())),
50 m_ElementNumbers(&(KLMElementNumbers::Instance())),
51 m_ChannelSpecificSimulation(false),
52 m_EfficiencyMode(c_Plane),
53 m_Fitter(nullptr)
54{
55 setDescription("KLM digitization module: create KLMDigits from KLMSimHits.");
57 addParam("SimulationMode", m_SimulationMode,
58 "Simulation mode (\"Generic\" or \"ChannelSpecific\").",
59 std::string("Generic"));
60 /*
61 * Initial digitization time is negative to work with cosmic events (the part
62 * of the track directed to the interaction pointhas a negative time).
63 */
64 addParam("DigitizationInitialTime", m_DigitizationInitialTime,
65 "Initial digitization time in CTIME periods.", -5);
66 addParam("SaveFPGAFit", m_SaveFPGAFit, "Save FPGA fit data and set a relation with KLMDigits.", false);
67 addParam("Efficiency", m_Efficiency,
68 "Efficiency determination mode (\"Strip\" or \"Plane\").",
69 std::string("Plane"));
70 addParam("CreateMultiStripDigits", m_CreateMultiStripDigits,
71 "Whether to create multi-strip digits in Run 1 data (not used for Run 2+).", true);
72 addParam("Debug", m_Debug,
73 "Debug mode (generates additional output files with histograms).",
74 false);
75}
76
78{
79}
80
82{
83 m_SimHits.isRequired();
84 m_Digits.registerInDataStore();
85 m_Digits.registerRelationTo(m_SimHits);
86 if (m_SaveFPGAFit) {
87 m_FPGAFits.registerInDataStore();
88 m_Digits.registerRelationTo(m_FPGAFits);
89 }
90 if (m_SimulationMode == "Generic") {
91 /* Nothing to do. */
92 } else if (m_SimulationMode == "ChannelSpecific") {
94 } else {
95 B2FATAL("Unknown simulation mode: " << m_SimulationMode);
96 }
97 if (m_Efficiency == "Strip")
99 else if (m_Efficiency == "Plane")
101 else
102 B2FATAL("Unknown efficiency mode: " << m_EfficiencyMode);
103}
104
106{
107 KLMChannelIndex klmChannels;
108 for (KLMChannelIndex& klmChannel : klmChannels) {
109 KLMChannelNumber channel = m_ElementNumbers->channelNumber(klmChannel.getSubdetector(), klmChannel.getSection(),
110 klmChannel.getSector(), klmChannel.getLayer(),
111 klmChannel.getPlane(), klmChannel.getStrip());
112 const KLMScintillatorFEEData* FEEData = m_FEEPar->getFEEData(channel);
113 if (FEEData == nullptr)
114 B2FATAL("Incomplete scintillator FEE data.");
115 if (FEEData->getPhotoelectronAmplitude() <= 0) {
116 B2ERROR("Non-positive photoelectron amplitude. The requested "
117 "channel-specific simulation is impossible. "
118 "KLMDigitizer is switched to the generic mode."
119 << LogVar("Section", klmChannel.getSection())
120 << LogVar("Layer", klmChannel.getLayer())
121 << LogVar("Sector", klmChannel.getSector())
122 << LogVar("Plane", klmChannel.getPlane())
123 << LogVar("Strip", klmChannel.getStrip()));
125 return;
126 }
127 }
128}
129
131{
132 if (!m_DigPar.isValid())
133 B2FATAL("KLM scintillator digitization parameters are not available.");
134 if (!m_FEEPar.isValid())
135 B2FATAL("KLM scintillator FEE parameters are not available.");
136 if (!m_ChannelStatus.isValid())
137 B2FATAL("KLM channel status data are not available.");
138 if (!m_StripEfficiency.isValid())
139 B2FATAL("KLM strip efficiency data are not available.");
140 if (!m_ScintillatorFirmware.isValid())
141 B2FATAL("KLM scintillator firmware version is not available.");
145 m_Fitter = new KLM::ScintillatorFirmware(m_DigPar->getNDigitizations());
147 m_CreateMultiStripDigitsByRun = false; // do not make multi-strip KLMDigits for Run 2+ events
148 if ((fwVersion == KLMScintillatorFirmware::FirmwareVersion::c_Invalid) || // this should never happen!
149 (fwVersion == KLMScintillatorFirmware::FirmwareVersion::c_Phase2) || // for very early data (deprecated)
150 (fwVersion == KLMScintillatorFirmware::FirmwareVersion::c_Run1)) { // for data up to and including 2022b
152 }
153 B2INFO("KLM multi-strip digits are " << (m_CreateMultiStripDigitsByRun ? "" : "NOT") << " simulated");
154}
155
156/*
157 * Digitization. Light propagation into the fiber, SiPM and electronics effects
158 * are simulated in KLM::ScintillatorSimulator class.
159 */
160
162{
164 m_ChannelStatus->getChannelStatus(channel);
165 if (status == KLMChannelStatus::c_Unknown)
166 B2FATAL("Incomplete KLM channel status data.");
167 return (status != KLMChannelStatus::c_Dead);
168}
169
171{
172 if (std::isnan(efficiency))
173 B2FATAL("Incomplete KLM efficiency data.");
174 double selection = gRandom->Uniform();
175 return (selection < efficiency);
176}
177
179{
180 std::multimap<KLMChannelNumber, const KLMSimHit*>::iterator
181 it, it2, lowerBound, upperBound;
182 it = m_MapChannelSimHit.begin();
183 while (it != m_MapChannelSimHit.end()) {
184 lowerBound = it;
185 upperBound = m_MapChannelSimHit.upper_bound(it->first);
186 it = upperBound;
187 if (not lowerBound->second->inRPC())
188 B2FATAL("KLMDigitizer::digitizeRPC is trying to process a scintillator hit.");
189 if (m_EfficiencyMode == c_Strip) {
190 float efficiency = m_StripEfficiency->getEfficiency(lowerBound->first);
191 if (!efficiencyCorrection(efficiency))
192 continue;
193 }
195 m_ElementNumbers->localChannelNumberBKLM(lowerBound->first));
196 /* Select hit that has the smallest time. */
197 it2 = lowerBound;
198 const KLMSimHit* hit = lowerBound->second;
199 double time = hit->getTime();
200 ++it2;
201 while (it2 != upperBound) {
202 if (it2->second->getTime() < time) {
203 time = it2->second->getTime();
204 hit = it2->second;
205 }
206 ++it2;
207 }
208 KLMDigit* digit = m_Digits.appendNew(hit, strip);
209 it2 = lowerBound;
210 while (it2 != upperBound) {
211 digit->addRelationTo(it2->second);
212 ++it2;
213 }
214 }
215}
216
218{
219 uint16_t tdc;
221 &(*m_DigPar), m_Fitter,
223 const KLMScintillatorFEEData* FEEData;
224 std::multimap<KLMChannelNumber, const KLMSimHit*>::iterator
225 it, lowerBound, upperBound;
226 for (int i = 0; i < KLM::c_NChannelsAsic; ++i)
227 m_AsicDigits[i] = nullptr;
228 it = m_MapChannelSimHit.begin();
229 while (it != m_MapChannelSimHit.end()) {
230 lowerBound = it;
231 upperBound = m_MapChannelSimHit.upper_bound(it->first);
232 it = upperBound;
233 if (lowerBound->second->inRPC())
234 B2FATAL("KLMDigitizer::digitizeScintillator is trying to process a RPC hit.");
235 const KLMSimHit* simHit = lowerBound->second;
236 if (m_EfficiencyMode == c_Strip) {
237 float efficiency = m_StripEfficiency->getEfficiency(lowerBound->first);
238 if (!efficiencyCorrection(efficiency))
239 continue;
240 }
242 FEEData = m_FEEPar->getFEEData(lowerBound->first);
243 if (FEEData == nullptr)
244 B2FATAL("Incomplete KLM scintillator FEE data.");
245 simulator.setFEEData(FEEData);
246 }
247 simulator.simulate(lowerBound, upperBound);
248 if (simulator.getNGeneratedPhotoelectrons() == 0)
249 continue;
250 const KLMElectronicsChannel* electronicsChannel =
251 m_ElectronicsMap->getElectronicsChannel(lowerBound->first);
252 int channel = (electronicsChannel->getChannel() - 1) %
253 KLM::c_NChannelsAsic;
254 KLMDigit* digit = new KLMDigit(simHit);
255 m_AsicDigits[channel] = digit;
256 m_AsicDigitSimHitsLowerBound[channel] = lowerBound;
257 m_AsicDigitSimHitsUpperBound[channel] = upperBound;
258 digit->setMCTime(simulator.getMCTime());
259 digit->setSiPMMCTime(simulator.getSiPMMCTime());
261 simulator.getNGeneratedPhotoelectrons());
262 if (simulator.getFitStatus() ==
263 KLM::c_ScintillatorFirmwareSuccessfulFit) {
264 tdc = simulator.getFPGAFit()->getStartTime();
265 digit->setCharge(simulator.getFPGAFit()->getMinimalAmplitude());
266 } else {
267 tdc = 0;
268 digit->setCharge(m_DigPar->getADCRange() - 1);
269 }
270 digit->setTDC(tdc);
271 digit->setTime(m_Time->getTimeSimulation(tdc, true));
272 digit->setFitStatus(simulator.getFitStatus());
273 digit->setNPhotoelectrons(simulator.getNPhotoelectrons());
274 digit->setEnergyDeposit(simulator.getEnergy());
275 if (m_SaveFPGAFit && (simulator.getFitStatus() ==
276 KLM::c_ScintillatorFirmwareSuccessfulFit)) {
278 m_FPGAFits.appendNew(*simulator.getFPGAFit());
279 digit->addRelationTo(fit);
280 }
281 }
282}
283
285{
286 std::multimap<KLMElectronicsChannel, const KLMSimHit*>::iterator
287 it, it2, upperBound;
288 std::multimap<KLMChannelNumber, const KLMSimHit*>::iterator it3;
289 it = m_MapAsicSimHit.begin();
290 while (it != m_MapAsicSimHit.end()) {
291 upperBound = m_MapAsicSimHit.upper_bound(it->first);
292 m_MapChannelSimHit.clear();
293 for (it2 = it; it2 != upperBound; ++it2) {
294 const KLMSimHit* hit = it2->second;
295 KLMChannelNumber channel =
297 hit->getSubdetector(), hit->getSection(), hit->getSector(),
298 hit->getLayer(), hit->getPlane(), hit->getStrip());
299 m_MapChannelSimHit.insert(
300 std::pair<KLMChannelNumber, const KLMSimHit*>(channel, hit));
301 }
304 int nDigits = 0;
305 for (int i = 0; i < KLM::c_NChannelsAsic; ++i) {
306 if (m_AsicDigits[i] != nullptr)
307 nDigits += 1;
308 }
309 bool multiStripMode = (nDigits >= 2);
310 int i = 0;
311 while (i < KLM::c_NChannelsAsic) {
312 KLMDigit* digit = m_AsicDigits[i];
313 if (digit == nullptr) {
314 ++i;
315 continue;
316 }
317 // Firmware bug (used OR of struck channel numbers in range 1..15) defeated the
318 // expected by-4 grouping so we assume the worst case: all 15 channels are struck.
319 // This will be reduced for BKLM scintillators if there are missing detectorChannels.
320 int minGroupChannel = 1;
321 int maxGroupChannel = KLM::c_NChannelsAsic;
322 KLMDigit* arrayDigit = m_Digits.appendNew(*digit);
323 KLMElectronicsChannel electronicsChannel(it->first);
324 int asic = electronicsChannel.getChannel();
325 bool connectedChannelFound = false;
326 int minStrip, maxStrip;
327 for (int j = minGroupChannel; j <= maxGroupChannel; ++j) {
328 electronicsChannel.setChannel(KLM::c_NChannelsAsic * asic + j);
329 const KLMChannelNumber* detectorChannel =
330 m_ElectronicsMap->getDetectorChannel(&electronicsChannel);
331 if (detectorChannel != nullptr) {
332 int subdetector, section, sector, layer, plane, strip;
334 *detectorChannel, &subdetector, &section, &sector, &layer,
335 &plane, &strip);
336 if (!connectedChannelFound) {
337 connectedChannelFound = true;
338 minStrip = strip;
339 maxStrip = strip;
340 } else {
341 if (strip < minStrip)
342 minStrip = strip;
343 if (strip > maxStrip)
344 maxStrip = strip;
345 }
346 }
347 }
348 /* This should never happen. */
349 if (!connectedChannelFound)
350 B2FATAL("Cannot find connected electronics channels.");
351 if (multiStripMode) {
352 arrayDigit->setStrip(minStrip);
353 arrayDigit->setLastStrip(maxStrip);
354 }
355 for (int j = i; j < maxGroupChannel; ++j) {
356 if (m_AsicDigits[j] == nullptr)
357 continue;
358 for (it3 = m_AsicDigitSimHitsLowerBound[j];
359 it3 != m_AsicDigitSimHitsUpperBound[j]; ++it3) {
360 arrayDigit->addRelationTo(it3->second);
361 }
362 }
363 i = maxGroupChannel;
364 }
365 for (i = 0; i < KLM::c_NChannelsAsic; ++i) {
366 if (m_AsicDigits[i] != nullptr)
367 delete m_AsicDigits[i];
368 }
369 } else {
370 for (int i = 0; i < KLM::c_NChannelsAsic; ++i) {
371 KLMDigit* digit = m_AsicDigits[i];
372 if (digit == nullptr)
373 continue;
374 KLMDigit* arrayDigit = m_Digits.appendNew(*digit);
375 for (it3 = m_AsicDigitSimHitsLowerBound[i];
376 it3 != m_AsicDigitSimHitsUpperBound[i]; ++it3) {
377 arrayDigit->addRelationTo(it3->second);
378 }
379 delete digit;
380 }
381 }
382 it = upperBound;
383 }
384}
385
387{
388 int i;
389 KLMChannelNumber channel;
390 m_MapChannelSimHit.clear();
391 m_MapAsicSimHit.clear();
392 if (m_EfficiencyMode == c_Plane) {
393 m_MapPlaneSimHit.clear();
394 for (i = 0; i < m_SimHits.getEntries(); i++) {
395 const KLMSimHit* hit = m_SimHits[i];
396 /* For RPCs. */
397 if (hit->getStrip() <= 0)
398 continue;
399 const MCParticle* particle = hit->getRelatedFrom<MCParticle>();
400 /*
401 * We do not simulate the plane efficiency for KLMSimHits
402 * from beam background because there are no MCParticles associated
403 * to them.
404 */
405 if (particle != nullptr) {
406 KLMPlaneNumber plane =
408 hit->getSubdetector(), hit->getSection(), hit->getSector(),
409 hit->getLayer(), hit->getPlane());
410 m_MapPlaneSimHit.insert(
411 std::pair<KLMPlaneNumber, const KLMSimHit*>(plane, hit));
412 } else {
413 B2ASSERT("The KLMSimHit is not related to any MCParticle and "
414 "it is also not a beam background hit.",
415 hit->getBackgroundTag() != BackgroundMetaData::bg_none);
416 channel =
418 hit->getSubdetector(), hit->getSection(), hit->getSector(),
419 hit->getLayer(), hit->getPlane(), hit->getStrip());
420 if (checkActive(channel)) {
421 bool rpc = hit->inRPC();
422 if (rpc) {
423 m_MapChannelSimHit.insert(std::pair<KLMChannelNumber, const KLMSimHit*>(channel, hit));
424 } else {
425 const KLMElectronicsChannel* electronicsChannel =
426 m_ElectronicsMap->getElectronicsChannel(channel);
427 if (electronicsChannel == nullptr)
428 B2FATAL("Incomplete electronics map.");
429 KLMElectronicsChannel asic = electronicsChannel->getAsic();
430 m_MapAsicSimHit.insert(std::pair<KLMElectronicsChannel, const KLMSimHit*>(asic, hit));
431 }
432 }
433 }
434 }
435 std::multimap<KLMPlaneNumber, const KLMSimHit*>::iterator it, it2;
441 std::multimap<const MCParticle*, const KLMSimHit*,
442 CompareMCParticlesByIndex> particleHitMap;
443 std::multimap<const MCParticle*, const KLMSimHit*>::iterator
444 itParticle, it2Particle;
445 it = m_MapPlaneSimHit.begin();
446 while (it != m_MapPlaneSimHit.end()) {
447 particleHitMap.clear();
448 it2 = it;
449 while (true) {
450 const KLMSimHit* hit = it2->second;
451 const MCParticle* particle = hit->getRelatedFrom<MCParticle>();
452 particleHitMap.insert(
453 std::pair<const MCParticle*, const KLMSimHit*>(particle, hit));
454 ++it2;
455 if (it2 == m_MapPlaneSimHit.end())
456 break;
457 if (it2->first != it->first)
458 break;
459 }
460 itParticle = particleHitMap.begin();
461 while (itParticle != particleHitMap.end()) {
462 it2Particle = itParticle;
463 const KLMSimHit* hit = it2Particle->second;
464 channel =
466 hit->getSubdetector(), hit->getSection(), hit->getSector(),
467 hit->getLayer(), hit->getPlane(), hit->getStrip());
468 float efficiency = m_StripEfficiency->getEfficiency(channel);
469 bool hitSelected = efficiencyCorrection(efficiency);
470 while (true) {
471 hit = it2Particle->second;
472 bool rpc = hit->inRPC();
473 if (hitSelected) {
474 for (int s = hit->getStrip(); s <= hit->getLastStrip(); ++s) {
475 channel =
477 hit->getSubdetector(), hit->getSection(), hit->getSector(),
478 hit->getLayer(), hit->getPlane(), s);
479 if (!checkActive(channel))
480 continue;
481 if (rpc) {
482 m_MapChannelSimHit.insert(
483 std::pair<KLMChannelNumber, const KLMSimHit*>(channel, hit));
484 } else {
485 const KLMElectronicsChannel* electronicsChannel =
486 m_ElectronicsMap->getElectronicsChannel(channel);
487 if (electronicsChannel == nullptr)
488 B2FATAL("Incomplete electronics map.");
489 KLMElectronicsChannel asic = electronicsChannel->getAsic();
490 m_MapAsicSimHit.insert(
491 std::pair<KLMElectronicsChannel, const KLMSimHit*>(
492 asic, hit));
493 }
494 }
495 }
496 ++it2Particle;
497 if (it2Particle == particleHitMap.end())
498 break;
499 if (it2Particle->first != itParticle->first)
500 break;
501 }
502 itParticle = it2Particle;
503 }
504 it = it2;
505 }
506 } else {
507 for (i = 0; i < m_SimHits.getEntries(); i++) {
508 const KLMSimHit* hit = m_SimHits[i];
509 if (hit->inRPC()) {
510 if (hit->getStrip() <= 0)
511 continue;
512 for (int s = hit->getStrip(); s <= hit->getLastStrip(); ++s) {
514 hit->getSection(), hit->getSector(), hit->getLayer(),
515 hit->getPlane(), s);
516 if (checkActive(channel)) {
517 m_MapChannelSimHit.insert(
518 std::pair<KLMChannelNumber, const KLMSimHit*>(channel, hit));
519 }
520 }
521 } else {
523 hit->getSubdetector(), hit->getSection(), hit->getSector(),
524 hit->getLayer(), hit->getPlane(), hit->getStrip());
525 if (checkActive(channel)) {
526 const KLMElectronicsChannel* electronicsChannel =
527 m_ElectronicsMap->getElectronicsChannel(channel);
528 if (electronicsChannel == nullptr)
529 B2FATAL("Incomplete electronics map.");
530 KLMElectronicsChannel asic = electronicsChannel->getAsic();
531 m_MapAsicSimHit.insert(
532 std::pair<KLMElectronicsChannel, const KLMSimHit*>(asic, hit));
533 }
534 }
535 }
536 }
537 digitizeRPC();
538 digitizeAsic();
539}
540
542{
543 delete m_Fitter;
544}
545
547{
548}
static int getStripByModule(int module)
Get strip number by module identifier.
KLM channel index.
ChannelStatus
Channel status.
@ c_Dead
Dead channel (no signal).
@ c_Unknown
Unknown status (no data).
KLM digit (class representing a digitized hit in RPCs or scintillators).
Definition: KLMDigit.h:29
void setMCTime(float time)
Set MC time.
Definition: KLMDigit.h:384
void setNGeneratedPhotoelectrons(int nPhotoelectrons)
Set generated number of photoelectrons.
Definition: KLMDigit.h:339
void setLastStrip(int lastStrip)
Set last strip number (for multi-strip digits).
Definition: KLMDigit.h:189
void setSiPMMCTime(float time)
Set SiPM MC time.
Definition: KLMDigit.h:402
void setEnergyDeposit(float eDep)
Set energy deposit.
Definition: KLMDigit.h:303
void setNPhotoelectrons(float nPhotoelectrons)
Set number of photoelectrons.
Definition: KLMDigit.h:321
void setStrip(int strip)
Set strip number.
Definition: KLMDigit.h:171
void setTime(float time)
Set hit time.
Definition: KLMDigit.h:285
void setTDC(uint16_t tdc)
Set TDC.
Definition: KLMDigit.h:267
void setFitStatus(int s)
Set fit status.
Definition: KLMDigit.h:366
void setCharge(uint16_t charge)
Set charge.
Definition: KLMDigit.h:231
std::multimap< KLMElectronicsChannel, const KLMSimHit * > m_MapAsicSimHit
Simulation hit map (by ASIC).
std::multimap< KLMPlaneNumber, const KLMSimHit * > m_MapPlaneSimHit
Simulation hit map (by plane).
KLMDigit * m_AsicDigits[KLM::c_NChannelsAsic]
Digits corresponding to ASIC channels.
EfficiencyMode m_EfficiencyMode
Efficiency determination mode (converted from the string parameter).
StoreArray< KLMDigit > m_Digits
KLM digits.
DBObjPtr< KLMChannelStatus > m_ChannelStatus
Channel status.
DBObjPtr< KLMScintillatorFEEParameters > m_FEEPar
Scintillator FEE parameters.
void initialize() override
Initializer.
bool m_CreateMultiStripDigitsByRun
Whether to create multi-strip digits for one particular run.
bool efficiencyCorrection(float efficiency)
Efficiency correction.
void event() override
This method is called for each event.
const KLMElementNumbers * m_ElementNumbers
Element numbers.
bool m_SaveFPGAFit
Save FPGA fit data (KLMScintillatorFirmwareFitResult).
bool checkActive(KLMChannelNumber channel)
Check if channel is active (status is not KLMChannelStatus::c_Dead).
void endRun() override
This method is called if the current run ends.
DBObjPtr< KLMScintillatorDigitizationParameters > m_DigPar
Scintillator digitization parameters.
std::multimap< KLMChannelNumber, const KLMSimHit * > m_MapChannelSimHit
Simulation hit map (by channel).
void terminate() override
This method is called at the end of the event processing.
bool m_Debug
Use debug mode in EKLM::ScintillatorSimulator or not.
StoreArray< KLMSimHit > m_SimHits
Simulation hits.
void digitizeRPC()
Digitization in RPCs.
int m_DigitizationInitialTime
Initial digitization time in CTIME periods.
std::multimap< KLMChannelNumber, constKLMSimHit * >::iterator m_AsicDigitSimHitsUpperBound[KLM::c_NChannelsAsic]
Simulation hits upper bound for ASIC digit.
void digitizeScintillator()
Digitization in scintillators.
void checkScintillatorFEEParameters()
Check scintillator FEE parameters for channel-specific simulation.
std::string m_Efficiency
Efficiency determination mode ("Strip" or "Plane").
void beginRun() override
Called when entering a new run.
DBObjPtr< KLMScintillatorFirmware > m_ScintillatorFirmware
Scintillator FEE firmware version.
DBObjPtr< KLMElectronicsMap > m_ElectronicsMap
Electronics map.
std::multimap< KLMChannelNumber, constKLMSimHit * >::iterator m_AsicDigitSimHitsLowerBound[KLM::c_NChannelsAsic]
Simulation hits lower bound for ASIC digit.
void digitizeAsic()
Digitization in ASIC.
StoreArray< KLMScintillatorFirmwareFitResult > m_FPGAFits
FPGA fits.
bool m_ChannelSpecificSimulation
Whether the simulation is channel-specific.
KLMTime * m_Time
Time conversion.
bool m_CreateMultiStripDigits
Whether to create multi-strip digits.
DBObjPtr< KLMStripEfficiency > m_StripEfficiency
Strip efficiency.
KLM::ScintillatorFirmware * m_Fitter
FPGA fitter.
std::string m_SimulationMode
Simulation mode.
BKLM electronics channel.
int getChannel() const
Get channel.
KLMElectronicsChannel getAsic() const
Get ASIC.
void setChannel(int channel)
Set channel.
KLM element numbers.
KLMChannelNumber channelNumberBKLM(int section, int sector, int layer, int plane, int strip) const
Get channel number for BKLM.
KLMChannelNumber channelNumber(int subdetector, int section, int sector, int layer, int plane, int strip) const
Get channel number.
KLMPlaneNumber planeNumber(int subdetector, int section, int sector, int layer, int plane) const
Get plane number.
void channelNumberToElementNumbers(KLMChannelNumber channel, int *subdetector, int *section, int *sector, int *layer, int *plane, int *strip) const
Get element numbers by channel number.
int localChannelNumberBKLM(KLMChannelNumber channel) const
Get local BKLM channel number.
float getPhotoelectronAmplitude() const
Get photoelectron amplitude.
int getMinimalAmplitude() const
Get minimal amplitude (ADC output).
int getStartTime() const
Get signal start time (in TDC counts).
FirmwareVersion
Enumerator for the scintillator firmware version.
@ c_Invalid
Flag for marking an invalid version.
@ c_Run1
Flag for Run 1 (from 2019a to 2022b)
@ c_Phase2
Flag for Phase 2 version.
KLM simulation hit.
Definition: KLMSimHit.h:31
KLM time conversion.
Definition: KLMTime.h:27
double getCTimePeriod() const
Get CTIME period.
Definition: KLMTime.h:53
double getTimeSimulation(int tdc, bool scintillator) const
Get time for simulation.
Definition: KLMTime.cc:66
void updateConstants()
Update constants from database objects.
Definition: KLMTime.cc:20
Digitize EKLMSim2Hits to get EKLM StripHits.
float getSiPMMCTime() const
Get SiPM MC time.
void setFEEData(const KLMScintillatorFEEData *FEEData)
Set FEE data.
enum ScintillatorFirmwareFitStatus getFitStatus() const
Get fit status.
double getEnergy()
Get total energy deposited in the strip (sum over ssimulation hits).
double getNPhotoelectrons()
Get number of photoelectrons (fit result).
KLMScintillatorFirmwareFitResult * getFPGAFit()
Get fit data.
int getNGeneratedPhotoelectrons()
Get generated number of photoelectrons.
void simulate(const std::multimap< KLMChannelNumber, const KLMSimHit * >::iterator &firstHit, const std::multimap< KLMChannelNumber, const KLMSimHit * >::iterator &end)
Simulate a strip.
A Class to store the Monte Carlo particle information.
Definition: MCParticle.h:32
int getIndex() const
Get 1-based index of the particle in the corresponding MCParticle list.
Definition: MCParticle.h:230
Base class for Modules.
Definition: Module.h:72
void setDescription(const std::string &description)
Sets the description of the module.
Definition: Module.cc:214
void setPropertyFlags(unsigned int propertyFlags)
Sets the flags for the module properties.
Definition: Module.cc:208
@ c_ParallelProcessingCertified
This module can be run in parallel processing mode safely (All I/O must be done through the data stor...
Definition: Module.h:80
void addRelationTo(const RelationsInterface< BASE > *object, float weight=1.0, const std::string &namedRelation="") const
Add a relation from this object to another object (with caching).
Comparison of MCParticles by index.
bool operator()(const MCParticle *particle1, const MCParticle *particle2) const
Compare MCParticles by index.
Class to store variables with their name which were sent to the logging service.
void addParam(const std::string &name, T &paramVariable, const std::string &description, const T &defaultValue)
Adds a new parameter to the module.
Definition: Module.h:560
#define REG_MODULE(moduleName)
Register the given module (without 'Module' suffix) with the framework.
Definition: Module.h:650
uint16_t KLMChannelNumber
Channel number.
uint16_t KLMPlaneNumber
Plane number.
Abstract base class for different kinds of events.