OPAL (Object Oriented Parallel Accelerator Library)  2024.1
OPAL
IpplTimings.cpp
Go to the documentation of this file.
1 // -*- C++ -*-
2 /***************************************************************************
3  *
4  * The IPPL Framework
5  *
6  ***************************************************************************/
7 
8 #include "Utility/IpplTimings.h"
9 #include "Utility/Inform.h"
10 #include "Message/GlobalComm.h"
11 #include "PETE/IpplExpressions.h"
12 
13 #include <boost/algorithm/string/predicate.hpp>
14 
15 #include <fstream>
16 #include <iostream>
17 #include <algorithm>
18 
20 std::stack<Timing*> IpplTimings::stashedInstance;
21 
23 // default constructor
25  TimerList(),
26  TimerMap()
27 { }
28 
29 
31 // destructor
33  for (TimerMap_t::iterator it = TimerMap.begin(); it != TimerMap.end(); ++ it) {
34  it->second = 0;
35  }
36  TimerMap.clear();
37 
38  TimerList.clear();
39 }
40 
41 
43 // create a timer, or get one that already exists
45  std::string s(nm);
46  TimerInfo *tptr = 0;
47  TimerMap_t::iterator loc = TimerMap.find(s);
48  if (loc == TimerMap.end()) {
49  tptr = new TimerInfo;
50  tptr->indx = TimerList.size();
51  tptr->name = s;
52  TimerMap.insert(TimerMap_t::value_type(s,tptr));
53  TimerList.push_back(my_auto_ptr<TimerInfo>(tptr));
54  } else {
55  tptr = (*loc).second;
56  }
57  return tptr->indx;
58 }
59 
60 
62 // start a timer
64  if (t >= TimerList.size())
65  return;
66  TimerList[t]->start();
67 }
68 
69 
71 // stop a timer, and accumulate it's values
73  if (t >= TimerList.size())
74  return;
75  TimerList[t]->stop();
76 }
77 
78 
80 // clear a timer, by turning it off and throwing away its time
82  if (t >= TimerList.size())
83  return;
84  TimerList[t]->clear();
85 }
86 
87 
89 // print out the timing results
90 void Timing::print() {
91  if (TimerList.size() < 1)
92  return;
93 
94  // report the average time for each timer
95  Inform msg("Timings");
96  msg << level1
97  << "-----------------------------------------------------------------";
98  msg << "\n";
99  msg << " Timing results for " << Ippl::getNodes() << " nodes:" << "\n";
100  msg << "-----------------------------------------------------------------";
101  msg << "\n";
102 
103  {
104  TimerInfo *tptr = TimerList[0].get();
105  double walltotal = 0.0, cputotal = 0.0;
106  reduce(tptr->wallTime, walltotal, OpMaxAssign());
107  reduce(tptr->cpuTime, cputotal, OpMaxAssign());
108  size_t lengthName = std::min(tptr->name.length(), 19lu);
109  msg << tptr->name.substr(0,lengthName)
110  << std::string().assign(20 - lengthName,'.')
111  << " Wall tot = " << std::setw(10) << walltotal << ","
112  << " CPU tot = " << std::setw(10) << cputotal << "\n"
113  << "\n";
114  }
115 
116  auto begin = ++ TimerList.begin();
117  auto end = TimerList.end();
118  std::sort(begin, end, [](const my_auto_ptr<TimerInfo>& a, const my_auto_ptr<TimerInfo>& b)
119  {
120  return boost::ilexicographical_compare(a->name, b->name);
121  });
122 
123  for (unsigned int i=1; i < TimerList.size(); ++i) {
124  TimerInfo *tptr = TimerList[i].get();
125  double wallmax = 0.0, cpumax = 0.0, wallmin = 0.0, cpumin = 0.0;
126  double wallavg = 0.0, cpuavg = 0.0;
127  reduce(tptr->wallTime, wallmax, OpMaxAssign());
128  reduce(tptr->cpuTime, cpumax, OpMaxAssign());
129  reduce(tptr->wallTime, wallmin, OpMinAssign());
130  reduce(tptr->cpuTime, cpumin, OpMinAssign());
131  reduce(tptr->wallTime, wallavg, OpAddAssign());
132  reduce(tptr->cpuTime, cpuavg, OpAddAssign());
133  size_t lengthName = std::min(tptr->name.length(), 19lu);
134 
135  msg << tptr->name.substr(0,lengthName)
136  << std::string().assign(20 - lengthName, '.')
137  << " Wall max = " << std::setw(10) << wallmax << ","
138  << " CPU max = " << std::setw(10) << cpumax << "\n"
139  << std::string().assign(20,' ')
140  << " Wall avg = " << std::setw(10) << wallavg / Ippl::getNodes() << ","
141  << " CPU avg = " << std::setw(10) << cpuavg / Ippl::getNodes() << "\n"
142  << std::string().assign(20,' ')
143  << " Wall min = " << std::setw(10) << wallmin << ","
144  << " CPU min = " << std::setw(10) << cpumin << "\n"
145  << "\n";
146  }
147  msg << "-----------------------------------------------------------------";
148  msg << endl;
149 }
150 
152 // save the timing results into a file
153 void Timing::print(const std::string &fn, const std::map<std::string, unsigned int> &problemSize) {
154 
155  std::ofstream *timer_stream;
156  Inform *msg;
157 
158  if (TimerList.size() < 1)
159  return;
160 
161  timer_stream = new std::ofstream;
162  timer_stream->open( fn.c_str(), std::ios::out );
163  msg = new Inform( 0, *timer_stream, 0 );
164  // report the average time for each timer
165  // Inform msg("Timings");
166  /*
167  *msg << "---------------------------------------------------------------------------";
168  *msg << "\n";
169  *msg << " Timing results for " << Ippl::getNodes() << " nodes:" << "\n";
170  *msg << "---------------------------------------------------------------------------";
171  *msg << " name nodes (cputot cpumax) (walltot wallmax) cpumin wallmin cpuav wallav ";
172  *msg << "\n";
173  */
174 
175  if (!problemSize.empty()) {
176  *msg << "Problem size:\n";
177  for (auto it: problemSize) {
178  *msg << " " << std::setw(10) << it.first << ": " << it.second << "\n";
179  }
180  *msg << endl;
181  }
182 
183  *msg << std::setw(27) << "num Nodes"
184  << std::setw(10) << "CPU tot"
185  << std::setw(11) << "Wall tot\n"
186  << std::string().assign(47,'=')
187  << "\n";
188  {
189  TimerInfo *tptr = TimerList[0].get();
190  double walltotal = 0.0, cputotal = 0.0;
191  reduce(tptr->wallTime, walltotal, OpMaxAssign());
192  reduce(tptr->cpuTime, cputotal, OpMaxAssign());
193  size_t lengthName = std::min(tptr->name.length(), 19lu);
194  *msg << tptr->name.substr(0,lengthName);
195  for (int j=lengthName; j < 20; ++j) {
196  *msg << ".";
197  }
198  *msg << " " << std::setw(6) << Ippl::getNodes()
199  << " " << std::setw(9) << std::setprecision(4) << cputotal
200  << " " << std::setw(9) << std::setprecision(4) << walltotal
201  << "\n";
202  }
203 
204  auto begin = ++ TimerList.begin();
205  auto end = TimerList.end();
206  std::sort(begin, end, [](const my_auto_ptr<TimerInfo>& a, const my_auto_ptr<TimerInfo>& b)
207  {
208  return boost::ilexicographical_compare(a->name, b->name);
209  });
210 
211  *msg << "\n"
212  << std::setw(27) << "num Nodes"
213  << std::setw(10) << "CPU max"
214  << std::setw(10) << "Wall max"
215  << std::setw(10) << "CPU min"
216  << std::setw(10) << "Wall min"
217  << std::setw(10) << "CPU avg"
218  << std::setw(11) << "Wall avg\n"
219  << std::string().assign(87,'=')
220  << "\n";
221  for (unsigned int i=0; i < TimerList.size(); ++i) {
222  TimerInfo *tptr = TimerList[i].get();
223  double wallmax = 0.0, cpumax = 0.0, wallmin = 0.0, cpumin = 0.0;
224  double wallavg = 0.0, cpuavg = 0.0;
225  reduce(tptr->wallTime, wallmax, OpMaxAssign());
226  reduce(tptr->cpuTime, cpumax, OpMaxAssign());
227  reduce(tptr->wallTime, wallmin, OpMinAssign());
228  reduce(tptr->cpuTime, cpumin, OpMinAssign());
229  reduce(tptr->wallTime, wallavg, OpAddAssign());
230  reduce(tptr->cpuTime, cpuavg, OpAddAssign());
231  size_t lengthName = std::min(tptr->name.length(), 19lu);
232  *msg << tptr->name.substr(0,lengthName);
233  for (int j=lengthName; j < 20; ++j) {
234  *msg << ".";
235  }
236  *msg << " " << std::setw(6) << Ippl::getNodes()
237  << " " << std::setw(9) << std::setprecision(4) << cpumax
238  << " " << std::setw(9) << std::setprecision(4) << wallmax
239  << " " << std::setw(9) << std::setprecision(4) << cpumin
240  << " " << std::setw(9) << std::setprecision(4) << wallmin
241  << " " << std::setw(9) << std::setprecision(4) << cpuavg / Ippl::getNodes()
242  << " " << std::setw(9) << std::setprecision(4) << wallavg / Ippl::getNodes()
243  << endl;
244  }
245  timer_stream->close();
246  delete msg;
247  delete timer_stream;
248 }
249 
252 
254  PAssert_EQ(stashedInstance.size(), 0);
255 
257  instance = new Timing();
258 }
259 
261  PAssert_GT(stashedInstance.size(), 0);
262 
263  delete instance;
264  instance = stashedInstance.top();
265  stashedInstance.pop();
266 }
#define PAssert_EQ(a, b)
Definition: PAssert.h:104
static std::stack< Timing * > stashedInstance
Definition: IpplTimings.h:233
void print()
Definition: IpplTimings.cpp:90
static Timing * instance
Definition: IpplTimings.h:232
and that you know you can do these things To protect your we need to make restrictions that forbid anyone to deny you these rights or to ask you to surrender the rights These restrictions translate to certain responsibilities for you if you distribute copies of the or if you modify it For if you distribute copies of such a whether gratis or for a you must give the recipients all the rights that you have You must make sure that receive or can get the source code And you must show them these terms so they know their rights We protect your rights with two distribute and or modify the software for each author s protection and we want to make certain that everyone understands that there is no warranty for this free software If the software is modified by someone else and passed we want its recipients to know that what they have is not the so that any problems introduced by others will not reflect on the original authors reputations any free program is threatened constantly by software patents We wish to avoid the danger that redistributors of a free program will individually obtain patent in effect making the program proprietary To prevent we have made it clear that any patent must be licensed for everyone s free use or not licensed at all The precise terms and conditions for distribution and modification follow GNU GENERAL PUBLIC LICENSE TERMS AND CONDITIONS FOR DISTRIBUTION AND MODIFICATION This License applies to any program or other work which contains a notice placed by the copyright holder saying it may be distributed under the terms of this General Public License The refers to any such program or and a work based on the Program means either the Program or any derivative work under copyright a work containing the Program or a portion of it
Definition: LICENSE:43
void startTimer(TimerRef)
Definition: IpplTimings.cpp:63
double wallTime
Definition: IpplTimings.h:110
void stopTimer(TimerRef)
Definition: IpplTimings.cpp:72
void clearTimer(TimerRef)
Definition: IpplTimings.cpp:81
double cpuTime
Definition: IpplTimings.h:109
unsigned int TimerRef
Definition: IpplTimings.h:122
clearpage the user may choose between constant or variable radius This model includes fringe fields begin
Definition: multipole_t.tex:6
Inform & endl(Inform &inf)
Definition: Inform.cpp:42
T::PETE_Expr_t::PETE_Return_t min(const PETE_Expr< T > &expr, NDIndex< D > &loc)
Definition: ReductionLoc.h:76
std::string::iterator iterator
Definition: MSLang.h:15
static int getNodes()
Definition: IpplInfo.cpp:670
Definition: Inform.h:42
TimerMap_t TimerMap
Definition: IpplTimings.h:167
TimerRef indx
Definition: IpplTimings.h:116
T * value_type(const SliceIterator< T > &)
IpplTimerInfo TimerInfo
Definition: IpplTimings.h:125
static void pop()
TimerList_t TimerList
Definition: IpplTimings.h:164
TimerRef getTimer(const char *)
Definition: IpplTimings.cpp:44
Inform & level1(Inform &inf)
Definition: Inform.cpp:45
std::string name
Definition: IpplTimings.h:106
static void stash()
#define PAssert_GT(a, b)
Definition: PAssert.h:108
end
Definition: multipole_t.tex:9
bool reduce(Communicate &, InputIterator, InputIterator, OutputIterator, const ReduceOp &, bool *IncludeVal=0)
Definition: GlobalComm.hpp:55