CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Pages
DQMStore.cc
Go to the documentation of this file.
7 #include "classlib/utils/RegexpMatch.h"
8 #include "classlib/utils/Regexp.h"
9 #include "classlib/utils/StringOps.h"
10 #include <google/protobuf/io/coded_stream.h>
11 #include <google/protobuf/io/gzip_stream.h>
12 #include <google/protobuf/io/zero_copy_stream_impl.h>
13 #include "TFile.h"
14 #include "TROOT.h"
15 #include "TKey.h"
16 #include "TClass.h"
17 #include "TSystem.h"
18 #include "TBufferFile.h"
19 #include <iterator>
20 #include <cerrno>
21 #include <boost/algorithm/string.hpp>
22 
23 #include <fstream>
24 #include <sstream>
25 #include <exception>
26 
53 static const std::string s_monitorDirName = "DQMData";
56 static const std::string s_referenceDirName = "Reference";
57 static const std::string s_collateDirName = "Collate";
58 static const std::string s_safe = "/ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-+=_()# ";
59 
60 static const lat::Regexp s_rxmeval ("^<(.*)>(i|f|s|e|t|qr)=(.*)</\\1>$");
61 static const lat::Regexp s_rxmeqr1 ("^st:(\\d+):([-+e.\\d]+):([^:]*):(.*)$");
62 static const lat::Regexp s_rxmeqr2 ("^st\\.(\\d+)\\.(.*)$");
63 static const lat::Regexp s_rxtrace ("(.*)\\((.*)\\+0x.*\\).*");
64 static const lat::Regexp s_rxpbfile (".*\\.pb$");
65 
69 static bool
71 {
72  return (ofdir.empty()
73  || (path.size() >= ofdir.size()
74  && path.compare(0, ofdir.size(), ofdir) == 0
75  && (path.size() == ofdir.size()
76  || path[ofdir.size()] == '/')));
77 }
78 
79 static void
81 {
82  clean.clear();
83  cleaned = &path;
84 
85  size_t len = path.size();
86  for ( ; len > 0 && path[len-1] == '/'; --len)
87  ;
88 
89  if (len != path.size())
90  {
91  clean = path.substr(0, len);
92  cleaned = &clean;
93  }
94 }
95 
96 static void
98 {
99  size_t slash = path.rfind('/');
100  if (slash != std::string::npos)
101  {
102  dir.append(path, 0, slash);
103  name.append(path, slash+1, std::string::npos);
104  }
105  else
106  name = path;
107 }
108 
109 static void
111 {
112  path.reserve(dir.size() + name.size() + 2);
113  path += dir;
114  if (! path.empty())
115  path += '/';
116  path += name;
117 }
118 
119 template <class T>
120 QCriterion *
122 { return new T(qtname); }
123 
124 template <class T>
125 void
127 { m[T::getAlgoName()] = &makeQCriterion<T>; }
128 
129 
131 fastmatch::fastmatch (std::string const& _fastString) :
132  fastString_ (_fastString), matching_ (UseFull)
133 {
134  try
135  {
136  regexp_ = NULL;
137  regexp_ = new lat::Regexp(fastString_, 0, lat::Regexp::Wildcard);
138  regexp_->study();
139  }
140  catch (lat::Error &e)
141  {
142  delete regexp_;
143  raiseDQMError("DQMStore", "Invalid wildcard pattern '%s' in quality"
144  " test specification", fastString_.c_str());
145  }
146 
147  // count stars ( "*" )
148  size_t starCount = 0;
149  int pos = -1;
150  while (true)
151  {
152  pos = fastString_.find("*", pos + 1 );
153  if ((size_t)pos == std::string::npos)
154  break;
155  starCount ++;
156  }
157 
158  // investigate for heuristics
159  if ((fastString_.find('"') != std::string::npos) ||
160  (fastString_.find(']') != std::string::npos) ||
161  (fastString_.find('?') != std::string::npos) ||
162  (fastString_.find('\\') != std::string::npos) ||
163  (starCount > 2))
164  {
165  // no fast version can be used
166  return;
167  }
168 
169  // match for pattern "*MyString" and "MyString*"
170  if (starCount == 1)
171  {
172  if (boost::algorithm::starts_with(fastString_, "*"))
173  {
175  fastString_.erase(0,1);
176  return;
177  }
178 
179  if (boost::algorithm::ends_with(fastString_, "*"))
180  {
182  fastString_.erase(fastString_.length()-1,1);
183  return;
184  }
185  }
186 
187  // match for pattern "*MyString*"
188  if (starCount == 2)
189  {
190  if (boost::algorithm::starts_with(fastString_, "*") &&
191  boost::algorithm::ends_with(fastString_, "*"))
192  {
193  matching_ = TwoStar;
194  fastString_.erase(0,1);
195  fastString_.erase(fastString_.size() - 1, 1);
196  return;
197  }
198  }
199 }
200 
202 {
203  if (regexp_ != NULL)
204  delete regexp_;
205 }
206 
208  std::string const& input) const
209 {
210  if (input.size() < pattern.size())
211  return false;
212 
213  // compare the two strings character by character for equalness:
214  // this does not create uneeded copies of std::string. The
215  // boost::algorithm implementation does
216  std::string::const_reverse_iterator rit_pattern = pattern.rbegin();
217  std::string::const_reverse_iterator rit_input = input.rbegin();
218 
219  for (; rit_pattern < pattern.rend(); rit_pattern++, rit_input++)
220  {
221  if (*rit_pattern != *rit_input)
222  // found a difference, fail
223  return false;
224  }
225  return true;
226 }
227 
229  std::string const& input) const
230 {
231  if (input.size() < pattern.size())
232  return false;
233 
234  // compare the two strings character by character for equalness:
235  // this does not create uneeded copies of std::string. The
236  // boost::algorithm implementation does.
237  std::string::const_iterator rit_pattern = pattern.begin();
238  std::string::const_iterator rit_input = input.begin();
239 
240  for (; rit_pattern < pattern.end(); rit_pattern++, rit_input++)
241  {
242  if (*rit_pattern != *rit_input)
243  // found a difference, fail
244  return false;
245  }
246  return true;
247 }
248 
249 bool fastmatch::match(std::string const& s) const
250 {
251  switch (matching_)
252  {
253  case OneStarStart:
255 
256  case OneStarEnd:
257  return compare_strings(fastString_, s);
258 
259  case TwoStar:
260  return (s.find(fastString_) != std::string::npos);
261 
262  default:
263  return regexp_->match(s);
264  }
265 }
266 
267 //IBooker methods
269  owner_->cd();
270 }
271 
273  owner_->cd(dir);
274 }
275 
277  owner_->setCurrentFolder(fullpath);
278 }
279 
281  owner_->goUp();
282 }
283 
285  return owner_->pwd();
286 }
287 
288 void DQMStore::IBooker::tag(MonitorElement *me, unsigned int tag) {
289  owner_->tag(me, tag);
290 }
291 
292 void DQMStore::IBooker::tagContents(const std::string &path, unsigned int myTag) {
293  owner_->tagContents(path, myTag);
294 }
295 
296 //IGetter methods
297 std::vector<MonitorElement*>
299  uint32_t runNumber /* = 0 */,
300  uint32_t lumi /* = 0 */) {
301  return owner_->getAllContents(path, runNumber, lumi);
302 }
303 
305  return owner_->get(path);
306 }
307 
309  MonitorElement *ptr = this->get(path);
310  if (ptr == nullptr) {
311  std::stringstream msg;
312  msg << "DQM object not found";
313 
314  msg << ": " << path;
315 
316  // can't use cms::Exception inside DQMStore
317  throw std::out_of_range(msg.str());
318  }
319  return ptr;
320 }
321 
322 std::vector<std::string> DQMStore::IGetter::getSubdirs(void) {
323  return owner_->getSubdirs();
324 }
325 
326 std::vector<std::string> DQMStore::IGetter::getMEs(void) {
327  return owner_->getMEs();
328 }
329 
331  return owner_->containsAnyMonitorable(path);
332 }
333 
335  return owner_->dirExists(path);
336 }
337 
339  owner_->cd();
340 }
341 
343  owner_->cd(dir);
344 }
345 
347  owner_->setCurrentFolder(fullpath);
348 }
349 
360  uint32_t streamId,
361  uint32_t moduleId) {
362  if (verbose_ > 1)
363  std::cout << "DQMStore::mergeAndResetMEsRunSummaryCache - Merging objects from run: "
364  << run
365  << ", stream: " << streamId
366  << " module: " << moduleId << std::endl;
367 
368  if (LSbasedMode_) {
369  return;
370  }
371 
372  std::string null_str("");
373  MonitorElement proto(&null_str, null_str, run, streamId, moduleId);
374  std::set<MonitorElement>::const_iterator e = data_.end();
375  std::set<MonitorElement>::const_iterator i = data_.lower_bound(proto);
376  while (i != e) {
377  if (i->data_.run != run
378  || i->data_.streamId != streamId
379  || i->data_.moduleId != moduleId)
380  break;
381 
382  // Handle Run-based histograms only.
383  if (i->getLumiFlag() || LSbasedMode_) {
384  ++i;
385  continue;
386  }
387 
388  // don't call the copy constructor
389  // we are just searching for a global histogram - a copy is not necessary
390  MonitorElement global_me(*i, MonitorElementNoCloneTag());
391  global_me.globalize();
392 
393  // Since this accesses the data, the operation must be
394  // be locked.
395  std::lock_guard<std::mutex> guard(book_mutex_);
396  std::set<MonitorElement>::const_iterator me = data_.find(global_me);
397  if (me != data_.end()) {
398  if (verbose_ > 1)
399  std::cout << "Found global Object, using it --> " << me->getFullname() << std::endl;
400 
401  //don't take any action if the ME is an INT || FLOAT || STRING
402  if(me->kind() >= MonitorElement::DQM_KIND_TH1F)
403  {
404  if(me->getTH1()->CanExtendAllAxes() && i->getTH1()->CanExtendAllAxes()) {
405  TList list;
406  list.Add(i->getTH1());
407  if( -1 == me->getTH1()->Merge(&list)) {
408  std::cout << "mergeAndResetMEsRunSummaryCache: Failed to merge DQM element "<<me->getFullname();
409  }
410  }
411  else
412  me->getTH1()->Add(i->getTH1());
413  }
414  } else {
415  if (verbose_ > 1)
416  std::cout << "No global Object found. " << std::endl;
417  std::pair<std::set<MonitorElement>::const_iterator, bool> gme;
418 
419  // this makes an actual and a single copy with Clone()'ed th1
420  MonitorElement actual_global_me(*i);
421  actual_global_me.globalize();
422  gme = data_.insert(std::move(actual_global_me));
423  assert(gme.second);
424  }
425  // TODO(rovere): eventually reset the local object and mark it as reusable??
426  ++i;
427  }
428 }
429 
431  uint32_t lumi,
432  uint32_t streamId,
433  uint32_t moduleId) {
434  if (verbose_ > 1)
435  std::cout << "DQMStore::mergeAndResetMEsLuminositySummaryCache - Merging objects from run: "
436  << run << " lumi: " << lumi
437  << ", stream: " << streamId
438  << " module: " << moduleId << std::endl;
439  std::string null_str("");
440  MonitorElement proto(&null_str, null_str, run, streamId, moduleId);
441  std::set<MonitorElement>::const_iterator e = data_.end();
442  std::set<MonitorElement>::const_iterator i = data_.lower_bound(proto);
443 
444  while (i != e) {
445  if (i->data_.run != run
446  || i->data_.streamId != streamId
447  || i->data_.moduleId != moduleId)
448  break;
449 
450  // Handle LS-based histograms only.
451  if (not (i->getLumiFlag() || LSbasedMode_)) {
452  ++i;
453  continue;
454  }
455 
456  MonitorElement global_me(*i, MonitorElementNoCloneTag());
457  global_me.globalize();
458  global_me.setLumi(lumi);
459  // Since this accesses the data, the operation must be
460  // be locked.
461  std::lock_guard<std::mutex> guard(book_mutex_);
462  std::set<MonitorElement>::const_iterator me = data_.find(global_me);
463  if (me != data_.end()) {
464  if (verbose_ > 1)
465  std::cout << "Found global Object, using it --> " << me->getFullname() << std::endl;
466 
467  //don't take any action if the ME is an INT || FLOAT || STRING
468  if(me->kind() >= MonitorElement::DQM_KIND_TH1F)
469  {
470  if(me->getTH1()->CanExtendAllAxes() && i->getTH1()->CanExtendAllAxes()) {
471  TList list;
472  list.Add(i->getTH1());
473  if( -1 == me->getTH1()->Merge(&list)) {
474  std::cout << "mergeAndResetMEsLuminositySummaryCache: Failed to merge DQM element "<<me->getFullname();
475  }
476  }
477  else
478  me->getTH1()->Add(i->getTH1());
479  }
480  } else {
481  if (verbose_ > 1)
482  std::cout << "No global Object found. " << std::endl;
483  std::pair<std::set<MonitorElement>::const_iterator, bool> gme;
484 
485  // this makes an actual and a single copy with Clone()'ed th1
486  MonitorElement actual_global_me(*i);
487  actual_global_me.globalize();
488  actual_global_me.setLumi(lumi);
489  gme = data_.insert(std::move(actual_global_me));
490  assert(gme.second);
491  }
492  // make the ME reusable for the next LS
493  const_cast<MonitorElement*>(&*i)->Reset();
494  ++i;
495  }
496 }
497 
500  : verbose_ (1),
501  verboseQT_ (1),
502  reset_ (false),
507  run_(0),
508  streamId_(0),
509  moduleId_(0),
510  stream_(nullptr),
511  pwd_ (""),
512  ibooker_(0),
513  igetter_(0)
514 {
515  if (!ibooker_)
516  ibooker_ = new DQMStore::IBooker(this);
517  if (!igetter_)
518  igetter_ = new DQMStore::IGetter(this);
519  initializeFrom(pset);
520 
521  if(pset.getUntrackedParameter<bool>("forceResetOnBeginRun",false)) {
523  }
524  ar.preallocateSignal_.connect([this](edm::service::SystemBounds const& iBounds) {
525  if(iBounds.maxNumberOfStreams() > 1 ) {
526  enableMultiThread_ = true;
527  }
528  });
529  if(pset.getUntrackedParameter<bool>("forceResetOnBeginLumi",false) && enableMultiThread_ == false) {
530  forceResetOnBeginLumi_ = true;
532  }
533 }
534 
536  : verbose_ (1),
537  verboseQT_ (1),
538  reset_ (false),
539  collateHistograms_ (false),
540  enableMultiThread_(false),
541  readSelectedDirectory_ (""),
542  run_(0),
543  streamId_(0),
544  moduleId_(0),
545  stream_(nullptr),
546  pwd_ (""),
547  ibooker_(0),
548  igetter_(0)
549 {
550  if (!ibooker_)
551  ibooker_ = new DQMStore::IBooker(this);
552  if (!igetter_)
553  igetter_ = new DQMStore::IGetter(this);
554  initializeFrom(pset);
555 }
556 
558 {
559  for (QCMap::iterator i = qtests_.begin(), e = qtests_.end(); i != e; ++i)
560  delete i->second;
561 
562  for (QTestSpecs::iterator i = qtestspecs_.begin(), e = qtestspecs_.end(); i != e; ++i)
563  delete i->first;
564 
565  if (stream_)
566  stream_->close();
567  delete stream_;
568 }
569 
570 void
572  makeDirectory("");
573  reset();
574 
575  // set steerable parameters
576  verbose_ = pset.getUntrackedParameter<int>("verbose", 0);
577  if (verbose_ > 0)
578  std::cout << "DQMStore: verbosity set to " << verbose_ << std::endl;
579 
580  verboseQT_ = pset.getUntrackedParameter<int>("verboseQT", 0);
581  if (verbose_ > 0)
582  std::cout << "DQMStore: QTest verbosity set to " << verboseQT_ << std::endl;
583 
584  collateHistograms_ = pset.getUntrackedParameter<bool>("collateHistograms", false);
585  if (collateHistograms_)
586  std::cout << "DQMStore: histogram collation is enabled\n";
587 
588  enableMultiThread_ = pset.getUntrackedParameter<bool>("enableMultiThread", false);
589  if (enableMultiThread_)
590  std::cout << "DQMStore: MultiThread option is enabled\n";
591 
592  LSbasedMode_ = pset.getUntrackedParameter<bool>("LSbasedMode", false);
593  if (LSbasedMode_)
594  std::cout << "DQMStore: LSbasedMode option is enabled\n";
595 
596  std::string ref = pset.getUntrackedParameter<std::string>("referenceFileName", "");
597  if (! ref.empty())
598  {
599  std::cout << "DQMStore: using reference file '" << ref << "'\n";
600  readFile(ref, true, "", s_referenceDirName, StripRunDirs, false);
601  }
602 
603  initQCriterion<Comp2RefChi2>(qalgos_);
604  initQCriterion<Comp2RefKolmogorov>(qalgos_);
605  initQCriterion<ContentsXRange>(qalgos_);
606  initQCriterion<ContentsYRange>(qalgos_);
607  initQCriterion<MeanWithinExpected>(qalgos_);
608  initQCriterion<Comp2RefEqualH>(qalgos_);
609  initQCriterion<DeadChannel>(qalgos_);
610  initQCriterion<NoisyChannel>(qalgos_);
611  initQCriterion<ContentsWithinExpected>(qalgos_);
612  initQCriterion<CompareToMedian>(qalgos_);
613  initQCriterion<CompareLastFilledBin>(qalgos_);
614  initQCriterion<CheckVariance>(qalgos_);
615 
616  scaleFlag_ = pset.getUntrackedParameter<double>("ScalingFlag", 0.0);
617  if (verbose_ > 0)
618  std::cout << "DQMStore: Scaling Flag set to " << scaleFlag_ << std::endl;
619 }
620 
621 /* Generic method to do a backtrace and print it to stdout. It is
622  customised to properly get the routine that called the booking of the
623  histograms, which, following the usual stack, is at position 4. The
624  name of the calling function is properly demangled and the original
625  shared library including this function is also printed. For a more
626  detailed explanation of the routines involved, see here:
627  http://www.gnu.org/software/libc/manual/html_node/Backtraces.html
628  http://gcc.gnu.org/onlinedocs/libstdc++/manual/ext_demangling.html.*/
629 
630 void
632 {
633  // the access to the member stream_ is implicitely protected against
634  // concurrency problems because the print_trace method is always called behind
635  // a lock (see bookTransaction).
636  if (!stream_)
637  stream_ = new std::ofstream("histogramBookingBT.log");
638 
639  void *array[10];
640  size_t size;
641  char **strings;
642  int r=0;
643  lat::RegexpMatch m;
644  m.reset();
645 
646  size = backtrace (array, 10);
647  strings = backtrace_symbols (array, size);
648 
649  if ((size > 4)
650  &&s_rxtrace.match(strings[4], 0, 0, &m))
651  {
652  char * demangled = abi::__cxa_demangle(m.matchString(strings[4], 2).c_str(), 0, 0, &r);
653  *stream_ << "\"" << dir << "/"
654  << name << "\" "
655  << (r ? m.matchString(strings[4], 2) : demangled) << " "
656  << m.matchString(strings[4], 1) << "\n";
657  free(demangled);
658  }
659  else
660  *stream_ << "Skipping "<< dir << "/" << name
661  << " with stack size " << size << "\n";
662  /* In this case print the full stack trace, up to main or to the
663  * maximum stack size, i.e. 10. */
664  if (verbose_ > 4)
665  {
666  size_t i;
667  m.reset();
668 
669  for (i = 0; i < size; i++)
670  if (s_rxtrace.match(strings[i], 0, 0, &m))
671  {
672  char * demangled = abi::__cxa_demangle(m.matchString(strings[i], 2).c_str(), 0, 0, &r);
673  *stream_ << "\t\t" << i << "/" << size << " "
674  << (r ? m.matchString(strings[i], 2) : demangled) << " "
675  << m.matchString(strings[i], 1) << std::endl;
676  free (demangled);
677  }
678  }
679  free (strings);
680 }
681 
686 void
687 DQMStore::setVerbose(unsigned /* level */)
688 { return; }
689 
694 const std::string &
695 DQMStore::pwd(void) const
696 { return pwd_; }
697 
699 void
701 { setCurrentFolder(""); }
702 
704 void
705 DQMStore::cd(const std::string &subdir)
706 {
708  const std::string *cleaned = 0;
709  cleanTrailingSlashes(subdir, clean, cleaned);
710 
711  if (! dirExists(*cleaned))
712  raiseDQMError("DQMStore", "Cannot 'cd' into non-existent directory '%s'",
713  cleaned->c_str());
714 
715  setCurrentFolder(*cleaned);
716 }
717 
722 void
724 {
726  const std::string *cleaned = 0;
727  cleanTrailingSlashes(fullpath, clean, cleaned);
728  makeDirectory(*cleaned);
729  pwd_ = *cleaned;
730 }
731 
733 void
735 {
736  size_t pos = pwd_.rfind('/');
737  if (pos == std::string::npos)
738  setCurrentFolder("");
739  else
740  setCurrentFolder(pwd_.substr(0, pos));
741 }
742 
743 // -------------------------------------------------------------------
746 void
748 {
749  std::string prev;
750  std::string subdir;
752  prev.reserve(path.size());
753  subdir.reserve(path.size());
754  name.reserve(path.size());
755  size_t prevname = 0;
756  size_t slash = 0;
757 
758  while (true)
759  {
760  // Create this subdirectory component.
761  subdir.clear();
762  subdir.append(path, 0, slash);
763  name.clear();
764  name.append(subdir, prevname, std::string::npos);
765  if (! prev.empty() && findObject(prev, name))
766  raiseDQMError("DQMStore", "Attempt to create subdirectory '%s'"
767  " which already exists as a monitor element",
768  subdir.c_str());
769 
770  if (! dirs_.count(subdir))
771  dirs_.insert(subdir);
772 
773  // Stop if we've reached the end (including possibly a trailing slash).
774  if (slash+1 >= path.size())
775  break;
776 
777  // Find the next slash, making sure we progress. If reach the end,
778  // process the last path component; the next loop round will terminate.
779  prevname = slash ? slash+1 : slash;
780  prev = subdir;
781  if ((slash = path.find('/', ++slash)) == std::string::npos)
782  slash = path.size();
783  }
784 }
785 
787 bool
789 { return dirs_.count(path) > 0; }
790 
794 template <class HISTO, class COLLATE>
797  const char *context, int kind,
798  HISTO *h, COLLATE collate)
799 {
800  assert(name.find('/') == std::string::npos);
801  if (verbose_ > 3)
802  print_trace(dir, name);
804  mergePath(path, dir, name);
805 
806  // Put us in charge of h.
807  h->SetDirectory(0);
808 
809  // Check if the request monitor element already exists.
810  MonitorElement *me = findObject(dir, name, run_, 0, streamId_, moduleId_);
811  if (me)
812  {
813  if (collateHistograms_)
814  {
815  collate(me, h, verbose_);
816  delete h;
817  return me;
818  }
819  else
820  {
821  if (verbose_ > 1)
822  std::cout << "DQMStore: "
823  << context << ": monitor element '"
824  << path << "' already exists, collating" << std::endl;
825  me->Reset();
826  collate(me, h, verbose_);
827  delete h;
828  return me;
829  }
830  }
831  else
832  {
833  // Create and initialise core object.
834  assert(dirs_.count(dir));
835  MonitorElement proto(&*dirs_.find(dir), name, run_, streamId_, moduleId_);
836  me = const_cast<MonitorElement &>(*data_.insert(std::move(proto)).first)
838 
839  // Initialise quality test information.
840  QTestSpecs::iterator qi = qtestspecs_.begin();
841  QTestSpecs::iterator qe = qtestspecs_.end();
842  for ( ; qi != qe; ++qi)
843  {
844  if ( qi->first->match(path) )
845  me->addQReport(qi->second);
846  }
847 
848  // If we just booked a (plain) MonitorElement, and there is a reference
849  // MonitorElement with the same name, link the two together.
850  // The other direction is handled by the extract method.
851  std::string refdir;
852  refdir.reserve(s_referenceDirName.size() + dir.size() + 1);
853  refdir += s_referenceDirName;
854  refdir += '/';
855  refdir += dir;
856  MonitorElement* referenceME = findObject(refdir, name);
857  if (referenceME) {
858  // We have booked a new MonitorElement with a specific dir and name.
859  // Then, if we can find the corresponding MonitorElement in the reference
860  // dir we assign the object_ of the reference MonitorElement to the
861  // reference_ property of our new MonitorElement.
862  me->data_.flags |= DQMNet::DQM_PROP_HAS_REFERENCE;
863  me->reference_ = referenceME->object_;
864  }
865 
866  // Return the monitor element.
867  return me;
868  }
869 }
870 
873  const std::string &name,
874  const char *context)
875 {
876  assert(name.find('/') == std::string::npos);
877  if (verbose_ > 3)
878  print_trace(dir, name);
879 
880  // Check if the request monitor element already exists.
881  if (MonitorElement *me = findObject(dir, name, run_, 0, streamId_, moduleId_))
882  {
883  if (verbose_ > 1)
884  {
886  mergePath(path, dir, name);
887 
888  std::cout << "DQMStore: "
889  << context << ": monitor element '"
890  << path << "' already exists, resetting" << std::endl;
891  }
892  me->Reset();
893  return me;
894  }
895  else
896  {
897  // Create it and return for initialisation.
898  assert(dirs_.count(dir));
899  MonitorElement proto(&*dirs_.find(dir), name, run_, streamId_, moduleId_);
900  return &const_cast<MonitorElement &>(*data_.insert(std::move(proto)).first);
901  }
902 }
903 
904 // -------------------------------------------------------------------
908 {
909  if (collateHistograms_)
910  {
911  if (MonitorElement *me = findObject(dir, name, run_, 0, streamId_, moduleId_))
912  {
913  me->Fill(0);
914  return me;
915  }
916  }
917 
918  return book(dir, name, "bookInt")
920 }
921 
925 { return bookInt(pwd_, name); }
926 
930 {
931  return bookInt(pwd_, name);
932 }
933 
934 // -------------------------------------------------------------------
938 {
939  if (collateHistograms_)
940  {
941  if (MonitorElement *me = findObject(dir, name, run_, 0, streamId_, moduleId_))
942  {
943  me->Fill(0.);
944  return me;
945  }
946  }
947 
948  return book(dir, name, "bookFloat")
950 }
951 
955 { return bookFloat(pwd_, name); }
956 
960 {
961  return bookFloat(pwd_, name);
962 }
963 
964 // -------------------------------------------------------------------
968  const std::string &name,
969  const std::string &value)
970 {
971  if (collateHistograms_)
972  {
973  if (MonitorElement *me = findObject(dir, name, run_, 0, streamId_, moduleId_))
974  return me;
975  }
976 
977  return book(dir, name, "bookString")
979 }
980 
983 DQMStore::bookString(const char *name, const char *value)
984 { return bookString(pwd_, name, value); }
985 
989 {
990  return bookString(pwd_, name, value);
991 }
992 
993 // -------------------------------------------------------------------
997 {
998  return book(dir, name, "book1D", MonitorElement::DQM_KIND_TH1F, h, collate1D);
999 }
1000 
1004 {
1005  return book(dir, name, "book1S", MonitorElement::DQM_KIND_TH1S, h, collate1S);
1006 }
1007 
1011 {
1012  return book(dir, name, "book1DD", MonitorElement::DQM_KIND_TH1D, h, collate1DD);
1013 }
1014 
1017 DQMStore::book1D(const char *name, const char *title,
1018  int nchX, double lowX, double highX)
1019 {
1020  return book1D(pwd_, name, new TH1F(name, title, nchX, lowX, highX));
1021 }
1022 
1026  int nchX, double lowX, double highX)
1027 {
1028  return book1D(pwd_, name, new TH1F(name.c_str(), title.c_str(), nchX, lowX, highX));
1029 }
1030 
1033 DQMStore::book1S(const char *name, const char *title,
1034  int nchX, double lowX, double highX)
1035 {
1036  return book1S(pwd_, name, new TH1S(name, title, nchX, lowX, highX));
1037 }
1038 
1042  int nchX, double lowX, double highX)
1043 {
1044  return book1S(pwd_, name, new TH1S(name.c_str(), title.c_str(), nchX, lowX, highX));
1045 }
1046 
1049 DQMStore::book1DD(const char *name, const char *title,
1050  int nchX, double lowX, double highX)
1051 {
1052  return book1DD(pwd_, name, new TH1D(name, title, nchX, lowX, highX));
1053 }
1054 
1058  int nchX, double lowX, double highX)
1059 {
1060  return book1DD(pwd_, name, new TH1D(name.c_str(), title.c_str(), nchX, lowX, highX));
1061 }
1062 
1065 DQMStore::book1D(const char *name, const char *title,
1066  int nchX, const float *xbinsize)
1067 {
1068  return book1D(pwd_, name, new TH1F(name, title, nchX, xbinsize));
1069 }
1070 
1074  int nchX, const float *xbinsize)
1075 {
1076  return book1D(pwd_, name, new TH1F(name.c_str(), title.c_str(), nchX, xbinsize));
1077 }
1078 
1081 DQMStore::book1D(const char *name, TH1F *source)
1082 {
1083  return book1D(pwd_, name, static_cast<TH1F *>(source->Clone(name)));
1084 }
1085 
1089 {
1090  return book1D(pwd_, name, static_cast<TH1F *>(source->Clone(name.c_str())));
1091 }
1092 
1095 DQMStore::book1S(const char *name, TH1S *source)
1096 {
1097  return book1S(pwd_, name, static_cast<TH1S *>(source->Clone(name)));
1098 }
1099 
1103 {
1104  return book1S(pwd_, name, static_cast<TH1S *>(source->Clone(name.c_str())));
1105 }
1106 
1109 DQMStore::book1DD(const char *name, TH1D *source)
1110 {
1111  return book1DD(pwd_, name, static_cast<TH1D *>(source->Clone(name)));
1112 }
1113 
1117 {
1118  return book1DD(pwd_, name, static_cast<TH1D *>(source->Clone(name.c_str())));
1119 }
1120 
1121 // -------------------------------------------------------------------
1125 {
1126  return book(dir, name, "book2D", MonitorElement::DQM_KIND_TH2F, h, collate2D);
1127 }
1128 
1132 {
1133  return book(dir, name, "book2S", MonitorElement::DQM_KIND_TH2S, h, collate2S);
1134 }
1135 
1139 {
1140  return book(dir, name, "book2DD", MonitorElement::DQM_KIND_TH2D, h, collate2DD);
1141 }
1142 
1145 DQMStore::book2D(const char *name, const char *title,
1146  int nchX, double lowX, double highX,
1147  int nchY, double lowY, double highY)
1148 {
1149  return book2D(pwd_, name, new TH2F(name, title,
1150  nchX, lowX, highX,
1151  nchY, lowY, highY));
1152 }
1153 
1157  int nchX, double lowX, double highX,
1158  int nchY, double lowY, double highY)
1159 {
1160  return book2D(pwd_, name, new TH2F(name.c_str(), title.c_str(),
1161  nchX, lowX, highX,
1162  nchY, lowY, highY));
1163 }
1164 
1167 DQMStore::book2S(const char *name, const char *title,
1168  int nchX, double lowX, double highX,
1169  int nchY, double lowY, double highY)
1170 {
1171  return book2S(pwd_, name, new TH2S(name, title,
1172  nchX, lowX, highX,
1173  nchY, lowY, highY));
1174 }
1175 
1179  int nchX, double lowX, double highX,
1180  int nchY, double lowY, double highY)
1181 {
1182  return book2S(pwd_, name, new TH2S(name.c_str(), title.c_str(),
1183  nchX, lowX, highX,
1184  nchY, lowY, highY));
1185 }
1186 
1189 DQMStore::book2DD(const char *name, const char *title,
1190  int nchX, double lowX, double highX,
1191  int nchY, double lowY, double highY)
1192 {
1193  return book2DD(pwd_, name, new TH2D(name, title,
1194  nchX, lowX, highX,
1195  nchY, lowY, highY));
1196 }
1197 
1201  int nchX, double lowX, double highX,
1202  int nchY, double lowY, double highY)
1203 {
1204  return book2DD(pwd_, name, new TH2D(name.c_str(), title.c_str(),
1205  nchX, lowX, highX,
1206  nchY, lowY, highY));
1207 }
1208 
1211 DQMStore::book2D(const char *name, const char *title,
1212  int nchX, const float *xbinsize, int nchY, const float *ybinsize)
1213 {
1214  return book2D(pwd_, name, new TH2F(name, title,
1215  nchX, xbinsize, nchY, ybinsize));
1216 }
1217 
1221  int nchX, const float *xbinsize, int nchY, const float *ybinsize)
1222 {
1223  return book2D(pwd_, name, new TH2F(name.c_str(), title.c_str(),
1224  nchX, xbinsize, nchY, ybinsize));
1225 }
1226 
1229 DQMStore::book2D(const char *name, TH2F *source)
1230 {
1231  return book2D(pwd_, name, static_cast<TH2F *>(source->Clone(name)));
1232 }
1233 
1237 {
1238  return book2D(pwd_, name, static_cast<TH2F *>(source->Clone(name.c_str())));
1239 }
1240 
1243 DQMStore::book2S(const char *name, TH2S *source)
1244 {
1245  return book2S(pwd_, name, static_cast<TH2S *>(source->Clone(name)));
1246 }
1247 
1251 {
1252  return book2S(pwd_, name, static_cast<TH2S *>(source->Clone(name.c_str())));
1253 }
1254 
1257 DQMStore::book2DD(const char *name, TH2D *source)
1258 {
1259  return book2DD(pwd_, name, static_cast<TH2D *>(source->Clone(name)));
1260 }
1261 
1265 {
1266  return book2DD(pwd_, name, static_cast<TH2D *>(source->Clone(name.c_str())));
1267 }
1268 
1269 // -------------------------------------------------------------------
1273 {
1274  return book(dir, name, "book3D", MonitorElement::DQM_KIND_TH3F, h, collate3D);
1275 }
1276 
1279 DQMStore::book3D(const char *name, const char *title,
1280  int nchX, double lowX, double highX,
1281  int nchY, double lowY, double highY,
1282  int nchZ, double lowZ, double highZ)
1283 {
1284  return book3D(pwd_, name, new TH3F(name, title,
1285  nchX, lowX, highX,
1286  nchY, lowY, highY,
1287  nchZ, lowZ, highZ));
1288 }
1289 
1293  int nchX, double lowX, double highX,
1294  int nchY, double lowY, double highY,
1295  int nchZ, double lowZ, double highZ)
1296 {
1297  return book3D(pwd_, name, new TH3F(name.c_str(), title.c_str(),
1298  nchX, lowX, highX,
1299  nchY, lowY, highY,
1300  nchZ, lowZ, highZ));
1301 }
1302 
1305 DQMStore::book3D(const char *name, TH3F *source)
1306 {
1307  return book3D(pwd_, name, static_cast<TH3F *>(source->Clone(name)));
1308 }
1309 
1313 {
1314  return book3D(pwd_, name, static_cast<TH3F *>(source->Clone(name.c_str())));
1315 }
1316 
1317 // -------------------------------------------------------------------
1321 {
1322  return book(dir, name, "bookProfile",
1324  h, collateProfile);
1325 }
1326 
1331 DQMStore::bookProfile(const char *name, const char *title,
1332  int nchX, double lowX, double highX,
1333  int /* nchY */, double lowY, double highY,
1334  const char *option /* = "s" */)
1335 {
1336  return bookProfile(pwd_, name, new TProfile(name, title,
1337  nchX, lowX, highX,
1338  lowY, highY,
1339  option));
1340 }
1341 
1347  int nchX, double lowX, double highX,
1348  int /* nchY */, double lowY, double highY,
1349  const char *option /* = "s" */)
1350 {
1351  return bookProfile(pwd_, name, new TProfile(name.c_str(), title.c_str(),
1352  nchX, lowX, highX,
1353  lowY, highY,
1354  option));
1355 }
1356 
1361 DQMStore::bookProfile(const char *name, const char *title,
1362  int nchX, double lowX, double highX,
1363  double lowY, double highY,
1364  const char *option /* = "s" */)
1365 {
1366  return bookProfile(pwd_, name, new TProfile(name, title,
1367  nchX, lowX, highX,
1368  lowY, highY,
1369  option));
1370 }
1371 
1377  int nchX, double lowX, double highX,
1378  double lowY, double highY,
1379  const char *option /* = "s" */)
1380 {
1381  return bookProfile(pwd_, name, new TProfile(name.c_str(), title.c_str(),
1382  nchX, lowX, highX,
1383  lowY, highY,
1384  option));
1385 }
1386 
1391 DQMStore::bookProfile(const char *name, const char *title,
1392  int nchX, const double *xbinsize,
1393  int /* nchY */, double lowY, double highY,
1394  const char *option /* = "s" */)
1395 {
1396  return bookProfile(pwd_, name, new TProfile(name, title,
1397  nchX, xbinsize,
1398  lowY, highY,
1399  option));
1400 }
1401 
1407  int nchX, const double *xbinsize,
1408  int /* nchY */, double lowY, double highY,
1409  const char *option /* = "s" */)
1410 {
1411  return bookProfile(pwd_, name, new TProfile(name.c_str(), title.c_str(),
1412  nchX, xbinsize,
1413  lowY, highY,
1414  option));
1415 }
1416 
1421 DQMStore::bookProfile(const char *name, const char *title,
1422  int nchX, const double *xbinsize,
1423  double lowY, double highY,
1424  const char *option /* = "s" */)
1425 {
1426  return bookProfile(pwd_, name, new TProfile(name, title,
1427  nchX, xbinsize,
1428  lowY, highY,
1429  option));
1430 }
1431 
1437  int nchX, const double *xbinsize,
1438  double lowY, double highY,
1439  const char *option /* = "s" */)
1440 {
1441  return bookProfile(pwd_, name, new TProfile(name.c_str(), title.c_str(),
1442  nchX, xbinsize,
1443  lowY, highY,
1444  option));
1445 }
1446 
1449 DQMStore::bookProfile(const char *name, TProfile *source)
1450 {
1451  return bookProfile(pwd_, name, static_cast<TProfile *>(source->Clone(name)));
1452 }
1453 
1457 {
1458  return bookProfile(pwd_, name, static_cast<TProfile *>(source->Clone(name.c_str())));
1459 }
1460 
1461 // -------------------------------------------------------------------
1465 {
1466  return book(dir, name, "bookProfile2D",
1468  h, collateProfile2D);
1469 }
1470 
1475 DQMStore::bookProfile2D(const char *name, const char *title,
1476  int nchX, double lowX, double highX,
1477  int nchY, double lowY, double highY,
1478  int /* nchZ */, double lowZ, double highZ,
1479  const char *option /* = "s" */)
1480 {
1481  return bookProfile2D(pwd_, name, new TProfile2D(name, title,
1482  nchX, lowX, highX,
1483  nchY, lowY, highY,
1484  lowZ, highZ,
1485  option));
1486 }
1487 
1493  int nchX, double lowX, double highX,
1494  int nchY, double lowY, double highY,
1495  int /* nchZ */, double lowZ, double highZ,
1496  const char *option /* = "s" */)
1497 {
1498  return bookProfile2D(pwd_, name, new TProfile2D(name.c_str(), title.c_str(),
1499  nchX, lowX, highX,
1500  nchY, lowY, highY,
1501  lowZ, highZ,
1502  option));
1503 }
1504 
1509 DQMStore::bookProfile2D(const char *name, const char *title,
1510  int nchX, double lowX, double highX,
1511  int nchY, double lowY, double highY,
1512  double lowZ, double highZ,
1513  const char *option /* = "s" */)
1514 {
1515  return bookProfile2D(pwd_, name, new TProfile2D(name, title,
1516  nchX, lowX, highX,
1517  nchY, lowY, highY,
1518  lowZ, highZ,
1519  option));
1520 }
1521 
1527  int nchX, double lowX, double highX,
1528  int nchY, double lowY, double highY,
1529  double lowZ, double highZ,
1530  const char *option /* = "s" */)
1531 {
1532  return bookProfile2D(pwd_, name, new TProfile2D(name.c_str(), title.c_str(),
1533  nchX, lowX, highX,
1534  nchY, lowY, highY,
1535  lowZ, highZ,
1536  option));
1537 }
1538 
1541 DQMStore::bookProfile2D(const char *name, TProfile2D *source)
1542 {
1543  return bookProfile2D(pwd_, name, static_cast<TProfile2D *>(source->Clone(name)));
1544 }
1545 
1549 {
1550  return bookProfile2D(pwd_, name, static_cast<TProfile2D *>(source->Clone(name.c_str())));
1551 }
1552 
1556 bool
1558 {
1559  if (me->getTH1()->GetNbinsX() != h->GetNbinsX()
1560  || me->getTH1()->GetNbinsY() != h->GetNbinsY()
1561  || me->getTH1()->GetNbinsZ() != h->GetNbinsZ()
1562  || me->getTH1()->GetXaxis()->GetXmin() != h->GetXaxis()->GetXmin()
1563  || me->getTH1()->GetYaxis()->GetXmin() != h->GetYaxis()->GetXmin()
1564  || me->getTH1()->GetZaxis()->GetXmin() != h->GetZaxis()->GetXmin()
1565  || me->getTH1()->GetXaxis()->GetXmax() != h->GetXaxis()->GetXmax()
1566  || me->getTH1()->GetYaxis()->GetXmax() != h->GetYaxis()->GetXmax()
1567  || me->getTH1()->GetZaxis()->GetXmax() != h->GetZaxis()->GetXmax()
1568  || !MonitorElement::CheckBinLabels((TAxis*)me->getTH1()->GetXaxis(),(TAxis*)h->GetXaxis())
1569  || !MonitorElement::CheckBinLabels((TAxis*)me->getTH1()->GetYaxis(),(TAxis*)h->GetYaxis())
1570  || !MonitorElement::CheckBinLabels((TAxis*)me->getTH1()->GetZaxis(),(TAxis*)h->GetZaxis()) )
1571  {
1572  if(verbose > 0)
1573  std::cout << "*** DQMStore: WARNING:"
1574  << "checkBinningMatches: different binning - cannot add object '"
1575  << h->GetName() << "' of type "
1576  << h->IsA()->GetName() << " to existing ME: '"
1577  << me->getFullname() << "'\n";
1578  return false;
1579  }
1580  return true;
1581 }
1582 
1583 void
1585 {
1586  if (checkBinningMatches(me,h,verbose))
1587  me->getTH1F()->Add(h);
1588 }
1589 
1590 void
1592 {
1593  if (checkBinningMatches(me,h,verbose))
1594  me->getTH1S()->Add(h);
1595 }
1596 
1597 void
1599 {
1600  if (checkBinningMatches(me,h,verbose))
1601  me->getTH1D()->Add(h);
1602 }
1603 
1604 void
1606 {
1607  if (checkBinningMatches(me,h,verbose))
1608  me->getTH2F()->Add(h);
1609 }
1610 
1611 void
1613 {
1614  if (checkBinningMatches(me,h,verbose))
1615  me->getTH2S()->Add(h);
1616 }
1617 
1618 void
1620 {
1621  if (checkBinningMatches(me,h,verbose))
1622  me->getTH2D()->Add(h);
1623 }
1624 
1625 void
1627 {
1628  if (checkBinningMatches(me,h,verbose))
1629  me->getTH3F()->Add(h);
1630 }
1631 
1632 void
1634 {
1635  if (checkBinningMatches(me,h,verbose))
1636  {
1637  TProfile *meh = me->getTProfile();
1638  me->addProfiles(h, meh, meh, 1, 1);
1639  }
1640 }
1641 
1642 void
1644 {
1645  if (checkBinningMatches(me,h,verbose))
1646  {
1647  TProfile2D *meh = me->getTProfile2D();
1648  me->addProfiles(h, meh, meh, 1, 1);
1649  }
1650 }
1651 
1656 void
1657 DQMStore::tag(MonitorElement *me, unsigned int myTag)
1658 {
1659  if (! myTag)
1660  raiseDQMError("DQMStore", "Attempt to tag monitor element '%s'"
1661  " with a zero tag", me->getFullname().c_str());
1662  if ((me->data_.flags & DQMNet::DQM_PROP_TAGGED) && myTag != me->data_.tag)
1663  raiseDQMError("DQMStore", "Attempt to tag monitor element '%s'"
1664  " twice with multiple tags", me->getFullname().c_str());
1665 
1666  me->data_.tag = myTag;
1668 }
1669 
1671 void
1672 DQMStore::tag(const std::string &path, unsigned int myTag)
1673 {
1674  std::string dir;
1675  std::string name;
1676  splitPath(dir, name, path);
1677 
1678  if (MonitorElement *me = findObject(dir, name))
1679  tag(me, myTag);
1680  else
1681  raiseDQMError("DQMStore", "Attempt to tag non-existent monitor element"
1682  " '%s' with tag %u", path.c_str(), myTag);
1683 
1684 }
1685 
1687 void
1688 DQMStore::tagContents(const std::string &path, unsigned int myTag)
1689 {
1690  MonitorElement proto(&path, std::string());
1691  MEMap::iterator e = data_.end();
1692  MEMap::iterator i = data_.lower_bound(proto);
1693  for ( ; i != e && path == *i->data_.dirname; ++i)
1694  tag(const_cast<MonitorElement *>(&*i), myTag);
1695 }
1696 
1699 void
1700 DQMStore::tagAllContents(const std::string &path, unsigned int myTag)
1701 {
1703  const std::string *cleaned = 0;
1704  cleanTrailingSlashes(path, clean, cleaned);
1705  MonitorElement proto(cleaned, std::string());
1706 
1707  // FIXME: WILDCARDS? Old one supported them, but nobody seemed to use them.
1708  MEMap::iterator e = data_.end();
1709  MEMap::iterator i = data_.lower_bound(proto);
1710  while (i != e && isSubdirectory(*cleaned, *i->data_.dirname))
1711  {
1712  tag(const_cast<MonitorElement *>(&*i), myTag);
1713  ++i;
1714  }
1715 }
1716 
1721 std::vector<std::string>
1723 {
1724  std::vector<std::string> result;
1725  std::set<std::string>::const_iterator e = dirs_.end();
1726  std::set<std::string>::const_iterator i = dirs_.find(pwd_);
1727 
1728  // If we didn't find current directory, the tree is empty, so quit.
1729  if (i == e)
1730  return result;
1731 
1732  // Skip the current directory and then start looking for immediate
1733  // subdirectories in the dirs_ list. Stop when we are no longer in
1734  // (direct or indirect) subdirectories of pwd_. Note that we don't
1735  // "know" which order the set will sort A/B, A/B/C and A/D.
1736  while (++i != e && isSubdirectory(pwd_, *i))
1737  if (i->find('/', pwd_.size()+1) == std::string::npos)
1738  result.push_back(*i);
1739 
1740  return result;
1741 }
1742 
1744 std::vector<std::string>
1745 DQMStore::getMEs(void) const
1746 {
1747  MonitorElement proto(&pwd_, std::string());
1748  std::vector<std::string> result;
1749  MEMap::const_iterator e = data_.end();
1750  MEMap::const_iterator i = data_.lower_bound(proto);
1751  for ( ; i != e && isSubdirectory(pwd_, *i->data_.dirname); ++i)
1752  if (pwd_ == *i->data_.dirname)
1753  result.push_back(i->getName());
1754 
1755  return result;
1756 }
1757 
1760 bool
1762 {
1763  MonitorElement proto(&path, std::string());
1764  MEMap::const_iterator e = data_.end();
1765  MEMap::const_iterator i = data_.lower_bound(proto);
1766  return (i != e && isSubdirectory(path, *i->data_.dirname));
1767 }
1768 
1772 {
1773  std::string dir;
1774  std::string name;
1775  splitPath(dir, name, path);
1776  MonitorElement proto(&dir, name);
1777  MEMap::const_iterator mepos = data_.find(proto);
1778  return (mepos == data_.end() ? 0
1779  : const_cast<MonitorElement *>(&*mepos));
1780 }
1781 
1783 std::vector<MonitorElement *>
1784 DQMStore::get(unsigned int tag) const
1785 {
1786  // FIXME: Use reverse map [tag -> path] / [tag -> dir]?
1787  std::vector<MonitorElement *> result;
1788  for (MEMap::const_iterator i = data_.begin(), e = data_.end(); i != e; ++i)
1789  {
1790  const MonitorElement &me = *i;
1791  if ((me.data_.flags & DQMNet::DQM_PROP_TAGGED) && me.data_.tag == tag)
1792  result.push_back(const_cast<MonitorElement *>(&me));
1793  }
1794  return result;
1795 }
1796 
1799 std::vector<MonitorElement *>
1801 {
1803  const std::string *cleaned = 0;
1804  cleanTrailingSlashes(path, clean, cleaned);
1805  MonitorElement proto(cleaned, std::string());
1806 
1807  std::vector<MonitorElement *> result;
1808  MEMap::const_iterator e = data_.end();
1809  MEMap::const_iterator i = data_.lower_bound(proto);
1810  for ( ; i != e && isSubdirectory(*cleaned, *i->data_.dirname); ++i)
1811  if (*cleaned == *i->data_.dirname)
1812  result.push_back(const_cast<MonitorElement *>(&*i));
1813 
1814  return result;
1815 }
1816 
1818 std::vector<MonitorElement *>
1819 DQMStore::getContents(const std::string &path, unsigned int tag) const
1820 {
1822  const std::string *cleaned = 0;
1823  cleanTrailingSlashes(path, clean, cleaned);
1824  MonitorElement proto(cleaned, std::string());
1825 
1826  std::vector<MonitorElement *> result;
1827  MEMap::const_iterator e = data_.end();
1828  MEMap::const_iterator i = data_.lower_bound(proto);
1829  for ( ; i != e && isSubdirectory(*cleaned, *i->data_.dirname); ++i)
1830  if (*cleaned == *i->data_.dirname
1831  && (i->data_.flags & DQMNet::DQM_PROP_TAGGED)
1832  && i->data_.tag == tag)
1833  result.push_back(const_cast<MonitorElement *>(&*i));
1834 
1835  return result;
1836 }
1837 
1842 void
1843 DQMStore::getContents(std::vector<std::string> &into, bool showContents /* = true */) const
1844 {
1845  into.clear();
1846  into.reserve(dirs_.size());
1847 
1848  MEMap::const_iterator me = data_.end();
1849  std::set<std::string>::const_iterator di = dirs_.begin();
1850  std::set<std::string>::const_iterator de = dirs_.end();
1851  for ( ; di != de; ++di)
1852  {
1853  MonitorElement proto(&*di, std::string());
1854  MEMap::const_iterator mi = data_.lower_bound(proto);
1855  MEMap::const_iterator m = mi;
1856  size_t sz = di->size() + 2;
1857  size_t nfound = 0;
1858  for ( ; m != me && isSubdirectory(*di, *m->data_.dirname); ++m)
1859  if (*di == *m->data_.dirname)
1860  {
1861  sz += m->data_.objname.size() + 1;
1862  ++nfound;
1863  }
1864 
1865  if (! nfound)
1866  continue;
1867 
1868  std::vector<std::string>::iterator istr
1869  = into.insert(into.end(), std::string());
1870 
1871  if (showContents)
1872  {
1873  istr->reserve(sz);
1874 
1875  *istr += *di;
1876  *istr += ':';
1877  for (sz = 0; mi != m; ++mi)
1878  {
1879  if (*di != *mi->data_.dirname)
1880  continue;
1881 
1882  if (sz > 0)
1883  *istr += ',';
1884 
1885  *istr += mi->data_.objname;
1886  ++sz;
1887  }
1888  }
1889  else
1890  {
1891  istr->reserve(di->size() + 2);
1892  *istr += *di;
1893  *istr += ':';
1894  }
1895  }
1896 }
1897 
1902  const std::string &name,
1903  const uint32_t run /* = 0 */,
1904  const uint32_t lumi /* = 0 */,
1905  const uint32_t streamId /* = 0 */,
1906  const uint32_t moduleId /* = 0 */) const
1907 {
1908  if (dir.find_first_not_of(s_safe) != std::string::npos)
1909  raiseDQMError("DQMStore", "Monitor element path name '%s' uses"
1910  " unacceptable characters", dir.c_str());
1911  if (name.find_first_not_of(s_safe) != std::string::npos)
1912  raiseDQMError("DQMStore", "Monitor element path name '%s' uses"
1913  " unacceptable characters", name.c_str());
1914 
1915  MonitorElement proto;
1916  proto.data_.dirname = &dir;
1917  proto.data_.objname = name;
1918  proto.data_.run = run;
1919  proto.data_.lumi = lumi;
1920  proto.data_.streamId = streamId;
1921  proto.data_.moduleId = moduleId;
1922 
1923  MEMap::const_iterator mepos = data_.find(proto);
1924  return (mepos == data_.end() ? 0
1925  : const_cast<MonitorElement *>(&*mepos));
1926 }
1927 
1930 void
1931 DQMStore::getAllTags(std::vector<std::string> &into) const
1932 {
1933  into.clear();
1934  into.reserve(dirs_.size());
1935 
1936  MEMap::const_iterator me = data_.end();
1937  std::set<std::string>::const_iterator di = dirs_.begin();
1938  std::set<std::string>::const_iterator de = dirs_.end();
1939  char tagbuf[32]; // more than enough for '/' and up to 10 digits
1940 
1941  for ( ; di != de; ++di)
1942  {
1943  MonitorElement proto(&*di, std::string());
1944  MEMap::const_iterator mi = data_.lower_bound(proto);
1945  MEMap::const_iterator m = mi;
1946  size_t sz = di->size() + 2;
1947  size_t nfound = 0;
1948  for ( ; m != me && isSubdirectory(*di, *m->data_.dirname); ++m)
1949  if (*di == *m->data_.dirname && (m->data_.flags & DQMNet::DQM_PROP_TAGGED))
1950  {
1951  // the tags count for '/' + up to 10 digits, otherwise ',' + ME name
1952  sz += 1 + m->data_.objname.size() + 11;
1953  ++nfound;
1954  }
1955 
1956  if (! nfound)
1957  continue;
1958 
1959  std::vector<std::string>::iterator istr
1960  = into.insert(into.end(), std::string());
1961 
1962  istr->reserve(sz);
1963 
1964  *istr += *di;
1965  *istr += ':';
1966  for (sz = 0; mi != m; ++mi)
1967  {
1968  if (*di == *m->data_.dirname && (m->data_.flags & DQMNet::DQM_PROP_TAGGED))
1969  {
1970  sprintf(tagbuf, "/%u", mi->data_.tag);
1971  if (sz > 0)
1972  *istr += ',';
1973  *istr += m->data_.objname;
1974  *istr += tagbuf;
1975  ++sz;
1976  }
1977  }
1978  }
1979 }
1980 
1983 std::vector<MonitorElement*>
1985  uint32_t runNumber /* = 0 */,
1986  uint32_t lumi /* = 0 */) const
1987 {
1989  const std::string *cleaned = 0;
1990  cleanTrailingSlashes(path, clean, cleaned);
1991  MonitorElement proto(cleaned, std::string(), runNumber);
1992  proto.setLumi(lumi);
1993 
1994  std::vector<MonitorElement *> result;
1995  MEMap::const_iterator e = data_.end();
1996  MEMap::const_iterator i = data_.lower_bound(proto);
1997  for ( ; i != e && isSubdirectory(*cleaned, *i->data_.dirname); ++i) {
1998  if (runNumber != 0) {
1999  if (i->data_.run > runNumber // TODO[rovere]: pleonastic? first we encounter local ME of the same run ...
2000  || i->data_.streamId != 0
2001  || i->data_.moduleId != 0)
2002  break;
2003  }
2004  if (lumi != 0) {
2005  if (i->data_.lumi > lumi
2006  || i->data_.streamId != 0
2007  || i->data_.moduleId != 0)
2008  break;
2009  }
2010  if (runNumber != 0 or lumi !=0) {
2011  assert(i->data_.streamId == 0);
2012  assert(i->data_.moduleId == 0);
2013  }
2014  result.push_back(const_cast<MonitorElement *>(&*i));
2015  }
2016 
2017  if (enableMultiThread_)
2018  {
2019  //save legacy modules when running MT
2020  i = data_.begin();
2021  for ( ; i != e && isSubdirectory(*cleaned, *i->data_.dirname); ++i) {
2022  if (i->data_.run != 0 || i->data_.streamId != 0 || i->data_.moduleId != 0) break;
2023  result.push_back(const_cast<MonitorElement *>(&*i));
2024  }
2025  }
2026 
2027  return result;
2028 }
2029 
2032 std::vector<MonitorElement*>
2033 DQMStore::getMatchingContents(const std::string &pattern, lat::Regexp::Syntax syntaxType /* = Wildcard */) const
2034 {
2035  lat::Regexp rx;
2036  try
2037  {
2038  rx = lat::Regexp(pattern, 0, syntaxType);
2039  rx.study();
2040  }
2041  catch (lat::Error &e)
2042  {
2043  raiseDQMError("DQMStore", "Invalid regular expression '%s': %s",
2044  pattern.c_str(), e.explain().c_str());
2045  }
2046 
2047  std::string path;
2048  std::vector<MonitorElement *> result;
2049  MEMap::const_iterator i = data_.begin();
2050  MEMap::const_iterator e = data_.end();
2051  for ( ; i != e; ++i)
2052  {
2053  path.clear();
2054  mergePath(path, *i->data_.dirname, i->data_.objname);
2055  if (rx.match(path))
2056  result.push_back(const_cast<MonitorElement *>(&*i));
2057  }
2058 
2059  return result;
2060 }
2061 
2065 
2068 void
2070 {
2071  MEMap::iterator mi = data_.begin();
2072  MEMap::iterator me = data_.end();
2073  for ( ; mi != me; ++mi)
2074  {
2075  MonitorElement &me = const_cast<MonitorElement &>(*mi);
2076  if (mi->wasUpdated())
2077  {
2078  if (me.resetMe())
2079  me.Reset();
2080  me.resetUpdate();
2081  }
2082  }
2083 
2084  reset_ = true;
2085 }
2086 
2090 
2092 void
2094 {
2095  MEMap::iterator mi = data_.begin();
2096  MEMap::iterator me = data_.end();
2097  for ( ; mi != me; ++mi)
2098  {
2099  if (forceResetOnBeginLumi_ && ((*mi).getLumiFlag() == false))
2100  continue;
2101  MonitorElement &me = const_cast<MonitorElement &>(*mi);
2102  me.Reset();
2103  me.resetUpdate();
2104  }
2105 
2106  reset_ = true;
2107 }
2108 
2112 
2116 void
2118 {
2119  if (!enableMultiThread_)
2120  return;
2121 
2122  std::lock_guard<std::mutex> guard(book_mutex_);
2123 
2124  std::string null_str("");
2125  MonitorElement proto(&null_str, null_str, run, 0, 0);
2126  proto.setLumi(lumi);
2127 
2128  std::set<MonitorElement>::const_iterator e = data_.end();
2129  std::set<MonitorElement>::const_iterator i = data_.lower_bound(proto);
2130 
2131  while (i != e) {
2132  if (i->data_.streamId != 0 ||
2133  i->data_.moduleId != 0)
2134  break;
2135  if (i->data_.lumi != lumi)
2136  break;
2137  if (i->data_.run != run)
2138  break;
2139 
2140  auto temp = i;
2141  ++i;
2142 
2143  if (verbose_ > 1) {
2144  std::cout << "DQMStore::deleteUnusedLumiHistograms: deleted monitor element '"
2145  << *i->data_.dirname << "/" << i->data_.objname << "'"
2146  << "flags " << i->data_.flags << "\n";
2147  }
2148 
2149  data_.erase(temp);
2150  }
2151 }
2152 
2158 bool
2160  bool overwrite, bool collateHistograms)
2161 {
2162  // NB: Profile histograms inherit from TH*D, checking order matters.
2163  MonitorElement *refcheck = 0;
2164  if (TProfile *h = dynamic_cast<TProfile *>(obj))
2165  {
2166  MonitorElement *me = findObject(dir, h->GetName());
2167  if (! me)
2168  me = bookProfile(dir, h->GetName(), (TProfile *) h->Clone());
2169  else if (overwrite)
2170  me->copyFrom(h);
2171  else if (isCollateME(me) || collateHistograms)
2172  collateProfile(me, h, verbose_);
2173  refcheck = me;
2174  }
2175  else if (TProfile2D *h = dynamic_cast<TProfile2D *>(obj))
2176  {
2177  MonitorElement *me = findObject(dir, h->GetName());
2178  if (! me)
2179  me = bookProfile2D(dir, h->GetName(), (TProfile2D *) h->Clone());
2180  else if (overwrite)
2181  me->copyFrom(h);
2182  else if (isCollateME(me) || collateHistograms)
2183  collateProfile2D(me, h, verbose_);
2184  refcheck = me;
2185  }
2186  else if (TH1F *h = dynamic_cast<TH1F *>(obj))
2187  {
2188  MonitorElement *me = findObject(dir, h->GetName());
2189  if (! me)
2190  me = book1D(dir, h->GetName(), (TH1F *) h->Clone());
2191  else if (overwrite)
2192  me->copyFrom(h);
2193  else if (isCollateME(me) || collateHistograms)
2194  collate1D(me, h, verbose_);
2195  refcheck = me;
2196  }
2197  else if (TH1S *h = dynamic_cast<TH1S *>(obj))
2198  {
2199  MonitorElement *me = findObject(dir, h->GetName());
2200  if (! me)
2201  me = book1S(dir, h->GetName(), (TH1S *) h->Clone());
2202  else if (overwrite)
2203  me->copyFrom(h);
2204  else if (isCollateME(me) || collateHistograms)
2205  collate1S(me, h, verbose_);
2206  refcheck = me;
2207  }
2208  else if (TH1D *h = dynamic_cast<TH1D *>(obj))
2209  {
2210  MonitorElement *me = findObject(dir, h->GetName());
2211  if (! me)
2212  me = book1DD(dir, h->GetName(), (TH1D *) h->Clone());
2213  else if (overwrite)
2214  me->copyFrom(h);
2215  else if (isCollateME(me) || collateHistograms)
2216  collate1DD(me, h, verbose_);
2217  refcheck = me;
2218  }
2219  else if (TH2F *h = dynamic_cast<TH2F *>(obj))
2220  {
2221  MonitorElement *me = findObject(dir, h->GetName());
2222  if (! me)
2223  me = book2D(dir, h->GetName(), (TH2F *) h->Clone());
2224  else if (overwrite)
2225  me->copyFrom(h);
2226  else if (isCollateME(me) || collateHistograms)
2227  collate2D(me, h, verbose_);
2228  refcheck = me;
2229  }
2230  else if (TH2S *h = dynamic_cast<TH2S *>(obj))
2231  {
2232  MonitorElement *me = findObject(dir, h->GetName());
2233  if (! me)
2234  me = book2S(dir, h->GetName(), (TH2S *) h->Clone());
2235  else if (overwrite)
2236  me->copyFrom(h);
2237  else if (isCollateME(me) || collateHistograms)
2238  collate2S(me, h, verbose_);
2239  refcheck = me;
2240  }
2241  else if (TH2D *h = dynamic_cast<TH2D *>(obj))
2242  {
2243  MonitorElement *me = findObject(dir, h->GetName());
2244  if (! me)
2245  me = book2DD(dir, h->GetName(), (TH2D *) h->Clone());
2246  else if (overwrite)
2247  me->copyFrom(h);
2248  else if (isCollateME(me) || collateHistograms)
2249  collate2DD(me, h, verbose_);
2250  refcheck = me;
2251  }
2252  else if (TH3F *h = dynamic_cast<TH3F *>(obj))
2253  {
2254  MonitorElement *me = findObject(dir, h->GetName());
2255  if (! me)
2256  me = book3D(dir, h->GetName(), (TH3F *) h->Clone());
2257  else if (overwrite)
2258  me->copyFrom(h);
2259  else if (isCollateME(me) || collateHistograms)
2260  collate3D(me, h, verbose_);
2261  refcheck = me;
2262  }
2263  else if (dynamic_cast<TObjString *>(obj))
2264  {
2265  lat::RegexpMatch m;
2266  if (! s_rxmeval.match(obj->GetName(), 0, 0, &m))
2267  {
2268  if (strstr(obj->GetName(), "CMSSW"))
2269  {
2270  if (verbose_)
2271  std::cout << "Input file version: " << obj->GetName() << std::endl;
2272  return true;
2273  }
2274  else if (strstr(obj->GetName(), "DQMPATCH"))
2275  {
2276  if (verbose_)
2277  std::cout << "DQM patch version: " << obj->GetName() << std::endl;
2278  return true;
2279  }
2280  else
2281  {
2282  std::cout << "*** DQMStore: WARNING: cannot extract object '"
2283  << obj->GetName() << "' of type '"
2284  << obj->IsA()->GetName() << "'\n";
2285  return false;
2286  }
2287  }
2288 
2289  std::string label = m.matchString(obj->GetName(), 1);
2290  std::string kind = m.matchString(obj->GetName(), 2);
2291  std::string value = m.matchString(obj->GetName(), 3);
2292 
2293  if (kind == "i")
2294  {
2295  MonitorElement *me = findObject(dir, label);
2296  if (! me || overwrite)
2297  {
2298  if (! me) me = bookInt(dir, label);
2299  me->Fill(atoll(value.c_str()));
2300  }
2301  }
2302  else if (kind == "f")
2303  {
2304  MonitorElement *me = findObject(dir, label);
2305  if (! me || overwrite)
2306  {
2307  if (! me) me = bookFloat(dir, label);
2308  me->Fill(atof(value.c_str()));
2309  }
2310  }
2311  else if (kind == "s")
2312  {
2313  MonitorElement *me = findObject(dir, label);
2314  if (! me)
2315  me = bookString(dir, label, value);
2316  else if (overwrite)
2317  me->Fill(value);
2318  }
2319  else if (kind == "e")
2320  {
2321  MonitorElement *me = findObject(dir, label);
2322  if (! me)
2323  {
2324  std::cout << "*** DQMStore: WARNING: no monitor element '"
2325  << label << "' in directory '"
2326  << dir << "' to be marked as efficiency plot.\n";
2327  return false;
2328  }
2329  me->setEfficiencyFlag();
2330  }
2331  else if (kind == "t")
2332  {
2333  MonitorElement *me = findObject(dir, label);
2334  if (! me)
2335  {
2336  std::cout << "*** DQMStore: WARNING: no monitor element '"
2337  << label << "' in directory '"
2338  << dir << "' for a tag\n";
2339  return false;
2340  }
2341  errno = 0;
2342  char *endp = 0;
2343  unsigned long val = strtoul(value.c_str(), &endp, 10);
2344  if ((val == 0 && errno) || *endp || val > ~uint32_t(0))
2345  {
2346  std::cout << "*** DQMStore: WARNING: cannot restore tag '"
2347  << value << "' for monitor element '"
2348  << label << "' in directory '"
2349  << dir << "' - invalid value\n";
2350  return false;
2351  }
2352  tag(me, val);
2353  }
2354  else if (kind == "qr")
2355  {
2356  // Handle qreports, but skip them while reading in references.
2357  if (! isSubdirectory(s_referenceDirName, dir))
2358  {
2359  size_t dot = label.find('.');
2360  if (dot == std::string::npos)
2361  {
2362  std::cout << "*** DQMStore: WARNING: quality report label in '" << label
2363  << "' is missing a '.' and cannot be extracted\n";
2364  return false;
2365  }
2366 
2367  std::string mename (label, 0, dot);
2368  std::string qrname (label, dot+1, std::string::npos);
2369 
2370  m.reset();
2371  DQMNet::QValue qv;
2372  if (s_rxmeqr1.match(value, 0, 0, &m))
2373  {
2374  qv.code = atoi(m.matchString(value, 1).c_str());
2375  qv.qtresult = strtod(m.matchString(value, 2).c_str(), 0);
2376  qv.message = m.matchString(value, 4);
2377  qv.qtname = qrname;
2378  qv.algorithm = m.matchString(value, 3);
2379  }
2380  else if (s_rxmeqr2.match(value, 0, 0, &m))
2381  {
2382  qv.code = atoi(m.matchString(value, 1).c_str());
2383  qv.qtresult = 0; // unavailable in old format
2384  qv.message = m.matchString(value, 2);
2385  qv.qtname = qrname;
2386  // qv.algorithm unavailable in old format
2387  }
2388  else
2389  {
2390  std::cout << "*** DQMStore: WARNING: quality test value '"
2391  << value << "' is incorrectly formatted\n";
2392  return false;
2393  }
2394 
2395  MonitorElement *me = findObject(dir, mename);
2396  if (! me)
2397  {
2398  std::cout << "*** DQMStore: WARNING: no monitor element '"
2399  << mename << "' in directory '"
2400  << dir << "' for quality test '"
2401  << label << "'\n";
2402  return false;
2403  }
2404 
2405  me->addQReport(qv, /* FIXME: getQTest(qv.qtname)? */ 0);
2406  }
2407  }
2408  else
2409  {
2410  std::cout << "*** DQMStore: WARNING: cannot extract object '"
2411  << obj->GetName() << "' of type '"
2412  << obj->IsA()->GetName() << "'\n";
2413  return false;
2414  }
2415  }
2416  else if (TNamed *n = dynamic_cast<TNamed *>(obj))
2417  {
2418  // For old DQM data.
2419  std::string s;
2420  s.reserve(6 + strlen(n->GetTitle()) + 2*strlen(n->GetName()));
2421  s += '<'; s += n->GetName(); s += '>';
2422  s += n->GetTitle();
2423  s += '<'; s += '/'; s += n->GetName(); s += '>';
2424  TObjString os(s.c_str());
2425  return extract(&os, dir, overwrite, collateHistograms_);
2426  }
2427  else
2428  {
2429  std::cout << "*** DQMStore: WARNING: cannot extract object '"
2430  << obj->GetName() << "' of type '" << obj->IsA()->GetName()
2431  << "' and with title '" << obj->GetTitle() << "'\n";
2432  return false;
2433  }
2434 
2435  // If we just read in a reference MonitorElement, and there is a
2436  // MonitorElement with the same name, link the two together.
2437  // The other direction is handled by the book() method.
2438  if (refcheck && isSubdirectory(s_referenceDirName, dir))
2439  {
2440  std::string mdir(dir, s_referenceDirName.size()+1, std::string::npos);
2441  if (MonitorElement *master = findObject(mdir, obj->GetName()))
2442  {
2443  // We have extracted a MonitorElement, and it's located in the reference
2444  // dir. Then we find the corresponding MonitorElement in the
2445  // non-reference dir and assign the object_ of the reference
2446  // MonitorElement to the reference_ property of the corresponding
2447  // non-reference MonitorElement.
2448  master->data_.flags |= DQMNet::DQM_PROP_HAS_REFERENCE;
2449  master->reference_ = refcheck->object_;
2450  }
2451  }
2452 
2453  return true;
2454 }
2455 
2459 bool
2461 {
2462  assert(! path.empty());
2463 
2464  // Find the first path component.
2465  size_t start = 0;
2466  size_t end = path.find('/', start);
2467  if (end == std::string::npos)
2468  end = path.size();
2469 
2470  while (true)
2471  {
2472  // Check if this subdirectory component exists. If yes, make sure
2473  // it is actually a subdirectory. Otherwise create or cd into it.
2474  std::string part(path, start, end-start);
2475  TObject *o = gDirectory->Get(part.c_str());
2476  if (o && ! dynamic_cast<TDirectory *>(o))
2477  raiseDQMError("DQMStore", "Attempt to create directory '%s' in a file"
2478  " fails because the part '%s' already exists and is not"
2479  " directory", path.c_str(), part.c_str());
2480  else if (! o)
2481  gDirectory->mkdir(part.c_str());
2482 
2483  if (! gDirectory->cd(part.c_str()))
2484  raiseDQMError("DQMStore", "Attempt to create directory '%s' in a file"
2485  " fails because could not cd into subdirectory '%s'",
2486  path.c_str(), part.c_str());
2487 
2488  // Stop if we reached the end, ignoring any trailing '/'.
2489  if (end+1 >= path.size())
2490  break;
2491 
2492  // Find the next path component.
2493  start = end+1;
2494  end = path.find('/', start);
2495  if (end == std::string::npos)
2496  end = path.size();
2497  }
2498 
2499  return true;
2500 }
2501 
2503  const std::string &path /* = "" */,
2504  const uint32_t run /* = 0 */,
2505  const uint32_t lumi /* = 0 */,
2506  const bool resetMEsAfterWriting /* = false */)
2507 {
2508  using google::protobuf::io::FileOutputStream;
2509  using google::protobuf::io::GzipOutputStream;
2510  using google::protobuf::io::StringOutputStream;
2511 
2512  std::lock_guard<std::mutex> guard(book_mutex_);
2513 
2514  std::set<std::string>::iterator di, de;
2515  MEMap::iterator mi, me = data_.end();
2516  dqmstorepb::ROOTFilePB dqmstore_message;
2517  int nme = 0;
2518 
2519  if (verbose_)
2520  std::cout << "\n DQMStore: Opening PBFile '"
2521  << filename << "'"<< std::endl;
2522 
2523  // Loop over the directory structure.
2524  for (di = dirs_.begin(), de = dirs_.end(); di != de; ++di)
2525  {
2526  // Check if we should process this directory. We process the
2527  // requested part of the object tree, including references.
2528  if (! path.empty()
2529  && ! isSubdirectory(path, *di))
2530  continue;
2531 
2532  // Loop over monitor elements in this directory.
2533  MonitorElement proto(&*di, std::string(), run, 0, 0);
2534  if (enableMultiThread_)
2535  proto.setLumi(lumi);
2536 
2537  mi = data_.lower_bound(proto);
2538  for ( ; mi != me && isSubdirectory(*di, *mi->data_.dirname); ++mi)
2539  {
2540  if (verbose_ > 1)
2541  std::cout << "Run: " << (*mi).run()
2542  << " Lumi: " << (*mi).lumi()
2543  << " LumiFlag: " << (*mi).getLumiFlag()
2544  << " streamId: " << (*mi).streamId()
2545  << " moduleId: " << (*mi).moduleId()
2546  << " fullpathname: " << (*mi).getFullname() << std::endl;
2547 
2548  // Upper bound in the loop over the MEs
2549  if (enableMultiThread_ && ((*mi).lumi() != lumi))
2550  break;
2551 
2552  // Skip if it isn't a direct child.
2553  if (*di != *mi->data_.dirname)
2554  continue;
2555 
2556  // Keep backward compatibility with the old way of
2557  // booking/handlind MonitorElements into the DQMStore. If run is
2558  // 0 it means that a booking happened w/ the old non-threadsafe
2559  // style, and we have to ignore the streamId and moduleId as a
2560  // consequence.
2561 
2562  if (run != 0 && (mi->data_.streamId !=0 || mi->data_.moduleId !=0))
2563  continue;
2564 
2565  if (verbose_ > 1)
2566  std::cout << "DQMStore::savePB: saving monitor element '"
2567  << *mi->data_.dirname << "/" << mi->data_.objname << "'"
2568  << "flags " << mi->data_.flags << "\n";
2569 
2570  nme++;
2571  dqmstorepb::ROOTFilePB::Histo* me = dqmstore_message.add_histo();
2572  me->set_full_pathname((*mi->data_.dirname) + '/' + mi->data_.objname);
2573  me->set_flags(mi->data_.flags);
2574 
2575  TObject *toWrite = nullptr;
2576  bool deleteObject = false;
2577 
2578  if (mi->kind() < MonitorElement::DQM_KIND_TH1F) {
2579  toWrite = new TObjString(mi->tagString().c_str());
2580  deleteObject = true;
2581  } else {
2582  toWrite = mi->object_;
2583  }
2584 
2585  TBufferFile buffer(TBufferFile::kWrite);
2586  buffer.WriteObject(toWrite);
2587  me->set_size(buffer.Length());
2588  me->set_streamed_histo((const void*)buffer.Buffer(),
2589  buffer.Length());
2590 
2591  if (deleteObject) {
2592  delete toWrite;
2593  }
2594 
2595  //reset the ME just written to make it available for the next LS (online)
2596  if (resetMEsAfterWriting)
2597  const_cast<MonitorElement*>(&*mi)->Reset();
2598  }
2599  }
2600 
2601  int filedescriptor = ::open(filename.c_str(),
2602  O_WRONLY | O_CREAT | O_TRUNC,
2603  S_IRUSR | S_IWUSR |
2604  S_IRGRP | S_IWGRP |
2605  S_IROTH);
2606  FileOutputStream file_stream(filedescriptor);
2608  options.format = GzipOutputStream::GZIP;
2609  options.compression_level = 6;
2610  GzipOutputStream gzip_stream(&file_stream,
2611  options);
2612  dqmstore_message.SerializeToZeroCopyStream(&gzip_stream);
2613 
2614  // we need to flush it before we close the fd
2615  gzip_stream.Close();
2616  file_stream.Close();
2617  ::close(filedescriptor);
2618 
2619  // Maybe make some noise.
2620  if (verbose_)
2621  std::cout << "DQMStore::savePB: successfully wrote " << nme
2622  << " objects from path '" << path
2623  << "' into DQM file '" << filename << "'\n";
2624 }
2625 
2626 
2631 void
2633  const std::string &path /* = "" */,
2634  const std::string &pattern /* = "" */,
2635  const std::string &rewrite /* = "" */,
2636  const uint32_t run /* = 0 */,
2637  const uint32_t lumi /* = 0 */,
2638  SaveReferenceTag ref /* = SaveWithReference */,
2639  int minStatus /* = dqm::qstatus::STATUS_OK */,
2640  const std::string &fileupdate /* = RECREATE */,
2641  const bool resetMEsAfterWriting /* = false */)
2642 {
2643  std::lock_guard<std::mutex> guard(book_mutex_);
2644 
2645  std::set<std::string>::iterator di, de;
2646  MEMap::iterator mi, me = data_.end();
2647  DQMNet::QReports::const_iterator qi, qe;
2648  int nme=0;
2649 
2650  // TFile flushes to disk with fsync() on every TDirectory written to
2651  // the file. This makes DQM file saving painfully slow, and
2652  // ironically makes it _more_ likely the file saving gets
2653  // interrupted and corrupts the file. The utility class below
2654  // simply ignores the flush synchronisation.
2655  class TFileNoSync : public TFile
2656  {
2657  public:
2658  TFileNoSync(const char *file, const char *opt) : TFile(file, opt) {}
2659  virtual Int_t SysSync(Int_t) override { return 0; }
2660  };
2661 
2662  // open output file, on 1st save recreate, later update
2663  if (verbose_)
2664  std::cout << "\n DQMStore: Opening TFile '" << filename
2665  << "' with option '" << fileupdate <<"'\n";
2666 
2667  TFileNoSync f(filename.c_str(), fileupdate.c_str()); // open file
2668  if(f.IsZombie())
2669  raiseDQMError("DQMStore", "Failed to create/update file '%s'", filename.c_str());
2670  f.cd();
2671 
2672  // Construct a regular expression from the pattern string.
2673  std::auto_ptr<lat::Regexp> rxpat;
2674  if (! pattern.empty())
2675  rxpat.reset(new lat::Regexp(pattern.c_str()));
2676 
2677  // Prepare a path for the reference object selection.
2678  std::string refpath;
2679  refpath.reserve(s_referenceDirName.size() + path.size() + 2);
2680  refpath += s_referenceDirName;
2681  if (! path.empty())
2682  {
2683  refpath += '/';
2684  refpath += path;
2685  }
2686 
2687  // Loop over the directory structure.
2688  for (di = dirs_.begin(), de = dirs_.end(); di != de; ++di)
2689  {
2690  // Check if we should process this directory. We process the
2691  // requested part of the object tree, including references.
2692  if (! path.empty()
2693  && ! isSubdirectory(path, *di)
2694  && ! isSubdirectory(refpath, *di))
2695  continue;
2696 
2697  // Loop over monitor elements in this directory.
2698  MonitorElement proto(&*di, std::string(), run, 0, 0);
2699  if (enableMultiThread_)
2700  proto.setLumi(lumi);
2701 
2702  mi = data_.lower_bound(proto);
2703  for ( ; mi != me && isSubdirectory(*di, *mi->data_.dirname); ++mi)
2704  {
2705  if (verbose_ > 1)
2706  std::cout << "DQMStore::save: Run: " << (*mi).run()
2707  << " Lumi: " << (*mi).lumi()
2708  << " LumiFlag: " << (*mi).getLumiFlag()
2709  << " streamId: " << (*mi).streamId()
2710  << " moduleId: " << (*mi).moduleId()
2711  << " fullpathname: " << (*mi).getFullname() << std::endl;
2712 
2713  // Upper bound in the loop over the MEs
2714  if (enableMultiThread_ && ((*mi).lumi() != lumi))
2715  break;
2716 
2717  // Skip if it isn't a direct child.
2718  if (*di != *mi->data_.dirname) {
2719  if (verbose_ > 1)
2720  std::cout << "DQMStore::save: isn't a direct child. Skipping" << std::endl;
2721  continue;
2722  }
2723 
2724  // Keep backward compatibility with the old way of
2725  // booking/handlind MonitorElements into the DQMStore. If run is
2726  // 0 it means that a booking happened w/ the old non-threadsafe
2727  // style, and we have to ignore the streamId and moduleId as a
2728  // consequence.
2729 
2730  if (run != 0 && (mi->data_.streamId !=0 || mi->data_.moduleId !=0)) {
2731  continue;
2732  }
2733 
2734  // Handle reference histograms, with three distinct cases:
2735  // 1) Skip all references entirely on saving.
2736  // 2) Blanket saving of all references.
2737  // 3) Save only references for monitor elements with qtests.
2738  // The latter two are affected by "path" sub-tree selection,
2739  // i.e. references are saved only in the selected tree part.
2740  if (isSubdirectory(refpath, *mi->data_.dirname))
2741  {
2742  if (ref == SaveWithoutReference)
2743  // Skip the reference entirely.
2744  continue;
2745  else if (ref == SaveWithReference)
2746  // Save all references regardless of qtests.
2747  ;
2748  else if (ref == SaveWithReferenceForQTest)
2749  {
2750  // Save only references for monitor elements with qtests
2751  // with an optional cut on minimum quality test result.
2752  int status = -1;
2753  std::string mname(mi->getFullname(), s_referenceDirName.size()+1, std::string::npos);
2754  MonitorElement *master = get(mname);
2755  if (master)
2756  for (size_t i = 0, e = master->data_.qreports.size(); i != e; ++i)
2757  status = std::max(status, master->data_.qreports[i].code);
2758 
2759  if (! master || status < minStatus)
2760  {
2761  if (verbose_ > 1)
2762  std::cout << "DQMStore::save: skipping monitor element '"
2763  << mi->data_.objname << "' while saving, status is "
2764  << status << ", required minimum status is "
2765  << minStatus << std::endl;
2766  continue;
2767  }
2768  }
2769  }
2770 
2771  if (verbose_ > 1)
2772  std::cout << "DQMStore::save: saving monitor element '"
2773  << mi->data_.objname << "'\n";
2774  nme++; // count saved histograms
2775 
2776  // Create the directory.
2777  gDirectory->cd("/");
2778  if (di->empty())
2780  else if (rxpat.get())
2781  cdInto(s_monitorDirName + '/' + lat::StringOps::replace(*di, *rxpat, rewrite));
2782  else
2783  cdInto(s_monitorDirName + '/' + *di);
2784 
2785  // Save the object.
2786  switch (mi->kind())
2787  {
2791  TObjString(mi->tagString().c_str()).Write();
2792  break;
2793 
2794  default:
2795  mi->object_->Write();
2796  break;
2797  }
2798 
2799  // Save quality reports if this is not in reference section.
2800  if (! isSubdirectory(s_referenceDirName, *mi->data_.dirname))
2801  {
2802  qi = mi->data_.qreports.begin();
2803  qe = mi->data_.qreports.end();
2804  for ( ; qi != qe; ++qi)
2805  TObjString(mi->qualityTagString(*qi).c_str()).Write();
2806  }
2807 
2808  // Save efficiency tag, if any
2809  if (mi->data_.flags & DQMNet::DQM_PROP_EFFICIENCY_PLOT)
2810  TObjString(mi->effLabelString().c_str()).Write();
2811 
2812  // Save tag if any
2813  if (mi->data_.flags & DQMNet::DQM_PROP_TAGGED)
2814  TObjString(mi->tagLabelString().c_str()).Write();
2815 
2816  //reset the ME just written to make it available for the next LS (online)
2817  if (resetMEsAfterWriting)
2818  const_cast<MonitorElement*>(&*mi)->Reset();
2819  }
2820  }
2821 
2822  f.Close();
2823 
2824  // Maybe make some noise.
2825  if (verbose_)
2826  std::cout << "DQMStore::save: successfully wrote " << nme
2827  << " objects from path '" << path
2828  << "' into DQM file '" << filename << "'\n";
2829 }
2830 
2833 unsigned int
2835  bool overwrite,
2836  const std::string &onlypath,
2837  const std::string &prepend,
2838  const std::string &curdir,
2839  OpenRunDirs stripdirs)
2840 {
2841  unsigned int ntot = 0;
2842  unsigned int count = 0;
2843 
2844  if (! file->cd(curdir.c_str()))
2845  raiseDQMError("DQMStore", "Failed to process directory '%s' while"
2846  " reading file '%s'", curdir.c_str(), file->GetName());
2847 
2848  // Figure out current directory name, but strip out the top
2849  // directory into which we dump everything.
2850  std::string dirpart = curdir;
2851  if (dirpart.compare(0, s_monitorDirName.size(), s_monitorDirName) == 0)
2852  {
2853  if (dirpart.size() == s_monitorDirName.size())
2854  dirpart.clear();
2855  else if (dirpart[s_monitorDirName.size()] == '/')
2856  dirpart.erase(0, s_monitorDirName.size()+1);
2857  }
2858 
2859  // See if we are going to skip this directory.
2860  bool skip = (! onlypath.empty() && ! isSubdirectory(onlypath, dirpart));
2861 
2862  if (prepend == s_collateDirName ||
2863  prepend == s_referenceDirName ||
2864  stripdirs == StripRunDirs )
2865  {
2866  // Remove Run # and RunSummary dirs
2867  // first look for Run summary,
2868  // if that is found and erased, also erase Run dir
2869  size_t slash = dirpart.find('/');
2870  size_t pos = dirpart.find("/Run summary");
2871  if (slash != std::string::npos && pos !=std::string::npos)
2872  {
2873  dirpart.erase(pos,12);
2874 
2875  pos = dirpart.find("Run ");
2876  size_t length = dirpart.find('/',pos+1)-pos+1;
2877  if (pos !=std::string::npos)
2878  dirpart.erase(pos,length);
2879  }
2880  }
2881 
2882  // If we are prepending, add it to the directory name,
2883  // and suppress reading of already existing reference histograms
2884  if (prepend == s_collateDirName ||
2885  prepend == s_referenceDirName)
2886  {
2887  size_t slash = dirpart.find('/');
2888  // If we are reading reference, skip previous reference.
2889  if (slash == std::string::npos // skip if Reference is toplevel folder, i.e. no slash
2890  && slash+1+s_referenceDirName.size() == dirpart.size()
2891  && dirpart.compare(slash+1, s_referenceDirName.size(), s_referenceDirName) == 0)
2892  return 0;
2893 
2894  slash = dirpart.find('/');
2895  // Skip reading of EventInfo subdirectory.
2896  if (slash != std::string::npos
2897  && slash + 10 == dirpart.size()
2898  && dirpart.compare( slash+1 , 9 , "EventInfo") == 0) {
2899  if (verbose_)
2900  std::cout << "DQMStore::readDirectory: skipping '" << dirpart << "'\n";
2901  return 0;
2902  }
2903 
2904  // Add prefix.
2905  if (dirpart.empty())
2906  dirpart = prepend;
2907  else
2908  dirpart = prepend + '/' + dirpart;
2909  }
2910  else if (! prepend.empty())
2911  {
2912  if (dirpart.empty())
2913  dirpart = prepend;
2914  else
2915  dirpart = prepend + '/' + dirpart;
2916  }
2917 
2918  // Loop over the contents of this directory in the file.
2919  // Post-pone string object handling to happen after other
2920  // objects have been read in so we are guaranteed to have
2921  // histograms by the time we read in quality tests and tags.
2922  TKey *key;
2923  TIter next (gDirectory->GetListOfKeys());
2924  std::list<TObject *> delayed;
2925  while ((key = (TKey *) next()))
2926  {
2927  std::auto_ptr<TObject> obj(key->ReadObj());
2928  if (dynamic_cast<TDirectory *>(obj.get()))
2929  {
2930  std::string subdir;
2931  subdir.reserve(curdir.size() + strlen(obj->GetName()) + 2);
2932  subdir += curdir;
2933  if (! curdir.empty())
2934  subdir += '/';
2935  subdir += obj->GetName();
2936 
2937  ntot += readDirectory(file, overwrite, onlypath, prepend, subdir, stripdirs);
2938  }
2939  else if (skip)
2940  ;
2941  else if (dynamic_cast<TObjString *>(obj.get()))
2942  {
2943  delayed.push_back(obj.release());
2944  }
2945  else
2946  {
2947  if (verbose_ > 2)
2948  std::cout << "DQMStore: reading object '" << obj->GetName()
2949  << "' of type '" << obj->IsA()->GetName()
2950  << "' from '" << file->GetName()
2951  << "' into '" << dirpart << "'\n";
2952 
2953  makeDirectory(dirpart);
2954  if (extract(obj.get(), dirpart, overwrite, collateHistograms_))
2955  ++count;
2956  }
2957  }
2958 
2959  while (! delayed.empty())
2960  {
2961  if (verbose_ > 2)
2962  std::cout << "DQMStore: reading object '" << delayed.front()->GetName()
2963  << "' of type '" << delayed.front()->IsA()->GetName()
2964  << "' from '" << file->GetName()
2965  << "' into '" << dirpart << "'\n";
2966 
2967  makeDirectory(dirpart);
2968  if (extract(delayed.front(), dirpart, overwrite, collateHistograms_))
2969  ++count;
2970 
2971  delete delayed.front();
2972  delayed.pop_front();
2973  }
2974 
2975  if (verbose_ > 1)
2976  std::cout << "DQMStore: read " << count << '/' << ntot
2977  << " objects from directory '" << dirpart << "'\n";
2978 
2979  return ntot + count;
2980 }
2981 
2988 bool
2990  bool overwrite /* = false */,
2991  const std::string &onlypath /* ="" */,
2992  const std::string &prepend /* ="" */,
2993  OpenRunDirs stripdirs /* =KeepRunDirs */,
2994  bool fileMustExist /* =true */)
2995 {
2996  return readFile(filename,overwrite,onlypath,prepend,stripdirs,fileMustExist);
2997 }
2998 
3003 bool
3005  OpenRunDirs stripdirs /* =StripRunDirs */,
3006  bool fileMustExist /* =true */)
3007 {
3008  bool overwrite = true;
3009  if (collateHistograms_) overwrite = false;
3010  if (verbose_)
3011  {
3012  std::cout << "DQMStore::load: reading from file '" << filename << "'\n";
3013  if (collateHistograms_)
3014  std::cout << "DQMStore::load: in collate mode " << "\n";
3015  else
3016  std::cout << "DQMStore::load: in overwrite mode " << "\n";
3017  }
3018 
3019  if (!s_rxpbfile.match(filename, 0, 0))
3020  return readFile(filename, overwrite, "", "", stripdirs, fileMustExist);
3021  else
3022  return readFilePB(filename, overwrite, "", "", stripdirs, fileMustExist);
3023 }
3024 
3030 bool
3032  bool overwrite /* = false */,
3033  const std::string &onlypath /* ="" */,
3034  const std::string &prepend /* ="" */,
3035  OpenRunDirs stripdirs /* =StripRunDirs */,
3036  bool fileMustExist /* =true */)
3037 {
3038 
3039  if (verbose_)
3040  std::cout << "DQMStore::readFile: reading from file '" << filename << "'\n";
3041 
3042  std::auto_ptr<TFile> f;
3043 
3044  try
3045  {
3046  f.reset(TFile::Open(filename.c_str()));
3047  if (! f.get() || f->IsZombie())
3048  raiseDQMError("DQMStore", "Failed to open file '%s'", filename.c_str());
3049  }
3050  catch (std::exception &)
3051  {
3052  if (fileMustExist)
3053  throw;
3054  else
3055  {
3056  if (verbose_)
3057  std::cout << "DQMStore::readFile: file '" << filename << "' does not exist, continuing\n";
3058  return false;
3059  }
3060  }
3061 
3062  unsigned n = readDirectory(f.get(), overwrite, onlypath, prepend, "", stripdirs);
3063  f->Close();
3064 
3065  MEMap::iterator mi = data_.begin();
3066  MEMap::iterator me = data_.end();
3067  for ( ; mi != me; ++mi)
3068  const_cast<MonitorElement &>(*mi).updateQReportStats();
3069 
3070  if (verbose_)
3071  {
3072  std::cout << "DQMStore::open: successfully read " << n
3073  << " objects from file '" << filename << "'";
3074  if (! onlypath.empty())
3075  std::cout << " from directory '" << onlypath << "'";
3076  if (! prepend.empty())
3077  std::cout << " into directory '" << prepend << "'";
3078  std::cout << std::endl;
3079  }
3080  return true;
3081 }
3082 
3086 inline TObject * DQMStore::extractNextObject(TBufferFile &buf) const {
3087  if (buf.Length() == buf.BufferSize())
3088  return 0;
3089  buf.InitMap();
3090  void *ptr = buf.ReadObjectAny(0);
3091  return reinterpret_cast<TObject *>(ptr);
3092 }
3093 
3096  std::string &objname,
3097  TObject ** obj) {
3098 
3099  size_t slash = h.full_pathname().rfind('/');
3100  size_t dirpos = (slash == std::string::npos ? 0 : slash);
3101  size_t namepos = (slash == std::string::npos ? 0 : slash+1);
3102  dirname.assign(h.full_pathname(), 0, dirpos);
3103  objname.assign(h.full_pathname(), namepos, std::string::npos);
3104  TBufferFile buf(TBufferFile::kRead, h.size(),
3105  (void*)h.streamed_histo().data(),
3106  kFALSE);
3107  buf.Reset();
3108  *obj = extractNextObject(buf);
3109  if (!*obj) {
3110  raiseDQMError("DQMStore", "Error reading element:'%s'" , h.full_pathname().c_str());
3111  }
3112 }
3113 
3114 bool
3116  bool overwrite /* = false */,
3117  const std::string &onlypath /* ="" */,
3118  const std::string &prepend /* ="" */,
3119  OpenRunDirs stripdirs /* =StripRunDirs */,
3120  bool fileMustExist /* =true */)
3121 {
3122  using google::protobuf::io::FileInputStream;
3123  using google::protobuf::io::FileOutputStream;
3124  using google::protobuf::io::GzipInputStream;
3125  using google::protobuf::io::GzipOutputStream;
3126  using google::protobuf::io::CodedInputStream;
3127  using google::protobuf::io::ArrayInputStream;
3128 
3129  if (verbose_)
3130  std::cout << "DQMStore::readFile: reading from file '" << filename << "'\n";
3131 
3132  int filedescriptor;
3133  if ((filedescriptor = ::open(filename.c_str(), O_RDONLY)) == -1) {
3134  if (fileMustExist)
3135  raiseDQMError("DQMStore", "Failed to open file '%s'", filename.c_str());
3136  else
3137  if (verbose_)
3138  std::cout << "DQMStore::readFile: file '" << filename << "' does not exist, continuing\n";
3139  return false;
3140  }
3141 
3142  dqmstorepb::ROOTFilePB dqmstore_message;
3143  FileInputStream fin(filedescriptor);
3144  GzipInputStream input(&fin);
3145  CodedInputStream input_coded(&input);
3146  input_coded.SetTotalBytesLimit(1024*1024*1024, -1);
3147  if (!dqmstore_message.ParseFromCodedStream(&input_coded)) {
3148  raiseDQMError("DQMStore", "Fatal parsing file '%s'", filename.c_str());
3149  return false;
3150  }
3151  ::close(filedescriptor);
3152 
3153  for (int i = 0; i < dqmstore_message.histo_size(); i++) {
3154  std::string path;
3155  std::string objname;
3156 
3157  TObject *obj = NULL;
3158  const dqmstorepb::ROOTFilePB::Histo &h = dqmstore_message.histo(i);
3159  get_info(h, path, objname, &obj);
3160 
3161  setCurrentFolder(path);
3162  if (obj)
3163  {
3164  /* Before calling the extract() check if histogram exists:
3165  * if it does - flags for the given monitor are already set (and merged)
3166  * else - set the flags after the histogram is created.
3167  */
3168  MonitorElement *me = findObject(path, objname);
3169 
3170  /* Run histograms should be collated and not overwritten,
3171  * Lumi histograms should be overwritten (and collate flag is not checked)
3172  */
3173  bool overwrite = h.flags() & DQMNet::DQM_PROP_LUMI;
3174  bool collate = !(h.flags() & DQMNet::DQM_PROP_LUMI);
3175  extract(static_cast<TObject *>(obj), path, overwrite, collate);
3176 
3177  if (me == nullptr) {
3178  me = findObject(path, objname);
3179  me->data_.flags = h.flags();
3180  }
3181 
3182  delete obj;
3183  }
3184  }
3185 
3186  cd();
3187  return true;
3188 }
3189 
3195 void
3197 {
3199  const std::string *cleaned = 0;
3200  cleanTrailingSlashes(path, clean, cleaned);
3201  MonitorElement proto(cleaned, std::string());
3202 
3203  MEMap::iterator e = data_.end();
3204  MEMap::iterator i = data_.lower_bound(proto);
3205  while (i != e && isSubdirectory(*cleaned, *i->data_.dirname))
3206  data_.erase(i++);
3207 
3208  std::set<std::string>::iterator de = dirs_.end();
3209  std::set<std::string>::iterator di = dirs_.lower_bound(*cleaned);
3210  while (di != de && isSubdirectory(*cleaned, *di))
3211  dirs_.erase(di++);
3212 }
3213 
3215 void
3217 {
3218  MonitorElement proto(&dir, std::string());
3219  MEMap::iterator e = data_.end();
3220  MEMap::iterator i = data_.lower_bound(proto);
3221  while (i != e && isSubdirectory(dir, *i->data_.dirname))
3222  if (dir == *i->data_.dirname)
3223  data_.erase(i++);
3224  else
3225  ++i;
3226 }
3227 
3229 void
3231 {
3233 }
3234 
3237 void
3239 {
3240  removeElement(pwd_, name);
3241 }
3242 
3245 void
3246 DQMStore::removeElement(const std::string &dir, const std::string &name, bool warning /* = true */)
3247 {
3248  MonitorElement proto(&dir, name);
3249  MEMap::iterator pos = data_.find(proto);
3250  if (pos != data_.end())
3251  data_.erase(pos);
3252  else if (warning)
3253  std::cout << "DQMStore: WARNING: attempt to remove non-existent"
3254  << " monitor element '" << name << "' in '" << dir << "'\n";
3255 }
3256 
3262 QCriterion *
3264 {
3265  QCMap::const_iterator i = qtests_.find(qtname);
3266  QCMap::const_iterator e = qtests_.end();
3267  return (i == e ? 0 : i->second);
3268 }
3269 
3273 QCriterion *
3274 DQMStore::createQTest(const std::string &algoname, const std::string &qtname)
3275 {
3276  if (qtests_.count(qtname))
3277  raiseDQMError("DQMStore", "Attempt to create duplicate quality test '%s'",
3278  qtname.c_str());
3279 
3280  QAMap::iterator i = qalgos_.find(algoname);
3281  if (i == qalgos_.end())
3282  raiseDQMError("DQMStore", "Cannot create a quality test using unknown"
3283  " algorithm '%s'", algoname.c_str());
3284 
3285  QCriterion *qc = i->second(qtname);
3286  qc->setVerbose(verboseQT_);
3287 
3288  qtests_[qtname] = qc;
3289  return qc;
3290 }
3291 
3294 void
3296 {
3297  // Clean the path
3299  const std::string *cleaned = 0;
3300  cleanTrailingSlashes(dir, clean, cleaned);
3301 
3302  // Validate the path.
3303  if (cleaned->find_first_not_of(s_safe) != std::string::npos)
3304  raiseDQMError("DQMStore", "Monitor element path name '%s'"
3305  " uses unacceptable characters", cleaned->c_str());
3306 
3307  // Redirect to the pattern match version.
3308  useQTestByMatch(*cleaned + "/*", qtname);
3309 }
3310 
3312 int
3314 {
3315  QCriterion *qc = getQCriterion(qtname);
3316  if (! qc)
3317  raiseDQMError("DQMStore", "Cannot apply non-existent quality test '%s'",
3318  qtname.c_str());
3319 
3320  fastmatch * fm = new fastmatch( pattern );
3321 
3322  // Record the test for future reference.
3323  QTestSpec qts(fm, qc);
3324  qtestspecs_.push_back(qts);
3325 
3326  // Apply the quality test.
3327  MEMap::iterator mi = data_.begin();
3328  MEMap::iterator me = data_.end();
3329  std::string path;
3330  int cases = 0;
3331  for ( ; mi != me; ++mi)
3332  {
3333  path.clear();
3334  mergePath(path, *mi->data_.dirname, mi->data_.objname);
3335  if (fm->match(path))
3336  {
3337  ++cases;
3338  const_cast<MonitorElement &>(*mi).addQReport(qts.second);
3339  }
3340  }
3341 
3342  //return the number of matched cases
3343  return cases;
3344 }
3347 void
3349 {
3350 
3351  if (verbose_ > 0)
3352  std::cout << "DQMStore: running runQTests() with reset = "
3353  << ( reset_ ? "true" : "false" ) << std::endl;
3354 
3355  // Apply quality tests to each monitor element, skipping references.
3356  MEMap::iterator mi = data_.begin();
3357  MEMap::iterator me = data_.end();
3358  for ( ; mi != me; ++mi)
3359  if (! isSubdirectory(s_referenceDirName, *mi->data_.dirname))
3360  const_cast<MonitorElement &>(*mi).runQTests();
3361 
3362  reset_ = false;
3363 }
3364 
3368 int
3369 DQMStore::getStatus(const std::string &path /* = "" */) const
3370 {
3372  const std::string *cleaned = 0;
3373  cleanTrailingSlashes(path, clean, cleaned);
3374 
3376  MEMap::const_iterator mi = data_.begin();
3377  MEMap::const_iterator me = data_.end();
3378  for ( ; mi != me; ++mi)
3379  {
3380  if (! cleaned->empty() && ! isSubdirectory(*cleaned, *mi->data_.dirname))
3381  continue;
3382 
3383  if (mi->hasError())
3384  return dqm::qstatus::ERROR;
3385  else if (mi->hasWarning())
3386  status = dqm::qstatus::WARNING;
3387  else if (status < dqm::qstatus::WARNING
3388  && mi->hasOtherReport())
3389  status = dqm::qstatus::OTHER;
3390  }
3391  return status;
3392 }
3393 
3399 void
3401 {
3402  if (me)
3403  me->softReset();
3404 }
3405 
3406 // reverts action of softReset
3407 void
3409 {
3410  if (me)
3411  me->disableSoftReset();
3412 }
3413 
3416 void
3418 {
3419  if (me)
3420  me->setAccumulate(flag);
3421 }
3422 
3426 void
3428 {
3429  std::vector<std::string> contents;
3430  getContents(contents);
3431 
3432  std::cout << " ------------------------------------------------------------\n"
3433  << " Directory structure: \n"
3434  << " ------------------------------------------------------------\n";
3435 
3436  std::copy(contents.begin(), contents.end(),
3437  std::ostream_iterator<std::string>(std::cout, "\n"));
3438 
3439  std::cout << " ------------------------------------------------------------\n";
3440 }
3441 
3445 // check if the collate option is active on the DQMStore
3446 bool
3448 {
3449  return collateHistograms_;
3450 }
3454 // check if the monitor element is in auto-collation folder
3455 bool
3457 { return me && isSubdirectory(s_collateDirName, *me->data_.dirname); }
3461 
3463 void
3465 {
3466  if (scaleFlag_ == 0.0) return;
3467  if (verbose_ > 0)
3468  std::cout << " =========== " << " ScaleFlag " << scaleFlag_ << std::endl;
3469  double factor = scaleFlag_;
3470  int events = 1;
3471  if (dirExists("Info/EventInfo")) {
3472  if ( scaleFlag_ == -1.0) {
3473  MonitorElement * scale_me = get("Info/EventInfo/ScaleFactor");
3474  if (scale_me && scale_me->kind()==MonitorElement::DQM_KIND_REAL) factor = scale_me->getFloatValue();
3475  }
3476  MonitorElement * event_me = get("Info/EventInfo/processedEvents");
3477  if (event_me && event_me->kind()==MonitorElement::DQM_KIND_INT) events = event_me->getIntValue();
3478  }
3479  factor = factor/(events*1.0);
3480 
3481  MEMap::iterator mi = data_.begin();
3482  MEMap::iterator me = data_.end();
3483  for ( ; mi != me; ++mi)
3484  {
3485  MonitorElement &me = const_cast<MonitorElement &>(*mi);
3486  switch (me.kind())
3487  {
3489  {
3490  me.getTH1F()->Scale(factor);
3491  break;
3492  }
3494  {
3495  me.getTH1S()->Scale(factor);
3496  break;
3497  }
3499  {
3500  me.getTH1D()->Scale(factor);
3501  break;
3502  }
3504  {
3505  me.getTH2F()->Scale(factor);
3506  break;
3507  }
3509  {
3510  me.getTH2S()->Scale(factor);
3511  break;
3512  }
3514  {
3515  me.getTH2D()->Scale(factor);
3516  break;
3517  }
3519  {
3520  me.getTH3F()->Scale(factor);
3521  break;
3522  }
3524  {
3525  me.getTProfile()->Scale(factor);
3526  break;
3527  }
3529  {
3530  me.getTProfile2D()->Scale(factor);
3531  break;
3532  }
3533  default:
3534  if (verbose_ > 0)
3535  std::cout << " The DQM object '" << me.getFullname() << "' is not scalable object " << std::endl;
3536  continue;
3537  }
3538  }
3539 }
QCriterion * getQCriterion(const std::string &qtname) const
Definition: DQMStore.cc:3263
MonitorElement * getElement(const std::string &path)
Definition: DQMStore.cc:308
IGetter * igetter_
Definition: DQMStore.h:723
bool compare_strings_reverse(std::string const &pattern, std::string const &input) const
Definition: DQMStore.cc:207
std::pair< fastmatch *, QCriterion * > QTestSpec
Definition: DQMStore.h:693
TH2S * getTH2S(void) const
TH1S * getTH1S(void) const
T getUntrackedParameter(std::string const &, T const &) const
int i
Definition: DBlmapReader.cc:9
DQMStore(const edm::ParameterSet &pset, edm::ActivityRegistry &)
Definition: DQMStore.cc:499
static const lat::Regexp s_rxmeqr2("^st\\.(\\d+)\\.(.*)$")
MonitorElement * book2S(const char *name, const char *title, int nchX, double lowX, double highX, int nchY, double lowY, double highY)
Book 2S histogram.
Definition: DQMStore.cc:1167
bool containsAnyMonitorable(const std::string &path) const
Definition: DQMStore.cc:1761
uint32_t moduleId
Definition: DQMNet.h:104
inline::google::protobuf::uint32 size() const
tuple array
Definition: mps_check.py:181
bool isCollateME(MonitorElement *me) const
Definition: DQMStore.cc:3456
void resetUpdate(void)
reset &quot;was updated&quot; flag
tuple start
Check for commandline option errors.
Definition: dqm_diff.py:58
bool cdInto(const std::string &path) const
Definition: DQMStore.cc:2460
const ::std::string & full_pathname() const
void cd(void)
Definition: DQMStore.cc:338
int getStatus(const std::string &path="") const
Definition: DQMStore.cc:3369
void copyFrom(TH1 *from)
MonitorElement * initialise(Kind kind)
static const int OTHER
static void mergePath(std::string &path, const std::string &dir, const std::string &name)
Definition: DQMStore.cc:110
std::string algorithm
Definition: DQMNet.h:93
std::vector< std::string > getSubdirs(void) const
Definition: DQMStore.cc:1722
TProfile2D * getTProfile2D(void) const
FWCore Framework interface EventSetupRecordImplementation h
Helper function to determine trigger accepts.
MonitorElement * book1D(const char *name, const char *title, int nchX, double lowX, double highX)
Book 1D histogram.
Definition: DQMStore.cc:1017
The Signals That Services Can Subscribe To This is based on ActivityRegistry and is current per Services can connect to the signals distributed by the ActivityRegistry in order to monitor the activity of the application Each possible callback has some defined which we here list in angle e< void, edm::EventIDconst &, edm::Timestampconst & > We also list in braces which AR_WATCH_USING_METHOD_ is used for those or
Definition: Activities.doc:12
void rmdir(const std::string &fullpath)
Definition: DQMStore.cc:3196
static void collate3D(MonitorElement *me, TH3F *h, unsigned verbose)
Definition: DQMStore.cc:1626
bool match(std::string const &s) const
Definition: DQMStore.cc:249
bool readFile(const std::string &filename, bool overwrite=false, const std::string &path="", const std::string &prepend="", OpenRunDirs stripdirs=StripRunDirs, bool fileMustExist=true)
Definition: DQMStore.cc:3031
MonitorElement * findObject(const std::string &dir, const std::string &name, const uint32_t run=0, const uint32_t lumi=0, const uint32_t streamId=0, const uint32_t moduleId=0) const
Definition: DQMStore.cc:1901
static void collateProfile(MonitorElement *me, TProfile *h, unsigned verbose)
Definition: DQMStore.cc:1633
MonitorElement * book3D(const char *name, const char *title, int nchX, double lowX, double highX, int nchY, double lowY, double highY, int nchZ, double lowZ, double highZ)
Book 3D histogram.
Definition: DQMStore.cc:1279
void setLumi(uint32_t ls)
void cd(void)
Definition: DQMStore.cc:268
void cd(void)
go to top directory (ie. root)
Definition: DQMStore.cc:700
MonitorElement * get(const std::string &path)
Definition: DQMStore.cc:304
MonitorElement * book2DD(const char *name, const char *title, int nchX, double lowX, double highX, int nchY, double lowY, double highY)
Book 2D double histogram.
Definition: DQMStore.cc:1189
uint32_t streamId_
Definition: DQMStore.h:709
tuple lumi
Definition: fjr2json.py:35
static const std::string s_safe
Definition: DQMStore.cc:58
static void splitPath(std::string &dir, std::string &name, const std::string &path)
Definition: DQMStore.cc:97
uint32_t flags
Definition: DQMNet.h:98
const std::string & pwd(void)
Definition: DQMStore.cc:284
assert(m_qm.get())
void disableSoftReset(void)
reverts action of softReset
static void collate2DD(MonitorElement *me, TH2D *h, unsigned verbose)
Definition: DQMStore.cc:1619
std::vector< MonitorElement * > getMatchingContents(const std::string &pattern, lat::Regexp::Syntax syntaxType=lat::Regexp::Wildcard) const
Definition: DQMStore.cc:2033
static const int WARNING
TH3F * getTH3F(void) const
static const uint32_t DQM_PROP_TAGGED
Definition: DQMNet.h:54
TH1D * getTH1D(void) const
MatchingHeuristicEnum matching_
Definition: DQMStore.h:72
void runQTests(void)
run all quality tests
#define NULL
Definition: scimark2.h:8
static const uint32_t DQM_PROP_EFFICIENCY_PLOT
Definition: DQMNet.h:63
void softReset(void)
TH2D * getTH2D(void) const
uint32_t tag
Definition: DQMNet.h:99
bool reset_
Definition: DQMStore.h:701
const std::string * dirname
Definition: DQMNet.h:105
MonitorElement * book1DD(const char *name, const char *title, int nchX, double lowX, double highX)
Book 1S histogram.
Definition: DQMStore.cc:1049
void initializeFrom(const edm::ParameterSet &)
Definition: DQMStore.cc:571
#define nullptr
OpenRunDirs
Definition: DQMStore.h:84
void set_flags(::google::protobuf::uint32 value)
uint32_t run
Definition: DQMNet.h:101
uint32_t moduleId_
Definition: DQMStore.h:710
const ::std::string & streamed_histo() const
void initQCriterion(std::map< std::string, QCriterion *(*)(const std::string &)> &m)
Definition: DQMStore.cc:126
QCMap qtests_
Definition: DQMStore.h:717
static const std::string s_collateDirName
Definition: DQMStore.cc:57
MonitorElement * book(const std::string &dir, const std::string &name, const char *context)
Definition: DQMStore.cc:872
static const std::string s_monitorDirName
name of global monitoring folder (containing all sources subdirectories)
Definition: DQMStore.cc:55
std::mutex book_mutex_
Definition: DQMStore.h:721
MonitorElement * bookFloat(const char *name)
Book float.
Definition: DQMStore.cc:954
static std::string const input
Definition: EdmProvDump.cc:44
SaveReferenceTag
Definition: DQMStore.h:78
tuple result
Definition: mps_fire.py:83
static const lat::Regexp s_rxtrace("(.*)\\((.*)\\+0x.*\\).*")
void Fill(long long x)
static void cleanTrailingSlashes(const std::string &path, std::string &clean, const std::string *&cleaned)
Definition: DQMStore.cc:80
Preallocate preallocateSignal_
signal is emitted before beginJob
void tag(MonitorElement *me, unsigned int myTag)
Definition: DQMStore.cc:1657
~DQMStore(void)
Definition: DQMStore.cc:557
void disableSoftReset(MonitorElement *me)
Definition: DQMStore.cc:3408
unsigned int maxNumberOfStreams() const
Definition: SystemBounds.h:43
static const lat::Regexp s_rxmeval("^<(.*)>(i|f|s|e|t|qr)=(.*)</\\1>$")
void forceReset(void)
Definition: DQMStore.cc:2093
static bool isSubdirectory(const std::string &ofdir, const std::string &path)
Definition: DQMStore.cc:70
std::vector< MonitorElement * > getAllContents(const std::string &path, uint32_t runNumber=0, uint32_t lumi=0) const
Definition: DQMStore.cc:1984
fastmatch(std::string const &_fastString)
Definition: DQMStore.cc:131
unsigned verboseQT_
Definition: DQMStore.h:700
static const uint32_t DQM_PROP_HAS_REFERENCE
Definition: DQMNet.h:53
void removeContents(void)
erase all monitoring elements in current directory (not including subfolders);
Definition: DQMStore.cc:3230
QTestSpecs qtestspecs_
Definition: DQMStore.h:719
double scaleFlag_
Definition: DQMStore.h:702
void deleteUnusedLumiHistograms(uint32_t run, uint32_t lumi)
Definition: DQMStore.cc:2117
void get_info(const dqmstorepb::ROOTFilePB_Histo &, std::string &dirname, std::string &objname, TObject **obj)
Definition: DQMStore.cc:3094
void watchPostSourceRun(PostSourceRun::slot_type const &iSlot)
MonitorElement * bookString(const char *name, const char *value)
Book string.
Definition: DQMStore.cc:983
void setAccumulate(bool)
uint32_t lumi
Definition: DQMNet.h:102
bool isCollate(void) const
Definition: DQMStore.cc:3447
void removeElement(const std::string &name)
Definition: DQMStore.cc:3238
void addProfiles(TProfile *h1, TProfile *h2, TProfile *sum, float c1, float c2)
def move
Definition: eostools.py:510
static void collateProfile2D(MonitorElement *me, TProfile2D *h, unsigned verbose)
Definition: DQMStore.cc:1643
double getFloatValue(void) const
void tag(MonitorElement *, unsigned int)
Definition: DQMStore.cc:288
TH1 * getTH1(void) const
double f[11][100]
uint32_t run_
Definition: DQMStore.h:708
MonitorElement * bookProfile(const char *name, const char *title, int nchX, double lowX, double highX, int nchY, double lowY, double highY, const char *option="s")
Definition: DQMStore.cc:1331
QCriterion * makeQCriterion(const std::string &qtname)
Definition: DQMStore.cc:121
#define end
Definition: vmac.h:37
void setVerbose(unsigned level)
Definition: DQMStore.cc:687
void softReset(MonitorElement *me)
Definition: DQMStore.cc:3400
std::string pwd_
Definition: DQMStore.h:713
Kind kind(void) const
Get the type of the monitor element.
void runQTests(void)
Definition: DQMStore.cc:3348
TObject * extractNextObject(TBufferFile &) const
Definition: DQMStore.cc:3086
lat::Regexp * regexp_
Definition: DQMStore.h:70
IBooker * ibooker_
Definition: DQMStore.h:722
MonitorElement * get(const std::string &path) const
get ME from full pathname (e.g. &quot;my/long/dir/my_histo&quot;)
Definition: DQMStore.cc:1771
QAMap qalgos_
Definition: DQMStore.h:718
const std::string getFullname(void) const
get full name of ME including Pathname
std::vector< MonitorElement * > getContents(const std::string &path) const
Definition: DQMStore.cc:1800
string key
FastSim: produces sample of signal events, overlayed with premixed minbias events.
std::string readSelectedDirectory_
Definition: DQMStore.h:707
std::vector< std::string > getMEs(void)
Definition: DQMStore.cc:326
std::string objname
Definition: DQMNet.h:106
void mergeAndResetMEsRunSummaryCache(uint32_t run, uint32_t streamId, uint32_t moduleId)
Definition: DQMStore.cc:359
std::string fastString_
Definition: DQMStore.h:71
std::vector< T * > clean
Definition: MVATrainer.cc:156
std::string qtname
Definition: DQMNet.h:92
DQMNet::CoreObject data_
bool dirExists(const std::string &path) const
true if directory exists
Definition: DQMStore.cc:788
void savePB(const std::string &filename, const std::string &path="", const uint32_t run=0, const uint32_t lumi=0, const bool resetMEsAfterWriting=false)
Definition: DQMStore.cc:2502
void getAllTags(std::vector< std::string > &into) const
Definition: DQMStore.cc:1931
bool dirExists(const std::string &path)
Definition: DQMStore.cc:334
bool load(const std::string &filename, OpenRunDirs stripdirs=StripRunDirs, bool fileMustExist=true)
Definition: DQMStore.cc:3004
void scaleElements(void)
Definition: DQMStore.cc:3464
~fastmatch()
Definition: DQMStore.cc:201
static void collate1DD(MonitorElement *me, TH1D *h, unsigned verbose)
Definition: DQMStore.cc:1598
void tagAllContents(const std::string &path, unsigned int myTag)
Definition: DQMStore.cc:1700
void setCurrentFolder(const std::string &fullpath)
Definition: DQMStore.cc:276
MonitorElement * initialise(MonitorElement *me, const std::string &path)
void watchPostSourceLumi(PostSourceLumi::slot_type const &iSlot)
void goUp(void)
Definition: DQMStore.cc:280
bool containsAnyMonitorable(const std::string &path)
Definition: DQMStore.cc:330
void tagContents(const std::string &, unsigned int)
Definition: DQMStore.cc:292
const ::dqmstorepb::ROOTFilePB_Histo & histo(int index) const
unsigned verbose_
Definition: DQMStore.h:699
void set_size(::google::protobuf::uint32 value)
MEMap data_
Definition: DQMStore.h:714
part
Definition: HCALResponse.h:20
int64_t getIntValue(void) const
static const std::string s_referenceDirName
Definition: DQMStore.cc:56
void print_trace(const std::string &dir, const std::string &name)
Definition: DQMStore.cc:631
int useQTestByMatch(const std::string &pattern, const std::string &qtname)
attach quality test &lt;qc&gt; to monitor elements matching &lt;pattern&gt;.
Definition: DQMStore.cc:3313
std::vector< MonitorElement * > getAllContents(const std::string &path, uint32_t runNumber=0, uint32_t lumi=0)
Definition: DQMStore.cc:298
TH1F * getTH1F(void) const
static void collate1D(MonitorElement *me, TH1F *h, unsigned verbose)
Definition: DQMStore.cc:1584
tuple demangled
Definition: symbols.py:61
static const lat::Regexp s_rxpbfile(".*\\.pb$")
std::vector< std::string > getMEs(void) const
get list of (non-dir) MEs of current directory
Definition: DQMStore.cc:1745
std::vector< std::string > getSubdirs(void)
Definition: DQMStore.cc:322
DQMStore * owner_
Definition: DQMStore.h:187
void setCurrentFolder(const std::string &fullpath)
Definition: DQMStore.cc:346
bool resetMe(void) const
true if ME should be reset at end of monitoring cycle
void set_full_pathname(const ::std::string &value)
unsigned int readDirectory(TFile *file, bool overwrite, const std::string &path, const std::string &prepend, const std::string &curdir, OpenRunDirs stripdirs)
Definition: DQMStore.cc:2834
void setVerbose(int verbose)
probability limits for warnings, errors
Definition: QTest.h:116
bool extract(TObject *obj, const std::string &dir, bool overwrite, bool collateHistograms)
Definition: DQMStore.cc:2159
bool forceResetOnBeginLumi_
Definition: DQMStore.h:706
T dot(const Basic3DVector &v) const
Scalar product, or &quot;dot&quot; product, with a vector of same type.
std::vector< boost::shared_ptr< fireworks::OptionNode > > Options
void tagContents(const std::string &path, unsigned int myTag)
tag all children of folder (does NOT include subfolders)
Definition: DQMStore.cc:1688
tuple events
Definition: patZpeak.py:19
if(dp >Float(M_PI)) dp-
inline::dqmstorepb::ROOTFilePB_Histo * add_histo()
void save(const std::string &filename, const std::string &path="", const std::string &pattern="", const std::string &rewrite="", const uint32_t run=0, const uint32_t lumi=0, SaveReferenceTag ref=SaveWithReference, int minStatus=dqm::qstatus::STATUS_OK, const std::string &fileupdate="RECREATE", const bool resetMEsAfterWriting=false)
Definition: DQMStore.cc:2632
bool readFilePB(const std::string &filename, bool overwrite=false, const std::string &path="", const std::string &prepend="", OpenRunDirs stripdirs=StripRunDirs, bool fileMustExist=true)
Definition: DQMStore.cc:3115
TProfile * getTProfile(void) const
void useQTest(const std::string &dir, const std::string &qtname)
Definition: DQMStore.cc:3295
tuple filename
Definition: lut2db_cfg.py:20
std::string message
Definition: DQMNet.h:91
void goUp(void)
equivalent to &quot;cd ..&quot;
Definition: DQMStore.cc:734
bool open(const std::string &filename, bool overwrite=false, const std::string &path="", const std::string &prepend="", OpenRunDirs stripdirs=KeepRunDirs, bool fileMustExist=true)
Definition: DQMStore.cc:2989
inline::google::protobuf::uint32 flags() const
static const int STATUS_OK
void setAccumulate(MonitorElement *me, bool flag)
Definition: DQMStore.cc:3417
tuple cout
Definition: gather_cfg.py:145
void setEfficiencyFlag(void)
static void collate1S(MonitorElement *me, TH1S *h, unsigned verbose)
Definition: DQMStore.cc:1591
void Reset(std::vector< TH2F > &depth)
std::ofstream * stream_
Definition: DQMStore.h:711
QCriterion * createQTest(const std::string &algoname, const std::string &qtname)
Definition: DQMStore.cc:3274
static bool checkBinningMatches(MonitorElement *me, TH1 *h, unsigned verbose)
Definition: DQMStore.cc:1557
dbl *** dir
Definition: mlp_gen.cc:35
volatile std::atomic< bool > shutdown_flag false
void showDirStructure(void) const
Definition: DQMStore.cc:3427
void reset(void)
Definition: DQMStore.cc:2069
bool deleteObject(T *fObject, const std::string &fInput, const std::string &fInputTag, HcalDbTool::IOVRun fInputRun, bool fVerbose)
TH2F * getTH2F(void) const
static void collate2D(MonitorElement *me, TH2F *h, unsigned verbose)
Definition: DQMStore.cc:1605
MonitorElement * bookInt(const char *name)
Book int.
Definition: DQMStore.cc:924
MonitorElement * book2D(const char *name, const char *title, int nchX, double lowX, double highX, int nchY, double lowY, double highY)
Book 2D histogram.
Definition: DQMStore.cc:1145
tuple collateHistograms
for(const auto &isodef:isoDefs)
long double T
uint32_t streamId
Definition: DQMNet.h:103
void mergeAndResetMEsLuminositySummaryCache(uint32_t run, uint32_t lumi, uint32_t streamId, uint32_t moduleId)
Definition: DQMStore.cc:430
float qtresult
Definition: DQMNet.h:90
std::set< std::string > dirs_
Definition: DQMStore.h:715
bool collateHistograms_
Definition: DQMStore.h:703
void Reset(void)
reset ME (ie. contents, errors, etc)
static const uint32_t DQM_PROP_LUMI
Definition: DQMNet.h:60
static std::string const source
Definition: EdmProvDump.cc:43
bool LSbasedMode_
Definition: DQMStore.h:705
void addQReport(const DQMNet::QValue &desc, QCriterion *qc)
Add quality report, from DQMStore.
MonitorElement * book1S(const char *name, const char *title, int nchX, double lowX, double highX)
Book 1S histogram.
Definition: DQMStore.cc:1033
tuple size
Write out results.
static const lat::Regexp s_rxmeqr1("^st:(\\d+):([-+e.\\d]+):([^:]*):(.*)$")
void makeDirectory(const std::string &path)
Definition: DQMStore.cc:747
void connect(U iFunc)
Definition: Signal.h:63
bool compare_strings(std::string const &pattern, std::string const &input) const
Definition: DQMStore.cc:228
void setCurrentFolder(const std::string &fullpath)
Definition: DQMStore.cc:723
static void collate2S(MonitorElement *me, TH2S *h, unsigned verbose)
Definition: DQMStore.cc:1612
static const int ERROR
How EventSelector::AcceptEvent() decides whether to accept an event for output otherwise it is excluding the probing of A single or multiple positive and the trigger will pass if any such matching triggers are PASS or EXCEPTION[A criterion thatmatches no triggers at all is detected and causes a throw.] A single negative with an expectation of appropriate bit checking in the decision and the trigger will pass if any such matching triggers are FAIL or EXCEPTION A wildcarded negative criterion that matches more than one trigger in the trigger list("!*","!HLTx*"if it matches 2 triggers or more) will accept the event if all the matching triggers are FAIL.It will reject the event if any of the triggers are PASS or EXCEPTION(this matches the behavior of"!*"before the partial wildcard feature was incorporated).Triggers which are in the READY state are completely ignored.(READY should never be returned since the trigger paths have been run
tuple status
Definition: mps_update.py:57
const std::string & pwd(void) const
Definition: DQMStore.cc:695
bool enableMultiThread_
Definition: DQMStore.h:704
void set_streamed_histo(const ::std::string &value)
static bool CheckBinLabels(const TAxis *a1, const TAxis *a2)
Check the consistency of the axis labels.
MonitorElement * bookProfile2D(const char *name, const char *title, int nchX, double lowX, double highX, int nchY, double lowY, double highY, int nchZ, double lowZ, double highZ, const char *option="s")
Definition: DQMStore.cc:1475
void raiseDQMError(const char *context, const char *fmt,...)
Definition: DQMError.cc:11