CMS 3D CMS Logo

SystemTimeKeeper.cc
Go to the documentation of this file.
1 // -*- C++ -*-
2 //
3 // Package: FWCore/Framework
4 // Class : SystemTimeKeeper
5 //
6 // Implementation:
7 // [Notes on implementation]
8 //
9 // Original Author: Chris Jones
10 // Created: Mon, 07 Jul 2014 14:37:32 GMT
11 //
12 
13 // system include files
14 #include <algorithm>
15 
16 // user include files
27 #include "SystemTimeKeeper.h"
28 
29 using namespace edm;
30 //
31 // constants, enums and typedefs
32 //
33 
34 //
35 // static data member definitions
36 //
37 
38 //
39 // constructors and destructor
40 //
41 SystemTimeKeeper::SystemTimeKeeper(unsigned int iNumStreams,
42  std::vector<const ModuleDescription*> const& iModules,
43  service::TriggerNamesService const& iNamesService,
44  ProcessContext const* iProcessContext):
45 m_streamEventTimer(iNumStreams),
46 m_streamPathTiming(iNumStreams),
47 m_modules(iModules),
48 m_processContext(iProcessContext),
49 m_minModuleID(0),
50 m_numberOfEvents(0)
51 {
52  std::sort(m_modules.begin(),m_modules.end(),
53  [] (const ModuleDescription* iLHS,
54  const ModuleDescription* iRHS) -> bool {
55  return iLHS->id() < iRHS->id();
56  });
57  if(not m_modules.empty()) {
58  m_minModuleID = m_modules.front()->id();
59  unsigned int numModuleSlots = m_modules.back()->id() - m_minModuleID + 1;
60  m_streamModuleTiming.resize(iNumStreams);
61  for(auto& stream: m_streamModuleTiming) {
62  stream.resize(numModuleSlots);
63  }
64  }
65 
66 
67  std::vector<unsigned int> numModulesInPath;
68  std::vector<unsigned int> numModulesInEndPath;
69 
70  const unsigned int numPaths = iNamesService.getTrigPaths().size();
71  const unsigned int numEndPaths = iNamesService.getEndPaths().size();
72  m_pathNames.reserve(numPaths+numEndPaths);
73  std::copy(iNamesService.getTrigPaths().begin(),
74  iNamesService.getTrigPaths().end(),
75  std::back_inserter(m_pathNames));
76  std::copy(iNamesService.getEndPaths().begin(),
77  iNamesService.getEndPaths().end(),
78  std::back_inserter(m_pathNames));
79 
80  numModulesInPath.reserve(numPaths);
81  numModulesInEndPath.reserve(numEndPaths);
82 
83  m_modulesOnPaths.reserve(numPaths+numEndPaths);
84 
85  for(unsigned int i =0; i<numPaths;++i) {
86  numModulesInPath.push_back(iNamesService.getTrigPathModules(i).size());
87  m_modulesOnPaths.push_back(iNamesService.getTrigPathModules(i));
88  }
89  for(unsigned int i =0; i<numEndPaths;++i) {
90  numModulesInEndPath.push_back(iNamesService.getEndPathModules(i).size());
91  m_modulesOnPaths.push_back(iNamesService.getEndPathModules(i));
92  }
93 
94  m_endPathOffset =numModulesInPath.size();
95 
96  for( auto& stream: m_streamPathTiming) {
97  unsigned int index = 0;
98  stream.resize(numModulesInPath.size()+numModulesInEndPath.size());
99  for(unsigned int numMods : numModulesInPath) {
100  stream[index].m_moduleTiming.resize(numMods);
101  ++index;
102  }
103  for(unsigned int numMods : numModulesInEndPath) {
104  stream[index].m_moduleTiming.resize(numMods);
105  ++index;
106  }
107 
108  }
109 }
110 
111 //
112 // member functions
113 //
116  PathContext const& iPath) {
117  unsigned int offset = 0;
118  if(iPath.isEndPath()) {
119  offset = m_endPathOffset;
120  }
121  assert(iPath.pathID()+offset < m_streamPathTiming[iStream.streamID().value()].size());
122  return m_streamPathTiming[iStream.streamID().value()][iPath.pathID()+offset];
123 }
124 
125 //NOTE: Have to check bounds rather than ProcessContext on the
126 // module callbacks because the ProcessContext could be for a
127 // SubProcess which requested an usncheduled execution of a
128 // module in a parent process. In that case the ProcessContext
129 // is for the SubProcess but the module is is for the parent process.
130 inline bool
131 SystemTimeKeeper::checkBounds(unsigned int id) const {
132  return id >= m_minModuleID and id <m_modules.size()+ m_minModuleID;
133 }
134 
135 
136 
137 void
140  m_streamEventTimer[iID.value()].start();
141 }
142 
143 void
145  m_streamEventTimer[iContext.streamID().value()].stop();
146 }
147 
148 void
150  PathContext const& iPath) {
151  if(m_processContext == iStream.processContext()) {
152  auto& timing = pathTiming(iStream,iPath);
153  timing.m_timer.start();
154  }
155 }
156 
157 void
159  PathContext const& iPath,
160  HLTPathStatus const& iStatus) {
161  if(m_processContext == iStream.processContext()) {
162 
163  auto& timing = pathTiming(iStream,iPath);
164  timing.m_timer.stop();
165 
166  //mark all modules up to and including the decision module as being visited
167  auto& modsOnPath = timing.m_moduleTiming;
168  for(unsigned int i = 0; i< iStatus.index()+1;++i) {
169  ++modsOnPath[i].m_timesVisited;
170  }
171  }
172 }
173 
174 
175 void
177  if(checkBounds(iModule.moduleDescription()->id())) {
178  auto& mod =
180  mod.m_timer.start();
181  ++(mod.m_timesRun);
182  }
183 }
185  ModuleCallingContext const& iModule) {
186  if(checkBounds(iModule.moduleDescription()->id())) {
187  auto& mod =
189  auto times = mod.m_timer.stop();
190 
191  if(iModule.type() == ParentContext::Type::kPlaceInPath ) {
192  auto place = iModule.placeInPathContext();
193 
194  auto& modTiming = pathTiming(iStream,*(place->pathContext())).m_moduleTiming[place->placeInPath()];
195  modTiming.m_realTime += times;
196  }
197  }
198 }
200  ModuleCallingContext const& iModule) {
201  if(checkBounds(iModule.moduleDescription()->id())) {
202  auto& mod =
204  auto times = mod.m_timer.stop();
205 
206  if(iModule.type() == ParentContext::Type::kPlaceInPath ) {
207  auto place = iModule.placeInPathContext();
208 
209  auto& modTiming = pathTiming(iStream,*(place->pathContext())).m_moduleTiming[place->placeInPath()];
210  modTiming.m_realTime += times;
211  }
212  }
213 }
214 void
216  ModuleCallingContext const& iModule) {
217  if(checkBounds(iModule.moduleDescription()->id())) {
218  auto& mod =
220  mod.m_timer.start();
221  }
222 }
223 
224 void
227 }
228 
229 void
232 }
233 
234 
235 static void
236 fillPathSummary(unsigned int iStartIndex,
237  unsigned int iEndIndex,
238  std::vector<std::string> const& iPathNames,
239  std::vector<std::vector<std::string>> const& iModulesOnPaths,
240  std::vector<std::vector<SystemTimeKeeper::PathTiming>> const& iPathTimings,
241  std::vector<PathTimingSummary>& iSummary) {
242  iSummary.resize(iEndIndex-iStartIndex);
243 
244  for(auto const& stream: iPathTimings) {
245  auto it = iSummary.begin();
246  for(unsigned int index = iStartIndex; index < iEndIndex; ++index, ++it) {
247  auto const& pathTiming = stream[index];
248  it->name = iPathNames[index];
249  it->bitPosition = index-iStartIndex;
250  if(not pathTiming.m_moduleTiming.empty()) {
251  it->timesRun += pathTiming.m_moduleTiming[0].m_timesVisited;
252  }
253  it->realTime += pathTiming.m_timer.realTime();
254  if(it->moduleInPathSummaries.empty()) {
255  it->moduleInPathSummaries.resize(pathTiming.m_moduleTiming.size());
256  }
257  for(unsigned int modIndex=0; modIndex < pathTiming.m_moduleTiming.size(); ++modIndex) {
258  auto const& modTiming =pathTiming.m_moduleTiming[modIndex];
259  auto& modSummary =it->moduleInPathSummaries[modIndex];
260  if(modSummary.moduleLabel.empty()) {
261  modSummary.moduleLabel = iModulesOnPaths[index][modIndex];
262  }
263  modSummary.timesVisited += modTiming.m_timesVisited;
264  modSummary.realTime += modTiming.m_realTime;
265  }
266  }
267  }
268 }
269 
270 void
272  {
274  double sumEventTime = 0.;
275  for(auto const& stream: m_streamEventTimer) {
276  sumEventTime += stream.realTime();
277  }
280  rep.eventSummary.sumStreamRealTime = sumEventTime;
281  }
282 
283  //Per module summary
284  {
285  auto& summary = rep.workerSummaries;
286  summary.resize(m_modules.size());
287  //Figure out how often a module was visited
288  std::map<std::string,unsigned int> visited;
289  for(auto const& stream: m_streamPathTiming) {
290  unsigned int pathIndex = 0;
291  for(auto const& path: stream) {
292  unsigned int modIndex = 0;
293  for(auto const& mod: path.m_moduleTiming) {
294  visited[m_modulesOnPaths[pathIndex][modIndex]] += mod.m_timesVisited;
295  ++modIndex;
296  }
297  ++pathIndex;
298  }
299  }
300 
301  unsigned int modIndex=0;
302  for(auto const& mod: m_modules) {
303  auto& outMod = summary[modIndex];
304  outMod.moduleLabel = mod->moduleLabel();
305  outMod.realTime = 0.;
306 
307  auto moduleId =mod->id()-m_minModuleID;
308  for(auto const& stream: m_streamModuleTiming) {
309  auto const& timing = stream[moduleId];
310  outMod.realTime += timing.m_timer.realTime();
311  outMod.timesRun += timing.m_timesRun;
312  }
313  outMod.timesVisited = visited[mod->moduleLabel()];
314  if(0 == outMod.timesVisited) {
315  outMod.timesVisited = outMod.timesRun;
316  }
317  ++modIndex;
318  }
319  }
321 
322  //Per path summary
323  {
326  }
327 }
328 
329 
330 //
331 // const member functions
332 //
333 
334 //
335 // static member functions
336 //
size
Write out results.
std::vector< std::vector< std::string > > m_modulesOnPaths
void fillTriggerTimingReport(TriggerTimingReport &rep) const
std::vector< PathTimingSummary > endPathSummaries
Strings const & getTrigPathModules(std::string const &name) const
void stopEvent(StreamContext const &)
std::atomic< unsigned int > m_numberOfEvents
void start()
Definition: CPUTimer.cc:74
void restartModuleEvent(StreamContext const &, ModuleCallingContext const &)
Strings const & getEndPaths() const
def copy(args, dbName)
double realTime() const
void startModuleEvent(StreamContext const &, ModuleCallingContext const &)
std::vector< ModuleInPathTiming > m_moduleTiming
std::vector< std::vector< ModuleTiming > > m_streamModuleTiming
std::vector< std::string > m_pathNames
bool isEndPath() const
Definition: PathContext.h:42
Strings const & getEndPathModules(std::string const &name) const
std::vector< const ModuleDescription * > m_modules
EventTimingSummary eventSummary
ProcessContext const * m_processContext
ModuleDescription const * moduleDescription() const
static void fillPathSummary(Path const &path, PathSummary &sum)
std::vector< PathTimingSummary > trigPathSummaries
unsigned int pathID() const
Definition: PathContext.h:39
ProcessContext const * processContext() const
Definition: StreamContext.h:63
Times stop()
Definition: CPUTimer.cc:94
rep
Definition: cuy.py:1188
void stopPath(StreamContext const &, PathContext const &, HLTPathStatus const &)
void stopModuleEvent(StreamContext const &, ModuleCallingContext const &)
StreamID const & streamID() const
Definition: StreamContext.h:57
double cpuTime() const
Definition: CPUTimer.cc:158
SystemTimeKeeper(unsigned int iNumStreams, std::vector< const ModuleDescription * > const &iModules, service::TriggerNamesService const &iNameService, ProcessContext const *iProcessContext)
unsigned int value() const
Definition: StreamID.h:46
void sort_all(RandomAccessSequence &s)
wrappers for std::sort
Definition: Algorithms.h:120
void startPath(StreamContext const &, PathContext const &)
void pauseModuleEvent(StreamContext const &, ModuleCallingContext const &)
HLT enums.
Strings const & getTrigPaths() const
std::vector< WallclockTimer > m_streamEventTimer
PathTiming & pathTiming(StreamContext const &, PathContext const &)
unsigned int m_endPathOffset
std::vector< WorkerTimingSummary > workerSummaries
T mod(const T &a, const T &b)
Definition: ecalDccMap.h:4
PlaceInPathContext const * placeInPathContext() const
std::vector< std::vector< PathTiming > > m_streamPathTiming
double realTime() const
Definition: CPUTimer.cc:150
bool checkBounds(unsigned int id) const
unsigned int id() const
unsigned int index() const
Definition: HLTPathStatus.h:55