ATLAS Offline Software
Loading...
Searching...
No Matches
CounterChain.cxx
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2026 CERN for the benefit of the ATLAS collaboration
3*/
4
7
8#include "CounterChain.h"
9#include <cstdint>
10
11
12CounterChain::CounterChain(const std::string& name, const MonitorBase* parent)
13 : CounterBase(name, parent), m_isInitialized(false)
14{
15 regHistogram("Group_perCall", "Chain group/Call;Group;Calls", VariableType::kPerCall, kLinear, -0.5, 9.5, 10);
16 regHistogram("Chain_perEvent", "Chain calls/Event;Chain call;Events", VariableType::kPerEvent, kLinear, -0.5, 49.5);
17 regHistogram("AlgCalls_perEvent", "Algorithm Calls/Event;Calls;Events", VariableType::kPerEvent, kLinear, -0.5, 999.5, 100);
18 regHistogram("Time_perCall", "CPU Time/Call;Time [ms];Calls", VariableType::kPerCall, kLog, 0.01, 100000);
19 regHistogram("Time_perEvent", "CPU Time/Event;Time [ms];Events", VariableType::kPerEvent);
20 regHistogram("UniqueTime_perCall", "Unique CPU Time/Call;Time [ms];Calls", VariableType::kPerCall, kLog, 0.01, 100000);
21 regHistogram("ChainPassed_perEvent", "Passed chain/Event;Passsed;Events", VariableType::kPerEvent, kLinear, -0.5, 1.5, 2);
22 regHistogram("Request_perEvent", "Number of requests/Event;Number of requests;Events", VariableType::kPerEvent, LogType::kLinear, -0.5, 299.5, 300);
23 regHistogram("NetworkRequest_perEvent", "Number of network requests/Event;Number of requests;Events", VariableType::kPerEvent, LogType::kLinear, -0.5, 149.5, 150);
24 regHistogram("CachedROBSize_perEvent", "Cached ROB Size/Event;ROB size;Events", VariableType::kPerEvent, LogType::kLinear, 0, 1024, 50);
25 regHistogram("NetworkROBSize_perEvent", "Network ROB Size/Event;ROB size;Events", VariableType::kPerEvent, LogType::kLinear, 0, 1024, 50);
26 regHistogram("RequestTime_perEvent", "ROB Elapsed Time/Event;Elapsed Time [ms];Events", VariableType::kPerEvent);
27}
28
29CounterChain::CounterChain(const std::string& name, unsigned nRos, const MonitorBase* parent)
30 : CounterChain(name, parent)
31{
32 regTProfile("ROSRequests_perEvent", "Number of ROS requests;ROS names;Numer of requests to ROS per event", VariableType::kPerCall, LogType::kLinear, 0, nRos, nRos);
33 regTProfile("NetworkROSRequests_perEvent", "Number of network ROS requests;ROS names;Numer of requests to ROS over the network per event", VariableType::kPerCall, LogType::kLinear, 0, nRos, nRos);
34 regTProfile("ROBRequestsPerROS_perEvent", "Number of ROBs per ROS requests;ROS names;Numer of ROBs requested per request", VariableType::kPerCall, LogType::kLinear, 0, nRos, nRos);
35 regTProfile("ROBRequestsPerROSPerEvent_perEvent", "Number of ROBs per ROS requests per event;ROS names;Numer of ROBs requested by ROS per event", VariableType::kPerCall, LogType::kLinear, 0, nRos, nRos);
36}
37
38
39StatusCode CounterChain::newEvent(const CostData& data, size_t index, const float weight) {
40
41 ATH_CHECK( increment("Chain_perEvent", weight) );
42
43 if (!m_isInitialized && variableExists("ROSRequests_perEvent")) {
44 // Set histograms labels
45 for (const auto& rosToRobPair : data.costROSData().getROStoROBMap()) {
46 int binForROS = data.costROSData().getBinForROS(rosToRobPair.first) + 1;
47 ATH_CHECK( getVariable("ROSRequests_perEvent").setBinLabel(binForROS, rosToRobPair.first));
48 ATH_CHECK( getVariable("NetworkROSRequests_perEvent").setBinLabel(binForROS, rosToRobPair.first));
49 ATH_CHECK( getVariable("ROBRequestsPerROS_perEvent").setBinLabel(binForROS, rosToRobPair.first));
50 ATH_CHECK( getVariable("ROBRequestsPerROSPerEvent_perEvent").setBinLabel(binForROS, rosToRobPair.first));
51 }
52
53 // Fill the bins with groups and add the labels
54 int bin = 1;
55 for (const std::string& group : data.seededChains()[index].groups){
56 ATH_CHECK( getVariable("Group_perCall").setBinLabel(bin, group) );
57 ATH_CHECK( getVariable("Group_perCall").fill(group, weight) );
58 ++bin;
59 }
60
61 m_isInitialized = true;
62 }
63
64 if (data.seededChains()[index].isPassRaw){
65 ATH_CHECK( increment("ChainPassed_perEvent", weight) );
66 }
67
68 // Monitor algorithms associated with chain name
69 if (!data.chainToAlgMap().count(getName())) return StatusCode::SUCCESS;
70
71 std::map<std::string, int> nRosPerEvent; // Accumulate how many times ROS was requested in a request per this event
72 std::map<std::string, int> nNetworkRosPerEvent; // Accumulate how many times ROS was requested in a request per this event
73 std::map<std::string, int> nRobsPerRosPerEvent; // Accumulate how many ROBs ROS requested per this event
74 const std::string slotStr{"slot"};
75 const std::string startStr{"start"};
76 const std::string stopStr{"stop"};
77 for (const size_t algIndex : data.chainToAlgMap().at(getName())){
78 const xAOD::TrigComposite* alg = data.costCollection().at(algIndex);
79 const uint32_t slot = alg->getDetail<uint32_t>(slotStr);
80 if (slot != data.onlineSlot()) {
81 continue; // When monitoring the master slot, this Monitor ignores algs running in different slots
82 }
83
84 ATH_CHECK( increment("AlgCalls_perEvent", weight) );
85
86 const uint64_t start = alg->getDetail<uint64_t>(startStr); // in mus
87 const uint64_t stop = alg->getDetail<uint64_t>(stopStr); // in mus
88 const float cpuTime = timeToMilliSec(start, stop);
89 ATH_CHECK( fill("Time_perEvent", cpuTime, weight) );
90 ATH_CHECK( fill("Time_perCall", cpuTime, weight) );
91
92 // Monitor data requests
93 if (!data.algToRequestMap().count(algIndex)) continue;
94 static const std::string idStr{"robs_id"};
95 static const std::string historyStr{"robs_history"};
96 static const std::string sizeStr{"robs_size"};
97 for (size_t requestIdx : data.algToRequestMap().at(algIndex)) {
98 const xAOD::TrigComposite* request = data.rosCollection().at(requestIdx);
99 const std::vector<uint32_t> robIdsPerRequest = request->getDetail<std::vector<uint32_t>>(idStr);
100 const std::vector<unsigned> robs_history = request->getDetail<std::vector<unsigned>>(historyStr);
101 const std::vector<uint32_t> robs_size = request->getDetail<std::vector<uint32_t>>(sizeStr);
102
103 std::map<std::string, int> nRobsPerRosPerRequest; // Accumulate how many ROBs ROS requested per request
104
105 bool networkRequestIncremented = false;
106 std::set<std::string> requestedROSes;
107 std::set<std::string> requestedNetworkROSes;
108 for (size_t i = 0; i < robs_size.size(); ++i) {
109 // ROB request was fetched over the network
110 if (robs_history[i] == robmonitor::RETRIEVED) {
111 // size is stored in words, should be in kilobytes
112 ATH_CHECK( fill("NetworkROBSize_perEvent", robs_size[i] / 500., weight) );
113 networkRequestIncremented = true;
114 }
115 // ROB request was cached
116 else if (robs_history[i] == robmonitor::HLT_CACHED || robs_history[i] == robmonitor::DCM_CACHED) {
117 ATH_CHECK( fill("CachedROBSize_perEvent", robs_size[i] / 500., weight) );
118 }
119
120 uint32_t robId = robIdsPerRequest[i];
121 if (variableExists("ROBRequestsPerROS_perEvent")){
122 std::string rosForROB = data.costROSData().getROSForROB(robId);
123 if (!rosForROB.empty()){
124 requestedROSes.insert(rosForROB);
125 nRobsPerRosPerRequest[rosForROB] += 1;
126 nRobsPerRosPerEvent[rosForROB] += 1;
127
128 if (robs_history[i] == robmonitor::RETRIEVED) {
129 requestedNetworkROSes.insert(std::move(rosForROB));
130 }
131 }
132 }
133 }
134
135 // Save number of ROBs per ROS per request
136 for (const auto& robPerRosPair : nRobsPerRosPerRequest) {
137 ATH_CHECK( fill("ROBRequestsPerROS_perEvent", data.costROSData().getBinForROS(robPerRosPair.first), robPerRosPair.second, weight) );
138 }
139
140 // Save the requested ROSes per request
141 for (const std::string& rosName : requestedROSes){
142 nRosPerEvent[rosName] += 1;
143 }
144
145 for (const std::string& rosName : requestedNetworkROSes){
146 nNetworkRosPerEvent[rosName] += 1;
147 }
148
149 ATH_CHECK( increment("Request_perEvent", weight) );
150
151 if (networkRequestIncremented) {
152 ATH_CHECK( increment("NetworkRequest_perEvent", weight) );
153 }
154
155 const float rosTime = timeToMilliSec(request->getDetail<uint64_t>("start"), request->getDetail<uint64_t>("stop"));
156 ATH_CHECK( fill("RequestTime_perEvent", rosTime, weight) );
157 }
158 }
159
160 // Save the requested ROSes per event
161 for (const auto& robPerRosPair : nRosPerEvent) {
162 ATH_CHECK( fill("ROSRequests_perEvent", data.costROSData().getBinForROS(robPerRosPair.first), robPerRosPair.second, weight) );
163 }
164
165 for (const auto& robPerRosPair : nNetworkRosPerEvent) {
166 ATH_CHECK( fill("NetworkROSRequests_perEvent", data.costROSData().getBinForROS(robPerRosPair.first), robPerRosPair.second, weight) );
167 }
168
169 // Save the number of ROBs per ROS per event
170 for (const auto& robPerRosPair : nRobsPerRosPerEvent) {
171 ATH_CHECK( fill("ROBRequestsPerROSPerEvent_perEvent", data.costROSData().getBinForROS(robPerRosPair.first), robPerRosPair.second, weight) );
172 }
173
174 // Monitor unique algorithms associated with chain name
175 if (!data.chainToUniqAlgMap().count(getName())) return StatusCode::SUCCESS;
176
177 for (const size_t algIndex : data.chainToUniqAlgMap().at(getName())){
178 const xAOD::TrigComposite* alg = data.costCollection().at(algIndex);
179 const uint32_t slot = alg->getDetail<uint32_t>(slotStr);
180 if (slot != data.onlineSlot()) {
181 continue;
182 }
183 const uint64_t start = alg->getDetail<uint64_t>(startStr); // in mus
184 const uint64_t stop = alg->getDetail<uint64_t>(stopStr); // in mus
185 const float cpuTime = timeToMilliSec(start, stop);
186
187 ATH_CHECK( fill("UniqueTime_perCall", cpuTime, weight) );
188 }
189
190 return StatusCode::SUCCESS;
191}
#define ATH_CHECK
Evaluate an expression and check for errors.
@ kPerEvent
Variable should buffer fill calls in an accumulator and fill the underlying histogram once at the end...
Definition Variable.h:21
@ kPerCall
Variable should fill underlying histogram on each fill.
Definition Variable.h:20
@ kLinear
Linear x-binning.
Definition Variable.h:29
@ kLog
Logarithmic x-binning.
Definition Variable.h:30
Caches and propagates event data to be used by monitoring algorithms.
Definition CostData.h:26
float timeToMilliSec(const uint64_t start, const uint64_t stop) const
Helper function.
CounterBase()=delete
Forbid default constructor.
StatusCode increment(std::string_view name, float weight=1.0)
Convenience function.
void regTProfile(const std::string &name, const std::string &title, const VariableType type=VariableType::kPerCall, const LogType xaxis=kLog, const float min=0.1, const float max=1000000., const size_t bins=70)
Book a TProfile for this Counter, to be filled in per-event monitoring.
void regHistogram(const std::string &name, const std::string &title, const VariableType type=VariableType::kPerCall, const LogType xaxis=kLog, const float min=0.1, const float max=1000000., const size_t bins=70)
Book a histogram for this Counter, to be filled in per-event monitoring.
const std::string & getName() const
Getter for Counter's name.
bool variableExists(const std::string &name) const
Check if a variable of a given name exists.
Variable & getVariable(std::string_view name)
Returns a mutable reference to a named Variable.
StatusCode fill(std::string_view name, float value, float weight=1.0)
Fill (for per-Call) or accumulate in a buffer (for per-Event) a quantity histogrammed by a named Vari...
virtual StatusCode newEvent(const CostData &data, size_t index, const float weight=1.) override
Concrete implimentation.
CounterChain()=delete
Forbid default constructor.
bool m_isInitialized
bool getDetail(const std::string &name, TYPE &value) const
Get an TYPE detail from the object.
Definition index.py:1
TrigComposite_v1 TrigComposite
Declare the latest version of the class.