1

L1 キャッシュ サイズ 32KB、L2 キャッシュ サイズ 256KB、共有 L3 キャッシュ サイズ 8MB (4 コア間で共有) のコア i7 システムがあります。パート A、B、C を順番に実行するプログラムを作成しました。(A) L2 キャッシュの 4 倍のサイズの大きな int 配列を作成し、大きな配列の 16 番目ごとの要素 (キャッシュ ライン サイズは 64B、16*4 B=64B) にアクセスして、すべてのデータが L2 にロードされるようにします。大きな配列 (B) のすべての要素のアクセス時間を書き留めてから、clflush を使用して、clflush(&bigarray[0]) ...clflush (&bigarray[1024]) のように、データ配列の複数の場所から手動でデータを削除します。(C) (B) で手動で削除された行を含む大きな配列の 16 番目ごとの要素に再度アクセスします。

アクセス時間を見つけるために、大きな配列にアクセスしている行の前後に rdtsc() を配置しました。i3 または i7 プロセッサのこのリンク clflush()から、i3/i7 マシンでの clflush の使用を知りました。

asm volatile ("cpuid; rdtsc" : "=a" (a), "=d" (d) : : "ebx", "ecx");

予想通り、単一の回線の立ち退き後のアクセス時間が長くなりましたが、驚いたことに、複数の場所へのアクセス時間は増えていません。

別の方法で説明しましょう。

シナリオ1 : clflush の前後に単一の配列要素にアクセスする

  • step1- (a[x]) にアクセスし、アクセス時間を見つける
  • step2- clflush(&a[x]) を使用してキャッシュから削除し、アクセス時間を見つけます

シナリオ2 : clflush の前後に複数の配列要素にアクセスする

  • step1- 配列の各要素 a[i] にアクセス
  • ステップ2-

    for all i { 
        clflush( &a[i]) } to evict from cache and find access time of all elements at i.
    

シナリオ 1 のように期待どおりの結果が得られましたが、clflush 後に配列要素にアクセスするためのアクセス時間が長くなりません。

理由は何ですか ?立ち退き後の正しいアクセス時間を知る方法。ハードウェアとソフトウェアのプリフェッチについて聞いたことがありますが、結果に影響していますか? その影響を克服し、正しい結果を知る方法は?

4

1 に答える 1