LLVM API Documentation

Timer.h

Go to the documentation of this file.
00001 //===-- llvm/Support/Timer.h - Interval Timing Support ----------*- C++ -*-===//
00002 //
00003 //                     The LLVM Compiler Infrastructure
00004 //
00005 // This file was developed by the LLVM research group and is distributed under
00006 // the University of Illinois Open Source License. See LICENSE.TXT for details.
00007 //
00008 //===----------------------------------------------------------------------===//
00009 //
00010 // This file defines three classes: Timer, TimeRegion, and TimerGroup,
00011 // documented below.
00012 //
00013 //===----------------------------------------------------------------------===//
00014 
00015 #ifndef LLVM_SUPPORT_TIMER_H
00016 #define LLVM_SUPPORT_TIMER_H
00017 
00018 #include "llvm/Support/DataTypes.h"
00019 #include <string>
00020 #include <vector>
00021 #include <iosfwd>
00022 #include <cassert>
00023 
00024 namespace llvm {
00025 
00026 class TimerGroup;
00027 
00028 /// Timer - This class is used to track the amount of time spent between
00029 /// invocations of it's startTimer()/stopTimer() methods.  Given appropriate OS
00030 /// support it can also keep track of the RSS of the program at various points.
00031 /// By default, the Timer will print the amount of time it has captured to
00032 /// standard error when the laster timer is destroyed, otherwise it is printed
00033 /// when it's TimerGroup is destroyed.  Timer's do not print their information
00034 /// if they are never started.
00035 ///
00036 class Timer {
00037   double Elapsed;        // Wall clock time elapsed in seconds
00038   double UserTime;       // User time elapsed
00039   double SystemTime;     // System time elapsed
00040   ssize_t MemUsed;       // Memory allocated (in bytes)
00041   size_t PeakMem;        // Peak memory used
00042   size_t PeakMemBase;    // Temporary for peak calculation...
00043   std::string Name;      // The name of this time variable
00044   bool Started;          // Has this time variable ever been started?
00045   TimerGroup *TG;        // The TimerGroup this Timer is in.
00046 public:
00047   Timer(const std::string &N);
00048   Timer(const std::string &N, TimerGroup &tg);
00049   Timer(const Timer &T);
00050   ~Timer();
00051 
00052   double getProcessTime() const { return UserTime+SystemTime; }
00053   double getWallTime() const { return Elapsed; }
00054   ssize_t getMemUsed() const { return MemUsed; }
00055   size_t getPeakMem() const { return PeakMem; }
00056   std::string getName() const { return Name; }
00057 
00058   const Timer &operator=(const Timer &T) {
00059     Elapsed = T.Elapsed;
00060     UserTime = T.UserTime;
00061     SystemTime = T.SystemTime;
00062     MemUsed = T.MemUsed;
00063     PeakMem = T.PeakMem;
00064     PeakMemBase = T.PeakMemBase;
00065     Name = T.Name;
00066     Started = T.Started;
00067     assert(TG == T.TG && "Can only assign timers in the same TimerGroup!");
00068     return *this;
00069   }
00070 
00071   // operator< - Allow sorting...
00072   bool operator<(const Timer &T) const {
00073     // Sort by Wall Time elapsed, as it is the only thing really accurate
00074     return Elapsed < T.Elapsed;
00075   }
00076   bool operator>(const Timer &T) const { return T.operator<(*this); }
00077 
00078   /// startTimer - Start the timer running.  Time between calls to
00079   /// startTimer/stopTimer is counted by the Timer class.  Note that these calls
00080   /// must be correctly paired.
00081   ///
00082   void startTimer();
00083 
00084   /// stopTimer - Stop the timer.
00085   ///
00086   void stopTimer();
00087 
00088   /// addPeakMemoryMeasurement - This method should be called whenever memory
00089   /// usage needs to be checked.  It adds a peak memory measurement to the
00090   /// currently active timers, which will be printed when the timer group prints
00091   ///
00092   static void addPeakMemoryMeasurement();
00093 
00094   /// print - Print the current timer to standard error, and reset the "Started"
00095   /// flag.
00096   void print(const Timer &Total, std::ostream &OS);
00097 
00098 private:
00099   friend class TimerGroup;
00100 
00101   // Copy ctor, initialize with no TG member.
00102   Timer(bool, const Timer &T);
00103 
00104   /// sum - Add the time accumulated in the specified timer into this timer.
00105   ///
00106   void sum(const Timer &T);
00107 };
00108 
00109 
00110 /// The TimeRegion class is used as a helper class to call the startTimer() and
00111 /// stopTimer() methods of the Timer class.  When the object is constructed, it
00112 /// starts the timer specified as it's argument.  When it is destroyed, it stops
00113 /// the relevant timer.  This makes it easy to time a region of code.
00114 ///
00115 class TimeRegion {
00116   Timer &T;
00117   TimeRegion(const TimeRegion &); // DO NOT IMPLEMENT
00118 public:
00119   TimeRegion(Timer &t) : T(t) {
00120     T.startTimer();
00121   }
00122   ~TimeRegion() {
00123     T.stopTimer();
00124   }
00125 };
00126 
00127 
00128 /// NamedRegionTimer - This class is basically a combination of TimeRegion and
00129 /// Timer.  It allows you to declare a new timer, AND specify the region to
00130 /// time, all in one statement.  All timers with the same name are merged.  This
00131 /// is primarily used for debugging and for hunting performance problems.
00132 ///
00133 struct NamedRegionTimer : public TimeRegion {
00134   NamedRegionTimer(const std::string &Name);
00135 };
00136 
00137 
00138 /// The TimerGroup class is used to group together related timers into a single
00139 /// report that is printed when the TimerGroup is destroyed.  It is illegal to
00140 /// destroy a TimerGroup object before all of the Timers in it are gone.  A
00141 /// TimerGroup can be specified for a newly created timer in its constructor.
00142 ///
00143 class TimerGroup {
00144   std::string Name;
00145   unsigned NumTimers;
00146   std::vector<Timer> TimersToPrint;
00147 public:
00148   TimerGroup(const std::string &name) : Name(name), NumTimers(0) {}
00149   ~TimerGroup() {
00150     assert(NumTimers == 0 &&
00151            "TimerGroup destroyed before all contained timers!");
00152   }
00153 
00154 private:
00155   friend class Timer;
00156   void addTimer() { ++NumTimers; }
00157   void removeTimer();
00158   void addTimerToPrint(const Timer &T) {
00159     TimersToPrint.push_back(Timer(true, T));
00160   }
00161 };
00162 
00163 } // End llvm namespace
00164 
00165 #endif