|
|
|
@ -21,7 +21,12 @@ |
|
|
|
|
#endif |
|
|
|
|
|
|
|
|
|
#if defined(__powerpc__) || defined(__ppc__) |
|
|
|
|
#ifdef __GLIBC__ |
|
|
|
|
#include <sys/platform/ppc.h> |
|
|
|
|
#elif defined(__FreeBSD__) |
|
|
|
|
#include <sys/sysctl.h> |
|
|
|
|
#include <sys/types.h> |
|
|
|
|
#endif |
|
|
|
|
#endif |
|
|
|
|
|
|
|
|
|
#include "absl/base/internal/sysinfo.h" |
|
|
|
@ -57,11 +62,43 @@ double UnscaledCycleClock::Frequency() { |
|
|
|
|
#elif defined(__powerpc__) || defined(__ppc__) |
|
|
|
|
|
|
|
|
|
int64_t UnscaledCycleClock::Now() { |
|
|
|
|
#ifdef __GLIBC__ |
|
|
|
|
return __ppc_get_timebase(); |
|
|
|
|
#else |
|
|
|
|
#ifdef __powerpc64__ |
|
|
|
|
int64_t tbr; |
|
|
|
|
asm volatile("mfspr %0, 268" : "=r"(tbr)); |
|
|
|
|
return tbr; |
|
|
|
|
#else |
|
|
|
|
int32_t tbu, tbl, tmp; |
|
|
|
|
asm volatile( |
|
|
|
|
"0:\n" |
|
|
|
|
"mftbu %[hi32]\n" |
|
|
|
|
"mftb %[lo32]\n" |
|
|
|
|
"mftbu %[tmp]\n" |
|
|
|
|
"cmpw %[tmp],%[hi32]\n" |
|
|
|
|
"bne 0b\n" |
|
|
|
|
: [ hi32 ] "=r"(tbu), [ lo32 ] "=r"(tbl), [ tmp ] "=r"(tmp)); |
|
|
|
|
return (static_cast<int64_t>(tbu) << 32) | tbl; |
|
|
|
|
#endif |
|
|
|
|
#endif |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
double UnscaledCycleClock::Frequency() { |
|
|
|
|
#ifdef __GLIBC__ |
|
|
|
|
return __ppc_get_timebase_freq(); |
|
|
|
|
#elif defined(__FreeBSD__) |
|
|
|
|
static once_flag init_timebase_frequency_once; |
|
|
|
|
static double timebase_frequency = 0.0; |
|
|
|
|
base_internal::LowLevelCallOnce(&init_timebase_frequency_once, [&]() { |
|
|
|
|
size_t length = sizeof(timebase_frequency); |
|
|
|
|
sysctlbyname("kern.timecounter.tc.timebase.frequency", &timebase_frequency, |
|
|
|
|
&length, nullptr, 0); |
|
|
|
|
}); |
|
|
|
|
return timebase_frequency; |
|
|
|
|
#else |
|
|
|
|
#error Must implement UnscaledCycleClock::Frequency() |
|
|
|
|
#endif |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
#elif defined(__aarch64__) |
|
|
|
|