00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012 #include "DQMServices/Components/src/DQMStoreStats.h"
00013 #include "FWCore/ServiceRegistry/interface/Service.h"
00014 #include "FWCore/MessageLogger/interface/JobReport.h"
00015
00016 using namespace std;
00017 using namespace edm;
00018
00019 template <class T>
00020 static unsigned int getEmptyMetric(T * array, int lenx, int leny, int lenz)
00021 {
00022
00023 unsigned int len = lenx+leny+lenz;
00024 unsigned int result=0;
00025
00026
00027
00028 for (unsigned int i=1; i<len; ++i)
00029 {
00030
00031 if (i%(lenx-1)==0)
00032 continue;
00033 if (i%lenx==0)
00034 continue;
00035 if (i%(lenx+leny-1)==0)
00036 continue;
00037 if (i%(lenx+leny)==0)
00038 continue;
00039 if (i%(lenx+leny+lenz-1)==0)
00040 continue;
00041
00042 if (array[i] == 0)
00043 result += 1;
00044 }
00045
00046 return result;
00047 }
00048
00049
00050
00051
00052 DQMStoreStats::DQMStoreStats( const edm::ParameterSet& ps )
00053 : subsystem_ (""),
00054 subfolder_ (""),
00055 nbinsglobal_ (0),
00056 nbinssubsys_ (0),
00057 nmeglobal_ (0),
00058 nmesubsys_ (0),
00059 maxbinsglobal_ (0),
00060 maxbinssubsys_ (0),
00061 maxbinsmeglobal_ (""),
00062 maxbinsmesubsys_ (""),
00063 statsdepth_ (1),
00064 pathnamematch_ ("*"),
00065 verbose_ (0)
00066 {
00067 parameters_ = ps;
00068 pathnamematch_ = ps.getUntrackedParameter<std::string>( "pathNameMatch", pathnamematch_ );
00069 statsdepth_ = ps.getUntrackedParameter<int>( "statsDepth", statsdepth_ );
00070 verbose_ = ps.getUntrackedParameter<int>( "verbose", verbose_ );
00071 dumpMemHistory_ = ps.getUntrackedParameter<bool>( "dumpMemoryHistory", false );
00072 runonendrun_ = ps.getUntrackedParameter<bool>( "runOnEndRun", true );
00073 runonendjob_ = ps.getUntrackedParameter<bool>( "runOnEndJob", false );
00074 runonendlumi_ = ps.getUntrackedParameter<bool>( "runOnEndLumi", false );
00075 runineventloop_ = ps.getUntrackedParameter<bool>( "runInEventLoop", false );
00076 dumpToFWJR_ = ps.getUntrackedParameter<bool>( "dumpToFWJR", false );
00077
00078 startingTime_ = time( 0 );
00079 }
00080
00081 DQMStoreStats::~DQMStoreStats(){
00082 }
00083
00084 void DQMStoreStats::calcIgProfDump(Folder &root)
00085 {
00086 std::ofstream stream("dqm-bin-stats.sql");
00087 stream << ""
00088 " PRAGMA journal_mode=OFF;"
00089 " PRAGMA count_changes=OFF;"
00090 " DROP TABLE IF EXISTS files;"
00091 " DROP TABLE IF EXISTS symbols;"
00092 " DROP TABLE IF EXISTS mainrows;"
00093 " DROP TABLE IF EXISTS children;"
00094 " DROP TABLE IF EXISTS parents;"
00095 " DROP TABLE IF EXISTS summary;"
00096 " CREATE TABLE children ("
00097 " self_id INTEGER CONSTRAINT self_exists REFERENCES mainrows(id),"
00098 " parent_id INTEGER CONSTRAINT parent_exists REFERENCES mainrows(id),"
00099 " from_parent_count INTEGER,"
00100 " from_parent_calls INTEGER,"
00101 " from_parent_paths INTEGER,"
00102 " pct REAL"
00103 " );"
00104 " CREATE TABLE files ("
00105 " id,"
00106 " name TEXT"
00107 " );"
00108 " CREATE TABLE mainrows ("
00109 " id INTEGER PRIMARY KEY,"
00110 " symbol_id INTEGER CONSTRAINT symbol_id_exists REFERENCES symbols(id),"
00111 " self_count INTEGER,"
00112 " cumulative_count INTEGER,"
00113 " kids INTEGER,"
00114 " self_calls INTEGER,"
00115 " total_calls INTEGER,"
00116 " self_paths INTEGER,"
00117 " total_paths INTEGER,"
00118 " pct REAL"
00119 " );"
00120 " CREATE TABLE parents ("
00121 " self_id INTEGER CONSTRAINT self_exists REFERENCES mainrows(id),"
00122 " child_id INTEGER CONSTRAINT child_exists REFERENCES mainrows(id),"
00123 " to_child_count INTEGER,"
00124 " to_child_calls INTEGER,"
00125 " to_child_paths INTEGER,"
00126 " pct REAL"
00127 " );"
00128 " CREATE TABLE summary ("
00129 " counter TEXT,"
00130 " total_count INTEGER,"
00131 " total_freq INTEGER,"
00132 " tick_period REAL"
00133 " );"
00134 " CREATE TABLE symbols ("
00135 " id,"
00136 " name TEXT,"
00137 " filename_id INTEGER CONSTRAINT file_id_exists REFERENCES files(id)"
00138 " );"
00139 " CREATE UNIQUE INDEX fileIndex ON files (id);"
00140 " CREATE INDEX selfCountIndex ON mainrows(self_count);"
00141 " CREATE UNIQUE INDEX symbolsIndex ON symbols (id);"
00142 " CREATE INDEX totalCountIndex ON mainrows(cumulative_count);" << std::endl;
00143
00144 std::string sql_statement("");
00145
00146 root.files(sql_statement);
00147 root.symbols(sql_statement);
00148 root.mainrows_cumulative(sql_statement);
00149 root.summary(sql_statement);
00150 VIterator<Folder *> subsystems = root.CreateIterator() ;
00151 size_t ii=0;
00152 for(subsystems.First() ; !subsystems.IsDone() ; subsystems.Next(), ++ii)
00153 {
00154 subsystems.CurrentItem()->mainrows(sql_statement);
00155 subsystems.CurrentItem()->parents(sql_statement);
00156 subsystems.CurrentItem()->children(sql_statement);
00157 }
00158 stream << sql_statement << std::endl;
00159 }
00160
00167 int DQMStoreStats::calcstats( int mode = DQMStoreStats::considerAllME ) {
00168
00170 nbinsglobal_ = 0;
00171 nbinssubsys_ = 0;
00172 maxbinsglobal_ = 0;
00173 maxbinssubsys_ = 0;
00174 std::string path = "";
00175 std::string subsystemname = "";
00176 std::string subfoldername = "";
00177 size_t subsysStringEnd = 0, subfolderStringBegin = 0, subfolderStringEnd = 0;
00178
00179
00180 std::vector<MonitorElement*> melist;
00181 melist = dbe_->getMatchingContents( pathnamematch_ );
00182
00183 Folder dbeFolder("root");
00184 DQMStoreStatsTopLevel dqmStoreStatsTopLevel;
00185
00186
00187 typedef std::vector <MonitorElement*>::iterator meIt;
00188 for(meIt it = melist.begin(); it != melist.end(); ++it) {
00189
00190
00191 if( mode == DQMStoreStats::considerOnlyLumiProductME &&
00192 !( (*it)->getLumiFlag() ) ) continue;
00193
00194
00195 std::string path = (*it)->getPathname();
00196
00197 subfolderStringBegin = 0;
00198 Folder * curr = &dbeFolder;
00199 while(1)
00200 {
00201 subfolderStringEnd = path.find( '/', subfolderStringBegin );
00202 if( std::string::npos == subfolderStringEnd )
00203 {
00204 curr = curr->cd(path.substr( subfolderStringBegin, path.size()-subfolderStringBegin ));
00205 break;
00206 }
00207 curr = curr->cd(path.substr( subfolderStringBegin, subfolderStringEnd-subfolderStringBegin ));
00208 subfolderStringBegin = ++subfolderStringEnd < path.size() ? subfolderStringEnd : path.size();
00209 }
00210
00211
00212 if( 0 == path.size() ) continue;
00213
00214 subsysStringEnd = path.find( '/', 0 );
00215 if( std::string::npos == subsysStringEnd ) subsysStringEnd = path.size();
00216
00217
00218 if( path.substr( 0, subsysStringEnd ) != subsystemname ) {
00219 DQMStoreStatsSubsystem aSubsystem;
00220 subsystemname = path.substr( 0, subsysStringEnd );
00221 aSubsystem.subsystemName_ = subsystemname;
00222 dqmStoreStatsTopLevel.push_back( aSubsystem );
00223 subfoldername = "";
00224 }
00225
00226
00227 if( path.size() == subsysStringEnd ) {
00228
00229 DQMStoreStatsSubfolder aSubfolder;
00230 aSubfolder.subfolderName_ = subsystemname;
00231 dqmStoreStatsTopLevel.back().push_back( aSubfolder );
00232 }
00233
00234 else {
00235
00236
00237 subfolderStringEnd = path.find( '/', subsysStringEnd + 1 );
00238 if( std::string::npos == subfolderStringEnd ) subfolderStringEnd = path.size();
00239
00240
00241 if( path.substr( subsysStringEnd + 1, subfolderStringEnd - subsysStringEnd - 1 ) != subfoldername ) {
00242 subfoldername = path.substr( subsysStringEnd + 1, subfolderStringEnd - subsysStringEnd - 1 );
00243 DQMStoreStatsSubfolder aSubfolder;
00244 aSubfolder.subfolderName_ = subfoldername;
00245 dqmStoreStatsTopLevel.back().push_back( aSubfolder );
00246 }
00247
00248 }
00249
00250
00251 DQMStoreStatsSubfolder& currentSubfolder = dqmStoreStatsTopLevel.back().back();
00252
00253 switch( (*it)->kind() ) {
00254
00255
00256 case MonitorElement::DQM_KIND_TH1F:
00257 currentSubfolder.AddBinsF( (*it)->getNbinsX(), getEmptyMetric((*it)->getTH1F()->GetArray(), (*it)->getTH1F()->fN, 0, 0) );
00258 curr->update( (*it)->getNbinsX(), getEmptyMetric((*it)->getTH1F()->GetArray(), (*it)->getTH1F()->fN, 0, 0), (*it)->getNbinsX()*sizeof( float ) );
00259 break;
00260 case MonitorElement::DQM_KIND_TH1S:
00261 currentSubfolder.AddBinsS( (*it)->getNbinsX(), getEmptyMetric((*it)->getTH1S()->GetArray(), (*it)->getTH1S()->fN, 0, 0) );
00262 curr->update( (*it)->getNbinsX(), getEmptyMetric((*it)->getTH1S()->GetArray(), (*it)->getTH1S()->fN, 0, 0), (*it)->getNbinsX()*sizeof( short ) );
00263 break;
00264 case MonitorElement::DQM_KIND_TH1D:
00265 currentSubfolder.AddBinsD( (*it)->getNbinsX(), getEmptyMetric((*it)->getTH1D()->GetArray(), (*it)->getTH1D()->fN, 0, 0) );
00266 curr->update( (*it)->getNbinsX(), getEmptyMetric((*it)->getTH1D()->GetArray(), (*it)->getTH1D()->fN, 0, 0), (*it)->getNbinsX()*sizeof( double ) );
00267 break;
00268 case MonitorElement::DQM_KIND_TPROFILE:
00269 currentSubfolder.AddBinsD( (*it)->getNbinsX(), getEmptyMetric((*it)->getTProfile()->GetArray(), (*it)->getTProfile()->fN, 0, 0) );
00270 curr->update( (*it)->getNbinsX(), getEmptyMetric((*it)->getTProfile()->GetArray(), (*it)->getTProfile()->fN, 0, 0), (*it)->getNbinsX()*sizeof( double ) );
00271 break;
00272
00273
00274 case MonitorElement::DQM_KIND_TH2F:
00275 currentSubfolder.AddBinsF( (*it)->getNbinsX() * (*it)->getNbinsY(), getEmptyMetric((*it)->getTH2F()->GetArray(), (*it)->getNbinsX()+2, (*it)->getNbinsY()+2, 0) );
00276 curr->update( (*it)->getNbinsX() * (*it)->getNbinsY(), getEmptyMetric((*it)->getTH2F()->GetArray(), (*it)->getNbinsX()+2, (*it)->getNbinsY()+2, 0), (*it)->getNbinsX() * (*it)->getNbinsY()*sizeof(float) );
00277 break;
00278 case MonitorElement::DQM_KIND_TH2S:
00279 currentSubfolder.AddBinsS( (*it)->getNbinsX() * (*it)->getNbinsY(), getEmptyMetric((*it)->getTH2S()->GetArray(), (*it)->getNbinsX()+2, (*it)->getNbinsY()+2, 0) );
00280 curr->update( (*it)->getNbinsX() * (*it)->getNbinsY(), getEmptyMetric((*it)->getTH2S()->GetArray(), (*it)->getNbinsX()+2, (*it)->getNbinsY()+2, 0), (*it)->getNbinsX() * (*it)->getNbinsY()*sizeof(short) );
00281 break;
00282 case MonitorElement::DQM_KIND_TH2D:
00283 currentSubfolder.AddBinsD( (*it)->getNbinsX() * (*it)->getNbinsY(), getEmptyMetric((*it)->getTH2D()->GetArray(), (*it)->getNbinsX()+2, (*it)->getNbinsY()+2, 0) );
00284 curr->update( (*it)->getNbinsX() * (*it)->getNbinsY(), getEmptyMetric((*it)->getTH2D()->GetArray(), (*it)->getNbinsX()+2, (*it)->getNbinsY()+2, 0), (*it)->getNbinsX() * (*it)->getNbinsY()*sizeof(double) );
00285 break;
00286 case MonitorElement::DQM_KIND_TPROFILE2D:
00287 currentSubfolder.AddBinsD( (*it)->getNbinsX() * (*it)->getNbinsY(), getEmptyMetric((*it)->getTProfile2D()->GetArray(), (*it)->getNbinsX()+2, (*it)->getNbinsY()+2, 0) );
00288 curr->update( (*it)->getNbinsX() * (*it)->getNbinsY(), getEmptyMetric((*it)->getTProfile2D()->GetArray(), (*it)->getNbinsX()+2, (*it)->getNbinsY()+2, 0), (*it)->getNbinsX() * (*it)->getNbinsY()*sizeof(double) );
00289 break;
00290
00291
00292 case MonitorElement::DQM_KIND_TH3F:
00293 currentSubfolder.AddBinsF( (*it)->getNbinsX() * (*it)->getNbinsY() * (*it)->getNbinsZ(), getEmptyMetric( (*it)->getTH3F()->GetArray(), (*it)->getNbinsX()+2, (*it)->getNbinsY()+2, (*it)->getNbinsZ()+2 ) );
00294 curr->update( (*it)->getNbinsX() * (*it)->getNbinsY() * (*it)->getNbinsZ(),
00295 getEmptyMetric( (*it)->getTH3F()->GetArray(), (*it)->getNbinsX()+2, (*it)->getNbinsY()+2, (*it)->getNbinsZ()+2 ),
00296 (*it)->getNbinsX() * (*it)->getNbinsY() * (*it)->getNbinsZ()*sizeof(float));
00297 break;
00298
00299 default: {}
00300
00301
00302
00303
00304
00305
00306 }
00307 }
00308
00309 if( mode == DQMStoreStats::considerAllME )
00310 calcIgProfDump(dbeFolder);
00311
00312
00313
00314 std::cout << endl;
00315 std::cout << "===========================================================================================" << std::endl;
00316 std::cout << "[DQMStoreStats::calcstats] -- Dumping stats results ";
00317 if( mode == DQMStoreStats::considerAllME ) std::cout << "FOR ALL ME" << std::endl;
00318 else if( mode == DQMStoreStats::considerOnlyLumiProductME ) std::cout << "FOR LUMI PRODUCTS ONLY" << std::endl;
00319 std::cout << "===========================================================================================" << std::endl;
00320 std::cout << endl;
00321
00322 std::cout << "------------------------------------------------------------------------------------------" << std::endl;
00323 std::cout << "Configuration:" << std::endl;
00324 std::cout << "------------------------------------------------------------------------------------------" << std::endl;
00325 std::cout << " > running ";
00326 if (runonendrun_) std::cout << "on run end." << std::endl;
00327 if (runonendlumi_) std::cout << "on lumi end." << std::endl;
00328 if (runonendjob_) std::cout << "on job end." << std::endl;
00329 if (runineventloop_) std::cout << "in event loop." << std::endl;
00330 std::cout << " > pathNameMatch = \"" << pathnamematch_ << "\"" << std::endl;
00331 std::cout << std::endl;
00332
00333
00334 std::cout << "------------------------------------------------------------------------------------------" << std::endl;
00335 std::cout << "Top level folder tree:" << std::endl;
00336 std::cout << "------------------------------------------------------------------------------------------" << std::endl;
00337 for( DQMStoreStatsTopLevel::const_iterator it0 = dqmStoreStatsTopLevel.begin(); it0 < dqmStoreStatsTopLevel.end(); ++it0 ) {
00338 std::cout << it0->subsystemName_ << " (subsystem)" << std::endl;
00339
00340 for( DQMStoreStatsSubsystem::const_iterator it1 = it0->begin(); it1 < it0->end(); ++it1 ) {
00341 std::cout << " |--> " << it1->subfolderName_ << " (subfolder)" << std::endl;
00342 }
00343
00344 }
00345
00346
00347
00348 unsigned int overallNHistograms = 0, overallNBins = 0, overallNEmptyBins = 0, overallNBytes = 0;
00349
00350 std::cout << std::endl;
00351 std::cout << "------------------------------------------------------------------------------------------" << std::endl;
00352 std::cout << "Detailed ressource usage information ";
00353 if( mode == DQMStoreStats::considerAllME ) std::cout << "FOR ALL ME" << std::endl;
00354 else if( mode == DQMStoreStats::considerOnlyLumiProductME ) std::cout << "FOR LUMI PRODUCTS ONLY" << std::endl;
00355 std::cout << "------------------------------------------------------------------------------------------" << std::endl;
00356 std::cout << "subsystem/folder histograms bins Empty bins Empty/Total bins per MB kB per" << std::endl;
00357 std::cout << " (total) (total) (total) histogram (total) histogram " << std::endl;
00358 std::cout << "------------------------------------------------------------------------------------------" << std::endl;
00359 for( DQMStoreStatsTopLevel::const_iterator it0 = dqmStoreStatsTopLevel.begin(); it0 < dqmStoreStatsTopLevel.end(); ++it0 ) {
00360 std::cout << it0->subsystemName_ << std::endl;
00361
00362 unsigned int nHistograms = 0, nBins = 0, nEmptyBins = 0, nBytes = 0;
00363
00364 for( DQMStoreStatsSubsystem::const_iterator it1 = it0->begin(); it1 < it0->end(); ++it1 ) {
00365
00366
00367 std::string thisSubfolderName( it1->subfolderName_ );
00368 if( thisSubfolderName.size() > 30 ) {
00369 thisSubfolderName.resize( 30 );
00370 thisSubfolderName.replace( thisSubfolderName.size() - 3, 3, 3, '.' );
00371 }
00372
00373 std::cout << " -> " << std::setw( 30 ) << std::left << thisSubfolderName;
00374 std::cout << std::setw( 14 ) << std::right << it1->totalHistos_;
00375 std::cout << std::setw( 14 ) << std::right << it1->totalBins_;
00376 std::cout << std::setw( 14 ) << std::right << it1->totalEmptyBins_;
00377 std::cout << std::setw( 14 ) << std::right << std::setprecision( 3 ) << (float)it1->totalEmptyBins_/(float)it1->totalBins_;
00378
00379
00380 if( it1->totalHistos_ ) {
00381 std::cout << std::setw( 14 ) << std::right << std::setprecision( 3 ) << it1->totalBins_ / float( it1->totalHistos_ );
00382 }
00383 else std::cout << std::setw( 14 ) << std::right << "-";
00384
00385 std::cout << std::setw( 14 ) << std::right << std::setprecision( 3 ) << it1->totalMemory_ / 1024. / 1024.;
00386
00387
00388 if( it1->totalHistos_ ) {
00389 std::cout << std::setw( 14 ) << std::right << std::setprecision( 3 ) << it1->totalMemory_ / 1024. / it1->totalHistos_;
00390 }
00391 else std::cout << std::setw( 14 ) << std::right << "-";
00392
00393 std::cout << std::endl;
00394
00395
00396 nHistograms += it1->totalHistos_;
00397 nBins += it1->totalBins_;
00398 nEmptyBins += it1->totalEmptyBins_;
00399 nBytes += it1->totalMemory_;
00400
00401 }
00402
00403
00404
00405
00406 overallNHistograms += nHistograms;
00407 overallNBins += nBins;
00408 overallNEmptyBins += nEmptyBins;
00409 overallNBytes += nBytes;
00410
00411
00412 std::cout << " " << std::setw( 30 ) << std::left << "SUBSYSTEM TOTAL";
00413 std::cout << std::setw( 14 ) << std::right << nHistograms;
00414 std::cout << std::setw( 14 ) << std::right << nBins;
00415 std::cout << std::setw( 14 ) << std::right << nEmptyBins;
00416 std::cout << std::setw( 14 ) << std::right << (float)nEmptyBins/(float)nBins;
00417 std::cout << std::setw( 14 ) << std::right << std::setprecision( 3 ) << nBins / float( nHistograms );
00418 std::cout << std::setw( 14 ) << std::right << std::setprecision( 3 ) << nBytes / 1024. / 1000.;
00419 std::cout << std::setw( 14 ) << std::right << std::setprecision( 3 ) << nBytes / 1024. / nHistograms;
00420 std::cout << std::endl;
00421
00422 std::cout << ".........................................................................................." << std::endl;
00423
00424 }
00425
00426
00427
00428 std::cout << std::endl;
00429 std::cout << "------------------------------------------------------------------------------------------" << std::endl;
00430 std::cout << "Grand total ";
00431 if( mode == DQMStoreStats::considerAllME ) std::cout << "FOR ALL ME:" << std::endl;
00432 else if( mode == DQMStoreStats::considerOnlyLumiProductME ) std::cout << "FOR LUMI PRODUCTS ONLY:" << std::endl;
00433 std::cout << "------------------------------------------------------------------------------------------" << std::endl;
00434 std::cout << "Number of subsystems: " << dqmStoreStatsTopLevel.size() << std::endl;
00435 std::cout << "Total number of histograms: " << overallNHistograms << " with: " << overallNBins << " bins alltogether" << std::endl;
00436 std::cout << "Total memory occupied by histograms (excl. overhead): " << overallNBytes / 1024. / 1000. << " MB" << std::endl;
00437
00438
00439
00440 std::cout << endl;
00441 std::cout << "===========================================================================================" << std::endl;
00442 std::cout << "[DQMStoreStats::calcstats] -- End of output ";
00443 if( mode == DQMStoreStats::considerAllME ) std::cout << "FOR ALL ME." << std::endl;
00444 else if( mode == DQMStoreStats::considerOnlyLumiProductME ) std::cout << "FOR LUMI PRODUCTS ONLY." << std::endl;
00445 std::cout << "===========================================================================================" << std::endl;
00446 std::cout << endl;
00447
00448
00449
00450
00451 if (dumpToFWJR_)
00452 {
00453 edm::Service<edm::JobReport> jr;
00454
00455 if (!jr.isAvailable())
00456 return 0;
00457
00458 std::map<std::string, std::string> jrInfo;
00459 unsigned int overallNHistograms = 0, overallNBins = 0, overallNBytes = 0;
00460
00461 jrInfo["Source"] = "DQMServices/Components";
00462 jrInfo["FileClass"] = "DQMStoreStats";
00463 if (runonendrun_)
00464 jrInfo["DumpType"] = "EndRun";
00465 if (runonendlumi_)
00466 jrInfo["DumpType"] = "EndLumi";
00467 if (runonendjob_)
00468 jrInfo["DumpType"] = "EndJob";
00469 if (runineventloop_)
00470 jrInfo["DumpType"] = "EventLoop";
00471 if( mode == DQMStoreStats::considerAllME )
00472 jrInfo["Type"] = "RunProduct";
00473 else if( mode == DQMStoreStats::considerOnlyLumiProductME )
00474 jrInfo["Type"] = "LumiProduct";
00475
00476
00477 jrInfo["pathNameMatch"] = pathnamematch_;
00478
00479 for (DQMStoreStatsTopLevel::const_iterator it0 = dqmStoreStatsTopLevel.begin(); it0 < dqmStoreStatsTopLevel.end(); ++it0 )
00480 {
00481 unsigned int nHistograms = 0, nBins = 0, nEmptyBins = 0, nBytes = 0;
00482 for( DQMStoreStatsSubsystem::const_iterator it1 = it0->begin(); it1 < it0->end(); ++it1 ) {
00483
00484 nHistograms += it1->totalHistos_;
00485 nBins += it1->totalBins_;
00486 nEmptyBins += it1->totalEmptyBins_;
00487 nBytes += it1->totalMemory_;
00488 }
00489 overallNHistograms += nHistograms;
00490 overallNBins += nBins;
00491 overallNBytes += nBytes;
00492 std::stringstream iss("");
00493 iss << nHistograms;
00494 jrInfo[it0->subsystemName_ + std::string("_h")] = iss.str();
00495 iss.str("");iss<<nBins;
00496 jrInfo[it0->subsystemName_ + std::string("_b")] = iss.str();
00497 iss.str("");iss<<nEmptyBins;
00498 jrInfo[it0->subsystemName_ + std::string("_be")] = iss.str();
00499 iss.str("");iss<< ((float)nEmptyBins/(float)nBins);
00500 jrInfo[it0->subsystemName_ + std::string("_fbe")] = iss.str();
00501 iss.str("");iss<< ((float)nBins/(float)nHistograms);
00502 jrInfo[it0->subsystemName_ + std::string("_b_h")] = iss.str();
00503 iss.str("");iss<<nBytes / 1024. / 1024.;
00504 jrInfo[it0->subsystemName_ + std::string("_MB")] = iss.str();
00505 iss.str("");iss<<nBytes / 1024. / nHistograms;
00506 jrInfo[it0->subsystemName_ + std::string("_Kb_h")] = iss.str();
00507 }
00508 jr->reportAnalysisFile("DQMStatsReport", jrInfo);
00509 }
00510
00511 return 0;
00512
00513 }
00514
00515
00516
00520 void DQMStoreStats::dumpMemoryProfile( void ) {
00521
00522 std::cout << std::endl;
00523 std::cout << "------------------------------------------------------------------------------------------" << std::endl;
00524 std::cout << "Memory profile:" << std::endl;
00525 std::cout << "------------------------------------------------------------------------------------------" << std::endl;
00526
00527
00528 std::pair<time_t, unsigned int> maxItem( 0, 0 );
00529 for( std::vector<std::pair<time_t, unsigned int> >::const_iterator it = memoryHistoryVector_.begin();
00530 it < memoryHistoryVector_.end(); ++it ) {
00531 if( it->second > maxItem.second ) {
00532 maxItem = *it;
00533 }
00534 }
00535
00536 std::stringstream rootOutputFileName;
00537 rootOutputFileName << "dqmStoreStats_memProfile_" << getpid() << ".root";
00538
00539
00540 if( dumpMemHistory_ && isOpenProcFileSuccessful_ ) {
00541
00542 TFile outputFile( rootOutputFileName.str().c_str(), "RECREATE" );
00543
00544 int aTime;
00545 float aMb;
00546
00547 TTree memHistoryTree( "dqmstorestats_memhistory", "memory history" );
00548 memHistoryTree.Branch( "seconds", &aTime, "seconds/I" );
00549 memHistoryTree.Branch( "megabytes", &aMb, "megabytes/F" );
00550 for( std::vector<std::pair<time_t, unsigned int> >::const_iterator it = memoryHistoryVector_.begin();
00551 it < memoryHistoryVector_.end(); ++it ) {
00552 aTime = it->first - startingTime_;
00553 aMb = it->second / 1000.;
00554 memHistoryTree.Fill();
00555 }
00556
00557 outputFile.Write();
00558 outputFile.Close();
00559
00560 }
00561
00562 std::cout << "Approx. maximum total virtual memory size of job: ";
00563 if( isOpenProcFileSuccessful_ && memoryHistoryVector_.size() ) {
00564 std::cout << maxItem.second / 1000.
00565 << " MB (reached " << maxItem.first - startingTime_ << " sec. after constructor called)," << std::endl;
00566 std::cout << " memory history written to: " << rootOutputFileName.str() << " (" << memoryHistoryVector_.size() << " samples)" << std::endl;
00567 } else {
00568 std::cout << "(could not be determined)" << std::endl;
00569 }
00570
00571 std::cout << std::endl << std::endl;
00572
00573 }
00574
00575
00576
00580 void DQMStoreStats::print(){
00581
00582 std::cout << " ---------- " << subsystem_ << " ---------- " << std::endl;
00583 std::cout << " " << subfolder_ << ": " ;
00584 std::cout << nmesubsys_ << " histograms with "
00585 << nbinssubsys_ << " bins. " ;
00586 if (nmesubsys_ > 0) std::cout << nbinssubsys_/nmesubsys_ << " bins/histogram " ;
00587 std::cout << std::endl;
00588 std::cout << " Largest histogram: " << maxbinsmesubsys_ << " with " <<
00589 maxbinssubsys_ << " bins." << std::endl;
00590 }
00591
00592
00593
00594
00598 std::pair<unsigned int, unsigned int> DQMStoreStats::readMemoryEntry( void ) const {
00599
00600
00601 if( isOpenProcFileSuccessful_ ) {
00602
00603 std::ifstream procFile( procFileName_.str().c_str(), ios::in );
00604
00605 std::string readBuffer( "" );
00606 unsigned int memSize = 0;
00607
00608
00609 while( !procFile.eof() ) {
00610 procFile >> readBuffer;
00611 if( std::string( "VmSize:" ) == readBuffer ) {
00612 procFile >> memSize;
00613 break;
00614 }
00615 }
00616
00617 procFile.close();
00618 return std::pair<time_t, unsigned int>( time( 0 ), memSize );
00619 }
00620
00621 return std::pair<time_t, unsigned int>( 0, 0 );
00622
00623 }
00624
00625
00626
00627
00628
00629
00630 void DQMStoreStats::beginJob() {
00631
00633 dbe_ = Service<DQMStore>().operator->();
00634
00635
00636 procFileName_ << "/proc/" << getpid() << "/status";
00637
00638
00639 std::ifstream procFile( procFileName_.str().c_str(), ios::in );
00640
00641 if( procFile.good() ) {
00642 isOpenProcFileSuccessful_ = true;
00643 }
00644 else {
00645 std::cerr << " [DQMStoreStats::beginJob] ** WARNING: could not open file: " << procFileName_.str() << std::endl;
00646 std::cerr << " Total memory profile will not be available." << std::endl;
00647 isOpenProcFileSuccessful_ = false;
00648 }
00649
00650 procFile.close();
00651
00652 }
00653
00654
00655
00656
00657 void DQMStoreStats::beginRun(const edm::Run& r, const EventSetup& context) {
00658 }
00659
00660
00661
00662
00663
00664 void DQMStoreStats::beginLuminosityBlock(const LuminosityBlock& lumiSeg,
00665 const EventSetup& context) {
00666 }
00667
00668
00669
00670
00671
00672 void DQMStoreStats::analyze(const Event& iEvent, const EventSetup& iSetup) {
00673
00674
00675 memoryHistoryVector_.push_back( readMemoryEntry() );
00676
00677 if (runineventloop_) {
00678 calcstats( DQMStoreStats::considerAllME );
00679 calcstats( DQMStoreStats::considerOnlyLumiProductME );
00680 dumpMemoryProfile();
00681 }
00682
00683 }
00684
00685
00686
00687
00688
00689 void DQMStoreStats::endLuminosityBlock(const LuminosityBlock& lumiSeg,
00690 const EventSetup& context) {
00691 if (runonendlumi_) {
00692 calcstats( DQMStoreStats::considerAllME );
00693 calcstats( DQMStoreStats::considerOnlyLumiProductME );
00694 dumpMemoryProfile();
00695 }
00696
00697 }
00698
00699
00700
00701
00702 void DQMStoreStats::endRun(const Run& r, const EventSetup& context) {
00703
00704 if (runonendrun_) {
00705 calcstats( DQMStoreStats::considerAllME );
00706 calcstats( DQMStoreStats::considerOnlyLumiProductME );
00707 dumpMemoryProfile();
00708 }
00709
00710 }
00711
00712
00713
00714
00715 void DQMStoreStats::endJob() {
00716
00717 if (runonendjob_) {
00718 calcstats( DQMStoreStats::considerAllME );
00719 calcstats( DQMStoreStats::considerOnlyLumiProductME );
00720 dumpMemoryProfile();
00721 }
00722
00723 }