diff -r e3b7c2d371d8 -r 98add689157b src/base/statistics.hh --- a/src/base/statistics.hh Sat Jul 10 02:21:10 2010 +0100 +++ b/src/base/statistics.hh Sat Jul 10 02:21:48 2010 +0100 @@ -68,6 +68,7 @@ #include "base/stats/visit.hh" #include "base/str.hh" #include "base/types.hh" +#include "base/misc.hh" class Callback; @@ -95,6 +96,8 @@ visitor.visit(*static_cast(this)); } bool zero() const { return s.zero(); } + void backup() { s.backup(); } + void restore() { s.restore(); } }; template @@ -376,6 +379,24 @@ for (off_type i = 0; i < size; ++i) self.data(i)->reset(info); } + + void + backup() + { + Derived &self = this->self(); + size_t size = self.size(); + for (off_type i = 0; i < size; ++i) + self.data(i)->backup(); + } + + void + restore() + { + Derived &self = this->self(); + size_t size = self.size(); + for (off_type i = 0; i < size; ++i) + self.data(i)->restore(); + } }; template class InfoProxyType> @@ -427,6 +448,8 @@ private: /** The statistic value. */ Counter data; + /** The backup value. */ + Counter dataBackup; public: struct Params : public StorageParams {}; @@ -478,6 +501,16 @@ * @return true if zero value */ bool zero() const { return data == Counter(); } + + /** + * Create a backup of the stat value. + */ + void backup() { dataBackup = data; } + + /** + * Restore the stat value from the backup. + */ + void restore() { data = dataBackup; } }; /** @@ -492,12 +525,15 @@ private: /** The current count. */ Counter current; - /** The tick of the last reset */ - Tick lastReset; /** The total count for all tick. */ mutable Result total; /** The tick that current last changed. */ mutable Tick last; + /** The total number of ticks counted. */ + Tick totalTicks; + /** The backups. */ + Counter backupCurrent; + Result backupTotal; public: struct Params : public StorageParams {}; @@ -507,7 +543,7 @@ * Build and initializes this stat storage. */ AvgStor(Info *info) - : current(0), lastReset(0), total(0), last(0) + : current(0), total(0), last(0), totalTicks(0) { } /** @@ -519,6 +555,7 @@ set(Counter val) { total += current * (curTick - last); + totalTicks += (curTick - last); last = curTick; current = val; } @@ -549,7 +586,7 @@ result() const { assert(last == curTick); - return (Result)(total + current) / (Result)(curTick - lastReset + 1); + return (Result)(total + current) / (Result)totalTicks; } /** @@ -564,6 +601,7 @@ prepare(Info *info) { total += current * (curTick - last); + totalTicks += curTick - last; last = curTick; } @@ -574,10 +612,31 @@ reset(Info *info) { total = 0.0; + totalTicks = 0; last = curTick; - lastReset = curTick; } + /** + * Backup stat value + */ + void + backup() + { + prepare(NULL); + backupCurrent = current; + backupTotal = total; + } + + /** + * Restore stat value + */ + void + restore() + { + current = backupCurrent; + total = backupTotal; + last = curTick; + } }; /** @@ -697,6 +756,9 @@ void reset() { data()->reset(this->info()); } void prepare() { data()->prepare(this->info()); } + + void backup() { data()->backup(); } + void restore() { data()->restore(); } }; class ProxyInfo : public ScalarInfo @@ -710,6 +772,8 @@ bool zero() const { return value() == 0; } void visit(Visit &visitor) { visitor.visit(*this); } + void backup() { } + void restore() { } }; template @@ -776,6 +840,8 @@ bool check() const { return proxy != NULL; } void prepare() { } void reset() { } + void backup() { } + void restore() { } }; ////////////////////////////////////////////////////////////////////// @@ -1016,6 +1082,20 @@ return storage != NULL; } + void + backup() + { + for (off_type i = 0; i < size(); ++i) + data(i)->backup(); + } + + void + restore() + { + for (off_type i = 0; i < size(); ++i) + data(i)->restore(); + } + public: VectorBase() : storage(NULL) @@ -1131,6 +1211,20 @@ } size_type size() const { return len; } + + void + backup() + { + for (off_type i = 0; i < size(); ++i) + data(i)->backup(); + } + + void + restore() + { + for (off_type i = 0; i < size(); ++i) + data(i)->restore(); + } }; template @@ -1257,6 +1351,22 @@ { return storage != NULL; } + + void + backup() + { + size_type size = this->size(); + for (off_type i = 0; i < size; ++i) + data(i)->backup(); + } + + void + restore() + { + size_type size = this->size(); + for (off_type i = 0; i < size; ++i) + data(i)->restore(); + } }; ////////////////////////////////////////////////////////////////////// @@ -1633,6 +1743,21 @@ { data()->reset(this->info()); } + + /** + * Backup stat value. + */ + void + backup() + { + warn_once("Not implemented backup / restore for distributions\n"); + } + + /** + * Restore stat value. + */ + void + restore() { } }; template @@ -2484,6 +2609,9 @@ bool zero() const; std::string str() const; + + void backup() { } + void restore() { } }; class FormulaNode : public Node @@ -2761,6 +2889,16 @@ std::list &statsList(); +/** + * Backup all statistics + */ +void backup(); + +/** + * Restore all statistics + */ +void restore(); + /* namespace Stats */ } #endif // __BASE_STATISTICS_HH__ diff -r e3b7c2d371d8 -r 98add689157b src/base/statistics.cc --- a/src/base/statistics.cc Sat Jul 10 02:21:10 2010 +0100 +++ b/src/base/statistics.cc Sat Jul 10 02:21:48 2010 +0100 @@ -377,4 +377,28 @@ resetQueue.add(cb); } +void +backup() +{ + list::iterator i = statsList().begin(); + list::iterator end = statsList().end(); + while (i != end) { + Info *info = *i; + info->backup(); + ++i; + } +} + +void +restore() +{ + list::iterator i = statsList().begin(); + list::iterator end = statsList().end(); + while (i != end) { + Info *info = *i; + info->restore(); + ++i; + } +} + /* namespace Stats */ } diff -r e3b7c2d371d8 -r 98add689157b src/base/stats/info.hh --- a/src/base/stats/info.hh Sat Jul 10 02:21:10 2010 +0100 +++ b/src/base/stats/info.hh Sat Jul 10 02:21:48 2010 +0100 @@ -133,6 +133,16 @@ virtual void visit(Visit &visitor) = 0; /** + * Create a backup of the stat. + */ + virtual void backup() = 0; + + /** + * Restore the stat from the backup. + */ + virtual void restore() = 0; + + /** * Checks if the first stat's name is alphabetically less than the second. * This function breaks names up at periods and considers each subname * separately. diff -r e3b7c2d371d8 -r 98add689157b src/python/m5/simulate.py --- a/src/python/m5/simulate.py Sat Jul 10 02:21:10 2010 +0100 +++ b/src/python/m5/simulate.py Sat Jul 10 02:21:48 2010 +0100 @@ -190,4 +190,10 @@ for old_cpu, new_cpu in cpuList: new_cpu.takeOverFrom(old_cpu, connectMem) +def backupStats(): + stats.backup() + +def restoreStats(): + stats.restore() + from internal.core import disableAllListeners diff -r e3b7c2d371d8 -r 98add689157b src/python/m5/stats.py --- a/src/python/m5/stats.py Sat Jul 10 02:21:10 2010 +0100 +++ b/src/python/m5/stats.py Sat Jul 10 02:21:48 2010 +0100 @@ -57,3 +57,9 @@ def reset(): internal.stats.reset() + +def backup(): + internal.stats.backup() + +def restore(): + internal.stats.restore() diff -r e3b7c2d371d8 -r 98add689157b src/python/swig/stats.i --- a/src/python/swig/stats.i Sat Jul 10 02:21:10 2010 +0100 +++ b/src/python/swig/stats.i Sat Jul 10 02:21:48 2010 +0100 @@ -56,6 +56,8 @@ void prepare(); void dump(); void reset(); +void backup(); +void restore(); std::list &statsList();