2
0

timer.cpp 2.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152
  1. // File: timer.cpp - Simple high-precision timer class. Supports Win32, X360, and POSIX/Linux
  2. #include <stdlib.h>
  3. #include <stdio.h>
  4. #include <assert.h>
  5. #include <time.h>
  6. #include "timer.h"
  7. #if defined(WIN32)
  8. #include <windows.h>
  9. #elif defined(_XBOX)
  10. #include <xtl.h>
  11. #endif
  12. unsigned long long timer::g_init_ticks;
  13. unsigned long long timer::g_freq;
  14. double timer::g_inv_freq;
  15. #if defined(WIN32) || defined(_XBOX)
  16. inline void query_counter(timer_ticks *pTicks)
  17. {
  18. QueryPerformanceCounter(reinterpret_cast<LARGE_INTEGER*>(pTicks));
  19. }
  20. inline void query_counter_frequency(timer_ticks *pTicks)
  21. {
  22. QueryPerformanceFrequency(reinterpret_cast<LARGE_INTEGER*>(pTicks));
  23. }
  24. #elif defined(__GNUC__)
  25. #include <sys/timex.h>
  26. inline void query_counter(timer_ticks *pTicks)
  27. {
  28. struct timeval cur_time;
  29. gettimeofday(&cur_time, NULL);
  30. *pTicks = static_cast<unsigned long long>(cur_time.tv_sec)*1000000ULL + static_cast<unsigned long long>(cur_time.tv_usec);
  31. }
  32. inline void query_counter_frequency(timer_ticks *pTicks)
  33. {
  34. *pTicks = 1000000;
  35. }
  36. #endif
  37. timer::timer() :
  38. m_start_time(0),
  39. m_stop_time(0),
  40. m_started(false),
  41. m_stopped(false)
  42. {
  43. if (!g_inv_freq)
  44. init();
  45. }
  46. timer::timer(timer_ticks start_ticks)
  47. {
  48. if (!g_inv_freq)
  49. init();
  50. m_start_time = start_ticks;
  51. m_started = true;
  52. m_stopped = false;
  53. }
  54. void timer::start(timer_ticks start_ticks)
  55. {
  56. m_start_time = start_ticks;
  57. m_started = true;
  58. m_stopped = false;
  59. }
  60. void timer::start()
  61. {
  62. query_counter(&m_start_time);
  63. m_started = true;
  64. m_stopped = false;
  65. }
  66. void timer::stop()
  67. {
  68. assert(m_started);
  69. query_counter(&m_stop_time);
  70. m_stopped = true;
  71. }
  72. double timer::get_elapsed_secs() const
  73. {
  74. assert(m_started);
  75. if (!m_started)
  76. return 0;
  77. timer_ticks stop_time = m_stop_time;
  78. if (!m_stopped)
  79. query_counter(&stop_time);
  80. timer_ticks delta = stop_time - m_start_time;
  81. return delta * g_inv_freq;
  82. }
  83. timer_ticks timer::get_elapsed_us() const
  84. {
  85. assert(m_started);
  86. if (!m_started)
  87. return 0;
  88. timer_ticks stop_time = m_stop_time;
  89. if (!m_stopped)
  90. query_counter(&stop_time);
  91. timer_ticks delta = stop_time - m_start_time;
  92. return (delta * 1000000ULL + (g_freq >> 1U)) / g_freq;
  93. }
  94. void timer::init()
  95. {
  96. if (!g_inv_freq)
  97. {
  98. query_counter_frequency(&g_freq);
  99. g_inv_freq = 1.0f / g_freq;
  100. query_counter(&g_init_ticks);
  101. }
  102. }
  103. timer_ticks timer::get_init_ticks()
  104. {
  105. if (!g_inv_freq)
  106. init();
  107. return g_init_ticks;
  108. }
  109. timer_ticks timer::get_ticks()
  110. {
  111. if (!g_inv_freq)
  112. init();
  113. timer_ticks ticks;
  114. query_counter(&ticks);
  115. return ticks - g_init_ticks;
  116. }
  117. double timer::ticks_to_secs(timer_ticks ticks)
  118. {
  119. if (!g_inv_freq)
  120. init();
  121. return ticks * g_inv_freq;
  122. }