timer.hh
Go to the documentation of this file.
1 // -*- mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
2 // vi: set et ts=4 sw=4 sts=4:
3 /*
4  Copyright (C) 2014 by Andreas Lauser
5 
6  This file is part of the Open Porous Media project (OPM).
7 
8  OPM is free software: you can redistribute it and/or modify
9  it under the terms of the GNU General Public License as published by
10  the Free Software Foundation, either version 2 of the License, or
11  (at your option) any later version.
12 
13  OPM is distributed in the hope that it will be useful,
14  but WITHOUT ANY WARRANTY; without even the implied warranty of
15  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16  GNU General Public License for more details.
17 
18  You should have received a copy of the GNU General Public License
19  along with OPM. If not, see <http://www.gnu.org/licenses/>.
20 */
26 #ifndef EWOMS_TIMER_HH
27 #define EWOMS_TIMER_HH
28 
29 #include <chrono>
30 #include <time.h>
31 
32 #if HAVE_MPI
33 #include <mpi.h>
34 #endif
35 
36 namespace Ewoms {
47 class Timer
48 {
49  struct TimeData
50  {
51  // The timespec data structure is more accurate than Linux (or at least POSIX)
52  // specific. for other operating systems, we use Dune::Timer
53 #if defined(CLOCK_MONOTONIC) && defined(CLOCK_PROCESS_CPUTIME_ID)
54  struct timespec realtimeData;
55  struct timespec cputimeData;
56 #else
57  std::chrono::high_resolution_clock::time_point realtimeData;
58  std::chrono::high_resolution_clock::time_point cputimeData;
59 #endif
60  };
61 public:
63  { halt(); }
64 
68  void start()
69  {
70  isStopped_ = false;
71  measure_(startTime_);
72  }
73 
77  void stop()
78  {
79  isStopped_ = true;
80  measure_(stopTime_);
81  }
82 
86  void halt()
87  {
88  isStopped_ = true;
89 
90  measure_(startTime_);
91  stopTime_ = startTime_;
92  }
93 
100  double realTimeElapsed() const
101  {
102  TimeData stopTime(stopTime_);
103 
104  if (!isStopped_)
105  measure_(stopTime);
106 
107  const auto &t1 = startTime_.realtimeData;
108  const auto &t2 = stopTime.realtimeData;
109 
110 #if defined(CLOCK_MONOTONIC) && defined(CLOCK_PROCESS_CPUTIME_ID)
111  return
112  static_cast<double>(t2.tv_sec - t1.tv_sec)
113  + static_cast<double>(t2.tv_nsec - t1.tv_nsec)/1e9;
114 #else
115  std::chrono::duration<double> dt =
116  std::chrono::duration_cast<std::chrono::duration<double> >(t2 - t1);
117  return dt.count();
118 #endif
119  }
120 
127  double cpuTimeElapsed() const
128  {
129  TimeData stopTime(stopTime_);
130 
131  if (!isStopped_)
132  measure_(stopTime);
133 
134  const auto &t1 = startTime_.cputimeData;
135  const auto &t2 = stopTime.cputimeData;
136 
137 #if defined(CLOCK_MONOTONIC) && defined(CLOCK_PROCESS_CPUTIME_ID)
138  return
139  static_cast<double>(t2.tv_sec - t1.tv_sec)
140  + static_cast<double>(t2.tv_nsec - t1.tv_nsec)/1e9;
141 #else
142  std::chrono::duration<double> dt =
143  std::chrono::duration_cast<std::chrono::duration<double> >(t2 - t1);
144  return dt.count();
145 #endif
146  }
147 
155  double globalCpuTimeElapsed() const
156  {
157  TimeData stopTime(stopTime_);
158 
159  if (!isStopped_)
160  measure_(stopTime);
161 
162  double val = cpuTimeElapsed();
163  double globalVal = val;
164 
165 #if HAVE_MPI
166  MPI_Reduce(&val,
167  &globalVal,
168  /*count=*/1,
169  MPI_DOUBLE,
170  MPI_SUM,
171  /*rootRank=*/0,
172  MPI_COMM_WORLD);
173 #endif
174  return globalVal;
175  }
176 
177 private:
178  // measure the current time and put it into the object passed via
179  // the argument.
180  static void measure_(TimeData& timeData)
181  {
182  // This method is more accurate than Linux (or at least POSIX) specific. for other operating
183  // systems, we use Dune::Timer
184 #if defined(CLOCK_MONOTONIC) && defined(CLOCK_PROCESS_CPUTIME_ID)
185  // measure the real time
186  clock_gettime(CLOCK_MONOTONIC, &timeData.realtimeData);
187 
188  // measure the CPU time
189  clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &timeData.cputimeData);
190 #else
191  timeData.realtimeData = std::chrono::high_resolution_clock::now();
192  timeData.cputimeData = std::chrono::high_resolution_clock::now();
193 #endif
194  }
195 
196  bool isStopped_;
197  TimeData startTime_;
198  TimeData stopTime_;
199 };
200 } // namespace Ewoms
201 
202 #endif
void halt()
Stop the measurement and always return 0 for all timing values.
Definition: timer.hh:86
Timer()
Definition: timer.hh:62
double cpuTimeElapsed() const
Return the CPU time [s] used by all threads of the local process.
Definition: timer.hh:127
double globalCpuTimeElapsed() const
Return the CPU time [s] used by all threads of the all processes of the simulation.
Definition: timer.hh:155
Definition: baseauxiliarymodule.hh:35
double realTimeElapsed() const
Return the real time [s] elapsed.
Definition: timer.hh:100
Provides an encapsulation to measure the system time.
Definition: timer.hh:47
void start()
Start counting the time resources used by the simulation.
Definition: timer.hh:68
void stop()
Stop counting the time resources used by the simulation.
Definition: timer.hh:77