x86 movdqu 命令 (movdqu 命令は、xmm- との間の 16 バイト データの移動をサポートします) を使用して、あるソース メモリ ロケーションからある宛先メモリ ロケーションに反復ごとに 64 バイトを移動するループで見られる結果の説明を求めています。整列されていないメモリ位置との間のレジスタ)。これは、memcpy()/java.lang.System.arraycopy() に似た関数を実装するコードの一部です。
コピーを実装しようとした 2 つの異なるパターンがあります。
パターン1
0x30013f74: prefetchnta BYTE PTR [rsi]
0x30013f77: prefetchnta BYTE PTR [rdi]
0x30013f7a: movdqu xmm3, XMMWORD PTR [rsi+0x30]
0x30013f7f: movdqu xmm2, XMMWORD PTR [rsi+0x20]
0x30013f84: movdqu XMMWORD PTR [rdi+0x30],xmm3
0x30013f89: movdqu XMMWORD PTR [rdi+0x20],xmm2
0x30013f8e: movdqu xmm1, XMMWORD PTR [rsi+0x10]
0x30013f93: movdqu xmm0, XMMWORD PTR [rsi]
0x30013f97: movdqu XMMWORD PTR [rdi+0x10], xmm1
0x30013f9c: movdqu XMMWORD PTR [rdi], xmm0
このパターンでは、rsi はソース (src) アドレスを保持し、rdi は宛先 (dst) アドレスを保持し、xmm レジスターは一時レジスターとして使用されます。このコードは、copylen_in_bytes/64 回繰り返されます。ご覧のとおり、ここでは ld-ld-st-st-ld-ld-st-st ロード-ストア パターンに従います。
パターン2
0x30013f74: prefetchnta BYTE PTR [rsi]
0x30013f77: prefetchnta BYTE PTR [rdi]
0x30013f7a: movdqu xmm3, XMMWORD PTR [rsi+0x30]
0x30013f7f: movdqu XMMWORD PTR [rdi+0x30], xmm3
0x30013f84: movdqu xmm2, XMMWORD PTR [rsi+0x20]
0x30013f89: movdqu XMMWORD PTR [rdi+0x20], xmm2
0x30013f8e: movdqu xmm1, XMMWORD PTR [rsi+0x10]
0x30013f93: movdqu XMMWORD PTR [rdi+0x10], xmm1
0x30013f98: movdqu xmm0, XMMWORD PTR [rsi]
0x30013f9c: movdqu XMMWORD PTR [rdi], xmm0
pattern2 では、ld-st-ld-st-ld-st-ld-st パターンに従います。
観察
このコードを数百回実行すると、src と dst がさまざまな 8 バイト境界で整列され、次のことがわかります。
Westmere の場合 (Xeon X5690)
パターン 1 は、実行ごとに非常に高い分散を示します。
パターン 2 はほとんど分散を示しません。
パターン 2 の最小時間 (観測された最速時間) は、パターン 1 の最小時間よりも (~8%) 長くなります。
Ivybridge で (Xean E5-2697 v2)
パターン 1 は、実行ごとに非常に高い分散を示します。
パターン 2 はほとんど分散を示しません。
パターン 2 の最小時間は、パターン 1 の最小時間よりも高くなっています (~20%)。
ハスウェル (Core i7-4770)
パターン 1 は、非常に高い実行ごとの分散を示しません。
パターン 2 はほとんど分散を示しません。
パターン 2 の最小時間は、パターン 1 の最小時間よりも高くなっています (~20%)。
奇妙なことに、Westmere と Ivybridge では、src/dest のアラインメントと悪い結果 (高い分散の原因) との間に相関関係がないようです。同じ src/dest アラインメントに対して良い数値と悪い数値が表示されます。
質問
キャッシュラインにまたがる movdqu のパフォーマンスが、キャッシュラインにまたがらない movdqu よりも悪いことは理解していますが、次のことはわかりません。
1) パターン 1 が Westmere と Ivybridge で高い分散を示すのはなぜですか? ロードストアの順序はどのように違いますか?
2) 異なるアーキテクチャ間で、パターン 2 の最小時間がパターン 1 よりも遅いのはなぜですか?
この長い投稿をお読みいただきありがとうございます。
カーシック