私は別のキャッシュレベルにメモリアクセスの正確な測定をしようと、プロービングのために、このコードを思いついたんだ:RDTSCとRDTSCPによる正確なメモリアクセス時間のプロービング?
__asm__ __volatile__(
"xor %%eax, %%eax \n"
"xor %%edi, %%edi \n"
"xor %%edx, %%edx \n"
/* time measurement */
"lfence \n"
"rdtsc \n"
"shl $32, %%rdx \n"
"or %%rdx, %%rax \n"
"movq %%rax, %%rdi \n"
/* memory access */
"movq (%%rsi), %%rbx\n"
/* time measurement */
"rdtscp \n"
"shl $32, %%rdx \n"
"or %%rdx, %%rax \n"
"movq %%rax, %%rsi \n"
"cpuid \n"
: /* output operands */
"=S"(t2), "=D"(t1)
: /* input operands */
"S" (mem)
: /* clobber description */
"ebx", "ecx", "edx", "cc", "memory"
);
L1およびL2キャッシュへのアクセスは、わずか8サイクルと結果によって異なりますが
./cache_testing
From Memory: 42
From L3: 46
From L2: 40
From L1: 38
./cache_testing
From Memory: 40
From L3: 38
From L2: 36
From L1: 40
:
__asm__ __volatile__(
"xor %%eax, %%eax \n"
"xor %%edi, %%edi \n"
"xor %%edx, %%edx \n"
/* time measurement */
"lfence \n"
"rdtsc \n"
"shl $32, %%rdx \n"
"or %%rdx, %%rax \n"
"movq %%rax, %%rdi \n"
/* memory access */
//"movq (%%rsi), %%rbx\n"
/* time measurement */
"rdtscp \n"
"shl $32, %%rdx \n"
"or %%rdx, %%rax \n"
"movq %%rax, %%rsi \n"
"cpuid \n"
: /* output operands */
"=S"(t2), "=D"(t1)
: /* input operands */
"S" (mem)
: /* clobber description */
"ebx", "ecx", "edx", "cc", "memory"
);
結果、このように見えた:はるかに変動しているので、私はタイミングを有するどの程度影響(離れて実際のメモリアクセスからの)周囲のコードをチェックすることを決めました
現時点で目的によって異なるキャッシュレベルにヒットしていないことは知っていますが、メモリアクセスが不足している場合のタイミングがどうしてそんなに変動しているのだろうと思います。 コードは最高優先順位のSCHED_FIFOとして実行され、1つのCPUに固定されており、実行中はディスパッチしないでください。 私のコードを改善して、それによって結果を改善できるかどうかは誰にでも分かりますか?
[Hasner Fogのmicroarch pdf](http://agner.org/optimize/)によると、Has Haswellのキャッシュ負荷 - >使用待ち時間の正確な数値は、L1では4c、L2では12cです。これを測定するための素晴らしい方法(特にL1の場合)は、ポインタを追うことです。 L1の場合は、それ自身を指すポインタを設定し、ループ内で 'mov(%rax)、%rax'を実行してください。 L2の場合、L1に収まらない大きなリンクリストが必要です。 –