Enable use of CLOCK_MONOTONIC_RAW for post 4.4 kernels.

Change-Id: I3c1f27c7e639df5128c36d81f715fa16e6c1cf13


[ROCm/ROCR-Runtime commit: 30fce248c6]
Этот коммит содержится в:
Sean Keely
2017-09-14 20:08:53 -05:00
родитель 6c0e9b2c6f
Коммит 595c7130d2
+30 -7
Просмотреть файл
@@ -47,12 +47,14 @@
#include <dlfcn.h>
#include <pthread.h>
#include <sched.h>
#include <string>
#include <cstring>
#include <sys/sysinfo.h>
#include <sys/time.h>
#include <sys/utsname.h>
#include <unistd.h>
#include <errno.h>
#include <cstring>
#include <string>
#include <atomic>
namespace os {
@@ -334,15 +336,36 @@ uint64_t ReadAccurateClock() {
}
uint64_t AccurateClockFrequency() {
static clockid_t clock = CLOCK_MONOTONIC;
static std::atomic<bool> first(true);
// Check kernel version - not a concurrency concern.
// use non-RAW for getres due to bug in older 2.6.x kernels
if (first.load(std::memory_order_acquire)) {
utsname kernelInfo;
if (uname(&kernelInfo) == 0) {
try {
std::string ver = kernelInfo.release;
size_t idx;
int major = std::stoi(ver, &idx);
int minor = std::stoi(ver.substr(idx + 1));
if ((major >= 4) && (minor >= 4)) {
clock = CLOCK_MONOTONIC_RAW;
}
} catch (...) {
// Kernel version string doesn't conform to the standard pattern.
// Keep using the "safe" (non-RAW) clock.
}
}
first.store(false, std::memory_order_release);
}
timespec time;
//use non-RAW for getres due to bug in older 2.6.x kernels
int err = clock_getres(CLOCK_MONOTONIC, &time);
assert(err == 0 && "clock_getres(CLOCK_MONOTONIC,...) failed");
int err = clock_getres(clock, &time);
assert(err == 0 && "clock_getres(CLOCK_MONOTONIC(_RAW),...) failed");
assert(time.tv_sec == 0 &&
"clock_getres(CLOCK_MONOTONIC,...) returned very low frequency "
"clock_getres(CLOCK_MONOTONIC(_RAW),...) returned very low frequency "
"(<1Hz).");
assert(time.tv_nsec < 0xFFFFFFFF &&
"clock_getres(CLOCK_MONOTONIC,...) returned very low frequency "
"clock_getres(CLOCK_MONOTONIC(_RAW),...) returned very low frequency "
"(<1Hz).");
if (invPeriod == 0.0) invPeriod = 1.0 / double(time.tv_nsec);
return 1000000000ull / uint64_t(time.tv_nsec);