Belle II Software development
TOPLaserCalibratorCollectorModule.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#include <top/modules/TOPLaserCalibratorCollector/TOPLaserCalibratorCollectorModule.h>
10
11//ROOT
12#include <TTree.h>
13#include <TMath.h>
14
15//TOP
16#include <top/dataobjects/TOPDigit.h>
17#include <top/dataobjects/TOPRawDigit.h>
18#include <top/dataobjects/TOPSimHit.h>
19
20#include <algorithm>
21#include <vector>
22
23using namespace Belle2;
24
25REG_MODULE(TOPLaserCalibratorCollector);
26
28{
29 // Set module properties
30 setDescription("Collector module for the TOP ChannelT0 calibration and the quality monitoring using laser and pulser data");
32
33 addParam("useReferencePulse", m_useReferencePulse, "Use the pulser as reference", bool(false));
34 addParam("refChannel", m_refChannel, "Channel to be used as reference");
35 addParam("refSlot", m_refSlot, "Slot to be used as reference");
36 addParam("pulserDeltaT", m_pulserDeltaT, "Approximate time difference between the two calpulses, in ns", float(21.8));
37 addParam("pulserDeltaTTolerance", m_pulserDeltaTTolerance, "Window around the nominal deltaT used to select a double pulse, in ns ",
38 float(2.));
39 addParam("storeMCTruth", m_storeMCTruth, " Store the TOPSimHits information instead of the TOPDigit one. \
40 If this option is used, useReferencePulse will be automatically set to false.");
41
42}
43
44
45
47{
48
49 // Create the output trees
50
51 auto hitTree = new TTree("hitTree", "hitTree");
52 hitTree->Branch<short>("channel", &m_channel);
53 hitTree->Branch<short>("asic", &m_asic);
54 hitTree->Branch<short>("asicChannel", &m_asicChannel);
55 hitTree->Branch<short>("boardstack", &m_boardstack);
56 hitTree->Branch<short>("slot", &m_slot);
57 hitTree->Branch<float>("hitTime", &m_hitTime);
58 hitTree->Branch<float>("dVdt", &m_dVdt);
59 hitTree->Branch<float>("refTime", &m_refTime);
60 hitTree->Branch<float>("amplitude", &m_amplitude);
61 hitTree->Branch<float>("width", &m_width);
62 hitTree->Branch<short>("sample", &m_sample);
63 hitTree->Branch<short>("window", &m_window);
64 hitTree->Branch<int>("event", &m_event);
65 hitTree->Branch<bool>("refTimeValid", &m_refTimeValid);
66
67 registerObject<TTree>("hitTree", hitTree);
68
69 m_TOPDigitArray.isRequired();
70
72 m_useReferencePulse = false;
73
74 m_event = 0;
75}
76
77
81{
82 float refTimes[16] = {0.}; // Reference time for each slot
83 std::vector<bool> refTimesValid(16, true);
84
85 // first loop over TOPDigits to find all the pairs of digits that satisfy the double-pulse conditions
87
88 std::vector<float> calPulseTimes[16];
89 for (const auto& digit : m_TOPDigitArray) {
90 if (digit.getHitQuality() != TOPDigit::c_CalPulse or digit.getChannel() != m_refChannel)
91 continue; // remove photons and everything not on the ref channel
92 calPulseTimes[digit.getModuleID() - 1].push_back(digit.getTime());
93 }
94
95 for (int i = 0; i < 16; i++) {
96 refTimesValid[i] = false;
97 auto& calTimes = calPulseTimes[i];
98 if (calTimes.size() < 2) continue;
99 std::sort(calTimes.begin(), calTimes.end());
100 for (unsigned k = 0; k < calTimes.size() - 1; k++) {
101 auto t1 = calTimes[k];
102 auto t2 = calTimes[k + 1];
103 if (fabs(fabs(t2 - t1) - m_pulserDeltaT) < m_pulserDeltaTTolerance) {
104 refTimes[i] = t1;
105 refTimesValid[i] = true;
106 break;
107 }
108 }
109 }
110
111 }
112
113 TTree* hitTree = getObjectPtr<TTree>("hitTree");
114
115 // then fill the tree with good digits (photons and cal pulses)
116 for (const auto& digit : m_TOPDigitArray) {
117 if (digit.getHitQuality() == TOPDigit::c_Junk) continue; // remove the bad hits
118 m_channel = digit.getChannel();
119 m_slot = digit.getModuleID(); // this is 1-based
120 m_asic = digit.getASICNumber();
121 m_asicChannel = digit.getASICChannel();
122 m_boardstack = digit.getBoardstackNumber();
123 m_dVdt = 0.5 * TMath::Sqrt(-2.*TMath::Log(0.5)) * digit.getPulseHeight() / digit.getPulseWidth();
124
125 if (m_refSlot > 0) {
126 m_refTime = refTimes[m_refSlot - 1];
127 m_refTimeValid = refTimesValid[m_refSlot - 1];
128 } else {
129 m_refTime = refTimes[m_slot - 1];
130 m_refTimeValid = refTimesValid[m_slot - 1];
131 }
132
133 m_amplitude = digit.getPulseHeight() ;
134 m_width = digit.getPulseWidth();
135
136 if (m_storeMCTruth) {
137 const auto* simHit = digit.getRelated<TOPSimHit>();
138 if (not simHit) continue; // no tree entry if MC truth doesn't exist
139 m_hitTime = simHit->getTime();
140 } else {
141 m_hitTime = digit.getTime() - m_refTime;
142 }
143
144 m_window = -1;
145 const auto* rawDigit = digit.getRelated<TOPRawDigit>();
146 if (rawDigit) m_window = rawDigit->getASICWindow(); // window from which the feature is extracted
147 m_sample = digit.getModulo256Sample(); // sample number referred in TBC
148 hitTree->Fill();
149 }
150 m_event++;
151}
void registerObject(const std::string &name, T *obj)
Register object with a name, takes ownership, do not access the pointer beyond prepare()
T * getObjectPtr(const std::string &name)
Calls the CalibObjManager to get the requested stored collector data.
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
TOPLaserCalibratorCollectorModule()
Constructor: Sets the description, the properties and the parameters of the module.
StoreArray< TOPDigit > m_TOPDigitArray
Required input array of TOPDigits.
bool m_storeMCTruth
Store the TOPSimHits information instead of the TOPDigit one.
float m_hitTime
Hit time with respect to the reference pulse (ns)
short m_asic
ASIC number (0-3 within boardstack)
float m_pulserDeltaTTolerance
Window around the nominal deltaT used to select a double pulse, in ns.
void collect() override
Main method, called for each event.
bool m_useReferencePulse
Use the electronic pulser as reference.
bool m_refTimeValid
true when the time of the reference pulse is valid
float m_pulserDeltaT
Approximate time difference between the two calpulses, in ns.
Class to store unpacked raw data (hits in feature-extraction format) It provides also calculation of ...
Definition TOPRawDigit.h:24
Class to store simulated hits of Cherenkov photons on PMT's input for digitization module (TOPDigitiz...
Definition TOPSimHit.h:27
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:559
#define REG_MODULE(moduleName)
Register the given module (without 'Module' suffix) with the framework.
Definition Module.h:649
Abstract base class for different kinds of events.