Index: include/llvm/Support/Timer.h =================================================================== --- include/llvm/Support/Timer.h +++ include/llvm/Support/Timer.h @@ -62,8 +62,8 @@ MemUsed -= RHS.MemUsed; } - /// print - Print the current timer to standard error, and reset the "Started" - /// flag. + /// print - Print the current time record to \p OS, with a breakdown showing + /// contributions to the \p Total time record. void print(const TimeRecord &Total, raw_ostream &OS) const; }; @@ -76,9 +76,10 @@ /// if they are never started. /// class Timer { - TimeRecord Time; + TimeRecord Time; // The total time captured + TimeRecord StartTime; // The time `startTimer' was last called std::string Name; // The name of this time variable. - bool Started; // Has this time variable ever been started? + bool Started; // Is the timer currently running? TimerGroup *TG; // The TimerGroup this Timer is in. Timer **Prev, *Next; // Doubly linked list of timers in the group. @@ -102,16 +103,24 @@ const std::string &getName() const { return Name; } bool isInitialized() const { return TG != nullptr; } - /// startTimer - Start the timer running. Time between calls to - /// startTimer/stopTimer is counted by the Timer class. Note that these calls - /// must be correctly paired. - /// + /// hasTriggered - Check if startTimer() has ever been called on this timer. + bool hasTriggered() const { return TimeRecord() < StartTime; } + + /// Start the timer running. Time between calls to startTimer/stopTimer is + /// counted by the Timer class. Note that these calls must be correctly + /// paired. void startTimer(); - /// stopTimer - Stop the timer. - /// + /// Stop the timer. void stopTimer(); + /// Stop the timer if it's running and clear the total time. This does not + /// affect the result of hasTriggered(). + void clear(); + + /// Return the duration for which this timer has been running. + TimeRecord getTotalTime() const { return Time; } + private: friend class TimerGroup; }; Index: lib/Support/Timer.cpp =================================================================== --- lib/Support/Timer.cpp +++ lib/Support/Timer.cpp @@ -96,11 +96,7 @@ //===----------------------------------------------------------------------===// void Timer::init(StringRef N) { - assert(!TG && "Timer already initialized"); - Name.assign(N.begin(), N.end()); - Started = false; - TG = getDefaultTimerGroup(); - TG->addTimer(*this); + init(N, *getDefaultTimerGroup()); } void Timer::init(StringRef N, TimerGroup &tg) { @@ -139,25 +135,22 @@ return Result; } -static ManagedStatic > ActiveTimers; - void Timer::startTimer() { + assert(!Started && "Cannot start a running timer"); Started = true; - ActiveTimers->push_back(this); - Time -= TimeRecord::getCurrentTime(true); + StartTime = TimeRecord::getCurrentTime(true); } void Timer::stopTimer() { + assert(Started && "Cannot stop a paused timer"); + Started = false; Time += TimeRecord::getCurrentTime(false); + Time -= StartTime; +} - if (ActiveTimers->back() == this) { - ActiveTimers->pop_back(); - } else { - std::vector::iterator I = - std::find(ActiveTimers->begin(), ActiveTimers->end(), this); - assert(I != ActiveTimers->end() && "stop but no startTimer?"); - ActiveTimers->erase(I); - } +void Timer::clear() { + Started = false; + Time = StartTime = TimeRecord(); } static void printVal(double Val, double Total, raw_ostream &OS) { @@ -275,8 +268,8 @@ sys::SmartScopedLock L(*TimerLock); // If the timer was started, move its data to TimersToPrint. - if (T.Started) - TimersToPrint.push_back(std::make_pair(T.Time, T.Name)); + if (T.hasTriggered()) + TimersToPrint.push_back(std::make_pair(T.getTotalTime(), T.getName())); T.TG = nullptr; @@ -361,12 +354,11 @@ // See if any of our timers were started, if so add them to TimersToPrint and // reset them. for (Timer *T = FirstTimer; T; T = T->Next) { - if (!T->Started) continue; - TimersToPrint.push_back(std::make_pair(T->Time, T->Name)); + if (!T->hasTriggered()) continue; + TimersToPrint.push_back(std::make_pair(T->getTotalTime(), T->getName())); // Clear out the time. - T->Started = 0; - T->Time = TimeRecord(); + T->clear(); } // If any timers were started, print the group. Index: unittests/Support/CMakeLists.txt =================================================================== --- unittests/Support/CMakeLists.txt +++ unittests/Support/CMakeLists.txt @@ -42,6 +42,7 @@ TargetRegistry.cpp ThreadLocalTest.cpp ThreadPool.cpp + TimerTest.cpp TimeValueTest.cpp TrailingObjectsTest.cpp UnicodeTest.cpp