以下循環執行數百次。
elma and elmc are both unsigned long (64-bit) arrays, so is res1 and res2.
SIMD代碼和標量代碼
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代碼快兩倍。以上提到的cachegrind輸出(指令讀取)如下。
第1行:668460000 2 2
第2行:668460000 1 1
第3行:89985000 1 1
第4行:89985000 1 1
第5行:617040000 2 2
第6行:44992500 0 0
第7行:44992500 0 0
第8行:539910000 1 1
第9行:128550000 0 0
第10行:。 。 。
第11行:205680000 0 0
第12行:205680000 0 0
從上面的圖,它顯示了註釋(標量的代碼)需要更少顯著比SIMD代碼指令數目。
這段代碼如何能更快?
這是你自己問題的重複。回到那裏,理解爲什麼這個答案(而不是你標記爲正確的答案)解決了這個問題:http://stackoverflow.com/questions/4394930/simd-code-runs-slower-than-scalar-code/4395337# 4395337 – 2010-12-09 12:27:29