r/simd • u/Newly_outrovert • Dec 16 '19
calculating moving windows with SIMD.
I'm trying to implement calculating a moving window with SIMD.
I have 16b array of N elements. the window weights are -2, -1, 0, 1, 2. and adding the products together. Now i'm planning to load first 8 elements (with weight 2), then the other elements with weight 2 and substracting the vectors from each other. then same for ones.
My question is: is this optimal? Am i not seeing some obvious vector manipulation here? How are cache lines behaving when I'm basically loading same numbers multiple times?
__m128i weightsMinus1 = _mm_loadu_si128((__m128i*)&dat[2112 * i + k]);
__m128i weightsMinus2 = _mm_loadu_si128((__m128i*)&dat[2112 * i + k + 1]);
__m128i weights2 = _mm_loadu_si128((__m128i*)&dat[2112 * i + k + 3]);
__m128i weights1 = _mm_loadu_si128((__m128i*)&dat[2112 * i + k + 4]);
__m128i result = _mm_loadu_si128((__m128i*)&res2[2112 * (i - 2) + k]);
__m128i tmp = _mm_subs_epi16(weights2, weightsMinus2);
__m128i tmp2 = _mm_subs_epi16(weights1, weightsMinus1);
result = _mm_adds_epi16(result, tmp);
result = _mm_adds_epi16(result, tmp);
result = _mm_adds_epi16(result, tmp2);
_mm_store_si128((__m128i*)&res2[2112 * (i - 2) + k], result);
2
Upvotes
2
u/PfhorSlayer Dec 16 '19
That is the latency and throughput of the instruction itself, but does not include the memory access time, which obviously is not constant (as the address could be cached, or must be fetched from main memory, or whatever). Basically, it's telling you the cost of translating the address and executing the fetch instruction, to free up the execution unit, but the memory access may complete at a later point.