diff options
Diffstat (limited to 'src/uscxml/concurrency')
-rw-r--r-- | src/uscxml/concurrency/DelayedEventQueue.cpp | 14 | ||||
-rw-r--r-- | src/uscxml/concurrency/DelayedEventQueue.h | 4 | ||||
-rw-r--r-- | src/uscxml/concurrency/Timer.cpp | 158 | ||||
-rw-r--r-- | src/uscxml/concurrency/Timer.h | 82 |
4 files changed, 129 insertions, 129 deletions
diff --git a/src/uscxml/concurrency/DelayedEventQueue.cpp b/src/uscxml/concurrency/DelayedEventQueue.cpp index ca43c8e..897e99d 100644 --- a/src/uscxml/concurrency/DelayedEventQueue.cpp +++ b/src/uscxml/concurrency/DelayedEventQueue.cpp @@ -100,12 +100,12 @@ void DelayedEventQueue::addEvent(std::string eventId, void (*callback)(void*, co } void DelayedEventQueue::cancelAllEvents() { - tthread::lock_guard<tthread::recursive_mutex> lock(_mutex); - while(_callbackData.size() > 0) { - event_del(_callbackData[_callbackData.begin()->first].event); - event_free(_callbackData[_callbackData.begin()->first].event); - _callbackData.erase(_callbackData.begin()); - } + tthread::lock_guard<tthread::recursive_mutex> lock(_mutex); + while(_callbackData.size() > 0) { + event_del(_callbackData[_callbackData.begin()->first].event); + event_free(_callbackData[_callbackData.begin()->first].event); + _callbackData.erase(_callbackData.begin()); + } } void DelayedEventQueue::cancelEvent(std::string eventId) { @@ -131,7 +131,7 @@ void DelayedEventQueue::stop() { if (_thread) { _thread->join(); delete _thread; - _thread = NULL; + _thread = NULL; } } diff --git a/src/uscxml/concurrency/DelayedEventQueue.h b/src/uscxml/concurrency/DelayedEventQueue.h index d89b715..7c2789f 100644 --- a/src/uscxml/concurrency/DelayedEventQueue.h +++ b/src/uscxml/concurrency/DelayedEventQueue.h @@ -57,8 +57,8 @@ public: void addEvent(std::string eventId, int fd, short opMask, void (*callback)(void*, const std::string eventId), void* userData, bool persist = true); void addEvent(std::string eventId, void (*callback)(void*, const std::string eventId), uint32_t delayMs, void* userData, bool persist = false); - void cancelEvent(std::string eventId); - void cancelAllEvents(); + void cancelEvent(std::string eventId); + void cancelAllEvents(); void start(); void stop(); diff --git a/src/uscxml/concurrency/Timer.cpp b/src/uscxml/concurrency/Timer.cpp index 2835173..77b712f 100644 --- a/src/uscxml/concurrency/Timer.cpp +++ b/src/uscxml/concurrency/Timer.cpp @@ -14,102 +14,102 @@ #define USECS_PER_SEC 1000000 #if _POSIX_TIMERS > 0 && defined(_POSIX_MONOTONIC_CLOCK) - // If we have it, use clock_gettime and CLOCK_MONOTONIC. +// If we have it, use clock_gettime and CLOCK_MONOTONIC. - #include <time.h> +#include <time.h> - double uscxml::Timer::monotonic_seconds() { - struct timespec time; - // Note: Make sure to link with -lrt to define clock_gettime. - clock_gettime(CLOCK_MONOTONIC, &time); - return ((double) time.tv_sec) + ((double) time.tv_nsec / (NANOS_PER_SECF)); - } +double uscxml::Timer::monotonic_seconds() { + struct timespec time; + // Note: Make sure to link with -lrt to define clock_gettime. + clock_gettime(CLOCK_MONOTONIC, &time); + return ((double) time.tv_sec) + ((double) time.tv_nsec / (NANOS_PER_SECF)); +} #elif defined(__APPLE__) - // If we don't have CLOCK_MONOTONIC, we might be on a Mac. There we instead - // use mach_absolute_time(). +// If we don't have CLOCK_MONOTONIC, we might be on a Mac. There we instead +// use mach_absolute_time(). - #include <mach/mach_time.h> +#include <mach/mach_time.h> - static mach_timebase_info_data_t info; - static void __attribute__((constructor)) init_info() { - mach_timebase_info(&info); - } +static mach_timebase_info_data_t info; +static void __attribute__((constructor)) init_info() { + mach_timebase_info(&info); +} - double uscxml::Timer::monotonic_seconds() { - uint64_t time = mach_absolute_time(); - double dtime = (double) time; - dtime *= (double) info.numer; - dtime /= (double) info.denom; - return dtime / NANOS_PER_SECF; - } +double uscxml::Timer::monotonic_seconds() { + uint64_t time = mach_absolute_time(); + double dtime = (double) time; + dtime *= (double) info.numer; + dtime /= (double) info.denom; + return dtime / NANOS_PER_SECF; +} #elif defined(_MSC_VER) - // On Windows, use QueryPerformanceCounter and QueryPerformanceFrequency. +// On Windows, use QueryPerformanceCounter and QueryPerformanceFrequency. #define NOMINMAX - #include <windows.h> +#include <windows.h> - static double PCFreq = 0.0; +static double PCFreq = 0.0; __int64 CounterStart = 0; - double uscxml::Timer::monotonic_seconds() { - if (CounterStart == 0) { - // Accoring to http://stackoverflow.com/a/1739265/447288, this will - // properly initialize the QueryPerformanceCounter. +double uscxml::Timer::monotonic_seconds() { + if (CounterStart == 0) { + // Accoring to http://stackoverflow.com/a/1739265/447288, this will + // properly initialize the QueryPerformanceCounter. - LARGE_INTEGER li; - int has_qpc = QueryPerformanceFrequency(&li); + LARGE_INTEGER li; + int has_qpc = QueryPerformanceFrequency(&li); - PCFreq = ((double) li.QuadPart) / 1000.0; - } - LARGE_INTEGER li; - QueryPerformanceCounter(&li); - return double(li.QuadPart - CounterStart)/PCFreq; - } + PCFreq = ((double) li.QuadPart) / 1000.0; + } + LARGE_INTEGER li; + QueryPerformanceCounter(&li); + return double(li.QuadPart - CounterStart)/PCFreq; +} #else - // Fall back to rdtsc. The reason we don't use clock() is this scary message - // from the man page: - // "On several other implementations, the value returned by clock() also - // includes the times of any children whose status has been collected via - // wait(2) (or another wait-type call)." - // - // Also, clock() only has microsecond accuracy. - // - // This whitepaper offered excellent advice on how to use rdtscp for - // profiling: http://download.intel.com/embedded/software/IA/324264.pdf - // - // Unfortunately, we can't follow its advice exactly with our semantics, - // so we're just going to use rdtscp with cpuid. - // - // Note that rdtscp will only be available on new processors. - - #include <stdint.h> - - static inline uint64_t rdtsc() { - uint32_t hi, lo; - asm volatile("rdtscp\n" - "movl %%edx, %0\n" - "movl %%eax, %1\n" - "cpuid" - : "=r" (hi), "=r" (lo) : : "%rax", "%rbx", "%rcx", "%rdx"); - return (((uint64_t)hi) << 32) | (uint64_t)lo; - } - - static uint64_t rdtsc_per_sec = 0; - static void __attribute__((constructor)) init_rdtsc_per_sec() { - uint64_t before, after; - - before = rdtsc(); - usleep(USECS_PER_SEC); - after = rdtsc(); - - rdtsc_per_sec = after - before; - } - - double uscxml::Timer::monotonic_seconds() { - return (double) rdtsc() / (double) rdtsc_per_sec; - } +// Fall back to rdtsc. The reason we don't use clock() is this scary message +// from the man page: +// "On several other implementations, the value returned by clock() also +// includes the times of any children whose status has been collected via +// wait(2) (or another wait-type call)." +// +// Also, clock() only has microsecond accuracy. +// +// This whitepaper offered excellent advice on how to use rdtscp for +// profiling: http://download.intel.com/embedded/software/IA/324264.pdf +// +// Unfortunately, we can't follow its advice exactly with our semantics, +// so we're just going to use rdtscp with cpuid. +// +// Note that rdtscp will only be available on new processors. + +#include <stdint.h> + +static inline uint64_t rdtsc() { + uint32_t hi, lo; + asm volatile("rdtscp\n" + "movl %%edx, %0\n" + "movl %%eax, %1\n" + "cpuid" + : "=r" (hi), "=r" (lo) : : "%rax", "%rbx", "%rcx", "%rdx"); + return (((uint64_t)hi) << 32) | (uint64_t)lo; +} + +static uint64_t rdtsc_per_sec = 0; +static void __attribute__((constructor)) init_rdtsc_per_sec() { + uint64_t before, after; + + before = rdtsc(); + usleep(USECS_PER_SEC); + after = rdtsc(); + + rdtsc_per_sec = after - before; +} + +double uscxml::Timer::monotonic_seconds() { + return (double) rdtsc() / (double) rdtsc_per_sec; +} #endif diff --git a/src/uscxml/concurrency/Timer.h b/src/uscxml/concurrency/Timer.h index 217f68f..1ecfeb2 100644 --- a/src/uscxml/concurrency/Timer.h +++ b/src/uscxml/concurrency/Timer.h @@ -18,56 +18,56 @@ namespace uscxml { class USCXML_API Timer { public: - - static double monotonic_seconds(); - - Timer() { - invocations = 0; - elapsed = 0; - } - - void start() { - if (invocations == 0) { - started = monotonic_seconds(); - } - invocations++; - } - - void reset() { - elapsed = 0; + + static double monotonic_seconds(); + + Timer() { + invocations = 0; + elapsed = 0; + } + + void start() { + if (invocations == 0) { + started = monotonic_seconds(); } - - void stop() { - if (invocations == 0) - return; - - invocations--; - if (invocations == 0) { - elapsed += monotonic_seconds() - started; - } - } - - ~Timer() { - } - double elapsed; + invocations++; + } + + void reset() { + elapsed = 0; + } + + void stop() { + if (invocations == 0) + return; + + invocations--; + if (invocations == 0) { + elapsed += monotonic_seconds() - started; + } + } + + ~Timer() { + } + double elapsed; protected: - size_t invocations; - double started; + size_t invocations; + double started; }; - + class USCXML_API Measurement { public: - Measurement(Timer* timer) : timer(timer) { - timer->start(); - } + Measurement(Timer* timer) : timer(timer) { + timer->start(); + } - ~Measurement() { - timer->stop(); - } + ~Measurement() { + timer->stop(); + } protected: - Timer* timer; + Timer* timer; }; } |