这是我用 C 编写的程序。
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <stdint.h>
static int DATA[1024]={1,2,3,4,.....1024};
inline void foo_0(void)
{
int j;
puts("Hello, I'm inside foo_0");
int k=0;
for(j=0;j<1024;j++)
{
//k=DATA[j];
DATA[j]+=1;
}
k+=0;
}
inline void foo_1(void)
{
int j;
puts("Hello, I'm inside foo_1");
int k=0;
for(j=0;j<1024;j+=4)
{
//k=DATA[j];
DATA[j]+=1;
}
k+=0;
}
inline void foo_2(void)
{
int j;
puts("Hello, I'm inside foo_2");
int k=0;
for(j=0;j<1024;j+=16)
{
//k=DATA[j];
DATA[j]+=1;
}
k+=0;
}
inline uint64_t rdtsc()
{
unsigned long a, d;
asm volatile ("cpuid; rdtsc" : "=a" (a), "=d" (d) : : "ebx", "ecx");// core i3/i7
return a | ((uint64_t)d << 32);
}
inline void clflush(volatile void *p)
{
asm volatile ("clflush (%0)" :: "r"(p));
}
int main(void)
{
volatile uint64_t start, end,temp;
unsigned long long total_time=0;
foo_0(); // This will load DATA array into memory
foo_1(); // DATA already loaded into memory
foo_2(); // DATA already loaded into memory
printf("**********************\n");
start=rdtsc();
foo_2();
end=rdtsc();
temp=end-start;
total_time=temp;
printf("Time taken foo_2 = %llu\n",total_time);
start=rdtsc();
foo_1();
end=rdtsc();
temp=end-start;
total_time=temp;
printf("Time taken foo_1 = %llu\n",total_time);
start=rdtsc();
foo_0();
end=rdtsc();
temp=end-start;
total_time=temp;
printf("Time taken foo_0 = %llu\n",total_time);
return 0;
}
输出:
Hello, I'm inside foo_0
Hello, I'm inside foo_1
Hello, I'm inside foo_2
**********************
Hello, I'm inside foo_2
**Time taken foo_2 = 6350**
Hello, I'm inside foo_1
**Time taken foo_1 = 10056**
Hello, I'm inside foo_0
**Time taken foo_0 = 21726**
编辑 1:
当我从所有三个函数中删除 puts() 时,我得到了这个结果
Time taken foo_0 = 16448
Time taken foo_1 = 4438
**********************
Time taken foo_2 = 1548
我期望所有三个 foo_0、foo_1 和 foo_2 的访问时间相同,因为当访问内存以访问一个整数时,整个缓存 block 被加载(64 字节是 block 大小,所以 16 个整数是加载到缓存 block 中),因此 1、4、16 整数的访问时间必须相同。我不明白那个。我在哪里犯错? 我在linux下使用gcc。提前致谢 。
编辑 2
根据 BЈовић 的回答和 Leeor 在评论中的建议,执行时间必须不同,因为在三个不同的函数中执行的加法运算次数不同。虽然在所有三种情况下都没有未命中,但是加法运算的执行次数各不相同,并且对于所有操作数据都是从缓存访问的(*不是从主内存*正如我所怀疑的那样)总时间取决于对数组执行的加法操作的数量,而不是缓存未命中/命中。所以我接受 BЈовић 的回答和 Leeor 的建议。谢谢大家。
最佳答案
1) 您的进程正在被其他进程推到后台,因此无法获得准确的时间。
2) 由于循环不同,时间不可能相同:
foo_0() : for(j=0;j<1024;j++)
foo_1():for(j=0;j<1024;j+=4)
foo_2() : for(j=0;j<1024;j+=16)
关于c - 使用 RDTSC 访问内存中的 ARRAY 时在 C 中出现意外输出,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21671521/