dune-common 2.1.1
|
00001 // -*- tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- 00002 // vi: set ts=8 sw=2 et sts=2: 00003 #ifndef DUNE_TIMER_HH 00004 #define DUNE_TIMER_HH 00005 00006 #ifndef TIMER_USE_STD_CLOCK 00007 // headers for getrusage(2) 00008 #include <sys/resource.h> 00009 #endif 00010 00011 #include <ctime> 00012 00013 // headers for stderror(3) 00014 #include <cstring> 00015 00016 // access to errno in C++ 00017 #include <cerrno> 00018 00019 #include "exceptions.hh" 00020 00021 namespace Dune { 00022 00032 class TimerError : public SystemError {} ; 00033 00034 00045 class Timer 00046 { 00047 public: 00048 00053 Timer (bool startImmediately=true) throw(TimerError) 00054 { 00055 isRunning_ = startImmediately; 00056 reset(); 00057 } 00058 00060 void reset() throw (TimerError) 00061 { 00062 sumElapsed_ = 0.0; 00063 storedLastElapsed_ = 0.0; 00064 rawReset(); 00065 } 00066 00067 00069 void start() throw (TimerError) 00070 { 00071 if (not(isRunning_)) 00072 { 00073 rawReset(); 00074 isRunning_ = true; 00075 } 00076 } 00077 00078 00080 double elapsed () const throw (TimerError) 00081 { 00082 // if timer is running add the time elapsed since last start to sum 00083 if (isRunning_) 00084 return sumElapsed_ + lastElapsed(); 00085 00086 return sumElapsed_; 00087 } 00088 00089 00091 double lastElapsed () const throw (TimerError) 00092 { 00093 // if timer is running return the current value 00094 if (isRunning_) 00095 return rawElapsed(); 00096 00097 // if timer is not running return stored value from last run 00098 return storedLastElapsed_; 00099 } 00100 00101 00103 double stop() throw (TimerError) 00104 { 00105 if (isRunning_) 00106 { 00107 // update storedLastElapsed_ and sumElapsed_ and stop timer 00108 storedLastElapsed_ = lastElapsed(); 00109 sumElapsed_ += storedLastElapsed_; 00110 isRunning_ = false; 00111 } 00112 return elapsed(); 00113 } 00114 00115 00116 private: 00117 00118 bool isRunning_; 00119 double sumElapsed_; 00120 double storedLastElapsed_; 00121 00122 00123 #ifdef TIMER_USE_STD_CLOCK 00124 void rawReset() throw (TimerError) 00125 { 00126 cstart = std::clock(); 00127 } 00128 00129 double rawElapsed () const throw (TimerError) 00130 { 00131 return (std::clock()-cstart) / static_cast<double>(CLOCKS_PER_SEC); 00132 } 00133 00134 std::clock_t cstart; 00135 #else 00136 void rawReset() throw (TimerError) 00137 { 00138 rusage ru; 00139 if (getrusage(RUSAGE_SELF, &ru)) 00140 DUNE_THROW(TimerError, strerror(errno)); 00141 cstart = ru.ru_utime; 00142 } 00143 00144 double rawElapsed () const throw (TimerError) 00145 { 00146 rusage ru; 00147 if (getrusage(RUSAGE_SELF, &ru)) 00148 DUNE_THROW(TimerError, strerror(errno)); 00149 return 1.0 * (ru.ru_utime.tv_sec - cstart.tv_sec) + (ru.ru_utime.tv_usec - cstart.tv_usec) / (1000.0 * 1000.0); 00150 } 00151 00152 struct timeval cstart; 00153 #endif 00154 }; // end class Timer 00155 00158 } // end namespace 00159 00160 #endif