diff options
author | Dave Jones <davej@redhat.com> | 2008-07-02 13:51:37 -0400 |
---|---|---|
committer | Dave Jones <davej@redhat.com> | 2008-07-02 13:51:37 -0400 |
commit | 48c773f4c03a6b83370682d23217dcabb7e51d50 (patch) | |
tree | b4e325e967014ce43fa7d7e57f2a490ab7e4405a /bench | |
parent | 89fbc7d42b1bb9bc2166de534ddd00ff903a4abe (diff) |
Improve MHz estimation.
The fatal flaw was that rdtsc was wrapping too soon as we were only
using 32bits of accuracy. Extending this to 64bit increases the
resolution of the timing dramatically. We can also do away with
all the other timing code as a bonus.
Diffstat (limited to 'bench')
-rw-r--r-- | bench/MHz.c | 37 |
1 files changed, 14 insertions, 23 deletions
diff --git a/bench/MHz.c b/bench/MHz.c index 87315a9..187aa28 100644 --- a/bench/MHz.c +++ b/bench/MHz.c @@ -17,11 +17,14 @@ #include "../x86info.h" -static unsigned long long int rdtsc(void) +static inline unsigned long long int rdtsc(void) { - unsigned long long int x; - __asm__ volatile (".byte 0x0f, 0x31" : "=A" (x)); - return x; + unsigned int low, high; + unsigned long tsc; + + __asm__ __volatile__("rdtsc" : "=a" (low), "=d" (high)); + tsc = ((unsigned long long) high << 32) | low; + return tsc; } static volatile int nosignal = 0; @@ -34,13 +37,9 @@ static void sighandler(int sig __attribute__((unused))) void estimate_MHz(struct cpudata *cpu) { cpu_set_t set; - struct timezone tz; - struct timeval tvstart, tvstop; unsigned long long int cycles[2]; /* gotta be 64 bit */ - unsigned long microseconds; /* total time taken */ unsigned int eax, ebx, ecx, edx; - unsigned long freq = 1; - unsigned long i; + unsigned long r; /* Make sure we have a TSC (and hence RDTSC) */ cpuid(cpu->number, 1, &eax, &ebx, &ecx, &edx); @@ -50,8 +49,6 @@ void estimate_MHz(struct cpudata *cpu) return; } - memset(&tz, 0, sizeof(tz)); - if (sched_getaffinity(getpid(), sizeof(set), &set) == 0) { CPU_ZERO(&set); CPU_SET(cpu->number, &set); @@ -64,25 +61,19 @@ void estimate_MHz(struct cpudata *cpu) } cycles[0] = rdtsc(); - gettimeofday(&tvstart, &tz); - alarm(3); - while (!nosignal) { - i = i * rand(); - } + alarm(1); + while (!nosignal) + r = r * rand(); - cycles[1] = rdtsc(); - gettimeofday(&tvstop, &tz); + nosignal = 0; - microseconds = ((tvstop.tv_sec-tvstart.tv_sec)*1000000) + - (tvstop.tv_usec-tvstart.tv_usec); + cycles[1] = rdtsc(); - cpu->MHz = (int) (cycles[1]-cycles[0]) / (microseconds/freq); + cpu->MHz = (cycles[1] - cycles[0]) / 1000000; if ((cpu->MHz % 50) > 15) cpu->MHz = ((cpu->MHz / 50) * 50) + 50; else cpu->MHz = ((cpu->MHz / 50) * 50); - - nosignal = 0; } |