次のループは何百回も実行されます。
elma and elmc are both unsigned long (64-bit) arrays, so is res1 and res2.
unsigned long simdstore[2];
__m128i *p, simda, simdb, simdc;
p = (__m128i *) simdstore;
for (i = 0; i < _polylen; i++)
{
u1 = (elma[i] >> l) & 15;
u2 = (elmc[i] >> l) & 15;
for (k = 0; k < 20; k++)
{
1. //res1[i + k] ^= _mulpre1[u1][k];
2. //res2[i + k] ^= _mulpre2[u2][k];
3. _mm_prefetch ((const void *) &_mulpre2[u2][k], _MM_HINT_T0);
4. _mm_prefetch ((const void *) &_mulpre1[u1][k], _MM_HINT_T0);
5. simda = _mm_set_epi64x (_mulpre2[u2][k], _mulpre1[u1][k]);
6. _mm_prefetch ((const void *) &res2[i + k], _MM_HINT_T0);
7. _mm_prefetch ((const void *) &res1[i + k], _MM_HINT_T0);
8. simdb = _mm_set_epi64x (res2[i + k], res1[i + k]);
9. simdc = _mm_xor_si128 (simda, simdb);
10. _mm_store_si128 (p, simdc);
11. res1[i + k] = simdstore[0];
12. res2[i + k] = simdstore[1];
}
}
for ループ内では、スカラー バージョンのコード (コメント付き) は、simd コードよりも 2 倍速く実行されます。上記の行の cachegrind 出力 (命令読み取り) を以下に示します。
行1:668,460,000 2 2 2
行目2行目:668,460,000 1 1
行3:89,985,000 1 1
行4:89,985,000 1 1
行
5
:617,040,000 2 2 2
行6:44,992,500 0 0
行7:44,992,500 0 : 128,550,000 0 0
行 10: 。. .
11 行目: 205,680,000 0 0
12 行目: 205,680,000 0 0
上の図から、コメント化された (スカラー コード) は、simd コードよりもはるかに少ない数の命令を必要とするように見えます。
このコードを高速化するにはどうすればよいですか?