29 #include <sys/resource.h> 120 if(gettimeofday(&t,
nullptr) < 0)
121 throw cms::Exception(
"SysCallFailed",
"Failed call to gettimeofday");
122 return static_cast<double>(t.tv_sec) + (static_cast<double>(t.tv_usec) * 1E-6);
127 getrusage(RUSAGE_SELF, &usage);
129 double totalCPUTime = 0.0;
131 totalCPUTime = (double)usage.ru_utime.tv_sec + (
double(usage.ru_utime.tv_usec) * 1E-6);
133 totalCPUTime += (double)usage.ru_stime.tv_sec + (
double(usage.ru_stime.tv_usec) * 1E-6);
136 getrusage(RUSAGE_CHILDREN, &usage);
137 totalCPUTime += (double)usage.ru_utime.tv_sec + (
double(usage.ru_utime.tv_usec) * 1E-6);
138 totalCPUTime += (double)usage.ru_stime.tv_sec + (
double(usage.ru_stime.tv_usec) * 1E-6);
148 static thread_local std::vector<double> s_stack;
155 assert(!modStack.empty());
156 double curr_module_time = modStack.back();
158 double t =
getTime() - curr_module_time;
177 threshold_(iPS.getUntrackedParameter<double>(
"excessiveTimeThreshold")),
187 bool checkThreshold =
true;
191 checkThreshold =
false;
269 while( not
extra_job_cpu_.compare_exchange_strong(expected,expected+iTime) ) {}
278 desc.
addUntracked<
bool>(
"summaryOnly",
false)->setComment(
279 "If 'true' do not report timing for each event");
280 desc.
addUntracked<
bool>(
"useJobReport",
true)->setComment(
281 "If 'true' write summary information to JobReport");
283 "Amount of time in seconds before reporting a module or source has taken excessive time. A value of 0.0 turns off this reporting.");
284 descriptions.
add(
"Timing", desc);
286 "This service reports the time it takes to run each module in a job.");
295 <<
"TimeReport> Report activated" <<
"\n" 296 <<
"TimeReport> Report columns headings for events: " 297 <<
"eventnum runnum timetaken\n" 298 <<
"TimeReport> Report columns headings for modules: " 299 <<
"eventnum runnum modulelabel modulename timetakeni\n" 305 const double job_end_time =
getTime();
306 const double job_end_cpu =
getCPU();
317 total_job_cpu =job_end_cpu + extra_job_cpu_ -
curr_job_cpu_ ;
329 total_loop_time = 0.0;
330 total_loop_cpu = 0.0;
333 double sum_all_events_time = 0;
336 double average_event_time = 0.0;
341 double event_throughput = 0.0;
342 if(total_loop_time != 0.0) {
347 <<
"TimeReport> Time report complete in " 348 << total_job_time <<
" seconds" 350 <<
" Time Summary: \n" 351 <<
" - Min event: " << min_event_time <<
"\n" 352 <<
" - Max event: " << max_event_time <<
"\n" 353 <<
" - Avg event: " << average_event_time <<
"\n" 354 <<
" - Total loop: " << total_loop_time <<
"\n" 355 <<
" - Total init: " << total_initialization_time <<
"\n" 356 <<
" - Total job: " << total_job_time <<
"\n" 357 <<
" Event Throughput: "<< event_throughput <<
" ev/s\n" 358 <<
" CPU Summary: \n" 359 <<
" - Total loop: " << total_loop_cpu <<
"\n" 360 <<
" - Total init: " << total_initialization_cpu <<
"\n" 361 <<
" - Total extra: " << extra_job_cpu_ <<
"\n" 362 <<
" - Total job: " << total_job_cpu <<
"\n";
367 std::map<std::string, std::string> reportData;
369 reportData.insert(std::make_pair(
"MinEventTime",
d2str(min_event_time)));
370 reportData.insert(std::make_pair(
"MaxEventTime",
d2str(max_event_time)));
371 reportData.insert(std::make_pair(
"AvgEventTime",
d2str(average_event_time)));
372 reportData.insert(std::make_pair(
"EventThroughput",
d2str(event_throughput)));
373 reportData.insert(std::make_pair(
"TotalJobTime",
d2str(total_job_time)));
374 reportData.insert(std::make_pair(
"TotalJobCPU",
d2str(total_job_cpu)));
375 reportData.insert(std::make_pair(
"TotalLoopTime",
d2str(total_loop_time)));
376 reportData.insert(std::make_pair(
"TotalLoopCPU",
d2str(total_loop_cpu)));
377 reportData.insert(std::make_pair(
"TotalInitTime",
d2str(total_initialization_time)));
378 reportData.insert(std::make_pair(
"TotalInitCPU",
d2str(total_initialization_cpu)));
379 reportData.insert(std::make_pair(
"NumberOfStreams",
ui2str(
nStreams_)));
380 reportData.insert(std::make_pair(
"NumberOfThreads",
ui2str(
nThreads_)));
381 reportSvc->reportPerformanceSummary(
"Timing", reportData);
397 auto const & eventID = iStream.
eventID();
400 << eventID.event() <<
" " 401 << eventID.run() <<
" " 410 auto const & eventID = iStream.
eventID();
414 LogPrint(
"TimeModule") <<
"TimeModule> " 415 << eventID.event() <<
" " 416 << eventID.run() <<
" " 417 << desc.moduleLabel() <<
" " 418 << desc.moduleName() <<
" " 490 <<
"ExcessiveTime: Module used " << t
491 <<
" seconds of time which exceeds the error threshold configured in the Timing Service of " void watchPostModuleGlobalEndLumi(PostModuleGlobalEndLumi::slot_type const &iSlot)
void watchPostModuleConstruction(PostModuleConstruction::slot_type const &iSlot)
std::vector< double > sum_events_time_
unsigned int maxNumberOfThreads() const
void watchPreModuleGlobalBeginRun(PreModuleGlobalBeginRun::slot_type const &iSlot)
void setComment(std::string const &value)
void watchPreEvent(PreEvent::slot_type const &iSlot)
std::atomic< double > last_run_cpu_
#define DEFINE_FWK_SERVICE_MAKER(concrete, maker)
std::vector< double > max_events_time_
ParameterDescriptionBase * addUntracked(U const &iLabel, T const &value)
void watchPostEndJob(PostEndJob::slot_type const &iSlot)
std::vector< double > curr_events_time_
void watchPreModuleEvent(PreModuleEvent::slot_type const &iSlot)
void watchPreModuleConstruction(PreModuleConstruction::slot_type const &iSlot)
void watchPostEvent(PostEvent::slot_type const &iSlot)
double getTotalCPU() const override
void preModule(ModuleDescription const &md)
void watchPreSourceConstruction(PreSourceConstruction::slot_type const &iSlot)
void watchPostSourceConstruction(PostSourceConstruction::slot_type const &iSlot)
void watchPreEventReadFromSource(PreEventReadFromSource::slot_type const &iSlot)
void watchPostModuleEvent(PostModuleEvent::slot_type const &iSlot)
void watchPostModuleGlobalBeginLumi(PostModuleGlobalBeginLumi::slot_type const &iSlot)
void watchPostModuleStreamEndLumi(PostModuleStreamEndLumi::slot_type const &iSlot)
void postEvent(StreamContext const &)
void preModuleStream(StreamContext const &, ModuleCallingContext const &)
void watchPostModuleStreamBeginRun(PostModuleStreamBeginRun::slot_type const &iSlot)
void watchPostSourceEvent(PostSourceEvent::slot_type const &iSlot)
edm::serviceregistry::AllArgsMaker< edm::TimingServiceBase, Timing > TimingMaker
void watchPreModuleGlobalEndRun(PreModuleGlobalEndRun::slot_type const &iSlot)
void preOpenFile(std::string const &, bool)
void preModuleGlobal(GlobalContext const &, ModuleCallingContext const &)
void postModule(ModuleDescription const &md)
Preallocate preallocateSignal_
signal is emitted before beginJob
unsigned int maxNumberOfStreams() const
void watchPreOpenFile(PreOpenFile::slot_type const &iSlot)
void postModuleStream(StreamContext const &, ModuleCallingContext const &)
void watchPostSourceRun(PostSourceRun::slot_type const &iSlot)
Timing(ParameterSet const &, ActivityRegistry &)
void watchPreSourceLumi(PreSourceLumi::slot_type const &iSlot)
ModuleDescription const * moduleDescription() const
void postModuleEvent(StreamContext const &, ModuleCallingContext const &)
std::atomic< double > last_run_time_
void watchPreModuleEndJob(PreModuleEndJob::slot_type const &iSlot)
static void fillDescriptions(edm::ConfigurationDescriptions &descriptions)
void watchPreSourceRun(PreSourceRun::slot_type const &iSlot)
void watchPreModuleBeginJob(PreModuleBeginJob::slot_type const &iSlot)
static double jobStartTime()
void watchPreModuleGlobalBeginLumi(PreModuleGlobalBeginLumi::slot_type const &iSlot)
void watchPostModuleStreamEndRun(PostModuleStreamEndRun::slot_type const &iSlot)
StreamID const & streamID() const
static std::string ui2str(unsigned int i)
void watchPreModuleStreamBeginLumi(PreModuleStreamBeginLumi::slot_type const &iSlot)
void setComment(std::string const &value)
unsigned int value() const
void watchPostSourceLumi(PostSourceLumi::slot_type const &iSlot)
void watchPostModuleGlobalEndRun(PostModuleGlobalEndRun::slot_type const &iSlot)
void watchPostModuleStreamBeginLumi(PostModuleStreamBeginLumi::slot_type const &iSlot)
std::atomic< unsigned long > total_event_count_
void watchPreModuleStreamEndLumi(PreModuleStreamEndLumi::slot_type const &iSlot)
void watchPreModuleStreamBeginRun(PreModuleStreamBeginRun::slot_type const &iSlot)
static std::vector< double > & moduleTimeStack()
void addToCPUTime(double iTime) override
static std::string d2str(double d)
void add(std::string const &label, ParameterSetDescription const &psetDescription)
void watchPostOpenFile(PostOpenFile::slot_type const &iSlot)
double postCommon() const
PostGlobalEndRun postGlobalEndRunSignal_
void postModuleGlobal(GlobalContext const &, ModuleCallingContext const &)
void watchPreModuleStreamEndRun(PreModuleStreamEndRun::slot_type const &iSlot)
void postOpenFile(std::string const &, bool)
void watchPostModuleBeginJob(PostModuleBeginJob::slot_type const &iSlot)
void postSourceEvent(StreamID)
void watchPostEventReadFromSource(PostEventReadFromSource::slot_type const &iSlot)
void watchPostModuleGlobalBeginRun(PostModuleGlobalBeginRun::slot_type const &iSlot)
EventID const & eventID() const
void watchPreSourceEvent(PreSourceEvent::slot_type const &iSlot)
std::atomic< double > extra_job_cpu_
void preSourceEvent(StreamID)
void watchPostModuleEndJob(PostModuleEndJob::slot_type const &iSlot)
void preEvent(StreamContext const &)
void watchPreModuleGlobalEndLumi(PreModuleGlobalEndLumi::slot_type const &iSlot)
std::vector< double > min_events_time_
void watchPostBeginJob(PostBeginJob::slot_type const &iSlot)
convenience function for attaching to signal