1 #ifndef LIBJMMCG_CORE_HP_TIMER_HPP
2 #define LIBJMMCG_CORE_HP_TIMER_HPP
26 #include "boost/date_time/posix_time/posix_time_types.hpp"
34 # if defined(i386) || defined(__i386__) || defined(__x86_64__
)
37 # if (__ARM_ARCH >= 6
)
38 inline std::uint64_t __rdtsc()
noexcept(
true) {
39 std::uint32_t pmccntr;
40 std::uint32_t pmuseren;
41 std::uint32_t pmcntenset;
43 asm volatile(
"mrc p15, 0, %0, c9, c14, 0" :
"=r"(pmuseren));
45 asm volatile(
"mrc p15, 0, %0, c9, c12, 1" :
"=r"(pmcntenset));
46 if (pmcntenset & 0x80000000ul) {
47 asm volatile(
"mrc p15, 0, %0, c9, c13, 0" :
"=r"(pmccntr));
49 return static_cast<std::uint64_t>(pmccntr) * 64ULL;
54 inline std::uint64_t __rdtscp(
unsigned int *)
noexcept(
true) {
57 inline std::uint64_t __cpuid(
int,
unsigned,
unsigned,
unsigned,
unsigned)
noexcept(
true) {
86 :
timer(t),
start(t.current_time()), interval(i) {
95 typename timer_t::time_utc_t &interval;
108 using element_type=
std::uint64_t;
131 const element_type end(
now());
137 const element_type start;
150 unsigned eax, ebx, ecx, edx;
152 __cpuid(1, eax, ebx, ecx, edx);
157 return __rdtscp(&cpu);
180 const element_type start;
213 assert(ticks>private_::start_ticks);
214 const element_type ticks_since_start=ticks-
private_::start_ticks;
215 const double microsecs_since_start=ticks_since_start/
private_::ticks_per_microsec
.mean;
216 assert(microsecs_since_start>=0);
217 return microsecs_since_start;
220 inline boost::posix_time::ptime
222 const boost::posix_time::ptime curr_UTC=private_::start_UTC+boost::posix_time::microseconds(
static_cast<
unsigned long long>(TSC_to_microsec(ticks)));
223 assert(curr_UTC>private_::start_UTC);
235 element_type delay_achieved;
238 assert(current>begin);
240 }
while (delay_achieved<delay);
241 assert(delay_achieved>=delay);
242 return delay_achieved;
250 # include "../experimental/NT-based/NTSpecific/hp_timer.hpp"
251 #elif defined(__unix__
)
252 # include "../unix/hp_timer.hpp"