您能告诉我如何使用clflush()说明吗?我编写了以下简单代码来测量从缓存中读取变量的执行时间与从缓存中驱逐变量之间的差异。但是我没有找到确凿的结果。使用clflush()驱逐缓存的正确方法是什么?
#include <stdio.h>
#include <stdint.h>
#include"cpucycles.c"
#define REPEAT 1900000
inline void clflush(volatile void *p)
{
asm volatile ("clflush (%0)" :: "r"(p));
}
inline uint64_t rdtsc()
{
unsigned long a, d;
asm volatile ("cpuid; rdtsc" : "=a" (a), "=d" (d) : : "ebx", "ecx");
return a | ((uint64_t)d << 32);
}
volatile int i;
inline void test()
{
uint64_t start, end,clock;
volatile int j;
long int rep;
int k;
clock=0;
for(rep=0;rep<REPEAT;rep++){
start = rdtsc();
j = i+1;
end = rdtsc();
clock=clock+(end-start);
k=j;
}
printf("took %lu ticks\n", clock);
}
inline void testflush()
{
uint64_t start, end,clock;
volatile int j;
int k;
long int rep;
clock=0;
for(rep=0;rep<REPEAT;rep++){
start = rdtsc();
j = i+1;
end = rdtsc();
clflush(&i);
clock=clock+(end-start);
k=j;
}
printf("took %lu ticks\n", clock);
}
int main(int ac, char **av)
{
i=5;
printf("------------------------------------------\n");
test();
printf("------------------------------------------\n");
testflush();
printf("------------------------------------------\n");
test();
return 0;
}
答案 0 :(得分:0)
看起来你的“同花”时间被其余代码所淹没。另外,如你所写的非刷新执行更少的代码行(没有刷新),使得比较“不公平”。
更像是什么:
#include <stdio.h>
#include <stdint.h>
#include <malloc.h>
#include <emmintrin.h>
#define REPEAT 1900000
volatile int i;
inline void test(void *v)
{
uint64_t start, end;
volatile int j;
long int rep;
int k;
start = __builtin_ia32_rdtsc();
for(rep=0;rep<REPEAT;rep++){
j = i+1;
_mm_clflush(v);
k=j;
}
end = __builtin_ia32_rdtsc();
printf("%p took %lu ticks\n", v, end-start);
}
int main(int ac, char **av)
{
void *v = malloc(1000);
i=5;
printf("------------------------------------------\n");
test(v);
printf("------------------------------------------\n");
test((void *)&i);
printf("------------------------------------------\n");
test(v);
free(v);
return 0;
}
通过这种方式,我们总是冲洗一些东西,但是一个测试会影响你的全局,另一个则不会。它也不使用任何内联asm。
使用-O3构建,这给出了非冲洗时的149次和冲洗时的312次。