-
Notifications
You must be signed in to change notification settings - Fork 298
/
measure_time_rdtsc.cpp
128 lines (105 loc) · 3.1 KB
/
measure_time_rdtsc.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
#include <Core/ModelicaDefine.h>
#include <Core/Modelica.h>
#include <Core/Utils/extension/measure_time_rdtsc.hpp>
MeasureTimeValuesRDTSC::MeasureTimeValuesRDTSC(unsigned long long time) : MeasureTimeValues(), _time(time), _maxTime(time) {}
MeasureTimeValuesRDTSC::MeasureTimeValuesRDTSC(const MeasureTimeValuesRDTSC &timeValues) : MeasureTimeValues(timeValues), _time(timeValues._time), _maxTime(timeValues._maxTime) {}
MeasureTimeValuesRDTSC::~MeasureTimeValuesRDTSC() {}
std::string MeasureTimeValuesRDTSC::serializeToJson() const
{
std::stringstream ss;
ss << "\"ncall\":" << _numCalcs << ",\"time\":" << _time << ",\"maxTime\":" << _maxTime << ",\"meanTime\":" << (_numCalcs == 0 ? 0 : _time/_numCalcs);
return ss.str();
}
void MeasureTimeValuesRDTSC::add(MeasureTimeValues *values)
{
MeasureTimeValuesRDTSC *val = static_cast<MeasureTimeValuesRDTSC*>(values);
_time += val->_time;
if( val->_time > _maxTime )
_maxTime = val->_time;
}
void MeasureTimeValuesRDTSC::sub(MeasureTimeValues *values)
{
MeasureTimeValuesRDTSC *val = static_cast<MeasureTimeValuesRDTSC*>(values);
if(_time > val->_time)
_time -= val->_time;
else
_time = 0ull;
}
void MeasureTimeValuesRDTSC::div(int counter)
{
_time = _time / counter;
}
MeasureTimeValuesRDTSC* MeasureTimeValuesRDTSC::clone() const
{
return new MeasureTimeValuesRDTSC(*this);
}
void MeasureTimeValuesRDTSC::reset()
{
MeasureTimeValues::reset();
_time = 0;
_maxTime = 0;
}
MeasureTimeRDTSC::MeasureTimeRDTSC() : MeasureTime()
{
}
MeasureTimeRDTSC::~MeasureTimeRDTSC()
{
}
void MeasureTimeRDTSC::initializeThread(unsigned long int threadNumber)
{
}
void MeasureTimeRDTSC::deinitializeThread()
{
}
void MeasureTimeRDTSC::getTimeValuesStartP(MeasureTimeValues *res) const
{
MeasureTimeValuesRDTSC *val = static_cast<MeasureTimeValuesRDTSC*>(res);
unsigned long long time = RDTSC();
val->_time = time;
}
void MeasureTimeRDTSC::getTimeValuesEndP(MeasureTimeValues *res) const
{
unsigned long long time = RDTSC();
MeasureTimeValuesRDTSC *val = static_cast<MeasureTimeValuesRDTSC*>(res);
val->_time = time;
}
MeasureTimeValues* MeasureTimeRDTSC::getZeroValuesP() const
{
return new MeasureTimeValuesRDTSC(0ull);
}
#if defined(_MSC_VER)
#if defined(__i386__) || defined(__x86_64__)
unsigned long long MeasureTimeRDTSC::RDTSC()
{
return _rdtsc();
}
#else
unsigned long long MeasureTimeRDTSC::RDTSC()
{
throw ModelicaSimulationError(UTILITY,"No time measurement for this processor arch.");
return 0;
}
#endif // defined(__i386__) || defined(__x86_64__)
#else
#if defined(__x86_64__)
unsigned long long MeasureTimeRDTSC::RDTSC()
{
unsigned hi, lo;
__asm__ __volatile__ ("rdtsc" : "=a"(lo), "=d"(hi));
return ((unsigned long long) lo) | (((unsigned long long) hi) << 32);
}
#elif defined(__i386__)
unsigned long long MeasureTimeRDTSC::RDTSC()
{
unsigned long long res;
asm volatile (".byte 0x0f, 0x31" : "=A" (res));
return res;
}
#else
unsigned long long MeasureTimeRDTSC::RDTSC()
{
throw ModelicaSimulationError(UTILITY,"No time measurement for this processor arch.");
return 0;
}
#endif //defined(__i386__)
#endif //defined(_MSC_VER)