]> git.tdb.fi Git - libs/core.git/blob - source/debug/profiler.cpp
Merge branch 'fs-master'
[libs/core.git] / source / debug / profiler.cpp
1 #include <msp/core/maputils.h>
2 #include <msp/time/units.h>
3 #include "profiler.h"
4
5 using namespace std;
6
7 namespace Msp {
8 namespace Debug {
9
10 Profiler::Profiler():
11         period(0),
12         inner(0)
13 { }
14
15 void Profiler::set_period(unsigned p)
16 {
17         if(p==period)
18                 return;
19
20         period = p;
21         for(map<string, ScopeInfo>::iterator i=scopes.begin(); i!=scopes.end(); ++i)
22         {
23                 ScopeInfo &si = i->second;
24                 if(p==0)
25                         si.history.clear();
26                 else
27                         si.history.assign(period, Time::zero);
28                 si.hist_pos = 0;
29         }
30 }
31
32 void Profiler::add_scope(const std::string &name)
33 {
34         if(!scopes.count(name))
35         {
36                 map<string, ScopeInfo>::iterator i = scopes.insert(map<string, ScopeInfo>::value_type(name, ScopeInfo())).first;
37                 i->second.history.resize(period);
38         }
39 }
40
41 ProfilingScope *Profiler::enter(ProfilingScope *ps)
42 {
43         ProfilingScope *old = inner;
44         inner = ps;
45         return old;
46 }
47
48 void Profiler::record(const string &scope_name, const string &parent, const Time::TimeDelta &time, const Time::TimeDelta &child_t)
49 {
50         map<string, ScopeInfo>::iterator i = scopes.find(scope_name);
51         if(i==scopes.end())
52         {
53                 i = scopes.insert(map<string, ScopeInfo>::value_type(scope_name, ScopeInfo())).first;
54                 i->second.history.resize(period);
55         }
56
57         ScopeInfo &si = i->second;
58         ++si.calls;
59         ++si.called_from[parent];
60         si.total_time += time;
61         si.self_time += time-child_t;
62         if(period)
63         {
64                 si.avg_time += time/period-si.history[si.hist_pos]/period;
65                 si.history[si.hist_pos++] = time;
66                 if(si.hist_pos>=period)
67                         si.hist_pos -= period;
68         }
69         else
70                 si.avg_time = si.total_time/si.calls;
71 }
72
73 const Profiler::ScopeInfo &Profiler::scope(const string &sn) const
74 {
75         return get_item(scopes, sn);
76 }
77
78
79 Profiler::ScopeInfo::ScopeInfo():
80         calls(0),
81         hist_pos(0)
82 { }
83
84 } // namespace Debug
85 } // namespace Msp