Belle II Software development
DQMHistAnalysisInput2.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// File : DQMHistAnalysisInput2.cc
10// Description :
11//-
12
13
14#include <dqm/analysis/modules/DQMHistAnalysisInput2.h>
15
16#include <TROOT.h>
17#include <TKey.h>
18
19#include <ctime>
20
21using namespace Belle2;
22
23//-----------------------------------------------------------------
24// Register the Module
25//-----------------------------------------------------------------
26REG_MODULE(DQMHistAnalysisInput2);
27
28//-----------------------------------------------------------------
29// Implementation
30//-----------------------------------------------------------------
31
34{
35 //Parameter definition
36 addParam("HistMemoryPath", m_mempath, "Path to Input Hist memory", std::string(""));
37 addParam("StatFileName", m_statname, "Filename for status export", std::string(""));
38 addParam("RefreshInterval", m_interval, "Refresh interval of histograms", 10);
39 addParam("RemoveEmpty", m_remove_empty, "Remove empty histograms", false);
40 addParam("EnableRunInfo", m_enable_run_info, "Enable Run Info", false);
41 B2DEBUG(1, "DQMHistAnalysisInput2: Constructor done.");
42}
43
45{
47 m_c_info = new TCanvas("DQMInfo/c_info", "");
48 m_c_info->SetTitle("");
49 }
50 m_eventMetaDataPtr.registerInDataStore();
51 B2DEBUG(1, "DQMHistAnalysisInput2: initialized.");
52}
53
54
56{
57 B2DEBUG(1, "DQMHistAnalysisInput2: beginRun called.");
62
63 m_last_beginrun = time(0);
65 m_lasttime -= std::chrono::seconds(1); // just change
66 m_forceChanged = true;
67}
68
70{
71 m_last_event = time(0);
73
74 TH1::AddDirectory(false);
76
77// we create a metadata and set the latest exp/run
78// if do not, execution will be terminate if file is not updated/zombie
79// if we only put dummy exp/run, we trigger begin/endRun ...
80 m_eventMetaDataPtr.create();
81 m_eventMetaDataPtr->setExperiment(m_expno);
83 m_eventMetaDataPtr->setEvent(m_count);
84
85 const std::filesystem::file_time_type ftime = std::filesystem::last_write_time(m_mempath);
86
87 if (m_lasttime == ftime) {
88 B2INFO("File not updated! -> Sleep");
89 sleep(m_interval);
90 setReturnValue(false);
91 return;
92 }
93 m_last_file_update = time(0);
94 m_lasttime = ftime;
95
96 char mbstr[100];
97 time_t now = time(0);
98 strftime(mbstr, sizeof(mbstr), "%F %T", localtime(&now));
99 B2INFO("[" << mbstr << "] before Load File");
100
101 std::unique_ptr<TFile> pFile = std::unique_ptr<TFile> (new TFile(m_mempath.c_str(), "READ"));
102 if (pFile->IsZombie()) {
103 B2WARNING("DQMHistAnalysisInput2: " << m_mempath + " is Zombie -> Sleep");
104 sleep(m_interval);
105 setReturnValue(false);
106 return;
107 }
108
109 now = time(0);
110 strftime(mbstr, sizeof(mbstr), "%F %T", localtime(&now));
111 B2INFO("[" << mbstr << "] after LoadFile");
112
113 const TDatime& mt = pFile->GetModificationDate();
114 TDatime mmt(mt.Convert());
115 std::string expno("UNKNOWN"), runno("UNKNOWN"), rtype("UNKNOWN");
116
117 pFile->cd();
118 TIter next(pFile->GetListOfKeys());
119 TKey* key = nullptr;
120
121 now = time(0);
122 strftime(mbstr, sizeof(mbstr), "%F %T", localtime(&now));
123 B2INFO("[" << mbstr << "] before input loop");
124
125 // check if histograms were updated since last DQM event (based on number of processed events)
126 if (m_nevent != getEventProcessed()) {
127 m_lastChange = std::string(mbstr);
128 }
129 // update number of processed events
131
132 std::vector<TH1*> hs; // temporary histograms storage vector
133
134 while ((key = (TKey*)next())) {
135 auto obj = key->ReadObj(); // I now own this object and have to take care to delete it
136 if (obj == nullptr) continue; // would be strange, but better check
137 if (!obj->IsA()->InheritsFrom("TH1")) {
138 delete obj;
139 continue; // other non supported (yet?)
140 }
141 TH1* h = (TH1*)obj; // we are sure its a TH1
142
143 if (m_remove_empty && h->GetEntries() == 0) {
144 delete obj;
145 continue;
146 }
147 // Remove ":" from folder name, workaround!
148 TString a = h->GetName();
149 a.ReplaceAll(":", "");
150 h->SetName(a);
151 B2DEBUG(1, "DQMHistAnalysisInput2: get histo " << a.Data());
152
153 // the following line prevent any histogram outside a directory to be processed
154 if (StringSplit(a.Data(), '/').size() <= 1) {
155 delete obj;
156 continue;
157 }
158
159 // only Histograms in the hs list will be taken care off
160 hs.push_back(h);
161
162 // the following workaround need to be improved
163 if (std::string(h->GetName()) == std::string("DQMInfo/expno")) expno = h->GetTitle();
164 if (std::string(h->GetName()) == std::string("DQMInfo/runno")) runno = h->GetTitle();
165 if (std::string(h->GetName()) == std::string("DQMInfo/rtype")) rtype = h->GetTitle();
166 }
167
168 now = time(0);
169 strftime(mbstr, sizeof(mbstr), "%F %T", localtime(&now));
170 B2INFO("[" << mbstr << "] before Close File");
171
172 // we are done with reading, so close it
173 pFile->Close();
174
175 now = time(0);
176 strftime(mbstr, sizeof(mbstr), "%F %T", localtime(&now));
177 B2INFO("[" << mbstr << "] before delete File");
178 pFile = nullptr;
179
180 now = time(0);
181 strftime(mbstr, sizeof(mbstr), "%F %T", localtime(&now));
182 B2INFO("[" << mbstr << "] after input loop");
183
184 if (expno == std::string("UNKNOWN") || runno == std::string("UNKNOWN")) {
185 B2WARNING("DQMHistAnalysisInput2: " << m_mempath + ": Exp " + expno + ", Run " + runno + ", RunType " + rtype + ", Last Updated " +
186 mmt.AsString());
187 setReturnValue(false);
188 for (auto& h : hs) delete h;
189 return;
190 } else {
191 if (m_c_info != NULL) m_c_info->SetTitle((m_mempath + ": Exp " + expno + ", Run " + runno + ", RunType " + rtype + ", Last Changed "
192 + m_lastChange + ", Last Updated "
193 + mmt.AsString() + ", Last DQM event " + std::string(mbstr)).c_str());
194 m_expno = std::stoi(expno);
195 m_runno = std::stoi(runno);
196 }
197 B2INFO("DQMHistAnalysisInput2: " << m_mempath + ": Exp " + expno + ", Run " + runno + ", RunType " + rtype + ", Last Updated " +
198 mmt.AsString());
199
200
201 m_count++;
202 // Override with updated values
203 m_eventMetaDataPtr->setExperiment(m_expno);
205 m_eventMetaDataPtr->setEvent(m_count);
206 m_eventMetaDataPtr->setTime(mt.Convert());
207
208 //setExpNr(m_expno); // redundant access from MetaData
209 //setRunNr(m_runno); // redundant access from MetaData
210 // ExtractRunType();// Run Type is processed above already, just take it
211 setRunType(rtype);
212 ExtractEvent(hs);
213
214 // this code must be run after "event processed" has been extracted
215 bool anyupdate = m_forceChanged; // flag if any histogram updated at all
216 m_forceChanged = false;
217 for (auto& h : hs) {
218 anyupdate |= addHist("", h->GetName(), h);
219 B2DEBUG(1, "Found : " << h->GetName() << " : " << h->GetEntries());
220 }
221
222 if (anyupdate) {
223 m_last_content_update = time(0);
224 } else {
225 // if there is no update, sleep a moment
226 sleep(m_interval);
227 }
228
229 // if no histogram was updated, we could stop processing
230 setReturnValue(anyupdate);
231}
232
234{
235 B2DEBUG(1, "DQMHistAnalysisInput2: endRun called");
236}
237
239{
240 B2DEBUG(1, "DQMHistAnalysisInput2: terminate called");
241 if (m_c_info) delete m_c_info;
242 clearlist(); // necessary in the Input Module! Otherwise ROOT may clean before we do
243}
244
246{
247 if (m_statname == "") return;
248 FILE* fh = fopen(m_statname.c_str(), "wt+");
249 if (fh) {
250 char mbstr[100];
251 time_t now = time(0);
252 strftime(mbstr, sizeof(mbstr), "%F %T", localtime(&now));
253 fprintf(fh, "%s,%s,%s,", m_statname.c_str(), m_mempath.c_str(), mbstr);
254 strftime(mbstr, sizeof(mbstr), "%F %T", localtime(&m_last_event));
255 fprintf(fh, "%s,", mbstr);
256 strftime(mbstr, sizeof(mbstr), "%F %T", localtime(&m_last_beginrun));
257 fprintf(fh, "%s,", mbstr);
258 strftime(mbstr, sizeof(mbstr), "%F %T", localtime(&m_last_file_update));
259 fprintf(fh, "%s,", mbstr);
260 strftime(mbstr, sizeof(mbstr), "%F %T", localtime(&m_last_content_update));
261 fprintf(fh, "%s\n", mbstr);
262
263 fclose(fh);
264 }
265}
std::string m_lastChange
last change date/time of shm input file
bool m_remove_empty
Whether to remove empty histograms.
void initialize() override final
Initialize the module.
std::string m_statname
The file name of the analysis for stats.
std::filesystem::file_time_type m_lasttime
Last time input file changes.
bool m_enable_run_info
Whether to enable the run info to be displayed.
void terminate() override final
This method is called at the end of the event processing.
time_t m_last_event
last time event loop entered
void event() override final
This method is called for each event.
bool m_forceChanged
enforce a content change on next event
std::string m_mempath
The name of the shared memory for the histograms.
time_t m_last_file_update
last time input file update detected
time_t m_last_content_update
last time input file content has changed
void endRun() override final
This method is called if the current run ends.
int m_interval
The name of the memory file (HLT or ExpressReco).
void beginRun() override final
Called when entering a new run.
StoreObjPtr< EventMetaData > m_eventMetaDataPtr
The metadata for each event.
TCanvas * m_c_info
The canvas hold the basic DQM info.
int m_nevent
DAQ number of processed events.
time_t m_last_beginrun
last time begin run entered
void write_state(void)
Write stats of analysis.
The base class for the histogram analysis module.
void clearlist(void)
Clear all static global lists.
static void clearHistList(void)
Clears the list of histograms.
std::vector< std::string > StringSplit(const std::string &s, const char delim)
Helper function for string token split.
static void clearRefList(void)
Clears the list of ref histograms.
void setRunType(std::string &t)
Set the Run Type.
static bool addHist(const std::string &dirname, const std::string &histname, TH1 *h)
Add histogram.
void clearCanvases(void)
Clear content of all Canvases.
static int getEventProcessed(void)
Get the number of processed events.
static void initHistListBeforeEvent(void)
Reset the list of histograms.
void ExtractEvent(std::vector< TH1 * > &hs)
Extract event processed from daq histogram, called from input module.
void resetDeltaList(void)
Reset Delta.
void setReturnValue(int value)
Sets the return value for this module as integer.
Definition: Module.cc:220
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
Abstract base class for different kinds of events.